Add a new state for ending the overall stream, and use it to decide
whether to pass the final EOS message up the bus instead of dropping
it. Fixes a small race that makes the testsuite sometimes not generate
the last fragment(s) sometimes because the wrong EOS gets
allowed through too early.
Part-of: <https://gitlab.freedesktop.org/gstreamer/gst-plugins-good/-/merge_requests/798>
Using the element state lock to avoid splitmuxsink shutting
down while doing element manipulations can lead to a deadlock on
shutdown if a fragment switch happens at exactly the wrong moment.
Use a private mutex and a shutdown boolean instead.
Part-of: <https://gitlab.freedesktop.org/gstreamer/gst-plugins-good/-/merge_requests/798>
If a pad gets into the check_completed_gop method and then
the underlying conditions change on the reference context,
things could get stuck in a busy loop when the context should
instead jump back out and wait for more data.
Part-of: <https://gitlab.freedesktop.org/gstreamer/gst-plugins-good/-/merge_requests/798>
- Release the split mux lock while removing the probes
- Flush the sinkpad to unblock other pads
- Turn check_completed_gop into a do while statement, when
waking up we want to recheck whether the current GOP is
ready for sending
Part-of: <https://gitlab.freedesktop.org/gstreamer/gst-plugins-good/-/merge_requests/719>
* Trying to disconnect a stream from a running splitmuxsink by flushing
it results in the FLUSH_START blocking in the stream queue's
gst_pad_pause_task because the flush did not unblock
complete_or_wait_on_out, so add a check for ctx->flushing there.
* Add a GST_SPLITMUX_BROADCAST_INPUT so check_completed_gop notices
flushing changed and the incoming push is unblocked.
* Pass the FLUSH_STOP along to the muxer without waiting.
Part-of: <https://gitlab.freedesktop.org/gstreamer/gst-plugins-good/-/merge_requests/687>
The calculated threshold for timecode might be varying depending on
"max-size-timecode" and framerate.
For instance, with framerate 29.97 (30000/1001) and
"max-size-timecode=00:02:00;02", every fragment will have identical
number of frames 3598. However, when "max-size-timecode=00:02:00;00",
calculated next keyframe via gst_video_time_code_add_interval()
can be different per fragment, but this is the nature of timecode.
To compensate such timecode drift, we should keep track of expected
timecode of next fragment based on observed timecode.
If the start of the GOP is >= the requested running time, put it into a
new fragment. That is, split-at-running-time would always ensure that a
split happens as early as possible after the given running time.
Previously it was comparing against the current incoming timestamp,
which does not tell us what we actually want to know as it has no direct
relation to the GOP start/end.
The queued time includes the duration of the last queued frame
(i.e., new keyframe) so the condition check should not be inclusive.
Note that the new fragment will be cut excluding the last frame
and therefore if the condition is inclusive way,
the fragment might have one frame shorter duration for all keyframe
stream such as jpeg or all-inter video streams.
Since the commit 94bb76b6b9, splitmuxsink
will split fragments based on queued time and the threshold of that.
So don't need to store the next timecode for split decision.
Not only the requested keyframe time, the queued size should be
a criterion for the split decision of timecode based mode
(same as max-size-time based split case).
If not configuring the sinks via the "location" property this can be
useful to know for which sink the fragment was actually opened/closed,
especially if finalization of the fragments is happening asynchronously.
Applications might handle locations and generally configuration of the
sink by themselves instead of having splitmuxsink set the location on
the sink. Nonetheless it makes sense to increment the fragment_id that
is passed to the signal so that applications know which fragment is
requested.
An application might try to access splitmuxsink from sync message handler
by g_object_{get,set} which takes lock also. In general, we don't
take lock around message handler.
Add a property which explicitly maps splitmuxsink pads to the
muxer pads they should connect to, overriding the implicit logic
that tries to match pads but yields arbitrary names.
When running in async-finalize mode, request new pads from the muxer
using the same names as old pads, instead of letting the muxer assign
new ones based on the pad template name.
The primary video stream is used to select fragment cut points
at keyframe boundaries. Auxilliary video streams may be
broken up at any packet - so fragments may not start with a keyframe
for those streams.
Make the debug output less confusing by not mentioning a src
pad when doing calculations on the sink pad side.
Improve debug around why a GOP is considered overflowing a fragment
There is only a single sink element in async-finalize mode, and we would
keep the running time from previous fragments set in that case. As we
don't ever set the running time for the very last fragment on EOS, this
would mean that the closing time reported for the very last fragment is
the same as the closing time of the previous fragment.
Apart from the obvious drawbacks of hardcoding, the drawback here was
that, if we subtracted 2 frames (instead of 2.6) from the target running
time, we'd request the next keyframe a bit too far into the future,
which would make our files split at the wrong position.
https://bugzilla.gnome.org/show_bug.cgi?id=797293
For drop-frame framerates, when the expected next max timecode wraps
around at the end of the day, we have to subtract the offset of the
daily jam, otherwise we end up with a duration that's a few frames too
long.
https://bugzilla.gnome.org/show_bug.cgi?id=797270
The behaviour of split-now is to output the current GOP after
starting a new file.
The newly-added split-after signal will output the current GOP
to the old file if possible once a new GOP is opened.
https://bugzilla.gnome.org/show_bug.cgi?id=796982
The stream context was holding a reference to the
internal queue and pads, with pad probes that were
in turn holding references to the stream context.
This lead to a leak if the request pads weren't explicitly
released.
https://bugzilla.gnome.org/show_bug.cgi?id=796893
When handling input with timestamps that repeat, sometimes
splitmuxsink would get confused and ignore a keyframe.
The logic in question is a holdover from before the cmd queue
moved the file cutting to the multiqueue output side and made
it deterministic, so it's no longer needed on the input
here.
https://bugzilla.gnome.org/show_bug.cgi?id=796773
This mode is useful for muxers that can take a long time to finalize a
file. Instead of blocking the whole upstream pipeline while the muxer is
doing its stuff, we can unlink it and spawn a new muxer+sink combination
to continue running normally.
This requires us to receive the muxer and sink (if needed) as factories,
optionally accompanied by their respective properties structures. Also
added the muxer-added and sink-added signals, in case custom code has to
be called for them.
https://bugzilla.gnome.org/show_bug.cgi?id=783754
It can happen during teardown that the reference context becomes NULL.
In that case, trying to send the fragment-opened-closed message would
lead to a crash.