Golang编写动态库实现回调函数

我们现在要做一个动态库,但是C++实在是比较难,于是就想能不能用更简单的golang来实现,golang也就是最近的版本才支持编译成动态库,在网上也没找到可用的案例,好在我们解决了这个问题,这边写个笔记造福大众。

main.go

package main
/*
#cgo CFLAGS: -I .
#include <unistd.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
typedef void (*callback)(void *,int);
extern void c_callback (void *,int);
extern callback _cb;
*/
import "C"
import (
"encoding/json"
"unsafe"
) func funccallback(gostring string,goint int) {
var cmsg *C.char = C.CString(gostring)
var ivalue C.int = C.int(len(gostring))
defer C.free(unsafe.Pointer(cmsg))
C.c_callback(unsafe.Pointer(cmsg),ivalue)
} //export register_rsucallback
func register_rsucallback(p C.callback) {
C._cb = p;
return
} //export test_callback
func test_callback() {
funccallback("hello,this is func callback.",123)
} func main() {
}

bridge.go

package main

/*
#include <stdio.h> typedef void (*callback)(void *,int); callback _cb; void c_callback(void* p,int i)
{
_cb(p,i);
}
*/
import "C"

这样写完直接调用以下命令即可生成main.dll文件和main.h文件

winows编译动态库参考我的这篇文章

go build -o main.dll -buildmode=c-shared main.go bridge.go

然后就是C语言的测试程序调用

main.c

#include <stdio.h>
#include "main.h" void gocallback(void* s,int len) {
printf("raw data: %s\n",s);
} int main() {
// 注册回调
register_callback(gocallback); // 测试回调
test_callback();
}

把C程序编译一下即可测试。

有时我们需要在别的包里调用这个回调函数,这时可以做一个工具

utils包callbackutils.go

package utils

type funVarType func(string,int)

var FunVar func(string,int)

func SetFuncAddr(a funVarType) {
FunVar=a
} func Funccallbackutil (gostring string,i int) {
FunVar(gostring,i)
}

在main.go中可以写个init函数做个初始化

func init() {
utils.SetFuncAddr(funccallback)
}

然后在写一个测试的函数导出

//export test_callbackutil
func test_callbackutil() {
utils.Funccallbackutil("hello this is func callbackutil test",123)
}

最后在main.c中调用测试函数即可测试。

Golang编写动态库实现回调函数的更多相关文章

  1. C#将C++动态库的回调函数封装成事件

    关于C#调用C++动态库的文章很多,调用动态库中回调函数的方法也不在少数.但大多数调用回调函数的方法依然保留了C++的语法特点. 比如有一段C++的回调函数代码,为了表达它的意思,我把注释也粘贴了进来 ...

  2. Golang调用windows下的dll动态库中的函数

    Golang调用windows下的dll动态库中的函数 使用syscall调用. package main import ( "fmt" "syscall" & ...

  3. Golang调用windows下的dll动态库中的函数 Golang 编译成 DLL 文件

    Golang调用windows下的dll动态库中的函数 package main import ( "fmt" "syscall" "time&quo ...

  4. C++编写动态库(.DLL)给C#调用方法

    1.在头文件中按照如下格式编写函数申明 extern "C" __declspec(dllexport) double __stdcall Add(double a, double ...

  5. windows下查看静态库和动态库的导出函数

    在window下查看动态库的导出函数可以用vs自带的Depends工具: 查看静态库的信息要用命令行来实现: dumpbin   /LINKERMEMBER   Test.lib   >   1 ...

  6. 从零开始编写动态库文件Makefile,C++版

    这篇文章前,假设你已经看过<跟我一起写Makefile(一)>,陈皓写的那个. 对现有的一个C++动态库文件和调用程序,分别编写Makefile文件,从零开始,花了四天时间才搞清楚一半,生 ...

  7. golang调用动态库

    测试动态库 test_so.h int test_so_func(int a,int b); test_so.c #include "test_so.h" int test_so_ ...

  8. 动态库(.so)隐藏函数名

    一.偶遇 error: undefined reference to  xxx 问题 尝试封装通用的接口到一个private.so,然后供客户端使用,private.so编译出来后由sample.cp ...

  9. 如何调用.so动态库中的函数,如何把自己的函数导出为.so的动态库函数供别人调用

    调用.so中的函数和平常的函数没有区别,只是在编译连接时加上-lxxxx就行了.要生成.so库,则编译时用下面的语句:gcc -shared -Wl,-soname,libmyfun.so -o li ...

随机推荐

  1. CSS层叠性

    比较id,类,标签的数量 谁多就谁在上面 255个类的权重等于一个id 当权重一样时,以后设置的为准 通过继承而来的,权重为0 !important (设置权重无限大)可以影响权重,但只能影响选中的, ...

  2. 3.下载CentOS镜像

    下载CentOS镜像 引子: 镜像可以看成是类似ZIP的压缩文件,与rar ZIP压缩包类似,镜像文件是无法直接使用的,需要利用一些虚拟光驱工具 进行解压后才能使用 我们这里就是CentOS系统的镜像 ...

  3. jQuery两种方法添加数据表格到HTML

    jQ创建表格的两种方法 1.模板字符串法   $(function () {           //模板字符串的方式添加到页面           $('#btn').click(function ...

  4. Linux 部署 iSCSI 客户端配置(Windows)

    Linux 部署 iSCSI 客户端配置(Windows) 客户端环境 Client :Windows 7 ip :192.168.121.138 一.首先查看客户端本地所有的磁盘 查看路径:邮件计算 ...

  5. linux进阶之yum管理

    一.部署私有repo源 1.官网下载需要的仓库: rsync -avrt --delete rsync://mirrors.ustc.edu.cn/centos/7/cloud/x86_64/open ...

  6. 9.10 nohup:用户退出系统进程继续工作

    nohup命令 可以将程序以忽略挂起信号的方式运行起来,被运行程序的输出信息将不会显示到终端.        无论是否将nohup命令的输出重定向到终端,输出都将写入到当前目录的nohup.out文件 ...

  7. 行业资讯 | Android WebView 致安卓应用闪退,mPaaS 助你规避这波 Bug

    根据外媒 9to5 Google 报道,3 月 23 日几个小时内,大量安卓用户遇到一些安卓应用连续闪退的情况,有人发现卸载安卓系统 WebView 就可以停止闪退.目前,谷歌已经发布了应用崩溃问题的 ...

  8. unity中UI坐标转3d世界坐标

    方法: public static Vector3 UIScreenToWorldPoint(Vector3 uiPostion) { uiPostion = UICamera.mainCamera. ...

  9. 详述盒子模型(包含padding、border、margin的详细用法和描述)

    提起盒子模型,我想无论是对于一个前端资深开发人员还是前端入门开发人员来说都不陌生,这是CSS最基础的知识. 但是惭愧地说,我之前理解的盒子模型,只是文字上的理解.我知道定义一个元素的宽度和高度时,设置 ...

  10. .Net RabbitMQ实战指南——客户端开发

    开发中关键的Class和Interface有Channel.Connection.ConnectionFactory.Consumer等,与RabbitMQ相关的开发工作,基本上是围绕Connecti ...