From dc65b072a13994ff02cc7b54f3b00ba087e7f86a Mon Sep 17 00:00:00 2001 From: zhangmeng <775834166@qq.com> Date: 星期三, 20 十一月 2019 14:05:52 +0800 Subject: [PATCH] add zerocopy --- godec.go | 19 ++++++ goffmpeg.go | 8 ++ gostream.go | 21 ++++++ goenc.go | 26 +++++++- goconv.go | 26 ++++++++ godecjpeg.go | 27 +++++++++ 6 files changed, 121 insertions(+), 6 deletions(-) diff --git a/goconv.go b/goconv.go index 311bdd4..cbf48af 100644 --- a/goconv.go +++ b/goconv.go @@ -124,4 +124,28 @@ return c.ConvToPicture(src) } -/////////////// for conv +/////////////// + +// ConvToPicture2 second +func (c *GoConv) ConvToPicture2(src []byte) (unsafe.Pointer, []byte) { + if c.conv == nil { + return nil, nil + } + + bgr := C.wrap_fn_conv(unsafe.Pointer(libcffmpeg), c.conv, (*C.uchar)(unsafe.Pointer(&src[0]))) + if bgr != nil { + const maxLen = 0x7fffffff + size := int(c.size) + data := (*[maxLen]byte)(unsafe.Pointer(bgr))[:size:size] + return bgr, data + } + return nil, nil +} + +// Resize2 resize2 +func (c *GoConv) Resize2(src []byte) (unsafe.Pointer, []byte) { + if c.SrcW == c.DstW && c.SrcH == c.DstH { + return nil, src + } + return c.ConvToPicture2(src) +} diff --git a/godec.go b/godec.go index aab8c7a..25baa88 100644 --- a/godec.go +++ b/godec.go @@ -19,10 +19,27 @@ var srcW, srcH, srcF C.int p := C.wrap_fn_decoder_pic(unsafe.Pointer(libcffmpeg), h.ffmpeg, &srcW, &srcH, &srcF, &length, &fid) - if srcW == 0 || srcH == 0 { + if p == nil || length == 0 || srcW == 0 || srcH == 0 { return nil, 0, 0, 0 } defer C.free(unsafe.Pointer(p)) return C.GoBytes(p, length), int(srcW), int(srcH), int64(fid) } + +// GetYUV2 get yuv data +func (h *GoFFMPEG) GetYUV2() (unsafe.Pointer, []byte, int, int, int64) { + var fid C.long + var length C.int + var srcW, srcH, srcF C.int + + p := C.wrap_fn_decoder_pic(unsafe.Pointer(libcffmpeg), h.ffmpeg, &srcW, &srcH, &srcF, &length, &fid) + if p == nil || length == 0 || srcW == 0 || srcH == 0 { + return nil, nil, 0, 0, 0 + } + const maxLen = 0x7fffffff + size := int(length) + data := (*[maxLen]byte)(unsafe.Pointer(p))[:size:size] + + return unsafe.Pointer(p), data, int(srcW), int(srcH), int64(fid) +} diff --git a/godecjpeg.go b/godecjpeg.go index 6cef6af..ac1151f 100644 --- a/godecjpeg.go +++ b/godecjpeg.go @@ -34,3 +34,30 @@ } return nil, int(width), int(height) } + +// Decode2 decode jpeg file +// return val: -1 open error; -2, find stream error; -3, converter create error +func Decode2(input string, gb bool) (unsafe.Pointer, []byte, int, int) { + in := C.CString(input) + defer C.free(unsafe.Pointer(in)) + + withGB := 0 + if gb { + withGB = 1 + } + + var width C.int + var height C.int + p := C.wrap_fn_decode(unsafe.Pointer(libcffmpeg), in, C.int(withGB), &width, &height) + + if width > 0 && height > 0 { + wid := int(width) + hei := int(height) + const maxLen = 0x7fffffff + size := int(width * height * 3) + data := (*[maxLen]byte)(unsafe.Pointer(p))[:size:size] + + return p, data, wid, hei + } + return nil, nil, 0, 0 +} diff --git a/goenc.go b/goenc.go index d7a6b43..858ed98 100644 --- a/goenc.go +++ b/goenc.go @@ -37,10 +37,8 @@ var size C.int var key C.int - cin := C.CBytes(in) - defer C.free(cin) - p := C.wrap_fn_encode(unsafe.Pointer(libcffmpeg), e.enc, cin, C.int(w), C.int(h), &size, &key) + p := C.wrap_fn_encode(unsafe.Pointer(libcffmpeg), e.enc, unsafe.Pointer(&in[0]), C.int(w), C.int(h), &size, &key) defer C.free(p) if p != nil && size > 0 { b := C.GoBytes(p, size) @@ -53,3 +51,25 @@ } return nil, 0, false } + +// Encode2 pic +func (e *GoEncoder) Encode2(in []byte, w, h int) (unsafe.Pointer, []byte, int, bool) { + + var size C.int + var key C.int + + p := C.wrap_fn_encode(unsafe.Pointer(libcffmpeg), e.enc, unsafe.Pointer(&in[0]), C.int(w), C.int(h), &size, &key) + if p != nil && size > 0 { + + isKey := false + if key > 0 { + isKey = true + } + const maxLen = 0x7fffffff + length := int(size) + data := (*[maxLen]byte)(unsafe.Pointer(p))[:length:length] + + return p, data, length, isKey + } + return nil, nil, 0, false +} diff --git a/goffmpeg.go b/goffmpeg.go index efaf6cc..252e7a1 100644 --- a/goffmpeg.go +++ b/goffmpeg.go @@ -99,3 +99,11 @@ func (h *GoFFMPEG) FPS() int { return int(C.wrap_fn_fps(unsafe.Pointer(libcffmpeg), h.ffmpeg)) } + +// ReleaseC release c memory +func ReleaseC(p unsafe.Pointer) { + if p == nil { + return + } + C.free(unsafe.Pointer(p)) +} diff --git a/gostream.go b/gostream.go index dc94166..7ae6636 100644 --- a/gostream.go +++ b/gostream.go @@ -14,13 +14,32 @@ var size C.int p := C.wrap_fn_get_avpacket(unsafe.Pointer(libcffmpeg), h.ffmpeg, &size, &key) + defer C.free(unsafe.Pointer(p)) if size <= 0 { return nil, 0, -1 } - defer C.free(unsafe.Pointer(p)) d := C.GoBytes(p, size) s := int(size) k := int(key) return d, s, k } + +//GetAVPacket2 get AVPacket +func (h *GoFFMPEG) GetAVPacket2() (unsafe.Pointer, []byte, int, int) { + var key C.int + var size C.int + + p := C.wrap_fn_get_avpacket(unsafe.Pointer(libcffmpeg), h.ffmpeg, &size, &key) + if size <= 0 { + return nil, nil, 0, -1 + } + + const maxLen = 0x7fffffff + length := int(size) + data := (*[maxLen]byte)(unsafe.Pointer(p))[:length:length] + + k := int(key) + + return p, data, length, k +} -- Gitblit v1.8.0