I have a MPEG-TS file which contains two video/audio stream-pairs:
$ gst-discoverer-1.0 Recorder_Aug01_12-30-39.ts
Analyzing Recorder_Aug01_12-30-39.ts
Done discovering Recorder_Aug01_12-30-39.ts
Topology:
container: MPEG-2 Transport Stream
audio: MPEG-2 AAC
audio: MPEG-4 AAC
video: H.264 (High Profile)
audio: MPEG-2 AAC
audio: MPEG-4 AAC
video: H.264 (High Profile)
Properties:
Duration: 0:01:49.662738259
Seekable: yes
Tags:
audio codec: MPEG-2 AAC
video codec: H.264
Now I would like to extract the first video and audio streams and the second video/audio into two separate MP4 containers.
Showing both video streams in parallel works with a simple pipeline:
$ gst-launch-1.0 filesrc location=Recorder_Aug01_12-30-39.ts ! tsdemux name=ts \
ts.video_0_0102 ! queue ! h264parse ! avdec_h264 ! videoconvert ! videoscale ! autovideosink \
ts.video_0_0100 ! queue ! h264parse ! avdec_h264 ! videoconvert ! videoscale ! autovideosink
When I introduce the mp4mux
together with a filesink
element on one stream it still work, the first video stream is shown and the second video is saved to a MP4 container file:
$ gst-launch-1.0 filesrc location=Recorder_Aug01_12-30-39.ts ! tsdemux name=ts \
ts.video_0_0102 ! queue ! h264parse ! avdec_h264 ! videoconvert ! videoscale ! ximagesink \
ts.video_0_0100 ! queue ! h264parse ! mp4mux ! filesink location=2.mp4
Now for my problem: Once I try to have both streams saved through filesinks it fails:
$ gst-launch-1.0 filesrc location=Recorder_Aug01_12-30-39.ts ! tsdemux name=ts \
ts.video_0_0102 ! queue ! h264parse ! mp4mux ! filesink location=1.mp4 \
ts.video_0_0100 ! queue ! h264parse ! mp4mux ! filesink location=2.mp4
Setting pipeline to PAUSED ...
Pipeline is PREROLLING ...
Pipeline is PREROLLED ...
Setting pipeline to PLAYING ...
New clock: GstSystemClock
ERROR: from element /GstPipeline:pipeline0/GstMP4Mux:mp4mux0: Could not multiplex stream.
Additional debug info:
gstqtmux.c(3486): gst_qt_mux_add_buffer (): /GstPipeline:pipeline0/GstMP4Mux:mp4mux0:
Buffer has no PTS.
Execution ended after 0:00:00.001992389
Setting pipeline to PAUSED ...
Setting pipeline to READY ...
Setting pipeline to NULL ...
Freeing pipeline ...
I would like to achieve this using gstreamer because it should later be part of a larger processing workflow that needs a lot of introspection, so using ffmpeg
or some external binary is no an option.
GStreamer Buffer has no PTS Failure Mode
This may not completely solve the problem using GStreamer, but this is a workaround that I'm now using. It involves isolating out the failing component which is the 'mp4mux' element in the gstreamer pipeline.
I'm finding that even a sample video encoding in Gstreamer is currently failing e.g. with the Buffer has no PTS failure mode:
Using Gstreamer for h264 Encoding only.
Removing the mp4mux element allows us to successfully create .h264 files. Particularly handy if you're using a Raspberry Pi omxh264 encoder element.
Solving the problem of Mixing Audio and Video
Now to convert that into an MP4 (the initial goal) we can use the nice lightweight Gpac MP4box.
Then you can add in your audio
Summary