【发布时间】:2017-09-13 04:18:14
【问题描述】:
我有两个自己的库,例如“IDA”和“XIDA”。并且我想让它们通过回调函数一起通信。
国际开发协会:
ida.h, ida.cpp, ida_a.h, ida_a.cpp
西达:
xida.h, xida.cpp, xida_a.h, xida_a.cpp
国际开发协会:
ida_a.h:
class IDA_A
{
private:
XIDA *mXIDA;
public:
static int IDA_Callback(void* this_ptr, void *vPara ){
std::cout << "IDA -- " << "INCOMING CALLBACK == NULL" << std::endl;
}
}
ida_a.cpp:
void IDA_A::Init(std::string vIdent){
this->mXIDA = new XIDA( (void*) &this->IDA_Callback);
}
现在西达:
xida.h:
class XIDA{
public:
XIDA(void *vPara);
};
xida.cpp:
XIDA_A m_XIDA_A;
XIDA::XIDA(void *vPara){
std::cout << "TEST XIDA ---- A" << std::endl;
m_XIDA_A.Init(vPara);
}
xida_a.h:
typedef int(*IDACallback) (void*, void*);
class XIDA_A{
private:
IDACallback mIDACallback;
public:
void Init(void *vPara);
}
xida_a.cpp:
1 void XIDA_A::Init(void *vPara){
2 int nErr = 0;
3 cout << "XIDA -- INIT A ************************************************** " << vPara << endl;
4 try{
5 this->mIDACallback = *static_cast < IDACallback* > (vPara);
6 } catch (...){
7 nErr = 1;
8 }
9 if(nErr == 0){
10 cout << "XIDA -- INIT B ************************************** " << this->mIDACallback << endl;
11 this->mIDACallback(NULL, NULL); // <------ HERE IS THE ERROR
12 }
13 }
正常调用时(通过终端和路径/bin),错误是:
Speicherzugriffsfehler (engl. memory access error <?>)
使用 Valgrind:
XIDA -- INIT A ************************************************** 0x4e40a19
XIDA -- INIT B ************************************** 1
==20001== Jump to the invalid address stated on the next line
==20001== at 0x20EC8348E5894855: ???
==20001== by 0x504C690: XIDA::XIDA(void*) (xida.cpp:10)
==20001== by 0x4E405CB: IDA_A::Init(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >) (ida_a.cpp:37)
==20001== by 0x4E3FE9F: IDA::IDA(char const*) (ida.cpp:13)
==20001== by 0x401932: main (main.cpp:13)
==20001== Address 0x20ec8348e5894855 is not stack'd, malloc'd or (recently) free'd
所以,现在我知道错误在哪里,但我不知道如何解决它。
【问题讨论】:
-
请尝试制作一个完整的(可编译的)示例。例如,类中缺少
IDA_A:: init ()的声明。 -
要解决此问题,请将所有
void *s 替换为适当的类型,并让编译器为您找到真正的错误,由于传递了错误的对象,这很可能表现为编译错误通过以前不透明的void *。在现代 C++ 中,很少有情况仍然需要使用void *s。 -
如果不使用魔法、精神力量或猜测,就无法在当前状态下回答问题。请组装一个minimal reproducible example。题外话,这段代码忽略了 C++ 的一些基本原则,从而引发了很多可能的错误。
-
@Sam Varshavchik:正如我之前已经写过的,我将 void* paras 更改为回调的 typedef,这是有效的。但我仍然想知道如何让它与 void* 一起工作。解决方案是,我可以使用“this->mIDACallback = (IDACallback) vPara;”而不是“this->mIDACallback = static_cast > (*vPara);”。你让我明白了。谢谢你,先生!
标签: c++ callback shared-libraries