1 /* muxavformat.c
2 
3    Copyright (c) 2003-2021 HandBrake Team
4    This file is part of the HandBrake source code
5    Homepage: <http://handbrake.fr/>.
6    It may be used under the terms of the GNU General Public License v2.
7    For full terms see the file COPYING file or visit http://www.gnu.org/licenses/gpl-2.0.html
8  */
9 
10 #include <ogg/ogg.h>
11 #include "libavformat/avformat.h"
12 #include "libavutil/avstring.h"
13 #include "libavutil/intreadwrite.h"
14 
15 #include "handbrake/handbrake.h"
16 #include "handbrake/ssautil.h"
17 #include "handbrake/lang.h"
18 #include "handbrake/hbffmpeg.h"
19 
20 struct hb_mux_data_s
21 {
22     enum
23     {
24         MUX_TYPE_VIDEO,
25         MUX_TYPE_AUDIO,
26         MUX_TYPE_SUBTITLE
27     } type;
28 
29     AVStream    *st;
30 
31     int64_t  duration;
32 
33     hb_buffer_t * delay_buf;
34 
35     int64_t  prev_chapter_tc;
36     int16_t  current_chapter;
37 
38     AVBSFContext            * bitstream_context;
39     hb_tx3g_style_context_t * tx3g;
40 };
41 
42 struct hb_mux_object_s
43 {
44     HB_MUX_COMMON;
45 
46     hb_job_t          * job;
47 
48     AVFormatContext   * oc;
49     AVRational          time_base;
50     AVPacket          * pkt;
51     AVPacket          * empty_pkt;
52 
53     int                 ntracks;
54     hb_mux_data_t    ** tracks;
55 };
56 
57 enum
58 {
59     META_HB,
60     META_MUX_MP4,
61     META_MUX_MKV,
62     META_MUX_WEBM,
63     META_MUX_LAST
64 };
65 
66 const char *metadata_keys[][META_MUX_LAST] =
67 {
68     {"Name",            "title",        "TITLE"},
69     {"Artist",          "artist",       "ARTIST"},
70     {"AlbumArtist",     "album_artist", "DIRECTOR"},
71     {"Composer",        "composer",     "COMPOSER"},
72     {"ReleaseDate",     "date",         "DATE_RELEASED"},
73     {"Comment",         "comment",      "SUMMARY"},
74     {"Album",           "album",        NULL},
75     {"Genre",           "genre",        "GENRE"},
76     {"Description",     "description",  "DESCRIPTION"},
77     {"LongDescription", "synopsis",     "SYNOPSIS"},
78     {NULL}
79 };
80 
lookup_meta_mux_key(int meta_mux,const char * hb_key)81 static const char * lookup_meta_mux_key(int meta_mux, const char * hb_key)
82 {
83     int ii;
84 
85     for (ii = 0; metadata_keys[ii][META_HB] != NULL; ii++)
86     {
87         if (!strcmp(hb_key, metadata_keys[ii][META_HB]))
88         {
89             return metadata_keys[ii][meta_mux];
90         }
91     }
92     return NULL;
93 }
94 
hb_lookup_meta_key(const char * mux_key)95 const char * hb_lookup_meta_key(const char * mux_key)
96 {
97     int ii, jj;
98 
99     for (ii = 0; metadata_keys[ii][META_HB] != NULL; ii++)
100     {
101         for (jj = 0; jj < META_MUX_LAST; jj++)
102         {
103             if (metadata_keys[ii][jj] != NULL &&
104                 !strcmp(mux_key, metadata_keys[ii][jj]))
105             {
106                 return metadata_keys[ii][META_HB];
107             }
108         }
109     }
110     return NULL;
111 }
112 
lookup_lang_code(int mux,char * iso639_2)113 static char* lookup_lang_code(int mux, char *iso639_2)
114 {
115     iso639_lang_t   *lang;
116     char *out = NULL;
117 
118     switch (mux)
119     {
120         case HB_MUX_AV_MP4:
121             out = iso639_2;
122             break;
123         case HB_MUX_AV_MKV:
124         case HB_MUX_AV_WEBM: // webm is a subset of mkv
125             // MKV lang codes should be ISO-639-2B if it exists,
126             // else ISO-639-2
127             lang =  lang_for_code2( iso639_2 );
128             out = lang->iso639_2b && *lang->iso639_2b ? lang->iso639_2b :
129                                                         lang->iso639_2;
130             break;
131         default:
132             break;
133     }
134     return out;
135 }
136 
137 /**********************************************************************
138  * avformatInit
139  **********************************************************************
140  * Allocates hb_mux_data_t structures, create file and write headers
141  *********************************************************************/
avformatInit(hb_mux_object_t * m)142 static int avformatInit( hb_mux_object_t * m )
143 {
144     hb_job_t   * job   = m->job;
145     hb_audio_t    * audio;
146     hb_mux_data_t * track;
147     int meta_mux;
148     int max_tracks;
149     int ii, jj, ret;
150 
151     int clock_min, clock_max, clock;
152     hb_video_framerate_get_limits(&clock_min, &clock_max, &clock);
153 
154     const char *muxer_name = NULL;
155 
156     uint8_t         default_track_flag = 1;
157     uint8_t         need_fonts = 0;
158     char *lang;
159 
160     m->pkt = av_packet_alloc();
161     m->empty_pkt = av_packet_alloc();
162 
163     m->pkt = av_packet_alloc();
164     if (m->pkt == NULL || m->empty_pkt == NULL)
165     {
166         hb_error("muxavformat: av_packet_alloc failed");
167         goto error;
168     }
169 
170     max_tracks = 1 + hb_list_count( job->list_audio ) +
171                      hb_list_count( job->list_subtitle );
172     m->tracks = calloc(max_tracks, sizeof(hb_mux_data_t*));
173 
174     AVDictionary * av_opts = NULL;
175     switch (job->mux)
176     {
177         case HB_MUX_AV_MP4:
178             m->time_base.num = 1;
179             m->time_base.den = 90000;
180             if( job->ipod_atom )
181                 muxer_name = "ipod";
182             else
183                 muxer_name = "mp4";
184             meta_mux = META_MUX_MP4;
185 
186             av_dict_set(&av_opts, "brand", "mp42", 0);
187             if (job->mp4_optimize)
188                 av_dict_set(&av_opts, "movflags", "faststart+disable_chpl+write_colr", 0);
189             else
190                 av_dict_set(&av_opts, "movflags", "+disable_chpl+write_colr", 0);
191             break;
192 
193         case HB_MUX_AV_MKV:
194             // libavformat is essentially hard coded such that it only
195             // works with a timebase of 1/1000
196             m->time_base.num = 1;
197             m->time_base.den = 1000;
198             muxer_name = "matroska";
199             meta_mux = META_MUX_MKV;
200             av_dict_set(&av_opts, "default_mode", "passthrough", 0);
201             break;
202 
203         case HB_MUX_AV_WEBM:
204             // libavformat is essentially hard coded such that it only
205             // works with a timebase of 1/1000
206             m->time_base.num = 1;
207             m->time_base.den = 1000;
208             muxer_name = "webm";
209             meta_mux = META_MUX_WEBM;
210             av_dict_set(&av_opts, "default_mode", "passthrough", 0);
211             break;
212 
213         default:
214         {
215             hb_error("Invalid Mux %x", job->mux);
216             goto error;
217         }
218     }
219 
220     ret = avformat_alloc_output_context2(&m->oc, NULL, muxer_name, job->file);
221     if (ret < 0)
222     {
223         hb_error( "Could not initialize avformat context." );
224         goto error;
225     }
226 
227     ret = avio_open2(&m->oc->pb, job->file, AVIO_FLAG_WRITE,
228                      &m->oc->interrupt_callback, NULL);
229     if( ret < 0 )
230     {
231       if( ret == -2 )
232       {
233         hb_error( "avio_open2 failed, errno -2: Could not write to indicated output file. Please check destination path and file permissions" );
234       }
235       else
236         hb_error( "avio_open2 failed, errno %d", ret);
237       goto error;
238     }
239 
240     /* Video track */
241     track = m->tracks[m->ntracks++] = calloc(1, sizeof( hb_mux_data_t ) );
242     job->mux_data = track;
243 
244     track->type = MUX_TYPE_VIDEO;
245     track->prev_chapter_tc = AV_NOPTS_VALUE;
246     track->st = avformat_new_stream(m->oc, NULL);
247     if (track->st == NULL)
248     {
249         hb_error("Could not initialize video stream");
250         goto error;
251     }
252 
253     track->st->codecpar->codec_type = AVMEDIA_TYPE_VIDEO;
254     track->st->time_base            = m->time_base;
255 
256     uint8_t *priv_data = NULL;
257     int priv_size = 0;
258     switch (job->vcodec)
259     {
260         case HB_VCODEC_X264_8BIT:
261         case HB_VCODEC_X264_10BIT:
262         case HB_VCODEC_QSV_H264:
263             track->st->codecpar->codec_id = AV_CODEC_ID_H264;
264             if (job->mux == HB_MUX_AV_MP4 && job->inline_parameter_sets)
265             {
266                 track->st->codecpar->codec_tag = MKTAG('a','v','c','3');
267             }
268             else
269             {
270                 track->st->codecpar->codec_tag = MKTAG('a','v','c','1');
271             }
272 
273             /* Taken from x264 muxers.c */
274             priv_size = 5 + 1 + 2 + job->config.h264.sps_length + 1 + 2 +
275                         job->config.h264.pps_length;
276             priv_data = av_malloc(priv_size + AV_INPUT_BUFFER_PADDING_SIZE);
277             if (priv_data == NULL)
278             {
279                 hb_error("H.264 extradata: malloc failure");
280                 goto error;
281             }
282 
283             priv_data[0] = 1;
284             priv_data[1] = job->config.h264.sps[1]; /* AVCProfileIndication */
285             priv_data[2] = job->config.h264.sps[2]; /* profile_compat */
286             priv_data[3] = job->config.h264.sps[3]; /* AVCLevelIndication */
287             priv_data[4] = 0xff; // nalu size length is four bytes
288             priv_data[5] = 0xe1; // one sps
289 
290             priv_data[6] = job->config.h264.sps_length >> 8;
291             priv_data[7] = job->config.h264.sps_length;
292 
293             memcpy(priv_data+8, job->config.h264.sps,
294                    job->config.h264.sps_length);
295 
296             priv_data[8+job->config.h264.sps_length] = 1; // one pps
297             priv_data[9+job->config.h264.sps_length] =
298                                         job->config.h264.pps_length >> 8;
299             priv_data[10+job->config.h264.sps_length] =
300                                         job->config.h264.pps_length;
301 
302             memcpy(priv_data+11+job->config.h264.sps_length,
303                    job->config.h264.pps, job->config.h264.pps_length );
304             break;
305 
306         case HB_VCODEC_FFMPEG_VCE_H264:
307         case HB_VCODEC_FFMPEG_NVENC_H264:
308         case HB_VCODEC_FFMPEG_VT_H264:
309         case HB_VCODEC_FFMPEG_MF_H264:
310             track->st->codecpar->codec_id = AV_CODEC_ID_H264;
311             if (job->mux == HB_MUX_AV_MP4 && job->inline_parameter_sets)
312             {
313                 track->st->codecpar->codec_tag = MKTAG('a','v','c','3');
314             }
315             else
316             {
317                 track->st->codecpar->codec_tag = MKTAG('a','v','c','1');
318             }
319             if (job->config.extradata.length > 0)
320             {
321                 priv_size = job->config.extradata.length;
322                 priv_data = av_malloc(priv_size + AV_INPUT_BUFFER_PADDING_SIZE);
323                 if (priv_data == NULL)
324                 {
325                     hb_error("H.264 extradata: malloc failure");
326                     goto error;
327                 }
328                 memcpy(priv_data,
329                        job->config.extradata.bytes,
330                        job->config.extradata.length);
331             }
332             break;
333 
334         case HB_VCODEC_FFMPEG_MPEG4:
335             track->st->codecpar->codec_id = AV_CODEC_ID_MPEG4;
336 
337             if (job->config.extradata.length > 0)
338             {
339                 priv_size = job->config.extradata.length;
340                 priv_data = av_malloc(priv_size + AV_INPUT_BUFFER_PADDING_SIZE);
341                 if (priv_data == NULL)
342                 {
343                     hb_error("MPEG-4 extradata: malloc failure");
344                     goto error;
345                 }
346                 memcpy(priv_data,
347                        job->config.extradata.bytes,
348                        job->config.extradata.length);
349             }
350             break;
351 
352         case HB_VCODEC_FFMPEG_MPEG2:
353             track->st->codecpar->codec_id = AV_CODEC_ID_MPEG2VIDEO;
354 
355             if (job->config.extradata.length > 0)
356             {
357                 priv_size = job->config.extradata.length;
358                 priv_data = av_malloc(priv_size + AV_INPUT_BUFFER_PADDING_SIZE);
359                 if (priv_data == NULL)
360                 {
361                     hb_error("MPEG-2 extradata: malloc failure");
362                     goto error;
363                 }
364                 memcpy(priv_data,
365                        job->config.extradata.bytes,
366                        job->config.extradata.length);
367             }
368             break;
369 
370         case HB_VCODEC_FFMPEG_VP8:
371             track->st->codecpar->codec_id = AV_CODEC_ID_VP8;
372             priv_data                  = NULL;
373             priv_size                  = 0;
374             break;
375 
376         case HB_VCODEC_FFMPEG_VP9:
377             track->st->codecpar->codec_id = AV_CODEC_ID_VP9;
378             priv_data                  = NULL;
379             priv_size                  = 0;
380             break;
381 
382         case HB_VCODEC_THEORA:
383         {
384             track->st->codecpar->codec_id = AV_CODEC_ID_THEORA;
385 
386             int size = 0;
387             ogg_packet *ogg_headers[3];
388 
389             for (ii = 0; ii < 3; ii++)
390             {
391                 ogg_headers[ii] = (ogg_packet *)job->config.theora.headers[ii];
392                 size += ogg_headers[ii]->bytes + 2;
393             }
394 
395             priv_size = size;
396             priv_data = av_malloc(priv_size + AV_INPUT_BUFFER_PADDING_SIZE);
397             if (priv_data == NULL)
398             {
399                 hb_error("Theora extradata: malloc failure");
400                 goto error;
401             }
402 
403             size = 0;
404             for(ii = 0; ii < 3; ii++)
405             {
406                 AV_WB16(priv_data + size, ogg_headers[ii]->bytes);
407                 size += 2;
408                 memcpy(priv_data+size, ogg_headers[ii]->packet,
409                                        ogg_headers[ii]->bytes);
410                 size += ogg_headers[ii]->bytes;
411             }
412         } break;
413 
414         case HB_VCODEC_X265_8BIT:
415         case HB_VCODEC_X265_10BIT:
416         case HB_VCODEC_X265_12BIT:
417         case HB_VCODEC_X265_16BIT:
418         case HB_VCODEC_QSV_H265:
419         case HB_VCODEC_QSV_H265_10BIT:
420             track->st->codecpar->codec_id  = AV_CODEC_ID_HEVC;
421             if (job->mux == HB_MUX_AV_MP4 && job->inline_parameter_sets)
422             {
423                 track->st->codecpar->codec_tag = MKTAG('h','e','v','1');
424             }
425             else
426             {
427                 track->st->codecpar->codec_tag = MKTAG('h','v','c','1');
428             }
429 
430             if (job->config.h265.headers_length > 0)
431             {
432                 priv_size = job->config.h265.headers_length;
433                 priv_data = av_malloc(priv_size + AV_INPUT_BUFFER_PADDING_SIZE);
434                 if (priv_data == NULL)
435                 {
436                     hb_error("H.265 extradata: malloc failure");
437                     goto error;
438                 }
439                 memcpy(priv_data, job->config.h265.headers, priv_size);
440             }
441             break;
442 
443         case HB_VCODEC_FFMPEG_VCE_H265:
444         case HB_VCODEC_FFMPEG_NVENC_H265:
445         case HB_VCODEC_FFMPEG_VT_H265:
446         case HB_VCODEC_FFMPEG_VT_H265_10BIT:
447         case HB_VCODEC_FFMPEG_MF_H265:
448             track->st->codecpar->codec_id  = AV_CODEC_ID_HEVC;
449             if (job->mux == HB_MUX_AV_MP4 && job->inline_parameter_sets)
450             {
451                 track->st->codecpar->codec_tag = MKTAG('h','e','v','1');
452             }
453             else
454             {
455                 track->st->codecpar->codec_tag = MKTAG('h','v','c','1');
456             }
457             if (job->config.extradata.length > 0)
458             {
459                 priv_size = job->config.extradata.length;
460                 priv_data = av_malloc(priv_size + AV_INPUT_BUFFER_PADDING_SIZE);
461                 if (priv_data == NULL)
462                 {
463                     hb_error("H.265 extradata: malloc failure");
464                     goto error;
465                 }
466                 memcpy(priv_data,
467                        job->config.extradata.bytes,
468                        job->config.extradata.length);
469             }
470             break;
471 
472         default:
473             hb_error("muxavformat: Unknown video codec: %x", job->vcodec);
474             goto error;
475     }
476     track->st->codecpar->extradata = priv_data;
477     track->st->codecpar->extradata_size = priv_size;
478 
479     track->st->sample_aspect_ratio.num        = job->par.num;
480     track->st->sample_aspect_ratio.den        = job->par.den;
481     track->st->codecpar->sample_aspect_ratio.num = job->par.num;
482     track->st->codecpar->sample_aspect_ratio.den = job->par.den;
483     track->st->codecpar->width                   = job->width;
484     track->st->codecpar->height                  = job->height;
485     track->st->disposition |= AV_DISPOSITION_DEFAULT;
486 
487     track->st->codecpar->color_primaries = hb_output_color_prim(job);
488     track->st->codecpar->color_trc       = hb_output_color_transfer(job);
489     track->st->codecpar->color_space     = hb_output_color_matrix(job);
490     track->st->codecpar->color_range     = job->color_range;
491 
492     if (job->color_transfer == HB_COLR_TRA_SMPTEST2084)
493     {
494         if (job->mastering.has_primaries || job->mastering.has_luminance)
495         {
496             AVMasteringDisplayMetadata mastering = hb_mastering_hb_to_ff(job->mastering);
497 
498             uint8_t *mastering_data = av_malloc(sizeof(AVMasteringDisplayMetadata));
499             memcpy(mastering_data, &mastering, sizeof(AVMasteringDisplayMetadata));
500 
501             av_stream_add_side_data(track->st,
502                                     AV_PKT_DATA_MASTERING_DISPLAY_METADATA,
503                                     mastering_data,
504                                     sizeof(AVMasteringDisplayMetadata));
505         }
506 
507         if (job->coll.max_cll && job->coll.max_fall)
508         {
509             AVContentLightMetadata coll;
510             coll.MaxCLL = job->coll.max_cll;
511             coll.MaxFALL = job->coll.max_fall;
512 
513             uint8_t *coll_data = av_malloc(sizeof(AVContentLightMetadata));
514             memcpy(coll_data, &coll, sizeof(AVContentLightMetadata));
515 
516             av_stream_add_side_data(track->st,
517                                     AV_PKT_DATA_CONTENT_LIGHT_LEVEL,
518                                     coll_data,
519                                     sizeof(AVContentLightMetadata));
520         }
521     }
522 
523     hb_rational_t vrate = job->vrate;
524 
525     // If the vrate is the internal clock rate, there's a good chance
526     // this is a standard rate that we have in our hb_video_rates table.
527     // Because of rounding errors and approximations made while
528     // measuring framerate, the actual value may not be exact.  So
529     // we look for rates that are "close" and make an adjustment
530     // to fps.den.
531     if (vrate.num == clock)
532     {
533         const hb_rate_t *video_framerate = NULL;
534         while ((video_framerate = hb_video_framerate_get_next(video_framerate)) != NULL)
535         {
536             if (abs(vrate.den - video_framerate->rate) < 10)
537             {
538                 vrate.den = video_framerate->rate;
539                 break;
540             }
541         }
542     }
543     hb_reduce(&vrate.num, &vrate.den, vrate.num, vrate.den);
544     track->st->avg_frame_rate.num = vrate.num;
545     track->st->avg_frame_rate.den = vrate.den;
546 
547     /* add the audio tracks */
548     for(ii = 0; ii < hb_list_count( job->list_audio ); ii++ )
549     {
550         audio = hb_list_item( job->list_audio, ii );
551         track = m->tracks[m->ntracks++] = calloc(1, sizeof( hb_mux_data_t ) );
552         audio->priv.mux_data = track;
553 
554         track->type = MUX_TYPE_AUDIO;
555 
556         track->st = avformat_new_stream(m->oc, NULL);
557         if (track->st == NULL)
558         {
559             hb_error("Could not initialize audio stream");
560             goto error;
561         }
562 
563         track->st->codecpar->codec_type = AVMEDIA_TYPE_AUDIO;
564         track->st->codecpar->initial_padding = audio->priv.config.init_delay *
565                                         audio->config.out.samplerate / 90000;
566         track->st->codecpar->frame_size = audio->config.out.samples_per_frame;
567         if (job->mux == HB_MUX_AV_MP4)
568         {
569             track->st->time_base.num = 1;
570             track->st->time_base.den = audio->config.out.samplerate;
571         }
572         else
573         {
574             track->st->time_base = m->time_base;
575         }
576 
577         priv_data = NULL;
578         priv_size = 0;
579         switch (audio->config.out.codec & HB_ACODEC_MASK)
580         {
581             case HB_ACODEC_DCA:
582             case HB_ACODEC_DCA_HD:
583                 track->st->codecpar->codec_id = AV_CODEC_ID_DTS;
584                 break;
585             case HB_ACODEC_AC3:
586                 track->st->codecpar->codec_id = AV_CODEC_ID_AC3;
587                 break;
588             case HB_ACODEC_FFEAC3:
589                 track->st->codecpar->codec_id = AV_CODEC_ID_EAC3;
590                 break;
591             case HB_ACODEC_FFTRUEHD:
592                 track->st->codecpar->codec_id = AV_CODEC_ID_TRUEHD;
593                 break;
594             case HB_ACODEC_MP2:
595                 track->st->codecpar->codec_id = AV_CODEC_ID_MP2;
596                 break;
597             case HB_ACODEC_LAME:
598             case HB_ACODEC_MP3:
599                 track->st->codecpar->codec_id = AV_CODEC_ID_MP3;
600                 break;
601             case HB_ACODEC_VORBIS:
602             {
603                 track->st->codecpar->codec_id = AV_CODEC_ID_VORBIS;
604 
605                 int jj, size = 0;
606                 ogg_packet *ogg_headers[3];
607 
608                 for (jj = 0; jj < 3; jj++)
609                 {
610                     ogg_headers[jj] = (ogg_packet *)audio->priv.config.vorbis.headers[jj];
611                     size += ogg_headers[jj]->bytes + 2;
612                 }
613 
614                 priv_size = size;
615                 priv_data = av_malloc(priv_size + AV_INPUT_BUFFER_PADDING_SIZE);
616                 if (priv_data == NULL)
617                 {
618                     hb_error("Vorbis extradata: malloc failure");
619                     goto error;
620                 }
621 
622                 size = 0;
623                 for(jj = 0; jj < 3; jj++)
624                 {
625                     AV_WB16(priv_data + size, ogg_headers[jj]->bytes);
626                     size += 2;
627                     memcpy(priv_data+size, ogg_headers[jj]->packet,
628                                            ogg_headers[jj]->bytes);
629                     size += ogg_headers[jj]->bytes;
630                 }
631             } break;
632             case HB_ACODEC_OPUS:
633                 track->st->codecpar->codec_id = AV_CODEC_ID_OPUS;
634 
635                 if (audio->priv.config.extradata.length)
636                 {
637                     priv_size = audio->priv.config.extradata.length;
638                     priv_data = av_malloc(priv_size + AV_INPUT_BUFFER_PADDING_SIZE);
639                     if (priv_data == NULL)
640                     {
641                         hb_error("OPUS extradata: malloc failure");
642                         goto error;
643                     }
644                     memcpy(priv_data,
645                            audio->priv.config.extradata.bytes,
646                            audio->priv.config.extradata.length);
647                 }
648                 break;
649             case HB_ACODEC_FFFLAC:
650             case HB_ACODEC_FFFLAC24:
651                 track->st->codecpar->codec_id = AV_CODEC_ID_FLAC;
652 
653                 if (audio->priv.config.extradata.length)
654                 {
655                     priv_size = audio->priv.config.extradata.length;
656                     priv_data = av_malloc(priv_size + AV_INPUT_BUFFER_PADDING_SIZE);
657                     if (priv_data == NULL)
658                     {
659                         hb_error("FLAC extradata: malloc failure");
660                         goto error;
661                     }
662                     memcpy(priv_data,
663                            audio->priv.config.extradata.bytes,
664                            audio->priv.config.extradata.length);
665                 }
666                 break;
667             case HB_ACODEC_FFAAC:
668             case HB_ACODEC_CA_AAC:
669             case HB_ACODEC_CA_HAAC:
670             case HB_ACODEC_FDK_AAC:
671             case HB_ACODEC_FDK_HAAC:
672                 track->st->codecpar->codec_id = AV_CODEC_ID_AAC;
673 
674                 // libav mkv muxer expects there to be extradata for
675                 // AAC and will crash if it is NULL.
676                 //
677                 // Also, libav can over-read the buffer by up to 8 bytes
678                 // when it fills it's get_bits cache.
679                 //
680                 // So allocate extra bytes
681                 priv_size = audio->priv.config.extradata.length;
682                 priv_data = av_malloc(priv_size + AV_INPUT_BUFFER_PADDING_SIZE);
683                 if (priv_data == NULL)
684                 {
685                     hb_error("AAC extradata: malloc failure");
686                     goto error;
687                 }
688                 memcpy(priv_data,
689                        audio->priv.config.extradata.bytes,
690                        audio->priv.config.extradata.length);
691 
692                 // AAC from pass-through source may be ADTS.
693                 // Therefore inserting "aac_adtstoasc" bitstream filter is
694                 // preferred.
695                 // The filter does nothing for non-ADTS bitstream.
696                 if (audio->config.out.codec == HB_ACODEC_AAC_PASS)
697                 {
698                     const AVBitStreamFilter  * bsf;
699                     AVBSFContext             * ctx;
700                     int                        ret;
701 
702                     bsf = av_bsf_get_by_name("aac_adtstoasc");
703                     ret = av_bsf_alloc(bsf, &ctx);
704                     if (ret < 0)
705                     {
706                         hb_error("AAC bitstream filter: alloc failure");
707                         goto error;
708                     }
709                     ctx->time_base_in.num = 1;
710                     ctx->time_base_in.den = audio->config.out.samplerate;
711                     track->bitstream_context = ctx;
712                 }
713                 break;
714             default:
715                 hb_error("muxavformat: Unknown audio codec: %x",
716                          audio->config.out.codec);
717                 goto error;
718         }
719         track->st->codecpar->extradata = priv_data;
720         track->st->codecpar->extradata_size = priv_size;
721         if (track->bitstream_context != NULL)
722         {
723             int ret;
724 
725             avcodec_parameters_copy(track->bitstream_context->par_in,
726                                     track->st->codecpar);
727             ret = av_bsf_init(track->bitstream_context);
728             if (ret < 0)
729             {
730                 hb_error("bitstream filter: init failure");
731                 goto error;
732             }
733         }
734 
735         if( default_track_flag )
736         {
737             track->st->disposition |= AV_DISPOSITION_DEFAULT;
738             default_track_flag = 0;
739         }
740 
741         lang = lookup_lang_code(job->mux, audio->config.lang.iso639_2 );
742         if (lang != NULL)
743         {
744             av_dict_set(&track->st->metadata, "language", lang, 0);
745         }
746         track->st->codecpar->sample_rate = audio->config.out.samplerate;
747         if (audio->config.out.codec & HB_ACODEC_PASS_FLAG)
748         {
749             track->st->codecpar->channels = av_get_channel_layout_nb_channels(audio->config.in.channel_layout);
750             track->st->codecpar->channel_layout = audio->config.in.channel_layout;
751         }
752         else
753         {
754             track->st->codecpar->channels = hb_mixdown_get_discrete_channel_count(audio->config.out.mixdown);
755             track->st->codecpar->channel_layout = hb_ff_mixdown_xlat(audio->config.out.mixdown, NULL);
756         }
757 
758         const char *name;
759         if (audio->config.out.name == NULL)
760         {
761             switch (track->st->codecpar->channels)
762             {
763                 case 1:
764                     name = "Mono";
765                     break;
766 
767                 case 2:
768                     name = "Stereo";
769                     break;
770 
771                 default:
772                     name = "Surround";
773                     break;
774             }
775         }
776         else
777         {
778             name = audio->config.out.name;
779         }
780         // Set audio track title
781         av_dict_set(&track->st->metadata, "title", name, 0);
782         if (job->mux == HB_MUX_AV_MP4)
783         {
784             // Some software (MPC, mediainfo) use hdlr description
785             // for track title
786             av_dict_set(&track->st->metadata, "handler_name", name, 0);
787         }
788     }
789 
790     // Check for audio track associations
791     for (ii = 0; ii < hb_list_count(job->list_audio); ii++)
792     {
793         audio = hb_list_item(job->list_audio, ii);
794         switch (audio->config.out.codec & HB_ACODEC_MASK)
795         {
796             case HB_ACODEC_FFAAC:
797             case HB_ACODEC_CA_AAC:
798             case HB_ACODEC_CA_HAAC:
799             case HB_ACODEC_FDK_AAC:
800             case HB_ACODEC_FDK_HAAC:
801                 break;
802 
803             default:
804             {
805                 // Mark associated fallback audio tracks for any non-aac track
806                 for(jj = 0; jj < hb_list_count( job->list_audio ); jj++ )
807                 {
808                     hb_audio_t    * fallback;
809                     int             codec;
810 
811                     if (ii == jj) continue;
812 
813                     fallback = hb_list_item( job->list_audio, jj );
814                     codec = fallback->config.out.codec & HB_ACODEC_MASK;
815                     if (fallback->config.in.track == audio->config.in.track &&
816                         (codec == HB_ACODEC_FFAAC ||
817                          codec == HB_ACODEC_CA_AAC ||
818                          codec == HB_ACODEC_CA_HAAC ||
819                          codec == HB_ACODEC_FDK_AAC ||
820                          codec == HB_ACODEC_FDK_HAAC))
821                     {
822                         hb_mux_data_t * fallback_track;
823                         int           * sd;
824 
825                         track = audio->priv.mux_data;
826                         fallback_track = fallback->priv.mux_data;
827                         sd = (int*)av_stream_new_side_data(track->st,
828                                                      AV_PKT_DATA_FALLBACK_TRACK,
829                                                      sizeof(int));
830                         if (sd != NULL)
831                         {
832                             *sd = fallback_track->st->index;
833                         }
834                     }
835                 }
836             } break;
837         }
838     }
839 
840     char * subidx_fmt =
841         "size: %dx%d\n"
842         "org: %d, %d\n"
843         "scale: 100%%, 100%%\n"
844         "alpha: 100%%\n"
845         "smooth: OFF\n"
846         "fadein/out: 50, 50\n"
847         "align: OFF at LEFT TOP\n"
848         "time offset: 0\n"
849         "forced subs: %s\n"
850         "palette: %06x, %06x, %06x, %06x, %06x, %06x, "
851         "%06x, %06x, %06x, %06x, %06x, %06x, %06x, %06x, %06x, %06x\n"
852         "custom colors: OFF, tridx: 0000, "
853         "colors: 000000, 000000, 000000, 000000\n";
854 
855     int subtitle_default = -1;
856     for( ii = 0; ii < hb_list_count( job->list_subtitle ); ii++ )
857     {
858         hb_subtitle_t *subtitle = hb_list_item( job->list_subtitle, ii );
859 
860         if( subtitle->config.dest == PASSTHRUSUB )
861         {
862             if ( subtitle->config.default_track )
863                 subtitle_default = ii;
864         }
865     }
866     // Quicktime requires that at least one subtitle is enabled,
867     // else it doesn't show any of the subtitles.
868     // So check to see if any of the subtitles are flagged to be
869     // the default.  The default will be the enabled track, else
870     // enable the first track.
871     if (job->mux == HB_MUX_AV_MP4 && subtitle_default == -1)
872     {
873         subtitle_default = 0;
874     }
875 
876     for( ii = 0; ii < hb_list_count( job->list_subtitle ); ii++ )
877     {
878         hb_subtitle_t * subtitle;
879         uint32_t        rgb[16];
880         char            subidx[2048];
881         int             len;
882 
883         subtitle = hb_list_item( job->list_subtitle, ii );
884         if (subtitle->config.dest != PASSTHRUSUB)
885             continue;
886 
887         track = m->tracks[m->ntracks++] = calloc(1, sizeof( hb_mux_data_t ) );
888         subtitle->mux_data = track;
889 
890         track->type = MUX_TYPE_SUBTITLE;
891         track->st = avformat_new_stream(m->oc, NULL);
892         if (track->st == NULL)
893         {
894             hb_error("Could not initialize subtitle stream");
895             goto error;
896         }
897 
898         track->st->codecpar->codec_type = AVMEDIA_TYPE_SUBTITLE;
899         track->st->time_base = m->time_base;
900         track->st->codecpar->width = subtitle->width;
901         track->st->codecpar->height = subtitle->height;
902 
903         priv_data = NULL;
904         priv_size = 0;
905         switch (subtitle->source)
906         {
907             case VOBSUB:
908             {
909                 int jj;
910                 track->st->codecpar->codec_id = AV_CODEC_ID_DVD_SUBTITLE;
911 
912                 for (jj = 0; jj < 16; jj++)
913                     rgb[jj] = hb_yuv2rgb(subtitle->palette[jj]);
914                 len = snprintf(subidx, 2048, subidx_fmt,
915                         subtitle->width, subtitle->height,
916                         0, 0, "OFF",
917                         rgb[0], rgb[1], rgb[2], rgb[3],
918                         rgb[4], rgb[5], rgb[6], rgb[7],
919                         rgb[8], rgb[9], rgb[10], rgb[11],
920                         rgb[12], rgb[13], rgb[14], rgb[15]);
921 
922                 priv_size = len + 1;
923                 priv_data = av_malloc(priv_size + AV_INPUT_BUFFER_PADDING_SIZE);
924                 if (priv_data == NULL)
925                 {
926                     hb_error("VOBSUB extradata: malloc failure");
927                     goto error;
928                 }
929                 memcpy(priv_data, subidx, priv_size);
930             } break;
931 
932             case PGSSUB:
933             {
934                 track->st->codecpar->codec_id = AV_CODEC_ID_HDMV_PGS_SUBTITLE;
935             } break;
936 
937             case DVBSUB:
938             {
939                 track->st->codecpar->codec_id = AV_CODEC_ID_DVB_SUBTITLE;
940                 if (subtitle->extradata != NULL)
941                 {
942                     priv_size = subtitle->extradata_size;
943                     priv_data = av_malloc(priv_size + AV_INPUT_BUFFER_PADDING_SIZE);
944                     memcpy(priv_data, subtitle->extradata, priv_size);
945                 }
946             } break;
947 
948             case CC608SUB:
949             case CC708SUB:
950             case TX3GSUB:
951             case UTF8SUB:
952             case SSASUB:
953             case IMPORTSRT:
954             case IMPORTSSA:
955             {
956                 if (job->mux == HB_MUX_AV_MP4)
957                 {
958                     track->st->codecpar->codec_id = AV_CODEC_ID_MOV_TEXT;
959                     track->tx3g = hb_tx3g_style_init(
960                                 job->height, (char*)subtitle->extradata);
961                 }
962                 else
963                 {
964                     track->st->codecpar->codec_id = AV_CODEC_ID_ASS;
965                     need_fonts = 1;
966 
967                     if (subtitle->extradata_size)
968                     {
969                         priv_size = subtitle->extradata_size;
970                         priv_data = av_malloc(priv_size + AV_INPUT_BUFFER_PADDING_SIZE);
971                         if (priv_data == NULL)
972                         {
973                             hb_error("SSA extradata: malloc failure");
974                             goto error;
975                         }
976                         memcpy(priv_data, subtitle->extradata, priv_size);
977                     }
978                 }
979             } break;
980 
981             default:
982                 continue;
983         }
984         if (track->st->codecpar->codec_id == AV_CODEC_ID_MOV_TEXT)
985         {
986             // Build codec extradata for tx3g.
987             // If we were using a libav codec to generate this data
988             // this would (or should) be done for us.
989             uint8_t properties[] = {
990                 0x00, 0x00, 0x00, 0x00,     // Display Flags
991                 0x01,                       // Horiz. Justification
992                 0xff,                       // Vert. Justification
993                 0x00, 0x00, 0x00, 0xff,     // Bg color
994                 0x00, 0x00, 0x00, 0x00,     // Default text box
995                 0x00, 0x00, 0x00, 0x00,
996                 0x00, 0x00, 0x00, 0x00,     // Reserved
997                 0x00, 0x01,                 // Font ID
998                 0x00,                       // Font face
999                 0x18,                       // Font size
1000                 0xff, 0xff, 0xff, 0xff,     // Fg color
1001                 // Font table:
1002                 0x00, 0x00, 0x00, 0x12,     // Font table size
1003                 'f','t','a','b',            // Tag
1004                 0x00, 0x01,                 // Count
1005                 0x00, 0x01,                 // Font ID
1006                 0x05,                       // Font name length
1007                 'A','r','i','a','l'         // Font name
1008             };
1009 
1010             int width, height, font_size;
1011             width     = job->width * job->par.num / job->par.den;
1012             font_size = 0.05 * job->height;
1013             if (font_size < 12)
1014             {
1015                 font_size = 12;
1016             }
1017             else if (font_size > 255)
1018             {
1019                 font_size = 255;
1020             }
1021             properties[25] = font_size;
1022             height = 3 * font_size;
1023             track->st->codecpar->width  = width;
1024             track->st->codecpar->height = height;
1025             properties[14] = height >> 8;
1026             properties[15] = height & 0xff;
1027             properties[16] = width >> 8;
1028             properties[17] = width & 0xff;
1029 
1030             priv_size = sizeof(properties);
1031             priv_data = av_malloc(priv_size + AV_INPUT_BUFFER_PADDING_SIZE);
1032             if (priv_data == NULL)
1033             {
1034                 hb_error("TX3G extradata: malloc failure");
1035                 goto error;
1036             }
1037             memcpy(priv_data, properties, priv_size);
1038         }
1039         track->st->codecpar->extradata = priv_data;
1040         track->st->codecpar->extradata_size = priv_size;
1041 
1042         if (ii == subtitle_default)
1043         {
1044             track->st->disposition |= AV_DISPOSITION_DEFAULT;
1045         }
1046         if (subtitle->config.default_track)
1047         {
1048             track->st->disposition |= AV_DISPOSITION_FORCED;
1049         }
1050 
1051         lang = lookup_lang_code(job->mux, subtitle->iso639_2 );
1052         if (lang != NULL)
1053         {
1054             av_dict_set(&track->st->metadata, "language", lang, 0);
1055         }
1056         if (subtitle->config.name != NULL && subtitle->config.name[0] != 0)
1057         {
1058             // Set subtitle track title
1059             av_dict_set(&track->st->metadata, "title",
1060                         subtitle->config.name, 0);
1061             if (job->mux == HB_MUX_AV_MP4)
1062             {
1063                 // Some software (MPC, mediainfo) use hdlr description
1064                 // for track title
1065                 av_dict_set(&track->st->metadata, "handler_name",
1066                             subtitle->config.name, 0);
1067             }
1068         }
1069     }
1070 
1071     if (need_fonts)
1072     {
1073         hb_list_t * list_attachment = job->list_attachment;
1074         int i;
1075         for ( i = 0; i < hb_list_count(list_attachment); i++ )
1076         {
1077             hb_attachment_t * attachment = hb_list_item( list_attachment, i );
1078 
1079             if ((attachment->type == FONT_TTF_ATTACH || attachment->type == FONT_OTF_ATTACH) &&
1080                 attachment->size > 0)
1081             {
1082                 AVStream *st = avformat_new_stream(m->oc, NULL);
1083                 if (st == NULL)
1084                 {
1085                     hb_error("Could not initialize attachment stream");
1086                     goto error;
1087                 }
1088 
1089                 st->codecpar->codec_type = AVMEDIA_TYPE_ATTACHMENT;
1090                 if (attachment->type == FONT_TTF_ATTACH)
1091                 {
1092                     st->codecpar->codec_id = AV_CODEC_ID_TTF;
1093                 }
1094                 else if (attachment->type == FONT_OTF_ATTACH)
1095                 {
1096                     st->codecpar->codec_id = MKBETAG( 0 ,'O','T','F');
1097                     av_dict_set(&st->metadata, "mimetype", "application/vnd.ms-opentype", 0);
1098                 }
1099 
1100                 priv_size = attachment->size;
1101                 priv_data = av_malloc(priv_size + AV_INPUT_BUFFER_PADDING_SIZE);
1102                 if (priv_data == NULL)
1103                 {
1104                     hb_error("Font extradata: malloc failure");
1105                     goto error;
1106                 }
1107                 memcpy(priv_data, attachment->data, priv_size);
1108 
1109                 st->codecpar->extradata = priv_data;
1110                 st->codecpar->extradata_size = priv_size;
1111 
1112                 av_dict_set(&st->metadata, "filename", attachment->name, 0);
1113             }
1114         }
1115     }
1116 
1117     if( job->metadata && job->metadata->dict )
1118     {
1119         hb_deep_log(2, "Writing Metadata to output file...");
1120         hb_dict_iter_t iter = hb_dict_iter_init(job->metadata->dict);
1121 
1122         while (iter != HB_DICT_ITER_DONE)
1123         {
1124             const char * key;
1125             hb_value_t * val;
1126 
1127             hb_dict_iter_next_ex(job->metadata->dict, &iter, &key, &val);
1128             if (key != NULL && val != NULL)
1129             {
1130                 const char * str = hb_value_get_string(val);
1131 
1132                 if (str != NULL)
1133                 {
1134                     const char * mux_key = lookup_meta_mux_key(meta_mux, key);
1135 
1136                     if (mux_key != NULL)
1137                     {
1138                         av_dict_set(&m->oc->metadata, mux_key, str, 0);
1139                     }
1140                 }
1141             }
1142         }
1143     }
1144 
1145     char tool_string[80];
1146     snprintf(tool_string, sizeof(tool_string), "HandBrake %s %i",
1147              HB_PROJECT_VERSION, HB_PROJECT_BUILD);
1148     av_dict_set(&m->oc->metadata, "encoding_tool", tool_string, 0);
1149     time_t now = time(NULL);
1150     struct tm * now_utc = gmtime(&now);
1151     char now_8601[24];
1152     strftime(now_8601, sizeof(now_8601), "%Y-%m-%dT%H:%M:%SZ", now_utc);
1153     av_dict_set(&m->oc->metadata, "creation_time", now_8601, 0);
1154 
1155     ret = avformat_write_header(m->oc, &av_opts);
1156     if( ret < 0 )
1157     {
1158         av_dict_free( &av_opts );
1159         hb_error( "muxavformat: avformat_write_header failed!");
1160         goto error;
1161     }
1162 
1163     AVDictionaryEntry *t = NULL;
1164     while( ( t = av_dict_get( av_opts, "", t, AV_DICT_IGNORE_SUFFIX ) ) )
1165     {
1166         hb_log( "muxavformat: Unknown option %s", t->key );
1167     }
1168     av_dict_free( &av_opts );
1169 
1170     return 0;
1171 
1172 error:
1173     free(job->mux_data);
1174     job->mux_data = NULL;
1175     avformat_free_context(m->oc);
1176     *job->done_error = HB_ERROR_INIT;
1177     *job->die = 1;
1178     return -1;
1179 }
1180 
add_chapter(hb_mux_object_t * m,int64_t start,int64_t end,char * title)1181 static int add_chapter(hb_mux_object_t *m, int64_t start, int64_t end, char * title)
1182 {
1183     AVChapter *chap;
1184     AVChapter **chapters;
1185     int nchap = m->oc->nb_chapters;
1186 
1187     nchap++;
1188     chapters = av_realloc(m->oc->chapters, nchap * sizeof(AVChapter*));
1189     if (chapters == NULL)
1190     {
1191         hb_error("chapter array: malloc failure");
1192         return -1;
1193     }
1194 
1195     chap = av_mallocz(sizeof(AVChapter));
1196     if (chap == NULL)
1197     {
1198         hb_error("chapter: malloc failure");
1199         return -1;
1200     }
1201 
1202     m->oc->chapters = chapters;
1203     m->oc->chapters[nchap-1] = chap;
1204     m->oc->nb_chapters = nchap;
1205 
1206     chap->id = nchap;
1207     chap->time_base = m->time_base;
1208     // libav does not currently have a good way to deal with chapters and
1209     // delayed stream timestamps.  It makes no corrections to the chapter
1210     // track.  A patch to libav would touch a lot of things, so for now,
1211     // work around the issue here.
1212     chap->start = start;
1213     chap->end = end;
1214     av_dict_set(&chap->metadata, "title", title, 0);
1215 
1216     return 0;
1217 }
1218 
avformatMux(hb_mux_object_t * m,hb_mux_data_t * track,hb_buffer_t * buf)1219 static int avformatMux(hb_mux_object_t *m, hb_mux_data_t *track, hb_buffer_t *buf)
1220 {
1221     int64_t    dts, pts, duration = AV_NOPTS_VALUE;
1222     hb_job_t * job     = m->job;
1223     uint8_t  * sub_out = NULL;
1224 
1225     if (track->type == MUX_TYPE_VIDEO && (job->mux & HB_MUX_MASK_MP4))
1226     {
1227         // compute dts duration for MP4 files
1228         hb_buffer_t * tmp;
1229 
1230         // delay by one frame so that we can compute duration properly.
1231         tmp = track->delay_buf;
1232         track->delay_buf = buf;
1233         buf = tmp;
1234     }
1235     if (buf == NULL)
1236     {
1237         if (job->mux == HB_MUX_AV_MP4 && track->type == MUX_TYPE_SUBTITLE)
1238         {
1239             // Write a final "empty" subtitle to terminate the last
1240             // subtitle that was written
1241             if (track->duration > 0)
1242             {
1243                 uint8_t empty[2] = {0,0};
1244 
1245                 m->empty_pkt->data = empty;
1246                 m->empty_pkt->size = 2;
1247                 m->empty_pkt->dts = track->duration;
1248                 m->empty_pkt->pts = track->duration;
1249                 m->empty_pkt->duration = 90;
1250                 m->empty_pkt->stream_index = track->st->index;
1251                 av_interleaved_write_frame(m->oc, m->empty_pkt);
1252                 av_packet_unref(m->empty_pkt);
1253             }
1254         }
1255         return 0;
1256     }
1257 
1258     if (track->type == MUX_TYPE_VIDEO &&
1259         (job->mux & (HB_MUX_MASK_MKV | HB_MUX_MASK_WEBM)) &&
1260         buf->s.renderOffset < 0)
1261     {
1262         // libav matroska muxer doesn't write dts to the output, but
1263         // if it sees a negative dts, it applies an offset to both pts
1264         // and dts to make it positive.  This offset breaks chapter
1265         // start times and A/V sync.  libav also requires that dts is
1266         // "monotonically increasing", which means it last_dts <= next_dts.
1267         // It also uses dts to determine track interleaving, so we need
1268         // to provide some reasonable dts value.
1269         // So when renderOffset < 0, set to 0 for mkv.
1270         buf->s.renderOffset = 0;
1271         // Note: for MP4, libav allows negative dts and creates an edts
1272         // (edit list) entry in this case.
1273     }
1274     if (buf->s.renderOffset == AV_NOPTS_VALUE)
1275     {
1276         dts = av_rescale_q(buf->s.start, (AVRational){1,90000},
1277                            track->st->time_base);
1278     }
1279     else
1280     {
1281         dts = av_rescale_q(buf->s.renderOffset, (AVRational){1,90000},
1282                            track->st->time_base);
1283     }
1284 
1285     pts = av_rescale_q(buf->s.start, (AVRational){1,90000},
1286                        track->st->time_base);
1287 
1288     if (track->type == MUX_TYPE_VIDEO && track->delay_buf != NULL)
1289     {
1290         int64_t delayed_dts;
1291         delayed_dts = av_rescale_q(track->delay_buf->s.renderOffset,
1292                                    (AVRational){1,90000},
1293                                    track->st->time_base);
1294         duration = delayed_dts - dts;
1295     }
1296     if (duration < 0 && buf->s.duration > 0)
1297     {
1298         duration = av_rescale_q(buf->s.duration, (AVRational){1,90000},
1299                                 track->st->time_base);
1300     }
1301     if (duration < 0)
1302     {
1303         // There is a possibility that some subtitles get through the pipeline
1304         // without ever discovering their true duration.  Make the duration
1305         // 10 seconds in this case. Unless they are PGS subs which should
1306         // have zero duration.
1307         if (track->type == MUX_TYPE_SUBTITLE &&
1308             track->st->codecpar->codec_id != AV_CODEC_ID_HDMV_PGS_SUBTITLE)
1309         {
1310             duration = av_rescale_q(10, (AVRational){1,1},
1311                                     track->st->time_base);
1312         }
1313         else if (track->type == MUX_TYPE_VIDEO)
1314         {
1315             duration = av_rescale_q(
1316                             (int64_t)job->vrate.den * 90000 / job->vrate.num,
1317                             (AVRational){1,90000}, track->st->time_base);
1318         }
1319         else
1320         {
1321             duration = 0;
1322         }
1323     }
1324 
1325     m->pkt->data = buf->data;
1326     m->pkt->size = buf->size;
1327     m->pkt->dts = dts;
1328     m->pkt->pts = pts;
1329     m->pkt->duration = duration;
1330 
1331     if (track->type == MUX_TYPE_VIDEO)
1332     {
1333         if ((buf->s.frametype == HB_FRAME_IDR) ||
1334             (buf->s.flags & HB_FLAG_FRAMETYPE_KEY))
1335         {
1336             m->pkt->flags |= AV_PKT_FLAG_KEY;
1337         }
1338 #ifdef AV_PKT_FLAG_DISPOSABLE
1339         if (!(buf->s.flags & HB_FLAG_FRAMETYPE_REF))
1340         {
1341             m->pkt->flags |= AV_PKT_FLAG_DISPOSABLE;
1342         }
1343 #endif
1344     }
1345     else if (buf->s.frametype & HB_FRAME_MASK_KEY)
1346     {
1347         m->pkt->flags |= AV_PKT_FLAG_KEY;
1348     }
1349 
1350     switch (track->type)
1351     {
1352         case MUX_TYPE_VIDEO:
1353         {
1354             if (job->chapter_markers && buf->s.new_chap)
1355             {
1356                 if (track->current_chapter > 0)
1357                 {
1358                     hb_chapter_t *chapter;
1359 
1360                     // reached chapter N, write marker for chapter N-1
1361                     // we don't know the end time of chapter N-1 till we receive
1362                     // chapter N.  So we are always writing the previous chapter
1363                     // mark.
1364                     // chapter numbers start at 1, but the list starts at 0
1365                     chapter = hb_list_item(job->list_chapter,
1366                                            track->current_chapter - 1);
1367 
1368                     // make sure we're not writing a chapter that has 0 length
1369                     if (chapter != NULL &&
1370                         track->prev_chapter_tc != AV_NOPTS_VALUE &&
1371                         track->prev_chapter_tc < m->pkt->pts)
1372                     {
1373                         char title[1024];
1374                         if (chapter->title != NULL)
1375                         {
1376                             snprintf(title, 1023, "%s", chapter->title);
1377                         }
1378                         else
1379                         {
1380                             snprintf(title, 1023, "Chapter %d",
1381                                      track->current_chapter);
1382                         }
1383                         add_chapter(m, track->prev_chapter_tc, m->pkt->pts, title);
1384                     }
1385                 }
1386                 track->current_chapter = buf->s.new_chap;
1387                 track->prev_chapter_tc = m->pkt->pts;
1388             }
1389         } break;
1390 
1391         case MUX_TYPE_SUBTITLE:
1392         {
1393             if (job->mux == HB_MUX_AV_MP4)
1394             {
1395                 /* Write an empty sample */
1396                 if ( track->duration < pts )
1397                 {
1398                     uint8_t empty[2] = {0,0};
1399 
1400                     m->empty_pkt->data = empty;
1401                     m->empty_pkt->size = 2;
1402                     m->empty_pkt->dts = track->duration;
1403                     m->empty_pkt->pts = track->duration;
1404                     m->empty_pkt->duration = pts - track->duration;
1405                     m->empty_pkt->stream_index = track->st->index;
1406                     int ret = av_interleaved_write_frame(m->oc, m->empty_pkt);
1407                     av_packet_unref(m->empty_pkt);
1408                     if (ret < 0)
1409                     {
1410                         char errstr[64];
1411                         av_strerror(ret, errstr, sizeof(errstr));
1412                         hb_error("avformatMux: track %d, av_interleaved_write_frame failed with error '%s' (empty_pkt)",
1413                                  track->st->index, errstr);
1414                         *job->done_error = HB_ERROR_UNKNOWN;
1415                         *job->die = 1;
1416                         return -1;
1417                     }
1418                 }
1419                 if (track->st->codecpar->codec_id == AV_CODEC_ID_MOV_TEXT)
1420                 {
1421                     uint8_t  * styleatom;
1422                     uint16_t   stylesize = 0;
1423                     uint8_t  * buffer;
1424                     uint16_t   buffersize = 0;
1425 
1426                     /*
1427                      * Copy the subtitle into buffer stripping markup and
1428                      * creating style atoms for them.
1429                      */
1430                     hb_muxmp4_process_subtitle_style(
1431                         track->tx3g, buf->data, &buffer,
1432                         &styleatom, &stylesize);
1433 
1434                     if (buffer != NULL)
1435                     {
1436                         buffersize = strlen((char*)buffer);
1437                         if (styleatom == NULL)
1438                         {
1439                             stylesize = 0;
1440                         }
1441                         sub_out = malloc(2 + buffersize + stylesize);
1442 
1443                         /* Write the subtitle sample */
1444                         memcpy(sub_out + 2, buffer, buffersize);
1445                         memcpy(sub_out + 2 + buffersize, styleatom, stylesize);
1446                         sub_out[0] = (buffersize >> 8) & 0xff;
1447                         sub_out[1] = buffersize & 0xff;
1448                         m->pkt->data = sub_out;
1449                         m->pkt->size = buffersize + stylesize + 2;
1450                     }
1451                     free(buffer);
1452                     free(styleatom);
1453                 }
1454             }
1455             if (m->pkt->data == NULL)
1456             {
1457                 // Memory allocation failure!
1458                 hb_error("avformatMux: subtitle memory allocation failure");
1459                 *job->done_error = HB_ERROR_UNKNOWN;
1460                 *job->die = 1;
1461                 return -1;
1462             }
1463         } break;
1464         case MUX_TYPE_AUDIO:
1465         default:
1466             break;
1467     }
1468     track->duration = pts + m->pkt->duration;
1469 
1470     if (track->bitstream_context)
1471     {
1472         int ret;
1473         ret = av_bsf_send_packet(track->bitstream_context, m->pkt);
1474         if (ret < 0)
1475         {
1476             hb_error("avformatMux: track %d av_bsf_send_packet failed",
1477                      track->st->index);
1478             return ret;
1479         }
1480         ret = av_bsf_receive_packet(track->bitstream_context, m->pkt);
1481         if (ret == AVERROR(EAGAIN) || ret == AVERROR_EOF)
1482         {
1483             return 0;
1484         }
1485         else if (ret < 0)
1486         {
1487             hb_error("avformatMux: track %d av_bsf_receive_packet failed",
1488                      track->st->index);
1489             return ret;
1490         }
1491     }
1492 
1493     m->pkt->stream_index = track->st->index;
1494     int ret = av_interleaved_write_frame(m->oc, m->pkt);
1495     av_packet_unref(m->pkt);
1496     if (sub_out != NULL)
1497     {
1498         free(sub_out);
1499     }
1500     // Many avformat muxer functions do not check the error status
1501     // of the AVIOContext.  So we need to check it ourselves to detect
1502     // write errors (like disk full condition).
1503     if (ret < 0 || m->oc->pb->error != 0)
1504     {
1505         char errstr[64];
1506         av_strerror(ret < 0 ? ret : m->oc->pb->error, errstr, sizeof(errstr));
1507         hb_error("avformatMux: track %d, av_interleaved_write_frame failed with error '%s'",
1508                  track->st->index, errstr);
1509         *job->done_error = HB_ERROR_UNKNOWN;
1510         *job->die = 1;
1511         return -1;
1512     }
1513 
1514     hb_buffer_close( &buf );
1515     return 0;
1516 }
1517 
avformatEnd(hb_mux_object_t * m)1518 static int avformatEnd(hb_mux_object_t *m)
1519 {
1520     hb_job_t *job           = m->job;
1521     hb_mux_data_t *track = job->mux_data;
1522 
1523     if( !job->mux_data )
1524     {
1525         /*
1526          * We must have failed to create the file in the first place.
1527          */
1528         return 0;
1529     }
1530 
1531     // Flush any delayed frames
1532     int ii;
1533     for (ii = 0; ii < m->ntracks; ii++)
1534     {
1535         avformatMux(m, m->tracks[ii], NULL);
1536 
1537         if (m->tracks[ii]->bitstream_context)
1538         {
1539             av_bsf_free(&m->tracks[ii]->bitstream_context);
1540         }
1541         if (m->tracks[ii]->tx3g)
1542         {
1543             hb_tx3g_style_close(&m->tracks[ii]->tx3g);
1544         }
1545     }
1546 
1547     if (job->chapter_markers)
1548     {
1549         hb_chapter_t *chapter;
1550 
1551         // get the last chapter
1552         chapter = hb_list_item(job->list_chapter, track->current_chapter - 1);
1553 
1554         // only write the last chapter marker if it lasts at least 1.5 second
1555         if (chapter != NULL && chapter->duration > 135000LL)
1556         {
1557             char title[1024];
1558             if (chapter->title != NULL)
1559             {
1560                 snprintf(title, 1023, "%s", chapter->title);
1561             }
1562             else
1563             {
1564                 snprintf(title, 1023, "Chapter %d", track->current_chapter);
1565             }
1566             add_chapter(m, track->prev_chapter_tc, track->duration, title);
1567         }
1568     }
1569 
1570     // Update and track private data that can change during
1571     // encode.
1572     for(ii = 0; ii < hb_list_count( job->list_audio ); ii++)
1573     {
1574         AVStream *st;
1575         hb_audio_t    * audio;
1576 
1577         audio = hb_list_item(job->list_audio, ii);
1578         st = audio->priv.mux_data->st;
1579 
1580         switch (audio->config.out.codec & HB_ACODEC_MASK)
1581         {
1582             case HB_ACODEC_FFFLAC:
1583             case HB_ACODEC_FFFLAC24:
1584                 if( audio->priv.config.extradata.length )
1585                 {
1586                     uint8_t *priv_data;
1587                     int priv_size;
1588 
1589                     priv_size = audio->priv.config.extradata.length;
1590                     priv_data = av_realloc(st->codecpar->extradata, priv_size +
1591                                            AV_INPUT_BUFFER_PADDING_SIZE);
1592                     if (priv_data == NULL)
1593                     {
1594                         break;
1595                     }
1596                     memcpy(priv_data,
1597                            audio->priv.config.extradata.bytes,
1598                            audio->priv.config.extradata.length);
1599                     st->codecpar->extradata = priv_data;
1600                     st->codecpar->extradata_size = priv_size;
1601                 }
1602                 break;
1603             default:
1604                 break;
1605         }
1606     }
1607 
1608     av_write_trailer(m->oc);
1609     avio_close(m->oc->pb);
1610     avformat_free_context(m->oc);
1611     av_packet_free(&m->pkt);
1612     av_packet_free(&m->empty_pkt);
1613     free(m->tracks);
1614     m->oc = NULL;
1615 
1616     return 0;
1617 }
1618 
hb_mux_avformat_init(hb_job_t * job)1619 hb_mux_object_t * hb_mux_avformat_init( hb_job_t * job )
1620 {
1621     hb_mux_object_t * m = calloc( sizeof( hb_mux_object_t ), 1 );
1622     m->init      = avformatInit;
1623     m->mux       = avformatMux;
1624     m->end       = avformatEnd;
1625     m->job       = job;
1626     return m;
1627 }
1628