< 返回版块

allwefantasy 发表于 2019-04-21 10:37

Tags:Rust,C,FFI,Struct,Pointer

I have desigh a Ctensor.

#[repr(C)]
pub struct CTensor {
    data: *const c_float,
    data_length: c_int,
    shape: *const c_int,
    shape_length: c_int,
}

and provide a function to create this struct:

#[no_mangle]
pub extern "C" fn create_tensor(data: *const c_float,
                                data_length: c_int,
                                shape: *const c_int,
                                shape_length: c_int, ) -> *mut CTensor {
    let ctensor = CTensor {
        data,
        data_length,
        shape,
        shape_length,
    };

    println!("create_tensor data: {:?} len:{:?}", unsafe { *ctensor.data }, ctensor.data_length);
    println!("create_tensor shape: {:?} len:{:?}", unsafe { *ctensor.shape }, ctensor.shape_length);

    Box::into_raw(Box::new(ctensor))
}

Then I call create_tensor in C side:

CTensor *xTensor = create_tensor(xP, 1, shape_x_p, 1);
CTensor *yTensor = create_tensor(yP, 1, shape_y_p, 1);

printf("-----%s------\n", "jack coo");
printf("CTensor in c data:%f len:%i \n", xTensor->data, xTensor->data_length);
printf("CTensor in c shape:%f len:%i \n", xTensor->shape, xTensor->shape_length);

In rust side, the resul is right:

create_tensor data: 1.0 len:1
create_tensor shape: 1 len:1
create_tensor data: 2.0 len:1
create_tensor shape: 1 len:1

But in C side, it's not work:

CTensor in c data:0.000000 len:-327289448
CTensor in c shape:0.000000 len:-327289476

And i still do no get point why it not work.

评论区

写评论
Mike Tang 2019-04-21 17:40

nice.

作者 allwefantasy 2019-04-21 11:01

补充:

修改uint32_t 为int32_t,然后打印的地方改成:

printf("-----%s------\n", "jack coo");
    printf("CTensor in c data:%f len:%d \n", *xTensor->data, xTensor->data_length);
    printf("CTensor in c shape:%f len:%d \n", *xTensor->shape, yTensor->shape_length);

    printf("CTensor in c data:%f len:%d \n", *yTensor->data, yTensor->data_length);
    printf("CTensor in c shape:%f len:%d \n", *yTensor->shape, yTensor->shape_length);

然后就work了。

作者 allwefantasy 2019-04-21 10:39

here is the all c code, if this helps:

##predictor.h

//
// Created by 祝 海林 on 17/4/2019.
//

#ifndef RUST_TF_PREDICTOR_PREDICTOR_H
#define RUST_TF_PREDICTOR_PREDICTOR_H

#include <stdint.h>

typedef struct Predictor_S Predictor_t;
typedef struct RawTensor RawTensor;

typedef struct CTensor {
    const float *data;
    uint32_t data_length;
    const uint32_t *shape;
    uint32_t shape_length;
} CTensor;

typedef struct CTensorArray {
    CTensor *data;
    uint32_t len;
} CTensorArray;


//typedef struct CTensorArray CTensorArray;

CTensor *create_tensor(float *data, uint32_t data_length, uint32_t *shape, uint32_t shape_length);

CTensorArray *create_tensor_array(CTensor *data, uint32_t len);

Predictor_t *load(char exported_dir[]);

CTensor *to_tensor(RawTensor *tensor);

RawTensor *predict(Predictor_t *predictor, char *output_name[], char *input_names[], CTensorArray *input_values);

#endif //RUST_TF_PREDICTOR_PREDICTOR_H

main.c:

//
// Created by 祝 海林 on 17/4/2019.
//
#include <stdint.h>
#include <stdio.h>
#include <predictor.h>
#include <stdlib.h>
#include "../src/predictor.h"


int main() {
    char path[] = "test_resources/regression-model";
    //Predictor_t *pre = load(path);

    float x[] = {1.0f};
    float y[] = {2.0f};

    float *xP;
    xP = x;
    float *yP;
    yP = y;


    uint32_t shape_x[] = {1};
    uint32_t shape_y[] = {1};

    uint32_t *shape_x_p;
    shape_x_p = shape_x;

    uint32_t *shape_y_p;
    shape_y_p = shape_y;

    CTensor *xTensor = create_tensor(xP, 1, shape_x_p, 1);
    CTensor *yTensor = create_tensor(yP, 1, shape_y_p, 1);

    printf("-----%s------\n", "jack coo");
    printf("CTensor in c data:%f len:%i \n", xTensor->data, xTensor->data_length);
    printf("CTensor in c shape:%f len:%i \n", xTensor->shape, xTensor->shape_length);


    CTensor *xy[] = {xTensor, yTensor};

    CTensor *xy_p;
    xy_p = xy;



//    CTensorArray *tarray = create_tensor_array(xy_p, 2);
//
//
//    RawTensor *wow = predict(pre, "y_hat", "x,y", tarray);
//    CTensor *res = to_tensor(wow);
//    int loop;
//
//    for (loop = 0; loop < res->data_length; loop++)
//        printf("%f \n", res->data[loop]);

    return 0;
}


1 共 3 条评论, 1 页