Download bindings/go/abi_test.go from chibifire/motion-bricks.cpp: direct link, hf CLI and curl.
- Browser
- Download file 3.98 kB
-
https://huggingface.co/chibifire/motion-bricks.cpp/resolve/main/bindings/go/abi_test.go
- Command line
-
hf download hf://chibifire/motion-bricks.cpp/bindings/go/abi_test.go
-
curl -L -o abi_test.go https://huggingface.co/chibifire/motion-bricks.cpp/resolve/main/bindings/go/abi_test.go
3.98 kB
| //go:build linux || darwin || freebsd | |
| package motionbricks | |
| import ( | |
| "math" | |
| "os" | |
| "testing" | |
| "unsafe" | |
| "github.com/ebitengine/purego" | |
| ) | |
| const ( | |
| statusOK = uint32(0) | |
| deviceAuto = uint32(0) | |
| deviceVulkan = uint32(2) | |
| abiVersion = uint32(1) | |
| errorCapacity = uint64(256) | |
| ) | |
| // TestOpaqueABIRoundTrip intentionally mirrors no C struct. Every object is an | |
| // opaque uintptr and every record field is accessed through a function. | |
| func TestOpaqueABIRoundTrip(t *testing.T) { | |
| library := os.Getenv("MOTIONBRICKS_LIB") | |
| if library == "" { | |
| t.Skip("set MOTIONBRICKS_LIB to the motion-bricks.cpp shared library") | |
| } | |
| handle, err := purego.Dlopen(library, purego.RTLD_NOW|purego.RTLD_LOCAL) | |
| if err != nil { | |
| t.Fatalf("dlopen %s: %v", library, err) | |
| } | |
| defer purego.Dlclose(handle) | |
| var version func() uint32 | |
| var optionsCreate func(unsafe.Pointer, unsafe.Pointer, uint64) uint32 | |
| var optionsFree func(uintptr) | |
| var optionsSetDevice func(uintptr, uint32, unsafe.Pointer, uint64) uint32 | |
| var optionsGetDevice func(uintptr, unsafe.Pointer, unsafe.Pointer, uint64) uint32 | |
| var commandCreate func(unsafe.Pointer, unsafe.Pointer, uint64) uint32 | |
| var commandFree func(uintptr) | |
| var commandSetMovement func(uintptr, float32, float32, float32, unsafe.Pointer, uint64) uint32 | |
| var commandGetMovement func(uintptr, unsafe.Pointer, unsafe.Pointer, unsafe.Pointer, unsafe.Pointer, uint64) uint32 | |
| purego.RegisterLibFunc(&version, handle, "mb_abi_version") | |
| purego.RegisterLibFunc(&optionsCreate, handle, "mb_runtime_options_create") | |
| purego.RegisterLibFunc(&optionsFree, handle, "mb_runtime_options_free") | |
| purego.RegisterLibFunc(&optionsSetDevice, handle, "mb_runtime_options_set_device") | |
| purego.RegisterLibFunc(&optionsGetDevice, handle, "mb_runtime_options_get_device") | |
| purego.RegisterLibFunc(&commandCreate, handle, "mb_command_create") | |
| purego.RegisterLibFunc(&commandFree, handle, "mb_command_free") | |
| purego.RegisterLibFunc(&commandSetMovement, handle, "mb_command_set_movement_direction") | |
| purego.RegisterLibFunc(&commandGetMovement, handle, "mb_command_get_movement_direction") | |
| if got := version(); got != abiVersion { | |
| t.Fatalf("ABI version = %d, want %d", got, abiVersion) | |
| } | |
| errorBuffer := make([]byte, errorCapacity) | |
| errorPointer := unsafe.Pointer(&errorBuffer[0]) | |
| var options uintptr | |
| if status := optionsCreate(unsafe.Pointer(&options), errorPointer, errorCapacity); status != statusOK { | |
| t.Fatalf("options create status %d: %q", status, errorBuffer) | |
| } | |
| if options == 0 { | |
| t.Fatal("options create returned a null handle") | |
| } | |
| defer optionsFree(options) | |
| var device uint32 = math.MaxUint32 | |
| if status := optionsGetDevice(options, unsafe.Pointer(&device), errorPointer, errorCapacity); status != statusOK { | |
| t.Fatalf("get default device status %d", status) | |
| } | |
| if device != deviceAuto { | |
| t.Fatalf("default device = %d, want auto", device) | |
| } | |
| if status := optionsSetDevice(options, deviceVulkan, errorPointer, errorCapacity); status != statusOK { | |
| t.Fatalf("set Vulkan status %d", status) | |
| } | |
| if status := optionsGetDevice(options, unsafe.Pointer(&device), errorPointer, errorCapacity); status != statusOK || device != deviceVulkan { | |
| t.Fatalf("Vulkan round trip status=%d device=%d", status, device) | |
| } | |
| var command uintptr | |
| if status := commandCreate(unsafe.Pointer(&command), errorPointer, errorCapacity); status != statusOK { | |
| t.Fatalf("command create status %d", status) | |
| } | |
| if command == 0 { | |
| t.Fatal("command create returned a null handle") | |
| } | |
| defer commandFree(command) | |
| if status := commandSetMovement(command, 1.0, 0.0, -0.25, errorPointer, errorCapacity); status != statusOK { | |
| t.Fatalf("set movement status %d", status) | |
| } | |
| var x, y, z float32 | |
| if status := commandGetMovement(command, unsafe.Pointer(&x), unsafe.Pointer(&y), unsafe.Pointer(&z), errorPointer, errorCapacity); status != statusOK { | |
| t.Fatalf("get movement status %d", status) | |
| } | |
| if x != 1.0 || y != 0.0 || z != -0.25 { | |
| t.Fatalf("movement = (%g, %g, %g)", x, y, z) | |
| } | |
| } | |