Documentation Index
Fetch the complete documentation index at: https://docs.oxd.sh/llms.txt
Use this file to discover all available pages before exploring further.
Setup
Placeliboxaccel.so (or .dylib / .dll) and oxaccel.h in your project directory.
cgo bindings
package accel
/*
#cgo LDFLAGS: -L${SRCDIR} -loxaccel
#cgo linux LDFLAGS: -lpthread -ldl -lm
#cgo darwin LDFLAGS: -framework Security -framework CoreFoundation
#include "oxaccel.h"
#include <stdlib.h>
*/
import "C"
import (
"errors"
"unsafe"
)
type Context struct {
ctx *C.OxAccel
}
type Config struct {
APIKey string
RelayHost string
RelayPort uint16
EnableFEC bool
EnableCompress bool
EnableMultipath bool
}
type Stats struct {
PacketsSent uint64
PacketsRecv uint64
BytesSent uint64
BytesRecv uint64
}
func New(cfg Config) (*Context, error) {
apiKey := C.CString(cfg.APIKey)
defer C.free(unsafe.Pointer(apiKey))
host := C.CString(cfg.RelayHost)
defer C.free(unsafe.Pointer(host))
ccfg := C.OxAccelConfig{
api_key: apiKey,
relay_host: host,
relay_port: C.uint16_t(cfg.RelayPort),
enable_fec: C.bool(cfg.EnableFEC),
enable_compression: C.bool(cfg.EnableCompress),
enable_multipath: C.bool(cfg.EnableMultipath),
}
ctx := C.ox_accel_create(&ccfg)
if ctx == nil {
return nil, errors.New("ox_accel_create failed")
}
return &Context{ctx: ctx}, nil
}
func (c *Context) Connect() error {
err := C.ox_accel_connect(c.ctx)
if err != C.OxAccelError_Ok {
return errors.New("ox_accel_connect failed")
}
return nil
}
func (c *Context) Send(data []byte) error {
err := C.ox_accel_send(c.ctx, (*C.uint8_t)(&data[0]), C.size_t(len(data)))
if err != C.OxAccelError_Ok {
return errors.New("ox_accel_send failed")
}
return nil
}
func (c *Context) Recv(buf []byte) (int, error) {
var outLen C.size_t
err := C.ox_accel_recv(c.ctx, (*C.uint8_t)(&buf[0]), C.size_t(len(buf)), &outLen)
if err != C.OxAccelError_Ok {
return 0, errors.New("ox_accel_recv failed")
}
return int(outLen), nil
}
func (c *Context) Stats() Stats {
var s C.AccelStats
C.ox_accel_stats(c.ctx, &s)
return Stats{
PacketsSent: uint64(s.packets_sent),
PacketsRecv: uint64(s.packets_recv),
BytesSent: uint64(s.bytes_sent),
BytesRecv: uint64(s.bytes_recv),
}
}
func (c *Context) Close() {
if c.ctx != nil {
C.ox_accel_destroy(c.ctx)
c.ctx = nil
}
}
func Version() string {
return C.GoString(C.ox_accel_version())
}
Usage
package main
import (
"fmt"
"log"
"myapp/accel"
)
func main() {
ctx, err := accel.New(accel.Config{
APIKey: "your-api-key",
RelayHost: "relay.oxd.sh",
RelayPort: 51820,
EnableFEC: true,
})
if err != nil {
log.Fatal(err)
}
defer ctx.Close()
if err := ctx.Connect(); err != nil {
log.Fatal(err)
}
// Send
ctx.Send([]byte("hello"))
// Receive
buf := make([]byte, 65536)
n, _ := ctx.Recv(buf)
fmt.Printf("Received %d bytes\n", n)
// Stats
s := ctx.Stats()
fmt.Printf("TX: %d packets, RX: %d packets\n",
s.PacketsSent, s.PacketsRecv)
}
cgo has overhead per call (~100ns). For high-frequency send/recv, batch multiple messages or use the C API directly from a goroutine pinned with
runtime.LockOSThread().