Codebase list gst-plugins-good1.0 / a690ceb
New upstream version 1.22.5 Jeremy Bícha 8 months ago
26 changed file(s) with 990 addition(s) and 489 deletion(s). Raw diff Collapse all Expand all
0 === release 1.22.5 ===
1
2 2023-07-20 15:22:48 +0100 Tim-Philipp Müller <tim@centricular.com>
3
4 * NEWS:
5 * RELEASE:
6 * docs/gst_plugins_cache.json:
7 * gst-plugins-good.doap:
8 * meson.build:
9 Release 1.22.5
10
11 2023-02-15 17:32:39 +0100 Edward Hervey <edward@centricular.com>
12
13 * ext/adaptivedemux2/hls/gsthlsdemux.c:
14 hlsdemux2: Don't set a referer when updating playlists
15 In the same way we don't for regular playlists in the base class.
16 If there is a referer specified by the app/user, the downloadhelper will set it
17 accordingly.
18 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/5057>
19
20 2023-02-15 18:06:36 +0100 Edward Hervey <edward@centricular.com>
21
22 * ext/adaptivedemux2/gstadaptivedemux-stream.c:
23 adaptivedemux2: Don't blindly set the main manifest URI as referer
24 There's no guarantee it will *actually* be the URI which refered to what we are
25 downloading. It could be a stream URI or anything else.
26 Instead of putting something wrong, put no (specific) referer as a better choice
27 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/5057>
28
29 2023-07-11 17:00:57 +0200 Bastien Nocera <hadess@hadess.net>
30
31 * ext/gtk/gtkgstbasewidget.c:
32 gtk: Fix critical caused by pointer movement when stream is getting ready
33 This check fixes a critical warning that can happen when a pointer motion
34 happens and the video doesn't have its width/height information available.
35 GStreamer-Video-CRITICAL **: gst_video_center_rect: assertion 'src->h != 0' failed
36 #0 g_logv (log_domain=0x7ffff705e176 "GStreamer-Video", log_level=G_LOG_LEVEL_CRITICAL, format=<optimized out>, args=<optimized out>) at ../../../../Projects/jhbuild/glib/glib/gmessages.c:1422
37 #1 0x00007ffff7e1a81d in g_log (log_domain=<optimized out>, log_level=log_level@entry=G_LOG_LEVEL_CRITICAL, format=format@entry=0x7ffff7e77a9d "%s: assertion '%s' failed") at ../../../../Projects/jhbuild/glib/glib/gmessages.c:1460
38 #2 0x00007ffff7e1b749 in g_return_if_fail_warning (log_domain=<optimized out>, pretty_function=<optimized out>, expression=<optimized out>) at ../../../../Projects/jhbuild/glib/glib/gmessages.c:2930
39 #3 0x00007ffff701d90b in gst_video_sink_center_rect (src=..., dst=..., result=result@entry=0x7fffffffc6d0, scaling=scaling@entry=1) at ../../../../Projects/jhbuild/gstreamer/subprojects/gst-plugins-base/gst-libs/gst/video/gstvideosink.c:105
40 #4 0x00007fffe5652dbb in _fit_stream_to_allocated_size (result=0x7fffffffc6d0, allocation=0x7fffffffc6c0, base_widget=0x9396f0) at ../../../../Projects/jhbuild/gstreamer/subprojects/gst-plugins-good/ext/gtk/gtkgstbasewidget.c:326
41 #5 gtk_gst_base_widget_display_size_to_stream_size (base_widget=base_widget@entry=0x9396f0, x=1207.7109375, y=811.84765625, stream_x=stream_x@entry=0x7fffffffc720, stream_y=stream_y@entry=0x7fffffffc728) at ../../../../Projects/jhbuild/gstreamer/subprojects/gst-plugins-good/ext/gtk/gtkgstbasewidget.c:344
42 #6 0x00007fffe5651a4b in gst_gtk_base_sink_navigation_send_event (navigation=0x5ff990, event=0x178a730) at ../../../../Projects/jhbuild/gstreamer/subprojects/gst-plugins-good/ext/gtk/gstgtkbasesink.c:340
43 #7 0x00007fffe5652432 in gtk_gst_base_widget_motion_event (widget=<optimized out>, event=event@entry=0x1f14b60) at ../../../../Projects/jhbuild/gstreamer/subprojects/gst-plugins-good/ext/gtk/gtkgstbasewidget.c:404
44 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/5051>
45
46 2023-07-13 16:27:05 +0200 Michael Tretter <m.tretter@pengutronix.de>
47
48 * sys/v4l2/gstv4l2videoenc.c:
49 v4l2videoenc: remove empty sink_query
50 The sink_query() function simply calls the sink_query() function of the parent
51 videoencoder class. Remove the override to simply directly call the parent's
52 function.
53 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/5036>
54
55 2023-07-13 16:16:44 +0200 Michael Tretter <m.tretter@pengutronix.de>
56
57 * sys/v4l2/gstv4l2videoenc.c:
58 v4l2videoenc: replace custom QUERY_CAPS handling with getcaps callback
59 The videoencoder base class uses getcaps() to ask a subclass for the caps in its
60 sink_query_default() implementation.
61 Replace the custom handling of the QUERY_CAPS in the v4l2videoenc with an
62 implementation of getcaps() that returns the caps that are supported by the
63 v4l2videoenc to return these caps in the query.
64 This getcaps() implementation also calls the provided proxy_getcaps(), which
65 sends a caps query to downstream. This fixes the v4l2videoenc element to respect
66 limits of downstream elements in a sink query.
67 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/5036>
68
69 2023-07-11 21:41:46 +0200 Carlos Rafael Giani <crg7475@mailbox.org>
70
71 * meson.build:
72 gl: Take into account viv-fb vs. viv_fb naming in meson scripts
73 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4959>
74
75 2023-05-16 21:24:44 +1000 Matthew Waters <matthew@centricular.com>
76
77 * ext/qt/gstqtglutility.cc:
78 * ext/qt/meson.build:
79 * meson.build:
80 gl: provide a pkg-config/gir file for the viv-fb backend
81 Required to be able to generate coherent bindings for window system
82 specific APIs due to limitations in gobject-introspection.
83 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4959>
84
85 2023-07-10 22:45:49 +0900 Seungha Yang <seungha@centricular.com>
86
87 * ext/qt6/qt6glitem.cc:
88 qt6: Set sampler filtering method
89 QQuickItem::smooth property doesn't seem to be propagated to
90 newly created QSGSimpleTextureNode automatically.
91 Fixes: https://gitlab.freedesktop.org/gstreamer/gstreamer/-/issues/2793
92 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/5016>
93
94 2023-07-09 17:44:03 +0200 David Craven <david@craven.ch>
95
96 * gst/matroska/matroska-read-common.c:
97 matroska: demux: Strip signal byte from encrypted blocks
98 Removes the signal byte when the frame is unencrypted to
99 be consistent with when the frame is encrypted.
100 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/5014>
101
102 2023-06-26 17:10:33 -0400 Nicolas Dufresne <nicolas.dufresne@collabora.com>
103
104 * sys/v4l2/gstv4l2videodec.c:
105 v4l2: videodec: Don't wait for src_ch if active
106 If the capture pool is already active, like when handling gaps at the
107 start of a stream, do not setup the decoder to wait for src_ch event.
108 Otherwise the decoder will endup waiting for that at the wrong moment
109 and exit the decoding thread unexpectedly.
110 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4996>
111
112 2023-06-26 17:08:57 -0400 Nicolas Dufresne <nicolas.dufresne@collabora.com>
113
114 * sys/v4l2/gstv4l2videodec.c:
115 v4l2: videodec: Move pool setup inside negotiate()
116 Move all the pool configuration inside the negotiate() virtual function.
117 This allow settting up a pool with default format whenever the base
118 class wants to start without input data, like gaps.
119 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4996>
120
121 2023-07-06 17:44:48 +0800 Hou Qi <qi.hou@nxp.com>
122
123 * sys/v4l2/gstv4l2videodec.c:
124 v4l2videodec: correctly register v4l2mpeg2dec
125 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4992>
126
127 2023-07-07 12:33:37 +0200 Guillaume Desmottes <guillaume.desmottes@onestream.live>
128
129 * gst/videofilter/gstvideoflip.c:
130 videoflip: fix critical when tag list is not writable
131 Fix this pipeline where the tag list is not writable:
132 gst-launch-1.0 videotestsrc ! taginject tags="image-orientation=rotate-90" ! videoflip video-direction=auto \
133 ! autovideosink
134 GStreamer-CRITICAL **: 12:34:36.310: gst_tag_list_add: assertion 'gst_tag_list_is_writable (list)' failed
135 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4990>
136
137 2023-07-06 14:27:42 +0200 Michael Olbrich <m.olbrich@pengutronix.de>
138
139 * sys/v4l2/gstv4l2src.c:
140 v4l2src: handle resolution change when buffers are copied
141 When buffers are copied then GST_V4L2_FLOW_RESOLUTION_CHANGE is returned by
142 gst_v4l2_buffer_pool_process() so do renegotiation here as well.
143 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4985>
144
145 2023-07-04 23:11:53 +0900 Seungha Yang <seungha@centricular.com>
146
147 * gst/rtsp/gstrtspsrc.c:
148 rtspsrc: Fix crash when is-live=false
149 The pad's parent (i.e., rtspsrc) can be nullptr since we add pads
150 later.
151 Co-authored-by: Jan Schmidt <jan@centricular.com>
152 Fixes: https://gitlab.freedesktop.org/gstreamer/gstreamer/-/issues/2751
153 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4971>
154
155 2023-07-04 10:57:01 +0200 Edward Hervey <edward@centricular.com>
156
157 * ext/adaptivedemux2/hls/gsthlsdemux-util.c:
158 hlsdemux2: Ensure processed webvtt ends with empty new line
159 Parsers downstream will use empty new lines to detect where an entry
160 ends. Failure to have a newline would cause the entry to be either
161 discarded or (wrongly) concatenated with the next entry
162 Fixes https://gitlab.freedesktop.org/gstreamer/gstreamer/-/issues/2752
163 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4970>
164
165 2023-06-21 17:05:47 +0200 Edward Hervey <edward@centricular.com>
166
167 * gst/matroska/matroska-demux.c:
168 matroska-demux: Properly handle early time-based segments
169 Refusing an incoming segment in < GST_MATROSKA_READ_STATE_DATA should only be
170 done if the incoming segment is not in GST_FORMAT_TIME.
171 In GST_FORMAT_TIME, we are just storing the values and returning, so we can
172 invert the order of the checks.
173 Fixes proper segment propagation in matroska/webm DASH use-cases
174 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4922>
175
176 2023-02-10 15:26:20 +0100 Edward Hervey <edward@centricular.com>
177
178 * ext/adaptivedemux2/gstadaptivedemux.c:
179 adaptivedemux2: Handle early SEEKING query
180 No pads are present yet, but we can still answer the query
181 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4922>
182
183 2023-02-09 17:22:34 +0100 Edward Hervey <edward@centricular.com>
184
185 * ext/adaptivedemux2/gstadaptivedemux.c:
186 adaptivedemux2: Fix non-accurate seeking
187 If no accurate positioning was required, default to snap to the previous segment
188 for improved responsiveness
189 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4922>
190
191 2023-02-09 14:54:27 +0100 Edward Hervey <edward@centricular.com>
192
193 * ext/adaptivedemux2/gstadaptivedemux.c:
194 adaptivedemux2: Handle return in seek handling
195 Various code path were repeating the same logic, and risk forgetting a lock
196 release.
197 Unify all of them
198 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4922>
199
200 2023-02-09 14:45:01 +0100 Edward Hervey <edward@centricular.com>
201
202 * ext/adaptivedemux2/gstadaptivedemux.c:
203 adaptivedemux2: Move API lock usage
204 It is not needed so early
205 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4922>
206
207 2023-02-08 17:24:18 +0100 Edward Hervey <edward@centricular.com>
208
209 * ext/adaptivedemux2/gstadaptivedemux-private.h:
210 * ext/adaptivedemux2/gstadaptivedemux-stream.c:
211 * ext/adaptivedemux2/gstadaptivedemux.c:
212 adaptivedemux2: Handle early key-unit seek
213 Is a seek is done on stream-collection post, there are no selected streams
214 yet. Therefore none would be chosen to adjust the key-unit seek.
215 If no streams are selected, fallback to a default stream (i.e. one which has
216 track(s) with GST_STREAM_FLAG_SELECT).
217 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4922>
218
219 2023-02-08 12:02:45 +0100 Edward Hervey <edward@centricular.com>
220
221 * ext/adaptivedemux2/gstadaptivedemux-track.c:
222 adaptivedemux2: Fix early seeking
223 When seeking is handled by the collection posting thread, there is a possibility
224 that some leftover data will be pushed by the stream thread.
225 Properly detect and reject those early segments (and buffers) by comparing it to
226 the main segment seqnum
227 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4922>
228
229 2023-06-06 11:34:03 +0200 Guillaume Desmottes <guillaume.desmottes@onestream.live>
230
231 * gst/videofilter/gstvideoflip.c:
232 videoflip: update orientation tag in auto mode
233 The frames are flipped according to the tag orientation so it's no longer accurate.
234 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4796>
235
236 2023-06-20 14:56:44 +0200 François Laignel <francois@centricular.com>
237
238 * gst/isomp4/qtdemux.c:
239 qtdemux: opus: set entry as sampled
240 ... otherwise streams with constant size samples defined with a single
241 `sample_size` for all samples in the `stsz` box fall in the category
242 `chunks_are_samples` in `qtdemux_stbl_init`, overriding the actual
243 sample count.
244 `FOURCC_soun` would set this automatically for `compression_id == 0xfffe`,
245 however `compression_id` is read from the Audio Sample Entry box at an offset
246 marked as "pre-defined" in some version of the spec and set to 0 both by
247 GStreamer and FFmpeg for opus streams.
248 Considering the stream `sampled` flag is set explicitely by other fourcc
249 variants, doing so for opus seems consistent.
250 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4908>
251
252 2023-06-20 19:10:38 +0100 Tim-Philipp Müller <tim@centricular.com>
253
254 * docs/gst_plugins_cache.json:
255 * meson.build:
256 Back to development
257 Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/4907>
258
0259 === release 1.22.4 ===
1260
2261 2023-06-20 17:42:25 +0100 Tim-Philipp Müller <tim@centricular.com>
+184
-3
NEWS less more
11
22 GStreamer 1.22.0 was originally released on 23 January 2023.
33
4 The latest bug-fix release in the stable 1.22 series is 1.22.4 and was
5 released on 20 June 2023.
4 The latest bug-fix release in the stable 1.22 series is 1.22.5 and was
5 released on 20 July 2023.
66
77 See https://gstreamer.freedesktop.org/releases/1.22/ for the latest
88 version of this document.
99
10 Last updated: Tuesday 20 June 2023, 16:30 UTC (log)
10 Last updated: Thursday 20 July 2023, 12:00 UTC (log)
1111
1212 Introduction
1313
20072007 - List of Merge Requests applied in 1.22.4
20082008 - List of Issues fixed in 1.22.4
20092009
2010 1.22.5
2011
2012 The fifth 1.22 bug-fix release (1.22.5) was released on 20 July 2023.
2013
2014 This release only contains bugfixes and security fixes and it should be
2015 safe to update from 1.22.x.
2016
2017 Highlighted bugfixes in 1.22.5
2018
2019 - Security fixes for the RealMedia demuxer
2020 - vaapi decoders, postproc: Disable DMAbuf from caps negotiation to
2021 fix garbled video in some cases
2022 - decodebin3, playbin3, parsebin fixes, especially for stream
2023 reconfiguration
2024 - hlsdemux2: fix early seeking; don’t pass referer when updating
2025 playlists; webvtt fixes
2026 - gtk: Fix critical caused by pointer movement when stream is getting
2027 ready
2028 - qt6: Set sampler filtering method, fixes bad quality with qml6glsink
2029 and gstqt6d3d11
2030 - v4l2src: handle resolution change when buffers are copied
2031 - videoflip: update orientation tag in auto mode
2032 - video timecode: Add support for framerates lower than 1fps and
2033 accept 119.88 (120/1.001) fps
2034 - webrtcsink: fixes for x264enc and NVIDIA encoders
2035 - cerbero: Pull ninja from system if possible, avoid spurious
2036 bootstrap of cmake
2037 - packages: Recipe updates for ffmpeg, libsoup, orc
2038 - various bug fixes, memory leak fixes, and other stability and
2039 reliability improvements
2040
2041 gstreamer
2042
2043 - taglist, plugins: fix compiler warnings with GLib >= 2.76
2044 - tracerutils: allow casting parameter types
2045 - inputselector: fix playing variable is never set
2046
2047 gst-plugins-base
2048
2049 - appsink: add missing make_writable call
2050 - audioaggregator: Do not post message before being constructed
2051 - decodebin3: Prevent a critical warning when reassigning output slots
2052 - decodebin3: Fix slot input linking when the associated stream has
2053 changed
2054 - decodebin3: Remove spurious input locking during parsebin
2055 reconfiguration
2056 - urisourcebin: Set source element to READY before querying it
2057 - gl/viv-fb: meson build updates
2058 - plugins: fix compiler warnings with GLib >= 2.76
2059 - subtitleoverlay: fix mutex error if sink caps is not video
2060 - video: timecode: Add support for framerates lower than 1fps
2061 - video: accept timecode of 119.88 (120/1.001) FPS
2062 - video: cannot attach time code meta when frame rate is 119.88
2063 (120000/1001)
2064 - videodecoder: fix copying buffer metas
2065
2066 gst-plugins-good
2067
2068 - adaptivedemux2: Fix early seeking
2069 - hlsdemux2: Ensure processed webvtt ends with empty new line
2070 - hlsdemux2: Don’t set a referer when updating playlists
2071 - matroska: demux: Strip signal byte when encrypted
2072 - rtspsrc: Fix crash when is-live=false
2073 - gtk: Fix critical caused by pointer movement when stream is getting
2074 ready
2075 - qt6: Set sampler filtering method, fixes bad quality with qml6glsink
2076 and gstqt6d3d11
2077 - qtdemux: opus: set entry as sampled
2078 - v4l2src: handle resolution change when buffers are copied
2079 - v4l2videodec: Fix handling of initial gaps
2080 - v4l2videodec: correctly register v4l2mpeg2dec
2081 - v4l2videoenc: replace custom QUERY_CAPS handling with getcaps
2082 callback
2083 - videoflip: update orientation tag in auto mode
2084 - videoflip: fix critical when tag list is not writable
2085
2086 gst-plugins-bad
2087
2088 - d3d11bufferpool: Fix heavy CPU usage in case of fixed-size pool
2089 - jpegparser: jpegdecoder: Don’t pollute bus and comply with spec
2090 - plugins: fix compiler warnings with GLib >= 2.76
2091 - webrtcbin: Prevent critical warning when creating an additional data
2092 channel
2093 - webrtcstats: Properly report IceCandidate type
2094
2095 gst-plugins-ugly
2096
2097 - rmdemux: add some integer overflow checks
2098
2099 gst-plugins-rs
2100
2101 - fallbackswitch: Change the threshold for trailing buffers
2102 - fallbackswitch: Fix pad health calculation and notifies
2103 - fmp4mux: Fix draining in chunk mode if keyframes are too late
2104 - livesync: Wait for the end timestamp of the previous buffer before
2105 looking at queue
2106 - livesync: Improve EOS handling
2107 - togglerecord: Clip segment before calculating timestamp/duration
2108 - togglerecord: Error out if main stream buffer has no valid running
2109 time
2110 - webrtcsink: fix pipeline when input caps contain max-framerate
2111 - webrtcsink: Configure only 4 threads for x264enc
2112 - webrtcsink: Translate force-keyunit events to force-IDR action
2113 signal for NVIDIA encoders
2114 - webrtcsink: Set config-interval=-1 and aggregate-mode=zero-latency
2115 on rtph264pay and rtph265pay
2116 - webrtcsink: Set VP8/VP9 payloader based on payloader element factory
2117 name
2118 - webrtcink: Use correct property types for nvvideoconvert
2119 - webrtc/signalling: fix race condition in message ordering
2120 - videofx: Minimize dependencies of the image crate
2121
2122 gst-libav
2123
2124 - No changes
2125
2126 gst-rtsp-server
2127
2128 - No changes
2129
2130 gstreamer-vaapi
2131
2132 - vaapidecode,vaapipostproc: Disable DMAbuf from caps negotiation.
2133
2134 gstreamer-sharp
2135
2136 - No changes
2137
2138 gst-omx
2139
2140 - No changes
2141
2142 gst-python
2143
2144 - No changes
2145
2146 gst-editing-services
2147
2148 - ges: some fixes for 32-bit systems
2149 - ges, nle: Avoid setting state or sending query when constructing
2150 objects
2151
2152 gst-validate + gst-integration-testsuites
2153
2154 - No changes
2155
2156 gst-examples
2157
2158 - No changes
2159
2160 Development build environment
2161
2162 - No changes
2163
2164 Cerbero build tool and packaging changes in 1.22.5
2165
2166 - Pull ninja from system if possible, avoid spurious bootstrap of
2167 cmake
2168 - ffmpeg: update to 5.0.3
2169 - libsoup: update to 2.74.3
2170 - orc: update to 0.4.34
2171
2172 Contributors to 1.22.5
2173
2174 Andoni Morales Alastruey, Bastien Nocera, Carlos Rafael Giani, David
2175 Craven, Doug Nazar, Edward Hervey, François Laignel, Guillaume
2176 Desmottes, He Junyan, Hou Qi, Jan Alexander Steffens (heftig), Jan
2177 Schmidt, Maksym Khomenko, Mathieu Duponchelle, Matthew Waters, Michael
2178 Olbrich, Michael Tretter, Nicolas Dufresne, Nirbheek Chauhan, Philippe
2179 Normand, Ruslan Khamidullin, Sebastian Dröge, Seungha Yang, Théo
2180 Maillart, Thibault Saunier, Tim-Philipp Müller, Víctor Manuel Jáquez
2181 Leal, Vivia Nikolaidou, Yatin Maan,
2182
2183 … and many others who have contributed bug reports, translations, sent
2184 suggestions or helped testing. Thank you all!
2185
2186 List of merge requests and issues fixed in 1.22.5
2187
2188 - List of Merge Requests applied in 1.22.5
2189 - List of Issues fixed in 1.22.5
2190
20102191 Schedule for 1.24
20112192
20122193 Our next major feature release will be 1.24, and 1.23 will be the
0 This is GStreamer gst-plugins-good 1.22.4.
0 This is GStreamer gst-plugins-good 1.22.5.
11
22 The GStreamer team is thrilled to announce a new major feature release
33 of your favourite cross-platform multimedia framework!
70267026 "construct": false,
70277027 "construct-only": false,
70287028 "controllable": false,
7029 "default": "GStreamer 1.22.4 FLV muxer",
7029 "default": "GStreamer 1.22.5 FLV muxer",
70307030 "mutable": "null",
70317031 "readable": true,
70327032 "type": "gchararray",
70387038 "construct": false,
70397039 "construct-only": false,
70407040 "controllable": false,
7041 "default": "GStreamer 1.22.4 FLV muxer",
7041 "default": "GStreamer 1.22.5 FLV muxer",
70427042 "mutable": "null",
70437043 "readable": true,
70447044 "type": "gchararray",
2125621256 "construct": false,
2125721257 "construct-only": false,
2125821258 "controllable": false,
21259 "default": "GStreamer/1.22.4",
21259 "default": "GStreamer/1.22.5",
2126021260 "mutable": "null",
2126121261 "readable": true,
2126221262 "type": "gchararray",
2181521815 "construct": false,
2181621816 "construct-only": false,
2181721817 "controllable": false,
21818 "default": "GStreamer 1.22.4",
21818 "default": "GStreamer 1.22.5",
2181921819 "mutable": "null",
2182021820 "readable": true,
2182121821 "type": "gchararray",
2325223252 "construct": false,
2325323253 "construct-only": false,
2325423254 "controllable": false,
23255 "default": "GStreamer souphttpsrc 1.22.4 ",
23255 "default": "GStreamer souphttpsrc 1.22.5 ",
2325623256 "mutable": "null",
2325723257 "readable": true,
2325823258 "type": "gchararray",
190190 gboolean gst_adaptive_demux2_stream_in_live_seek_range (GstAdaptiveDemux * demux,
191191 GstAdaptiveDemux2Stream * stream);
192192 gboolean gst_adaptive_demux2_stream_is_selected_locked (GstAdaptiveDemux2Stream *stream);
193 gboolean gst_adaptive_demux2_stream_is_default_locked (GstAdaptiveDemux2Stream *stream);
193194
194195 gboolean gst_adaptive_demux_has_next_period (GstAdaptiveDemux * demux);
195196 void gst_adaptive_demux_advance_period (GstAdaptiveDemux * demux);
14261426 }
14271427
14281428 if (!downloadhelper_submit_request (demux->download_helper,
1429 demux->manifest_uri, DOWNLOAD_FLAG_NONE, request, NULL))
1429 NULL, DOWNLOAD_FLAG_NONE, request, NULL))
14301430 return GST_FLOW_ERROR;
14311431
14321432 stream->download_active = TRUE;
20962096 return FALSE;
20972097 }
20982098
2099 gboolean
2100 gst_adaptive_demux2_stream_is_default_locked (GstAdaptiveDemux2Stream * stream)
2101 {
2102 GList *tmp;
2103
2104 for (tmp = stream->tracks; tmp; tmp = tmp->next) {
2105 GstAdaptiveDemuxTrack *track = tmp->data;
2106 if (track->flags & GST_STREAM_FLAG_SELECT)
2107 return TRUE;
2108 }
2109
2110 return FALSE;
2111 }
2112
20992113 /**
21002114 * gst_adaptive_demux2_stream_is_selected:
21012115 * @stream: A #GstAdaptiveDemux2Stream
508508 GST_DEBUG_OBJECT (pad, "buffer %" GST_PTR_FORMAT, buffer);
509509
510510 TRACKS_LOCK (demux);
511
512 /* Discard buffers that are received outside of a valid segment. This can
513 * happen if a flushing seek (which resets the track segment seqnums) was
514 * received but the stream is still providing buffers before returning.
515 */
516 if (track->input_segment_seqnum == GST_SEQNUM_INVALID) {
517 GST_DEBUG_OBJECT (pad,
518 "Dropping buffer because we do not have a valid input segment");
519 gst_buffer_unref (buffer);
520 TRACKS_UNLOCK (demux);
521 return GST_FLOW_OK;
522 }
511523
512524 ts = GST_BUFFER_DTS_OR_PTS (buffer);
513525
658670 return TRUE;
659671 }
660672
673 if (seg_seqnum != demux->priv->segment_seqnum) {
674 GST_DEBUG_OBJECT (pad, "Ignoring non-current segment");
675 gst_event_unref (event);
676 TRACKS_UNLOCK (demux);
677
678 return TRUE;
679 }
680
661681 track->input_segment_seqnum = seg_seqnum;
662682 gst_event_copy_segment (event, &track->input_segment);
663683 if (track->input_segment.rate >= 0)
13881388 }
13891389
13901390 static gboolean
1391 gst_adaptive_demux_query (GstElement * element, GstQuery * query)
1392 {
1393 GstAdaptiveDemux *demux = GST_ADAPTIVE_DEMUX_CAST (element);
1394
1395 GST_LOG_OBJECT (demux, "%" GST_PTR_FORMAT, query);
1396
1397 switch (GST_QUERY_TYPE (query)) {
1398 case GST_QUERY_BUFFERING:
1399 {
1400 GstFormat format;
1401 gst_query_parse_buffering_range (query, &format, NULL, NULL, NULL);
1402
1403 if (!demux->output_period) {
1404 if (format != GST_FORMAT_TIME) {
1405 GST_DEBUG_OBJECT (demux,
1406 "No period setup yet, can't answer non-TIME buffering queries");
1407 return FALSE;
1408 }
1409
1410 GST_DEBUG_OBJECT (demux,
1411 "No period setup yet, but still answering buffering query");
1412 return TRUE;
1413 }
1414 }
1415 default:
1416 break;
1417 }
1418
1419 return GST_ELEMENT_CLASS (parent_class)->query (element, query);
1420 }
1421
1422 static gboolean
14231391 gst_adaptive_demux_send_event (GstElement * element, GstEvent * event)
14241392 {
14251393 GstAdaptiveDemux *demux = GST_ADAPTIVE_DEMUX_CAST (element);
20091977 gint64 start, stop;
20101978 guint32 seqnum;
20111979 gboolean update;
2012 gboolean ret;
1980 gboolean ret = FALSE;
20131981 GstSegment oldsegment;
20141982 GstEvent *flush_event;
20151983
20161984 GST_INFO_OBJECT (demux, "Received seek event");
20171985
2018 GST_API_LOCK (demux);
2019
20201986 gst_event_parse_seek (event, &rate, &format, &flags, &start_type, &start,
20211987 &stop_type, &stop);
20221988
20231989 if (format != GST_FORMAT_TIME) {
2024 GST_API_UNLOCK (demux);
20251990 GST_WARNING_OBJECT (demux,
20261991 "Adaptive demuxers only support TIME-based seeking");
20271992 gst_event_unref (event);
20301995
20311996 if (flags & GST_SEEK_FLAG_SEGMENT) {
20321997 GST_FIXME_OBJECT (demux, "Handle segment seeks");
2033 GST_API_UNLOCK (demux);
20341998 gst_event_unref (event);
20351999 return FALSE;
20362000 }
20372001
20382002 seqnum = gst_event_get_seqnum (event);
20392003
2004 GST_API_LOCK (demux);
20402005 if (!GST_ADAPTIVE_SCHEDULER_LOCK (demux)) {
20412006 GST_LOG_OBJECT (demux, "Failed to acquire scheduler context");
2007 GST_API_UNLOCK (demux);
20422008 return FALSE;
20432009 }
20442010
20592025 GST_ERROR_OBJECT (demux,
20602026 "Instant rate change seeks only supported in the "
20612027 "same direction, without flushing and position change");
2062 GST_ADAPTIVE_SCHEDULER_UNLOCK (demux);
2063 GST_API_UNLOCK (demux);
2064 return FALSE;
2028 goto unlock_return;
20652029 }
20662030
20672031 rate_multiplier = rate / demux->segment.rate;
20772041 demux->instant_rate_multiplier = rate_multiplier;
20782042 GST_ADAPTIVE_DEMUX_SEGMENT_UNLOCK (demux);
20792043 }
2080
2081 GST_ADAPTIVE_SCHEDULER_UNLOCK (demux);
2082 GST_API_UNLOCK (demux);
2083 gst_event_unref (event);
2084
2085 return ret;
2086 }
2087
2088 if (!gst_adaptive_demux_can_seek (demux)) {
2089 GST_ADAPTIVE_SCHEDULER_UNLOCK (demux);
2090
2091 GST_API_UNLOCK (demux);
2092 gst_event_unref (event);
2093 return FALSE;
2094 }
2044 goto unlock_return;
2045 }
2046
2047 if (!gst_adaptive_demux_can_seek (demux))
2048 goto unlock_return;
20952049
20962050 /* We can only accept flushing seeks from this point onward */
20972051 if (!(flags & GST_SEEK_FLAG_FLUSH)) {
20982052 GST_ERROR_OBJECT (demux,
20992053 "Non-flushing non-instant-rate seeks are not possible");
2100
2101 GST_ADAPTIVE_SCHEDULER_UNLOCK (demux);
2102
2103 GST_API_UNLOCK (demux);
2104 gst_event_unref (event);
2105 return FALSE;
2054 goto unlock_return;
21062055 }
21072056
21082057 if (gst_adaptive_demux_is_live (demux)) {
21122061
21132062 if (!gst_adaptive_demux_get_live_seek_range (demux, &range_start,
21142063 &range_stop)) {
2115 GST_ADAPTIVE_SCHEDULER_UNLOCK (demux);
2116 GST_API_UNLOCK (demux);
2117 gst_event_unref (event);
21182064 GST_WARNING_OBJECT (demux, "Failure getting the live seek ranges");
2119 return FALSE;
2065 goto unlock_return;
21202066 }
21212067
21222068 GST_DEBUG_OBJECT (demux,
21782124 }
21792125
21802126 /* If the seek position is still outside of the seekable range, refuse the seek */
2181 if (!start_valid || !stop_valid) {
2182 GST_ADAPTIVE_SCHEDULER_UNLOCK (demux);
2183 GST_API_UNLOCK (demux);
2184 gst_event_unref (event);
2185 return FALSE;
2186 }
2127 if (!start_valid || !stop_valid)
2128 goto unlock_return;
21872129
21882130 /* Re-create seek event with changed/updated values */
21892131 if (changed) {
22112153
22122154 GST_ADAPTIVE_DEMUX_SEGMENT_LOCK (demux);
22132155
2214 /*
2215 * Handle snap seeks as follows:
2216 * 1) do the snap seeking a (random) active stream
2217 * 2) use the final position on this stream to seek
2218 * on the other streams to the same position
2219 *
2220 * We can't snap at all streams at the same time as they might end in
2221 * different positions, so just pick one and align all others to that
2222 * position.
2223 */
2224
2225 GstAdaptiveDemux2Stream *stream = NULL;
2226 GList *iter;
2227 /* Pick a random active stream on which to do the stream seek */
2228 for (iter = demux->output_period->streams; iter; iter = iter->next) {
2229 GstAdaptiveDemux2Stream *cand = iter->data;
2230 if (gst_adaptive_demux2_stream_is_selected_locked (cand)) {
2231 stream = cand;
2232 break;
2233 }
2234 }
2235
2236 if (stream && IS_SNAP_SEEK (flags)) {
2237 GstClockTimeDiff ts;
2238 GstSeekFlags stream_seek_flags = flags;
2239
2240 /* snap-seek on the chosen stream and then
2241 * use the resulting position to seek on all streams */
2242 if (rate >= 0) {
2243 if (start_type != GST_SEEK_TYPE_NONE)
2244 ts = start;
2245 else {
2246 ts = gst_segment_position_from_running_time (&demux->segment,
2247 GST_FORMAT_TIME, demux->priv->global_output_position);
2248 start_type = GST_SEEK_TYPE_SET;
2156 if (!IS_SNAP_SEEK (flags) && !(flags & GST_SEEK_FLAG_ACCURATE)) {
2157 /* If no accurate seeking was specified, we want to default to seeking to
2158 * the previous segment for efficient/fast playback. */
2159 flags |= GST_SEEK_FLAG_KEY_UNIT;
2160 }
2161
2162 if (IS_SNAP_SEEK (flags)) {
2163 GstAdaptiveDemux2Stream *default_stream = NULL;
2164 GstAdaptiveDemux2Stream *stream = NULL;
2165 GList *iter;
2166 /*
2167 * Handle snap seeks as follows:
2168 * 1) do the snap seeking a (random) active stream
2169 * 1.1) If none are active yet (early-seek), pick a random default one
2170 * 2) use the final position on this stream to seek
2171 * on the other streams to the same position
2172 *
2173 * We can't snap at all streams at the same time as they might end in
2174 * different positions, so just pick one and align all others to that
2175 * position.
2176 */
2177
2178 /* Pick a random active stream on which to do the stream seek */
2179 for (iter = demux->output_period->streams; iter; iter = iter->next) {
2180 GstAdaptiveDemux2Stream *cand = iter->data;
2181 if (gst_adaptive_demux2_stream_is_selected_locked (cand)) {
2182 stream = cand;
2183 break;
22492184 }
2250 } else {
2251 if (stop_type != GST_SEEK_TYPE_NONE)
2252 ts = stop;
2253 else {
2254 stop_type = GST_SEEK_TYPE_SET;
2255 ts = gst_segment_position_from_running_time (&demux->segment,
2256 GST_FORMAT_TIME, demux->priv->global_output_position);
2185 if (default_stream == NULL
2186 && gst_adaptive_demux2_stream_is_default_locked (cand))
2187 default_stream = cand;
2188 }
2189
2190 if (stream == NULL)
2191 stream = default_stream;
2192
2193 if (stream) {
2194 GstClockTimeDiff ts;
2195 GstSeekFlags stream_seek_flags = flags;
2196
2197 /* snap-seek on the chosen stream and then
2198 * use the resulting position to seek on all streams */
2199 if (rate >= 0) {
2200 if (start_type != GST_SEEK_TYPE_NONE)
2201 ts = start;
2202 else {
2203 ts = gst_segment_position_from_running_time (&demux->segment,
2204 GST_FORMAT_TIME, demux->priv->global_output_position);
2205 start_type = GST_SEEK_TYPE_SET;
2206 }
2207 } else {
2208 if (stop_type != GST_SEEK_TYPE_NONE)
2209 ts = stop;
2210 else {
2211 stop_type = GST_SEEK_TYPE_SET;
2212 ts = gst_segment_position_from_running_time (&demux->segment,
2213 GST_FORMAT_TIME, demux->priv->global_output_position);
2214 }
22572215 }
2258 }
2259
2260 if (gst_adaptive_demux2_stream_seek (stream, rate >= 0, stream_seek_flags,
2261 ts, &ts) != GST_FLOW_OK) {
2262 GST_ADAPTIVE_SCHEDULER_UNLOCK (demux);
2263
2264 GST_API_UNLOCK (demux);
2216
2217 if (gst_adaptive_demux2_stream_seek (stream, rate >= 0, stream_seek_flags,
2218 ts, &ts) != GST_FLOW_OK) {
2219 GST_ADAPTIVE_DEMUX_SEGMENT_UNLOCK (demux);
2220 goto unlock_return;
2221 }
2222 /* replace event with a new one without snapping to seek on all streams */
22652223 gst_event_unref (event);
2266 return FALSE;
2267 }
2268
2269 /* replace event with a new one without snapping to seek on all streams */
2270 gst_event_unref (event);
2271 if (rate >= 0) {
2272 start = ts;
2273 } else {
2274 stop = ts;
2275 }
2276 event =
2277 gst_event_new_seek (rate, format, REMOVE_SNAP_FLAGS (flags),
2278 start_type, start, stop_type, stop);
2279 GST_DEBUG_OBJECT (demux, "Adapted snap seek to %" GST_PTR_FORMAT, event);
2224 if (rate >= 0) {
2225 start = ts;
2226 } else {
2227 stop = ts;
2228 }
2229 event =
2230 gst_event_new_seek (rate, format, REMOVE_SNAP_FLAGS (flags),
2231 start_type, start, stop_type, stop);
2232 GST_DEBUG_OBJECT (demux, "Adapted snap seek to %" GST_PTR_FORMAT, event);
2233 }
22802234 }
22812235
22822236 ret = gst_segment_do_seek (&demux->segment, rate, format, flags, start_type,
23282282 /* Restart the demux */
23292283 gst_adaptive_demux_start_tasks (demux);
23302284
2285 unlock_return:
23312286 GST_ADAPTIVE_SCHEDULER_UNLOCK (demux);
23322287 GST_API_UNLOCK (demux);
23332288 gst_event_unref (event);
25702525 }
25712526
25722527 static gboolean
2528 gst_adaptive_demux_handle_query_seeking (GstAdaptiveDemux * demux,
2529 GstQuery * query)
2530 {
2531 GstFormat fmt = GST_FORMAT_UNDEFINED;
2532 gint64 stop = -1;
2533 gint64 start = 0;
2534 gboolean ret = FALSE;
2535
2536 if (!g_atomic_int_get (&demux->priv->have_manifest)) {
2537 GST_INFO_OBJECT (demux,
2538 "Don't have manifest yet, can't answer seeking query");
2539 return FALSE; /* can't answer without manifest */
2540 }
2541
2542 GST_MANIFEST_LOCK (demux);
2543
2544 gst_query_parse_seeking (query, &fmt, NULL, NULL, NULL);
2545 GST_INFO_OBJECT (demux, "Received GST_QUERY_SEEKING with format %d", fmt);
2546 if (fmt == GST_FORMAT_TIME) {
2547 GstClockTime duration;
2548 gboolean can_seek = gst_adaptive_demux_can_seek (demux);
2549
2550 ret = TRUE;
2551 if (can_seek) {
2552 if (gst_adaptive_demux_is_live (demux)) {
2553 ret = gst_adaptive_demux_get_live_seek_range (demux, &start, &stop);
2554
2555 if (!ret) {
2556 GST_MANIFEST_UNLOCK (demux);
2557 GST_INFO_OBJECT (demux, "can't answer seeking query");
2558 return FALSE;
2559 }
2560 } else {
2561 duration = demux->priv->duration;
2562 if (GST_CLOCK_TIME_IS_VALID (duration) && duration > 0)
2563 stop = duration;
2564 }
2565 }
2566 gst_query_set_seeking (query, fmt, can_seek, start, stop);
2567 GST_INFO_OBJECT (demux, "GST_QUERY_SEEKING returning with start : %"
2568 GST_TIME_FORMAT ", stop : %" GST_TIME_FORMAT,
2569 GST_TIME_ARGS (start), GST_TIME_ARGS (stop));
2570 }
2571 GST_MANIFEST_UNLOCK (demux);
2572 return ret;
2573 }
2574
2575 static gboolean
25732576 gst_adaptive_demux_src_query (GstPad * pad, GstObject * parent,
25742577 GstQuery * query)
25752578 {
25782581
25792582 if (query == NULL)
25802583 return FALSE;
2581
25822584
25832585 switch (query->type) {
25842586 case GST_QUERY_DURATION:{
26162618 ret = TRUE;
26172619 break;
26182620 }
2619 case GST_QUERY_SEEKING:{
2620 GstFormat fmt;
2621 gint64 stop = -1;
2622 gint64 start = 0;
2623
2624 if (!g_atomic_int_get (&demux->priv->have_manifest)) {
2625 GST_INFO_OBJECT (demux,
2626 "Don't have manifest yet, can't answer seeking query");
2627 return FALSE; /* can't answer without manifest */
2628 }
2629
2630 GST_MANIFEST_LOCK (demux);
2631
2632 gst_query_parse_seeking (query, &fmt, NULL, NULL, NULL);
2633 GST_INFO_OBJECT (demux, "Received GST_QUERY_SEEKING with format %d", fmt);
2634 if (fmt == GST_FORMAT_TIME) {
2635 GstClockTime duration;
2636 gboolean can_seek = gst_adaptive_demux_can_seek (demux);
2637
2638 ret = TRUE;
2639 if (can_seek) {
2640 if (gst_adaptive_demux_is_live (demux)) {
2641 ret = gst_adaptive_demux_get_live_seek_range (demux, &start, &stop);
2642 if (!ret) {
2643 GST_MANIFEST_UNLOCK (demux);
2644 GST_INFO_OBJECT (demux, "can't answer seeking query");
2645 return FALSE;
2646 }
2647 } else {
2648 duration = demux->priv->duration;
2649 if (GST_CLOCK_TIME_IS_VALID (duration) && duration > 0)
2650 stop = duration;
2651 }
2652 }
2653 gst_query_set_seeking (query, fmt, can_seek, start, stop);
2654 GST_INFO_OBJECT (demux, "GST_QUERY_SEEKING returning with start : %"
2655 GST_TIME_FORMAT ", stop : %" GST_TIME_FORMAT,
2656 GST_TIME_ARGS (start), GST_TIME_ARGS (stop));
2657 }
2658 GST_MANIFEST_UNLOCK (demux);
2659 break;
2660 }
2621 case GST_QUERY_SEEKING:
2622 ret = gst_adaptive_demux_handle_query_seeking (demux, query);
2623 break;
26612624 case GST_QUERY_URI:
26622625
26632626 GST_MANIFEST_LOCK (demux);
26852648 }
26862649
26872650 return ret;
2651 }
2652
2653 static gboolean
2654 gst_adaptive_demux_query (GstElement * element, GstQuery * query)
2655 {
2656 GstAdaptiveDemux *demux = GST_ADAPTIVE_DEMUX_CAST (element);
2657
2658 GST_LOG_OBJECT (demux, "%" GST_PTR_FORMAT, query);
2659
2660 switch (GST_QUERY_TYPE (query)) {
2661 case GST_QUERY_BUFFERING:
2662 {
2663 GstFormat format;
2664 gst_query_parse_buffering_range (query, &format, NULL, NULL, NULL);
2665
2666 if (!demux->output_period) {
2667 if (format != GST_FORMAT_TIME) {
2668 GST_DEBUG_OBJECT (demux,
2669 "No period setup yet, can't answer non-TIME buffering queries");
2670 return FALSE;
2671 }
2672
2673 GST_DEBUG_OBJECT (demux,
2674 "No period setup yet, but still answering buffering query");
2675 return TRUE;
2676 }
2677 }
2678 case GST_QUERY_SEEKING:
2679 {
2680 /* Source pads might not be present early on which would cause the default
2681 * element query handler to fail, yet we can answer this query */
2682 return gst_adaptive_demux_handle_query_seeking (demux, query);
2683 }
2684 default:
2685 break;
2686 }
2687
2688 return GST_ELEMENT_CLASS (parent_class)->query (element, query);
26882689 }
26892690
26902691 gboolean
943943 out:
944944 if (ret) {
945945 gchar *newfile;
946
947 /* Ensure file always ends with an empty newline by adding an empty
948 * line. This helps downstream parsers properly detect entries */
949 g_ptr_array_add (builder, g_strdup ("\n"));
946950 /* Add NULL-terminator to string list */
947951 g_ptr_array_add (builder, NULL);
948952 newfile = g_strjoinv ("\n", (gchar **) builder->pdata);
18561856 GstHLSMediaPlaylist * current)
18571857 {
18581858 GstAdaptiveDemux *adaptive_demux;
1859 const gchar *main_uri;
18601859 DownloadRequest *download;
18611860 GstBuffer *buf;
18621861 gchar *playlist_data;
18651864 gboolean playlist_uri_change = FALSE;
18661865
18671866 adaptive_demux = GST_ADAPTIVE_DEMUX (demux);
1868 main_uri = gst_adaptive_demux_get_manifest_ref_uri (adaptive_demux);
18691867
18701868 /* If there's no previous playlist, or the URI changed this
18711869 * is not a refresh/update but a switch to a new playlist */
18771875
18781876 download =
18791877 downloadhelper_fetch_uri (adaptive_demux->download_helper,
1880 uri, main_uri, DOWNLOAD_FLAG_COMPRESS | DOWNLOAD_FLAG_FORCE_REFRESH, err);
1878 uri, NULL, DOWNLOAD_FLAG_COMPRESS | DOWNLOAD_FLAG_FORCE_REFRESH, err);
18811879
18821880 if (download == NULL)
18831881 return NULL;
322322 dst.w = allocation->width;
323323 dst.h = allocation->height;
324324
325 gst_video_sink_center_rect (src, dst, result, TRUE);
325 if (base_widget->display_width > 0 && base_widget->display_height > 0)
326 gst_video_sink_center_rect (src, dst, result, TRUE);
326327 } else {
327328 result->x = 0;
328329 result->y = 0;
4343 #include <gst/gl/wayland/gstgldisplay_wayland.h>
4444 #endif
4545
46 #if GST_GL_HAVE_WINDOW_VIV_FB
46 #if GST_GL_HAVE_WINDOW_VIV_FB && defined (HAVE_QT_VIV_FB)
4747 #include <gst/gl/viv-fb/gstgldisplay_viv_fb.h>
4848 #endif
4949
116116 }
117117 #elif GST_GL_HAVE_PLATFORM_EGL && defined (HAVE_QT_EGLFS)
118118 if (QString::fromUtf8("eglfs") == app->platformName()) {
119 #if GST_GL_HAVE_WINDOW_VIV_FB
119 #if GST_GL_HAVE_WINDOW_VIV_FB && defined (HAVE_QT_VIV_FB)
120120 /* FIXME: Could get the display directly from Qt like this
121121 * QPlatformNativeInterface *native =
122122 * QGuiApplication::platformNativeInterface();
201201 }
202202 #endif
203203 #if GST_GL_HAVE_PLATFORM_EGL && defined (HAVE_QT_EGLFS)
204 #if GST_GL_HAVE_WINDOW_VIV_FB
204 #if GST_GL_HAVE_WINDOW_VIV_FB && defined (HAVE_QT_VIV_FB)
205205 if (GST_IS_GL_DISPLAY_VIV_FB (display)) {
206206 #else
207207 if (GST_IS_GL_DISPLAY_EGL (display)) {
183183 endif
184184 endif
185185
186 # EGL windowing for Vivante Framebuffer (e.g. i.MX6)
187 qt5_viv_fb = qt5_egl \
188 .require(host_system == 'linux') \
189 .require(gstglviv_fb_dep.found(), error_message: 'gstreamer-gl-viv_fb-1.0 is required') \
190 .require(gst_gl_have_platform_egl, error_message: 'egl platform support in gstreamer-gl is required')
191 if qt5_viv_fb.allowed()
192 qt_defines += ['-DHAVE_QT_VIV_FB']
193 optional_deps += gstglviv_fb_dep
194 have_qt_windowing = true
195 endif
196
186197 if qt5_option.require(have_qt_windowing).allowed()
187198 # rpath is needed to be able to load the plugin on macOS inside the devenv
188199 qmlgl_kwargs = {}
290290 gst_gl_context_activate (this->priv->other_context, TRUE);
291291
292292 if (!texNode) {
293 bool is_smooth = this->smooth ();
293294 texNode = new GstQSG6OpenGLNode (this);
295 texNode->setFiltering (is_smooth ? QSGTexture::Filtering::Linear :
296 QSGTexture::Filtering::Nearest);
294297 this->priv->m_node = texNode;
295298 }
296299
1297712977 channel_mapping_family, stream_count, coupled_count,
1297812978 channel_mapping);
1297912979 g_free (channel_mapping);
12980
12981 entry->sampled = TRUE;
12982
1298012983 break;
1298112984 }
1298212985 default:
62306230 "received format %d segment %" GST_SEGMENT_FORMAT, segment->format,
62316231 segment);
62326232
6233 if (demux->common.state < GST_MATROSKA_READ_STATE_DATA) {
6234 GST_DEBUG_OBJECT (demux, "still starting");
6235 goto exit;
6236 }
6237
62386233 if (segment->format == GST_FORMAT_TIME) {
62396234 demux->upstream_format_is_time = TRUE;
62406235 demux->segment_seqnum = gst_event_get_seqnum (event);
62416236 gst_segment_copy_into (segment, &demux->common.segment);
62426237 GST_DEBUG_OBJECT (demux, "Got segment in TIME format: %" GST_PTR_FORMAT,
62436238 event);
6239 goto exit;
6240 }
6241
6242 if (demux->common.state < GST_MATROSKA_READ_STATE_DATA) {
6243 GST_DEBUG_OBJECT (demux, "still starting");
62446244 goto exit;
62456245 }
62466246
447447
448448 /* Unencrypted buffer */
449449 if (!(signal_byte & GST_MATROSKA_BLOCK_ENCRYPTED)) {
450 *size_out = gst_byte_reader_get_remaining (&reader);
451 gst_byte_reader_get_data (&reader, *size_out, (const guint8 **) data_out);
450452 return TRUE;
451453 }
452454
31553155 GstEvent * event)
31563156 {
31573157 GstRTSPStream *stream;
3158 GstRTSPSrc *self = GST_RTSPSRC (GST_OBJECT_PARENT (parent));
31593158
31603159 stream = gst_pad_get_element_private (pad);
31613160
3162 event = gst_rtspsrc_update_src_event (self, stream, event);
3161 event = gst_rtspsrc_update_src_event (stream->parent, stream, event);
31633162
31643163 return gst_pad_push_event (stream->srcpad, event);
31653164 }
17871787
17881788 if (gst_video_orientation_from_tag (taglist, &method)) {
17891789 gst_video_flip_set_method (vf, method, TRUE);
1790
1791 if (vf->method == GST_VIDEO_ORIENTATION_AUTO) {
1792 /* update the orientation tag as we rotate the video accordingly */
1793 if (gst_tag_list_is_writable (taglist)) {
1794 gst_tag_list_add (taglist, GST_TAG_MERGE_REPLACE,
1795 "image-orientation", "rotate-0", NULL);
1796 } else {
1797 taglist = gst_tag_list_copy (taglist);
1798
1799 gst_tag_list_add (taglist, GST_TAG_MERGE_REPLACE,
1800 "image-orientation", "rotate-0", NULL);
1801
1802 gst_event_unref (event);
1803 event = gst_event_new_tag (taglist);
1804 }
1805 }
17901806 }
17911807 break;
17921808 default:
3333
3434 <release>
3535 <Version>
36 <revision>1.22.5</revision>
37 <branch>1.22</branch>
38 <name></name>
39 <created>2023-07-20</created>
40 <file-release rdf:resource="https://gstreamer.freedesktop.org/src/gst-plugins-good/gst-plugins-good-1.22.5.tar.xz" />
41 </Version>
42 </release>
43
44 <release>
45 <Version>
3646 <revision>1.22.4</revision>
3747 <branch>1.22</branch>
3848 <name></name>
00 project('gst-plugins-good', 'c',
1 version : '1.22.4',
1 version : '1.22.5',
22 meson_version : '>= 0.62',
33 default_options : [ 'warning_level=1',
44 'buildtype=debugoptimized' ])
320320 gstglx11_dep = dependency('', required : false)
321321 gstglwayland_dep = dependency('', required : false)
322322 gstglegl_dep = dependency('', required : false)
323 gstglviv_fb_dep = dependency('', required : false)
323324
324325 have_gstgl = gstgl_dep.found()
325326
339340 message('GStreamer OpenGL platforms: @0@'.format(' '.join(gst_gl_platforms)))
340341 message('GStreamer OpenGL apis: @0@'.format(' '.join(gst_gl_apis)))
341342
342 foreach ws : ['x11', 'wayland', 'android', 'cocoa', 'eagl', 'win32', 'dispmanx', 'viv_fb']
343 foreach ws : ['x11', 'wayland', 'android', 'cocoa', 'eagl', 'win32', 'dispmanx']
343344 set_variable('gst_gl_have_window_@0@'.format(ws), gst_gl_winsys.contains(ws))
344345 endforeach
346 # Handling viv-fb separately, because the winsys is called "viv-fb", but the
347 # variable suffix must be "viv_fb" (dashes are not allowed in variable names).
348 set_variable('gst_gl_have_window_viv_fb', gst_gl_winsys.contains('viv-fb'))
345349
346350 foreach p : ['glx', 'egl', 'cgl', 'eagl', 'wgl']
347351 set_variable('gst_gl_have_platform_@0@'.format(p), gst_gl_platforms.contains(p))
368372 if gst_gl_have_platform_egl
369373 gstglegl_dep = dependency('gstreamer-gl-egl-1.0', version : gst_req,
370374 fallback : ['gst-plugins-base', 'gstglegl_dep'], required: true)
375 endif
376 if gst_gl_have_window_viv_fb
377 gstglviv_fb_dep = dependency('gstreamer-gl-viv-fb-1.0', version : gst_req,
378 fallback : ['gst-plugins-base', 'gstglviv_fb_dep'], required: true)
371379 endif
372380 endif
373381
55 #, fuzzy
66 msgid ""
77 msgstr ""
8 "Project-Id-Version: gst-plugins-good-1.22.4\n"
8 "Project-Id-Version: gst-plugins-good-1.22.5\n"
99 "Report-Msgid-Bugs-To: \n"
10 "POT-Creation-Date: 2023-06-20 17:45+0100\n"
10 "POT-Creation-Date: 2023-07-20 15:24+0100\n"
1111 "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
1212 "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
1313 "Language-Team: LANGUAGE <LL@li.org>\n"
110110 #: gst/isomp4/qtdemux.c:4364 gst/isomp4/qtdemux.c:8521
111111 #: gst/isomp4/qtdemux.c:8528 gst/isomp4/qtdemux.c:9836
112112 #: gst/isomp4/qtdemux.c:10278 gst/isomp4/qtdemux.c:10285
113 #: gst/isomp4/qtdemux.c:13522
113 #: gst/isomp4/qtdemux.c:13525
114114 msgid "This file is corrupt and cannot be played."
115115 msgstr ""
116116
134134 msgid "The video in this file might not play correctly."
135135 msgstr ""
136136
137 #: gst/rtsp/gstrtspsrc.c:7894
137 #: gst/rtsp/gstrtspsrc.c:7893
138138 msgid ""
139139 "No supported stream was found. You might need to install a GStreamer RTSP "
140140 "extension plugin for Real media streams."
141141 msgstr ""
142142
143 #: gst/rtsp/gstrtspsrc.c:7899
143 #: gst/rtsp/gstrtspsrc.c:7898
144144 msgid ""
145145 "No supported stream was found. You might need to allow more transport "
146146 "protocols or may otherwise be missing the right GStreamer RTSP extension "
347347 msgid "Failed to allocated required memory."
348348 msgstr ""
349349
350 #: sys/v4l2/gstv4l2src.c:977 sys/v4l2/gstv4l2videodec.c:695
351 #: sys/v4l2/gstv4l2videodec.c:1064 sys/v4l2/gstv4l2videoenc.c:861
350 #: sys/v4l2/gstv4l2src.c:977 sys/v4l2/gstv4l2videodec.c:525
351 #: sys/v4l2/gstv4l2videodec.c:1048 sys/v4l2/gstv4l2videoenc.c:881
352352 msgid "Failed to allocate required memory."
353353 msgstr ""
354354
367367 msgid "Decoder on device %s has no supported input format"
368368 msgstr ""
369369
370 #: sys/v4l2/gstv4l2videodec.c:1078
370 #: sys/v4l2/gstv4l2videodec.c:1062
371371 msgid "Failed to start decoding thread."
372372 msgstr ""
373373
374 #: sys/v4l2/gstv4l2videodec.c:1085 sys/v4l2/gstv4l2videoenc.c:882
374 #: sys/v4l2/gstv4l2videodec.c:1069 sys/v4l2/gstv4l2videoenc.c:902
375375 msgid "Failed to process frame."
376376 msgstr ""
377377
385385 msgid "Encoder on device %s has no supported input format"
386386 msgstr ""
387387
388 #: sys/v4l2/gstv4l2videoenc.c:826
388 #: sys/v4l2/gstv4l2videoenc.c:846
389389 msgid "Failed to force keyframe."
390390 msgstr ""
391391
392 #: sys/v4l2/gstv4l2videoenc.c:874
392 #: sys/v4l2/gstv4l2videoenc.c:894
393393 msgid "Failed to start encoding thread."
394394 msgstr ""
395395
55 #, fuzzy
66 msgid ""
77 msgstr ""
8 "Project-Id-Version: gst-plugins-good-1.22.4\n"
8 "Project-Id-Version: gst-plugins-good-1.22.5\n"
99 "Report-Msgid-Bugs-To: \n"
10 "POT-Creation-Date: 2023-06-20 17:45+0100\n"
10 "POT-Creation-Date: 2023-07-20 15:24+0100\n"
1111 "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
1212 "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
1313 "Language-Team: LANGUAGE <LL@li.org>\n"
110110 #: gst/isomp4/qtdemux.c:4364 gst/isomp4/qtdemux.c:8521
111111 #: gst/isomp4/qtdemux.c:8528 gst/isomp4/qtdemux.c:9836
112112 #: gst/isomp4/qtdemux.c:10278 gst/isomp4/qtdemux.c:10285
113 #: gst/isomp4/qtdemux.c:13522
113 #: gst/isomp4/qtdemux.c:13525
114114 msgid "This file is corrupt and cannot be played."
115115 msgstr ""
116116
134134 msgid "The video in this file might not play correctly."
135135 msgstr ""
136136
137 #: gst/rtsp/gstrtspsrc.c:7894
137 #: gst/rtsp/gstrtspsrc.c:7893
138138 msgid ""
139139 "No supported stream was found. You might need to install a GStreamer RTSP "
140140 "extension plugin for Real media streams."
141141 msgstr ""
142142
143 #: gst/rtsp/gstrtspsrc.c:7899
143 #: gst/rtsp/gstrtspsrc.c:7898
144144 msgid ""
145145 "No supported stream was found. You might need to allow more transport "
146146 "protocols or may otherwise be missing the right GStreamer RTSP extension "
347347 msgid "Failed to allocated required memory."
348348 msgstr ""
349349
350 #: sys/v4l2/gstv4l2src.c:977 sys/v4l2/gstv4l2videodec.c:695
351 #: sys/v4l2/gstv4l2videodec.c:1064 sys/v4l2/gstv4l2videoenc.c:861
350 #: sys/v4l2/gstv4l2src.c:977 sys/v4l2/gstv4l2videodec.c:525
351 #: sys/v4l2/gstv4l2videodec.c:1048 sys/v4l2/gstv4l2videoenc.c:881
352352 msgid "Failed to allocate required memory."
353353 msgstr ""
354354
367367 msgid "Decoder on device %s has no supported input format"
368368 msgstr ""
369369
370 #: sys/v4l2/gstv4l2videodec.c:1078
370 #: sys/v4l2/gstv4l2videodec.c:1062
371371 msgid "Failed to start decoding thread."
372372 msgstr ""
373373
374 #: sys/v4l2/gstv4l2videodec.c:1085 sys/v4l2/gstv4l2videoenc.c:882
374 #: sys/v4l2/gstv4l2videodec.c:1069 sys/v4l2/gstv4l2videoenc.c:902
375375 msgid "Failed to process frame."
376376 msgstr ""
377377
385385 msgid "Encoder on device %s has no supported input format"
386386 msgstr ""
387387
388 #: sys/v4l2/gstv4l2videoenc.c:826
388 #: sys/v4l2/gstv4l2videoenc.c:846
389389 msgid "Failed to force keyframe."
390390 msgstr ""
391391
392 #: sys/v4l2/gstv4l2videoenc.c:874
392 #: sys/v4l2/gstv4l2videoenc.c:894
393393 msgid "Failed to start encoding thread."
394394 msgstr ""
395395
11471147 return ret;
11481148 }
11491149
1150 static gboolean
1151 gst_v4l2src_handle_resolution_change (GstV4l2Src * v4l2src)
1152 {
1153 GST_INFO_OBJECT (v4l2src, "Resolution change detected.");
1154
1155 /* It is required to always cycle through streamoff, we also need to
1156 * streamoff in order to allow locking a new DV_TIMING which will
1157 * influence the output of TRY_FMT */
1158 gst_v4l2src_stop (GST_BASE_SRC (v4l2src));
1159
1160 /* Force renegotiation */
1161 v4l2src->renegotiation_adjust = v4l2src->offset + 1;
1162 v4l2src->pending_set_fmt = TRUE;
1163
1164 return gst_base_src_negotiate (GST_BASE_SRC (v4l2src));
1165 }
1166
11501167 static GstFlowReturn
11511168 gst_v4l2src_create (GstPushSrc * src, GstBuffer ** buf)
11521169 {
11651182
11661183 if (G_UNLIKELY (ret != GST_FLOW_OK)) {
11671184 if (ret == GST_V4L2_FLOW_RESOLUTION_CHANGE) {
1168 GST_INFO_OBJECT (v4l2src, "Resolution change detected.");
1169
1170 /* It is required to always cycle through streamoff, we also need to
1171 * streamoff in order to allow locking a new DV_TIMING which will
1172 * influence the output of TRY_FMT */
1173 gst_v4l2src_stop (GST_BASE_SRC (src));
1174
1175 /* Force renegotiation */
1176 v4l2src->renegotiation_adjust = v4l2src->offset + 1;
1177 v4l2src->pending_set_fmt = TRUE;
1178
1179 if (!gst_base_src_negotiate (GST_BASE_SRC (src))) {
1185 if (!gst_v4l2src_handle_resolution_change (v4l2src)) {
11801186 ret = GST_FLOW_NOT_NEGOTIATED;
11811187 goto error;
11821188 }
11921198 ret = gst_v4l2_buffer_pool_process (obj_pool, buf, NULL);
11931199 if (obj_pool)
11941200 gst_object_unref (obj_pool);
1201
1202 if (G_UNLIKELY (ret == GST_V4L2_FLOW_RESOLUTION_CHANGE)) {
1203 if (!gst_v4l2src_handle_resolution_change (v4l2src)) {
1204 ret = GST_FLOW_NOT_NEGOTIATED;
1205 goto error;
1206 }
1207 }
11951208 }
11961209
11971210 } while (ret == GST_V4L2_FLOW_CORRUPTED_BUFFER ||
358358 }
359359
360360 static gboolean
361 gst_v4l2_video_remove_padding (GstCapsFeatures * features,
362 GstStructure * structure, gpointer user_data)
363 {
364 GstV4l2VideoDec *self = GST_V4L2_VIDEO_DEC (user_data);
365 GstVideoAlignment *align = &self->v4l2capture->align;
366 GstVideoInfo *info = &self->v4l2capture->info;
367 int width, height;
368
369 if (!gst_structure_get_int (structure, "width", &width))
370 return TRUE;
371
372 if (!gst_structure_get_int (structure, "height", &height))
373 return TRUE;
374
375 if (align->padding_left != 0 || align->padding_top != 0 ||
376 height != info->height + align->padding_bottom)
377 return TRUE;
378
379 if (height == info->height + align->padding_bottom) {
380 /* Some drivers may round up width to the padded with */
381 if (width == info->width + align->padding_right)
382 gst_structure_set (structure,
383 "width", G_TYPE_INT, width - align->padding_right,
384 "height", G_TYPE_INT, height - align->padding_bottom, NULL);
385 /* Some drivers may keep visible width and only round up bytesperline */
386 else if (width == info->width)
387 gst_structure_set (structure,
388 "height", G_TYPE_INT, height - align->padding_bottom, NULL);
389 }
390
391 return TRUE;
392 }
393
394 static gboolean
361395 gst_v4l2_video_dec_negotiate (GstVideoDecoder * decoder)
362396 {
363397 GstV4l2VideoDec *self = GST_V4L2_VIDEO_DEC (decoder);
398 GstV4l2Error error = GST_V4L2_ERROR_INIT;
399 GstVideoInfo info;
400 GstVideoCodecState *output_state;
401 GstCaps *acquired_caps, *fixation_caps, *available_caps, *caps, *filter;
402 GstStructure *st;
403 gboolean active;
404 GstBufferPool *cpool;
405 gboolean ret;
364406
365407 /* We don't allow renegotiation without careful disabling the pool */
366 {
367 GstBufferPool *cpool = gst_v4l2_object_get_buffer_pool (self->v4l2capture);
368 if (cpool) {
369 gboolean is_active = gst_buffer_pool_is_active (cpool);
370 gst_object_unref (cpool);
371 if (is_active)
372 return TRUE;
373 }
374 }
375
376 return GST_VIDEO_DECODER_CLASS (parent_class)->negotiate (decoder);
408 cpool = gst_v4l2_object_get_buffer_pool (self->v4l2capture);
409 if (cpool) {
410 gboolean is_active = gst_buffer_pool_is_active (cpool);
411 gst_object_unref (cpool);
412 if (is_active)
413 return TRUE;
414 }
415
416 /* init capture fps according to output */
417 self->v4l2capture->info.fps_d = self->v4l2output->info.fps_d;
418 self->v4l2capture->info.fps_n = self->v4l2output->info.fps_n;
419
420 /* For decoders G_FMT returns coded size, G_SELECTION returns visible size
421 * in the compose rectangle. gst_v4l2_object_acquire_format() checks both
422 * and returns the visible size as with/height and the coded size as
423 * padding. */
424 if (!gst_v4l2_object_acquire_format (self->v4l2capture, &info))
425 goto not_negotiated;
426
427 /* gst_v4l2_object_acquire_format() does not set fps, copy from sink */
428 info.fps_n = self->v4l2output->info.fps_n;
429 info.fps_d = self->v4l2output->info.fps_d;
430
431 gst_caps_replace (&self->probed_srccaps, NULL);
432 self->probed_srccaps = gst_v4l2_object_probe_caps (self->v4l2capture,
433 gst_v4l2_object_get_raw_caps ());
434 /* Create caps from the acquired format, remove the format field */
435 acquired_caps = gst_video_info_to_caps (&info);
436 GST_DEBUG_OBJECT (self, "Acquired caps: %" GST_PTR_FORMAT, acquired_caps);
437 fixation_caps = gst_caps_copy (acquired_caps);
438 st = gst_caps_get_structure (fixation_caps, 0);
439 gst_structure_remove_fields (st, "format", "colorimetry", "chroma-site",
440 NULL);
441
442 /* Probe currently available pixel formats */
443 available_caps = gst_caps_copy (self->probed_srccaps);
444 GST_DEBUG_OBJECT (self, "Available caps: %" GST_PTR_FORMAT, available_caps);
445
446 /* Replace coded size with visible size, we want to negotiate visible size
447 * with downstream, not coded size. */
448 gst_caps_map_in_place (available_caps, gst_v4l2_video_remove_padding, self);
449
450 filter = gst_caps_intersect_full (available_caps, fixation_caps,
451 GST_CAPS_INTERSECT_FIRST);
452 GST_DEBUG_OBJECT (self, "Filtered caps: %" GST_PTR_FORMAT, filter);
453 gst_caps_unref (fixation_caps);
454 gst_caps_unref (available_caps);
455 caps = gst_pad_peer_query_caps (decoder->srcpad, filter);
456 gst_caps_unref (filter);
457
458 GST_DEBUG_OBJECT (self, "Possible decoded caps: %" GST_PTR_FORMAT, caps);
459 if (gst_caps_is_empty (caps)) {
460 gst_caps_unref (caps);
461 goto not_negotiated;
462 }
463
464 /* Prefer the acquired caps over anything suggested downstream, this ensure
465 * that we preserves the bit depth, as we don't have any fancy fixation
466 * process */
467 if (gst_caps_is_subset (acquired_caps, caps)) {
468 gst_caps_unref (acquired_caps);
469 goto use_acquired_caps;
470 }
471
472 /* Fixate pixel format */
473 caps = gst_caps_fixate (caps);
474
475 GST_DEBUG_OBJECT (self, "Chosen decoded caps: %" GST_PTR_FORMAT, caps);
476
477 /* Try to set negotiated format, on success replace acquired format */
478 if (gst_v4l2_object_set_format (self->v4l2capture, caps, &error))
479 gst_video_info_from_caps (&info, caps);
480 else
481 gst_v4l2_clear_error (&error);
482
483 use_acquired_caps:
484 gst_caps_unref (caps);
485
486 /* catch possible bogus driver that don't enumerate the format it actually
487 * returned from G_FMT */
488 if (!self->v4l2capture->fmtdesc)
489 goto not_negotiated;
490
491 output_state = gst_video_decoder_set_output_state (decoder,
492 info.finfo->format, info.width, info.height, self->input_state);
493
494 /* Copy the rest of the information, there might be more in the future */
495 output_state->info.interlace_mode = info.interlace_mode;
496 output_state->info.colorimetry = info.colorimetry;
497 gst_video_codec_state_unref (output_state);
498
499 ret = GST_VIDEO_DECODER_CLASS (parent_class)->negotiate (decoder);
500 if (!ret)
501 goto not_negotiated;
502
503 /* The pool may be created through gst_video_decoder_negotiate(), so must
504 * be kept after */
505 cpool = gst_v4l2_object_get_buffer_pool (self->v4l2capture);
506 gst_v4l2_buffer_pool_enable_resolution_change (GST_V4L2_BUFFER_POOL (cpool));
507
508 /* Ensure our internal pool is activated */
509 active = gst_buffer_pool_set_active (cpool, TRUE);
510 if (cpool)
511 gst_object_unref (cpool);
512 if (!active)
513 goto activate_failed;
514
515 return TRUE;
516
517 not_negotiated:
518 GST_ERROR_OBJECT (self, "not negotiated");
519 gst_v4l2_error (self, &error);
520 gst_v4l2_object_stop (self->v4l2capture);
521 return FALSE;
522 activate_failed:
523 GST_ELEMENT_ERROR (self, RESOURCE, SETTINGS,
524 (_("Failed to allocate required memory.")),
525 ("Buffer pool activation failed"));
526 gst_v4l2_object_stop (self->v4l2capture);
527 return FALSE;
377528 }
378529
379530 static gboolean
531682 return FALSE;
532683 }
533684
534 static gboolean
535 gst_v4l2_video_remove_padding (GstCapsFeatures * features,
536 GstStructure * structure, gpointer user_data)
537 {
538 GstV4l2VideoDec *self = GST_V4L2_VIDEO_DEC (user_data);
539 GstVideoAlignment *align = &self->v4l2capture->align;
540 GstVideoInfo *info = &self->v4l2capture->info;
541 int width, height;
542
543 if (!gst_structure_get_int (structure, "width", &width))
544 return TRUE;
545
546 if (!gst_structure_get_int (structure, "height", &height))
547 return TRUE;
548
549 if (align->padding_left != 0 || align->padding_top != 0 ||
550 height != info->height + align->padding_bottom)
551 return TRUE;
552
553 if (height == info->height + align->padding_bottom) {
554 /* Some drivers may round up width to the padded with */
555 if (width == info->width + align->padding_right)
556 gst_structure_set (structure,
557 "width", G_TYPE_INT, width - align->padding_right,
558 "height", G_TYPE_INT, height - align->padding_bottom, NULL);
559 /* Some drivers may keep visible width and only round up bytesperline */
560 else if (width == info->width)
561 gst_structure_set (structure,
562 "height", G_TYPE_INT, height - align->padding_bottom, NULL);
563 }
564
565 return TRUE;
566 }
567
568 static GstFlowReturn
569 gst_v4l2_video_dec_setup_capture (GstVideoDecoder * decoder)
570 {
571 GstV4l2VideoDec *self = GST_V4L2_VIDEO_DEC (decoder);
572 GstV4l2Error error = GST_V4L2_ERROR_INIT;
573 GstVideoInfo info;
574 GstVideoCodecState *output_state;
575 GstCaps *acquired_caps, *fixation_caps, *available_caps, *caps, *filter;
576 GstStructure *st;
577 GstBufferPool *cpool;
578 gboolean active;
579
580 if (G_UNLIKELY (!GST_V4L2_IS_ACTIVE (self->v4l2capture))) {
581 /* init capture fps according to output */
582 self->v4l2capture->info.fps_d = self->v4l2output->info.fps_d;
583 self->v4l2capture->info.fps_n = self->v4l2output->info.fps_n;
584
585 /* For decoders G_FMT returns coded size, G_SELECTION returns visible size
586 * in the compose rectangle. gst_v4l2_object_acquire_format() checks both
587 * and returns the visible size as with/height and the coded size as
588 * padding. */
589 if (!gst_v4l2_object_acquire_format (self->v4l2capture, &info))
590 goto not_negotiated;
591
592 /* gst_v4l2_object_acquire_format() does not set fps, copy from sink */
593 info.fps_n = self->v4l2output->info.fps_n;
594 info.fps_d = self->v4l2output->info.fps_d;
595
596 gst_caps_replace (&self->probed_srccaps, NULL);
597 self->probed_srccaps = gst_v4l2_object_probe_caps (self->v4l2capture,
598 gst_v4l2_object_get_raw_caps ());
599 /* Create caps from the acquired format, remove the format field */
600 acquired_caps = gst_video_info_to_caps (&info);
601 GST_DEBUG_OBJECT (self, "Acquired caps: %" GST_PTR_FORMAT, acquired_caps);
602 fixation_caps = gst_caps_copy (acquired_caps);
603 st = gst_caps_get_structure (fixation_caps, 0);
604 gst_structure_remove_fields (st, "format", "colorimetry", "chroma-site",
605 NULL);
606
607 /* Probe currently available pixel formats */
608 available_caps = gst_caps_copy (self->probed_srccaps);
609 GST_DEBUG_OBJECT (self, "Available caps: %" GST_PTR_FORMAT, available_caps);
610
611 /* Replace coded size with visible size, we want to negotiate visible size
612 * with downstream, not coded size. */
613 gst_caps_map_in_place (available_caps, gst_v4l2_video_remove_padding, self);
614
615 filter = gst_caps_intersect_full (available_caps, fixation_caps,
616 GST_CAPS_INTERSECT_FIRST);
617 GST_DEBUG_OBJECT (self, "Filtered caps: %" GST_PTR_FORMAT, filter);
618 gst_caps_unref (fixation_caps);
619 gst_caps_unref (available_caps);
620 caps = gst_pad_peer_query_caps (decoder->srcpad, filter);
621 gst_caps_unref (filter);
622
623 GST_DEBUG_OBJECT (self, "Possible decoded caps: %" GST_PTR_FORMAT, caps);
624 if (gst_caps_is_empty (caps)) {
625 gst_caps_unref (caps);
626 goto not_negotiated;
627 }
628
629 /* Prefer the acquired caps over anything suggested downstream, this ensure
630 * that we preserves the bit depth, as we don't have any fancy fixation
631 * process */
632 if (gst_caps_is_subset (acquired_caps, caps)) {
633 gst_caps_unref (acquired_caps);
634 goto use_acquired_caps;
635 }
636
637 /* Fixate pixel format */
638 caps = gst_caps_fixate (caps);
639
640 GST_DEBUG_OBJECT (self, "Chosen decoded caps: %" GST_PTR_FORMAT, caps);
641
642 /* Try to set negotiated format, on success replace acquired format */
643 if (gst_v4l2_object_set_format (self->v4l2capture, caps, &error))
644 gst_video_info_from_caps (&info, caps);
645 else
646 gst_v4l2_clear_error (&error);
647
648 use_acquired_caps:
649 gst_caps_unref (caps);
650
651 /* catch possible bogus driver that don't enumerate the format it actually
652 * returned from G_FMT */
653 if (!self->v4l2capture->fmtdesc)
654 goto not_negotiated;
655
656 output_state = gst_video_decoder_set_output_state (decoder,
657 info.finfo->format, info.width, info.height, self->input_state);
658
659 /* Copy the rest of the information, there might be more in the future */
660 output_state->info.interlace_mode = info.interlace_mode;
661 output_state->info.colorimetry = info.colorimetry;
662 gst_video_codec_state_unref (output_state);
663
664 if (!gst_video_decoder_negotiate (decoder)) {
665 if (GST_PAD_IS_FLUSHING (decoder->srcpad))
666 goto flushing;
667 else
668 goto not_negotiated;
669 }
670
671 /* The pool may be created through gst_video_decoder_negotiate(), so must
672 * be kept after */
673 cpool = gst_v4l2_object_get_buffer_pool (self->v4l2capture);
674 gst_v4l2_buffer_pool_enable_resolution_change (GST_V4L2_BUFFER_POOL
675 (cpool));
676
677 /* Ensure our internal pool is activated */
678 active = gst_buffer_pool_set_active (cpool, TRUE);
679 if (cpool)
680 gst_object_unref (cpool);
681 if (!active)
682 goto activate_failed;
683 }
684
685 return GST_FLOW_OK;
686
687 not_negotiated:
688 GST_ERROR_OBJECT (self, "not negotiated");
689 gst_v4l2_error (self, &error);
690 gst_v4l2_object_stop (self->v4l2capture);
691 return GST_FLOW_NOT_NEGOTIATED;
692 activate_failed:
693 GST_ELEMENT_ERROR (self, RESOURCE, SETTINGS,
694 (_("Failed to allocate required memory.")),
695 ("Buffer pool activation failed"));
696 gst_v4l2_object_stop (self->v4l2capture);
697 return GST_FLOW_ERROR;
698 flushing:
699 gst_v4l2_object_stop (self->v4l2capture);
700 return GST_FLOW_FLUSHING;
701 }
702
703685 /* Only used initially to wait for a SRC_CH event
704686 * called with decoder stream lock */
705687 static GstFlowReturn
750732 }
751733
752734 GST_DEBUG_OBJECT (decoder, "Setup the capture queue");
753 ret = gst_v4l2_video_dec_setup_capture (decoder);
754 /* FIXME not super nice ? */
755 if (ret == GST_FLOW_FLUSHING || GST_PAD_IS_FLUSHING (decoder->sinkpad)
756 || GST_PAD_IS_FLUSHING (decoder->srcpad)) {
757 ret = GST_FLOW_FLUSHING;
758 GST_VIDEO_DECODER_STREAM_UNLOCK (decoder);
759 goto beach;
760 }
761 if (ret != GST_FLOW_OK) {
762 GST_ERROR_OBJECT (decoder, "Failed to setup capture queue");
763 GST_VIDEO_DECODER_STREAM_UNLOCK (decoder);
764 goto beach;
765 }
766
767 /* just a safety, as introducing mistakes in setup_capture seems rather
735 if (G_UNLIKELY (!GST_V4L2_IS_ACTIVE (self->v4l2capture))) {
736 if (!gst_video_decoder_negotiate (decoder)) {
737 /* FIXME not super nice ? */
738 if (GST_PAD_IS_FLUSHING (decoder->sinkpad)
739 || GST_PAD_IS_FLUSHING (decoder->srcpad)) {
740 ret = GST_FLOW_FLUSHING;
741 } else {
742 ret = GST_FLOW_NOT_NEGOTIATED;
743 GST_ERROR_OBJECT (decoder, "Failed to setup capture queue");
744 }
745 GST_VIDEO_DECODER_STREAM_UNLOCK (decoder);
746 goto beach;
747 }
748 }
749
750 /* just a safety, as introducing mistakes in negotiation seems rather
768751 * easy.*/
769752 g_return_if_fail (GST_V4L2_IS_ACTIVE (self->v4l2capture));
770753 }
990973 gst_buffer_unref (codec_data);
991974
992975 /* Only wait for source change if the formats supports it */
993 if (self->v4l2output->fmtdesc->flags & V4L2_FMT_FLAG_DYN_RESOLUTION) {
976 if (!GST_V4L2_IS_ACTIVE (self->v4l2capture) &&
977 self->v4l2output->fmtdesc->flags & V4L2_FMT_FLAG_DYN_RESOLUTION) {
994978 gst_v4l2_object_unlock_stop (self->v4l2capture);
995979 self->wait_for_source_change = TRUE;
996980 }
13831367 gint mpegversion = 0;
13841368 gst_structure_get_int (s, "mpegversion", &mpegversion);
13851369
1386 switch (mpegversion) {
1387 /* MPEG 2 decoders supports MPEG 1 format */
1388 case 1:
1389 case 2:
1390 SET_META ("MPEG2");
1391 cdata->codec = gst_v4l2_mpeg2_get_codec ();
1392 break;
1393 case 4:
1394 SET_META ("MPEG4");
1395 cdata->codec = gst_v4l2_mpeg4_get_codec ();
1396 break;
1397 default:
1398 g_warning ("Unsupported MPEG Video version %i", mpegversion);
1399 break;
1370 if (mpegversion == 4) {
1371 SET_META ("MPEG4");
1372 cdata->codec = gst_v4l2_mpeg4_get_codec ();
1373 } else {
1374 /* MPEG 2 decoders supports MPEG 1 format */
1375 SET_META ("MPEG2");
1376 cdata->codec = gst_v4l2_mpeg2_get_codec ();
14001377 }
14011378 } else if (gst_structure_has_name (s, "video/x-h263")) {
14021379 SET_META ("H263");
516516 return failed;
517517 }
518518
519 static GstCaps *
520 gst_v4l2_video_enc_sink_getcaps (GstVideoEncoder * encoder, GstCaps * filter)
521 {
522 GstV4l2VideoEnc *self = GST_V4L2_VIDEO_ENC (encoder);
523 GstCaps *probed_caps = NULL;
524 GstCaps *caps;
525
526 if (self->probed_sinkcaps)
527 probed_caps = gst_caps_ref (self->probed_sinkcaps);
528
529 caps = gst_video_encoder_proxy_getcaps (encoder, probed_caps, filter);
530
531 if (probed_caps)
532 gst_caps_unref (probed_caps);
533
534 GST_DEBUG_OBJECT (self, "Returning sink caps %" GST_PTR_FORMAT, caps);
535
536 return caps;
537 }
538
519539 static gboolean
520540 gst_v4l2_video_enc_negotiate (GstVideoEncoder * encoder)
521541 {
10051025 }
10061026
10071027 static gboolean
1008 gst_v4l2_video_enc_sink_query (GstVideoEncoder * encoder, GstQuery * query)
1009 {
1010 gboolean ret = TRUE;
1011 GstV4l2VideoEnc *self = GST_V4L2_VIDEO_ENC (encoder);
1012
1013 switch (GST_QUERY_TYPE (query)) {
1014 case GST_QUERY_CAPS:{
1015 GstCaps *filter, *result = NULL;
1016 GstPad *pad = GST_VIDEO_ENCODER_SINK_PAD (encoder);
1017
1018 gst_query_parse_caps (query, &filter);
1019
1020 if (self->probed_sinkcaps)
1021 result = gst_caps_ref (self->probed_sinkcaps);
1022 else
1023 result = gst_pad_get_pad_template_caps (pad);
1024
1025 if (filter) {
1026 GstCaps *tmp = result;
1027 result =
1028 gst_caps_intersect_full (filter, tmp, GST_CAPS_INTERSECT_FIRST);
1029 gst_caps_unref (tmp);
1030 }
1031
1032 GST_DEBUG_OBJECT (self, "Returning sink caps %" GST_PTR_FORMAT, result);
1033
1034 gst_query_set_caps_result (query, result);
1035 gst_caps_unref (result);
1036 break;
1037 }
1038
1039 default:
1040 ret = GST_VIDEO_ENCODER_CLASS (parent_class)->sink_query (encoder, query);
1041 break;
1042 }
1043
1044 return ret;
1045 }
1046
1047 static gboolean
10481028 gst_v4l2_video_enc_sink_event (GstVideoEncoder * encoder, GstEvent * event)
10491029 {
10501030 GstV4l2VideoEnc *self = GST_V4L2_VIDEO_ENC (encoder);
11691149 video_encoder_class->flush = GST_DEBUG_FUNCPTR (gst_v4l2_video_enc_flush);
11701150 video_encoder_class->set_format =
11711151 GST_DEBUG_FUNCPTR (gst_v4l2_video_enc_set_format);
1152 video_encoder_class->getcaps =
1153 GST_DEBUG_FUNCPTR (gst_v4l2_video_enc_sink_getcaps);
11721154 video_encoder_class->negotiate =
11731155 GST_DEBUG_FUNCPTR (gst_v4l2_video_enc_negotiate);
11741156 video_encoder_class->decide_allocation =
11751157 GST_DEBUG_FUNCPTR (gst_v4l2_video_enc_decide_allocation);
11761158 video_encoder_class->propose_allocation =
11771159 GST_DEBUG_FUNCPTR (gst_v4l2_video_enc_propose_allocation);
1178 video_encoder_class->sink_query =
1179 GST_DEBUG_FUNCPTR (gst_v4l2_video_enc_sink_query);
11801160 video_encoder_class->src_query =
11811161 GST_DEBUG_FUNCPTR (gst_v4l2_video_enc_src_query);
11821162 video_encoder_class->sink_event =