1. 程式人生 > >Go語言第十八課 CGO

Go語言第十八課 CGO

可藉助CGO實現Go語言對C的呼叫,下面展示幾種呼叫方式。

1、直接巢狀C程式碼

C程式碼內容如下:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

char* test_hello(const char* name){
    const char* hello=" -> hello";
    char* result=(char*)malloc(sizeof(char)*(strlen(name))+strlen(hello));
    strcpy(result,name);
    strcat(result,hello);
    return result;
}

int main()
{
    char* str=test_hello("yuyong");
    printf("%s\n",str);
    free(str);
}

執行結果:

yuyong -> hello

Go程式碼如下:

package main

/*
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

char* test_hello(const char* name){
    const char* hello=" -> hello";
    char* result=(char*)malloc(sizeof(char)*(strlen(name))+strlen(hello));
    strcpy(result,name);
    strcat(result,hello);
    return result;
}
*/
import "C"
import "fmt"

func main() {
	fmt.Println(C.GoString(C.test_hello(C.CString("yuyong"))));
}

執行結果同C程式碼。

2、引用C原始碼方式

在Go main函式所在檔案的同級目錄下新建兩個檔案

test.h

#ifndef TEST_YUYONG_H
#define TEST_YUYONG_H

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

char* test_hello(const char* name);

#endif

test.c

#include"test.h"
char* test_hello(const char* name){
    const char* hello=" -> hello";
    char* result=(char*)malloc(sizeof(char)*(strlen(name))+strlen(hello));
    strcpy(result,name);
    strcat(result,hello);
    return result;
}

Go程式碼如下:

package main

/*
#include"test.c"
*/
import "C"
import "fmt"

func main() {
	fmt.Println(C.GoString(C.test_hello(C.CString("yuyong"))));
}

結果與1相同。

這兩種方式呼叫C是最簡單最基本的,下面我們嘗試藉助.so檔案實現Go呼叫C/C++程式碼。

3、動態連結庫方式

將上面的C檔案(test.h和test.c)編譯成動態連結庫libtest.so

然後在Go main函式所在檔案的同級目錄下新建兩個目錄,lib和include

其中lib裡面放入libtest.so,include裡面放入test.h

Go程式碼如下:

package main

/*
#cgo CFLAGS : -I./include
#cgo LDFLAGS: -L./lib -ltest
#include "test.h"
*/
import "C"

import "fmt"

func main() {
	fmt.Println(C.GoString(C.test_hello(C.CString("yuyong"))));
}

配置環境變數

export LD_LIBRARY_PATH=/home/yong/Desktop/cgo-test20180723001/test_001/lib

其中LD_LIBRARY_PATH就是libtest.so所在目錄

如果用的是Goland則可以配置如下:

Edit Configurations... --> Environment

新增,name=LD_LIBRARY_PATH,value=/home/yong/Desktop/cgo-test20180723001/test_001/lib

執行結果同上。