The timestamp offset can be negative, and it can be a bigger negative
number than the latency introduced by the rtpjitterbuffer so the overall
timeout offset can be negative.
Using the negative offset for calculating how many packets can still
arrive in time when encountering a lost packet in an equidistant stream
would then overflow and instead of considering fewer packets lost a lot
more packets are considered lost.
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/5296>
This elements pass RTP packets along unchanged and appear as a RTP
payloader element.
This is useful, for example when using the gstreamer-rtsp-server
library, in the case where you are receiving RTP packets from a
different source and want to serve them over RTSP. Since the
gst-rtsp-server library expect the element marked as payX to be a RTP
payloader element and assumes certain properties are available.
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/5204>
The hack enforcing strictly increasing timestamps was, according to the
code comments, because librtmp was confused with backwards timestamps.
rtmp2sink is not using librtmp as rtmpsink did, so this is no longer
required.
Also changing the timestamps is causing audio glitches when streaming to
Youtube.
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/5212>
Fixes https://gitlab.freedesktop.org/gstreamer/gstreamer/-/issues/2771
This EOS branch exists so that if a seek with a stop is made, qtdemux
stops accepting bytes from the sink after the entire requested playback
range is demuxed, as otherwise we could keep download content that is
not being used.
This patch fixes two flaws that were present in that EOS check:
1) A comparison was made between track time and movie time without conversion.
This made the check trigger early in files with edit lists. This patch fixes
this by converting the track PTS to movie PTS (stream time) for the check.
2) To avoid sending a EOS prematurely when the segment stop is within a GOP and
B-frames are present, the check for EOS should only be done for keyframes. I
gather this was already the intention with the existing code, but because it
used `stream->on_keyframe` instead of the local variable `keyframe` the old
code was checking if the *previous* frame was a keyframe.
It's interesting to note that these two flaws in the old code mask each other
in most cases: the track PTS will have reached the movie end PTS, but EOS would
only be sent if the previous frame was a keyframe. A simple case where they
wouldn't mask each other, reproducing the bug, is a sequence of 3 frame GOPs
with structure I-B-P.
The following validateflow tests have been added to future-proof the
fix:
* validate.test.mp4.qtdemux_ibpibp_non_frag_pull.default
* validate.test.mp4.qtdemux_ibpibp_non_frag_push.default
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/5021>
We were checking if the tag list is writable, but it may actually be
shared through the same event (tee upstream or multiple consumers).
Fix a bug where multiple branches have a videoflip element checking the
taglist. The first one was changing the orientation back to rotate-0
which was resetting the other instances.
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/5097>
Fix this pipeline where the tag list is not writable:
gst-launch-1.0 videotestsrc ! taginject tags="image-orientation=rotate-90" ! videoflip video-direction=auto \
! autovideosink
GStreamer-CRITICAL **: 12:34:36.310: gst_tag_list_add: assertion 'gst_tag_list_is_writable (list)' failed
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4987>
Refusing an incoming segment in < GST_MATROSKA_READ_STATE_DATA should only be
done if the incoming segment is not in GST_FORMAT_TIME.
In GST_FORMAT_TIME, we are just storing the values and returning, so we can
invert the order of the checks.
Fixes proper segment propagation in matroska/webm DASH use-cases
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/3914>
... otherwise streams with constant size samples defined with a single
`sample_size` for all samples in the `stsz` box fall in the category
`chunks_are_samples` in `qtdemux_stbl_init`, overriding the actual
sample count.
`FOURCC_soun` would set this automatically for `compression_id == 0xfffe`,
however `compression_id` is read from the Audio Sample Entry box at an offset
marked as "pre-defined" in some version of the spec and set to 0 both by
GStreamer and FFmpeg for opus streams.
Considering the stream `sampled` flag is set explicitely by other fourcc
variants, doing so for opus seems consistent.
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4903>
The "Encapsulation of Opus in ISO Base Media File Format" [1] specifications,
§ 4.3.2 Opus Specific Box, indicates that data must be stored as big-endian.
In `build_opus_extension`, `gst_byte_writer_put*_le ()` variants were used,
causing audio streams conversion to Opus in mp4 to offset samples due to the
PreSkip field incorrect value (29ms early in our test cases).
[1] https://opus-codec.org/docs/opus_in_isobmff.html#4.3.2
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4875>
When doing a segment seek, the base offset in the new segment
would be increased by segment.position which is basically the
timestamp of the last packet. This does not include the duration
of the last packet though, so might be slightly shorter than the
actual duration of the clip or the requested segment.
Increase the base offset by the segment duration instead when
accumulating segments, which is more correct as it doesn't cut
off the last frame and makes the effective loop segment duration
consistent with the actual duration returned from a duration
query.
In case a segment stop was specified it's also possible that
some data was sent beyond the stop that's necessary for decoding
so the base offset increment should be based on that then and
not on the timestamp of the last buffer pushed out.
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4604>
The muxer used a fixed value of 2 channels because the TR 102 366 spec
says they're to be ignored. However, the demuxer still trusted them,
resulting in bad caps.
Make the muxer fill in the correct channel count anyway (FFmpeg already
does) and make the demuxer ignore the value.
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4739>
Allow a project to use gstreamer-full as a static library
and link to create a binary without dependencies.
Introduce the option 'gst-full-target-type' to
select the build type, dynamic(default) or static.
In gstreamer-full/static build configuration gstreamer (gst.c)
needs the symbol gst_init_static_plugins which is defined
in gstreamer-full.
All the tests and examples are linking with gstreamer but the
symbol gst_init_static_plugins is only defined in the gstreamer-full
library. gstreamer-full can not be built first as it needs to know what plugins
will be built.
One option would be to build all the examples and tests after
gstreamer-full as the tools.
Disable tools build in subprojects too as it will be built at the end of
build process.
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4128>
Since c0bf793c05 ("flvmux: Set PTS based on
running time") the timestamp of the output buffer is already in running
time. So using that for 'srcpad->segment.position' does not work correctly
because gst_aggregator_simple_get_next_time() will convert it again with
gst_segment_to_running_time().
This means that the timestamp returned by
gst_aggregator_simple_get_next_time() may be incorrect. For example, if
flvmux is added to a already runinng pipeline then the timestamp is too
small and gst_aggregator_wait_and_check() returns immediately. As a result,
buffers may be muxed in the wrong order.
To fix this, use the PTS of the incoming buffer instead of the outgoing
buffer. Also add the duration as get_next_time() is supposed to return the
timestamp of the next buffer, not the current one.
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4701>
The index is already incremented by 3 every iteration so multiplying it
by 3 additionally on each array access is doing it twice and does not
work.
This caused invalid files to be created if there's more than one CEA608
triplet in a buffer, and out of bounds memory reads.
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4634>
Make splitmuxsrc deal better with stream reordering by
making the largest observed PTS contiguous in the
next fragment. Previously, it selected DTS, but then
aligned that with the segment start of the next fragment,
which holds PTS values - leading to glitches in
streams that don't have PTS = DTS at the start.
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4637>
It could indeed be used uninitialized, but only if one of the
g_return_val_if_fail() caused an early return.
../subprojects/gst-plugins-good/gst/rtpmanager/rtpjitterbuffer.c: In function ‘rtp_jitter_buffer_append_query’:
../subprojects/gst-plugins-good/gst/rtpmanager/rtpjitterbuffer.c🔢10: warning: ‘head’ may be used uninitialized
[-Wmaybe-uninitialized]
1234 | return head;
| ^~~~
../subprojects/gst-plugins-good/gst/rtpmanager/rtpjitterbuffer.c:1232:12: note: ‘head’ was declared here
1232 | gboolean head;
| ^~~~
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4616>
This is a fix for a data race leading to:
> GLib-CRITICAL: g_hash_table_foreach:
> assertion 'version == hash_table->version' failed
Identified sequence:
* `rtp_session_on_timeout` acquires the lock on `session` and proceeds with its
processing.
* `rtp_session_process_rtcp` is called (debug log : received RTCP packet) and
attempts to acquire the lock on `session`, which is still held by
`rtp_session_on_timeout`.
* as part of an hash table iterator, `rtp_session_on_timeout` transitively
invokes `source_caps` which releases the lock on `session` so as to call
`session->callbacks.caps`.
* Since `rtp_session_process_rtcp` was waiting for the lock to be released, it
succeeds in acquiring it and proceeds with `rtp_session_process_rr` which
transitively calls `g_hash_table_insert` via `add_source`.
* After `source_caps` re-acquires the lock and gives the control flow back to
`rtp_session_on_timeout`, the hash table iterator is changed, resulting in the
assertion failure.
This commits copies `sess->ssrcs[sess->mask_idx]` and iterates on the copy so
the iterator is not affected by a concurrent change due to the lock being
released in the `source_caps` callback.
Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4555>