golang動(dòng)態(tài)庫(kù)(so)生成與使用方法教程
前言
go語(yǔ)言有很多的庫(kù),在開(kāi)發(fā)c語(yǔ)言的時(shí)候?yàn)榱丝焖偻瓿赡承┕δ?可以直接通過(guò)go語(yǔ)言的庫(kù)進(jìn)行調(diào)用.那么我們將go語(yǔ)言開(kāi)發(fā)的程序編譯成so動(dòng)態(tài)庫(kù)文件就可以給c或者c++程序調(diào)用.
go文件編寫(xiě)
如果想要導(dǎo)出C能使用的動(dòng)態(tài)庫(kù).我們需要將函數(shù)的名稱編寫(xiě)為大寫(xiě).
并且還需要添加導(dǎo)出注釋(重要) //export HelloWorld 這個(gè)注釋必須寫(xiě),并且//后面不要有空格.
package main
/*
#include <stdlib.h>
*/
import "C"
import "fmt"
//export HelloWorld
func HelloWorld(str *C.char) *C.char{
fmt.Printf(C.GoString(str))
return str
}
func main() {
// fmt.Printf("Done\n")
}so編譯命令
go mod init test go mod tidy go build -buildmode=c-shared -o libtest.so
編譯成功后會(huì)自動(dòng)生成libtest.so 以及 libtest.h文件
可以通過(guò)一下命令檢查是否編寫(xiě)編譯成功.
readelf -a libtest.so| grep -i hello
C語(yǔ)言測(cè)試程序
main.c文件
#include "libtest.h"
void main(int argc, char* argv[]) {
char * str = HelloWorld("asdf");
print(str);
}如果libtest.h文件為自動(dòng)生成,我們可以自己手動(dòng)編寫(xiě)libtest.h文件
#ifndef __INTERFACE_H__ #define __INTERFACE_H__ char* HelloWorld(char *); #endif
CMakeList.txt編寫(xiě)
cmake_minimum_required(VERSION 2.8)
project(demo)
# C++11 編譯
set(CMAKE_BUILD_TYPE "Debug")
set(CMAKE_CXX_STANDARD 11)
# set(CMAKE_SHARED_LINKER_FLAGS " -L./ -Wl,-rpath=./")
SET(CMAKE_INCLUDE_CURRENT_DIR ON)
SET(CMAKE_CXX_STANDARD_REQUIRED ON)
set( demo_SOURCE
${CMAKE_CURRENT_SOURCE_DIR}/main.c
)
link_directories(${PROJECT_SOURCE_DIR})
SET(EXECUTABLE_OUTPUT_PATH ${PROJECT_BINARY_DIR})
add_executable(demo ${demo_SOURCE})
target_link_libraries(demo -ltest )
編譯C程序
mkdir build cd build cmake .. make
運(yùn)行
./demo
高級(jí)用法
注意:go語(yǔ)言中申請(qǐng)的內(nèi)存不要直接c中使用,因?yàn)間o語(yǔ)言的內(nèi)存管理是自己決定的,因此你不知道他在什么時(shí)候自動(dòng)釋放,因此如果需要在go語(yǔ)言中使用內(nèi)容請(qǐng)使用c.malloc來(lái)申請(qǐng)內(nèi)容返回到C語(yǔ)言中。C語(yǔ)言注意要自己調(diào)用free釋放哦。
func add() (**C.char, *C.char) {
//a := []string{"1111111111111111111", "222", "333"}
a, err := Parsefilelist()
if err != nil {
fmt.Println(err)
return nil, C.CString(err.Error())
}
count := len(a)
c_count := C.int(count)
//使用完請(qǐng)釋放該內(nèi)存空間,防止內(nèi)存泄露
cArray := C.malloc(C.size_t(c_count) * C.size_t(unsafe.Sizeof(uintptr(0))))
b := (*[1024]*C.char)(cArray)
for index, value := range a {
b[index] = C.CString(value)
}
return (**C.char)(&b[0]), nil
}總結(jié)
到此這篇關(guān)于golang動(dòng)態(tài)庫(kù)(so)生成與使用的文章就介紹到這了,更多相關(guān)golang動(dòng)態(tài)庫(kù)so使用內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
Go?并發(fā)編程協(xié)程及調(diào)度機(jī)制詳情
這篇文章主要介紹了Go并發(fā)編程協(xié)程及調(diào)度機(jī)制詳情,協(xié)程是Go語(yǔ)言最大的特色之一,goroutine的實(shí)現(xiàn)其實(shí)是通過(guò)協(xié)程,更多相關(guān)內(nèi)容需要的朋友可以參考一下2022-09-09
Golang?WebSocket創(chuàng)建單獨(dú)會(huì)話詳細(xì)實(shí)例
這篇文章主要給大家介紹了關(guān)于Golang?WebSocket創(chuàng)建單獨(dú)會(huì)話的相關(guān)資料,WebSocket 協(xié)議主要為了解決基于 HTTP/1.x 的 Web 應(yīng)用無(wú)法實(shí)現(xiàn)服務(wù)端向客戶端主動(dòng)推送的問(wèn)題,文中通過(guò)代碼介紹的非常詳細(xì),需要的朋友可以參考下2023-11-11
Go語(yǔ)言dolphinscheduler任務(wù)調(diào)度處理
這篇文章主要為大家介紹了Go語(yǔ)言dolphinscheduler任務(wù)調(diào)度處理,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2022-06-06
Golang導(dǎo)入包的幾種方式(點(diǎn),別名與下劃線)
這篇文章主要介紹了Golang導(dǎo)入包的幾種方式(點(diǎn),別名與下劃線),文中通過(guò)示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2022-02-02

