Go呼叫C/C++
cgo
golang是類C的語言 支援呼叫C介面(不支援呼叫C++)
Go呼叫C/C++的方式 :
- C : 直接呼叫C API
- C++ : 通過實現一層封裝的C介面來呼叫C++介面
Go整合C/C++的方式
-
go的原始碼中直接宣告C程式碼
比較簡單的應用情況 可以直接使用這種方法 C程式碼直接寫在go程式碼的註釋中
註釋之後緊跟import "C" 通過C.xx來引用C的結構和函式
package main /* #include <stdio.h> #include <stdlib.h> typedef struct { int id; }ctx; ctx *createCtx(int id) { ctx *obj = (ctx *)malloc(sizeof(ctx)); obj->id = id; return obj; } */ import "C" import ( "fmt" "sync" ) func main() { var ctx *C.ctx = C.createCtx(100) fmt.Printf("id : %d\n", ctx.id) }
-
通過封裝實現呼叫C++介面
目錄結構 :C++程式碼放置在cpp目錄下
C++程式碼需要提前編譯成動態庫(拷貝到系統庫目錄可以防止go找不到動態庫路徑),go程式執行時會去連結
. ├── cpp │├── cwrap.cpp │├── cwrap.h │├── libgotest.dylib │├── test.cpp │└── test.h ├── main.go
test.cpp和test.h是C++介面的實現
cwrap.h和cwrap.cpp是封裝的C介面的實現
- test.h
#ifndef __TEST_H__ #define __TEST_H__ #include <stdio.h> class Test { public: void call(); }; #endif
- test.cpp
#include "test.h" void Test::call() { printf("call from c++ language\n"); }
- cwrap.cpp
#include "cwrap.h" #include "test.h" void call() { Test ctx; ctx.call(); }
- cwrap.h
#ifndef __CWRAP_H__ #define __CWRAP_H__ #ifdef __cplusplus extern "C" { #endif void call(); #ifdef __cplusplus } #endif #endif
- main.go
package main /* #cgo CFLAGS: -Icpp #cgo LDFLAGS: -lgotest #include "cwrap.h" */ import "C" func main() { C.call() }