From 5fe586913f060bd0e435809ecf7a4954838ce072 Mon Sep 17 00:00:00 2001 From: Trek H Date: Tue, 11 Aug 2020 11:43:17 +0930 Subject: [PATCH 01/14] alsa, revid: added correct device configuration and defaulting for audio --- device/alsa/alsa.go | 43 +++++++++++++++++++++-------- revid/config/config.go | 1 - revid/config/variables.go | 58 ++++++++++++++++++++++++--------------- 3 files changed, 68 insertions(+), 34 deletions(-) diff --git a/device/alsa/alsa.go b/device/alsa/alsa.go index 3a6e7b14..372d934d 100644 --- a/device/alsa/alsa.go +++ b/device/alsa/alsa.go @@ -45,11 +45,10 @@ import ( ) const ( - pkg = "alsa: " - rbTimeout = 100 * time.Millisecond - rbNextTimeout = 2000 * time.Millisecond - rbLen = 200 - defaultSampleRate = 48000 + pkg = "alsa: " + rbTimeout = 100 * time.Millisecond + rbNextTimeout = 2000 * time.Millisecond + rbLen = 200 ) // "running" means the input goroutine is reading from the ALSA device and writing to the ringbuffer. @@ -61,6 +60,23 @@ const ( stopped ) +const ( + defaultSampleRate = 48000 + defaultBitDepth = 16 + defaultChannels = 1 + defaultRecPeriod = 1.0 + defaultCodec = codecutil.PCM +) + +// Configuration field errors. +var ( + errInvalidSampleRate = errors.New("invalid sample rate, defaulting") + errInvalidChannels = errors.New("invalid number of channels, defaulting") + errInvalidBitDepth = errors.New("invalid bitdepth, defaulting") + errInvalidRecPeriod = errors.New("invalid record period, defaulting") + errInvalidCodec = errors.New("invalid audio codec, defaulting") +) + // An ALSA device holds everything we need to know about the audio input stream and implements io.Reader and device.AVDevice. type ALSA struct { l Logger // Logger for device's routines to log to. @@ -107,19 +123,24 @@ func (d *ALSA) Name() string { func (d *ALSA) Set(c config.Config) error { var errs device.MultiError if c.SampleRate <= 0 { - errs = append(errs, fmt.Errorf("invalid sample rate: %v", c.SampleRate)) + errs = append(errs, errInvalidSampleRate) + c.SampleRate = defaultSampleRate } if c.Channels <= 0 { - errs = append(errs, fmt.Errorf("invalid number of channels: %v", c.Channels)) + errs = append(errs, errInvalidChannels) + c.Channels = defaultChannels } if c.BitDepth <= 0 { - errs = append(errs, fmt.Errorf("invalid bitdepth: %v", c.BitDepth)) + errs = append(errs, errInvalidBitDepth) + c.BitDepth = defaultBitDepth } if c.RecPeriod <= 0 { - errs = append(errs, fmt.Errorf("invalid recording period: %v", c.RecPeriod)) + errs = append(errs, errInvalidRecPeriod) + c.RecPeriod = defaultRecPeriod } - if !codecutil.IsValid(c.InputCodec) { - errs = append(errs, errors.New("invalid codec")) + if c.InputCodec != codecutil.ADPCM && c.InputCodec != codecutil.PCM { + errs = append(errs, errInvalidCodec) + c.InputCodec = defaultCodec } d.Config = Config{ SampleRate: c.SampleRate, diff --git a/revid/config/config.go b/revid/config/config.go index 52a1264c..9f6a776b 100644 --- a/revid/config/config.go +++ b/revid/config/config.go @@ -50,7 +50,6 @@ const ( InputAudio // Outputs. - OutputAudio OutputRTMP OutputRTP OutputHTTP diff --git a/revid/config/variables.go b/revid/config/variables.go index 0f0b6af5..647f9696 100644 --- a/revid/config/variables.go +++ b/revid/config/variables.go @@ -40,20 +40,19 @@ import ( // Default variable values. const ( // General revid defaults. - defaultInput = InputRaspivid - defaultOutput = OutputHTTP - defaultInputCodec = codecutil.H264 - defaultVerbosity = logger.Error - defaultRTPAddr = "localhost:6970" - defaultCameraIP = "192.168.1.50" - defaultBurstPeriod = 10 // Seconds - defaultMinFrames = 100 - defaultFrameRate = 25 - defaultWriteRate = 25 - defaultClipDuration = 0 - defaultAudioInputCodec = codecutil.ADPCM - defaultPSITime = 2 - defaultFileFPS = 0 + defaultInput = InputRaspivid + defaultOutput = OutputHTTP + defaultInputCodec = codecutil.H264 + defaultVerbosity = logger.Error + defaultRTPAddr = "localhost:6970" + defaultCameraIP = "192.168.1.50" + defaultBurstPeriod = 10 // Seconds + defaultMinFrames = 100 + defaultFrameRate = 25 + defaultWriteRate = 25 + defaultClipDuration = 0 + defaultPSITime = 2 + defaultFileFPS = 0 // Ring buffer defaults. defaultRBCapacity = 50000000 // => 50MB @@ -138,6 +137,11 @@ var Variables = []struct { } }, }, + { + Name: "Channels", + Type_: "uint", + Update: func(c *Config, v string) { c.Channels = parseUint("Channels", v, c) }, + }, { Name: "Exposure", Type_: "enum:auto,night,nightpreview,backlight,spotlight,sports,snow,beach,verylong,fixedfps,antishake,fireworks", @@ -243,14 +247,8 @@ var Variables = []struct { switch c.InputCodec { case codecutil.H264, codecutil.MJPEG, codecutil.PCM, codecutil.ADPCM: default: - switch c.Input { - case OutputAudio: - c.LogInvalidField("InputCodec", defaultAudioInputCodec) - c.InputCodec = defaultAudioInputCodec - default: - c.LogInvalidField("InputCodec", defaultInputCodec) - c.InputCodec = defaultInputCodec - } + c.LogInvalidField("InputCodec", defaultInputCodec) + c.InputCodec = defaultInputCodec } }, }, @@ -449,6 +447,17 @@ var Variables = []struct { c.RBWriteTimeout = lessThanOrEqual("RBWriteTimeout", c.RBWriteTimeout, 0, c, defaultRBWriteTimeout) }, }, + { + Name: "RecPeriod", + Type_: "float", + Update: func(c *Config, v string) { + _v, err := strconv.ParseFloat(v, 64) + if err != nil { + c.Logger.Log(logger.Warning, fmt.Sprintf("invalid %s param", "RecPeriod"), "value", v) + } + return _v + }, + }, { Name: "Rotation", Type_: "uint", @@ -470,6 +479,11 @@ var Variables = []struct { } }, }, + { + Name: "SampleRate", + Type_: "uint", + Update: func(c *Config, v string) { c.SampleRate = parseUint("SampleRate", v, c) }, + }, { Name: "Saturation", Type_: "int", From 03a24475f888e3ac105fe0871aed542db151d526 Mon Sep 17 00:00:00 2001 From: Trek H Date: Tue, 11 Aug 2020 13:49:41 +0930 Subject: [PATCH 02/14] revid: bug fix to pass tests --- revid/config/variables.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/revid/config/variables.go b/revid/config/variables.go index 647f9696..12959c8d 100644 --- a/revid/config/variables.go +++ b/revid/config/variables.go @@ -455,7 +455,7 @@ var Variables = []struct { if err != nil { c.Logger.Log(logger.Warning, fmt.Sprintf("invalid %s param", "RecPeriod"), "value", v) } - return _v + c.RecPeriod = _v }, }, { From adf5ddece165764abd76b03dafae337664de6b08 Mon Sep 17 00:00:00 2001 From: Trek H Date: Tue, 11 Aug 2020 20:17:52 +0930 Subject: [PATCH 03/14] revid, alsa: reorder audio setup --- device/alsa/alsa.go | 4 ++++ revid/audio_linux.go | 29 ++++++++++++++++++++--------- revid/revid.go | 6 ++++++ 3 files changed, 30 insertions(+), 9 deletions(-) diff --git a/device/alsa/alsa.go b/device/alsa/alsa.go index 3a6e7b14..e4db1c31 100644 --- a/device/alsa/alsa.go +++ b/device/alsa/alsa.go @@ -437,6 +437,10 @@ func (d *ALSA) formatBuffer() pcm.Buffer { return formatted } +func (d *ALSA) DataSize() int { + return pcm.DataSize(d.SampleRate, d.Channels, d.BitDepth, d.RecPeriod, d.Codec) +} + // nearestPowerOfTwo finds and returns the nearest power of two to the given integer. // If the lower and higher power of two are the same distance, it returns the higher power. // For negative values, 1 is returned. diff --git a/revid/audio_linux.go b/revid/audio_linux.go index d7c78b28..4c128922 100644 --- a/revid/audio_linux.go +++ b/revid/audio_linux.go @@ -29,13 +29,32 @@ import ( "strconv" "bitbucket.org/ausocean/av/codec/codecutil" - "bitbucket.org/ausocean/av/codec/pcm" "bitbucket.org/ausocean/av/container/mts" "bitbucket.org/ausocean/av/device/alsa" "bitbucket.org/ausocean/utils/logger" ) func (r *Revid) setupAudio() error { + // Create new ALSA device. + d := alsa.New(r.cfg.Logger) + r.input = d + + // Configure ALSA device. + r.cfg.Logger.Log(logger.Debug, "configuring input device") + err := r.input.Set(r.cfg) + if err != nil { + r.cfg.Logger.Log(logger.Warning, "errors from configuring input device", "errors", err) + } + r.cfg.Logger.Log(logger.Info, "input device configured") + + // Set revid's lexer. + l, err := codecutil.NewByteLexer(d.DataSize()) + if err != nil { + return err + } + r.lexTo = l.Lex + + // Add metadata. mts.Meta.Add("sampleRate", strconv.Itoa(int(r.cfg.SampleRate))) mts.Meta.Add("channels", strconv.Itoa(int(r.cfg.Channels))) mts.Meta.Add("period", fmt.Sprintf("%.6f", r.cfg.RecPeriod)) @@ -50,13 +69,5 @@ func (r *Revid) setupAudio() error { r.cfg.Logger.Log(logger.Fatal, "no audio codec set in config") } - r.input = alsa.New(r.cfg.Logger) - - l, err := codecutil.NewByteLexer(pcm.DataSize(r.cfg.SampleRate, r.cfg.Channels, r.cfg.BitDepth, r.cfg.RecPeriod, r.cfg.InputCodec)) - if err != nil { - return err - } - r.lexTo = l.Lex - return nil } diff --git a/revid/revid.go b/revid/revid.go index d0d981b4..75d06e76 100644 --- a/revid/revid.go +++ b/revid/revid.go @@ -392,6 +392,12 @@ func (r *Revid) setupPipeline(mtsEnc func(dst io.WriteCloser, rate float64) (io. } } + // input.Set does not need to be called for InputAudio since it is called + // in setupAudio above, so we can return here. + if r.cfg.Input == config.InputAudio { + return nil + } + // Configure the input device. We know that defaults are set, so no need to // return error, but we should log. r.cfg.Logger.Log(logger.Debug, "configuring input device") From b6580af65e387b8afcfcd69785e348b04d6c72d1 Mon Sep 17 00:00:00 2001 From: Trek H Date: Wed, 12 Aug 2020 11:04:45 +0930 Subject: [PATCH 04/14] revid: fixed bugs to do with lex timing for audio --- revid/revid.go | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) diff --git a/revid/revid.go b/revid/revid.go index 75d06e76..e1ba16ad 100644 --- a/revid/revid.go +++ b/revid/revid.go @@ -211,6 +211,7 @@ func (r *Revid) reset(c config.Config) error { } case config.InputAudio: st = mts.EncodeAudio + encOptions = append(encOptions, mts.TimeBasedPSI(time.Duration(r.cfg.PSITime)*time.Second)) default: panic("unknown input type") } @@ -460,10 +461,16 @@ func (r *Revid) Start() error { } r.cfg.Logger.Log(logger.Info, "revid reset") - // Calculate delay between frames based on FileFPS. + // Calculate delay between frames based on FileFPS for Video or RecPeriod for audio. d := time.Duration(0) - if r.cfg.FileFPS != 0 { - d = time.Duration(1000/r.cfg.FileFPS) * time.Millisecond + if r.cfg.Input == config.InputAudio { + if r.cfg.RecPeriod != 0 { + d = time.Duration(r.cfg.RecPeriod * float64(time.Second)) + } + } else { + if r.cfg.FileFPS != 0 { + d = time.Duration(1000/r.cfg.FileFPS) * time.Millisecond + } } r.cfg.Logger.Log(logger.Debug, "starting input processing routine") From c394dc9d895b5ea9d2f02a53d240aa328e751961 Mon Sep 17 00:00:00 2001 From: Trek H Date: Thu, 13 Aug 2020 15:28:59 +0930 Subject: [PATCH 05/14] alsa, revid: reverted changes to revid and changed how ALSA implements Device --- device/alsa/alsa.go | 12 ++++++++++-- revid/audio_linux.go | 2 +- revid/revid.go | 6 ------ 3 files changed, 11 insertions(+), 9 deletions(-) diff --git a/device/alsa/alsa.go b/device/alsa/alsa.go index 970a325f..eadf7bd3 100644 --- a/device/alsa/alsa.go +++ b/device/alsa/alsa.go @@ -116,11 +116,11 @@ func (d *ALSA) Name() string { return "ALSA" } -// Set will take a Config struct, check the validity of the relevant fields +// Setup will take a Config struct, check the validity of the relevant fields // and then performs any configuration necessary. If fields are not valid, // an error is added to the multiError and a default value is used. // It then initialises the ALSA device which can then be started, read from, and stopped. -func (d *ALSA) Set(c config.Config) error { +func (d *ALSA) Setup(c config.Config) error { var errs device.MultiError if c.SampleRate <= 0 { errs = append(errs, errInvalidSampleRate) @@ -185,6 +185,14 @@ func (d *ALSA) Set(c config.Config) error { return nil } +// Set exists to satisfy the implementation of the Device interface that revid uses. +// Everything that would usually be in Set is in the Setup function. +// This is because an ALSA device is different to other devices in that it +// outputs binary non-packetised data and it requires a different configuration procedure. +func (d *ALSA) Set(c config.Config) error { + return nil +} + // Start will start recording audio and writing to the ringbuffer. // Once an ALSA device has been stopped it cannot be started again. This is likely to change in future. func (d *ALSA) Start() error { diff --git a/revid/audio_linux.go b/revid/audio_linux.go index 4c128922..d3d08a58 100644 --- a/revid/audio_linux.go +++ b/revid/audio_linux.go @@ -41,7 +41,7 @@ func (r *Revid) setupAudio() error { // Configure ALSA device. r.cfg.Logger.Log(logger.Debug, "configuring input device") - err := r.input.Set(r.cfg) + err := d.Setup(r.cfg) if err != nil { r.cfg.Logger.Log(logger.Warning, "errors from configuring input device", "errors", err) } diff --git a/revid/revid.go b/revid/revid.go index 75d06e76..d0d981b4 100644 --- a/revid/revid.go +++ b/revid/revid.go @@ -392,12 +392,6 @@ func (r *Revid) setupPipeline(mtsEnc func(dst io.WriteCloser, rate float64) (io. } } - // input.Set does not need to be called for InputAudio since it is called - // in setupAudio above, so we can return here. - if r.cfg.Input == config.InputAudio { - return nil - } - // Configure the input device. We know that defaults are set, so no need to // return error, but we should log. r.cfg.Logger.Log(logger.Debug, "configuring input device") From ba08c58af40b0d2a87bbc0eed2ce95bedba4ef47 Mon Sep 17 00:00:00 2001 From: Trek H Date: Thu, 13 Aug 2020 15:42:28 +0930 Subject: [PATCH 06/14] alsa: added comment for exported function DataSize --- device/alsa/alsa.go | 2 ++ 1 file changed, 2 insertions(+) diff --git a/device/alsa/alsa.go b/device/alsa/alsa.go index eadf7bd3..72b643a1 100644 --- a/device/alsa/alsa.go +++ b/device/alsa/alsa.go @@ -466,6 +466,8 @@ func (d *ALSA) formatBuffer() pcm.Buffer { return formatted } +// DataSize returns the size in bytes of the data ALSA device d will +// output in the duration of a single recording period. func (d *ALSA) DataSize() int { return pcm.DataSize(d.SampleRate, d.Channels, d.BitDepth, d.RecPeriod, d.Codec) } From 456b711b2810d2b983bfc4e650be762973fa6dad Mon Sep 17 00:00:00 2001 From: Trek H Date: Thu, 13 Aug 2020 15:51:24 +0930 Subject: [PATCH 07/14] alsa: test files updated to use Setup instead of Set --- device/alsa/alsa_test.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/device/alsa/alsa_test.go b/device/alsa/alsa_test.go index aeeb6ac9..918a022a 100644 --- a/device/alsa/alsa_test.go +++ b/device/alsa/alsa_test.go @@ -53,7 +53,7 @@ func TestDevice(t *testing.T) { // Create a new ALSA device, start, read/lex, and then stop it. l := logger.New(logger.Debug, os.Stderr, true) ai := New(l) - err := ai.Set(c) + err := ai.Setup(c) // If there was an error opening the device, skip this test. if _, ok := err.(OpenError); ok { t.Skip(err) @@ -119,7 +119,7 @@ func TestIsRunning(t *testing.T) { l := logger.New(logger.Debug, &bytes.Buffer{}, true) // Discard logs. d := New(l) - err := d.Set(config.Config{ + err := d.Setup(config.Config{ SampleRate: sampleRate, Channels: channels, BitDepth: bitDepth, From abbe35d7a89423059e0f33be98614d74fcbf8c27 Mon Sep 17 00:00:00 2001 From: Trek H Date: Thu, 13 Aug 2020 16:23:19 +0930 Subject: [PATCH 08/14] alsa: improve documentation --- device/alsa/alsa.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/device/alsa/alsa.go b/device/alsa/alsa.go index 72b643a1..0ebfa931 100644 --- a/device/alsa/alsa.go +++ b/device/alsa/alsa.go @@ -117,7 +117,7 @@ func (d *ALSA) Name() string { } // Setup will take a Config struct, check the validity of the relevant fields -// and then performs any configuration necessary. If fields are not valid, +// and then perform any configuration necessary. If fields are not valid, // an error is added to the multiError and a default value is used. // It then initialises the ALSA device which can then be started, read from, and stopped. func (d *ALSA) Setup(c config.Config) error { From ddf9707d95adf95a7664dfe7d6295b6cfe23528c Mon Sep 17 00:00:00 2001 From: Trek H Date: Thu, 13 Aug 2020 16:25:37 +0930 Subject: [PATCH 09/14] revid: change comment --- revid/revid.go | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/revid/revid.go b/revid/revid.go index e1ba16ad..383e3253 100644 --- a/revid/revid.go +++ b/revid/revid.go @@ -461,7 +461,8 @@ func (r *Revid) Start() error { } r.cfg.Logger.Log(logger.Info, "revid reset") - // Calculate delay between frames based on FileFPS for Video or RecPeriod for audio. + // Calculate delay between frames based on FileFPS for Video or + // between recording periods for audio. d := time.Duration(0) if r.cfg.Input == config.InputAudio { if r.cfg.RecPeriod != 0 { From cc8d205d674d91f9932d36d1d1ee60a66a158be9 Mon Sep 17 00:00:00 2001 From: Trek H Date: Fri, 14 Aug 2020 11:32:32 +0930 Subject: [PATCH 10/14] revid: simplify write rate --- container/mts/options.go | 4 ++-- go.sum | 1 + revid/config/config.go | 5 ++--- revid/config/config_test.go | 1 - revid/config/parameter/generate_parameters.go | 1 - revid/config/parameter/parameters.go | 13 ------------- revid/config/variables.go | 9 --------- revid/revid.go | 7 ++++--- 8 files changed, 9 insertions(+), 32 deletions(-) diff --git a/container/mts/options.go b/container/mts/options.go index eee206cf..0d46692f 100644 --- a/container/mts/options.go +++ b/container/mts/options.go @@ -97,12 +97,12 @@ func MediaType(mt int) func(*Encoder) error { // Rate is an option that can be passed to NewEncoder. It is used to specifiy // the rate at which the access units should be played in playback. This will // be used to create timestamps and counts such as PTS and PCR. -func Rate(r int) func(*Encoder) error { +func Rate(r float64) func(*Encoder) error { return func(e *Encoder) error { if r < 1 || r > 60 { return ErrInvalidRate } - e.writePeriod = time.Duration(float64(time.Second) / float64(r)) + e.writePeriod = time.Duration(float64(time.Second) / r) return nil } } diff --git a/go.sum b/go.sum index 0537db2b..5b5ce051 100644 --- a/go.sum +++ b/go.sum @@ -66,6 +66,7 @@ golang.org/x/image v0.0.0-20200119044424-58c23975cae1 h1:5h3ngYt7+vXCDZCup/HkCQg golang.org/x/image v0.0.0-20200119044424-58c23975cae1/go.mod h1:FeLwcggjj3mMvU+oOTbSwawSJRM1uh48EjtB4UJZlP0= golang.org/x/sys v0.0.0-20190913121621-c3b328c6e5a7/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= +golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543 h1:E7g+9GITq07hpfrRu66IVDexMakfv52eLZ2CXBWiKr4= golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= diff --git a/revid/config/config.go b/revid/config/config.go index 9f6a776b..cefe81d4 100644 --- a/revid/config/config.go +++ b/revid/config/config.go @@ -230,9 +230,8 @@ type Config struct { // qualityStandard, qualityFair, qualityGood, qualityGreat and qualityExcellent. VBRQuality Quality - VerticalFlip bool // VerticalFlip flips video vertically for Raspivid input. - Width uint // Width defines the input video width Raspivid input. - WriteRate float64 // WriteRate is how many times a second revid encoders will be written to. + VerticalFlip bool // VerticalFlip flips video vertically for Raspivid input. + Width uint // Width defines the input video width Raspivid input. } // Validate checks for any errors in the config fields and defaults settings diff --git a/revid/config/config_test.go b/revid/config/config_test.go index 36831eda..b59410e3 100644 --- a/revid/config/config_test.go +++ b/revid/config/config_test.go @@ -51,7 +51,6 @@ func TestValidate(t *testing.T) { BurstPeriod: defaultBurstPeriod, MinFrames: defaultMinFrames, FrameRate: defaultFrameRate, - WriteRate: defaultWriteRate, ClipDuration: defaultClipDuration, PSITime: defaultPSITime, FileFPS: defaultFileFPS, diff --git a/revid/config/parameter/generate_parameters.go b/revid/config/parameter/generate_parameters.go index dacdc1bf..ad2cff36 100644 --- a/revid/config/parameter/generate_parameters.go +++ b/revid/config/parameter/generate_parameters.go @@ -130,7 +130,6 @@ var params = []Param{ {N: "VBRQuality", BT: "uint8", E: []string{"Standard", "Fair", "Good", "Great", "Excellent"}}, {N: "VerticalFlip", BT: "bool"}, {N: "Width", BT: "uint", Min: 640, Max: 1920}, - {N: "WriteRate", BT: "float64"}, } const fileHeader = ` diff --git a/revid/config/parameter/parameters.go b/revid/config/parameter/parameters.go index 6d0fa773..bd127ed7 100644 --- a/revid/config/parameter/parameters.go +++ b/revid/config/parameter/parameters.go @@ -915,16 +915,3 @@ func (w *Width) Set(val string) error { *w = Width(_v) return nil } - -type WriteRate float64 - -func (w *WriteRate) Type() string { return "float64" } -func (w *WriteRate) Set(val string) error { - _v, err := strconv.ParseFloat(val, 64) - if err != nil { - return fmt.Errorf("could not convert set string to float: %w", err) - } - - *w = WriteRate(_v) - return nil -} diff --git a/revid/config/variables.go b/revid/config/variables.go index 12959c8d..f84fa02b 100644 --- a/revid/config/variables.go +++ b/revid/config/variables.go @@ -49,7 +49,6 @@ const ( defaultBurstPeriod = 10 // Seconds defaultMinFrames = 100 defaultFrameRate = 25 - defaultWriteRate = 25 defaultClipDuration = 0 defaultPSITime = 2 defaultFileFPS = 0 @@ -536,14 +535,6 @@ var Variables = []struct { Type_: "uint", Update: func(c *Config, v string) { c.Width = parseUint("Width", v, c) }, }, - { - Name: "WriteRate", - Type_: "uint", - Update: func(c *Config, v string) { c.WriteRate = float64(parseUint("WriteRate", v, c)) }, - Validate: func(c *Config) { - c.WriteRate = float64(lessThanOrEqual("WriteRate", uint(c.WriteRate), 0, c, defaultWriteRate)) - }, - }, } func parseUint(n, v string, c *Config) uint { diff --git a/revid/revid.go b/revid/revid.go index 41b83602..179ec64e 100644 --- a/revid/revid.go +++ b/revid/revid.go @@ -169,7 +169,7 @@ func (r *Revid) reset(c config.Config) error { r.cfg.Logger.Log(logger.Debug, "setting up revid pipeline") err = r.setupPipeline( - func(dst io.WriteCloser, fps float64) (io.WriteCloser, error) { + func(dst io.WriteCloser, rate float64) (io.WriteCloser, error) { var st int var encOptions []func(*mts.Encoder) error @@ -212,10 +212,11 @@ func (r *Revid) reset(c config.Config) error { case config.InputAudio: st = mts.EncodeAudio encOptions = append(encOptions, mts.TimeBasedPSI(time.Duration(r.cfg.PSITime)*time.Second)) + rate = 1 / r.cfg.RecPeriod default: panic("unknown input type") } - encOptions = append(encOptions, mts.MediaType(st), mts.Rate(int(fps))) + encOptions = append(encOptions, mts.MediaType(st), mts.Rate(rate)) return mts.NewEncoder(dst, &encLog{r.cfg.Logger}, encOptions...) }, func(dst io.WriteCloser, fps int) (io.WriteCloser, error) { @@ -311,7 +312,7 @@ func (r *Revid) setupPipeline(mtsEnc func(dst io.WriteCloser, rate float64) (io. // as a destination. if len(mtsSenders) != 0 { mw := multiWriter(mtsSenders...) - e, _ := mtsEnc(mw, r.cfg.WriteRate) + e, _ := mtsEnc(mw, float64(r.cfg.FrameRate)) encoders = append(encoders, e) } From 6ecce76602e7bb97f77f9e5688b452b8edb5a391 Mon Sep 17 00:00:00 2001 From: Trek H Date: Fri, 14 Aug 2020 12:20:51 +0930 Subject: [PATCH 11/14] revid: improve comments --- go.sum | 1 + revid/revid.go | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/go.sum b/go.sum index 0537db2b..5b5ce051 100644 --- a/go.sum +++ b/go.sum @@ -66,6 +66,7 @@ golang.org/x/image v0.0.0-20200119044424-58c23975cae1 h1:5h3ngYt7+vXCDZCup/HkCQg golang.org/x/image v0.0.0-20200119044424-58c23975cae1/go.mod h1:FeLwcggjj3mMvU+oOTbSwawSJRM1uh48EjtB4UJZlP0= golang.org/x/sys v0.0.0-20190913121621-c3b328c6e5a7/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= +golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543 h1:E7g+9GITq07hpfrRu66IVDexMakfv52eLZ2CXBWiKr4= golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= diff --git a/revid/revid.go b/revid/revid.go index 41b83602..23f8cd68 100644 --- a/revid/revid.go +++ b/revid/revid.go @@ -455,7 +455,7 @@ func (r *Revid) Start() error { } r.cfg.Logger.Log(logger.Info, "revid reset") - // Calculate delay between frames based on FileFPS for Video or + // Calculate delay between frames based on FileFPS for video or // between recording periods for audio. d := time.Duration(0) if r.cfg.Input == config.InputAudio { From 7cf449b5c9944bbc5323632f33a5a8d743e2668e Mon Sep 17 00:00:00 2001 From: Trek H Date: Fri, 14 Aug 2020 12:34:20 +0930 Subject: [PATCH 12/14] revid: simplify --- revid/revid.go | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/revid/revid.go b/revid/revid.go index 23f8cd68..1952f889 100644 --- a/revid/revid.go +++ b/revid/revid.go @@ -459,11 +459,9 @@ func (r *Revid) Start() error { // between recording periods for audio. d := time.Duration(0) if r.cfg.Input == config.InputAudio { - if r.cfg.RecPeriod != 0 { d = time.Duration(r.cfg.RecPeriod * float64(time.Second)) } - } else { - if r.cfg.FileFPS != 0 { + } else if r.cfg.FileFPS != 0 { d = time.Duration(1000/r.cfg.FileFPS) * time.Millisecond } } From 3ec7eddfedfc7d6cf3c9798036ef65401322d1c8 Mon Sep 17 00:00:00 2001 From: Trek H Date: Fri, 14 Aug 2020 12:54:07 +0930 Subject: [PATCH 13/14] revid: syntax --- revid/revid.go | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/revid/revid.go b/revid/revid.go index 1952f889..e28b44ca 100644 --- a/revid/revid.go +++ b/revid/revid.go @@ -459,11 +459,9 @@ func (r *Revid) Start() error { // between recording periods for audio. d := time.Duration(0) if r.cfg.Input == config.InputAudio { - d = time.Duration(r.cfg.RecPeriod * float64(time.Second)) - } + d = time.Duration(r.cfg.RecPeriod * float64(time.Second)) } else if r.cfg.FileFPS != 0 { - d = time.Duration(1000/r.cfg.FileFPS) * time.Millisecond - } + d = time.Duration(1000/r.cfg.FileFPS) * time.Millisecond } r.cfg.Logger.Log(logger.Debug, "starting input processing routine") From 5ad8a6ed2d9953cd1fe0b95cac3659053dec479a Mon Sep 17 00:00:00 2001 From: Trek H Date: Fri, 14 Aug 2020 13:07:03 +0930 Subject: [PATCH 14/14] revid: update encder test to use Rate() with float argument --- container/mts/encoder_test.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/container/mts/encoder_test.go b/container/mts/encoder_test.go index fb32ac24..3c9c5dd5 100644 --- a/container/mts/encoder_test.go +++ b/container/mts/encoder_test.go @@ -191,7 +191,7 @@ func TestEncodePcm(t *testing.T) { sampleSize := 2 blockSize := 16000 writeFreq := float64(sampleRate*sampleSize) / float64(blockSize) - e, err := NewEncoder(nopCloser{&buf}, (*testLogger)(t), PacketBasedPSI(10), Rate(int(writeFreq)), MediaType(EncodeAudio)) + e, err := NewEncoder(nopCloser{&buf}, (*testLogger)(t), PacketBasedPSI(10), Rate(writeFreq), MediaType(EncodeAudio)) if err != nil { t.Fatalf("could not create MTS encoder, failed with error: %v", err) }