FFmpeg coverage


Directory: ../../../ffmpeg/
File: src/fftools/ffmpeg_mux.c
Date: 2023-06-04 16:45:34
Exec Total Coverage
Lines: 399 530 75.3%
Functions: 24 25 96.0%
Branches: 218 310 70.3%

Line Branch Exec Source
1 /*
2 * This file is part of FFmpeg.
3 *
4 * FFmpeg is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2.1 of the License, or (at your option) any later version.
8 *
9 * FFmpeg is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
13 *
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with FFmpeg; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
17 */
18
19 #include <stdatomic.h>
20 #include <stdio.h>
21 #include <string.h>
22
23 #include "ffmpeg.h"
24 #include "ffmpeg_mux.h"
25 #include "objpool.h"
26 #include "sync_queue.h"
27 #include "thread_queue.h"
28
29 #include "libavutil/fifo.h"
30 #include "libavutil/intreadwrite.h"
31 #include "libavutil/log.h"
32 #include "libavutil/mem.h"
33 #include "libavutil/timestamp.h"
34 #include "libavutil/thread.h"
35
36 #include "libavcodec/packet.h"
37
38 #include "libavformat/avformat.h"
39 #include "libavformat/avio.h"
40
41 int want_sdp = 1;
42
43 988325 static Muxer *mux_from_of(OutputFile *of)
44 {
45 988325 return (Muxer*)of;
46 }
47
48 490437 static int64_t filesize(AVIOContext *pb)
49 {
50 490437 int64_t ret = -1;
51
52
2/2
✓ Branch 0 taken 481389 times.
✓ Branch 1 taken 9048 times.
490437 if (pb) {
53 481389 ret = avio_size(pb);
54
2/2
✓ Branch 0 taken 101515 times.
✓ Branch 1 taken 379874 times.
481389 if (ret <= 0) // FIXME improve avio_size() so it works with non seekable output too
55 101515 ret = avio_tell(pb);
56 }
57
58 490437 return ret;
59 }
60
61 483871 static int write_packet(Muxer *mux, OutputStream *ost, AVPacket *pkt)
62 {
63 483871 MuxStream *ms = ms_from_ost(ost);
64 483871 AVFormatContext *s = mux->fc;
65 int64_t fs;
66 uint64_t frame_num;
67 int ret;
68
69 483871 fs = filesize(s->pb);
70 483871 atomic_store(&mux->last_filesize, fs);
71
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 483871 times.
483871 if (fs >= mux->limit_filesize) {
72 ret = AVERROR_EOF;
73 goto fail;
74 }
75
76
3/4
✓ Branch 0 taken 117551 times.
✓ Branch 1 taken 366320 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 117551 times.
483871 if (ost->type == AVMEDIA_TYPE_VIDEO && ost->vsync_method == VSYNC_DROP)
77 pkt->pts = pkt->dts = AV_NOPTS_VALUE;
78
79 483871 av_packet_rescale_ts(pkt, pkt->time_base, ost->st->time_base);
80 483871 pkt->time_base = ost->st->time_base;
81
82
2/2
✓ Branch 0 taken 230716 times.
✓ Branch 1 taken 253155 times.
483871 if (!(s->oformat->flags & AVFMT_NOTIMESTAMPS)) {
83
1/2
✓ Branch 0 taken 230716 times.
✗ Branch 1 not taken.
230716 if (pkt->dts != AV_NOPTS_VALUE &&
84
2/2
✓ Branch 0 taken 228551 times.
✓ Branch 1 taken 2165 times.
230716 pkt->pts != AV_NOPTS_VALUE &&
85
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 228551 times.
228551 pkt->dts > pkt->pts) {
86 av_log(s, AV_LOG_WARNING, "Invalid DTS: %"PRId64" PTS: %"PRId64" in output stream %d:%d, replacing by guess\n",
87 pkt->dts, pkt->pts,
88 ost->file_index, ost->st->index);
89 pkt->pts =
90 pkt->dts = pkt->pts + pkt->dts + ms->last_mux_dts + 1
91 - FFMIN3(pkt->pts, pkt->dts, ms->last_mux_dts + 1)
92 - FFMAX3(pkt->pts, pkt->dts, ms->last_mux_dts + 1);
93 }
94
6/6
✓ Branch 0 taken 86728 times.
✓ Branch 1 taken 143988 times.
✓ Branch 2 taken 1215 times.
✓ Branch 3 taken 85513 times.
✓ Branch 4 taken 1200 times.
✓ Branch 5 taken 15 times.
230716 if ((ost->type == AVMEDIA_TYPE_AUDIO || ost->type == AVMEDIA_TYPE_VIDEO || ost->type == AVMEDIA_TYPE_SUBTITLE) &&
95
1/2
✓ Branch 0 taken 230701 times.
✗ Branch 1 not taken.
230701 pkt->dts != AV_NOPTS_VALUE &&
96
2/2
✓ Branch 0 taken 225315 times.
✓ Branch 1 taken 5386 times.
230701 ms->last_mux_dts != AV_NOPTS_VALUE) {
97 225315 int64_t max = ms->last_mux_dts + !(s->oformat->flags & AVFMT_TS_NONSTRICT);
98
2/2
✓ Branch 0 taken 30 times.
✓ Branch 1 taken 225285 times.
225315 if (pkt->dts < max) {
99
3/4
✓ Branch 0 taken 19 times.
✓ Branch 1 taken 11 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 19 times.
30 int loglevel = max - pkt->dts > 2 || ost->type == AVMEDIA_TYPE_VIDEO ? AV_LOG_WARNING : AV_LOG_DEBUG;
100
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 30 times.
30 if (exit_on_error)
101 loglevel = AV_LOG_ERROR;
102 30 av_log(s, loglevel, "Non-monotonous DTS in output stream "
103 "%d:%d; previous: %"PRId64", current: %"PRId64"; ",
104 30 ost->file_index, ost->st->index, ms->last_mux_dts, pkt->dts);
105
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 30 times.
30 if (exit_on_error) {
106 ret = AVERROR(EINVAL);
107 goto fail;
108 }
109
110 30 av_log(s, loglevel, "changing to %"PRId64". This may result "
111 "in incorrect timestamps in the output file.\n",
112 max);
113
1/2
✓ Branch 0 taken 30 times.
✗ Branch 1 not taken.
30 if (pkt->pts >= pkt->dts)
114 30 pkt->pts = FFMAX(pkt->pts, max);
115 30 pkt->dts = max;
116 }
117 }
118 }
119 483871 ms->last_mux_dts = pkt->dts;
120
121 483871 ms->data_size_mux += pkt->size;
122 483871 frame_num = atomic_fetch_add(&ost->packets_written, 1);
123
124 483871 pkt->stream_index = ost->index;
125
126
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 483871 times.
483871 if (debug_ts) {
127 av_log(ost, AV_LOG_INFO, "muxer <- type:%s "
128 "pkt_pts:%s pkt_pts_time:%s pkt_dts:%s pkt_dts_time:%s duration:%s duration_time:%s size:%d\n",
129 av_get_media_type_string(ost->type),
130 av_ts2str(pkt->pts), av_ts2timestr(pkt->pts, &ost->st->time_base),
131 av_ts2str(pkt->dts), av_ts2timestr(pkt->dts, &ost->st->time_base),
132 av_ts2str(pkt->duration), av_ts2timestr(pkt->duration, &ost->st->time_base),
133 pkt->size
134 );
135 }
136
137
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 483871 times.
483871 if (ms->stats.io)
138 enc_stats_write(ost, &ms->stats, NULL, pkt, frame_num);
139
140 483871 ret = av_interleaved_write_frame(s, pkt);
141
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 483871 times.
483871 if (ret < 0) {
142 av_log(ost, AV_LOG_ERROR,
143 "Error submitting a packet to the muxer: %s\n",
144 av_err2str(ret));
145 goto fail;
146 }
147
148 483871 return 0;
149 fail:
150 av_packet_unref(pkt);
151 return ret;
152 }
153
154 490757 static int sync_queue_process(Muxer *mux, OutputStream *ost, AVPacket *pkt, int *stream_eof)
155 {
156 490757 OutputFile *of = &mux->of;
157
158
2/2
✓ Branch 0 taken 838 times.
✓ Branch 1 taken 489919 times.
490757 if (ost->sq_idx_mux >= 0) {
159 838 int ret = sq_send(mux->sq_mux, ost->sq_idx_mux, SQPKT(pkt));
160
2/2
✓ Branch 0 taken 802 times.
✓ Branch 1 taken 36 times.
838 if (ret < 0) {
161
1/2
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
36 if (ret == AVERROR_EOF)
162 36 *stream_eof = 1;
163
164 36 return ret;
165 }
166
167 740 while (1) {
168 1542 ret = sq_receive(mux->sq_mux, -1, SQPKT(mux->sq_pkt));
169
2/2
✓ Branch 0 taken 802 times.
✓ Branch 1 taken 740 times.
1542 if (ret < 0)
170
3/4
✓ Branch 0 taken 791 times.
✓ Branch 1 taken 11 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 791 times.
802 return (ret == AVERROR_EOF || ret == AVERROR(EAGAIN)) ? 0 : ret;
171
172 740 ret = write_packet(mux, of->streams[ret],
173 mux->sq_pkt);
174
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 740 times.
740 if (ret < 0)
175 return ret;
176 }
177
2/2
✓ Branch 0 taken 483131 times.
✓ Branch 1 taken 6788 times.
489919 } else if (pkt)
178 483131 return write_packet(mux, ost, pkt);
179
180 6788 return 0;
181 }
182
183 6566 static void thread_set_name(OutputFile *of)
184 {
185 char name[16];
186 6566 snprintf(name, sizeof(name), "mux%d:%s", of->index, of->format->name);
187 6566 ff_thread_setname(name);
188 6566 }
189
190 6566 static void *muxer_thread(void *arg)
191 {
192 6566 Muxer *mux = arg;
193 6566 OutputFile *of = &mux->of;
194 6566 AVPacket *pkt = NULL;
195 6566 int ret = 0;
196
197 6566 pkt = av_packet_alloc();
198
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6566 times.
6566 if (!pkt) {
199 ret = AVERROR(ENOMEM);
200 goto finish;
201 }
202
203 6566 thread_set_name(of);
204
205 490757 while (1) {
206 OutputStream *ost;
207 497323 int stream_idx, stream_eof = 0;
208
209 497323 ret = tq_receive(mux->tq, &stream_idx, pkt);
210
2/2
✓ Branch 0 taken 6566 times.
✓ Branch 1 taken 490757 times.
497323 if (stream_idx < 0) {
211 6566 av_log(mux, AV_LOG_VERBOSE, "All streams finished\n");
212 6566 ret = 0;
213 6566 break;
214 }
215
216 490757 ost = of->streams[stream_idx];
217
2/2
✓ Branch 0 taken 483955 times.
✓ Branch 1 taken 6802 times.
490757 ret = sync_queue_process(mux, ost, ret < 0 ? NULL : pkt, &stream_eof);
218 490757 av_packet_unref(pkt);
219
2/2
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 490721 times.
490757 if (ret == AVERROR_EOF) {
220
1/2
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
36 if (stream_eof) {
221 36 tq_receive_finish(mux->tq, stream_idx);
222 } else {
223 av_log(mux, AV_LOG_VERBOSE, "Muxer returned EOF\n");
224 ret = 0;
225 break;
226 }
227
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 490721 times.
490721 } else if (ret < 0) {
228 av_log(mux, AV_LOG_ERROR, "Error muxing a packet\n");
229 break;
230 }
231 }
232
233 6566 finish:
234 6566 av_packet_free(&pkt);
235
236
2/2
✓ Branch 0 taken 6822 times.
✓ Branch 1 taken 6566 times.
13388 for (unsigned int i = 0; i < mux->fc->nb_streams; i++)
237 6822 tq_receive_finish(mux->tq, i);
238
239 6566 av_log(mux, AV_LOG_VERBOSE, "Terminating muxer thread\n");
240
241 6566 return (void*)(intptr_t)ret;
242 }
243
244 495398 static int thread_submit_packet(Muxer *mux, OutputStream *ost, AVPacket *pkt)
245 {
246 495398 int ret = 0;
247
248
4/4
✓ Branch 0 taken 483977 times.
✓ Branch 1 taken 11421 times.
✓ Branch 2 taken 4 times.
✓ Branch 3 taken 483973 times.
495398 if (!pkt || ost->finished & MUXER_FINISHED)
249 11425 goto finish;
250
251 483973 ret = tq_send(mux->tq, ost->index, pkt);
252
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 483955 times.
483973 if (ret < 0)
253 18 goto finish;
254
255 483955 return 0;
256
257 11443 finish:
258
2/2
✓ Branch 0 taken 22 times.
✓ Branch 1 taken 11421 times.
11443 if (pkt)
259 22 av_packet_unref(pkt);
260
261 11443 ost->finished |= MUXER_FINISHED;
262 11443 tq_send_finish(mux->tq, ost->index);
263
2/2
✓ Branch 0 taken 11425 times.
✓ Branch 1 taken 18 times.
11443 return ret == AVERROR_EOF ? 0 : ret;
264 }
265
266 340 static int queue_packet(OutputStream *ost, AVPacket *pkt)
267 {
268 340 MuxStream *ms = ms_from_ost(ost);
269 340 AVPacket *tmp_pkt = NULL;
270 int ret;
271
272
2/2
✓ Branch 1 taken 18 times.
✓ Branch 2 taken 322 times.
340 if (!av_fifo_can_write(ms->muxing_queue)) {
273 18 size_t cur_size = av_fifo_can_read(ms->muxing_queue);
274
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 size_t pkt_size = pkt ? pkt->size : 0;
275 18 unsigned int are_we_over_size =
276 18 (ms->muxing_queue_data_size + pkt_size) > ms->muxing_queue_data_threshold;
277
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
18 size_t limit = are_we_over_size ? ms->max_muxing_queue_size : SIZE_MAX;
278 18 size_t new_size = FFMIN(2 * cur_size, limit);
279
280
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
18 if (new_size <= cur_size) {
281 av_log(ost, AV_LOG_ERROR,
282 "Too many packets buffered for output stream %d:%d.\n",
283 ost->file_index, ost->st->index);
284 return AVERROR(ENOSPC);
285 }
286 18 ret = av_fifo_grow2(ms->muxing_queue, new_size - cur_size);
287
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
18 if (ret < 0)
288 return ret;
289 }
290
291
2/2
✓ Branch 0 taken 337 times.
✓ Branch 1 taken 3 times.
340 if (pkt) {
292 337 ret = av_packet_make_refcounted(pkt);
293
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 337 times.
337 if (ret < 0)
294 return ret;
295
296 337 tmp_pkt = av_packet_alloc();
297
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 337 times.
337 if (!tmp_pkt)
298 return AVERROR(ENOMEM);
299
300 337 av_packet_move_ref(tmp_pkt, pkt);
301 337 ms->muxing_queue_data_size += tmp_pkt->size;
302 }
303 340 av_fifo_write(ms->muxing_queue, &tmp_pkt, 1);
304
305 340 return 0;
306 }
307
308 495398 static int submit_packet(Muxer *mux, AVPacket *pkt, OutputStream *ost)
309 {
310 int ret;
311
312
2/2
✓ Branch 0 taken 495058 times.
✓ Branch 1 taken 340 times.
495398 if (mux->tq) {
313 495058 return thread_submit_packet(mux, ost, pkt);
314 } else {
315 /* the muxer is not initialized yet, buffer the packet */
316 340 ret = queue_packet(ost, pkt);
317
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 340 times.
340 if (ret < 0) {
318 if (pkt)
319 av_packet_unref(pkt);
320 return ret;
321 }
322 }
323
324 340 return 0;
325 }
326
327 495409 void of_output_packet(OutputFile *of, AVPacket *pkt, OutputStream *ost, int eof)
328 {
329 495409 Muxer *mux = mux_from_of(of);
330 495409 MuxStream *ms = ms_from_ost(ost);
331 const char *err_msg;
332 495409 int ret = 0;
333
334
4/4
✓ Branch 0 taken 483988 times.
✓ Branch 1 taken 11421 times.
✓ Branch 2 taken 483987 times.
✓ Branch 3 taken 1 times.
495409 if (!eof && pkt->dts != AV_NOPTS_VALUE)
335 483987 ost->last_mux_dts = av_rescale_q(pkt->dts, pkt->time_base, AV_TIME_BASE_Q);
336
337 /* apply the output bitstream filters */
338
2/2
✓ Branch 0 taken 7554 times.
✓ Branch 1 taken 487855 times.
495409 if (ms->bsf_ctx) {
339 7554 int bsf_eof = 0;
340
341
2/2
✓ Branch 0 taken 7362 times.
✓ Branch 1 taken 192 times.
7554 ret = av_bsf_send_packet(ms->bsf_ctx, eof ? NULL : pkt);
342
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 7554 times.
7554 if (ret < 0) {
343 err_msg = "submitting a packet for bitstream filtering";
344 goto fail;
345 }
346
347
2/2
✓ Branch 0 taken 14905 times.
✓ Branch 1 taken 192 times.
15097 while (!bsf_eof) {
348 14905 ret = av_bsf_receive_packet(ms->bsf_ctx, pkt);
349
2/2
✓ Branch 0 taken 7360 times.
✓ Branch 1 taken 7545 times.
14905 if (ret == AVERROR(EAGAIN))
350 7360 return;
351
2/2
✓ Branch 0 taken 192 times.
✓ Branch 1 taken 7353 times.
7545 else if (ret == AVERROR_EOF)
352 192 bsf_eof = 1;
353
2/2
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 7351 times.
7353 else if (ret < 0) {
354 2 err_msg = "applying bitstream filters to a packet";
355 2 goto fail;
356 }
357
358
2/2
✓ Branch 0 taken 7351 times.
✓ Branch 1 taken 192 times.
7543 ret = submit_packet(mux, bsf_eof ? NULL : pkt, ost);
359
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 7543 times.
7543 if (ret < 0)
360 goto mux_fail;
361 }
362 } else {
363
2/2
✓ Branch 0 taken 476626 times.
✓ Branch 1 taken 11229 times.
487855 ret = submit_packet(mux, eof ? NULL : pkt, ost);
364
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 487855 times.
487855 if (ret < 0)
365 goto mux_fail;
366 }
367
368 488047 return;
369
370 mux_fail:
371 err_msg = "submitting a packet to the muxer";
372
373 2 fail:
374 2 av_log(ost, AV_LOG_ERROR, "Error %s\n", err_msg);
375
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 2 times.
2 if (exit_on_error)
376 exit_program(1);
377
378 }
379
380 68053 void of_streamcopy(OutputStream *ost, const AVPacket *pkt, int64_t dts)
381 {
382 68053 OutputFile *of = output_files[ost->file_index];
383 68053 MuxStream *ms = ms_from_ost(ost);
384
2/2
✓ Branch 0 taken 1077 times.
✓ Branch 1 taken 66976 times.
68053 int64_t start_time = (of->start_time == AV_NOPTS_VALUE) ? 0 : of->start_time;
385 68053 int64_t ost_tb_start_time = av_rescale_q(start_time, AV_TIME_BASE_Q, ost->mux_timebase);
386 68053 AVPacket *opkt = ost->pkt;
387
388 68053 av_packet_unref(opkt);
389
390
2/2
✓ Branch 0 taken 2727 times.
✓ Branch 1 taken 65326 times.
68053 if (of->recording_time != INT64_MAX &&
391
2/2
✓ Branch 0 taken 1536 times.
✓ Branch 1 taken 1191 times.
2727 dts >= of->recording_time + start_time)
392 1536 pkt = NULL;
393
394 // EOF: flush output bitstream filters.
395
2/2
✓ Branch 0 taken 2031 times.
✓ Branch 1 taken 66022 times.
68053 if (!pkt) {
396 2031 of_output_packet(of, opkt, ost, 1);
397 2278 return;
398 }
399
400
4/4
✓ Branch 0 taken 722 times.
✓ Branch 1 taken 65300 times.
✓ Branch 2 taken 64 times.
✓ Branch 3 taken 658 times.
66022 if (!ms->streamcopy_started && !(pkt->flags & AV_PKT_FLAG_KEY) &&
401
1/2
✓ Branch 0 taken 64 times.
✗ Branch 1 not taken.
64 !ms->copy_initial_nonkeyframes)
402 64 return;
403
404
2/2
✓ Branch 0 taken 658 times.
✓ Branch 1 taken 65300 times.
65958 if (!ms->streamcopy_started) {
405
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 658 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
658 if (!ms->copy_prior_start &&
406 (pkt->pts == AV_NOPTS_VALUE ?
407 dts < ms->ts_copy_start :
408 pkt->pts < av_rescale_q(ms->ts_copy_start, AV_TIME_BASE_Q, pkt->time_base)))
409 return;
410
411
4/4
✓ Branch 0 taken 187 times.
✓ Branch 1 taken 471 times.
✓ Branch 2 taken 183 times.
✓ Branch 3 taken 4 times.
658 if (of->start_time != AV_NOPTS_VALUE && dts < of->start_time)
412 183 return;
413 }
414
415
1/2
✗ Branch 1 not taken.
✓ Branch 2 taken 65775 times.
65775 if (av_packet_ref(opkt, pkt) < 0)
416 exit_program(1);
417
418 65775 opkt->time_base = ost->mux_timebase;
419
420
2/2
✓ Branch 0 taken 58821 times.
✓ Branch 1 taken 6954 times.
65775 if (pkt->pts != AV_NOPTS_VALUE)
421 58821 opkt->pts = av_rescale_q(pkt->pts, pkt->time_base, opkt->time_base) - ost_tb_start_time;
422
423
2/2
✓ Branch 0 taken 6717 times.
✓ Branch 1 taken 59058 times.
65775 if (pkt->dts == AV_NOPTS_VALUE) {
424 6717 opkt->dts = av_rescale_q(dts, AV_TIME_BASE_Q, opkt->time_base);
425
2/2
✓ Branch 0 taken 50840 times.
✓ Branch 1 taken 8218 times.
59058 } else if (ost->st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO) {
426 50840 int duration = av_get_audio_frame_duration2(ost->par_in, pkt->size);
427
2/2
✓ Branch 0 taken 15023 times.
✓ Branch 1 taken 35817 times.
50840 if(!duration)
428 15023 duration = ost->par_in->frame_size;
429 101680 opkt->dts = av_rescale_delta(pkt->time_base, pkt->dts,
430 50840 (AVRational){1, ost->par_in->sample_rate}, duration,
431 &ms->ts_rescale_delta_last, opkt->time_base);
432 /* dts will be set immediately afterwards to what pts is now */
433 50840 opkt->pts = opkt->dts - ost_tb_start_time;
434 } else
435 8218 opkt->dts = av_rescale_q(pkt->dts, pkt->time_base, opkt->time_base);
436 65775 opkt->dts -= ost_tb_start_time;
437
438 65775 opkt->duration = av_rescale_q(pkt->duration, pkt->time_base, opkt->time_base);
439
440 {
441 65775 int ret = trigger_fix_sub_duration_heartbeat(ost, pkt);
442
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 65775 times.
65775 if (ret < 0) {
443 av_log(NULL, AV_LOG_ERROR,
444 "Subtitle heartbeat logic failed in %s! (%s)\n",
445 __func__, av_err2str(ret));
446 exit_program(1);
447 }
448 }
449
450 65775 of_output_packet(of, opkt, ost, 0);
451
452 65775 ms->streamcopy_started = 1;
453 }
454
455 13132 static int thread_stop(Muxer *mux)
456 {
457 void *ret;
458
459
3/4
✓ Branch 0 taken 13132 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 6566 times.
✓ Branch 3 taken 6566 times.
13132 if (!mux || !mux->tq)
460 6566 return 0;
461
462
2/2
✓ Branch 0 taken 6822 times.
✓ Branch 1 taken 6566 times.
13388 for (unsigned int i = 0; i < mux->fc->nb_streams; i++)
463 6822 tq_send_finish(mux->tq, i);
464
465 6566 pthread_join(mux->thread, &ret);
466
467 6566 tq_free(&mux->tq);
468
469 6566 return (int)(intptr_t)ret;
470 }
471
472 967910 static void pkt_move(void *dst, void *src)
473 {
474 967910 av_packet_move_ref(dst, src);
475 967910 }
476
477 6566 static int thread_start(Muxer *mux)
478 {
479 6566 AVFormatContext *fc = mux->fc;
480 ObjPool *op;
481 int ret;
482
483 6566 op = objpool_alloc_packets();
484
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6566 times.
6566 if (!op)
485 return AVERROR(ENOMEM);
486
487 6566 mux->tq = tq_alloc(fc->nb_streams, mux->thread_queue_size, op, pkt_move);
488
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6566 times.
6566 if (!mux->tq) {
489 objpool_free(&op);
490 return AVERROR(ENOMEM);
491 }
492
493 6566 ret = pthread_create(&mux->thread, NULL, muxer_thread, (void*)mux);
494
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6566 times.
6566 if (ret) {
495 tq_free(&mux->tq);
496 return AVERROR(ret);
497 }
498
499 /* flush the muxing queues */
500
2/2
✓ Branch 0 taken 6822 times.
✓ Branch 1 taken 6566 times.
13388 for (int i = 0; i < fc->nb_streams; i++) {
501 6822 OutputStream *ost = mux->of.streams[i];
502 6822 MuxStream *ms = ms_from_ost(ost);
503 AVPacket *pkt;
504
505 /* try to improve muxing time_base (only possible if nothing has been written yet) */
506
2/2
✓ Branch 1 taken 6724 times.
✓ Branch 2 taken 98 times.
6822 if (!av_fifo_can_read(ms->muxing_queue))
507 6724 ost->mux_timebase = ost->st->time_base;
508
509
2/2
✓ Branch 1 taken 340 times.
✓ Branch 2 taken 6822 times.
7162 while (av_fifo_read(ms->muxing_queue, &pkt, 1) >= 0) {
510 340 ret = thread_submit_packet(mux, ost, pkt);
511
2/2
✓ Branch 0 taken 337 times.
✓ Branch 1 taken 3 times.
340 if (pkt) {
512 337 ms->muxing_queue_data_size -= pkt->size;
513 337 av_packet_free(&pkt);
514 }
515
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 340 times.
340 if (ret < 0)
516 return ret;
517 }
518 }
519
520 6566 return 0;
521 }
522
523 static int print_sdp(void)
524 {
525 char sdp[16384];
526 int i;
527 int j, ret;
528 AVIOContext *sdp_pb;
529 AVFormatContext **avc;
530
531 for (i = 0; i < nb_output_files; i++) {
532 if (!mux_from_of(output_files[i])->header_written)
533 return 0;
534 }
535
536 avc = av_malloc_array(nb_output_files, sizeof(*avc));
537 if (!avc)
538 return AVERROR(ENOMEM);
539 for (i = 0, j = 0; i < nb_output_files; i++) {
540 if (!strcmp(output_files[i]->format->name, "rtp")) {
541 avc[j] = mux_from_of(output_files[i])->fc;
542 j++;
543 }
544 }
545
546 if (!j) {
547 av_log(NULL, AV_LOG_ERROR, "No output streams in the SDP.\n");
548 ret = AVERROR(EINVAL);
549 goto fail;
550 }
551
552 ret = av_sdp_create(avc, j, sdp, sizeof(sdp));
553 if (ret < 0)
554 goto fail;
555
556 if (!sdp_filename) {
557 printf("SDP:\n%s\n", sdp);
558 fflush(stdout);
559 } else {
560 ret = avio_open2(&sdp_pb, sdp_filename, AVIO_FLAG_WRITE, &int_cb, NULL);
561 if (ret < 0) {
562 av_log(NULL, AV_LOG_ERROR, "Failed to open sdp file '%s'\n", sdp_filename);
563 goto fail;
564 }
565
566 avio_print(sdp_pb, sdp);
567 avio_closep(&sdp_pb);
568 av_freep(&sdp_filename);
569 }
570
571 // SDP successfully written, allow muxer threads to start
572 ret = 1;
573
574 fail:
575 av_freep(&avc);
576 return ret;
577 }
578
579 6822 int mux_check_init(Muxer *mux)
580 {
581 6822 OutputFile *of = &mux->of;
582 6822 AVFormatContext *fc = mux->fc;
583 int ret, i;
584
585
2/2
✓ Branch 0 taken 7395 times.
✓ Branch 1 taken 6566 times.
13961 for (i = 0; i < fc->nb_streams; i++) {
586 7395 OutputStream *ost = of->streams[i];
587
2/2
✓ Branch 0 taken 256 times.
✓ Branch 1 taken 7139 times.
7395 if (!ost->initialized)
588 256 return 0;
589 }
590
591 6566 ret = avformat_write_header(fc, &mux->opts);
592
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6566 times.
6566 if (ret < 0) {
593 av_log(mux, AV_LOG_ERROR, "Could not write header (incorrect codec "
594 "parameters ?): %s\n", av_err2str(ret));
595 return ret;
596 }
597 //assert_avoptions(of->opts);
598 6566 mux->header_written = 1;
599
600 6566 av_dump_format(fc, of->index, fc->url, 1);
601 6566 nb_output_dumped++;
602
603
2/4
✓ Branch 0 taken 6566 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 6566 times.
6566 if (sdp_filename || want_sdp) {
604 ret = print_sdp();
605 if (ret < 0) {
606 av_log(NULL, AV_LOG_ERROR, "Error writing the SDP.\n");
607 return ret;
608 } else if (ret == 1) {
609 /* SDP is written only after all the muxers are ready, so now we
610 * start ALL the threads */
611 for (i = 0; i < nb_output_files; i++) {
612 ret = thread_start(mux_from_of(output_files[i]));
613 if (ret < 0)
614 return ret;
615 }
616 }
617 } else {
618 6566 ret = thread_start(mux_from_of(of));
619
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6566 times.
6566 if (ret < 0)
620 return ret;
621 }
622
623 6566 return 0;
624 }
625
626 6822 static int bsf_init(MuxStream *ms)
627 {
628 6822 OutputStream *ost = &ms->ost;
629 6822 AVBSFContext *ctx = ms->bsf_ctx;
630 int ret;
631
632
2/2
✓ Branch 0 taken 6724 times.
✓ Branch 1 taken 98 times.
6822 if (!ctx)
633 6724 return avcodec_parameters_copy(ost->st->codecpar, ost->par_in);
634
635 98 ret = avcodec_parameters_copy(ctx->par_in, ost->par_in);
636
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 98 times.
98 if (ret < 0)
637 return ret;
638
639 98 ctx->time_base_in = ost->st->time_base;
640
641 98 ret = av_bsf_init(ctx);
642
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 98 times.
98 if (ret < 0) {
643 av_log(ms, AV_LOG_ERROR, "Error initializing bitstream filter: %s\n",
644 ctx->filter->name);
645 return ret;
646 }
647
648 98 ret = avcodec_parameters_copy(ost->st->codecpar, ctx->par_out);
649
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 98 times.
98 if (ret < 0)
650 return ret;
651 98 ost->st->time_base = ctx->time_base_out;
652
653 98 return 0;
654 }
655
656 6822 int of_stream_init(OutputFile *of, OutputStream *ost)
657 {
658 6822 Muxer *mux = mux_from_of(of);
659 6822 MuxStream *ms = ms_from_ost(ost);
660 int ret;
661
662 /* initialize bitstream filters for the output stream
663 * needs to be done here, because the codec id for streamcopy is not
664 * known until now */
665 6822 ret = bsf_init(ms);
666
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6822 times.
6822 if (ret < 0)
667 return ret;
668
669 6822 ost->initialized = 1;
670
671 6822 return mux_check_init(mux);
672 }
673
674 6566 static int check_written(OutputFile *of)
675 {
676 6566 int64_t total_packets_written = 0;
677 6566 int pass1_used = 1;
678 6566 int ret = 0;
679
680
2/2
✓ Branch 0 taken 6822 times.
✓ Branch 1 taken 6566 times.
13388 for (int i = 0; i < of->nb_streams; i++) {
681 6822 OutputStream *ost = of->streams[i];
682 6822 uint64_t packets_written = atomic_load(&ost->packets_written);
683
684 6822 total_packets_written += packets_written;
685
686
2/2
✓ Branch 0 taken 6326 times.
✓ Branch 1 taken 496 times.
6822 if (ost->enc_ctx &&
687
2/2
✓ Branch 0 taken 6322 times.
✓ Branch 1 taken 4 times.
6326 (ost->enc_ctx->flags & (AV_CODEC_FLAG_PASS1 | AV_CODEC_FLAG_PASS2))
688 != AV_CODEC_FLAG_PASS1)
689 6322 pass1_used = 0;
690
691
2/2
✓ Branch 0 taken 37 times.
✓ Branch 1 taken 6785 times.
6822 if (!packets_written &&
692
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 37 times.
37 (abort_on_flags & ABORT_ON_FLAG_EMPTY_OUTPUT_STREAM)) {
693 av_log(ost, AV_LOG_FATAL, "Empty output stream\n");
694 ret = err_merge(ret, AVERROR(EINVAL));
695 }
696 }
697
698
2/2
✓ Branch 0 taken 12 times.
✓ Branch 1 taken 6554 times.
6566 if (!total_packets_written) {
699 12 int level = AV_LOG_WARNING;
700
701
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 12 times.
12 if (abort_on_flags & ABORT_ON_FLAG_EMPTY_OUTPUT) {
702 ret = err_merge(ret, AVERROR(EINVAL));
703 level = AV_LOG_FATAL;
704 }
705
706
2/2
✓ Branch 0 taken 11 times.
✓ Branch 1 taken 1 times.
12 av_log(of, level, "Output file is empty, nothing was encoded%s\n",
707 pass1_used ? "" : "(check -ss / -t / -frames parameters if used)");
708 }
709
710 6566 return ret;
711 }
712
713 6566 static void mux_final_stats(Muxer *mux)
714 {
715 6566 OutputFile *of = &mux->of;
716 6566 uint64_t total_packets = 0, total_size = 0;
717 6566 uint64_t video_size = 0, audio_size = 0, subtitle_size = 0,
718 6566 extra_size = 0, other_size = 0;
719
720 6566 uint8_t overhead[16] = "unknown";
721 6566 int64_t file_size = of_filesize(of);
722
723 6566 av_log(of, AV_LOG_VERBOSE, "Output file #%d (%s):\n",
724 of->index, of->url);
725
726
2/2
✓ Branch 0 taken 6822 times.
✓ Branch 1 taken 6566 times.
13388 for (int j = 0; j < of->nb_streams; j++) {
727 6822 OutputStream *ost = of->streams[j];
728 6822 MuxStream *ms = ms_from_ost(ost);
729 6822 const AVCodecParameters *par = ost->st->codecpar;
730 6822 const enum AVMediaType type = par->codec_type;
731 6822 const uint64_t s = ms->data_size_mux;
732
733
4/4
✓ Branch 0 taken 5344 times.
✓ Branch 1 taken 1397 times.
✓ Branch 2 taken 68 times.
✓ Branch 3 taken 13 times.
6822 switch (type) {
734 5344 case AVMEDIA_TYPE_VIDEO: video_size += s; break;
735 1397 case AVMEDIA_TYPE_AUDIO: audio_size += s; break;
736 68 case AVMEDIA_TYPE_SUBTITLE: subtitle_size += s; break;
737 13 default: other_size += s; break;
738 }
739
740 6822 extra_size += par->extradata_size;
741 6822 total_size += s;
742 6822 total_packets += atomic_load(&ost->packets_written);
743
744 6822 av_log(of, AV_LOG_VERBOSE, " Output stream #%d:%d (%s): ",
745 of->index, j, av_get_media_type_string(type));
746
2/2
✓ Branch 0 taken 6326 times.
✓ Branch 1 taken 496 times.
6822 if (ost->enc) {
747 6326 av_log(of, AV_LOG_VERBOSE, "%"PRIu64" frames encoded",
748 ost->frames_encoded);
749
2/2
✓ Branch 0 taken 1189 times.
✓ Branch 1 taken 5137 times.
6326 if (type == AVMEDIA_TYPE_AUDIO)
750 1189 av_log(of, AV_LOG_VERBOSE, " (%"PRIu64" samples)", ost->samples_encoded);
751 6326 av_log(of, AV_LOG_VERBOSE, "; ");
752 }
753
754 6822 av_log(of, AV_LOG_VERBOSE, "%"PRIu64" packets muxed (%"PRIu64" bytes); ",
755 6822 atomic_load(&ost->packets_written), s);
756
757 6822 av_log(of, AV_LOG_VERBOSE, "\n");
758 }
759
760 6566 av_log(of, AV_LOG_VERBOSE, " Total: %"PRIu64" packets (%"PRIu64" bytes) muxed\n",
761 total_packets, total_size);
762
763
6/6
✓ Branch 0 taken 6554 times.
✓ Branch 1 taken 12 times.
✓ Branch 2 taken 6467 times.
✓ Branch 3 taken 87 times.
✓ Branch 4 taken 4537 times.
✓ Branch 5 taken 1930 times.
6566 if (total_size && file_size > 0 && file_size >= total_size) {
764 4537 snprintf(overhead, sizeof(overhead), "%f%%",
765 4537 100.0 * (file_size - total_size) / total_size);
766 }
767
768 6566 av_log(of, AV_LOG_INFO,
769 "video:%1.0fkB audio:%1.0fkB subtitle:%1.0fkB other streams:%1.0fkB "
770 "global headers:%1.0fkB muxing overhead: %s\n",
771 video_size / 1024.0,
772 audio_size / 1024.0,
773 subtitle_size / 1024.0,
774 other_size / 1024.0,
775 extra_size / 1024.0,
776 overhead);
777 6566 }
778
779 6566 int of_write_trailer(OutputFile *of)
780 {
781 6566 Muxer *mux = mux_from_of(of);
782 6566 AVFormatContext *fc = mux->fc;
783 6566 int ret, mux_result = 0;
784
785
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6566 times.
6566 if (!mux->tq) {
786 av_log(mux, AV_LOG_ERROR,
787 "Nothing was written into output file, because "
788 "at least one of its streams received no packets.\n");
789 return AVERROR(EINVAL);
790 }
791
792 6566 mux_result = thread_stop(mux);
793
794 6566 ret = av_write_trailer(fc);
795
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6566 times.
6566 if (ret < 0) {
796 av_log(mux, AV_LOG_ERROR, "Error writing trailer: %s\n", av_err2str(ret));
797 mux_result = err_merge(mux_result, ret);
798 }
799
800 6566 mux->last_filesize = filesize(fc->pb);
801
802
2/2
✓ Branch 0 taken 6479 times.
✓ Branch 1 taken 87 times.
6566 if (!(of->format->flags & AVFMT_NOFILE)) {
803 6479 ret = avio_closep(&fc->pb);
804
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6479 times.
6479 if (ret < 0) {
805 av_log(mux, AV_LOG_ERROR, "Error closing file: %s\n", av_err2str(ret));
806 mux_result = err_merge(mux_result, ret);
807 }
808 }
809
810 6566 mux_final_stats(mux);
811
812 // check whether anything was actually written
813 6566 ret = check_written(of);
814 6566 mux_result = err_merge(mux_result, ret);
815
816 6566 return mux_result;
817 }
818
819 6822 static void ost_free(OutputStream **post)
820 {
821 6822 OutputStream *ost = *post;
822 MuxStream *ms;
823
824
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6822 times.
6822 if (!ost)
825 return;
826 6822 ms = ms_from_ost(ost);
827
828 6822 enc_free(&ost->enc);
829
830
2/2
✓ Branch 0 taken 4 times.
✓ Branch 1 taken 6818 times.
6822 if (ost->logfile) {
831
1/2
✗ Branch 1 not taken.
✓ Branch 2 taken 4 times.
4 if (fclose(ost->logfile))
832 av_log(ms, AV_LOG_ERROR,
833 "Error closing logfile, loss of information possible: %s\n",
834 av_err2str(AVERROR(errno)));
835 4 ost->logfile = NULL;
836 }
837
838
1/2
✓ Branch 0 taken 6822 times.
✗ Branch 1 not taken.
6822 if (ms->muxing_queue) {
839 AVPacket *pkt;
840
1/2
✗ Branch 1 not taken.
✓ Branch 2 taken 6822 times.
6822 while (av_fifo_read(ms->muxing_queue, &pkt, 1) >= 0)
841 av_packet_free(&pkt);
842 6822 av_fifo_freep2(&ms->muxing_queue);
843 }
844
845 6822 avcodec_parameters_free(&ost->par_in);
846
847 6822 av_bsf_free(&ms->bsf_ctx);
848
849 6822 av_packet_free(&ost->pkt);
850 6822 av_dict_free(&ost->encoder_opts);
851
852 6822 av_freep(&ost->kf.pts);
853 6822 av_expr_free(ost->kf.pexpr);
854
855 6822 av_freep(&ost->logfile_prefix);
856 6822 av_freep(&ost->apad);
857
858 #if FFMPEG_OPT_MAP_CHANNEL
859 6822 av_freep(&ost->audio_channels_map);
860 6822 ost->audio_channels_mapped = 0;
861 #endif
862
863 6822 av_dict_free(&ost->sws_dict);
864 6822 av_dict_free(&ost->swr_opts);
865
866
2/2
✓ Branch 0 taken 6326 times.
✓ Branch 1 taken 496 times.
6822 if (ost->enc_ctx)
867 6326 av_freep(&ost->enc_ctx->stats_in);
868 6822 avcodec_free_context(&ost->enc_ctx);
869
870
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6822 times.
6822 for (int i = 0; i < ost->enc_stats_pre.nb_components; i++)
871 av_freep(&ost->enc_stats_pre.components[i].str);
872 6822 av_freep(&ost->enc_stats_pre.components);
873
874
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6822 times.
6822 for (int i = 0; i < ost->enc_stats_post.nb_components; i++)
875 av_freep(&ost->enc_stats_post.components[i].str);
876 6822 av_freep(&ost->enc_stats_post.components);
877
878
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6822 times.
6822 for (int i = 0; i < ms->stats.nb_components; i++)
879 av_freep(&ms->stats.components[i].str);
880 6822 av_freep(&ms->stats.components);
881
882 6822 av_freep(post);
883 }
884
885 6566 static void fc_close(AVFormatContext **pfc)
886 {
887 6566 AVFormatContext *fc = *pfc;
888
889
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6566 times.
6566 if (!fc)
890 return;
891
892
2/2
✓ Branch 0 taken 6479 times.
✓ Branch 1 taken 87 times.
6566 if (!(fc->oformat->flags & AVFMT_NOFILE))
893 6479 avio_closep(&fc->pb);
894 6566 avformat_free_context(fc);
895
896 6566 *pfc = NULL;
897 }
898
899 6566 void of_close(OutputFile **pof)
900 {
901 6566 OutputFile *of = *pof;
902 Muxer *mux;
903
904
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6566 times.
6566 if (!of)
905 return;
906 6566 mux = mux_from_of(of);
907
908 6566 thread_stop(mux);
909
910 6566 sq_free(&of->sq_encode);
911 6566 sq_free(&mux->sq_mux);
912
913
2/2
✓ Branch 0 taken 6822 times.
✓ Branch 1 taken 6566 times.
13388 for (int i = 0; i < of->nb_streams; i++)
914 6822 ost_free(&of->streams[i]);
915 6566 av_freep(&of->streams);
916
917 6566 av_dict_free(&mux->opts);
918
919 6566 av_packet_free(&mux->sq_pkt);
920
921 6566 fc_close(&mux->fc);
922
923 6566 av_freep(pof);
924 }
925
926 466396 int64_t of_filesize(OutputFile *of)
927 {
928 466396 Muxer *mux = mux_from_of(of);
929 466396 return atomic_load(&mux->last_filesize);
930 }
931