2017-01-16 93 views
0

问题如上所述。当我尝试读取加载的* .so文件(使用libdl)值,whih在结构我得到错误的价值观 代码应用:C++从结构数组中得到了错误的值

#include <dlfcn.h> 
#include <iostream> 

/* For face data type reproduction */ 
#define GET_FACE_XYZ_SIZE 1 
/* For face_array reproduction */ 
#define GET_FACE_ARRAY_SIZE 2 
#define GET_OBJECT_DATA 3 

typedef struct face { 
    float x[1000]; 
    float y[1000]; 
    float z[1000]; 
    int vertices; 
} face; 


int main() 
{ 
    void *hook; 
    int (*fn)(int request_type, void *ptr); 
    hook = dlopen("/root/osms/dlopen-test/lib.so", RTLD_LAZY); 
    if(!hook) 
    { 
     std::cout << "Couldn't find lib.so" << std::endl; 
    } 
    fn = dlsym(hook, "object_info"); 
    int face_array_size = fn(GET_FACE_ARRAY_SIZE, NULL); 
    std::cout << "FACE_ARRAY_SIZE: " << face_array_size << std::endl; 
    face pointer[face_array_size]; 
    fn(NULL, pointer); 
    dlclose(hook); 
    std::cout << "pointer[0].z[1]: " << pointer[0].z[1] << std::endl; 
return 0; 
} 

和lib.so代码:

/* For face data type reproduction */ 
#define GET_FACE_XYZ_SIZE 1 
/* For face array reproduction */ 
#define GET_FACE_ARRAY_SIZE 2 
#define GET_OBJECT_DATA 3 

typedef struct face { 
    float x[1000]; 
    float y[1000]; 
    float z[1000]; 
    int vertices; 
} face; 

extern "C" int object_info(int request, void *ptr) 
{ 
    face face_array[2]; 
    face_array[0].x[0] = 1.1; 
    face_array[0].y[0] = 0.5; 
    face_array[0].z[0] = 1.2; 
    face_array[0].x[1] = 1.6; 
    face_array[0].y[1] = -0.11; 
    face_array[0].z[1] = -12; 
    face_array[0].x[2] = -0.12; 
    face_array[0].y[2] = 0.24; 
    face_array[0].z[2] = -0.12; 
    face_array[0].vertices = 3; 

    face_array[1].x[0] = -1.1; 
    face_array[1].y[0] = 0.15; 
    face_array[1].z[0] = -1.2; 
    face_array[1].x[1] = -1.6; 
    face_array[1].y[1] = 0.11; 
    face_array[1].z[1] = 1.2; 
    face_array[1].x[2] = 0.12; 
    face_array[1].y[2] = -0.24; 
    face_array[1].z[2] = 0.12; 
    face_array[1].vertices = 3; 

    if(request == GET_FACE_ARRAY_SIZE) 
    { 
     return 2; 
    } 
    else 
    { 
     ptr = face_array; 
    } 
} 

期望的输出是pointer[0].z[1]: -12但我得到pointer[0].z[1]: -0.12。我的代码有什么问题?

在此先感谢

回答

1

访问

pointer[0].z[1] 

是未定义行为,因为它有一个不确定的值。


object_info从未修改由ptr指向的数组。它只是修改本地数组,并指定本地ptr指向该本地数组。

解决方案:不要声明本地数组,而是修改参数指向的数组。换句话说,repace face face_array[2];有:

face* face_array = (face*)ptr; 

,摆脱,什么也不做有意义的ptr = face_array;的。


object_info声明为返回int,但并非所有的代码路径返回一个值。当函数在没有返回语句的情况下到达object_info的末尾时,行为是未定义的。

解决方案:如果函数不是void,则始终返回一个值。


face_array_size不是编译时间常数的值,所以将face pointer[face_array_size];声明一个可变长度数组。 VLA在C++中是不允许的。

既可以使用C(自C99以来支持VLA,但仅支持自C11以来的版本),也可以使用动态数组:std::vector<face>或者因为您的程序不符合标准而使用它们。

0

函数object_info中的变量“face_array”和main中的变量“pointer”不是同一个变量。 语句“ptr = face_array”不会更改“指针”的内容。

extern "C" int object_info(int request, face *face_array) 
{ 
if(request == GET_FACE_ARRAY_SIZE) 
    return 2; 
face_array[0].x[0] = 1.1; 
face_array[0].y[0] = 0.5; 
face_array[0].z[0] = 1.2; 
face_array[0].x[1] = 1.6; 
face_array[0].y[1] = -0.11; 
face_array[0].z[1] = -12; 
face_array[0].x[2] = -0.12; 
face_array[0].y[2] = 0.24; 
face_array[0].z[2] = -0.12; 
face_array[0].vertices = 3; 

face_array[1].x[0] = -1.1; 
face_array[1].y[0] = 0.15; 
face_array[1].z[0] = -1.2; 
face_array[1].x[1] = -1.6; 
face_array[1].y[1] = 0.11; 
face_array[1].z[1] = 1.2; 
face_array[1].x[2] = 0.12; 
face_array[1].y[2] = -0.24; 
face_array[1].z[2] = 0.12; 
face_array[1].vertices = 3; 

}