为什么这个简单的LinuxC程序加载会在运行时崩溃?

为什么这个简单的LinuxC程序加载会在运行时崩溃?,c,linux,shared-libraries,function-pointers,dlsym,C,Linux,Shared Libraries,Function Pointers,Dlsym,我正在尝试编写一个最小的程序,在运行时加载我的共享对象(.so) 不幸的是,它在运行时挂起,尽管执行了错误检查:-( 我对我在源代码级别忽略的内容非常感兴趣 下面是源代码和运行程序的shell会话 文件“libsample.c”: 我的shell会话日志: 有什么想法吗?在这里 (*symver)(); 代码取消引用作为要运行的库函数入口点接收的内容。这将解析为一个随机地址,在调用该地址时,通常会使程序崩溃 要解决此问题,请定义 sample_func_t symver = NULL; 其

我正在尝试编写一个最小的程序,在运行时加载我的共享对象(.so)

不幸的是,它在运行时挂起,尽管执行了错误检查:-(

我对我在源代码级别忽略的内容非常感兴趣

下面是源代码和运行程序的shell会话

文件“libsample.c”:

我的shell会话日志:

有什么想法吗?

在这里

 (*symver)();
代码取消引用作为要运行的库函数入口点接收的内容。这将解析为一个随机地址,在调用该地址时,通常会使程序崩溃

要解决此问题,请定义

sample_func_t symver = NULL;
其中,
samle\u func\t
已经是指针类型,因为

typedef void (*sample_func_t) (void);
(注意
*

然后有两种可能分配
symver

  • “脏”的那个

    “脏”,因为编译器可能会发出如下警告:

     ISO C forbids assignment between function pointer and ‘void *’
    
    symver(); /* No need to dereference here. */
    
  • “更干净”的那个

  • 最后调用如下函数:

     ISO C forbids assignment between function pointer and ‘void *’
    
    symver(); /* No need to dereference here. */
    

    另一方面,您确定要使
    stdout
    无缓冲吗?并且您确实知道
    stderr
    在默认情况下是无缓冲的吗?您是否检查了dlsym是否返回了非空值。如果返回空值,则不一定意味着错误-这意味着根本找不到符号。最坏的情况下,是多余的dlerror()调用将再次清除错误状态。我没有忘记在文件test.c第19..25行中使用Dleror()检查dlsym()状态。并且dlsym()调用返回值被分配给之前初始化为NULL的变量“symver”。读取此变量时,我得到了指针0x7f5e96df86f0(从一次运行更改为另一次运行),这显然不是空的。我不确定在这里调用我刚获得的入口点所使用的语法;请告诉我.Thx(注意,它是一个简单的void func_name(void)类东西的入口点。)妙招:愚蠢的手指!显然是第17行的错别字:多余的星号!当我从*(void*$#!(void))()…等不可读的东西切换到更可读的typedef时,这种错别字有时会发生在我身上。这与复制/粘贴错误的精神是一样的。
     symver = dlsym(h_lib, "sample_check");
    
     ISO C forbids assignment between function pointer and ‘void *’
    
     *(void**)(&symver) = dlsym(h_lib, "sample_check");
    
    symver(); /* No need to dereference here. */