I'm trying to call the C++ function:
void TestFunc(void(*f)(void)) { f(); }
From Go Code.
I would really want it to be that I just pass a Go function to that function. I know that I can wrap it into a class, and solve it using %feature("director"), but that's not the optimal solution in my case.
From what I saw in this page, the pointers to function in Go, should be the same as in C++, so I tried the following .swig file:
%{
#include "test.h"
%}
%typemap(gotype) FUNC* "func()"
%typemap(in) FUNC* {
$1 = (void(*)(void))$input;
}
%apply FUNC* { void(*)(void) };
%include "test.h"
I was quiet surprised that it worked at first, but then noticed that it doesn't always work :(.
For example, in this Go code, it works as expected:
import "fmt"
import "test_wrap"
func main() {
b := false
test_wrap.TestFunc(func() { b = true })
fmt.Println(b) // This actually DOES print "true"!
}
But in other cases, it doesn't work. For example, here:
import "fmt"
import "test_wrap"
func main() {
test_wrap.TestFunc(func() { fmt.Println("SUCCESS") })
fmt.Println("Done")
}
I actually get:
SUCCESS
SIGILL: illegal instruction
PC=0x4c20005d000
goroutine 1 [syscall]:
test_wrap._swig_wrap_TestFunc(0x400cb0, 0x400c2a)
base_go_test__wrap_gc.c:33 +0x32
test_wrap.TestFunc(0x400cb0, 0x2)
base_go_test__wrap.go:37 +0x25
main.main()
test.go:8 +0x2a
goroutine 2 [syscall]:
created by runtime.main
go/gc/src/pkg/runtime/proc.c:225
rax 0x0
rbx 0x0
rcx 0x0
rdx 0x8
rdi 0x4c200073050
rsi 0x4c20004c0f0
rbp 0x0
rsp 0x4c20004c100
r8 0x2
r9 0x4b0ae0
r10 0x4f5620
r11 0x4dbb88
r12 0x4f5530
r13 0x7fad5977f9c0
r14 0x0
r15 0x3
rip 0x4c20005d000
rflags 0x10202
cs 0x33
fs 0x0
gs 0x0
Please notice that it did print "SUCCESS", this means that the function DID run, and even if I put more complex (and long) code into this function, it does execute perfectly, but it didn't come back :(.
Please let me know what you think, and how I can solve this problem. I don't mind adding some code on the C++ part, but I really want the Go part look "clean".
Thank you.