From ce9d0b53845659d210947d9c6b42e6ad8e023043 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Tue, 10 Dec 2024 16:26:34 +0800 Subject: [PATCH 01/31] OpenIOContextWithDictionary --- io_context.go | 15 +++++++++++++++ io_context_test.go | 9 +++++++++ 2 files changed, 24 insertions(+) diff --git a/io_context.go b/io_context.go index 710d932..f7c4e11 100644 --- a/io_context.go +++ b/io_context.go @@ -119,6 +119,21 @@ func OpenIOContext(filename string, flags IOContextFlags) (*IOContext, error) { return newIOContextFromC(c), nil } +// https://ffmpeg.org/doxygen/7.0/avio_8c.html#ae8589aae955d16ca228b6b9d66ced33d +func OpenIOContextWithDictionary(filename string, flags IOContextFlags, d *Dictionary) (*IOContext, error) { + cfi := C.CString(filename) + defer C.free(unsafe.Pointer(cfi)) + var dc **C.AVDictionary + if d != nil { + dc = &d.c + } + var c *C.AVIOContext + if err := newError(C.avio_open2(&c, cfi, C.int(flags), nil, dc)); err != nil { + return nil, err + } + return newIOContextFromC(c), nil +} + func (ic *IOContext) Class() *Class { return newClassFromC(unsafe.Pointer(ic.c)) } diff --git a/io_context_test.go b/io_context_test.go index 09d4576..d2aa1e9 100644 --- a/io_context_test.go +++ b/io_context_test.go @@ -67,6 +67,15 @@ func TestOpenIOContext(t *testing.T) { b, err := os.ReadFile(path) require.NoError(t, err) require.Equal(t, "test", string(b)) + + d := NewDictionary() + _ = d.Set("k", "v", 0) + cd, err := OpenIOContextWithDictionary(path, NewIOContextFlags(IOContextFlagRead), d) + require.NoError(t, err) + cdl := cd.Class() + require.NotNil(t, cdl) + require.Equal(t, "AVIOContext", cdl.Name()) + err = os.Remove(path) require.NoError(t, err) } From 7aed9ec8cd3beb109e81fe8fa1764ff9ea0863b2 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Wed, 11 Dec 2024 10:50:51 +0800 Subject: [PATCH 02/31] OpenIOContext --- io_context.go | 13 +------------ io_context_test.go | 13 +++---------- 2 files changed, 4 insertions(+), 22 deletions(-) diff --git a/io_context.go b/io_context.go index f7c4e11..1bdc28c 100644 --- a/io_context.go +++ b/io_context.go @@ -108,19 +108,8 @@ func AllocIOContext(bufferSize int, writable bool, readFunc IOContextReadFunc, s return } -// https://ffmpeg.org/doxygen/7.0/avio_8c.html#ab1b99c5b70aa59f15ab7cd4cbb40381e -func OpenIOContext(filename string, flags IOContextFlags) (*IOContext, error) { - cfi := C.CString(filename) - defer C.free(unsafe.Pointer(cfi)) - var c *C.AVIOContext - if err := newError(C.avio_open(&c, cfi, C.int(flags))); err != nil { - return nil, err - } - return newIOContextFromC(c), nil -} - // https://ffmpeg.org/doxygen/7.0/avio_8c.html#ae8589aae955d16ca228b6b9d66ced33d -func OpenIOContextWithDictionary(filename string, flags IOContextFlags, d *Dictionary) (*IOContext, error) { +func OpenIOContext(filename string, flags IOContextFlags, d *Dictionary) (*IOContext, error) { cfi := C.CString(filename) defer C.free(unsafe.Pointer(cfi)) var dc **C.AVDictionary diff --git a/io_context_test.go b/io_context_test.go index d2aa1e9..a2acec2 100644 --- a/io_context_test.go +++ b/io_context_test.go @@ -56,7 +56,9 @@ func TestIOContext(t *testing.T) { func TestOpenIOContext(t *testing.T) { path := filepath.Join(t.TempDir(), "iocontext.txt") - c, err := OpenIOContext(path, NewIOContextFlags(IOContextFlagWrite)) + d := NewDictionary() + _ = d.Set("k", "v", 0) + c, err := OpenIOContext(path, NewIOContextFlags(IOContextFlagWrite), d) require.NoError(t, err) cl := c.Class() require.NotNil(t, cl) @@ -67,15 +69,6 @@ func TestOpenIOContext(t *testing.T) { b, err := os.ReadFile(path) require.NoError(t, err) require.Equal(t, "test", string(b)) - - d := NewDictionary() - _ = d.Set("k", "v", 0) - cd, err := OpenIOContextWithDictionary(path, NewIOContextFlags(IOContextFlagRead), d) - require.NoError(t, err) - cdl := cd.Class() - require.NotNil(t, cdl) - require.Equal(t, "AVIOContext", cdl.Name()) - err = os.Remove(path) require.NoError(t, err) } From 27d143ea4e7b58f4f4337791ab38ee1723dc14d6 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Wed, 11 Dec 2024 11:00:06 +0800 Subject: [PATCH 03/31] OpenIOContext --- class_test.go | 2 +- examples/remuxing/main.go | 2 +- examples/transcoding/main.go | 2 +- format_context_test.go | 4 ++-- 4 files changed, 5 insertions(+), 5 deletions(-) diff --git a/class_test.go b/class_test.go index d462407..58debed 100644 --- a/class_test.go +++ b/class_test.go @@ -48,7 +48,7 @@ func TestClassers(t *testing.T) { fmc2 := AllocFormatContext() require.NoError(t, fmc2.OpenInput("testdata/video.mp4", nil, nil)) path := filepath.Join(t.TempDir(), "iocontext.txt") - ic1, err := OpenIOContext(path, NewIOContextFlags(IOContextFlagWrite)) + ic1, err := OpenIOContext(path, NewIOContextFlags(IOContextFlagWrite), nil) require.NoError(t, err) defer os.RemoveAll(path) ic2, err := AllocIOContext(1, true, nil, nil, nil) diff --git a/examples/remuxing/main.go b/examples/remuxing/main.go index 9ea9713..f799707 100644 --- a/examples/remuxing/main.go +++ b/examples/remuxing/main.go @@ -103,7 +103,7 @@ func main() { // If this is a file, we need to use an io context if !outputFormatContext.OutputFormat().Flags().Has(astiav.IOFormatFlagNofile) { // Open io context - ioContext, err := astiav.OpenIOContext(*output, astiav.NewIOContextFlags(astiav.IOContextFlagWrite)) + ioContext, err := astiav.OpenIOContext(*output, astiav.NewIOContextFlags(astiav.IOContextFlagWrite), nil) if err != nil { log.Fatal(fmt.Errorf("main: opening io context failed: %w", err)) } diff --git a/examples/transcoding/main.go b/examples/transcoding/main.go index 3bf897d..0fea684 100644 --- a/examples/transcoding/main.go +++ b/examples/transcoding/main.go @@ -334,7 +334,7 @@ func openOutputFile() (err error) { if !outputFormatContext.OutputFormat().Flags().Has(astiav.IOFormatFlagNofile) { // Open io context var ioContext *astiav.IOContext - if ioContext, err = astiav.OpenIOContext(*output, astiav.NewIOContextFlags(astiav.IOContextFlagWrite)); err != nil { + if ioContext, err = astiav.OpenIOContext(*output, astiav.NewIOContextFlags(astiav.IOContextFlagWrite), nil); err != nil { err = fmt.Errorf("main: opening io context failed: %w", err) return } diff --git a/format_context_test.go b/format_context_test.go index f65f680..9f8ce6a 100644 --- a/format_context_test.go +++ b/format_context_test.go @@ -61,7 +61,7 @@ func TestFormatContext(t *testing.T) { fc3 := AllocFormatContext() require.NotNil(t, fc3) defer fc3.Free() - io, err := OpenIOContext("testdata/video.mp4", NewIOContextFlags(IOContextFlagRead)) + io, err := OpenIOContext("testdata/video.mp4", NewIOContextFlags(IOContextFlagRead), nil) require.NoError(t, err) defer io.Close() //nolint:errcheck fc3.SetPb(io) @@ -130,7 +130,7 @@ func TestFormatContext(t *testing.T) { require.NotNil(t, os) require.NoError(t, is.CodecParameters().Copy(os.CodecParameters())) } - ic, err := OpenIOContext(outputPath, NewIOContextFlags(IOContextFlagWrite)) + ic, err := OpenIOContext(outputPath, NewIOContextFlags(IOContextFlagWrite), nil) require.NoError(t, err) fc7.SetPb(ic) require.NoError(t, fc7.WriteHeader(nil)) From e4f6abc3d303a8aebdc70e5e6fc08c345a55b41c Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Thu, 12 Dec 2024 16:59:18 +0800 Subject: [PATCH 04/31] IOInterrupterCB --- class_test.go | 2 +- examples/remuxing/main.go | 2 +- examples/transcoding/main.go | 2 +- format_context_test.go | 4 ++-- io_context.go | 8 ++++++-- io_context_test.go | 4 +--- io_interrupter.go | 9 +++++++++ 7 files changed, 21 insertions(+), 10 deletions(-) diff --git a/class_test.go b/class_test.go index 58debed..3b3f320 100644 --- a/class_test.go +++ b/class_test.go @@ -48,7 +48,7 @@ func TestClassers(t *testing.T) { fmc2 := AllocFormatContext() require.NoError(t, fmc2.OpenInput("testdata/video.mp4", nil, nil)) path := filepath.Join(t.TempDir(), "iocontext.txt") - ic1, err := OpenIOContext(path, NewIOContextFlags(IOContextFlagWrite), nil) + ic1, err := OpenIOContext(path, NewIOContextFlags(IOContextFlagWrite), nil, nil) require.NoError(t, err) defer os.RemoveAll(path) ic2, err := AllocIOContext(1, true, nil, nil, nil) diff --git a/examples/remuxing/main.go b/examples/remuxing/main.go index f799707..eaed6bf 100644 --- a/examples/remuxing/main.go +++ b/examples/remuxing/main.go @@ -103,7 +103,7 @@ func main() { // If this is a file, we need to use an io context if !outputFormatContext.OutputFormat().Flags().Has(astiav.IOFormatFlagNofile) { // Open io context - ioContext, err := astiav.OpenIOContext(*output, astiav.NewIOContextFlags(astiav.IOContextFlagWrite), nil) + ioContext, err := astiav.OpenIOContext(*output, astiav.NewIOContextFlags(astiav.IOContextFlagWrite), nil, nil) if err != nil { log.Fatal(fmt.Errorf("main: opening io context failed: %w", err)) } diff --git a/examples/transcoding/main.go b/examples/transcoding/main.go index 0fea684..aa805cb 100644 --- a/examples/transcoding/main.go +++ b/examples/transcoding/main.go @@ -334,7 +334,7 @@ func openOutputFile() (err error) { if !outputFormatContext.OutputFormat().Flags().Has(astiav.IOFormatFlagNofile) { // Open io context var ioContext *astiav.IOContext - if ioContext, err = astiav.OpenIOContext(*output, astiav.NewIOContextFlags(astiav.IOContextFlagWrite), nil); err != nil { + if ioContext, err = astiav.OpenIOContext(*output, astiav.NewIOContextFlags(astiav.IOContextFlagWrite), nil, nil); err != nil { err = fmt.Errorf("main: opening io context failed: %w", err) return } diff --git a/format_context_test.go b/format_context_test.go index 9f8ce6a..20d0cf7 100644 --- a/format_context_test.go +++ b/format_context_test.go @@ -61,7 +61,7 @@ func TestFormatContext(t *testing.T) { fc3 := AllocFormatContext() require.NotNil(t, fc3) defer fc3.Free() - io, err := OpenIOContext("testdata/video.mp4", NewIOContextFlags(IOContextFlagRead), nil) + io, err := OpenIOContext("testdata/video.mp4", NewIOContextFlags(IOContextFlagRead), nil, nil) require.NoError(t, err) defer io.Close() //nolint:errcheck fc3.SetPb(io) @@ -130,7 +130,7 @@ func TestFormatContext(t *testing.T) { require.NotNil(t, os) require.NoError(t, is.CodecParameters().Copy(os.CodecParameters())) } - ic, err := OpenIOContext(outputPath, NewIOContextFlags(IOContextFlagWrite), nil) + ic, err := OpenIOContext(outputPath, NewIOContextFlags(IOContextFlagWrite), nil, nil) require.NoError(t, err) fc7.SetPb(ic) require.NoError(t, fc7.WriteHeader(nil)) diff --git a/io_context.go b/io_context.go index 1bdc28c..0cd73fe 100644 --- a/io_context.go +++ b/io_context.go @@ -109,15 +109,19 @@ func AllocIOContext(bufferSize int, writable bool, readFunc IOContextReadFunc, s } // https://ffmpeg.org/doxygen/7.0/avio_8c.html#ae8589aae955d16ca228b6b9d66ced33d -func OpenIOContext(filename string, flags IOContextFlags, d *Dictionary) (*IOContext, error) { +func OpenIOContext(filename string, flags IOContextFlags, cb *IOInterrupterCB, d *Dictionary) (*IOContext, error) { cfi := C.CString(filename) defer C.free(unsafe.Pointer(cfi)) var dc **C.AVDictionary if d != nil { dc = &d.c } + var cii *C.AVIOInterruptCB = nil + if cb != nil { + cii = &cb.c + } var c *C.AVIOContext - if err := newError(C.avio_open2(&c, cfi, C.int(flags), nil, dc)); err != nil { + if err := newError(C.avio_open2(&c, cfi, C.int(flags), cii, dc)); err != nil { return nil, err } return newIOContextFromC(c), nil diff --git a/io_context_test.go b/io_context_test.go index a2acec2..3a8b269 100644 --- a/io_context_test.go +++ b/io_context_test.go @@ -56,9 +56,7 @@ func TestIOContext(t *testing.T) { func TestOpenIOContext(t *testing.T) { path := filepath.Join(t.TempDir(), "iocontext.txt") - d := NewDictionary() - _ = d.Set("k", "v", 0) - c, err := OpenIOContext(path, NewIOContextFlags(IOContextFlagWrite), d) + c, err := OpenIOContext(path, NewIOContextFlags(IOContextFlagWrite), nil, nil) require.NoError(t, err) cl := c.Class() require.NotNil(t, cl) diff --git a/io_interrupter.go b/io_interrupter.go index 9ede1fe..ca1fbe0 100644 --- a/io_interrupter.go +++ b/io_interrupter.go @@ -6,6 +6,11 @@ import "C" type IOInterrupter interface { Interrupt() Resume() + CB() *IOInterrupterCB +} + +type IOInterrupterCB struct { + c C.AVIOInterruptCB } type defaultIOInterrupter struct { @@ -26,3 +31,7 @@ func (i *defaultIOInterrupter) Interrupt() { func (i *defaultIOInterrupter) Resume() { i.i = 0 } + +func (i *defaultIOInterrupter) CB() *IOInterrupterCB { + return &IOInterrupterCB{c: i.c} +} From a3c8b86200b84d9955e255c11c680a0ae73d76da Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Thu, 12 Dec 2024 17:23:47 +0800 Subject: [PATCH 05/31] OpenIOContext(filename string, flags IOContextFlags, ii *IOInterrupter, d *Dictionary) --- io_context.go | 6 +++--- io_interrupter.go | 26 ++++++++------------------ 2 files changed, 11 insertions(+), 21 deletions(-) diff --git a/io_context.go b/io_context.go index 0cd73fe..063e95d 100644 --- a/io_context.go +++ b/io_context.go @@ -109,7 +109,7 @@ func AllocIOContext(bufferSize int, writable bool, readFunc IOContextReadFunc, s } // https://ffmpeg.org/doxygen/7.0/avio_8c.html#ae8589aae955d16ca228b6b9d66ced33d -func OpenIOContext(filename string, flags IOContextFlags, cb *IOInterrupterCB, d *Dictionary) (*IOContext, error) { +func OpenIOContext(filename string, flags IOContextFlags, ii *IOInterrupter, d *Dictionary) (*IOContext, error) { cfi := C.CString(filename) defer C.free(unsafe.Pointer(cfi)) var dc **C.AVDictionary @@ -117,8 +117,8 @@ func OpenIOContext(filename string, flags IOContextFlags, cb *IOInterrupterCB, d dc = &d.c } var cii *C.AVIOInterruptCB = nil - if cb != nil { - cii = &cb.c + if ii != nil { + cii = &ii.c } var c *C.AVIOContext if err := newError(C.avio_open2(&c, cfi, C.int(flags), cii, dc)); err != nil { diff --git a/io_interrupter.go b/io_interrupter.go index ca1fbe0..88a5206 100644 --- a/io_interrupter.go +++ b/io_interrupter.go @@ -3,35 +3,25 @@ package astiav //#include "io_interrupter.h" import "C" -type IOInterrupter interface { - Interrupt() - Resume() - CB() *IOInterrupterCB -} - -type IOInterrupterCB struct { - c C.AVIOInterruptCB -} - -type defaultIOInterrupter struct { +type IOInterrupter struct { c C.AVIOInterruptCB i C.int } -func newDefaultIOInterrupter() *defaultIOInterrupter { - i := &defaultIOInterrupter{} +func NewIOInterrupter() *IOInterrupter { + i := &IOInterrupter{} i.c = C.astiavNewInterruptCallback(&i.i) return i } -func (i *defaultIOInterrupter) Interrupt() { +func (i *IOInterrupter) Interrupt() { i.i = 1 } -func (i *defaultIOInterrupter) Resume() { - i.i = 0 +func (i *IOInterrupter) Interrupted() bool { + return i.i == 1 } -func (i *defaultIOInterrupter) CB() *IOInterrupterCB { - return &IOInterrupterCB{c: i.c} +func (i *IOInterrupter) Resume() { + i.i = 0 } From 9894cd7a1f341b63256700de171d9d0b38acdb9d Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Fri, 13 Dec 2024 13:58:26 +0800 Subject: [PATCH 06/31] Program and Discard --- .gitignore | 3 +- discard.go | 17 +++++++++++ discard_test.go | 17 +++++++++++ program.go | 75 +++++++++++++++++++++++++++++++++++++++++++++++++ program_test.go | 9 ++++++ 5 files changed, 120 insertions(+), 1 deletion(-) create mode 100644 discard.go create mode 100644 discard_test.go diff --git a/.gitignore b/.gitignore index ee79665..5ac245f 100644 --- a/.gitignore +++ b/.gitignore @@ -1,2 +1,3 @@ .DS_STORE -coverage.out \ No newline at end of file +coverage.out +.idea \ No newline at end of file diff --git a/discard.go b/discard.go new file mode 100644 index 0000000..de524f7 --- /dev/null +++ b/discard.go @@ -0,0 +1,17 @@ +package astiav + +//#include +import "C" + +// https://ffmpeg.org/doxygen/7.0/group__lavc__decoding.html#ga352363bce7d3ed82c101b3bc001d1c16 +type Discard C.enum_AVDiscard + +const ( + DiscardNone = Discard(C.AVDISCARD_NONE) // discard nothing + DiscardDefault = Discard(C.AVDISCARD_DEFAULT) // discard useless packets like 0 size packets in avi + DiscardNonRef = Discard(C.AVDISCARD_NONREF) // discard all non reference + DiscardBidirectional = Discard(C.AVDISCARD_BIDIR) // discard all bidirectional frames + DiscardNonIntra = Discard(C.AVDISCARD_NONINTRA) // discard all non intra frames + DiscardNonKey = Discard(C.AVDISCARD_NONKEY) // discard all frames except keyframes + DiscardAll = Discard(C.AVDISCARD_ALL) // discard all +) diff --git a/discard_test.go b/discard_test.go new file mode 100644 index 0000000..780f9ea --- /dev/null +++ b/discard_test.go @@ -0,0 +1,17 @@ +package astiav + +import ( + "testing" + + "github.com/stretchr/testify/require" +) + +func TestDiscard(t *testing.T) { + require.Equal(t, int(DiscardNone), -16) + require.Equal(t, int(DiscardDefault), 0) + require.Equal(t, int(DiscardNonRef), 8) + require.Equal(t, int(DiscardBidirectional), 16) + require.Equal(t, int(DiscardNonIntra), 24) + require.Equal(t, int(DiscardNonKey), 32) + require.Equal(t, int(DiscardAll), 48) +} diff --git a/program.go b/program.go index 76863bf..694a720 100644 --- a/program.go +++ b/program.go @@ -55,3 +55,78 @@ func (p *Program) Streams() (ss []*Stream) { } return } + +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a8c87564167b87f54be9171778d51fe49 +func (p *Program) Flags() int { + return int(p.c.flags) +} + +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a8c87564167b87f54be9171778d51fe49 +func (p *Program) SetFlags(f int) { + p.c.flags = C.int(f) +} + +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a9c7a07c08a1f960aaa49f3f47633af5c +func (p *Program) Discard() Discard { + return Discard(p.c.discard) +} + +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a9c7a07c08a1f960aaa49f3f47633af5c +func (p *Program) SetDiscard(d Discard) { + p.c.discard = int32(d) +} + +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a7967d41af4812ed61a28762e988c7a02 +func (p *Program) StreamIndex() uint { + return uint(C.uint(*p.c.stream_index)) +} + +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#ae9dab38d4694e3da9cba0f882f4e43d3 +func (p *Program) Metadata() *Dictionary { + return newDictionaryFromC(p.c.metadata) +} + +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#ae9dab38d4694e3da9cba0f882f4e43d3 +func (p *Program) SetMetadata(d *Dictionary) { + p.c.metadata = d.c +} + +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a4c1539ea3c98da979b95a59a3ea163cb +func (p *Program) ProgramNum() int { + return int(p.c.program_num) +} + +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a02011963a63c291c6dc6d4eefa56cd69 +func (p *Program) PmtPid() int { + return int(p.c.pmt_pid) +} + +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a7e026323df87e84a72ec5e5c8ce341a5 +func (p *Program) PcrPid() int { + return int(p.c.pcr_pid) +} + +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#acac8164436263b310d867ec650a2ea58 +func (p *Program) PmtVersion() int { + return int(p.c.pmt_version) +} + +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a2276db4d51695120664d527f20b7c532 +func (p *Program) StartTime() int64 { + return int64(p.c.start_time) +} + +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a5a7795c918153d0f64d68a838e172db4 +func (p *Program) EndTime() int64 { + return int64(p.c.end_time) +} + +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a7e539e286876577e158039f6e7678452 +func (p *Program) PtsWrapReference() int64 { + return int64(p.c.pts_wrap_reference) +} + +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#aa3f8af78093a910ff766ac5af381758b +func (p *Program) PtsWrapBehavior() int { + return int(p.c.pts_wrap_behavior) +} diff --git a/program_test.go b/program_test.go index 6c15724..3d54163 100644 --- a/program_test.go +++ b/program_test.go @@ -22,4 +22,13 @@ func TestProgram(t *testing.T) { ss := p.Streams() require.Equal(t, 1, len(ss)) require.Equal(t, s.ID(), ss[0].ID()) + + p.SetFlags(1) + require.Equal(t, 1, p.Flags()) + p.SetDiscard(DiscardAll) + require.Equal(t, DiscardAll, p.Discard()) + d := NewDictionary() + _ = d.Set("service_name", "test_service_name", 0) + p.SetMetadata(d) + require.Equal(t, p.Metadata().Get("service_name", nil, 0).Value(), "test_service_name") } From 385462d8bd46f4f29c15b1696b12280ff9aff306 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Fri, 13 Dec 2024 14:15:54 +0800 Subject: [PATCH 07/31] Program and Discard --- program.go | 5 +++++ program_test.go | 2 ++ 2 files changed, 7 insertions(+) diff --git a/program.go b/program.go index 694a720..7a28797 100644 --- a/program.go +++ b/program.go @@ -96,6 +96,11 @@ func (p *Program) ProgramNum() int { return int(p.c.program_num) } +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a4c1539ea3c98da979b95a59a3ea163cb +func (p *Program) SetProgramNum(n int) { + p.c.program_num = C.int(n) +} + // https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a02011963a63c291c6dc6d4eefa56cd69 func (p *Program) PmtPid() int { return int(p.c.pmt_pid) diff --git a/program_test.go b/program_test.go index 3d54163..41010a7 100644 --- a/program_test.go +++ b/program_test.go @@ -25,6 +25,8 @@ func TestProgram(t *testing.T) { p.SetFlags(1) require.Equal(t, 1, p.Flags()) + p.SetProgramNum(101) + require.Equal(t, 101, p.ProgramNum()) p.SetDiscard(DiscardAll) require.Equal(t, DiscardAll, p.Discard()) d := NewDictionary() From e80f3ccf56c58d56ec8e2c1795ac2feefe8ff1be Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Fri, 13 Dec 2024 20:11:57 +0800 Subject: [PATCH 08/31] Program and Discard --- discard.go | 14 +++++++------- discard_test.go | 17 ----------------- program.go | 4 ++-- program_test.go | 21 ++++++++++----------- 4 files changed, 19 insertions(+), 37 deletions(-) delete mode 100644 discard_test.go diff --git a/discard.go b/discard.go index de524f7..e5b930a 100644 --- a/discard.go +++ b/discard.go @@ -7,11 +7,11 @@ import "C" type Discard C.enum_AVDiscard const ( - DiscardNone = Discard(C.AVDISCARD_NONE) // discard nothing - DiscardDefault = Discard(C.AVDISCARD_DEFAULT) // discard useless packets like 0 size packets in avi - DiscardNonRef = Discard(C.AVDISCARD_NONREF) // discard all non reference - DiscardBidirectional = Discard(C.AVDISCARD_BIDIR) // discard all bidirectional frames - DiscardNonIntra = Discard(C.AVDISCARD_NONINTRA) // discard all non intra frames - DiscardNonKey = Discard(C.AVDISCARD_NONKEY) // discard all frames except keyframes - DiscardAll = Discard(C.AVDISCARD_ALL) // discard all + DiscardNone = Discard(C.AVDISCARD_NONE) + DiscardDefault = Discard(C.AVDISCARD_DEFAULT) + DiscardNonRef = Discard(C.AVDISCARD_NONREF) + DiscardBidirectional = Discard(C.AVDISCARD_BIDIR) + DiscardNonIntra = Discard(C.AVDISCARD_NONINTRA) + DiscardNonKey = Discard(C.AVDISCARD_NONKEY) + DiscardAll = Discard(C.AVDISCARD_ALL) ) diff --git a/discard_test.go b/discard_test.go deleted file mode 100644 index 780f9ea..0000000 --- a/discard_test.go +++ /dev/null @@ -1,17 +0,0 @@ -package astiav - -import ( - "testing" - - "github.com/stretchr/testify/require" -) - -func TestDiscard(t *testing.T) { - require.Equal(t, int(DiscardNone), -16) - require.Equal(t, int(DiscardDefault), 0) - require.Equal(t, int(DiscardNonRef), 8) - require.Equal(t, int(DiscardBidirectional), 16) - require.Equal(t, int(DiscardNonIntra), 24) - require.Equal(t, int(DiscardNonKey), 32) - require.Equal(t, int(DiscardAll), 48) -} diff --git a/program.go b/program.go index 7a28797..f71a0d9 100644 --- a/program.go +++ b/program.go @@ -92,12 +92,12 @@ func (p *Program) SetMetadata(d *Dictionary) { } // https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a4c1539ea3c98da979b95a59a3ea163cb -func (p *Program) ProgramNum() int { +func (p *Program) ProgramNumber() int { return int(p.c.program_num) } // https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a4c1539ea3c98da979b95a59a3ea163cb -func (p *Program) SetProgramNum(n int) { +func (p *Program) SetProgramNumber(n int) { p.c.program_num = C.int(n) } diff --git a/program_test.go b/program_test.go index 41010a7..cc5c7f3 100644 --- a/program_test.go +++ b/program_test.go @@ -14,6 +14,16 @@ func TestProgram(t *testing.T) { require.Equal(t, 1, p.ID()) p.SetID(2) require.Equal(t, 2, p.ID()) + p.SetFlags(1) + require.Equal(t, 1, p.Flags()) + p.SetProgramNumber(101) + require.Equal(t, 101, p.ProgramNumber()) + p.SetDiscard(DiscardAll) + require.Equal(t, DiscardAll, p.Discard()) + d := NewDictionary() + require.NoError(t, d.Set("service_name", "test_service_name", 0)) + p.SetMetadata(d) + require.Equal(t, p.Metadata().Get("service_name", nil, 0).Value(), "test_service_name") s := fc.NewStream(nil) s.SetID(2) require.Equal(t, 0, p.NbStreams()) @@ -22,15 +32,4 @@ func TestProgram(t *testing.T) { ss := p.Streams() require.Equal(t, 1, len(ss)) require.Equal(t, s.ID(), ss[0].ID()) - - p.SetFlags(1) - require.Equal(t, 1, p.Flags()) - p.SetProgramNum(101) - require.Equal(t, 101, p.ProgramNum()) - p.SetDiscard(DiscardAll) - require.Equal(t, DiscardAll, p.Discard()) - d := NewDictionary() - _ = d.Set("service_name", "test_service_name", 0) - p.SetMetadata(d) - require.Equal(t, p.Metadata().Get("service_name", nil, 0).Value(), "test_service_name") } From ffb44b53a76df580c21579eb9d42bac16fa1da60 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Fri, 13 Dec 2024 20:29:47 +0800 Subject: [PATCH 09/31] Program and Discard --- program.go | 8 ++++++-- program_test.go | 12 ++++++++++-- 2 files changed, 16 insertions(+), 4 deletions(-) diff --git a/program.go b/program.go index f71a0d9..e00ef0d 100644 --- a/program.go +++ b/program.go @@ -77,8 +77,12 @@ func (p *Program) SetDiscard(d Discard) { } // https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a7967d41af4812ed61a28762e988c7a02 -func (p *Program) StreamIndex() uint { - return uint(C.uint(*p.c.stream_index)) +func (p *Program) StreamIndex() *uint { + if p.c.stream_index == nil { + return nil + } + u := uint(C.uint(*p.c.stream_index)) + return &u } // https://ffmpeg.org/doxygen/7.0/structAVProgram.html#ae9dab38d4694e3da9cba0f882f4e43d3 diff --git a/program_test.go b/program_test.go index cc5c7f3..fb33bbc 100644 --- a/program_test.go +++ b/program_test.go @@ -16,14 +16,22 @@ func TestProgram(t *testing.T) { require.Equal(t, 2, p.ID()) p.SetFlags(1) require.Equal(t, 1, p.Flags()) - p.SetProgramNumber(101) - require.Equal(t, 101, p.ProgramNumber()) p.SetDiscard(DiscardAll) require.Equal(t, DiscardAll, p.Discard()) + require.Nil(t, p.StreamIndex(), nil) d := NewDictionary() require.NoError(t, d.Set("service_name", "test_service_name", 0)) p.SetMetadata(d) require.Equal(t, p.Metadata().Get("service_name", nil, 0).Value(), "test_service_name") + p.SetProgramNumber(101) + require.Equal(t, 101, p.ProgramNumber()) + require.Equal(t, p.PmtPid(), 0) + require.Equal(t, p.PcrPid(), 0) + require.Equal(t, p.PmtVersion(), -1) + require.Equal(t, p.StartTime(), int64(-9223372036854775808)) + require.Equal(t, p.EndTime(), int64(-9223372036854775808)) + require.Equal(t, p.PtsWrapReference(), int64(-9223372036854775808)) + require.Equal(t, p.PtsWrapBehavior(), 0) s := fc.NewStream(nil) s.SetID(2) require.Equal(t, 0, p.NbStreams()) From 64a05c0527bf4d00654c5bd329ea3dafc66ec2f7 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Sat, 14 Dec 2024 12:34:13 +0800 Subject: [PATCH 10/31] Program and Discard --- program.go | 5 ----- 1 file changed, 5 deletions(-) diff --git a/program.go b/program.go index e00ef0d..7578b35 100644 --- a/program.go +++ b/program.go @@ -61,11 +61,6 @@ func (p *Program) Flags() int { return int(p.c.flags) } -// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a8c87564167b87f54be9171778d51fe49 -func (p *Program) SetFlags(f int) { - p.c.flags = C.int(f) -} - // https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a9c7a07c08a1f960aaa49f3f47633af5c func (p *Program) Discard() Discard { return Discard(p.c.discard) From 213eb4624d4fcfd2535cce2ddb89b0910a732cb9 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Sat, 14 Dec 2024 12:36:33 +0800 Subject: [PATCH 11/31] Program and Discard --- program_test.go | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/program_test.go b/program_test.go index fb33bbc..6c792b7 100644 --- a/program_test.go +++ b/program_test.go @@ -14,8 +14,7 @@ func TestProgram(t *testing.T) { require.Equal(t, 1, p.ID()) p.SetID(2) require.Equal(t, 2, p.ID()) - p.SetFlags(1) - require.Equal(t, 1, p.Flags()) + require.Equal(t, 0, p.Flags()) p.SetDiscard(DiscardAll) require.Equal(t, DiscardAll, p.Discard()) require.Nil(t, p.StreamIndex(), nil) From a24d493bba1f60ff91b94a95917be12f707d1bb8 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Mon, 16 Dec 2024 15:19:45 +0800 Subject: [PATCH 12/31] CodecContext MaxBFrames() SetMaxBFrames(n int) --- codec_context.go | 10 ++++++++++ codec_context_test.go | 2 ++ 2 files changed, 12 insertions(+) diff --git a/codec_context.go b/codec_context.go index d92215f..fba3a7c 100644 --- a/codec_context.go +++ b/codec_context.go @@ -455,3 +455,13 @@ func goAstiavCodecContextGetFormat(cc *C.AVCodecContext, pfsCPtr *C.enum_AVPixel // Callback return C.enum_AVPixelFormat(c(pfs)) } + +// https://ffmpeg.org/doxygen/7.0/structAVCodecContext.html#a3e5334a611a3e2a6a653805bb9e2d4d4 +func (cc *CodecContext) MaxBFrames() int { + return int(cc.c.max_b_frames) +} + +// https://ffmpeg.org/doxygen/7.0/structAVCodecContext.html#a3e5334a611a3e2a6a653805bb9e2d4d4 +func (cc *CodecContext) SetMaxBFrames(n int) { + cc.c.max_b_frames = C.int(n) +} diff --git a/codec_context_test.go b/codec_context_test.go index 6f18b6c..759234b 100644 --- a/codec_context_test.go +++ b/codec_context_test.go @@ -101,6 +101,7 @@ func TestCodecContext(t *testing.T) { cc4.SetTimeBase(NewRational(15, 1)) cc4.SetWidth(16) cc4.SetExtraHardwareFrames(4) + cc4.SetMaxBFrames(1) require.Equal(t, int64(1), cc4.BitRate()) require.True(t, cc4.ChannelLayout().Equal(ChannelLayout21)) require.Equal(t, NewCodecContextFlags(4), cc4.Flags()) @@ -121,6 +122,7 @@ func TestCodecContext(t *testing.T) { require.Equal(t, NewRational(15, 1), cc4.TimeBase()) require.Equal(t, 16, cc4.Width()) require.Equal(t, 4, cc4.ExtraHardwareFrames()) + require.Equal(t, 1, cc4.MaxBFrames()) cc5 := AllocCodecContext(nil) require.NotNil(t, cc5) From 6750680fb06518d26cfd8a09c223a9061ccf4403 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Tue, 17 Dec 2024 10:39:50 +0800 Subject: [PATCH 13/31] another pr --- codec_context.go | 10 ---------- codec_context_test.go | 2 -- 2 files changed, 12 deletions(-) diff --git a/codec_context.go b/codec_context.go index fba3a7c..d92215f 100644 --- a/codec_context.go +++ b/codec_context.go @@ -455,13 +455,3 @@ func goAstiavCodecContextGetFormat(cc *C.AVCodecContext, pfsCPtr *C.enum_AVPixel // Callback return C.enum_AVPixelFormat(c(pfs)) } - -// https://ffmpeg.org/doxygen/7.0/structAVCodecContext.html#a3e5334a611a3e2a6a653805bb9e2d4d4 -func (cc *CodecContext) MaxBFrames() int { - return int(cc.c.max_b_frames) -} - -// https://ffmpeg.org/doxygen/7.0/structAVCodecContext.html#a3e5334a611a3e2a6a653805bb9e2d4d4 -func (cc *CodecContext) SetMaxBFrames(n int) { - cc.c.max_b_frames = C.int(n) -} diff --git a/codec_context_test.go b/codec_context_test.go index 759234b..6f18b6c 100644 --- a/codec_context_test.go +++ b/codec_context_test.go @@ -101,7 +101,6 @@ func TestCodecContext(t *testing.T) { cc4.SetTimeBase(NewRational(15, 1)) cc4.SetWidth(16) cc4.SetExtraHardwareFrames(4) - cc4.SetMaxBFrames(1) require.Equal(t, int64(1), cc4.BitRate()) require.True(t, cc4.ChannelLayout().Equal(ChannelLayout21)) require.Equal(t, NewCodecContextFlags(4), cc4.Flags()) @@ -122,7 +121,6 @@ func TestCodecContext(t *testing.T) { require.Equal(t, NewRational(15, 1), cc4.TimeBase()) require.Equal(t, 16, cc4.Width()) require.Equal(t, 4, cc4.ExtraHardwareFrames()) - require.Equal(t, 1, cc4.MaxBFrames()) cc5 := AllocCodecContext(nil) require.NotNil(t, cc5) From 5bcf20763cb55c2d99b5a67492abcc1264714927 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Tue, 17 Dec 2024 16:29:23 +0800 Subject: [PATCH 14/31] delete Flags() --- program.go | 5 ----- program_test.go | 1 - 2 files changed, 6 deletions(-) diff --git a/program.go b/program.go index 7578b35..74d14ef 100644 --- a/program.go +++ b/program.go @@ -56,11 +56,6 @@ func (p *Program) Streams() (ss []*Stream) { return } -// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a8c87564167b87f54be9171778d51fe49 -func (p *Program) Flags() int { - return int(p.c.flags) -} - // https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a9c7a07c08a1f960aaa49f3f47633af5c func (p *Program) Discard() Discard { return Discard(p.c.discard) diff --git a/program_test.go b/program_test.go index 6c792b7..5ea2c9c 100644 --- a/program_test.go +++ b/program_test.go @@ -14,7 +14,6 @@ func TestProgram(t *testing.T) { require.Equal(t, 1, p.ID()) p.SetID(2) require.Equal(t, 2, p.ID()) - require.Equal(t, 0, p.Flags()) p.SetDiscard(DiscardAll) require.Equal(t, DiscardAll, p.Discard()) require.Nil(t, p.StreamIndex(), nil) From cf06f771e7261fa80a0834a9885fcc350b404fee Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Tue, 17 Dec 2024 18:35:54 +0800 Subject: [PATCH 15/31] delete Flags() --- program.go | 15 --------------- 1 file changed, 15 deletions(-) diff --git a/program.go b/program.go index 74d14ef..bf9fd70 100644 --- a/program.go +++ b/program.go @@ -95,21 +95,6 @@ func (p *Program) SetProgramNumber(n int) { p.c.program_num = C.int(n) } -// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a02011963a63c291c6dc6d4eefa56cd69 -func (p *Program) PmtPid() int { - return int(p.c.pmt_pid) -} - -// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a7e026323df87e84a72ec5e5c8ce341a5 -func (p *Program) PcrPid() int { - return int(p.c.pcr_pid) -} - -// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#acac8164436263b310d867ec650a2ea58 -func (p *Program) PmtVersion() int { - return int(p.c.pmt_version) -} - // https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a2276db4d51695120664d527f20b7c532 func (p *Program) StartTime() int64 { return int64(p.c.start_time) From c0e22afe2fdabdf17cb8c70b96b68855da8de9b4 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Tue, 17 Dec 2024 18:36:12 +0800 Subject: [PATCH 16/31] delete Flags() --- program_test.go | 3 --- 1 file changed, 3 deletions(-) diff --git a/program_test.go b/program_test.go index 5ea2c9c..d62c051 100644 --- a/program_test.go +++ b/program_test.go @@ -23,9 +23,6 @@ func TestProgram(t *testing.T) { require.Equal(t, p.Metadata().Get("service_name", nil, 0).Value(), "test_service_name") p.SetProgramNumber(101) require.Equal(t, 101, p.ProgramNumber()) - require.Equal(t, p.PmtPid(), 0) - require.Equal(t, p.PcrPid(), 0) - require.Equal(t, p.PmtVersion(), -1) require.Equal(t, p.StartTime(), int64(-9223372036854775808)) require.Equal(t, p.EndTime(), int64(-9223372036854775808)) require.Equal(t, p.PtsWrapReference(), int64(-9223372036854775808)) From 4fb268faadcaf22bca53f9ca3f23b1947da6ab29 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Tue, 17 Dec 2024 18:47:50 +0800 Subject: [PATCH 17/31] delete PmtVersion() --- program.go | 20 ++++++++++++++++++++ program_test.go | 4 ++++ 2 files changed, 24 insertions(+) diff --git a/program.go b/program.go index bf9fd70..60b3dcc 100644 --- a/program.go +++ b/program.go @@ -95,6 +95,26 @@ func (p *Program) SetProgramNumber(n int) { p.c.program_num = C.int(n) } +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a02011963a63c291c6dc6d4eefa56cd69 +func (p *Program) PmtPid() int { + return int(p.c.pmt_pid) +} + +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a02011963a63c291c6dc6d4eefa56cd69 +func (p *Program) SetPmtPid(n int) { + p.c.pmt_pid = C.int(n) +} + +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a7e026323df87e84a72ec5e5c8ce341a5 +func (p *Program) PcrPid() int { + return int(p.c.pcr_pid) +} + +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a7e026323df87e84a72ec5e5c8ce341a5 +func (p *Program) SetPcrPid(n int) { + p.c.pcr_pid = C.int(n) +} + // https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a2276db4d51695120664d527f20b7c532 func (p *Program) StartTime() int64 { return int64(p.c.start_time) diff --git a/program_test.go b/program_test.go index d62c051..50a604d 100644 --- a/program_test.go +++ b/program_test.go @@ -23,6 +23,10 @@ func TestProgram(t *testing.T) { require.Equal(t, p.Metadata().Get("service_name", nil, 0).Value(), "test_service_name") p.SetProgramNumber(101) require.Equal(t, 101, p.ProgramNumber()) + p.SetPmtPid(201) + require.Equal(t, 201, p.PmtPid()) + p.SetPcrPid(301) + require.Equal(t, 301, p.PcrPid()) require.Equal(t, p.StartTime(), int64(-9223372036854775808)) require.Equal(t, p.EndTime(), int64(-9223372036854775808)) require.Equal(t, p.PtsWrapReference(), int64(-9223372036854775808)) From 13bb06083c71921c0f992e2a9f16b7b3668a65d7 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Wed, 18 Dec 2024 11:23:08 +0800 Subject: [PATCH 18/31] SetStreamIndex --- program.go | 7 +++++++ program_test.go | 7 ++++++- 2 files changed, 13 insertions(+), 1 deletion(-) diff --git a/program.go b/program.go index 60b3dcc..e8ff9c4 100644 --- a/program.go +++ b/program.go @@ -75,6 +75,13 @@ func (p *Program) StreamIndex() *uint { return &u } +// https://ffmpeg.org/doxygen/7.0/structAVProgram.html#a7967d41af4812ed61a28762e988c7a02 +func (p *Program) SetStreamIndex(n uint) { + if p.c.stream_index != nil { + *p.c.stream_index = C.uint(n) + } +} + // https://ffmpeg.org/doxygen/7.0/structAVProgram.html#ae9dab38d4694e3da9cba0f882f4e43d3 func (p *Program) Metadata() *Dictionary { return newDictionaryFromC(p.c.metadata) diff --git a/program_test.go b/program_test.go index 50a604d..19f7ea4 100644 --- a/program_test.go +++ b/program_test.go @@ -16,7 +16,6 @@ func TestProgram(t *testing.T) { require.Equal(t, 2, p.ID()) p.SetDiscard(DiscardAll) require.Equal(t, DiscardAll, p.Discard()) - require.Nil(t, p.StreamIndex(), nil) d := NewDictionary() require.NoError(t, d.Set("service_name", "test_service_name", 0)) p.SetMetadata(d) @@ -34,8 +33,14 @@ func TestProgram(t *testing.T) { s := fc.NewStream(nil) s.SetID(2) require.Equal(t, 0, p.NbStreams()) + require.Nil(t, p.StreamIndex(), nil) p.AddStream(s) require.Equal(t, 1, p.NbStreams()) + require.Equal(t, uint(0), *p.StreamIndex()) + var streamIndex uint = 1 + p.SetStreamIndex(streamIndex) + require.Equal(t, streamIndex, *p.StreamIndex()) + s.SetIndex(int(streamIndex)) ss := p.Streams() require.Equal(t, 1, len(ss)) require.Equal(t, s.ID(), ss[0].ID()) From dec5570f0389afe18adb0ed824a9ad6d42342830 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Wed, 18 Dec 2024 11:28:50 +0800 Subject: [PATCH 19/31] SetStreamIndex --- program_test.go | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/program_test.go b/program_test.go index 19f7ea4..db8ede3 100644 --- a/program_test.go +++ b/program_test.go @@ -26,9 +26,9 @@ func TestProgram(t *testing.T) { require.Equal(t, 201, p.PmtPid()) p.SetPcrPid(301) require.Equal(t, 301, p.PcrPid()) - require.Equal(t, p.StartTime(), int64(-9223372036854775808)) - require.Equal(t, p.EndTime(), int64(-9223372036854775808)) - require.Equal(t, p.PtsWrapReference(), int64(-9223372036854775808)) + require.Equal(t, p.StartTime(), NoPtsValue) + require.Equal(t, p.EndTime(), NoPtsValue) + require.Equal(t, p.PtsWrapReference(), NoPtsValue) require.Equal(t, p.PtsWrapBehavior(), 0) s := fc.NewStream(nil) s.SetID(2) From a27bb0fbfdc2ff0b99bee5361782822b9c2e548f Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Wed, 18 Dec 2024 18:25:27 +0800 Subject: [PATCH 20/31] MaxBFrames() SetMaxBFrames(n int) RcMaxRate() SetRcMaxRate(n int64) RcMinRate() SetRcMinRate(n int64) RcBufferSize() SetRcBufferSize(n int) --- codec_context.go | 40 ++++++++++++++++++++++++++++++++++++++++ codec_context_test.go | 8 ++++++++ program_test.go | 6 ------ 3 files changed, 48 insertions(+), 6 deletions(-) diff --git a/codec_context.go b/codec_context.go index d92215f..4edf11a 100644 --- a/codec_context.go +++ b/codec_context.go @@ -455,3 +455,43 @@ func goAstiavCodecContextGetFormat(cc *C.AVCodecContext, pfsCPtr *C.enum_AVPixel // Callback return C.enum_AVPixelFormat(c(pfs)) } + +// https://ffmpeg.org/doxygen/7.0/structAVCodecContext.html#a3e5334a611a3e2a6a653805bb9e2d4d4 +func (cc *CodecContext) MaxBFrames() int { + return int(cc.c.max_b_frames) +} + +// https://ffmpeg.org/doxygen/7.0/structAVCodecContext.html#a3e5334a611a3e2a6a653805bb9e2d4d4 +func (cc *CodecContext) SetMaxBFrames(n int) { + cc.c.max_b_frames = C.int(n) +} + +// https://ffmpeg.org/doxygen/7.0/structAVCodecContext.html#aa2b5582f1a360534310b686cc3f7c668 +func (cc *CodecContext) RcMaxRate() int64 { + return int64(cc.c.rc_max_rate) +} + +// https://ffmpeg.org/doxygen/7.0/structAVCodecContext.html#aa2b5582f1a360534310b686cc3f7c668 +func (cc *CodecContext) SetRcMaxRate(n int64) { + cc.c.rc_max_rate = C.int64_t(n) +} + +// https://ffmpeg.org/doxygen/7.0/structAVCodecContext.html#ac265c70b89e87455ec05eb2978def81b +func (cc *CodecContext) RcMinRate() int64 { + return int64(cc.c.rc_min_rate) +} + +// https://ffmpeg.org/doxygen/7.0/structAVCodecContext.html#ac265c70b89e87455ec05eb2978def81b +func (cc *CodecContext) SetRcMinRate(n int64) { + cc.c.rc_min_rate = C.int64_t(n) +} + +// https://ffmpeg.org/doxygen/7.0/structAVCodecContext.html#a15000607a7e2371162348bb35b0184c1 +func (cc *CodecContext) RcBufferSize() int { + return int(cc.c.rc_buffer_size) +} + +// https://ffmpeg.org/doxygen/7.0/structAVCodecContext.html#a15000607a7e2371162348bb35b0184c1 +func (cc *CodecContext) SetRcBufferSize(n int) { + cc.c.rc_buffer_size = C.int(n) +} diff --git a/codec_context_test.go b/codec_context_test.go index 6f18b6c..57fef52 100644 --- a/codec_context_test.go +++ b/codec_context_test.go @@ -101,6 +101,10 @@ func TestCodecContext(t *testing.T) { cc4.SetTimeBase(NewRational(15, 1)) cc4.SetWidth(16) cc4.SetExtraHardwareFrames(4) + cc4.SetMaxBFrames(1) + cc4.SetRcMaxRate(1_5000_000) + cc4.SetRcMinRate(1_5000_000) + cc4.SetRcBufferSize(1_5000_000) require.Equal(t, int64(1), cc4.BitRate()) require.True(t, cc4.ChannelLayout().Equal(ChannelLayout21)) require.Equal(t, NewCodecContextFlags(4), cc4.Flags()) @@ -121,6 +125,10 @@ func TestCodecContext(t *testing.T) { require.Equal(t, NewRational(15, 1), cc4.TimeBase()) require.Equal(t, 16, cc4.Width()) require.Equal(t, 4, cc4.ExtraHardwareFrames()) + require.Equal(t, 1, cc4.MaxBFrames()) + require.Equal(t, 1_5000_000, cc4.RcMaxRate()) + require.Equal(t, 1_5000_000, cc4.RcMinRate()) + require.Equal(t, 1_5000_000, cc4.RcBufferSize()) cc5 := AllocCodecContext(nil) require.NotNil(t, cc5) diff --git a/program_test.go b/program_test.go index db8ede3..9445e7d 100644 --- a/program_test.go +++ b/program_test.go @@ -33,14 +33,8 @@ func TestProgram(t *testing.T) { s := fc.NewStream(nil) s.SetID(2) require.Equal(t, 0, p.NbStreams()) - require.Nil(t, p.StreamIndex(), nil) p.AddStream(s) require.Equal(t, 1, p.NbStreams()) - require.Equal(t, uint(0), *p.StreamIndex()) - var streamIndex uint = 1 - p.SetStreamIndex(streamIndex) - require.Equal(t, streamIndex, *p.StreamIndex()) - s.SetIndex(int(streamIndex)) ss := p.Streams() require.Equal(t, 1, len(ss)) require.Equal(t, s.ID(), ss[0].ID()) From eb4cba6e74551fb74198953128fd8d2ce4747e97 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Thu, 19 Dec 2024 09:34:42 +0800 Subject: [PATCH 21/31] rename rate control methods --- codec_context.go | 12 ++++++------ codec_context_test.go | 12 ++++++------ 2 files changed, 12 insertions(+), 12 deletions(-) diff --git a/codec_context.go b/codec_context.go index 4edf11a..0ff2ae5 100644 --- a/codec_context.go +++ b/codec_context.go @@ -467,31 +467,31 @@ func (cc *CodecContext) SetMaxBFrames(n int) { } // https://ffmpeg.org/doxygen/7.0/structAVCodecContext.html#aa2b5582f1a360534310b686cc3f7c668 -func (cc *CodecContext) RcMaxRate() int64 { +func (cc *CodecContext) RateControlMaxRate() int64 { return int64(cc.c.rc_max_rate) } // https://ffmpeg.org/doxygen/7.0/structAVCodecContext.html#aa2b5582f1a360534310b686cc3f7c668 -func (cc *CodecContext) SetRcMaxRate(n int64) { +func (cc *CodecContext) SetRateControlMaxRate(n int64) { cc.c.rc_max_rate = C.int64_t(n) } // https://ffmpeg.org/doxygen/7.0/structAVCodecContext.html#ac265c70b89e87455ec05eb2978def81b -func (cc *CodecContext) RcMinRate() int64 { +func (cc *CodecContext) RateControlMinRate() int64 { return int64(cc.c.rc_min_rate) } // https://ffmpeg.org/doxygen/7.0/structAVCodecContext.html#ac265c70b89e87455ec05eb2978def81b -func (cc *CodecContext) SetRcMinRate(n int64) { +func (cc *CodecContext) SetRateControlMinRate(n int64) { cc.c.rc_min_rate = C.int64_t(n) } // https://ffmpeg.org/doxygen/7.0/structAVCodecContext.html#a15000607a7e2371162348bb35b0184c1 -func (cc *CodecContext) RcBufferSize() int { +func (cc *CodecContext) RateControlBufferSize() int { return int(cc.c.rc_buffer_size) } // https://ffmpeg.org/doxygen/7.0/structAVCodecContext.html#a15000607a7e2371162348bb35b0184c1 -func (cc *CodecContext) SetRcBufferSize(n int) { +func (cc *CodecContext) SetRateControlBufferSize(n int) { cc.c.rc_buffer_size = C.int(n) } diff --git a/codec_context_test.go b/codec_context_test.go index 57fef52..69ab042 100644 --- a/codec_context_test.go +++ b/codec_context_test.go @@ -102,9 +102,9 @@ func TestCodecContext(t *testing.T) { cc4.SetWidth(16) cc4.SetExtraHardwareFrames(4) cc4.SetMaxBFrames(1) - cc4.SetRcMaxRate(1_5000_000) - cc4.SetRcMinRate(1_5000_000) - cc4.SetRcBufferSize(1_5000_000) + cc4.SetRateControlMaxRate(int64(1_5000_000)) + cc4.SetRateControlMinRate(int64(1_5000_000)) + cc4.SetRateControlBufferSize(1_5000_000) require.Equal(t, int64(1), cc4.BitRate()) require.True(t, cc4.ChannelLayout().Equal(ChannelLayout21)) require.Equal(t, NewCodecContextFlags(4), cc4.Flags()) @@ -126,9 +126,9 @@ func TestCodecContext(t *testing.T) { require.Equal(t, 16, cc4.Width()) require.Equal(t, 4, cc4.ExtraHardwareFrames()) require.Equal(t, 1, cc4.MaxBFrames()) - require.Equal(t, 1_5000_000, cc4.RcMaxRate()) - require.Equal(t, 1_5000_000, cc4.RcMinRate()) - require.Equal(t, 1_5000_000, cc4.RcBufferSize()) + require.Equal(t, 1_5000_000, cc4.RateControlMaxRate()) + require.Equal(t, 1_5000_000, cc4.RateControlMinRate()) + require.Equal(t, 1_5000_000, cc4.RateControlBufferSize()) cc5 := AllocCodecContext(nil) require.NotNil(t, cc5) From 882e8d8608985b587e45c0dde9263178d85dcc24 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Thu, 19 Dec 2024 19:05:12 +0800 Subject: [PATCH 22/31] test passed --- codec_context_test.go | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/codec_context_test.go b/codec_context_test.go index 69ab042..1ea6b9f 100644 --- a/codec_context_test.go +++ b/codec_context_test.go @@ -102,9 +102,9 @@ func TestCodecContext(t *testing.T) { cc4.SetWidth(16) cc4.SetExtraHardwareFrames(4) cc4.SetMaxBFrames(1) - cc4.SetRateControlMaxRate(int64(1_5000_000)) - cc4.SetRateControlMinRate(int64(1_5000_000)) - cc4.SetRateControlBufferSize(1_5000_000) + cc4.SetRateControlMaxRate(1_500_000) + cc4.SetRateControlMinRate(1_500_000) + cc4.SetRateControlBufferSize(1_500_000) require.Equal(t, int64(1), cc4.BitRate()) require.True(t, cc4.ChannelLayout().Equal(ChannelLayout21)) require.Equal(t, NewCodecContextFlags(4), cc4.Flags()) @@ -126,9 +126,9 @@ func TestCodecContext(t *testing.T) { require.Equal(t, 16, cc4.Width()) require.Equal(t, 4, cc4.ExtraHardwareFrames()) require.Equal(t, 1, cc4.MaxBFrames()) - require.Equal(t, 1_5000_000, cc4.RateControlMaxRate()) - require.Equal(t, 1_5000_000, cc4.RateControlMinRate()) - require.Equal(t, 1_5000_000, cc4.RateControlBufferSize()) + require.Equal(t, int64(1_500_000), cc4.RateControlMaxRate()) + require.Equal(t, int64(1_500_000), cc4.RateControlMinRate()) + require.Equal(t, 1_500_000, cc4.RateControlBufferSize()) cc5 := AllocCodecContext(nil) require.NotNil(t, cc5) From 2b1c4885c6df7e50a686985aa1a0e5995e1fdc88 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Mon, 23 Dec 2024 13:12:54 +0800 Subject: [PATCH 23/31] bufferSrcCtx initialize with dictionary --- buffersrc_filter_context.go | 8 ++++++-- buffersrc_filter_context_test.go | 16 ++++++++++++++++ examples/filtering/main.go | 2 +- examples/hardware_decoding_filtering/main.go | 2 +- examples/transcoding/main.go | 2 +- filter_graph_test.go | 2 +- 6 files changed, 26 insertions(+), 6 deletions(-) create mode 100644 buffersrc_filter_context_test.go diff --git a/buffersrc_filter_context.go b/buffersrc_filter_context.go index 131722f..86caf2e 100644 --- a/buffersrc_filter_context.go +++ b/buffersrc_filter_context.go @@ -25,8 +25,12 @@ func (bfc *BuffersrcFilterContext) FilterContext() *FilterContext { } // https://ffmpeg.org/doxygen/7.0/group__lavfi.html#ga8c15af28902395399fe455f6f8236848 -func (bfc *BuffersrcFilterContext) Initialize() error { - return newError(C.avfilter_init_dict(bfc.fc.c, nil)) +func (bfc *BuffersrcFilterContext) Initialize(d *Dictionary) error { + var dc **C.AVDictionary + if d != nil { + dc = &d.c + } + return newError(C.avfilter_init_dict(bfc.fc.c, dc)) } // https://ffmpeg.org/doxygen/7.0/group__lavfi__buffersrc.html#ga398cd2a84f8b4a588197ab9d90135048 diff --git a/buffersrc_filter_context_test.go b/buffersrc_filter_context_test.go new file mode 100644 index 0000000..b363fed --- /dev/null +++ b/buffersrc_filter_context_test.go @@ -0,0 +1,16 @@ +package astiav + +import ( + "github.com/stretchr/testify/require" + "testing" +) + +func TestBuffersrcFilterContext(t *testing.T) { + fg := AllocFilterGraph() + filter := FindFilterByName("movie") + bufferSrcCtx, err := fg.NewBuffersrcFilterContext(filter, "movie") + require.NoError(t, err) + d := NewDictionary() + require.NoError(t, d.Set("filename", "testdata/video.mp4", 0)) + require.NoError(t, bufferSrcCtx.Initialize(d)) +} diff --git a/examples/filtering/main.go b/examples/filtering/main.go index cbf57f8..3b667df 100644 --- a/examples/filtering/main.go +++ b/examples/filtering/main.go @@ -274,7 +274,7 @@ func initFilter() (err error) { } // Initialize buffersrc context - if err = s.buffersrcContext.Initialize(); err != nil { + if err = s.buffersrcContext.Initialize(nil); err != nil { err = fmt.Errorf("main: initializing buffersrc context failed: %w", err) return } diff --git a/examples/hardware_decoding_filtering/main.go b/examples/hardware_decoding_filtering/main.go index 0d3fade..2a0dc6d 100644 --- a/examples/hardware_decoding_filtering/main.go +++ b/examples/hardware_decoding_filtering/main.go @@ -319,7 +319,7 @@ func initFilter() (err error) { } // Initialize buffersrc context - if err = buffersrcContext.Initialize(); err != nil { + if err = buffersrcContext.Initialize(nil); err != nil { err = fmt.Errorf("main: initializing buffersrc context failed: %w", err) return } diff --git a/examples/transcoding/main.go b/examples/transcoding/main.go index 0576388..657201d 100644 --- a/examples/transcoding/main.go +++ b/examples/transcoding/main.go @@ -431,7 +431,7 @@ func initFilters() (err error) { } // Initialize buffersrc context - if err = s.buffersrcContext.Initialize(); err != nil { + if err = s.buffersrcContext.Initialize(nil); err != nil { err = fmt.Errorf("main: initializing buffersrc context failed: %w", err) return } diff --git a/filter_graph_test.go b/filter_graph_test.go index 8e728f8..9e5d11d 100644 --- a/filter_graph_test.go +++ b/filter_graph_test.go @@ -182,7 +182,7 @@ func TestFilterGraph(t *testing.T) { buffersrcContextParameters.SetWidth(src.width) } buffersrcContext.SetParameters(buffersrcContextParameters) - require.NoError(t, buffersrcContext.Initialize()) + require.NoError(t, buffersrcContext.Initialize(nil)) buffersrcContexts = append(buffersrcContexts, buffersrcContext) o := AllocFilterInOut() From a5aeb81fd6573d78c92361420073666d8e54ecfa Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Mon, 23 Dec 2024 17:28:48 +0800 Subject: [PATCH 24/31] bufferSrcCtx initialize with dictionary --- filter_context.go | 12 ++++++++++++ filter_graph.go | 15 +++++++++++++++ filter_graph_test.go | 37 +++++++++++++++++++++++++++++++++++++ 3 files changed, 64 insertions(+) diff --git a/filter_context.go b/filter_context.go index c911a40..6fe2248 100644 --- a/filter_context.go +++ b/filter_context.go @@ -39,3 +39,15 @@ func (fc *FilterContext) Free() { func (fc *FilterContext) Class() *Class { return newClassFromC(unsafe.Pointer(fc.c)) } + +// https://ffmpeg.org/doxygen/7.0/structAVFilterContext.html#addd946fbe5af506a2b19f9ad7cb97c35 +func (fc *FilterContext) SetHardwareDeviceContext(hdc *HardwareDeviceContext) { + if fc.c.hw_device_ctx != nil { + C.av_buffer_unref(&fc.c.hw_device_ctx) + } + if hdc != nil { + fc.c.hw_device_ctx = hdc.c + } else { + fc.c.hw_device_ctx = nil + } +} diff --git a/filter_graph.go b/filter_graph.go index 46ec6a2..bd26739 100644 --- a/filter_graph.go +++ b/filter_graph.go @@ -4,6 +4,7 @@ package astiav import "C" import ( "errors" + "math" "unsafe" ) @@ -154,3 +155,17 @@ func (g *FilterGraph) SendCommand(target, cmd, args string, f FilterCommandFlags }) return } + +// https://ffmpeg.org/doxygen/7.0/structAVFilterGraph.html#a0ba5c820c760788ea5f8e40c476f9704 +func (g *FilterGraph) NbFilters() int { + return int(g.c.nb_filters) +} + +// https://ffmpeg.org/doxygen/7.0/structAVFilterGraph.html#a1dafd3d239f7c2f5e3ac109578ef926d +func (g *FilterGraph) Filters() (fs []*FilterContext) { + fcs := (*[(math.MaxInt32 - 1) / unsafe.Sizeof((*C.AVFilterContext)(nil))](*C.AVFilterContext))(unsafe.Pointer(g.c.filters)) + for i := 0; i < g.NbFilters(); i++ { + fs = append(fs, newFilterContext(fcs[i])) + } + return +} diff --git a/filter_graph_test.go b/filter_graph_test.go index 9e5d11d..0f1b533 100644 --- a/filter_graph_test.go +++ b/filter_graph_test.go @@ -247,6 +247,43 @@ func TestFilterGraph(t *testing.T) { require.Equal(t, 1, len(os)) require.Equal(t, MediaTypeAudio, os[0].MediaType()) + fg3 := AllocFilterGraph() + require.NotNil(t, fg3) + defer fg3.Free() + outputs := AllocFilterInOut() + br := FindFilterByName("buffer") + brCtx, err := fg3.NewBuffersrcFilterContext(br, "in") + require.NoError(t, err) + brCtxParameters := AllocBuffersrcFilterContextParameters() + brCtxParameters.SetPixelFormat(PixelFormatYuv420P) + brCtxParameters.SetSampleAspectRatio(NewRational(1, 1)) + brCtxParameters.SetWidth(1080) + brCtxParameters.SetHeight(720) + brCtxParameters.SetTimeBase(NewRational(1, 30)) + err = brCtx.SetParameters(brCtxParameters) + require.NoError(t, err) + err = brCtx.Initialize(nil) + require.NoError(t, err) + outputs.SetName("in") + outputs.SetFilterContext(brCtx.FilterContext()) + outputs.SetPadIdx(0) + outputs.SetNext(nil) + inputs := AllocFilterInOut() + bs := FindFilterByName("buffersink") + bsCtx, err := fg3.NewBuffersinkFilterContext(bs, "out") + require.NoError(t, err) + inputs.SetName("out") + inputs.SetFilterContext(bsCtx.FilterContext()) + inputs.SetPadIdx(0) + inputs.SetNext(nil) + err = fg3.Parse("movie=filename=testdata/video.mp4[mv];[in][mv]overlay=x=100:y=100[ol];[ol]scale=w=1080:h=720[out]", outputs, inputs) + require.NoError(t, err) + var filterNames string + for _, filterContext := range fg3.Filters() { + filterNames += fmt.Sprintf("[%s]", filterContext.Class().ItemName()) + } + require.Equal(t, "[in][out][Parsed_movie_0][Parsed_overlay_1][Parsed_scale_2]", filterNames) + // TODO Test BuffersrcAddFrame // TODO Test BuffersinkGetFrame } From f8274113444283ab4abbfa955928bda4a463fd25 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Mon, 23 Dec 2024 18:32:20 +0800 Subject: [PATCH 25/31] SetHardwareDeviceContext --- filter_context.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/filter_context.go b/filter_context.go index 6fe2248..8232046 100644 --- a/filter_context.go +++ b/filter_context.go @@ -46,7 +46,7 @@ func (fc *FilterContext) SetHardwareDeviceContext(hdc *HardwareDeviceContext) { C.av_buffer_unref(&fc.c.hw_device_ctx) } if hdc != nil { - fc.c.hw_device_ctx = hdc.c + fc.c.hw_device_ctx = C.av_buffer_ref(hdc.c) } else { fc.c.hw_device_ctx = nil } From 5271cbc27f7d074a14fb82d257245abe711ab3b7 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Mon, 23 Dec 2024 18:34:21 +0800 Subject: [PATCH 26/31] SetHardwareDeviceContext --- filter_context.go | 12 ------------ filter_graph.go | 15 --------------- filter_graph_test.go | 37 ------------------------------------- 3 files changed, 64 deletions(-) diff --git a/filter_context.go b/filter_context.go index 8232046..c911a40 100644 --- a/filter_context.go +++ b/filter_context.go @@ -39,15 +39,3 @@ func (fc *FilterContext) Free() { func (fc *FilterContext) Class() *Class { return newClassFromC(unsafe.Pointer(fc.c)) } - -// https://ffmpeg.org/doxygen/7.0/structAVFilterContext.html#addd946fbe5af506a2b19f9ad7cb97c35 -func (fc *FilterContext) SetHardwareDeviceContext(hdc *HardwareDeviceContext) { - if fc.c.hw_device_ctx != nil { - C.av_buffer_unref(&fc.c.hw_device_ctx) - } - if hdc != nil { - fc.c.hw_device_ctx = C.av_buffer_ref(hdc.c) - } else { - fc.c.hw_device_ctx = nil - } -} diff --git a/filter_graph.go b/filter_graph.go index bd26739..46ec6a2 100644 --- a/filter_graph.go +++ b/filter_graph.go @@ -4,7 +4,6 @@ package astiav import "C" import ( "errors" - "math" "unsafe" ) @@ -155,17 +154,3 @@ func (g *FilterGraph) SendCommand(target, cmd, args string, f FilterCommandFlags }) return } - -// https://ffmpeg.org/doxygen/7.0/structAVFilterGraph.html#a0ba5c820c760788ea5f8e40c476f9704 -func (g *FilterGraph) NbFilters() int { - return int(g.c.nb_filters) -} - -// https://ffmpeg.org/doxygen/7.0/structAVFilterGraph.html#a1dafd3d239f7c2f5e3ac109578ef926d -func (g *FilterGraph) Filters() (fs []*FilterContext) { - fcs := (*[(math.MaxInt32 - 1) / unsafe.Sizeof((*C.AVFilterContext)(nil))](*C.AVFilterContext))(unsafe.Pointer(g.c.filters)) - for i := 0; i < g.NbFilters(); i++ { - fs = append(fs, newFilterContext(fcs[i])) - } - return -} diff --git a/filter_graph_test.go b/filter_graph_test.go index 0f1b533..9e5d11d 100644 --- a/filter_graph_test.go +++ b/filter_graph_test.go @@ -247,43 +247,6 @@ func TestFilterGraph(t *testing.T) { require.Equal(t, 1, len(os)) require.Equal(t, MediaTypeAudio, os[0].MediaType()) - fg3 := AllocFilterGraph() - require.NotNil(t, fg3) - defer fg3.Free() - outputs := AllocFilterInOut() - br := FindFilterByName("buffer") - brCtx, err := fg3.NewBuffersrcFilterContext(br, "in") - require.NoError(t, err) - brCtxParameters := AllocBuffersrcFilterContextParameters() - brCtxParameters.SetPixelFormat(PixelFormatYuv420P) - brCtxParameters.SetSampleAspectRatio(NewRational(1, 1)) - brCtxParameters.SetWidth(1080) - brCtxParameters.SetHeight(720) - brCtxParameters.SetTimeBase(NewRational(1, 30)) - err = brCtx.SetParameters(brCtxParameters) - require.NoError(t, err) - err = brCtx.Initialize(nil) - require.NoError(t, err) - outputs.SetName("in") - outputs.SetFilterContext(brCtx.FilterContext()) - outputs.SetPadIdx(0) - outputs.SetNext(nil) - inputs := AllocFilterInOut() - bs := FindFilterByName("buffersink") - bsCtx, err := fg3.NewBuffersinkFilterContext(bs, "out") - require.NoError(t, err) - inputs.SetName("out") - inputs.SetFilterContext(bsCtx.FilterContext()) - inputs.SetPadIdx(0) - inputs.SetNext(nil) - err = fg3.Parse("movie=filename=testdata/video.mp4[mv];[in][mv]overlay=x=100:y=100[ol];[ol]scale=w=1080:h=720[out]", outputs, inputs) - require.NoError(t, err) - var filterNames string - for _, filterContext := range fg3.Filters() { - filterNames += fmt.Sprintf("[%s]", filterContext.Class().ItemName()) - } - require.Equal(t, "[in][out][Parsed_movie_0][Parsed_overlay_1][Parsed_scale_2]", filterNames) - // TODO Test BuffersrcAddFrame // TODO Test BuffersinkGetFrame } From 144ff0bf6a6b4901782d6b8656925e54c5007c49 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Mon, 23 Dec 2024 19:16:33 +0800 Subject: [PATCH 27/31] FilterGraph.NbFilters() FilterGraph.Filters() FilterContext.SetHardwareDeviceContext(hdc *HardwareDeviceContext) --- filter_context.go | 12 ++++++++++++ filter_graph.go | 15 +++++++++++++++ filter_graph_test.go | 37 +++++++++++++++++++++++++++++++++++++ 3 files changed, 64 insertions(+) diff --git a/filter_context.go b/filter_context.go index c911a40..8232046 100644 --- a/filter_context.go +++ b/filter_context.go @@ -39,3 +39,15 @@ func (fc *FilterContext) Free() { func (fc *FilterContext) Class() *Class { return newClassFromC(unsafe.Pointer(fc.c)) } + +// https://ffmpeg.org/doxygen/7.0/structAVFilterContext.html#addd946fbe5af506a2b19f9ad7cb97c35 +func (fc *FilterContext) SetHardwareDeviceContext(hdc *HardwareDeviceContext) { + if fc.c.hw_device_ctx != nil { + C.av_buffer_unref(&fc.c.hw_device_ctx) + } + if hdc != nil { + fc.c.hw_device_ctx = C.av_buffer_ref(hdc.c) + } else { + fc.c.hw_device_ctx = nil + } +} diff --git a/filter_graph.go b/filter_graph.go index 46ec6a2..bd26739 100644 --- a/filter_graph.go +++ b/filter_graph.go @@ -4,6 +4,7 @@ package astiav import "C" import ( "errors" + "math" "unsafe" ) @@ -154,3 +155,17 @@ func (g *FilterGraph) SendCommand(target, cmd, args string, f FilterCommandFlags }) return } + +// https://ffmpeg.org/doxygen/7.0/structAVFilterGraph.html#a0ba5c820c760788ea5f8e40c476f9704 +func (g *FilterGraph) NbFilters() int { + return int(g.c.nb_filters) +} + +// https://ffmpeg.org/doxygen/7.0/structAVFilterGraph.html#a1dafd3d239f7c2f5e3ac109578ef926d +func (g *FilterGraph) Filters() (fs []*FilterContext) { + fcs := (*[(math.MaxInt32 - 1) / unsafe.Sizeof((*C.AVFilterContext)(nil))](*C.AVFilterContext))(unsafe.Pointer(g.c.filters)) + for i := 0; i < g.NbFilters(); i++ { + fs = append(fs, newFilterContext(fcs[i])) + } + return +} diff --git a/filter_graph_test.go b/filter_graph_test.go index 9e5d11d..0f1b533 100644 --- a/filter_graph_test.go +++ b/filter_graph_test.go @@ -247,6 +247,43 @@ func TestFilterGraph(t *testing.T) { require.Equal(t, 1, len(os)) require.Equal(t, MediaTypeAudio, os[0].MediaType()) + fg3 := AllocFilterGraph() + require.NotNil(t, fg3) + defer fg3.Free() + outputs := AllocFilterInOut() + br := FindFilterByName("buffer") + brCtx, err := fg3.NewBuffersrcFilterContext(br, "in") + require.NoError(t, err) + brCtxParameters := AllocBuffersrcFilterContextParameters() + brCtxParameters.SetPixelFormat(PixelFormatYuv420P) + brCtxParameters.SetSampleAspectRatio(NewRational(1, 1)) + brCtxParameters.SetWidth(1080) + brCtxParameters.SetHeight(720) + brCtxParameters.SetTimeBase(NewRational(1, 30)) + err = brCtx.SetParameters(brCtxParameters) + require.NoError(t, err) + err = brCtx.Initialize(nil) + require.NoError(t, err) + outputs.SetName("in") + outputs.SetFilterContext(brCtx.FilterContext()) + outputs.SetPadIdx(0) + outputs.SetNext(nil) + inputs := AllocFilterInOut() + bs := FindFilterByName("buffersink") + bsCtx, err := fg3.NewBuffersinkFilterContext(bs, "out") + require.NoError(t, err) + inputs.SetName("out") + inputs.SetFilterContext(bsCtx.FilterContext()) + inputs.SetPadIdx(0) + inputs.SetNext(nil) + err = fg3.Parse("movie=filename=testdata/video.mp4[mv];[in][mv]overlay=x=100:y=100[ol];[ol]scale=w=1080:h=720[out]", outputs, inputs) + require.NoError(t, err) + var filterNames string + for _, filterContext := range fg3.Filters() { + filterNames += fmt.Sprintf("[%s]", filterContext.Class().ItemName()) + } + require.Equal(t, "[in][out][Parsed_movie_0][Parsed_overlay_1][Parsed_scale_2]", filterNames) + // TODO Test BuffersrcAddFrame // TODO Test BuffersinkGetFrame } From 9a24afcc1657ce7a93db6fc3f91d5733be49a482 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Tue, 24 Dec 2024 09:55:06 +0800 Subject: [PATCH 28/31] filter_graph_test --- filter_graph_test.go | 45 ++++++++------------------------------------ 1 file changed, 8 insertions(+), 37 deletions(-) diff --git a/filter_graph_test.go b/filter_graph_test.go index 0f1b533..4cd7382 100644 --- a/filter_graph_test.go +++ b/filter_graph_test.go @@ -194,6 +194,14 @@ func TestFilterGraph(t *testing.T) { outputs = o } + require.Equal(t, len(buffersrcContexts)+1, fg.NbFilters()) + fs := fg.Filters() + require.Equal(t, len(buffersrcContexts)+1, len(fs)) + require.Equal(t, buffersinkContext.FilterContext(), fs[0]) + for idx, c := range fs[1:] { + require.Equal(t, buffersrcContexts[idx].FilterContext(), c) + } + require.NoError(t, fg.Parse(v.content, inputs, outputs)) require.NoError(t, fg.Configure()) @@ -247,43 +255,6 @@ func TestFilterGraph(t *testing.T) { require.Equal(t, 1, len(os)) require.Equal(t, MediaTypeAudio, os[0].MediaType()) - fg3 := AllocFilterGraph() - require.NotNil(t, fg3) - defer fg3.Free() - outputs := AllocFilterInOut() - br := FindFilterByName("buffer") - brCtx, err := fg3.NewBuffersrcFilterContext(br, "in") - require.NoError(t, err) - brCtxParameters := AllocBuffersrcFilterContextParameters() - brCtxParameters.SetPixelFormat(PixelFormatYuv420P) - brCtxParameters.SetSampleAspectRatio(NewRational(1, 1)) - brCtxParameters.SetWidth(1080) - brCtxParameters.SetHeight(720) - brCtxParameters.SetTimeBase(NewRational(1, 30)) - err = brCtx.SetParameters(brCtxParameters) - require.NoError(t, err) - err = brCtx.Initialize(nil) - require.NoError(t, err) - outputs.SetName("in") - outputs.SetFilterContext(brCtx.FilterContext()) - outputs.SetPadIdx(0) - outputs.SetNext(nil) - inputs := AllocFilterInOut() - bs := FindFilterByName("buffersink") - bsCtx, err := fg3.NewBuffersinkFilterContext(bs, "out") - require.NoError(t, err) - inputs.SetName("out") - inputs.SetFilterContext(bsCtx.FilterContext()) - inputs.SetPadIdx(0) - inputs.SetNext(nil) - err = fg3.Parse("movie=filename=testdata/video.mp4[mv];[in][mv]overlay=x=100:y=100[ol];[ol]scale=w=1080:h=720[out]", outputs, inputs) - require.NoError(t, err) - var filterNames string - for _, filterContext := range fg3.Filters() { - filterNames += fmt.Sprintf("[%s]", filterContext.Class().ItemName()) - } - require.Equal(t, "[in][out][Parsed_movie_0][Parsed_overlay_1][Parsed_scale_2]", filterNames) - // TODO Test BuffersrcAddFrame // TODO Test BuffersinkGetFrame } From 876caa5d33401afd36d9231f8a92bdef3fd746ff Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Tue, 24 Dec 2024 10:38:24 +0800 Subject: [PATCH 29/31] FilterGraph.Dump --- filter_graph.go | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/filter_graph.go b/filter_graph.go index bd26739..c8e1629 100644 --- a/filter_graph.go +++ b/filter_graph.go @@ -169,3 +169,8 @@ func (g *FilterGraph) Filters() (fs []*FilterContext) { } return } + +// https://ffmpeg.org/doxygen/7.0/group__lavfi.html#gadb442aca4e5a8c3ba740f6049f0a288b +func (g *FilterGraph) Dump() string { + return C.GoString(C.avfilter_graph_dump(g.c, nil)) +} From 3e0bc8f39f545d11e26bfcb48c2c459feb7ea53f Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Tue, 24 Dec 2024 10:52:32 +0800 Subject: [PATCH 30/31] FilterGraph.Dump --- filter_graph.go | 7 ++++++- filter_graph_test.go | 1 + 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/filter_graph.go b/filter_graph.go index c8e1629..3e38afd 100644 --- a/filter_graph.go +++ b/filter_graph.go @@ -172,5 +172,10 @@ func (g *FilterGraph) Filters() (fs []*FilterContext) { // https://ffmpeg.org/doxygen/7.0/group__lavfi.html#gadb442aca4e5a8c3ba740f6049f0a288b func (g *FilterGraph) Dump() string { - return C.GoString(C.avfilter_graph_dump(g.c, nil)) + var res = C.avfilter_graph_dump(g.c, nil) + if res == nil { + return "" + } + defer C.free(unsafe.Pointer(res)) + return C.GoString(res) } diff --git a/filter_graph_test.go b/filter_graph_test.go index c4a32a9..5d3dd15 100644 --- a/filter_graph_test.go +++ b/filter_graph_test.go @@ -205,6 +205,7 @@ func TestFilterGraph(t *testing.T) { require.NoError(t, fg.Parse(v.content, inputs, outputs)) require.NoError(t, fg.Configure()) + require.NotEmpty(t, fg.Dump()) require.Equal(t, v.buffersink.frameRate, buffersinkContext.FrameRate()) require.Equal(t, v.buffersink.mediaType, buffersinkContext.MediaType()) From 3304eeab998ccc8dfb34b0abccab436cf27c1068 Mon Sep 17 00:00:00 2001 From: ma3315865 Date: Tue, 24 Dec 2024 18:01:15 +0800 Subject: [PATCH 31/31] remove FilterGraph.Dump --- filter_graph.go | 10 ---------- filter_graph_test.go | 1 - 2 files changed, 11 deletions(-) diff --git a/filter_graph.go b/filter_graph.go index 3e38afd..bd26739 100644 --- a/filter_graph.go +++ b/filter_graph.go @@ -169,13 +169,3 @@ func (g *FilterGraph) Filters() (fs []*FilterContext) { } return } - -// https://ffmpeg.org/doxygen/7.0/group__lavfi.html#gadb442aca4e5a8c3ba740f6049f0a288b -func (g *FilterGraph) Dump() string { - var res = C.avfilter_graph_dump(g.c, nil) - if res == nil { - return "" - } - defer C.free(unsafe.Pointer(res)) - return C.GoString(res) -} diff --git a/filter_graph_test.go b/filter_graph_test.go index 5d3dd15..c4a32a9 100644 --- a/filter_graph_test.go +++ b/filter_graph_test.go @@ -205,7 +205,6 @@ func TestFilterGraph(t *testing.T) { require.NoError(t, fg.Parse(v.content, inputs, outputs)) require.NoError(t, fg.Configure()) - require.NotEmpty(t, fg.Dump()) require.Equal(t, v.buffersink.frameRate, buffersinkContext.FrameRate()) require.Equal(t, v.buffersink.mediaType, buffersinkContext.MediaType())