由买买提看人间百态

boards

本页内容为未名空间相应帖子的节选和存档,一周内的贴子最多显示50字,超过一周显示500字 访问原贴
Programming版 - C++调用go函数出错,哪位大师给查查?
进入Programming版参与讨论
1 (共1页)
m*****n
发帖数: 3575
1
go:
-----------------------------
//export OnLogin_1
func OnLogin_1(status C.int) {
fmt.Println("target1 ok:", status)
}
=============================
h:
-----------------------------
typedef void (*nfun)(int LoginStatus);
extern nfun OnLogin_1;
=============================
cpp:
-----------------------------
std::cout << "=====Login Succeeded @" << this->target << std::endl;
if(this->target==1) OnLogin_1(1);
=============================
运行时候最后两行为:
=====Login Succeeded @1
段错误,已经保存
这个段错误是咋出来的呢?是不是哪里语法不对?
m********5
发帖数: 17667
2
不是大师, 也不需要大师
你编译通过了, 多数不是c call go的问题, 问题多数出在c++. 你问的问题其实会非常
让人恼火, 因为你代码没有贴全, 也没有stack trace. 有诚意的话, 你用lldb导出
stack trace贴出来.
注意你用了 `extern nfun OnLogin_1;` 但你却没有贴你如何dlopen 动态获得
OnLogin_1. 这谁知道你哪儿出问题了. 你应该用ASAN检查你的代码, 至少应该先初始
化为nullptr, 然后在使用OnLogin_1之前总是assert(OnLogin_1). 如果你总是这样写
代码, 你的code reviewer估计会被气疯. 尽量不要用extern, 在这里显然非常容易导
致错误. 你应该包装一个golib object, 在 golib constructor 里面dlopen, 如果无
法dlopen应该throw, golib object应该own一个uniqe ptr来存lib handle, 并且在
constructor里面assert你是否能得到有效的func
pointer, 其他地方通过 golib.OnLogin_1(xx) 来调用. RAII, 基本中的基本
你的cpp里面用了好多this, 感觉不是很好, 除非你是用的lambda, 但同样没有相应代
码支持, 如果是我学生这么问c++问题, 我肯定给不及格.
m*****n
发帖数: 3575
3
额,是这样,我是在人家开发好的代码上二次开发。
我不知道lldb或stack trace,问题就在于它不是纯c++程序,也不是纯go的程序,所以
就两不管。
这个主程序是go调用c++的lib去连接一个金融行情接口
然后每一个接口会起用单独一个交易所给定的class,这就是this的来源。
target可以有若干个,这里只举例第1个,即第一个行情地址。
因为交易所定义的交互是先去连接它,然后连上了就请求登录,如果登录成功了它就会
调用一个函数。
然后我在这个函数里面写了调用go的OnLogin_1
实际上就把1这个整数传回go
然后让go据此下一步行动。这里要做的只是把它打印出来。
当然,我打算在连接断开是也调用这个函数,只是会传0.
在go里面定义了该函数,是export出去,即放在C里面。
而C++里面用的extern,意思是这个函数不是C,而是C++的
所以我从go里面定义,到C去得知并调用都写了,应该算是很全了。

【在 m********5 的大作中提到】
: 不是大师, 也不需要大师
: 你编译通过了, 多数不是c call go的问题, 问题多数出在c++. 你问的问题其实会非常
: 让人恼火, 因为你代码没有贴全, 也没有stack trace. 有诚意的话, 你用lldb导出
: stack trace贴出来.
: 注意你用了 `extern nfun OnLogin_1;` 但你却没有贴你如何dlopen 动态获得
: OnLogin_1. 这谁知道你哪儿出问题了. 你应该用ASAN检查你的代码, 至少应该先初始
: 化为nullptr, 然后在使用OnLogin_1之前总是assert(OnLogin_1). 如果你总是这样写
: 代码, 你的code reviewer估计会被气疯. 尽量不要用extern, 在这里显然非常容易导
: 致错误. 你应该包装一个golib object, 在 golib constructor 里面dlopen, 如果无
: 法dlopen应该throw, golib object应该own一个uniqe ptr来存lib handle, 并且在

