Put all files in ctest
directory.
cd ctest
go test
#include <stdio.h> | |
#include <string.h> | |
#include "ctest.h" | |
void c_call(void *in, int lin, void *out, int *lout) | |
{ | |
char *ain = (char*) in; | |
char *aout = (char*) out; | |
printf("C: c_call with: '%s', %d bytes\n", ain, lin); | |
int j = 0; | |
for (int i = 0; i < lin; i++) { | |
char c = ain[i]; | |
if (i < (lin-1)) { | |
if (c == 'G' && ain[i+1] == 'o') { | |
c = 'C'; | |
i++; | |
} | |
} | |
aout[j] = c; | |
j++; | |
} | |
*lout = j; | |
printf("C: all done"); | |
} |
package ctest | |
/* | |
#include "ctest.h" | |
void c_call(void*, int, void* , int*); | |
*/ | |
import "C" | |
import ( | |
"fmt" | |
"reflect" | |
"unsafe" | |
) | |
func CallCFunc(input []byte) []byte { | |
var inputLength int = len(input) | |
const MAX_OUTPUT int = 10 | |
var output []byte = make([]byte, MAX_OUTPUT) | |
// Conversion to C types | |
var inPtr unsafe.Pointer = unsafe.Pointer(&input[0]) | |
var inL C.int = C.int(inputLength) | |
var outPtr unsafe.Pointer = unsafe.Pointer(&output[0]) | |
var outL C.int = C.int(0) | |
// Call the C function | |
defer func() { | |
p := recover() | |
if p != nil { | |
fmt.Printf("Panic with %s: %s\n", reflect.TypeOf(p).String(), p) | |
} | |
}() | |
C.c_call(inPtr, inL, outPtr, &outL) | |
// Copy the result to a new buffer | |
var length int = int(outL) | |
res := append([]byte{}, output[:length]...) | |
// Return result | |
return res | |
} |
#ifndef CTEST_H | |
#define CTEST_H | |
void c_call(void*, int, void* , int*); | |
#endif |
package ctest | |
import ( | |
"github.com/stretchr/testify/assert" | |
"testing" | |
) | |
func TestCCall(t *testing.T) { | |
var result []byte = CallCFunc([]byte("Hello Go!")) | |
assert.Equal(t, "Hello C!", string(result)) | |
} | |
func TestCCallArrayOverflow(t *testing.T) { | |
var result []byte = CallCFunc([]byte("Hello, hello Go!")) | |
assert.Equal(t, 0, len(result)) | |
} |