In order to call the Go program in the C/C++ program, the Go library is written, so how to call the callback function of the C language in the library function? Let's try it.
#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_callback
func register_callback(p C.callback) {
C._cb = p;
return
}
//export test_callback
func test_callback() {
funccallback("hello,this is func callback.",123)
}
func main() {
}
Two functions register_callback and test_callback are opened to C
Go library functions call back functions in C programs through a bridge function
package main
/*
#include <stdio.h>
typedef void (*callback)(void *,int);
callback _cb;
void c_callback(void* p,int i)
{
_cb(p,i);
}
*/
import "C"
Compile the go library
go build -o libcallback.so -buildmode=c-shared libcallback.go bridge.go
One thing I didn’t understand, why can’t I put the bridge function of bridge.go in libcallback.go, but need to separate a file bridge.go?
C main program
#include <stdio.h>
#include "libcallback.h"
void gocallback(void* s,int len) {
printf("raw data: %s\n",(char *)s);
}
int main() {
// 注册回调
register_callback(gocallback);
// 测试回调
test_callback();
}
Compile
gcc -o testcallback main.c ./libcallback.so
operation result
$ ./testcallback
raw data: hello,this is func callback.
Program call relationship
Gray is Go function, red is C language function, Call _cb stores the pointer of callback function.