2014-11-20 84 views
1

在以下C++代码,我试图从共享库加载函数。Segfault转换指针与reinterpret_cast

void* tmp = dlsym(dl_lib, symbol); 
_fun = reinterpret_cast<plot_sample_fun*>(tmp); 

但是,在转换指针时reinterpret_cast段错误。这里有什么问题?

编辑:

为了提供进一步的上下文中,

typedef void plot_sample_fun(const void *, double **, char ***, size_t *); 

class Foo { 
    void bar(); // Loads _fun as above. 

    plot_sample_fun* _fun; 
}; 
+1

您可以阅读http://stackoverflow.com/questions/310451/should-i-use-static-cast-or-reinterpret-cast-when-casting-a-void-to-whatever – chrizke 2014-11-20 19:02:42

+3

什么是_fun? reinterpret_cast不会自行执行例外。它只会迫使编译器相信指针是某种类型的。但是,段错误是关于将指针存储在其他一些内存位置。 – AlexanderVX 2014-11-20 19:06:34

+1

它确实是segfaults的'reinterpret_cast',而不是以后使用的指针?为什么你不检查它不是null? – 2014-11-20 19:09:18

回答

2

指针物理上只是一个包含某个地址的整型变量。

reinterpret_cast只是让编译器相信指针是特定类型的技巧。

在上面的代码示例中,段错误的唯一可能性是第一行,但作者说第二行,或者第二行,原因是_fun是某种悬挂引用,因此它写入不正确的内存位置。

笔者更新我们的指针类型后,它更清楚正确的代码应该是这样的:

typedef void (plot_sample_fun*)(const void *, double **, char ***, size_t *); 

而且分配:

_fun = reinterpret_cast<plot_sample_fun>(tmp); 

和类成员声明不应该有星号*

plot_sample_fun _fun; 

如果这没有帮助,那么我们想知道是否实例o包含_fun的f类已正确分配,尚未发布。

+0

你的后一种解释很有希望,但我怎样才能解决这个悬而未决的参考?我用更多的上下文更新了我的问题。 – ehuang 2014-11-20 23:45:28

+0

Eric,请让我们知道_fun变量是什么。 – AlexanderVX 2014-11-20 23:46:17

+0

它是typedef plot_sample_fun中的类型。 – ehuang 2014-11-20 23:48:07

2

reinterpret_cast本身不能段错误,因为它仅改变用于编译器的表达式的类型。 它被编译掉并且在运行时上不做任何事情(不像例如dynamic_cast)。

什么是失败是您在程序中稍后使用指针。

与static_cast不同,但像const_cast会,使用reinterpret_cast表达不编译任何CPU指令

我建议编译与调试的程序中关闭on(-g with gcc/clang),然后在调试器中运行它,查看实际失败的内容。