CGO: ¿Cómo se utilizan los punteros en Golang para acceder a los datos de una matriz en C

Estoy escribiendo una aplicación para la plataforma de Windows usando FFmpeg y es Golang wrapper goav, pero tengo problemas para entender cómo usar los punteros C para obtener acceso a la matriz de datos a la que apuntan.

Estoy tratando de obtener los datos almacenados en la clase AVFrame y usar Ir para escribirlos en un archivo, y finalmente una textura en OpenGl para hacer un reproductor de video con transiciones geniales.

Creo que entender cómo emitir y acceder a los datos en C hará que la encoding sea mucho más fácil.

He eliminado todas las partes relevantes del código C, la envoltura y mi código, como se muestra a continuación:

Código C – libavutil / frame.h

#include  typedef struct AVFrame { #define AV_NUM_DATA_POINTERS 8 uint8_t *data[AV_NUM_DATA_POINTERS]; } 

Envoltorio de Golang Goav: no sé realmente qué está pasando aquí con los inseguros. Los punteros y el casting, pero me da acceso al código C subyacente

 package avutil /* #cgo pkg-config: libavutil #include  #include  */ import "C" import ( "unsafe" ) type Frame C.struct_AVFrame func AvFrameAlloc() *Frame { return (*Frame)(unsafe.Pointer(C.av_frame_alloc())) } func Data(f *Frame) *uint8 { return (*uint8)(unsafe.Pointer((*C.uint8_t)(unsafe.Pointer(&f.data)))) } 

Mi codigo de golang

 package main import "github.com/giorgisio/goav/avutil" func main() { videoFrame := avutil.AvFrameAlloc() data := avutil.Data(videoFrame) fmt.Println(data) // here i want the values from data[0] to data[7], but how? } 

Dado que el autor de la biblioteca no construyó un encabezado de segmento para que unsafe.Pointer contigo, tendrás que convertir el valor de retorno que obtienes en un unsafe.Pointer en memoria.

Aquí hay un código de ejemplo que debe ejecutarse como está en el patio de recreo.

 package main import ( "fmt" "unsafe" ) func main() { nums := []uint8{1, 2, 3, 4, 5, 6, 7, 8} val := &nums[0] // val is the equivalent of the *uint8 the Data function returns ptr := unsafe.Pointer(val) sixthVal := (*uint8)(unsafe.Pointer(uintptr(ptr) + 5*unsafe.Sizeof(*val))) fmt.Println("Sixth element:", *sixthVal) } 

Por supuesto, tendrá que estar muy seguro de saber cuántos elementos hay para no acceder a la memoria no válida.