这种类型转换是否正确?

时间:2012-12-02 16:50:32

标签: c haskell shared-libraries

基本上我的代码在NucleoProf_init中崩溃,通过gdb的堆栈跟踪判断,以及这是我调用的唯一函数。

#include <HsFFI.h>

static char *argv[] = {"NucleoProf", "", "", 0};
static int argc = 1;

HsBool NucleoProf_init(void){

   // Initialize Haskell runtime
   hs_init(&argc,  (char***)&argv );

   return HS_BOOL_TRUE;
}

我怀疑这是我传递argv参数的方式,或者是argv的类型转换,因为堆栈跟踪包含以下内容:

#3  0x00007ffff5956282 in setFullProgArgv ()
    from /usr/lib/ghc/libHSrts-ghc7.4.1.so
#4  0x00007ffff5956d04 in hs_init_ghc () from /usr/lib/ghc/libHSrts-ghc7.4.1.so
#5  0x00007ffff5b9ed4f in NucleoProf_init ()

问题:这是“合成”一个简单的命令行的正确方法吗?

2 个答案:

答案 0 :(得分:4)

你可以试试这个:

char ** p = argv;
hs_init(&argc, &p);

目前还不清楚为什么你需要按地址传递数组,但我不知道你正在使用的API。仔细检查手册,看看这些值是否可以被函数更改,以及之后是否需要处理它们。

答案 1 :(得分:2)

这是错误的,因为,首先,它是错误的类型。获取数组的地址会产生指向数组的指针。 &argv具有类型char *(*)[4],即“指向char的4个指针数组的指针”。这不是您想要的char ***类型。您强行将其强制转换为隐藏类型不兼容。

您想要一个char ***,它是指向实际char **变量的指针。但是你在任何地方都没有char **变量。您有argvchar *[4]变量,这是完全不同的。数组变量就是 - 它在内存中按顺序排列的元素集合;内存中任何地方都没有存储任何地址。

你的根本混淆可能是数组不是指针这一事实。数组具有不同的大小(数组的大小是其长度乘以其组件类型的大小),指针和数组类型(指向数组的指针与指向指针的指针非常不同;与数组数组和指针数组相同)和语义(数组不能分配或传递)。在某些情况下,数组表达式可以隐含地降级到指针rvalue;但在这种情况下,您正在使用需要左值的地址,因此不适用。永远不要将数组与指针混淆。