m********5
发帖数: 17667
4
1. 你对extern理解有误, 请去看看C++的基本教程
2. 而且你如果用func pointer你必须动态dlopen, 是不能通过linker来连接, 可以去
看看基本的 c教程
3. 如果你不知道怎么动态加载库, 你就完全没必要这么用. 直接 `extern void
OnLogin_1(int);` 即可通过linker连接. 你可以自己随便写个go文件编译成库, 就有
自动生成的header, 你可以看看里面是怎么写的.
我的建议, 鉴于你缺乏基本的C/C++ 常识, 与其自己乱试浪费时间, 不如花上3天好好
找本C++的书看看, 看完以后你几个小时就能搞定一切.
初学者就不要随便用指针了, 指针都需要封装到很底部, 最烦看到满篇指针的程序.

【在 m*****n 的大作中提到】
: 额,是这样,我是在人家开发好的代码上二次开发。
: 我不知道lldb或stack trace,问题就在于它不是纯c++程序,也不是纯go的程序,所以
: 就两不管。
: 这个主程序是go调用c++的lib去连接一个金融行情接口
: 然后每一个接口会起用单独一个交易所给定的class,这就是this的来源。
: target可以有若干个,这里只举例第1个,即第一个行情地址。
: 因为交易所定义的交互是先去连接它,然后连上了就请求登录,如果登录成功了它就会
: 调用一个函数。
: 然后我在这个函数里面写了调用go的OnLogin_1
: 实际上就把1这个整数传回go

m*****n
发帖数: 3575
5
你对this这么大气干嘛?
人家交易所给的接口就是要这样写
一个连接是一个class,也是一个thread

【在 m********5 的大作中提到】
: 1. 你对extern理解有误, 请去看看C++的基本教程
: 2. 而且你如果用func pointer你必须动态dlopen, 是不能通过linker来连接, 可以去
: 看看基本的 c教程
: 3. 如果你不知道怎么动态加载库, 你就完全没必要这么用. 直接 `extern void
: OnLogin_1(int);` 即可通过linker连接. 你可以自己随便写个go文件编译成库, 就有
: 自动生成的header, 你可以看看里面是怎么写的.
: 我的建议, 鉴于你缺乏基本的C/C++ 常识, 与其自己乱试浪费时间, 不如花上3天好好
: 找本C++的书看看, 看完以后你几个小时就能搞定一切.
: 初学者就不要随便用指针了, 指针都需要封装到很底部, 最烦看到满篇指针的程序.

b*********n
发帖数: 2284
6
能给推荐一本三五天能看完的c++书吗?不要那种六百页加的。我就是业余c++,经常出
一些诡异的错误。

【在 m********5 的大作中提到】
: 1. 你对extern理解有误, 请去看看C++的基本教程
: 2. 而且你如果用func pointer你必须动态dlopen, 是不能通过linker来连接, 可以去
: 看看基本的 c教程
: 3. 如果你不知道怎么动态加载库, 你就完全没必要这么用. 直接 `extern void
: OnLogin_1(int);` 即可通过linker连接. 你可以自己随便写个go文件编译成库, 就有
: 自动生成的header, 你可以看看里面是怎么写的.
: 我的建议, 鉴于你缺乏基本的C/C++ 常识, 与其自己乱试浪费时间, 不如花上3天好好
: 找本C++的书看看, 看完以后你几个小时就能搞定一切.
: 初学者就不要随便用指针了, 指针都需要封装到很底部, 最烦看到满篇指针的程序.

m*****n
发帖数: 3575
7
好像是CGO语法的问题,和C++的错误无关。
CGO的export并不能实现把它定义为C可以调用的函数,
还要再多一步转接。
1 (共1页)
进入Programming版参与讨论