go c 数据传输
func Opus2Aac(opusData []byte) []byte {
pushURL := C.CString(self.dst_url) // 会创建一个c内存. 手动要释放
defer C.free(unsafe.Pointer(pushURL))
srcp := (*C.uchar)(unsafe.Pointer(&opusData[0]))
srcLen := (C.int)(len(opusData))
dst := make([]byte, 2048) // go 申请内存, c申请参考下面的
dstp := (*C.uchar)(unsafe.Pointer(&dst[0]))
var retSize C.int
// void Opus2aac(AudioTranscode* at, unsigned char* src, int len, unsigned char* dst, int* retSize);
C.Opus2aac(self.opus_to_aac_ctx, srcp, srcLen, dstp, &retSize)
rett := (int)(retSize)
if rett <= 0 {
return nil
}
return dst[:rett]
}
// c 申请内存 go 释放 可能会内存泄漏
src, err := hex.DecodeString(line)
if err != nil || len(src) <= 0 {
fmt.Println("err:", err)
return
}
srcp := (*C.uchar)(unsafe.Pointer(&src[0]))
srcLen := (C.int)(len(src))
ts := (C.int)(n * 100)
var dst uintptr
dstp := (**C.uchar)(unsafe.Pointer(&dst)) // 用**, c malloc
ret := C.transcode(at, srcp, srcLen, dstp, ts)
rett := (int)(ret)
// uintptr 转 slice
outputData := struct {
addr uintptr
len int
cap int
}{dst, rett, rett}
outputslice := *(*[]byte)(unsafe.Pointer(&outputData))
outputImgData := make([]byte, rett)
copy(outputImgData, outputslice)
C.free(unsafe.Pointer(dst))
fmt.Printf("go==ret=%d==%x", len(outputslice), outputslice[:])
go 调 c, c 调 go
#pragma once
#ifdef __cplusplus
extern "C" {
#endif
int func1();
#ifdef __cplusplus
}
#endif
#pragma once
#ifdef __cplusplus
extern "C" {
#endif
int test();
#ifdef __cplusplus
}
#endif
rm libtrans.a
g++ -o tmp_trans.o -c trans_audio.cpp
gcc -o tmp_call.o -c call_cpp.c
ar -crs libtrans.a tmp_call.o tmp_trans.o
rm tmp_trans.o
rm tmp_call.o
/*
#cgo CFLAGS: -Iinclude
#cgo LDFLAGS: -L/usr/local/Cellar/ffmpeg/3.4.1/lib -lavdevice -lavformat -lavfilter -lavcodec -lswresample -lswscale -lavutil
#include"trans.h"
*/
import "C"
c调用go的日志库
- .go文件, 注释必须
//export LogPrint
func LogPrint(info *C.char) {
infoString := C.GoString(info)
log.Info(infoString)
}
- .h 文件
typedef void (*CGO_LOGPRINT)( const char *info);
extern void LogPrint( char *);
- .c文件
CGO_LOGPRINT c_logprint = LogPrint;
void cgoLogPrint(const char* szBuffer) {
c_logprint(szBuffer);
return;
}
void cgoLogPrintf(const char* fmt, ...) {
char szBuffer[512];
va_list vlist;
va_start(vlist, fmt);
vsprintf(szBuffer, fmt, vlist);
va_end(vlist);
c_logprint(szBuffer);
}
- 编译 go build
- c日志格式化
#define PPrint(fmt) \
cgoLogPrintf("[%s/%s:%d] " fmt, __FILE__, __FUNCTION__, __LINE__)
#define PPrintf(fmt, ...) \
cgoLogPrintf("[%s/%s:%d] " fmt, __FILE__, __FUNCTION__, __LINE__, __VA_ARGS__)