]> git.sesse.net Git - ffmpeg/blob - ffmpeg_opt.c
Merge commit '4843a9c74f77f5eb8d2b1ee648fe2ac6e2a48ec3'
[ffmpeg] / ffmpeg_opt.c
1 /*
2  * ffmpeg option parsing
3  *
4  * This file is part of FFmpeg.
5  *
6  * FFmpeg is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2.1 of the License, or (at your option) any later version.
10  *
11  * FFmpeg is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with FFmpeg; if not, write to the Free Software
18  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
19  */
20
21 #include <stdint.h>
22
23 #include "ffmpeg.h"
24 #include "cmdutils.h"
25
26 #include "libavformat/avformat.h"
27
28 #include "libavcodec/avcodec.h"
29
30 #include "libavfilter/avfilter.h"
31
32 #include "libavutil/avassert.h"
33 #include "libavutil/avstring.h"
34 #include "libavutil/avutil.h"
35 #include "libavutil/channel_layout.h"
36 #include "libavutil/intreadwrite.h"
37 #include "libavutil/fifo.h"
38 #include "libavutil/mathematics.h"
39 #include "libavutil/opt.h"
40 #include "libavutil/parseutils.h"
41 #include "libavutil/pixdesc.h"
42 #include "libavutil/pixfmt.h"
43
44 #define MATCH_PER_STREAM_OPT(name, type, outvar, fmtctx, st)\
45 {\
46     int i, ret;\
47     for (i = 0; i < o->nb_ ## name; i++) {\
48         char *spec = o->name[i].specifier;\
49         if ((ret = check_stream_specifier(fmtctx, st, spec)) > 0)\
50             outvar = o->name[i].u.type;\
51         else if (ret < 0)\
52             exit_program(1);\
53     }\
54 }
55
56 #define MATCH_PER_TYPE_OPT(name, type, outvar, fmtctx, mediatype)\
57 {\
58     int i;\
59     for (i = 0; i < o->nb_ ## name; i++) {\
60         char *spec = o->name[i].specifier;\
61         if (!strcmp(spec, mediatype))\
62             outvar = o->name[i].u.type;\
63     }\
64 }
65
66 const HWAccel hwaccels[] = {
67 #if HAVE_VDPAU_X11
68     { "vdpau", vdpau_init, HWACCEL_VDPAU, AV_PIX_FMT_VDPAU },
69 #endif
70 #if HAVE_DXVA2_LIB
71     { "dxva2", dxva2_init, HWACCEL_DXVA2, AV_PIX_FMT_DXVA2_VLD },
72 #endif
73 #if CONFIG_VDA
74     { "vda",   vda_init,   HWACCEL_VDA,   AV_PIX_FMT_VDA },
75 #endif
76     { 0 },
77 };
78
79 char *vstats_filename;
80
81 float audio_drift_threshold = 0.1;
82 float dts_delta_threshold   = 10;
83 float dts_error_threshold   = 3600*30;
84
85 int audio_volume      = 256;
86 int audio_sync_method = 0;
87 int video_sync_method = VSYNC_AUTO;
88 int do_deinterlace    = 0;
89 int do_benchmark      = 0;
90 int do_benchmark_all  = 0;
91 int do_hex_dump       = 0;
92 int do_pkt_dump       = 0;
93 int copy_ts           = 0;
94 int start_at_zero     = 0;
95 int copy_tb           = -1;
96 int debug_ts          = 0;
97 int exit_on_error     = 0;
98 int print_stats       = -1;
99 int qp_hist           = 0;
100 int stdin_interaction = 1;
101 int frame_bits_per_raw_sample = 0;
102 float max_error_rate  = 2.0/3;
103
104
105 static int intra_only         = 0;
106 static int file_overwrite     = 0;
107 static int no_file_overwrite  = 0;
108 static int do_psnr            = 0;
109 static int input_sync;
110 static int override_ffserver  = 0;
111
112 static void uninit_options(OptionsContext *o)
113 {
114     const OptionDef *po = options;
115     int i;
116
117     /* all OPT_SPEC and OPT_STRING can be freed in generic way */
118     while (po->name) {
119         void *dst = (uint8_t*)o + po->u.off;
120
121         if (po->flags & OPT_SPEC) {
122             SpecifierOpt **so = dst;
123             int i, *count = (int*)(so + 1);
124             for (i = 0; i < *count; i++) {
125                 av_freep(&(*so)[i].specifier);
126                 if (po->flags & OPT_STRING)
127                     av_freep(&(*so)[i].u.str);
128             }
129             av_freep(so);
130             *count = 0;
131         } else if (po->flags & OPT_OFFSET && po->flags & OPT_STRING)
132             av_freep(dst);
133         po++;
134     }
135
136     for (i = 0; i < o->nb_stream_maps; i++)
137         av_freep(&o->stream_maps[i].linklabel);
138     av_freep(&o->stream_maps);
139     av_freep(&o->audio_channel_maps);
140     av_freep(&o->streamid_map);
141     av_freep(&o->attachments);
142 }
143
144 static void init_options(OptionsContext *o)
145 {
146     memset(o, 0, sizeof(*o));
147
148     o->stop_time = INT64_MAX;
149     o->mux_max_delay  = 0.7;
150     o->start_time     = AV_NOPTS_VALUE;
151     o->recording_time = INT64_MAX;
152     o->limit_filesize = UINT64_MAX;
153     o->chapters_input_file = INT_MAX;
154     o->accurate_seek  = 1;
155 }
156
157 /* return a copy of the input with the stream specifiers removed from the keys */
158 static AVDictionary *strip_specifiers(AVDictionary *dict)
159 {
160     AVDictionaryEntry *e = NULL;
161     AVDictionary    *ret = NULL;
162
163     while ((e = av_dict_get(dict, "", e, AV_DICT_IGNORE_SUFFIX))) {
164         char *p = strchr(e->key, ':');
165
166         if (p)
167             *p = 0;
168         av_dict_set(&ret, e->key, e->value, 0);
169         if (p)
170             *p = ':';
171     }
172     return ret;
173 }
174
175 static int opt_sameq(void *optctx, const char *opt, const char *arg)
176 {
177     av_log(NULL, AV_LOG_ERROR, "Option '%s' was removed. "
178            "If you are looking for an option to preserve the quality (which is not "
179            "what -%s was for), use -qscale 0 or an equivalent quality factor option.\n",
180            opt, opt);
181     return AVERROR(EINVAL);
182 }
183
184 static int opt_video_channel(void *optctx, const char *opt, const char *arg)
185 {
186     av_log(NULL, AV_LOG_WARNING, "This option is deprecated, use -channel.\n");
187     return opt_default(optctx, "channel", arg);
188 }
189
190 static int opt_video_standard(void *optctx, const char *opt, const char *arg)
191 {
192     av_log(NULL, AV_LOG_WARNING, "This option is deprecated, use -standard.\n");
193     return opt_default(optctx, "standard", arg);
194 }
195
196 static int opt_audio_codec(void *optctx, const char *opt, const char *arg)
197 {
198     OptionsContext *o = optctx;
199     return parse_option(o, "codec:a", arg, options);
200 }
201
202 static int opt_video_codec(void *optctx, const char *opt, const char *arg)
203 {
204     OptionsContext *o = optctx;
205     return parse_option(o, "codec:v", arg, options);
206 }
207
208 static int opt_subtitle_codec(void *optctx, const char *opt, const char *arg)
209 {
210     OptionsContext *o = optctx;
211     return parse_option(o, "codec:s", arg, options);
212 }
213
214 static int opt_data_codec(void *optctx, const char *opt, const char *arg)
215 {
216     OptionsContext *o = optctx;
217     return parse_option(o, "codec:d", arg, options);
218 }
219
220 static int opt_map(void *optctx, const char *opt, const char *arg)
221 {
222     OptionsContext *o = optctx;
223     StreamMap *m = NULL;
224     int i, negative = 0, file_idx;
225     int sync_file_idx = -1, sync_stream_idx = 0;
226     char *p, *sync;
227     char *map;
228
229     if (*arg == '-') {
230         negative = 1;
231         arg++;
232     }
233     map = av_strdup(arg);
234
235     /* parse sync stream first, just pick first matching stream */
236     if (sync = strchr(map, ',')) {
237         *sync = 0;
238         sync_file_idx = strtol(sync + 1, &sync, 0);
239         if (sync_file_idx >= nb_input_files || sync_file_idx < 0) {
240             av_log(NULL, AV_LOG_FATAL, "Invalid sync file index: %d.\n", sync_file_idx);
241             exit_program(1);
242         }
243         if (*sync)
244             sync++;
245         for (i = 0; i < input_files[sync_file_idx]->nb_streams; i++)
246             if (check_stream_specifier(input_files[sync_file_idx]->ctx,
247                                        input_files[sync_file_idx]->ctx->streams[i], sync) == 1) {
248                 sync_stream_idx = i;
249                 break;
250             }
251         if (i == input_files[sync_file_idx]->nb_streams) {
252             av_log(NULL, AV_LOG_FATAL, "Sync stream specification in map %s does not "
253                                        "match any streams.\n", arg);
254             exit_program(1);
255         }
256     }
257
258
259     if (map[0] == '[') {
260         /* this mapping refers to lavfi output */
261         const char *c = map + 1;
262         GROW_ARRAY(o->stream_maps, o->nb_stream_maps);
263         m = &o->stream_maps[o->nb_stream_maps - 1];
264         m->linklabel = av_get_token(&c, "]");
265         if (!m->linklabel) {
266             av_log(NULL, AV_LOG_ERROR, "Invalid output link label: %s.\n", map);
267             exit_program(1);
268         }
269     } else {
270         file_idx = strtol(map, &p, 0);
271         if (file_idx >= nb_input_files || file_idx < 0) {
272             av_log(NULL, AV_LOG_FATAL, "Invalid input file index: %d.\n", file_idx);
273             exit_program(1);
274         }
275         if (negative)
276             /* disable some already defined maps */
277             for (i = 0; i < o->nb_stream_maps; i++) {
278                 m = &o->stream_maps[i];
279                 if (file_idx == m->file_index &&
280                     check_stream_specifier(input_files[m->file_index]->ctx,
281                                            input_files[m->file_index]->ctx->streams[m->stream_index],
282                                            *p == ':' ? p + 1 : p) > 0)
283                     m->disabled = 1;
284             }
285         else
286             for (i = 0; i < input_files[file_idx]->nb_streams; i++) {
287                 if (check_stream_specifier(input_files[file_idx]->ctx, input_files[file_idx]->ctx->streams[i],
288                             *p == ':' ? p + 1 : p) <= 0)
289                     continue;
290                 GROW_ARRAY(o->stream_maps, o->nb_stream_maps);
291                 m = &o->stream_maps[o->nb_stream_maps - 1];
292
293                 m->file_index   = file_idx;
294                 m->stream_index = i;
295
296                 if (sync_file_idx >= 0) {
297                     m->sync_file_index   = sync_file_idx;
298                     m->sync_stream_index = sync_stream_idx;
299                 } else {
300                     m->sync_file_index   = file_idx;
301                     m->sync_stream_index = i;
302                 }
303             }
304     }
305
306     if (!m) {
307         av_log(NULL, AV_LOG_FATAL, "Stream map '%s' matches no streams.\n", arg);
308         exit_program(1);
309     }
310
311     av_freep(&map);
312     return 0;
313 }
314
315 static int opt_attach(void *optctx, const char *opt, const char *arg)
316 {
317     OptionsContext *o = optctx;
318     GROW_ARRAY(o->attachments, o->nb_attachments);
319     o->attachments[o->nb_attachments - 1] = arg;
320     return 0;
321 }
322
323 static int opt_map_channel(void *optctx, const char *opt, const char *arg)
324 {
325     OptionsContext *o = optctx;
326     int n;
327     AVStream *st;
328     AudioChannelMap *m;
329
330     GROW_ARRAY(o->audio_channel_maps, o->nb_audio_channel_maps);
331     m = &o->audio_channel_maps[o->nb_audio_channel_maps - 1];
332
333     /* muted channel syntax */
334     n = sscanf(arg, "%d:%d.%d", &m->channel_idx, &m->ofile_idx, &m->ostream_idx);
335     if ((n == 1 || n == 3) && m->channel_idx == -1) {
336         m->file_idx = m->stream_idx = -1;
337         if (n == 1)
338             m->ofile_idx = m->ostream_idx = -1;
339         return 0;
340     }
341
342     /* normal syntax */
343     n = sscanf(arg, "%d.%d.%d:%d.%d",
344                &m->file_idx,  &m->stream_idx, &m->channel_idx,
345                &m->ofile_idx, &m->ostream_idx);
346
347     if (n != 3 && n != 5) {
348         av_log(NULL, AV_LOG_FATAL, "Syntax error, mapchan usage: "
349                "[file.stream.channel|-1][:syncfile:syncstream]\n");
350         exit_program(1);
351     }
352
353     if (n != 5) // only file.stream.channel specified
354         m->ofile_idx = m->ostream_idx = -1;
355
356     /* check input */
357     if (m->file_idx < 0 || m->file_idx >= nb_input_files) {
358         av_log(NULL, AV_LOG_FATAL, "mapchan: invalid input file index: %d\n",
359                m->file_idx);
360         exit_program(1);
361     }
362     if (m->stream_idx < 0 ||
363         m->stream_idx >= input_files[m->file_idx]->nb_streams) {
364         av_log(NULL, AV_LOG_FATAL, "mapchan: invalid input file stream index #%d.%d\n",
365                m->file_idx, m->stream_idx);
366         exit_program(1);
367     }
368     st = input_files[m->file_idx]->ctx->streams[m->stream_idx];
369     if (st->codec->codec_type != AVMEDIA_TYPE_AUDIO) {
370         av_log(NULL, AV_LOG_FATAL, "mapchan: stream #%d.%d is not an audio stream.\n",
371                m->file_idx, m->stream_idx);
372         exit_program(1);
373     }
374     if (m->channel_idx < 0 || m->channel_idx >= st->codec->channels) {
375         av_log(NULL, AV_LOG_FATAL, "mapchan: invalid audio channel #%d.%d.%d\n",
376                m->file_idx, m->stream_idx, m->channel_idx);
377         exit_program(1);
378     }
379     return 0;
380 }
381
382 /**
383  * Parse a metadata specifier passed as 'arg' parameter.
384  * @param arg  metadata string to parse
385  * @param type metadata type is written here -- g(lobal)/s(tream)/c(hapter)/p(rogram)
386  * @param index for type c/p, chapter/program index is written here
387  * @param stream_spec for type s, the stream specifier is written here
388  */
389 static void parse_meta_type(char *arg, char *type, int *index, const char **stream_spec)
390 {
391     if (*arg) {
392         *type = *arg;
393         switch (*arg) {
394         case 'g':
395             break;
396         case 's':
397             if (*(++arg) && *arg != ':') {
398                 av_log(NULL, AV_LOG_FATAL, "Invalid metadata specifier %s.\n", arg);
399                 exit_program(1);
400             }
401             *stream_spec = *arg == ':' ? arg + 1 : "";
402             break;
403         case 'c':
404         case 'p':
405             if (*(++arg) == ':')
406                 *index = strtol(++arg, NULL, 0);
407             break;
408         default:
409             av_log(NULL, AV_LOG_FATAL, "Invalid metadata type %c.\n", *arg);
410             exit_program(1);
411         }
412     } else
413         *type = 'g';
414 }
415
416 static int copy_metadata(char *outspec, char *inspec, AVFormatContext *oc, AVFormatContext *ic, OptionsContext *o)
417 {
418     AVDictionary **meta_in = NULL;
419     AVDictionary **meta_out = NULL;
420     int i, ret = 0;
421     char type_in, type_out;
422     const char *istream_spec = NULL, *ostream_spec = NULL;
423     int idx_in = 0, idx_out = 0;
424
425     parse_meta_type(inspec,  &type_in,  &idx_in,  &istream_spec);
426     parse_meta_type(outspec, &type_out, &idx_out, &ostream_spec);
427
428     if (!ic) {
429         if (type_out == 'g' || !*outspec)
430             o->metadata_global_manual = 1;
431         if (type_out == 's' || !*outspec)
432             o->metadata_streams_manual = 1;
433         if (type_out == 'c' || !*outspec)
434             o->metadata_chapters_manual = 1;
435         return 0;
436     }
437
438     if (type_in == 'g' || type_out == 'g')
439         o->metadata_global_manual = 1;
440     if (type_in == 's' || type_out == 's')
441         o->metadata_streams_manual = 1;
442     if (type_in == 'c' || type_out == 'c')
443         o->metadata_chapters_manual = 1;
444
445     /* ic is NULL when just disabling automatic mappings */
446     if (!ic)
447         return 0;
448
449 #define METADATA_CHECK_INDEX(index, nb_elems, desc)\
450     if ((index) < 0 || (index) >= (nb_elems)) {\
451         av_log(NULL, AV_LOG_FATAL, "Invalid %s index %d while processing metadata maps.\n",\
452                 (desc), (index));\
453         exit_program(1);\
454     }
455
456 #define SET_DICT(type, meta, context, index)\
457         switch (type) {\
458         case 'g':\
459             meta = &context->metadata;\
460             break;\
461         case 'c':\
462             METADATA_CHECK_INDEX(index, context->nb_chapters, "chapter")\
463             meta = &context->chapters[index]->metadata;\
464             break;\
465         case 'p':\
466             METADATA_CHECK_INDEX(index, context->nb_programs, "program")\
467             meta = &context->programs[index]->metadata;\
468             break;\
469         case 's':\
470             break; /* handled separately below */ \
471         default: av_assert0(0);\
472         }\
473
474     SET_DICT(type_in, meta_in, ic, idx_in);
475     SET_DICT(type_out, meta_out, oc, idx_out);
476
477     /* for input streams choose first matching stream */
478     if (type_in == 's') {
479         for (i = 0; i < ic->nb_streams; i++) {
480             if ((ret = check_stream_specifier(ic, ic->streams[i], istream_spec)) > 0) {
481                 meta_in = &ic->streams[i]->metadata;
482                 break;
483             } else if (ret < 0)
484                 exit_program(1);
485         }
486         if (!meta_in) {
487             av_log(NULL, AV_LOG_FATAL, "Stream specifier %s does not match  any streams.\n", istream_spec);
488             exit_program(1);
489         }
490     }
491
492     if (type_out == 's') {
493         for (i = 0; i < oc->nb_streams; i++) {
494             if ((ret = check_stream_specifier(oc, oc->streams[i], ostream_spec)) > 0) {
495                 meta_out = &oc->streams[i]->metadata;
496                 av_dict_copy(meta_out, *meta_in, AV_DICT_DONT_OVERWRITE);
497             } else if (ret < 0)
498                 exit_program(1);
499         }
500     } else
501         av_dict_copy(meta_out, *meta_in, AV_DICT_DONT_OVERWRITE);
502
503     return 0;
504 }
505
506 static int opt_recording_timestamp(void *optctx, const char *opt, const char *arg)
507 {
508     OptionsContext *o = optctx;
509     char buf[128];
510     int64_t recording_timestamp = parse_time_or_die(opt, arg, 0) / 1E6;
511     struct tm time = *gmtime((time_t*)&recording_timestamp);
512     if (!strftime(buf, sizeof(buf), "creation_time=%FT%T%z", &time))
513         return -1;
514     parse_option(o, "metadata", buf, options);
515
516     av_log(NULL, AV_LOG_WARNING, "%s is deprecated, set the 'creation_time' metadata "
517                                  "tag instead.\n", opt);
518     return 0;
519 }
520
521 static AVCodec *find_codec_or_die(const char *name, enum AVMediaType type, int encoder)
522 {
523     const AVCodecDescriptor *desc;
524     const char *codec_string = encoder ? "encoder" : "decoder";
525     AVCodec *codec;
526
527     codec = encoder ?
528         avcodec_find_encoder_by_name(name) :
529         avcodec_find_decoder_by_name(name);
530
531     if (!codec && (desc = avcodec_descriptor_get_by_name(name))) {
532         codec = encoder ? avcodec_find_encoder(desc->id) :
533                           avcodec_find_decoder(desc->id);
534         if (codec)
535             av_log(NULL, AV_LOG_VERBOSE, "Matched %s '%s' for codec '%s'.\n",
536                    codec_string, codec->name, desc->name);
537     }
538
539     if (!codec) {
540         av_log(NULL, AV_LOG_FATAL, "Unknown %s '%s'\n", codec_string, name);
541         exit_program(1);
542     }
543     if (codec->type != type) {
544         av_log(NULL, AV_LOG_FATAL, "Invalid %s type '%s'\n", codec_string, name);
545         exit_program(1);
546     }
547     return codec;
548 }
549
550 static AVCodec *choose_decoder(OptionsContext *o, AVFormatContext *s, AVStream *st)
551 {
552     char *codec_name = NULL;
553
554     MATCH_PER_STREAM_OPT(codec_names, str, codec_name, s, st);
555     if (codec_name) {
556         AVCodec *codec = find_codec_or_die(codec_name, st->codec->codec_type, 0);
557         st->codec->codec_id = codec->id;
558         return codec;
559     } else
560         return avcodec_find_decoder(st->codec->codec_id);
561 }
562
563 /* Add all the streams from the given input file to the global
564  * list of input streams. */
565 static void add_input_streams(OptionsContext *o, AVFormatContext *ic)
566 {
567     int i, ret;
568
569     for (i = 0; i < ic->nb_streams; i++) {
570         AVStream *st = ic->streams[i];
571         AVCodecContext *dec = st->codec;
572         InputStream *ist = av_mallocz(sizeof(*ist));
573         char *framerate = NULL, *hwaccel = NULL, *hwaccel_device = NULL;
574         char *codec_tag = NULL;
575         char *next;
576         char *discard_str = NULL;
577         const AVOption *discard_opt = av_opt_find(dec, "skip_frame", NULL, 0, 0);
578
579         if (!ist)
580             exit_program(1);
581
582         GROW_ARRAY(input_streams, nb_input_streams);
583         input_streams[nb_input_streams - 1] = ist;
584
585         ist->st = st;
586         ist->file_index = nb_input_files;
587         ist->discard = 1;
588         st->discard  = AVDISCARD_ALL;
589
590         ist->ts_scale = 1.0;
591         MATCH_PER_STREAM_OPT(ts_scale, dbl, ist->ts_scale, ic, st);
592
593         MATCH_PER_STREAM_OPT(codec_tags, str, codec_tag, ic, st);
594         if (codec_tag) {
595             uint32_t tag = strtol(codec_tag, &next, 0);
596             if (*next)
597                 tag = AV_RL32(codec_tag);
598             st->codec->codec_tag = tag;
599         }
600
601         ist->dec = choose_decoder(o, ic, st);
602         ist->decoder_opts = filter_codec_opts(o->g->codec_opts, ist->st->codec->codec_id, ic, st, ist->dec);
603
604         ist->reinit_filters = -1;
605         MATCH_PER_STREAM_OPT(reinit_filters, i, ist->reinit_filters, ic, st);
606
607         MATCH_PER_STREAM_OPT(discard, str, discard_str, ic, st);
608         ist->user_set_discard = AVDISCARD_NONE;
609         if (discard_str && av_opt_eval_int(dec, discard_opt, discard_str, &ist->user_set_discard) < 0) {
610             av_log(NULL, AV_LOG_ERROR, "Error parsing discard %s.\n",
611                     discard_str);
612             exit_program(1);
613         }
614
615         ist->filter_in_rescale_delta_last = AV_NOPTS_VALUE;
616
617         ist->dec_ctx = avcodec_alloc_context3(ist->dec);
618         if (!ist->dec_ctx) {
619             av_log(NULL, AV_LOG_ERROR, "Error allocating the decoder context.\n");
620             exit_program(1);
621         }
622
623         ret = avcodec_copy_context(ist->dec_ctx, dec);
624         if (ret < 0) {
625             av_log(NULL, AV_LOG_ERROR, "Error initializing the decoder context.\n");
626             exit_program(1);
627         }
628
629         switch (dec->codec_type) {
630         case AVMEDIA_TYPE_VIDEO:
631             if(!ist->dec)
632                 ist->dec = avcodec_find_decoder(dec->codec_id);
633             if (av_codec_get_lowres(dec)) {
634                 dec->flags |= CODEC_FLAG_EMU_EDGE;
635             }
636
637             ist->resample_height  = ist->dec_ctx->height;
638             ist->resample_width   = ist->dec_ctx->width;
639             ist->resample_pix_fmt = ist->dec_ctx->pix_fmt;
640
641             MATCH_PER_STREAM_OPT(frame_rates, str, framerate, ic, st);
642             if (framerate && av_parse_video_rate(&ist->framerate,
643                                                  framerate) < 0) {
644                 av_log(NULL, AV_LOG_ERROR, "Error parsing framerate %s.\n",
645                        framerate);
646                 exit_program(1);
647             }
648
649             ist->top_field_first = -1;
650             MATCH_PER_STREAM_OPT(top_field_first, i, ist->top_field_first, ic, st);
651
652             MATCH_PER_STREAM_OPT(hwaccels, str, hwaccel, ic, st);
653             if (hwaccel) {
654                 if (!strcmp(hwaccel, "none"))
655                     ist->hwaccel_id = HWACCEL_NONE;
656                 else if (!strcmp(hwaccel, "auto"))
657                     ist->hwaccel_id = HWACCEL_AUTO;
658                 else {
659                     int i;
660                     for (i = 0; hwaccels[i].name; i++) {
661                         if (!strcmp(hwaccels[i].name, hwaccel)) {
662                             ist->hwaccel_id = hwaccels[i].id;
663                             break;
664                         }
665                     }
666
667                     if (!ist->hwaccel_id) {
668                         av_log(NULL, AV_LOG_FATAL, "Unrecognized hwaccel: %s.\n",
669                                hwaccel);
670                         av_log(NULL, AV_LOG_FATAL, "Supported hwaccels: ");
671                         for (i = 0; hwaccels[i].name; i++)
672                             av_log(NULL, AV_LOG_FATAL, "%s ", hwaccels[i].name);
673                         av_log(NULL, AV_LOG_FATAL, "\n");
674                         exit_program(1);
675                     }
676                 }
677             }
678
679             MATCH_PER_STREAM_OPT(hwaccel_devices, str, hwaccel_device, ic, st);
680             if (hwaccel_device) {
681                 ist->hwaccel_device = av_strdup(hwaccel_device);
682                 if (!ist->hwaccel_device)
683                     exit_program(1);
684             }
685             ist->hwaccel_pix_fmt = AV_PIX_FMT_NONE;
686
687             break;
688         case AVMEDIA_TYPE_AUDIO:
689             ist->guess_layout_max = INT_MAX;
690             MATCH_PER_STREAM_OPT(guess_layout_max, i, ist->guess_layout_max, ic, st);
691             guess_input_channel_layout(ist);
692
693             ist->resample_sample_fmt     = ist->dec_ctx->sample_fmt;
694             ist->resample_sample_rate    = ist->dec_ctx->sample_rate;
695             ist->resample_channels       = ist->dec_ctx->channels;
696             ist->resample_channel_layout = ist->dec_ctx->channel_layout;
697
698             break;
699         case AVMEDIA_TYPE_DATA:
700         case AVMEDIA_TYPE_SUBTITLE: {
701             char *canvas_size = NULL;
702             if(!ist->dec)
703                 ist->dec = avcodec_find_decoder(dec->codec_id);
704             MATCH_PER_STREAM_OPT(fix_sub_duration, i, ist->fix_sub_duration, ic, st);
705             MATCH_PER_STREAM_OPT(canvas_sizes, str, canvas_size, ic, st);
706             if (canvas_size &&
707                 av_parse_video_size(&ist->dec_ctx->width, &ist->dec_ctx->height, canvas_size) < 0) {
708                 av_log(NULL, AV_LOG_FATAL, "Invalid canvas size: %s.\n", canvas_size);
709                 exit_program(1);
710             }
711             break;
712         }
713         case AVMEDIA_TYPE_ATTACHMENT:
714         case AVMEDIA_TYPE_UNKNOWN:
715             break;
716         default:
717             abort();
718         }
719     }
720 }
721
722 static void assert_file_overwrite(const char *filename)
723 {
724     if (file_overwrite && no_file_overwrite) {
725         fprintf(stderr, "Error, both -y and -n supplied. Exiting.\n");
726         exit_program(1);
727     }
728
729     if (!file_overwrite) {
730         const char *proto_name = avio_find_protocol_name(filename);
731         if (proto_name && !strcmp(proto_name, "file") && avio_check(filename, 0) == 0) {
732             if (stdin_interaction && !no_file_overwrite) {
733                 fprintf(stderr,"File '%s' already exists. Overwrite ? [y/N] ", filename);
734                 fflush(stderr);
735                 term_exit();
736                 signal(SIGINT, SIG_DFL);
737                 if (!read_yesno()) {
738                     av_log(NULL, AV_LOG_FATAL, "Not overwriting - exiting\n");
739                     exit_program(1);
740                 }
741                 term_init();
742             }
743             else {
744                 av_log(NULL, AV_LOG_FATAL, "File '%s' already exists. Exiting.\n", filename);
745                 exit_program(1);
746             }
747         }
748     }
749 }
750
751 static void dump_attachment(AVStream *st, const char *filename)
752 {
753     int ret;
754     AVIOContext *out = NULL;
755     AVDictionaryEntry *e;
756
757     if (!st->codec->extradata_size) {
758         av_log(NULL, AV_LOG_WARNING, "No extradata to dump in stream #%d:%d.\n",
759                nb_input_files - 1, st->index);
760         return;
761     }
762     if (!*filename && (e = av_dict_get(st->metadata, "filename", NULL, 0)))
763         filename = e->value;
764     if (!*filename) {
765         av_log(NULL, AV_LOG_FATAL, "No filename specified and no 'filename' tag"
766                "in stream #%d:%d.\n", nb_input_files - 1, st->index);
767         exit_program(1);
768     }
769
770     assert_file_overwrite(filename);
771
772     if ((ret = avio_open2(&out, filename, AVIO_FLAG_WRITE, &int_cb, NULL)) < 0) {
773         av_log(NULL, AV_LOG_FATAL, "Could not open file %s for writing.\n",
774                filename);
775         exit_program(1);
776     }
777
778     avio_write(out, st->codec->extradata, st->codec->extradata_size);
779     avio_flush(out);
780     avio_close(out);
781 }
782
783 static int open_input_file(OptionsContext *o, const char *filename)
784 {
785     InputFile *f;
786     AVFormatContext *ic;
787     AVInputFormat *file_iformat = NULL;
788     int err, i, ret;
789     int64_t timestamp;
790     AVDictionary **opts;
791     AVDictionary *unused_opts = NULL;
792     AVDictionaryEntry *e = NULL;
793     int orig_nb_streams;                     // number of streams before avformat_find_stream_info
794     char *   video_codec_name = NULL;
795     char *   audio_codec_name = NULL;
796     char *subtitle_codec_name = NULL;
797     int scan_all_pmts_set = 0;
798
799     if (o->format) {
800         if (!(file_iformat = av_find_input_format(o->format))) {
801             av_log(NULL, AV_LOG_FATAL, "Unknown input format: '%s'\n", o->format);
802             exit_program(1);
803         }
804     }
805
806     if (!strcmp(filename, "-"))
807         filename = "pipe:";
808
809     stdin_interaction &= strncmp(filename, "pipe:", 5) &&
810                          strcmp(filename, "/dev/stdin");
811
812     /* get default parameters from command line */
813     ic = avformat_alloc_context();
814     if (!ic) {
815         print_error(filename, AVERROR(ENOMEM));
816         exit_program(1);
817     }
818     if (o->nb_audio_sample_rate) {
819         av_dict_set_int(&o->g->format_opts, "sample_rate", o->audio_sample_rate[o->nb_audio_sample_rate - 1].u.i, 0);
820     }
821     if (o->nb_audio_channels) {
822         /* because we set audio_channels based on both the "ac" and
823          * "channel_layout" options, we need to check that the specified
824          * demuxer actually has the "channels" option before setting it */
825         if (file_iformat && file_iformat->priv_class &&
826             av_opt_find(&file_iformat->priv_class, "channels", NULL, 0,
827                         AV_OPT_SEARCH_FAKE_OBJ)) {
828             av_dict_set_int(&o->g->format_opts, "channels", o->audio_channels[o->nb_audio_channels - 1].u.i, 0);
829         }
830     }
831     if (o->nb_frame_rates) {
832         /* set the format-level framerate option;
833          * this is important for video grabbers, e.g. x11 */
834         if (file_iformat && file_iformat->priv_class &&
835             av_opt_find(&file_iformat->priv_class, "framerate", NULL, 0,
836                         AV_OPT_SEARCH_FAKE_OBJ)) {
837             av_dict_set(&o->g->format_opts, "framerate",
838                         o->frame_rates[o->nb_frame_rates - 1].u.str, 0);
839         }
840     }
841     if (o->nb_frame_sizes) {
842         av_dict_set(&o->g->format_opts, "video_size", o->frame_sizes[o->nb_frame_sizes - 1].u.str, 0);
843     }
844     if (o->nb_frame_pix_fmts)
845         av_dict_set(&o->g->format_opts, "pixel_format", o->frame_pix_fmts[o->nb_frame_pix_fmts - 1].u.str, 0);
846
847     MATCH_PER_TYPE_OPT(codec_names, str,    video_codec_name, ic, "v");
848     MATCH_PER_TYPE_OPT(codec_names, str,    audio_codec_name, ic, "a");
849     MATCH_PER_TYPE_OPT(codec_names, str, subtitle_codec_name, ic, "s");
850
851     ic->video_codec_id   = video_codec_name ?
852         find_codec_or_die(video_codec_name   , AVMEDIA_TYPE_VIDEO   , 0)->id : AV_CODEC_ID_NONE;
853     ic->audio_codec_id   = audio_codec_name ?
854         find_codec_or_die(audio_codec_name   , AVMEDIA_TYPE_AUDIO   , 0)->id : AV_CODEC_ID_NONE;
855     ic->subtitle_codec_id= subtitle_codec_name ?
856         find_codec_or_die(subtitle_codec_name, AVMEDIA_TYPE_SUBTITLE, 0)->id : AV_CODEC_ID_NONE;
857
858     if (video_codec_name)
859         av_format_set_video_codec   (ic, find_codec_or_die(video_codec_name   , AVMEDIA_TYPE_VIDEO   , 0));
860     if (audio_codec_name)
861         av_format_set_audio_codec   (ic, find_codec_or_die(audio_codec_name   , AVMEDIA_TYPE_AUDIO   , 0));
862     if (subtitle_codec_name)
863         av_format_set_subtitle_codec(ic, find_codec_or_die(subtitle_codec_name, AVMEDIA_TYPE_SUBTITLE, 0));
864
865     ic->flags |= AVFMT_FLAG_NONBLOCK;
866     ic->interrupt_callback = int_cb;
867
868     if (!av_dict_get(o->g->format_opts, "scan_all_pmts", NULL, AV_DICT_MATCH_CASE)) {
869         av_dict_set(&o->g->format_opts, "scan_all_pmts", "1", AV_DICT_DONT_OVERWRITE);
870         scan_all_pmts_set = 1;
871     }
872     /* open the input file with generic avformat function */
873     err = avformat_open_input(&ic, filename, file_iformat, &o->g->format_opts);
874     if (err < 0) {
875         print_error(filename, err);
876         exit_program(1);
877     }
878     if (scan_all_pmts_set)
879         av_dict_set(&o->g->format_opts, "scan_all_pmts", NULL, AV_DICT_MATCH_CASE);
880     remove_avoptions(&o->g->format_opts, o->g->codec_opts);
881     assert_avoptions(o->g->format_opts);
882
883     /* apply forced codec ids */
884     for (i = 0; i < ic->nb_streams; i++)
885         choose_decoder(o, ic, ic->streams[i]);
886
887     /* Set AVCodecContext options for avformat_find_stream_info */
888     opts = setup_find_stream_info_opts(ic, o->g->codec_opts);
889     orig_nb_streams = ic->nb_streams;
890
891     /* If not enough info to get the stream parameters, we decode the
892        first frames to get it. (used in mpeg case for example) */
893     ret = avformat_find_stream_info(ic, opts);
894     if (ret < 0) {
895         av_log(NULL, AV_LOG_FATAL, "%s: could not find codec parameters\n", filename);
896         if (ic->nb_streams == 0) {
897             avformat_close_input(&ic);
898             exit_program(1);
899         }
900     }
901
902     timestamp = (o->start_time == AV_NOPTS_VALUE) ? 0 : o->start_time;
903     /* add the stream start time */
904     if (ic->start_time != AV_NOPTS_VALUE)
905         timestamp += ic->start_time;
906
907     /* if seeking requested, we execute it */
908     if (o->start_time != AV_NOPTS_VALUE) {
909         ret = avformat_seek_file(ic, -1, INT64_MIN, timestamp, timestamp, 0);
910         if (ret < 0) {
911             av_log(NULL, AV_LOG_WARNING, "%s: could not seek to position %0.3f\n",
912                    filename, (double)timestamp / AV_TIME_BASE);
913         }
914     }
915
916     /* update the current parameters so that they match the one of the input stream */
917     add_input_streams(o, ic);
918
919     /* dump the file content */
920     av_dump_format(ic, nb_input_files, filename, 0);
921
922     GROW_ARRAY(input_files, nb_input_files);
923     f = av_mallocz(sizeof(*f));
924     if (!f)
925         exit_program(1);
926     input_files[nb_input_files - 1] = f;
927
928     f->ctx        = ic;
929     f->ist_index  = nb_input_streams - ic->nb_streams;
930     f->start_time = o->start_time;
931     f->recording_time = o->recording_time;
932     f->input_ts_offset = o->input_ts_offset;
933     f->ts_offset  = o->input_ts_offset - (copy_ts ? (start_at_zero && ic->start_time != AV_NOPTS_VALUE ? ic->start_time : 0) : timestamp);
934     f->nb_streams = ic->nb_streams;
935     f->rate_emu   = o->rate_emu;
936     f->accurate_seek = o->accurate_seek;
937
938     /* check if all codec options have been used */
939     unused_opts = strip_specifiers(o->g->codec_opts);
940     for (i = f->ist_index; i < nb_input_streams; i++) {
941         e = NULL;
942         while ((e = av_dict_get(input_streams[i]->decoder_opts, "", e,
943                                 AV_DICT_IGNORE_SUFFIX)))
944             av_dict_set(&unused_opts, e->key, NULL, 0);
945     }
946
947     e = NULL;
948     while ((e = av_dict_get(unused_opts, "", e, AV_DICT_IGNORE_SUFFIX))) {
949         const AVClass *class = avcodec_get_class();
950         const AVOption *option = av_opt_find(&class, e->key, NULL, 0,
951                                              AV_OPT_SEARCH_CHILDREN | AV_OPT_SEARCH_FAKE_OBJ);
952         const AVClass *fclass = avformat_get_class();
953         const AVOption *foption = av_opt_find(&fclass, e->key, NULL, 0,
954                                              AV_OPT_SEARCH_CHILDREN | AV_OPT_SEARCH_FAKE_OBJ);
955         if (!option || foption)
956             continue;
957
958
959         if (!(option->flags & AV_OPT_FLAG_DECODING_PARAM)) {
960             av_log(NULL, AV_LOG_ERROR, "Codec AVOption %s (%s) specified for "
961                    "input file #%d (%s) is not a decoding option.\n", e->key,
962                    option->help ? option->help : "", nb_input_files - 1,
963                    filename);
964             exit_program(1);
965         }
966
967         av_log(NULL, AV_LOG_WARNING, "Codec AVOption %s (%s) specified for "
968                "input file #%d (%s) has not been used for any stream. The most "
969                "likely reason is either wrong type (e.g. a video option with "
970                "no video streams) or that it is a private option of some decoder "
971                "which was not actually used for any stream.\n", e->key,
972                option->help ? option->help : "", nb_input_files - 1, filename);
973     }
974     av_dict_free(&unused_opts);
975
976     for (i = 0; i < o->nb_dump_attachment; i++) {
977         int j;
978
979         for (j = 0; j < ic->nb_streams; j++) {
980             AVStream *st = ic->streams[j];
981
982             if (check_stream_specifier(ic, st, o->dump_attachment[i].specifier) == 1)
983                 dump_attachment(st, o->dump_attachment[i].u.str);
984         }
985     }
986
987     for (i = 0; i < orig_nb_streams; i++)
988         av_dict_free(&opts[i]);
989     av_freep(&opts);
990
991     return 0;
992 }
993
994 static uint8_t *get_line(AVIOContext *s)
995 {
996     AVIOContext *line;
997     uint8_t *buf;
998     char c;
999
1000     if (avio_open_dyn_buf(&line) < 0) {
1001         av_log(NULL, AV_LOG_FATAL, "Could not alloc buffer for reading preset.\n");
1002         exit_program(1);
1003     }
1004
1005     while ((c = avio_r8(s)) && c != '\n')
1006         avio_w8(line, c);
1007     avio_w8(line, 0);
1008     avio_close_dyn_buf(line, &buf);
1009
1010     return buf;
1011 }
1012
1013 static int get_preset_file_2(const char *preset_name, const char *codec_name, AVIOContext **s)
1014 {
1015     int i, ret = -1;
1016     char filename[1000];
1017     const char *base[3] = { getenv("AVCONV_DATADIR"),
1018                             getenv("HOME"),
1019                             AVCONV_DATADIR,
1020                             };
1021
1022     for (i = 0; i < FF_ARRAY_ELEMS(base) && ret < 0; i++) {
1023         if (!base[i])
1024             continue;
1025         if (codec_name) {
1026             snprintf(filename, sizeof(filename), "%s%s/%s-%s.avpreset", base[i],
1027                      i != 1 ? "" : "/.avconv", codec_name, preset_name);
1028             ret = avio_open2(s, filename, AVIO_FLAG_READ, &int_cb, NULL);
1029         }
1030         if (ret < 0) {
1031             snprintf(filename, sizeof(filename), "%s%s/%s.avpreset", base[i],
1032                      i != 1 ? "" : "/.avconv", preset_name);
1033             ret = avio_open2(s, filename, AVIO_FLAG_READ, &int_cb, NULL);
1034         }
1035     }
1036     return ret;
1037 }
1038
1039 static void choose_encoder(OptionsContext *o, AVFormatContext *s, OutputStream *ost)
1040 {
1041     char *codec_name = NULL;
1042
1043     MATCH_PER_STREAM_OPT(codec_names, str, codec_name, s, ost->st);
1044     if (!codec_name) {
1045         ost->st->codec->codec_id = av_guess_codec(s->oformat, NULL, s->filename,
1046                                                   NULL, ost->st->codec->codec_type);
1047         ost->enc = avcodec_find_encoder(ost->st->codec->codec_id);
1048     } else if (!strcmp(codec_name, "copy"))
1049         ost->stream_copy = 1;
1050     else {
1051         ost->enc = find_codec_or_die(codec_name, ost->st->codec->codec_type, 1);
1052         ost->st->codec->codec_id = ost->enc->id;
1053     }
1054 }
1055
1056 static OutputStream *new_output_stream(OptionsContext *o, AVFormatContext *oc, enum AVMediaType type, int source_index)
1057 {
1058     OutputStream *ost;
1059     AVStream *st = avformat_new_stream(oc, NULL);
1060     int idx      = oc->nb_streams - 1, ret = 0;
1061     char *bsf = NULL, *next, *codec_tag = NULL;
1062     AVBitStreamFilterContext *bsfc, *bsfc_prev = NULL;
1063     double qscale = -1;
1064     int i;
1065
1066     if (!st) {
1067         av_log(NULL, AV_LOG_FATAL, "Could not alloc stream.\n");
1068         exit_program(1);
1069     }
1070
1071     if (oc->nb_streams - 1 < o->nb_streamid_map)
1072         st->id = o->streamid_map[oc->nb_streams - 1];
1073
1074     GROW_ARRAY(output_streams, nb_output_streams);
1075     if (!(ost = av_mallocz(sizeof(*ost))))
1076         exit_program(1);
1077     output_streams[nb_output_streams - 1] = ost;
1078
1079     ost->file_index = nb_output_files - 1;
1080     ost->index      = idx;
1081     ost->st         = st;
1082     st->codec->codec_type = type;
1083     choose_encoder(o, oc, ost);
1084
1085     ost->enc_ctx = avcodec_alloc_context3(ost->enc);
1086     if (!ost->enc_ctx) {
1087         av_log(NULL, AV_LOG_ERROR, "Error allocating the encoding context.\n");
1088         exit_program(1);
1089     }
1090     ost->enc_ctx->codec_type = type;
1091
1092     if (ost->enc) {
1093         AVIOContext *s = NULL;
1094         char *buf = NULL, *arg = NULL, *preset = NULL;
1095
1096         ost->encoder_opts  = filter_codec_opts(o->g->codec_opts, ost->enc->id, oc, st, ost->enc);
1097
1098         MATCH_PER_STREAM_OPT(presets, str, preset, oc, st);
1099         if (preset && (!(ret = get_preset_file_2(preset, ost->enc->name, &s)))) {
1100             do  {
1101                 buf = get_line(s);
1102                 if (!buf[0] || buf[0] == '#') {
1103                     av_free(buf);
1104                     continue;
1105                 }
1106                 if (!(arg = strchr(buf, '='))) {
1107                     av_log(NULL, AV_LOG_FATAL, "Invalid line found in the preset file.\n");
1108                     exit_program(1);
1109                 }
1110                 *arg++ = 0;
1111                 av_dict_set(&ost->encoder_opts, buf, arg, AV_DICT_DONT_OVERWRITE);
1112                 av_free(buf);
1113             } while (!s->eof_reached);
1114             avio_close(s);
1115         }
1116         if (ret) {
1117             av_log(NULL, AV_LOG_FATAL,
1118                    "Preset %s specified for stream %d:%d, but could not be opened.\n",
1119                    preset, ost->file_index, ost->index);
1120             exit_program(1);
1121         }
1122     } else {
1123         ost->encoder_opts = filter_codec_opts(o->g->codec_opts, AV_CODEC_ID_NONE, oc, st, NULL);
1124     }
1125
1126     ost->max_frames = INT64_MAX;
1127     MATCH_PER_STREAM_OPT(max_frames, i64, ost->max_frames, oc, st);
1128     for (i = 0; i<o->nb_max_frames; i++) {
1129         char *p = o->max_frames[i].specifier;
1130         if (!*p && type != AVMEDIA_TYPE_VIDEO) {
1131             av_log(NULL, AV_LOG_WARNING, "Applying unspecific -frames to non video streams, maybe you meant -vframes ?\n");
1132             break;
1133         }
1134     }
1135
1136     ost->copy_prior_start = -1;
1137     MATCH_PER_STREAM_OPT(copy_prior_start, i, ost->copy_prior_start, oc ,st);
1138
1139     MATCH_PER_STREAM_OPT(bitstream_filters, str, bsf, oc, st);
1140     while (bsf) {
1141         char *arg = NULL;
1142         if (next = strchr(bsf, ','))
1143             *next++ = 0;
1144         if (arg = strchr(bsf, '='))
1145             *arg++ = 0;
1146         if (!(bsfc = av_bitstream_filter_init(bsf))) {
1147             av_log(NULL, AV_LOG_FATAL, "Unknown bitstream filter %s\n", bsf);
1148             exit_program(1);
1149         }
1150         if (bsfc_prev)
1151             bsfc_prev->next = bsfc;
1152         else
1153             ost->bitstream_filters = bsfc;
1154         av_dict_set(&ost->bsf_args, bsfc->filter->name, arg, 0);
1155
1156         bsfc_prev = bsfc;
1157         bsf       = next;
1158     }
1159
1160     MATCH_PER_STREAM_OPT(codec_tags, str, codec_tag, oc, st);
1161     if (codec_tag) {
1162         uint32_t tag = strtol(codec_tag, &next, 0);
1163         if (*next)
1164             tag = AV_RL32(codec_tag);
1165         ost->enc_ctx->codec_tag = tag;
1166     }
1167
1168     MATCH_PER_STREAM_OPT(qscale, dbl, qscale, oc, st);
1169     if (qscale >= 0) {
1170         ost->enc_ctx->flags |= CODEC_FLAG_QSCALE;
1171         ost->enc_ctx->global_quality = FF_QP2LAMBDA * qscale;
1172     }
1173
1174     if (oc->oformat->flags & AVFMT_GLOBALHEADER)
1175         ost->enc_ctx->flags |= CODEC_FLAG_GLOBAL_HEADER;
1176
1177     av_opt_get_int(o->g->sws_opts, "sws_flags", 0, &ost->sws_flags);
1178
1179     av_dict_copy(&ost->swr_opts, o->g->swr_opts, 0);
1180     if (ost->enc && av_get_exact_bits_per_sample(ost->enc->id) == 24)
1181         av_dict_set(&ost->swr_opts, "output_sample_bits", "24", 0);
1182
1183     av_dict_copy(&ost->resample_opts, o->g->resample_opts, 0);
1184
1185     ost->source_index = source_index;
1186     if (source_index >= 0) {
1187         ost->sync_ist = input_streams[source_index];
1188         input_streams[source_index]->discard = 0;
1189         input_streams[source_index]->st->discard = input_streams[source_index]->user_set_discard;
1190     }
1191     ost->last_mux_dts = AV_NOPTS_VALUE;
1192
1193     return ost;
1194 }
1195
1196 static void parse_matrix_coeffs(uint16_t *dest, const char *str)
1197 {
1198     int i;
1199     const char *p = str;
1200     for (i = 0;; i++) {
1201         dest[i] = atoi(p);
1202         if (i == 63)
1203             break;
1204         p = strchr(p, ',');
1205         if (!p) {
1206             av_log(NULL, AV_LOG_FATAL, "Syntax error in matrix \"%s\" at coeff %d\n", str, i);
1207             exit_program(1);
1208         }
1209         p++;
1210     }
1211 }
1212
1213 /* read file contents into a string */
1214 static uint8_t *read_file(const char *filename)
1215 {
1216     AVIOContext *pb      = NULL;
1217     AVIOContext *dyn_buf = NULL;
1218     int ret = avio_open(&pb, filename, AVIO_FLAG_READ);
1219     uint8_t buf[1024], *str;
1220
1221     if (ret < 0) {
1222         av_log(NULL, AV_LOG_ERROR, "Error opening file %s.\n", filename);
1223         return NULL;
1224     }
1225
1226     ret = avio_open_dyn_buf(&dyn_buf);
1227     if (ret < 0) {
1228         avio_closep(&pb);
1229         return NULL;
1230     }
1231     while ((ret = avio_read(pb, buf, sizeof(buf))) > 0)
1232         avio_write(dyn_buf, buf, ret);
1233     avio_w8(dyn_buf, 0);
1234     avio_closep(&pb);
1235
1236     ret = avio_close_dyn_buf(dyn_buf, &str);
1237     if (ret < 0)
1238         return NULL;
1239     return str;
1240 }
1241
1242 static char *get_ost_filters(OptionsContext *o, AVFormatContext *oc,
1243                              OutputStream *ost)
1244 {
1245     AVStream *st = ost->st;
1246
1247     if (ost->filters_script && ost->filters) {
1248         av_log(NULL, AV_LOG_ERROR, "Both -filter and -filter_script set for "
1249                "output stream #%d:%d.\n", nb_output_files, st->index);
1250         exit_program(1);
1251     }
1252
1253     if (ost->filters_script)
1254         return read_file(ost->filters_script);
1255     else if (ost->filters)
1256         return av_strdup(ost->filters);
1257
1258     return av_strdup(st->codec->codec_type == AVMEDIA_TYPE_VIDEO ?
1259                      "null" : "anull");
1260 }
1261
1262 static void check_streamcopy_filters(OptionsContext *o, AVFormatContext *oc,
1263                                      const OutputStream *ost, enum AVMediaType type)
1264 {
1265     if (ost->filters_script || ost->filters) {
1266         av_log(NULL, AV_LOG_ERROR,
1267                "%s '%s' was defined for %s output stream %d:%d but codec copy was selected.\n"
1268                "Filtering and streamcopy cannot be used together.\n",
1269                ost->filters ? "Filtergraph" : "Filtergraph script",
1270                ost->filters ? ost->filters : ost->filters_script,
1271                av_get_media_type_string(type), ost->file_index, ost->index);
1272         exit_program(1);
1273     }
1274 }
1275
1276 static OutputStream *new_video_stream(OptionsContext *o, AVFormatContext *oc, int source_index)
1277 {
1278     AVStream *st;
1279     OutputStream *ost;
1280     AVCodecContext *video_enc;
1281     char *frame_rate = NULL, *frame_aspect_ratio = NULL;
1282
1283     ost = new_output_stream(o, oc, AVMEDIA_TYPE_VIDEO, source_index);
1284     st  = ost->st;
1285     video_enc = ost->enc_ctx;
1286
1287     MATCH_PER_STREAM_OPT(frame_rates, str, frame_rate, oc, st);
1288     if (frame_rate && av_parse_video_rate(&ost->frame_rate, frame_rate) < 0) {
1289         av_log(NULL, AV_LOG_FATAL, "Invalid framerate value: %s\n", frame_rate);
1290         exit_program(1);
1291     }
1292     if (frame_rate && video_sync_method == VSYNC_PASSTHROUGH)
1293         av_log(NULL, AV_LOG_ERROR, "Using -vsync 0 and -r can produce invalid output files\n");
1294
1295     MATCH_PER_STREAM_OPT(frame_aspect_ratios, str, frame_aspect_ratio, oc, st);
1296     if (frame_aspect_ratio) {
1297         AVRational q;
1298         if (av_parse_ratio(&q, frame_aspect_ratio, 255, 0, NULL) < 0 ||
1299             q.num <= 0 || q.den <= 0) {
1300             av_log(NULL, AV_LOG_FATAL, "Invalid aspect ratio: %s\n", frame_aspect_ratio);
1301             exit_program(1);
1302         }
1303         ost->frame_aspect_ratio = q;
1304     }
1305
1306     MATCH_PER_STREAM_OPT(filter_scripts, str, ost->filters_script, oc, st);
1307     MATCH_PER_STREAM_OPT(filters,        str, ost->filters,        oc, st);
1308
1309     if (!ost->stream_copy) {
1310         const char *p = NULL;
1311         char *frame_size = NULL;
1312         char *frame_pix_fmt = NULL;
1313         char *intra_matrix = NULL, *inter_matrix = NULL;
1314         char *chroma_intra_matrix = NULL;
1315         int do_pass = 0;
1316         int i;
1317
1318         MATCH_PER_STREAM_OPT(frame_sizes, str, frame_size, oc, st);
1319         if (frame_size && av_parse_video_size(&video_enc->width, &video_enc->height, frame_size) < 0) {
1320             av_log(NULL, AV_LOG_FATAL, "Invalid frame size: %s.\n", frame_size);
1321             exit_program(1);
1322         }
1323
1324         video_enc->bits_per_raw_sample = frame_bits_per_raw_sample;
1325         MATCH_PER_STREAM_OPT(frame_pix_fmts, str, frame_pix_fmt, oc, st);
1326         if (frame_pix_fmt && *frame_pix_fmt == '+') {
1327             ost->keep_pix_fmt = 1;
1328             if (!*++frame_pix_fmt)
1329                 frame_pix_fmt = NULL;
1330         }
1331         if (frame_pix_fmt && (video_enc->pix_fmt = av_get_pix_fmt(frame_pix_fmt)) == AV_PIX_FMT_NONE) {
1332             av_log(NULL, AV_LOG_FATAL, "Unknown pixel format requested: %s.\n", frame_pix_fmt);
1333             exit_program(1);
1334         }
1335         st->sample_aspect_ratio = video_enc->sample_aspect_ratio;
1336
1337         if (intra_only)
1338             video_enc->gop_size = 0;
1339         MATCH_PER_STREAM_OPT(intra_matrices, str, intra_matrix, oc, st);
1340         if (intra_matrix) {
1341             if (!(video_enc->intra_matrix = av_mallocz(sizeof(*video_enc->intra_matrix) * 64))) {
1342                 av_log(NULL, AV_LOG_FATAL, "Could not allocate memory for intra matrix.\n");
1343                 exit_program(1);
1344             }
1345             parse_matrix_coeffs(video_enc->intra_matrix, intra_matrix);
1346         }
1347         MATCH_PER_STREAM_OPT(chroma_intra_matrices, str, chroma_intra_matrix, oc, st);
1348         if (chroma_intra_matrix) {
1349             uint16_t *p = av_mallocz(sizeof(*video_enc->chroma_intra_matrix) * 64);
1350             if (!p) {
1351                 av_log(NULL, AV_LOG_FATAL, "Could not allocate memory for intra matrix.\n");
1352                 exit_program(1);
1353             }
1354             av_codec_set_chroma_intra_matrix(video_enc, p);
1355             parse_matrix_coeffs(p, chroma_intra_matrix);
1356         }
1357         MATCH_PER_STREAM_OPT(inter_matrices, str, inter_matrix, oc, st);
1358         if (inter_matrix) {
1359             if (!(video_enc->inter_matrix = av_mallocz(sizeof(*video_enc->inter_matrix) * 64))) {
1360                 av_log(NULL, AV_LOG_FATAL, "Could not allocate memory for inter matrix.\n");
1361                 exit_program(1);
1362             }
1363             parse_matrix_coeffs(video_enc->inter_matrix, inter_matrix);
1364         }
1365
1366         MATCH_PER_STREAM_OPT(rc_overrides, str, p, oc, st);
1367         for (i = 0; p; i++) {
1368             int start, end, q;
1369             int e = sscanf(p, "%d,%d,%d", &start, &end, &q);
1370             if (e != 3) {
1371                 av_log(NULL, AV_LOG_FATAL, "error parsing rc_override\n");
1372                 exit_program(1);
1373             }
1374             /* FIXME realloc failure */
1375             video_enc->rc_override =
1376                 av_realloc(video_enc->rc_override,
1377                            sizeof(RcOverride) * (i + 1));
1378             video_enc->rc_override[i].start_frame = start;
1379             video_enc->rc_override[i].end_frame   = end;
1380             if (q > 0) {
1381                 video_enc->rc_override[i].qscale         = q;
1382                 video_enc->rc_override[i].quality_factor = 1.0;
1383             }
1384             else {
1385                 video_enc->rc_override[i].qscale         = 0;
1386                 video_enc->rc_override[i].quality_factor = -q/100.0;
1387             }
1388             p = strchr(p, '/');
1389             if (p) p++;
1390         }
1391         video_enc->rc_override_count = i;
1392
1393         if (do_psnr)
1394             video_enc->flags|= CODEC_FLAG_PSNR;
1395
1396         /* two pass mode */
1397         MATCH_PER_STREAM_OPT(pass, i, do_pass, oc, st);
1398         if (do_pass) {
1399             if (do_pass & 1) {
1400                 video_enc->flags |= CODEC_FLAG_PASS1;
1401                 av_dict_set(&ost->encoder_opts, "flags", "+pass1", AV_DICT_APPEND);
1402             }
1403             if (do_pass & 2) {
1404                 video_enc->flags |= CODEC_FLAG_PASS2;
1405                 av_dict_set(&ost->encoder_opts, "flags", "+pass2", AV_DICT_APPEND);
1406             }
1407         }
1408
1409         MATCH_PER_STREAM_OPT(passlogfiles, str, ost->logfile_prefix, oc, st);
1410         if (ost->logfile_prefix &&
1411             !(ost->logfile_prefix = av_strdup(ost->logfile_prefix)))
1412             exit_program(1);
1413
1414         MATCH_PER_STREAM_OPT(forced_key_frames, str, ost->forced_keyframes, oc, st);
1415         if (ost->forced_keyframes)
1416             ost->forced_keyframes = av_strdup(ost->forced_keyframes);
1417
1418         MATCH_PER_STREAM_OPT(force_fps, i, ost->force_fps, oc, st);
1419
1420         ost->top_field_first = -1;
1421         MATCH_PER_STREAM_OPT(top_field_first, i, ost->top_field_first, oc, st);
1422
1423
1424         ost->avfilter = get_ost_filters(o, oc, ost);
1425         if (!ost->avfilter)
1426             exit_program(1);
1427     } else {
1428         MATCH_PER_STREAM_OPT(copy_initial_nonkeyframes, i, ost->copy_initial_nonkeyframes, oc ,st);
1429     }
1430
1431     if (ost->stream_copy)
1432         check_streamcopy_filters(o, oc, ost, AVMEDIA_TYPE_VIDEO);
1433
1434     return ost;
1435 }
1436
1437 static OutputStream *new_audio_stream(OptionsContext *o, AVFormatContext *oc, int source_index)
1438 {
1439     int n;
1440     AVStream *st;
1441     OutputStream *ost;
1442     AVCodecContext *audio_enc;
1443
1444     ost = new_output_stream(o, oc, AVMEDIA_TYPE_AUDIO, source_index);
1445     st  = ost->st;
1446
1447     audio_enc = ost->enc_ctx;
1448     audio_enc->codec_type = AVMEDIA_TYPE_AUDIO;
1449
1450     MATCH_PER_STREAM_OPT(filter_scripts, str, ost->filters_script, oc, st);
1451     MATCH_PER_STREAM_OPT(filters,        str, ost->filters,        oc, st);
1452
1453     if (!ost->stream_copy) {
1454         char *sample_fmt = NULL;
1455
1456         MATCH_PER_STREAM_OPT(audio_channels, i, audio_enc->channels, oc, st);
1457
1458         MATCH_PER_STREAM_OPT(sample_fmts, str, sample_fmt, oc, st);
1459         if (sample_fmt &&
1460             (audio_enc->sample_fmt = av_get_sample_fmt(sample_fmt)) == AV_SAMPLE_FMT_NONE) {
1461             av_log(NULL, AV_LOG_FATAL, "Invalid sample format '%s'\n", sample_fmt);
1462             exit_program(1);
1463         }
1464
1465         MATCH_PER_STREAM_OPT(audio_sample_rate, i, audio_enc->sample_rate, oc, st);
1466
1467         MATCH_PER_STREAM_OPT(apad, str, ost->apad, oc, st);
1468         ost->apad = av_strdup(ost->apad);
1469
1470         ost->avfilter = get_ost_filters(o, oc, ost);
1471         if (!ost->avfilter)
1472             exit_program(1);
1473
1474         /* check for channel mapping for this audio stream */
1475         for (n = 0; n < o->nb_audio_channel_maps; n++) {
1476             AudioChannelMap *map = &o->audio_channel_maps[n];
1477             if ((map->ofile_idx   == -1 || ost->file_index == map->ofile_idx) &&
1478                 (map->ostream_idx == -1 || ost->st->index  == map->ostream_idx)) {
1479                 InputStream *ist;
1480
1481                 if (map->channel_idx == -1) {
1482                     ist = NULL;
1483                 } else if (ost->source_index < 0) {
1484                     av_log(NULL, AV_LOG_FATAL, "Cannot determine input stream for channel mapping %d.%d\n",
1485                            ost->file_index, ost->st->index);
1486                     continue;
1487                 } else {
1488                     ist = input_streams[ost->source_index];
1489                 }
1490
1491                 if (!ist || (ist->file_index == map->file_idx && ist->st->index == map->stream_idx)) {
1492                     if (av_reallocp_array(&ost->audio_channels_map,
1493                                           ost->audio_channels_mapped + 1,
1494                                           sizeof(*ost->audio_channels_map)
1495                                           ) < 0 )
1496                         exit_program(1);
1497
1498                     ost->audio_channels_map[ost->audio_channels_mapped++] = map->channel_idx;
1499                 }
1500             }
1501         }
1502     }
1503
1504     if (ost->stream_copy)
1505         check_streamcopy_filters(o, oc, ost, AVMEDIA_TYPE_AUDIO);
1506
1507     return ost;
1508 }
1509
1510 static OutputStream *new_data_stream(OptionsContext *o, AVFormatContext *oc, int source_index)
1511 {
1512     OutputStream *ost;
1513
1514     ost = new_output_stream(o, oc, AVMEDIA_TYPE_DATA, source_index);
1515     if (!ost->stream_copy) {
1516         av_log(NULL, AV_LOG_FATAL, "Data stream encoding not supported yet (only streamcopy)\n");
1517         exit_program(1);
1518     }
1519
1520     return ost;
1521 }
1522
1523 static OutputStream *new_attachment_stream(OptionsContext *o, AVFormatContext *oc, int source_index)
1524 {
1525     OutputStream *ost = new_output_stream(o, oc, AVMEDIA_TYPE_ATTACHMENT, source_index);
1526     ost->stream_copy = 1;
1527     ost->finished    = 1;
1528     return ost;
1529 }
1530
1531 static OutputStream *new_subtitle_stream(OptionsContext *o, AVFormatContext *oc, int source_index)
1532 {
1533     AVStream *st;
1534     OutputStream *ost;
1535     AVCodecContext *subtitle_enc;
1536
1537     ost = new_output_stream(o, oc, AVMEDIA_TYPE_SUBTITLE, source_index);
1538     st  = ost->st;
1539     subtitle_enc = ost->enc_ctx;
1540
1541     subtitle_enc->codec_type = AVMEDIA_TYPE_SUBTITLE;
1542
1543     MATCH_PER_STREAM_OPT(copy_initial_nonkeyframes, i, ost->copy_initial_nonkeyframes, oc, st);
1544
1545     if (!ost->stream_copy) {
1546         char *frame_size = NULL;
1547
1548         MATCH_PER_STREAM_OPT(frame_sizes, str, frame_size, oc, st);
1549         if (frame_size && av_parse_video_size(&subtitle_enc->width, &subtitle_enc->height, frame_size) < 0) {
1550             av_log(NULL, AV_LOG_FATAL, "Invalid frame size: %s.\n", frame_size);
1551             exit_program(1);
1552         }
1553     }
1554
1555     return ost;
1556 }
1557
1558 /* arg format is "output-stream-index:streamid-value". */
1559 static int opt_streamid(void *optctx, const char *opt, const char *arg)
1560 {
1561     OptionsContext *o = optctx;
1562     int idx;
1563     char *p;
1564     char idx_str[16];
1565
1566     av_strlcpy(idx_str, arg, sizeof(idx_str));
1567     p = strchr(idx_str, ':');
1568     if (!p) {
1569         av_log(NULL, AV_LOG_FATAL,
1570                "Invalid value '%s' for option '%s', required syntax is 'index:value'\n",
1571                arg, opt);
1572         exit_program(1);
1573     }
1574     *p++ = '\0';
1575     idx = parse_number_or_die(opt, idx_str, OPT_INT, 0, MAX_STREAMS-1);
1576     o->streamid_map = grow_array(o->streamid_map, sizeof(*o->streamid_map), &o->nb_streamid_map, idx+1);
1577     o->streamid_map[idx] = parse_number_or_die(opt, p, OPT_INT, 0, INT_MAX);
1578     return 0;
1579 }
1580
1581 static int copy_chapters(InputFile *ifile, OutputFile *ofile, int copy_metadata)
1582 {
1583     AVFormatContext *is = ifile->ctx;
1584     AVFormatContext *os = ofile->ctx;
1585     AVChapter **tmp;
1586     int i;
1587
1588     tmp = av_realloc_f(os->chapters, is->nb_chapters + os->nb_chapters, sizeof(*os->chapters));
1589     if (!tmp)
1590         return AVERROR(ENOMEM);
1591     os->chapters = tmp;
1592
1593     for (i = 0; i < is->nb_chapters; i++) {
1594         AVChapter *in_ch = is->chapters[i], *out_ch;
1595         int64_t start_time = (ofile->start_time == AV_NOPTS_VALUE) ? 0 : ofile->start_time;
1596         int64_t ts_off   = av_rescale_q(start_time - ifile->ts_offset,
1597                                        AV_TIME_BASE_Q, in_ch->time_base);
1598         int64_t rt       = (ofile->recording_time == INT64_MAX) ? INT64_MAX :
1599                            av_rescale_q(ofile->recording_time, AV_TIME_BASE_Q, in_ch->time_base);
1600
1601
1602         if (in_ch->end < ts_off)
1603             continue;
1604         if (rt != INT64_MAX && in_ch->start > rt + ts_off)
1605             break;
1606
1607         out_ch = av_mallocz(sizeof(AVChapter));
1608         if (!out_ch)
1609             return AVERROR(ENOMEM);
1610
1611         out_ch->id        = in_ch->id;
1612         out_ch->time_base = in_ch->time_base;
1613         out_ch->start     = FFMAX(0,  in_ch->start - ts_off);
1614         out_ch->end       = FFMIN(rt, in_ch->end   - ts_off);
1615
1616         if (copy_metadata)
1617             av_dict_copy(&out_ch->metadata, in_ch->metadata, 0);
1618
1619         os->chapters[os->nb_chapters++] = out_ch;
1620     }
1621     return 0;
1622 }
1623
1624 static int read_ffserver_streams(OptionsContext *o, AVFormatContext *s, const char *filename)
1625 {
1626     int i, err;
1627     AVFormatContext *ic = avformat_alloc_context();
1628
1629     ic->interrupt_callback = int_cb;
1630     err = avformat_open_input(&ic, filename, NULL, NULL);
1631     if (err < 0)
1632         return err;
1633     /* copy stream format */
1634     for(i=0;i<ic->nb_streams;i++) {
1635         AVStream *st;
1636         OutputStream *ost;
1637         AVCodec *codec;
1638         const char *enc_config;
1639
1640         codec = avcodec_find_encoder(ic->streams[i]->codec->codec_id);
1641         if (!codec) {
1642             av_log(s, AV_LOG_ERROR, "no encoder found for codec id %i\n", ic->streams[i]->codec->codec_id);
1643             return AVERROR(EINVAL);
1644         }
1645         if (codec->type == AVMEDIA_TYPE_AUDIO)
1646             opt_audio_codec(o, "c:a", codec->name);
1647         else if (codec->type == AVMEDIA_TYPE_VIDEO)
1648             opt_video_codec(o, "c:v", codec->name);
1649         ost   = new_output_stream(o, s, codec->type, -1);
1650         st    = ost->st;
1651
1652         avcodec_get_context_defaults3(st->codec, codec);
1653         enc_config = av_stream_get_recommended_encoder_configuration(ic->streams[i]);
1654         if (enc_config) {
1655             AVDictionary *opts = NULL;
1656             av_dict_parse_string(&opts, enc_config, "=", ",", 0);
1657             av_opt_set_dict2(st->codec, &opts, AV_OPT_SEARCH_CHILDREN);
1658             av_dict_free(&opts);
1659         }
1660
1661         if (st->codec->codec_type == AVMEDIA_TYPE_AUDIO && !ost->stream_copy)
1662             choose_sample_fmt(st, codec);
1663         else if (st->codec->codec_type == AVMEDIA_TYPE_VIDEO && !ost->stream_copy)
1664             choose_pixel_fmt(st, st->codec, codec, st->codec->pix_fmt);
1665         avcodec_copy_context(ost->enc_ctx, st->codec);
1666         if (enc_config)
1667             av_dict_parse_string(&ost->encoder_opts, enc_config, "=", ",", 0);
1668     }
1669
1670     avformat_close_input(&ic);
1671     return err;
1672 }
1673
1674 static void init_output_filter(OutputFilter *ofilter, OptionsContext *o,
1675                                AVFormatContext *oc)
1676 {
1677     OutputStream *ost;
1678
1679     switch (avfilter_pad_get_type(ofilter->out_tmp->filter_ctx->output_pads,
1680                                   ofilter->out_tmp->pad_idx)) {
1681     case AVMEDIA_TYPE_VIDEO: ost = new_video_stream(o, oc, -1); break;
1682     case AVMEDIA_TYPE_AUDIO: ost = new_audio_stream(o, oc, -1); break;
1683     default:
1684         av_log(NULL, AV_LOG_FATAL, "Only video and audio filters are supported "
1685                "currently.\n");
1686         exit_program(1);
1687     }
1688
1689     ost->source_index = -1;
1690     ost->filter       = ofilter;
1691
1692     ofilter->ost      = ost;
1693
1694     if (ost->stream_copy) {
1695         av_log(NULL, AV_LOG_ERROR, "Streamcopy requested for output stream %d:%d, "
1696                "which is fed from a complex filtergraph. Filtering and streamcopy "
1697                "cannot be used together.\n", ost->file_index, ost->index);
1698         exit_program(1);
1699     }
1700
1701     if (ost->avfilter && (ost->filters || ost->filters_script)) {
1702         const char *opt = ost->filters ? "-vf/-af/-filter" : "-filter_script";
1703         av_log(NULL, AV_LOG_ERROR,
1704                "%s '%s' was specified through the %s option "
1705                "for output stream %d:%d, which is fed from a complex filtergraph.\n"
1706                "%s and -filter_complex cannot be used together for the same stream.\n",
1707                ost->filters ? "Filtergraph" : "Filtergraph script",
1708                ost->filters ? ost->filters : ost->filters_script,
1709                opt, ost->file_index, ost->index, opt);
1710         exit_program(1);
1711     }
1712
1713     if (configure_output_filter(ofilter->graph, ofilter, ofilter->out_tmp) < 0) {
1714         av_log(NULL, AV_LOG_FATAL, "Error configuring filter.\n");
1715         exit_program(1);
1716     }
1717     avfilter_inout_free(&ofilter->out_tmp);
1718 }
1719
1720 static int configure_complex_filters(void)
1721 {
1722     int i, ret = 0;
1723
1724     for (i = 0; i < nb_filtergraphs; i++)
1725         if (!filtergraphs[i]->graph &&
1726             (ret = configure_filtergraph(filtergraphs[i])) < 0)
1727             return ret;
1728     return 0;
1729 }
1730
1731 static int open_output_file(OptionsContext *o, const char *filename)
1732 {
1733     AVFormatContext *oc;
1734     int i, j, err;
1735     AVOutputFormat *file_oformat;
1736     OutputFile *of;
1737     OutputStream *ost;
1738     InputStream  *ist;
1739     AVDictionary *unused_opts = NULL;
1740     AVDictionaryEntry *e = NULL;
1741
1742     if (configure_complex_filters() < 0) {
1743         av_log(NULL, AV_LOG_FATAL, "Error configuring filters.\n");
1744         exit_program(1);
1745     }
1746
1747     if (o->stop_time != INT64_MAX && o->recording_time != INT64_MAX) {
1748         o->stop_time = INT64_MAX;
1749         av_log(NULL, AV_LOG_WARNING, "-t and -to cannot be used together; using -t.\n");
1750     }
1751
1752     if (o->stop_time != INT64_MAX && o->recording_time == INT64_MAX) {
1753         int64_t start_time = o->start_time == AV_NOPTS_VALUE ? 0 : o->start_time;
1754         if (o->stop_time <= start_time) {
1755             av_log(NULL, AV_LOG_ERROR, "-to value smaller than -ss; aborting.\n");
1756             exit_program(1);
1757         } else {
1758             o->recording_time = o->stop_time - start_time;
1759         }
1760     }
1761
1762     GROW_ARRAY(output_files, nb_output_files);
1763     of = av_mallocz(sizeof(*of));
1764     if (!of)
1765         exit_program(1);
1766     output_files[nb_output_files - 1] = of;
1767
1768     of->ost_index      = nb_output_streams;
1769     of->recording_time = o->recording_time;
1770     of->start_time     = o->start_time;
1771     of->limit_filesize = o->limit_filesize;
1772     of->shortest       = o->shortest;
1773     av_dict_copy(&of->opts, o->g->format_opts, 0);
1774
1775     if (!strcmp(filename, "-"))
1776         filename = "pipe:";
1777
1778     err = avformat_alloc_output_context2(&oc, NULL, o->format, filename);
1779     if (!oc) {
1780         print_error(filename, err);
1781         exit_program(1);
1782     }
1783
1784     of->ctx = oc;
1785     if (o->recording_time != INT64_MAX)
1786         oc->duration = o->recording_time;
1787
1788     file_oformat= oc->oformat;
1789     oc->interrupt_callback = int_cb;
1790
1791     /* create streams for all unlabeled output pads */
1792     for (i = 0; i < nb_filtergraphs; i++) {
1793         FilterGraph *fg = filtergraphs[i];
1794         for (j = 0; j < fg->nb_outputs; j++) {
1795             OutputFilter *ofilter = fg->outputs[j];
1796
1797             if (!ofilter->out_tmp || ofilter->out_tmp->name)
1798                 continue;
1799
1800             switch (avfilter_pad_get_type(ofilter->out_tmp->filter_ctx->output_pads,
1801                                           ofilter->out_tmp->pad_idx)) {
1802             case AVMEDIA_TYPE_VIDEO:    o->video_disable    = 1; break;
1803             case AVMEDIA_TYPE_AUDIO:    o->audio_disable    = 1; break;
1804             case AVMEDIA_TYPE_SUBTITLE: o->subtitle_disable = 1; break;
1805             }
1806             init_output_filter(ofilter, o, oc);
1807         }
1808     }
1809
1810     /* ffserver seeking with date=... needs a date reference */
1811     if (!strcmp(file_oformat->name, "ffm") &&
1812         av_strstart(filename, "http:", NULL)) {
1813         int err = parse_option(o, "metadata", "creation_time=now", options);
1814         if (err < 0) {
1815             print_error(filename, err);
1816             exit_program(1);
1817         }
1818     }
1819
1820     if (!strcmp(file_oformat->name, "ffm") && !override_ffserver &&
1821         av_strstart(filename, "http:", NULL)) {
1822         int j;
1823         /* special case for files sent to ffserver: we get the stream
1824            parameters from ffserver */
1825         int err = read_ffserver_streams(o, oc, filename);
1826         if (err < 0) {
1827             print_error(filename, err);
1828             exit_program(1);
1829         }
1830         for(j = nb_output_streams - oc->nb_streams; j < nb_output_streams; j++) {
1831             ost = output_streams[j];
1832             for (i = 0; i < nb_input_streams; i++) {
1833                 ist = input_streams[i];
1834                 if(ist->st->codec->codec_type == ost->st->codec->codec_type){
1835                     ost->sync_ist= ist;
1836                     ost->source_index= i;
1837                     if(ost->st->codec->codec_type == AVMEDIA_TYPE_AUDIO) ost->avfilter = av_strdup("anull");
1838                     if(ost->st->codec->codec_type == AVMEDIA_TYPE_VIDEO) ost->avfilter = av_strdup("null");
1839                     ist->discard = 0;
1840                     ist->st->discard = ist->user_set_discard;
1841                     break;
1842                 }
1843             }
1844             if(!ost->sync_ist){
1845                 av_log(NULL, AV_LOG_FATAL, "Missing %s stream which is required by this ffm\n", av_get_media_type_string(ost->st->codec->codec_type));
1846                 exit_program(1);
1847             }
1848         }
1849     } else if (!o->nb_stream_maps) {
1850         char *subtitle_codec_name = NULL;
1851         /* pick the "best" stream of each type */
1852
1853         /* video: highest resolution */
1854         if (!o->video_disable && av_guess_codec(oc->oformat, NULL, filename, NULL, AVMEDIA_TYPE_VIDEO) != AV_CODEC_ID_NONE) {
1855             int area = 0, idx = -1;
1856             int qcr = avformat_query_codec(oc->oformat, oc->oformat->video_codec, 0);
1857             for (i = 0; i < nb_input_streams; i++) {
1858                 int new_area;
1859                 ist = input_streams[i];
1860                 new_area = ist->st->codec->width * ist->st->codec->height;
1861                 if((qcr!=MKTAG('A', 'P', 'I', 'C')) && (ist->st->disposition & AV_DISPOSITION_ATTACHED_PIC))
1862                     new_area = 1;
1863                 if (ist->st->codec->codec_type == AVMEDIA_TYPE_VIDEO &&
1864                     new_area > area) {
1865                     if((qcr==MKTAG('A', 'P', 'I', 'C')) && !(ist->st->disposition & AV_DISPOSITION_ATTACHED_PIC))
1866                         continue;
1867                     area = new_area;
1868                     idx = i;
1869                 }
1870             }
1871             if (idx >= 0)
1872                 new_video_stream(o, oc, idx);
1873         }
1874
1875         /* audio: most channels */
1876         if (!o->audio_disable && av_guess_codec(oc->oformat, NULL, filename, NULL, AVMEDIA_TYPE_AUDIO) != AV_CODEC_ID_NONE) {
1877             int channels = 0, idx = -1;
1878             for (i = 0; i < nb_input_streams; i++) {
1879                 ist = input_streams[i];
1880                 if (ist->st->codec->codec_type == AVMEDIA_TYPE_AUDIO &&
1881                     ist->st->codec->channels > channels) {
1882                     channels = ist->st->codec->channels;
1883                     idx = i;
1884                 }
1885             }
1886             if (idx >= 0)
1887                 new_audio_stream(o, oc, idx);
1888         }
1889
1890         /* subtitles: pick first */
1891         MATCH_PER_TYPE_OPT(codec_names, str, subtitle_codec_name, oc, "s");
1892         if (!o->subtitle_disable && (avcodec_find_encoder(oc->oformat->subtitle_codec) || subtitle_codec_name)) {
1893             for (i = 0; i < nb_input_streams; i++)
1894                 if (input_streams[i]->st->codec->codec_type == AVMEDIA_TYPE_SUBTITLE) {
1895                     AVCodecDescriptor const *input_descriptor =
1896                         avcodec_descriptor_get(input_streams[i]->st->codec->codec_id);
1897                     AVCodecDescriptor const *output_descriptor = NULL;
1898                     AVCodec const *output_codec =
1899                         avcodec_find_encoder(oc->oformat->subtitle_codec);
1900                     int input_props = 0, output_props = 0;
1901                     if (output_codec)
1902                         output_descriptor = avcodec_descriptor_get(output_codec->id);
1903                     if (input_descriptor)
1904                         input_props = input_descriptor->props & (AV_CODEC_PROP_TEXT_SUB | AV_CODEC_PROP_BITMAP_SUB);
1905                     if (output_descriptor)
1906                         output_props = output_descriptor->props & (AV_CODEC_PROP_TEXT_SUB | AV_CODEC_PROP_BITMAP_SUB);
1907                     if (subtitle_codec_name ||
1908                         input_props & output_props ||
1909                         // Map dvb teletext which has neither property to any output subtitle encoder
1910                         input_descriptor && output_descriptor &&
1911                         (!input_descriptor->props ||
1912                          !output_descriptor->props)) {
1913                         new_subtitle_stream(o, oc, i);
1914                         break;
1915                     }
1916                 }
1917         }
1918         /* do something with data? */
1919     } else {
1920         for (i = 0; i < o->nb_stream_maps; i++) {
1921             StreamMap *map = &o->stream_maps[i];
1922
1923             if (map->disabled)
1924                 continue;
1925
1926             if (map->linklabel) {
1927                 FilterGraph *fg;
1928                 OutputFilter *ofilter = NULL;
1929                 int j, k;
1930
1931                 for (j = 0; j < nb_filtergraphs; j++) {
1932                     fg = filtergraphs[j];
1933                     for (k = 0; k < fg->nb_outputs; k++) {
1934                         AVFilterInOut *out = fg->outputs[k]->out_tmp;
1935                         if (out && !strcmp(out->name, map->linklabel)) {
1936                             ofilter = fg->outputs[k];
1937                             goto loop_end;
1938                         }
1939                     }
1940                 }
1941 loop_end:
1942                 if (!ofilter) {
1943                     av_log(NULL, AV_LOG_FATAL, "Output with label '%s' does not exist "
1944                            "in any defined filter graph, or was already used elsewhere.\n", map->linklabel);
1945                     exit_program(1);
1946                 }
1947                 init_output_filter(ofilter, o, oc);
1948             } else {
1949                 int src_idx = input_files[map->file_index]->ist_index + map->stream_index;
1950
1951                 ist = input_streams[input_files[map->file_index]->ist_index + map->stream_index];
1952                 if(o->subtitle_disable && ist->st->codec->codec_type == AVMEDIA_TYPE_SUBTITLE)
1953                     continue;
1954                 if(o->   audio_disable && ist->st->codec->codec_type == AVMEDIA_TYPE_AUDIO)
1955                     continue;
1956                 if(o->   video_disable && ist->st->codec->codec_type == AVMEDIA_TYPE_VIDEO)
1957                     continue;
1958                 if(o->    data_disable && ist->st->codec->codec_type == AVMEDIA_TYPE_DATA)
1959                     continue;
1960
1961                 switch (ist->st->codec->codec_type) {
1962                 case AVMEDIA_TYPE_VIDEO:      ost = new_video_stream     (o, oc, src_idx); break;
1963                 case AVMEDIA_TYPE_AUDIO:      ost = new_audio_stream     (o, oc, src_idx); break;
1964                 case AVMEDIA_TYPE_SUBTITLE:   ost = new_subtitle_stream  (o, oc, src_idx); break;
1965                 case AVMEDIA_TYPE_DATA:       ost = new_data_stream      (o, oc, src_idx); break;
1966                 case AVMEDIA_TYPE_ATTACHMENT: ost = new_attachment_stream(o, oc, src_idx); break;
1967                 default:
1968                     av_log(NULL, AV_LOG_FATAL, "Cannot map stream #%d:%d - unsupported type.\n",
1969                            map->file_index, map->stream_index);
1970                     exit_program(1);
1971                 }
1972             }
1973         }
1974     }
1975
1976     /* handle attached files */
1977     for (i = 0; i < o->nb_attachments; i++) {
1978         AVIOContext *pb;
1979         uint8_t *attachment;
1980         const char *p;
1981         int64_t len;
1982
1983         if ((err = avio_open2(&pb, o->attachments[i], AVIO_FLAG_READ, &int_cb, NULL)) < 0) {
1984             av_log(NULL, AV_LOG_FATAL, "Could not open attachment file %s.\n",
1985                    o->attachments[i]);
1986             exit_program(1);
1987         }
1988         if ((len = avio_size(pb)) <= 0) {
1989             av_log(NULL, AV_LOG_FATAL, "Could not get size of the attachment %s.\n",
1990                    o->attachments[i]);
1991             exit_program(1);
1992         }
1993         if (!(attachment = av_malloc(len))) {
1994             av_log(NULL, AV_LOG_FATAL, "Attachment %s too large to fit into memory.\n",
1995                    o->attachments[i]);
1996             exit_program(1);
1997         }
1998         avio_read(pb, attachment, len);
1999
2000         ost = new_attachment_stream(o, oc, -1);
2001         ost->stream_copy               = 0;
2002         ost->attachment_filename       = o->attachments[i];
2003         ost->finished                  = 1;
2004         ost->enc_ctx->extradata      = attachment;
2005         ost->enc_ctx->extradata_size = len;
2006
2007         p = strrchr(o->attachments[i], '/');
2008         av_dict_set(&ost->st->metadata, "filename", (p && *p) ? p + 1 : o->attachments[i], AV_DICT_DONT_OVERWRITE);
2009         avio_close(pb);
2010     }
2011
2012     for (i = nb_output_streams - oc->nb_streams; i < nb_output_streams; i++) { //for all streams of this output file
2013         AVDictionaryEntry *e;
2014         ost = output_streams[i];
2015
2016         if ((ost->stream_copy || ost->attachment_filename)
2017             && (e = av_dict_get(o->g->codec_opts, "flags", NULL, AV_DICT_IGNORE_SUFFIX))
2018             && (!e->key[5] || check_stream_specifier(oc, ost->st, e->key+6)))
2019             if (av_opt_set(ost->st->codec, "flags", e->value, 0) < 0)
2020                 exit_program(1);
2021     }
2022
2023     /* check if all codec options have been used */
2024     unused_opts = strip_specifiers(o->g->codec_opts);
2025     for (i = of->ost_index; i < nb_output_streams; i++) {
2026         e = NULL;
2027         while ((e = av_dict_get(output_streams[i]->encoder_opts, "", e,
2028                                 AV_DICT_IGNORE_SUFFIX)))
2029             av_dict_set(&unused_opts, e->key, NULL, 0);
2030     }
2031
2032     e = NULL;
2033     while ((e = av_dict_get(unused_opts, "", e, AV_DICT_IGNORE_SUFFIX))) {
2034         const AVClass *class = avcodec_get_class();
2035         const AVOption *option = av_opt_find(&class, e->key, NULL, 0,
2036                                              AV_OPT_SEARCH_CHILDREN | AV_OPT_SEARCH_FAKE_OBJ);
2037         const AVClass *fclass = avformat_get_class();
2038         const AVOption *foption = av_opt_find(&fclass, e->key, NULL, 0,
2039                                               AV_OPT_SEARCH_CHILDREN | AV_OPT_SEARCH_FAKE_OBJ);
2040         if (!option || foption)
2041             continue;
2042
2043
2044         if (!(option->flags & AV_OPT_FLAG_ENCODING_PARAM)) {
2045             av_log(NULL, AV_LOG_ERROR, "Codec AVOption %s (%s) specified for "
2046                    "output file #%d (%s) is not an encoding option.\n", e->key,
2047                    option->help ? option->help : "", nb_output_files - 1,
2048                    filename);
2049             exit_program(1);
2050         }
2051
2052         // gop_timecode is injected by generic code but not always used
2053         if (!strcmp(e->key, "gop_timecode"))
2054             continue;
2055
2056         av_log(NULL, AV_LOG_WARNING, "Codec AVOption %s (%s) specified for "
2057                "output file #%d (%s) has not been used for any stream. The most "
2058                "likely reason is either wrong type (e.g. a video option with "
2059                "no video streams) or that it is a private option of some encoder "
2060                "which was not actually used for any stream.\n", e->key,
2061                option->help ? option->help : "", nb_output_files - 1, filename);
2062     }
2063     av_dict_free(&unused_opts);
2064
2065     /* check filename in case of an image number is expected */
2066     if (oc->oformat->flags & AVFMT_NEEDNUMBER) {
2067         if (!av_filename_number_test(oc->filename)) {
2068             print_error(oc->filename, AVERROR(EINVAL));
2069             exit_program(1);
2070         }
2071     }
2072
2073     if (!(oc->oformat->flags & AVFMT_NOFILE)) {
2074         /* test if it already exists to avoid losing precious files */
2075         assert_file_overwrite(filename);
2076
2077         /* open the file */
2078         if ((err = avio_open2(&oc->pb, filename, AVIO_FLAG_WRITE,
2079                               &oc->interrupt_callback,
2080                               &of->opts)) < 0) {
2081             print_error(filename, err);
2082             exit_program(1);
2083         }
2084     } else if (strcmp(oc->oformat->name, "image2")==0 && !av_filename_number_test(filename))
2085         assert_file_overwrite(filename);
2086
2087     if (o->mux_preload) {
2088         av_dict_set_int(&of->opts, "preload", o->mux_preload*AV_TIME_BASE, 0);
2089     }
2090     oc->max_delay = (int)(o->mux_max_delay * AV_TIME_BASE);
2091
2092     /* copy metadata */
2093     for (i = 0; i < o->nb_metadata_map; i++) {
2094         char *p;
2095         int in_file_index = strtol(o->metadata_map[i].u.str, &p, 0);
2096
2097         if (in_file_index >= nb_input_files) {
2098             av_log(NULL, AV_LOG_FATAL, "Invalid input file index %d while processing metadata maps\n", in_file_index);
2099             exit_program(1);
2100         }
2101         copy_metadata(o->metadata_map[i].specifier, *p ? p + 1 : p, oc,
2102                       in_file_index >= 0 ?
2103                       input_files[in_file_index]->ctx : NULL, o);
2104     }
2105
2106     /* copy chapters */
2107     if (o->chapters_input_file >= nb_input_files) {
2108         if (o->chapters_input_file == INT_MAX) {
2109             /* copy chapters from the first input file that has them*/
2110             o->chapters_input_file = -1;
2111             for (i = 0; i < nb_input_files; i++)
2112                 if (input_files[i]->ctx->nb_chapters) {
2113                     o->chapters_input_file = i;
2114                     break;
2115                 }
2116         } else {
2117             av_log(NULL, AV_LOG_FATAL, "Invalid input file index %d in chapter mapping.\n",
2118                    o->chapters_input_file);
2119             exit_program(1);
2120         }
2121     }
2122     if (o->chapters_input_file >= 0)
2123         copy_chapters(input_files[o->chapters_input_file], of,
2124                       !o->metadata_chapters_manual);
2125
2126     /* copy global metadata by default */
2127     if (!o->metadata_global_manual && nb_input_files){
2128         av_dict_copy(&oc->metadata, input_files[0]->ctx->metadata,
2129                      AV_DICT_DONT_OVERWRITE);
2130         if(o->recording_time != INT64_MAX)
2131             av_dict_set(&oc->metadata, "duration", NULL, 0);
2132         av_dict_set(&oc->metadata, "creation_time", NULL, 0);
2133     }
2134     if (!o->metadata_streams_manual)
2135         for (i = of->ost_index; i < nb_output_streams; i++) {
2136             InputStream *ist;
2137             if (output_streams[i]->source_index < 0)         /* this is true e.g. for attached files */
2138                 continue;
2139             ist = input_streams[output_streams[i]->source_index];
2140             av_dict_copy(&output_streams[i]->st->metadata, ist->st->metadata, AV_DICT_DONT_OVERWRITE);
2141             if (!output_streams[i]->stream_copy)
2142                 av_dict_set(&output_streams[i]->st->metadata, "encoder", NULL, 0);
2143         }
2144
2145     /* process manually set metadata */
2146     for (i = 0; i < o->nb_metadata; i++) {
2147         AVDictionary **m;
2148         char type, *val;
2149         const char *stream_spec;
2150         int index = 0, j, ret = 0;
2151
2152         val = strchr(o->metadata[i].u.str, '=');
2153         if (!val) {
2154             av_log(NULL, AV_LOG_FATAL, "No '=' character in metadata string %s.\n",
2155                    o->metadata[i].u.str);
2156             exit_program(1);
2157         }
2158         *val++ = 0;
2159
2160         parse_meta_type(o->metadata[i].specifier, &type, &index, &stream_spec);
2161         if (type == 's') {
2162             for (j = 0; j < oc->nb_streams; j++) {
2163                 if ((ret = check_stream_specifier(oc, oc->streams[j], stream_spec)) > 0) {
2164                     av_dict_set(&oc->streams[j]->metadata, o->metadata[i].u.str, *val ? val : NULL, 0);
2165                 } else if (ret < 0)
2166                     exit_program(1);
2167             }
2168         }
2169         else {
2170             switch (type) {
2171             case 'g':
2172                 m = &oc->metadata;
2173                 break;
2174             case 'c':
2175                 if (index < 0 || index >= oc->nb_chapters) {
2176                     av_log(NULL, AV_LOG_FATAL, "Invalid chapter index %d in metadata specifier.\n", index);
2177                     exit_program(1);
2178                 }
2179                 m = &oc->chapters[index]->metadata;
2180                 break;
2181             default:
2182                 av_log(NULL, AV_LOG_FATAL, "Invalid metadata specifier %s.\n", o->metadata[i].specifier);
2183                 exit_program(1);
2184             }
2185             av_dict_set(m, o->metadata[i].u.str, *val ? val : NULL, 0);
2186         }
2187     }
2188
2189     return 0;
2190 }
2191
2192 static int opt_target(void *optctx, const char *opt, const char *arg)
2193 {
2194     OptionsContext *o = optctx;
2195     enum { PAL, NTSC, FILM, UNKNOWN } norm = UNKNOWN;
2196     static const char *const frame_rates[] = { "25", "30000/1001", "24000/1001" };
2197
2198     if (!strncmp(arg, "pal-", 4)) {
2199         norm = PAL;
2200         arg += 4;
2201     } else if (!strncmp(arg, "ntsc-", 5)) {
2202         norm = NTSC;
2203         arg += 5;
2204     } else if (!strncmp(arg, "film-", 5)) {
2205         norm = FILM;
2206         arg += 5;
2207     } else {
2208         /* Try to determine PAL/NTSC by peeking in the input files */
2209         if (nb_input_files) {
2210             int i, j, fr;
2211             for (j = 0; j < nb_input_files; j++) {
2212                 for (i = 0; i < input_files[j]->nb_streams; i++) {
2213                     AVCodecContext *c = input_files[j]->ctx->streams[i]->codec;
2214                     if (c->codec_type != AVMEDIA_TYPE_VIDEO ||
2215                         !c->time_base.num)
2216                         continue;
2217                     fr = c->time_base.den * 1000 / c->time_base.num;
2218                     if (fr == 25000) {
2219                         norm = PAL;
2220                         break;
2221                     } else if ((fr == 29970) || (fr == 23976)) {
2222                         norm = NTSC;
2223                         break;
2224                     }
2225                 }
2226                 if (norm != UNKNOWN)
2227                     break;
2228             }
2229         }
2230         if (norm != UNKNOWN)
2231             av_log(NULL, AV_LOG_INFO, "Assuming %s for target.\n", norm == PAL ? "PAL" : "NTSC");
2232     }
2233
2234     if (norm == UNKNOWN) {
2235         av_log(NULL, AV_LOG_FATAL, "Could not determine norm (PAL/NTSC/NTSC-Film) for target.\n");
2236         av_log(NULL, AV_LOG_FATAL, "Please prefix target with \"pal-\", \"ntsc-\" or \"film-\",\n");
2237         av_log(NULL, AV_LOG_FATAL, "or set a framerate with \"-r xxx\".\n");
2238         exit_program(1);
2239     }
2240
2241     if (!strcmp(arg, "vcd")) {
2242         opt_video_codec(o, "c:v", "mpeg1video");
2243         opt_audio_codec(o, "c:a", "mp2");
2244         parse_option(o, "f", "vcd", options);
2245
2246         parse_option(o, "s", norm == PAL ? "352x288" : "352x240", options);
2247         parse_option(o, "r", frame_rates[norm], options);
2248         opt_default(NULL, "g", norm == PAL ? "15" : "18");
2249
2250         opt_default(NULL, "b:v", "1150000");
2251         opt_default(NULL, "maxrate", "1150000");
2252         opt_default(NULL, "minrate", "1150000");
2253         opt_default(NULL, "bufsize", "327680"); // 40*1024*8;
2254
2255         opt_default(NULL, "b:a", "224000");
2256         parse_option(o, "ar", "44100", options);
2257         parse_option(o, "ac", "2", options);
2258
2259         opt_default(NULL, "packetsize", "2324");
2260         opt_default(NULL, "muxrate", "1411200"); // 2352 * 75 * 8;
2261
2262         /* We have to offset the PTS, so that it is consistent with the SCR.
2263            SCR starts at 36000, but the first two packs contain only padding
2264            and the first pack from the other stream, respectively, may also have
2265            been written before.
2266            So the real data starts at SCR 36000+3*1200. */
2267         o->mux_preload = (36000 + 3 * 1200) / 90000.0; // 0.44
2268     } else if (!strcmp(arg, "svcd")) {
2269
2270         opt_video_codec(o, "c:v", "mpeg2video");
2271         opt_audio_codec(o, "c:a", "mp2");
2272         parse_option(o, "f", "svcd", options);
2273
2274         parse_option(o, "s", norm == PAL ? "480x576" : "480x480", options);
2275         parse_option(o, "r", frame_rates[norm], options);
2276         parse_option(o, "pix_fmt", "yuv420p", options);
2277         opt_default(NULL, "g", norm == PAL ? "15" : "18");
2278
2279         opt_default(NULL, "b:v", "2040000");
2280         opt_default(NULL, "maxrate", "2516000");
2281         opt_default(NULL, "minrate", "0"); // 1145000;
2282         opt_default(NULL, "bufsize", "1835008"); // 224*1024*8;
2283         opt_default(NULL, "scan_offset", "1");
2284
2285         opt_default(NULL, "b:a", "224000");
2286         parse_option(o, "ar", "44100", options);
2287
2288         opt_default(NULL, "packetsize", "2324");
2289
2290     } else if (!strcmp(arg, "dvd")) {
2291
2292         opt_video_codec(o, "c:v", "mpeg2video");
2293         opt_audio_codec(o, "c:a", "ac3");
2294         parse_option(o, "f", "dvd", options);
2295
2296         parse_option(o, "s", norm == PAL ? "720x576" : "720x480", options);
2297         parse_option(o, "r", frame_rates[norm], options);
2298         parse_option(o, "pix_fmt", "yuv420p", options);
2299         opt_default(NULL, "g", norm == PAL ? "15" : "18");
2300
2301         opt_default(NULL, "b:v", "6000000");
2302         opt_default(NULL, "maxrate", "9000000");
2303         opt_default(NULL, "minrate", "0"); // 1500000;
2304         opt_default(NULL, "bufsize", "1835008"); // 224*1024*8;
2305
2306         opt_default(NULL, "packetsize", "2048");  // from www.mpucoder.com: DVD sectors contain 2048 bytes of data, this is also the size of one pack.
2307         opt_default(NULL, "muxrate", "10080000"); // from mplex project: data_rate = 1260000. mux_rate = data_rate * 8
2308
2309         opt_default(NULL, "b:a", "448000");
2310         parse_option(o, "ar", "48000", options);
2311
2312     } else if (!strncmp(arg, "dv", 2)) {
2313
2314         parse_option(o, "f", "dv", options);
2315
2316         parse_option(o, "s", norm == PAL ? "720x576" : "720x480", options);
2317         parse_option(o, "pix_fmt", !strncmp(arg, "dv50", 4) ? "yuv422p" :
2318                           norm == PAL ? "yuv420p" : "yuv411p", options);
2319         parse_option(o, "r", frame_rates[norm], options);
2320
2321         parse_option(o, "ar", "48000", options);
2322         parse_option(o, "ac", "2", options);
2323
2324     } else {
2325         av_log(NULL, AV_LOG_ERROR, "Unknown target: %s\n", arg);
2326         return AVERROR(EINVAL);
2327     }
2328
2329     av_dict_copy(&o->g->codec_opts,  codec_opts, AV_DICT_DONT_OVERWRITE);
2330     av_dict_copy(&o->g->format_opts, format_opts, AV_DICT_DONT_OVERWRITE);
2331
2332     return 0;
2333 }
2334
2335 static int opt_vstats_file(void *optctx, const char *opt, const char *arg)
2336 {
2337     av_free (vstats_filename);
2338     vstats_filename = av_strdup (arg);
2339     return 0;
2340 }
2341
2342 static int opt_vstats(void *optctx, const char *opt, const char *arg)
2343 {
2344     char filename[40];
2345     time_t today2 = time(NULL);
2346     struct tm *today = localtime(&today2);
2347
2348     snprintf(filename, sizeof(filename), "vstats_%02d%02d%02d.log", today->tm_hour, today->tm_min,
2349              today->tm_sec);
2350     return opt_vstats_file(NULL, opt, filename);
2351 }
2352
2353 static int opt_video_frames(void *optctx, const char *opt, const char *arg)
2354 {
2355     OptionsContext *o = optctx;
2356     return parse_option(o, "frames:v", arg, options);
2357 }
2358
2359 static int opt_audio_frames(void *optctx, const char *opt, const char *arg)
2360 {
2361     OptionsContext *o = optctx;
2362     return parse_option(o, "frames:a", arg, options);
2363 }
2364
2365 static int opt_data_frames(void *optctx, const char *opt, const char *arg)
2366 {
2367     OptionsContext *o = optctx;
2368     return parse_option(o, "frames:d", arg, options);
2369 }
2370
2371 static int opt_default_new(OptionsContext *o, const char *opt, const char *arg)
2372 {
2373     int ret;
2374     AVDictionary *cbak = codec_opts;
2375     AVDictionary *fbak = format_opts;
2376     codec_opts = NULL;
2377     format_opts = NULL;
2378
2379     ret = opt_default(NULL, opt, arg);
2380
2381     av_dict_copy(&o->g->codec_opts , codec_opts, 0);
2382     av_dict_copy(&o->g->format_opts, format_opts, 0);
2383     av_dict_free(&codec_opts);
2384     av_dict_free(&format_opts);
2385     codec_opts = cbak;
2386     format_opts = fbak;
2387
2388     return ret;
2389 }
2390
2391 static int opt_preset(void *optctx, const char *opt, const char *arg)
2392 {
2393     OptionsContext *o = optctx;
2394     FILE *f=NULL;
2395     char filename[1000], line[1000], tmp_line[1000];
2396     const char *codec_name = NULL;
2397
2398     tmp_line[0] = *opt;
2399     tmp_line[1] = 0;
2400     MATCH_PER_TYPE_OPT(codec_names, str, codec_name, NULL, tmp_line);
2401
2402     if (!(f = get_preset_file(filename, sizeof(filename), arg, *opt == 'f', codec_name))) {
2403         if(!strncmp(arg, "libx264-lossless", strlen("libx264-lossless"))){
2404             av_log(NULL, AV_LOG_FATAL, "Please use -preset <speed> -qp 0\n");
2405         }else
2406             av_log(NULL, AV_LOG_FATAL, "File for preset '%s' not found\n", arg);
2407         exit_program(1);
2408     }
2409
2410     while (fgets(line, sizeof(line), f)) {
2411         char *key = tmp_line, *value, *endptr;
2412
2413         if (strcspn(line, "#\n\r") == 0)
2414             continue;
2415         av_strlcpy(tmp_line, line, sizeof(tmp_line));
2416         if (!av_strtok(key,   "=",    &value) ||
2417             !av_strtok(value, "\r\n", &endptr)) {
2418             av_log(NULL, AV_LOG_FATAL, "%s: Invalid syntax: '%s'\n", filename, line);
2419             exit_program(1);
2420         }
2421         av_log(NULL, AV_LOG_DEBUG, "ffpreset[%s]: set '%s' = '%s'\n", filename, key, value);
2422
2423         if      (!strcmp(key, "acodec")) opt_audio_codec   (o, key, value);
2424         else if (!strcmp(key, "vcodec")) opt_video_codec   (o, key, value);
2425         else if (!strcmp(key, "scodec")) opt_subtitle_codec(o, key, value);
2426         else if (!strcmp(key, "dcodec")) opt_data_codec    (o, key, value);
2427         else if (opt_default_new(o, key, value) < 0) {
2428             av_log(NULL, AV_LOG_FATAL, "%s: Invalid option or argument: '%s', parsed as '%s' = '%s'\n",
2429                    filename, line, key, value);
2430             exit_program(1);
2431         }
2432     }
2433
2434     fclose(f);
2435
2436     return 0;
2437 }
2438
2439 static int opt_old2new(void *optctx, const char *opt, const char *arg)
2440 {
2441     OptionsContext *o = optctx;
2442     char *s = av_asprintf("%s:%c", opt + 1, *opt);
2443     int ret = parse_option(o, s, arg, options);
2444     av_free(s);
2445     return ret;
2446 }
2447
2448 static int opt_bitrate(void *optctx, const char *opt, const char *arg)
2449 {
2450     OptionsContext *o = optctx;
2451
2452     if(!strcmp(opt, "ab")){
2453         av_dict_set(&o->g->codec_opts, "b:a", arg, 0);
2454         return 0;
2455     } else if(!strcmp(opt, "b")){
2456         av_log(NULL, AV_LOG_WARNING, "Please use -b:a or -b:v, -b is ambiguous\n");
2457         av_dict_set(&o->g->codec_opts, "b:v", arg, 0);
2458         return 0;
2459     }
2460     av_dict_set(&o->g->codec_opts, opt, arg, 0);
2461     return 0;
2462 }
2463
2464 static int opt_qscale(void *optctx, const char *opt, const char *arg)
2465 {
2466     OptionsContext *o = optctx;
2467     char *s;
2468     int ret;
2469     if(!strcmp(opt, "qscale")){
2470         av_log(NULL, AV_LOG_WARNING, "Please use -q:a or -q:v, -qscale is ambiguous\n");
2471         return parse_option(o, "q:v", arg, options);
2472     }
2473     s = av_asprintf("q%s", opt + 6);
2474     ret = parse_option(o, s, arg, options);
2475     av_free(s);
2476     return ret;
2477 }
2478
2479 static int opt_profile(void *optctx, const char *opt, const char *arg)
2480 {
2481     OptionsContext *o = optctx;
2482     if(!strcmp(opt, "profile")){
2483         av_log(NULL, AV_LOG_WARNING, "Please use -profile:a or -profile:v, -profile is ambiguous\n");
2484         av_dict_set(&o->g->codec_opts, "profile:v", arg, 0);
2485         return 0;
2486     }
2487     av_dict_set(&o->g->codec_opts, opt, arg, 0);
2488     return 0;
2489 }
2490
2491 static int opt_video_filters(void *optctx, const char *opt, const char *arg)
2492 {
2493     OptionsContext *o = optctx;
2494     return parse_option(o, "filter:v", arg, options);
2495 }
2496
2497 static int opt_audio_filters(void *optctx, const char *opt, const char *arg)
2498 {
2499     OptionsContext *o = optctx;
2500     return parse_option(o, "filter:a", arg, options);
2501 }
2502
2503 static int opt_vsync(void *optctx, const char *opt, const char *arg)
2504 {
2505     if      (!av_strcasecmp(arg, "cfr"))         video_sync_method = VSYNC_CFR;
2506     else if (!av_strcasecmp(arg, "vfr"))         video_sync_method = VSYNC_VFR;
2507     else if (!av_strcasecmp(arg, "passthrough")) video_sync_method = VSYNC_PASSTHROUGH;
2508     else if (!av_strcasecmp(arg, "drop"))        video_sync_method = VSYNC_DROP;
2509
2510     if (video_sync_method == VSYNC_AUTO)
2511         video_sync_method = parse_number_or_die("vsync", arg, OPT_INT, VSYNC_AUTO, VSYNC_VFR);
2512     return 0;
2513 }
2514
2515 static int opt_timecode(void *optctx, const char *opt, const char *arg)
2516 {
2517     OptionsContext *o = optctx;
2518     char *tcr = av_asprintf("timecode=%s", arg);
2519     int ret = parse_option(o, "metadata:g", tcr, options);
2520     if (ret >= 0)
2521         ret = av_dict_set(&o->g->codec_opts, "gop_timecode", arg, 0);
2522     av_free(tcr);
2523     return 0;
2524 }
2525
2526 static int opt_channel_layout(void *optctx, const char *opt, const char *arg)
2527 {
2528     OptionsContext *o = optctx;
2529     char layout_str[32];
2530     char *stream_str;
2531     char *ac_str;
2532     int ret, channels, ac_str_size;
2533     uint64_t layout;
2534
2535     layout = av_get_channel_layout(arg);
2536     if (!layout) {
2537         av_log(NULL, AV_LOG_ERROR, "Unknown channel layout: %s\n", arg);
2538         return AVERROR(EINVAL);
2539     }
2540     snprintf(layout_str, sizeof(layout_str), "%"PRIu64, layout);
2541     ret = opt_default_new(o, opt, layout_str);
2542     if (ret < 0)
2543         return ret;
2544
2545     /* set 'ac' option based on channel layout */
2546     channels = av_get_channel_layout_nb_channels(layout);
2547     snprintf(layout_str, sizeof(layout_str), "%d", channels);
2548     stream_str = strchr(opt, ':');
2549     ac_str_size = 3 + (stream_str ? strlen(stream_str) : 0);
2550     ac_str = av_mallocz(ac_str_size);
2551     if (!ac_str)
2552         return AVERROR(ENOMEM);
2553     av_strlcpy(ac_str, "ac", 3);
2554     if (stream_str)
2555         av_strlcat(ac_str, stream_str, ac_str_size);
2556     ret = parse_option(o, ac_str, layout_str, options);
2557     av_free(ac_str);
2558
2559     return ret;
2560 }
2561
2562 static int opt_audio_qscale(void *optctx, const char *opt, const char *arg)
2563 {
2564     OptionsContext *o = optctx;
2565     return parse_option(o, "q:a", arg, options);
2566 }
2567
2568 static int opt_filter_complex(void *optctx, const char *opt, const char *arg)
2569 {
2570     GROW_ARRAY(filtergraphs, nb_filtergraphs);
2571     if (!(filtergraphs[nb_filtergraphs - 1] = av_mallocz(sizeof(*filtergraphs[0]))))
2572         return AVERROR(ENOMEM);
2573     filtergraphs[nb_filtergraphs - 1]->index      = nb_filtergraphs - 1;
2574     filtergraphs[nb_filtergraphs - 1]->graph_desc = av_strdup(arg);
2575     if (!filtergraphs[nb_filtergraphs - 1]->graph_desc)
2576         return AVERROR(ENOMEM);
2577     return 0;
2578 }
2579
2580 static int opt_filter_complex_script(void *optctx, const char *opt, const char *arg)
2581 {
2582     uint8_t *graph_desc = read_file(arg);
2583     if (!graph_desc)
2584         return AVERROR(EINVAL);
2585
2586     GROW_ARRAY(filtergraphs, nb_filtergraphs);
2587     if (!(filtergraphs[nb_filtergraphs - 1] = av_mallocz(sizeof(*filtergraphs[0]))))
2588         return AVERROR(ENOMEM);
2589     filtergraphs[nb_filtergraphs - 1]->index      = nb_filtergraphs - 1;
2590     filtergraphs[nb_filtergraphs - 1]->graph_desc = graph_desc;
2591     return 0;
2592 }
2593
2594 void show_help_default(const char *opt, const char *arg)
2595 {
2596     /* per-file options have at least one of those set */
2597     const int per_file = OPT_SPEC | OPT_OFFSET | OPT_PERFILE;
2598     int show_advanced = 0, show_avoptions = 0;
2599
2600     if (opt && *opt) {
2601         if (!strcmp(opt, "long"))
2602             show_advanced = 1;
2603         else if (!strcmp(opt, "full"))
2604             show_advanced = show_avoptions = 1;
2605         else
2606             av_log(NULL, AV_LOG_ERROR, "Unknown help option '%s'.\n", opt);
2607     }
2608
2609     show_usage();
2610
2611     printf("Getting help:\n"
2612            "    -h      -- print basic options\n"
2613            "    -h long -- print more options\n"
2614            "    -h full -- print all options (including all format and codec specific options, very long)\n"
2615            "    See man %s for detailed description of the options.\n"
2616            "\n", program_name);
2617
2618     show_help_options(options, "Print help / information / capabilities:",
2619                       OPT_EXIT, 0, 0);
2620
2621     show_help_options(options, "Global options (affect whole program "
2622                       "instead of just one file:",
2623                       0, per_file | OPT_EXIT | OPT_EXPERT, 0);
2624     if (show_advanced)
2625         show_help_options(options, "Advanced global options:", OPT_EXPERT,
2626                           per_file | OPT_EXIT, 0);
2627
2628     show_help_options(options, "Per-file main options:", 0,
2629                       OPT_EXPERT | OPT_AUDIO | OPT_VIDEO | OPT_SUBTITLE |
2630                       OPT_EXIT, per_file);
2631     if (show_advanced)
2632         show_help_options(options, "Advanced per-file options:",
2633                           OPT_EXPERT, OPT_AUDIO | OPT_VIDEO | OPT_SUBTITLE, per_file);
2634
2635     show_help_options(options, "Video options:",
2636                       OPT_VIDEO, OPT_EXPERT | OPT_AUDIO, 0);
2637     if (show_advanced)
2638         show_help_options(options, "Advanced Video options:",
2639                           OPT_EXPERT | OPT_VIDEO, OPT_AUDIO, 0);
2640
2641     show_help_options(options, "Audio options:",
2642                       OPT_AUDIO, OPT_EXPERT | OPT_VIDEO, 0);
2643     if (show_advanced)
2644         show_help_options(options, "Advanced Audio options:",
2645                           OPT_EXPERT | OPT_AUDIO, OPT_VIDEO, 0);
2646     show_help_options(options, "Subtitle options:",
2647                       OPT_SUBTITLE, 0, 0);
2648     printf("\n");
2649
2650     if (show_avoptions) {
2651         int flags = AV_OPT_FLAG_DECODING_PARAM | AV_OPT_FLAG_ENCODING_PARAM;
2652         show_help_children(avcodec_get_class(), flags);
2653         show_help_children(avformat_get_class(), flags);
2654 #if CONFIG_SWSCALE
2655         show_help_children(sws_get_class(), flags);
2656 #endif
2657         show_help_children(swr_get_class(), AV_OPT_FLAG_AUDIO_PARAM);
2658         show_help_children(avfilter_get_class(), AV_OPT_FLAG_VIDEO_PARAM | AV_OPT_FLAG_AUDIO_PARAM | AV_OPT_FLAG_FILTERING_PARAM);
2659     }
2660 }
2661
2662 void show_usage(void)
2663 {
2664     av_log(NULL, AV_LOG_INFO, "Hyper fast Audio and Video encoder\n");
2665     av_log(NULL, AV_LOG_INFO, "usage: %s [options] [[infile options] -i infile]... {[outfile options] outfile}...\n", program_name);
2666     av_log(NULL, AV_LOG_INFO, "\n");
2667 }
2668
2669 enum OptGroup {
2670     GROUP_OUTFILE,
2671     GROUP_INFILE,
2672 };
2673
2674 static const OptionGroupDef groups[] = {
2675     [GROUP_OUTFILE] = { "output file",  NULL, OPT_OUTPUT },
2676     [GROUP_INFILE]  = { "input file",   "i",  OPT_INPUT },
2677 };
2678
2679 static int open_files(OptionGroupList *l, const char *inout,
2680                       int (*open_file)(OptionsContext*, const char*))
2681 {
2682     int i, ret;
2683
2684     for (i = 0; i < l->nb_groups; i++) {
2685         OptionGroup *g = &l->groups[i];
2686         OptionsContext o;
2687
2688         init_options(&o);
2689         o.g = g;
2690
2691         ret = parse_optgroup(&o, g);
2692         if (ret < 0) {
2693             av_log(NULL, AV_LOG_ERROR, "Error parsing options for %s file "
2694                    "%s.\n", inout, g->arg);
2695             return ret;
2696         }
2697
2698         av_log(NULL, AV_LOG_DEBUG, "Opening an %s file: %s.\n", inout, g->arg);
2699         ret = open_file(&o, g->arg);
2700         uninit_options(&o);
2701         if (ret < 0) {
2702             av_log(NULL, AV_LOG_ERROR, "Error opening %s file %s.\n",
2703                    inout, g->arg);
2704             return ret;
2705         }
2706         av_log(NULL, AV_LOG_DEBUG, "Successfully opened the file.\n");
2707     }
2708
2709     return 0;
2710 }
2711
2712 int ffmpeg_parse_options(int argc, char **argv)
2713 {
2714     OptionParseContext octx;
2715     uint8_t error[128];
2716     int ret;
2717
2718     memset(&octx, 0, sizeof(octx));
2719
2720     /* split the commandline into an internal representation */
2721     ret = split_commandline(&octx, argc, argv, options, groups,
2722                             FF_ARRAY_ELEMS(groups));
2723     if (ret < 0) {
2724         av_log(NULL, AV_LOG_FATAL, "Error splitting the argument list: ");
2725         goto fail;
2726     }
2727
2728     /* apply global options */
2729     ret = parse_optgroup(NULL, &octx.global_opts);
2730     if (ret < 0) {
2731         av_log(NULL, AV_LOG_FATAL, "Error parsing global options: ");
2732         goto fail;
2733     }
2734
2735     /* open input files */
2736     ret = open_files(&octx.groups[GROUP_INFILE], "input", open_input_file);
2737     if (ret < 0) {
2738         av_log(NULL, AV_LOG_FATAL, "Error opening input files: ");
2739         goto fail;
2740     }
2741
2742     /* open output files */
2743     ret = open_files(&octx.groups[GROUP_OUTFILE], "output", open_output_file);
2744     if (ret < 0) {
2745         av_log(NULL, AV_LOG_FATAL, "Error opening output files: ");
2746         goto fail;
2747     }
2748
2749 fail:
2750     uninit_parse_context(&octx);
2751     if (ret < 0) {
2752         av_strerror(ret, error, sizeof(error));
2753         av_log(NULL, AV_LOG_FATAL, "%s\n", error);
2754     }
2755     return ret;
2756 }
2757
2758 static int opt_progress(void *optctx, const char *opt, const char *arg)
2759 {
2760     AVIOContext *avio = NULL;
2761     int ret;
2762
2763     if (!strcmp(arg, "-"))
2764         arg = "pipe:";
2765     ret = avio_open2(&avio, arg, AVIO_FLAG_WRITE, &int_cb, NULL);
2766     if (ret < 0) {
2767         av_log(NULL, AV_LOG_ERROR, "Failed to open progress URL \"%s\": %s\n",
2768                arg, av_err2str(ret));
2769         return ret;
2770     }
2771     progress_avio = avio;
2772     return 0;
2773 }
2774
2775 #define OFFSET(x) offsetof(OptionsContext, x)
2776 const OptionDef options[] = {
2777     /* main options */
2778 #include "cmdutils_common_opts.h"
2779     { "f",              HAS_ARG | OPT_STRING | OPT_OFFSET |
2780                         OPT_INPUT | OPT_OUTPUT,                      { .off       = OFFSET(format) },
2781         "force format", "fmt" },
2782     { "y",              OPT_BOOL,                                    {              &file_overwrite },
2783         "overwrite output files" },
2784     { "n",              OPT_BOOL,                                    {              &no_file_overwrite },
2785         "never overwrite output files" },
2786     { "c",              HAS_ARG | OPT_STRING | OPT_SPEC |
2787                         OPT_INPUT | OPT_OUTPUT,                      { .off       = OFFSET(codec_names) },
2788         "codec name", "codec" },
2789     { "codec",          HAS_ARG | OPT_STRING | OPT_SPEC |
2790                         OPT_INPUT | OPT_OUTPUT,                      { .off       = OFFSET(codec_names) },
2791         "codec name", "codec" },
2792     { "pre",            HAS_ARG | OPT_STRING | OPT_SPEC |
2793                         OPT_OUTPUT,                                  { .off       = OFFSET(presets) },
2794         "preset name", "preset" },
2795     { "map",            HAS_ARG | OPT_EXPERT | OPT_PERFILE |
2796                         OPT_OUTPUT,                                  { .func_arg = opt_map },
2797         "set input stream mapping",
2798         "[-]input_file_id[:stream_specifier][,sync_file_id[:stream_specifier]]" },
2799     { "map_channel",    HAS_ARG | OPT_EXPERT | OPT_PERFILE | OPT_OUTPUT, { .func_arg = opt_map_channel },
2800         "map an audio channel from one stream to another", "file.stream.channel[:syncfile.syncstream]" },
2801     { "map_metadata",   HAS_ARG | OPT_STRING | OPT_SPEC |
2802                         OPT_OUTPUT,                                  { .off       = OFFSET(metadata_map) },
2803         "set metadata information of outfile from infile",
2804         "outfile[,metadata]:infile[,metadata]" },
2805     { "map_chapters",   HAS_ARG | OPT_INT | OPT_EXPERT | OPT_OFFSET |
2806                         OPT_OUTPUT,                                  { .off = OFFSET(chapters_input_file) },
2807         "set chapters mapping", "input_file_index" },
2808     { "t",              HAS_ARG | OPT_TIME | OPT_OFFSET |
2809                         OPT_INPUT | OPT_OUTPUT,                      { .off = OFFSET(recording_time) },
2810         "record or transcode \"duration\" seconds of audio/video",
2811         "duration" },
2812     { "to",             HAS_ARG | OPT_TIME | OPT_OFFSET | OPT_OUTPUT,  { .off = OFFSET(stop_time) },
2813         "record or transcode stop time", "time_stop" },
2814     { "fs",             HAS_ARG | OPT_INT64 | OPT_OFFSET | OPT_OUTPUT, { .off = OFFSET(limit_filesize) },
2815         "set the limit file size in bytes", "limit_size" },
2816     { "ss",             HAS_ARG | OPT_TIME | OPT_OFFSET |
2817                         OPT_INPUT | OPT_OUTPUT,                      { .off = OFFSET(start_time) },
2818         "set the start time offset", "time_off" },
2819     { "accurate_seek",  OPT_BOOL | OPT_OFFSET | OPT_EXPERT |
2820                         OPT_INPUT,                                   { .off = OFFSET(accurate_seek) },
2821         "enable/disable accurate seeking with -ss" },
2822     { "itsoffset",      HAS_ARG | OPT_TIME | OPT_OFFSET |
2823                         OPT_EXPERT | OPT_INPUT,                      { .off = OFFSET(input_ts_offset) },
2824         "set the input ts offset", "time_off" },
2825     { "itsscale",       HAS_ARG | OPT_DOUBLE | OPT_SPEC |
2826                         OPT_EXPERT | OPT_INPUT,                      { .off = OFFSET(ts_scale) },
2827         "set the input ts scale", "scale" },
2828     { "timestamp",      HAS_ARG | OPT_PERFILE,                       { .func_arg = opt_recording_timestamp },
2829         "set the recording timestamp ('now' to set the current time)", "time" },
2830     { "metadata",       HAS_ARG | OPT_STRING | OPT_SPEC | OPT_OUTPUT, { .off = OFFSET(metadata) },
2831         "add metadata", "string=string" },
2832     { "dframes",        HAS_ARG | OPT_PERFILE | OPT_EXPERT |
2833                         OPT_OUTPUT,                                  { .func_arg = opt_data_frames },
2834         "set the number of data frames to output", "number" },
2835     { "benchmark",      OPT_BOOL | OPT_EXPERT,                       { &do_benchmark },
2836         "add timings for benchmarking" },
2837     { "benchmark_all",  OPT_BOOL | OPT_EXPERT,                       { &do_benchmark_all },
2838       "add timings for each task" },
2839     { "progress",       HAS_ARG | OPT_EXPERT,                        { .func_arg = opt_progress },
2840       "write program-readable progress information", "url" },
2841     { "stdin",          OPT_BOOL | OPT_EXPERT,                       { &stdin_interaction },
2842       "enable or disable interaction on standard input" },
2843     { "timelimit",      HAS_ARG | OPT_EXPERT,                        { .func_arg = opt_timelimit },
2844         "set max runtime in seconds", "limit" },
2845     { "dump",           OPT_BOOL | OPT_EXPERT,                       { &do_pkt_dump },
2846         "dump each input packet" },
2847     { "hex",            OPT_BOOL | OPT_EXPERT,                       { &do_hex_dump },
2848         "when dumping packets, also dump the payload" },
2849     { "re",             OPT_BOOL | OPT_EXPERT | OPT_OFFSET |
2850                         OPT_INPUT,                                   { .off = OFFSET(rate_emu) },
2851         "read input at native frame rate", "" },
2852     { "target",         HAS_ARG | OPT_PERFILE | OPT_OUTPUT,          { .func_arg = opt_target },
2853         "specify target file type (\"vcd\", \"svcd\", \"dvd\","
2854         " \"dv\", \"dv50\", \"pal-vcd\", \"ntsc-svcd\", ...)", "type" },
2855     { "vsync",          HAS_ARG | OPT_EXPERT,                        { opt_vsync },
2856         "video sync method", "" },
2857     { "async",          HAS_ARG | OPT_INT | OPT_EXPERT,              { &audio_sync_method },
2858         "audio sync method", "" },
2859     { "adrift_threshold", HAS_ARG | OPT_FLOAT | OPT_EXPERT,          { &audio_drift_threshold },
2860         "audio drift threshold", "threshold" },
2861     { "copyts",         OPT_BOOL | OPT_EXPERT,                       { &copy_ts },
2862         "copy timestamps" },
2863     { "start_at_zero",  OPT_BOOL | OPT_EXPERT,                       { &start_at_zero },
2864         "shift input timestamps to start at 0 when using copyts" },
2865     { "copytb",         HAS_ARG | OPT_INT | OPT_EXPERT,              { &copy_tb },
2866         "copy input stream time base when stream copying", "mode" },
2867     { "shortest",       OPT_BOOL | OPT_EXPERT | OPT_OFFSET |
2868                         OPT_OUTPUT,                                  { .off = OFFSET(shortest) },
2869         "finish encoding within shortest input" },
2870     { "apad",           OPT_STRING | HAS_ARG | OPT_SPEC |
2871                         OPT_OUTPUT,                                  { .off = OFFSET(apad) },
2872         "audio pad", "" },
2873     { "dts_delta_threshold", HAS_ARG | OPT_FLOAT | OPT_EXPERT,       { &dts_delta_threshold },
2874         "timestamp discontinuity delta threshold", "threshold" },
2875     { "dts_error_threshold", HAS_ARG | OPT_FLOAT | OPT_EXPERT,       { &dts_error_threshold },
2876         "timestamp error delta threshold", "threshold" },
2877     { "xerror",         OPT_BOOL | OPT_EXPERT,                       { &exit_on_error },
2878         "exit on error", "error" },
2879     { "copyinkf",       OPT_BOOL | OPT_EXPERT | OPT_SPEC |
2880                         OPT_OUTPUT,                                  { .off = OFFSET(copy_initial_nonkeyframes) },
2881         "copy initial non-keyframes" },
2882     { "copypriorss",    OPT_INT | HAS_ARG | OPT_EXPERT | OPT_SPEC | OPT_OUTPUT,   { .off = OFFSET(copy_prior_start) },
2883         "copy or discard frames before start time" },
2884     { "frames",         OPT_INT64 | HAS_ARG | OPT_SPEC | OPT_OUTPUT, { .off = OFFSET(max_frames) },
2885         "set the number of frames to output", "number" },
2886     { "tag",            OPT_STRING | HAS_ARG | OPT_SPEC |
2887                         OPT_EXPERT | OPT_OUTPUT | OPT_INPUT,         { .off = OFFSET(codec_tags) },
2888         "force codec tag/fourcc", "fourcc/tag" },
2889     { "q",              HAS_ARG | OPT_EXPERT | OPT_DOUBLE |
2890                         OPT_SPEC | OPT_OUTPUT,                       { .off = OFFSET(qscale) },
2891         "use fixed quality scale (VBR)", "q" },
2892     { "qscale",         HAS_ARG | OPT_EXPERT | OPT_PERFILE |
2893                         OPT_OUTPUT,                                  { .func_arg = opt_qscale },
2894         "use fixed quality scale (VBR)", "q" },
2895     { "profile",        HAS_ARG | OPT_EXPERT | OPT_PERFILE | OPT_OUTPUT, { .func_arg = opt_profile },
2896         "set profile", "profile" },
2897     { "filter",         HAS_ARG | OPT_STRING | OPT_SPEC | OPT_OUTPUT, { .off = OFFSET(filters) },
2898         "set stream filtergraph", "filter_graph" },
2899     { "filter_script",  HAS_ARG | OPT_STRING | OPT_SPEC | OPT_OUTPUT, { .off = OFFSET(filter_scripts) },
2900         "read stream filtergraph description from a file", "filename" },
2901     { "reinit_filter",  HAS_ARG | OPT_INT | OPT_SPEC | OPT_INPUT,    { .off = OFFSET(reinit_filters) },
2902         "reinit filtergraph on input parameter changes", "" },
2903     { "filter_complex", HAS_ARG | OPT_EXPERT,                        { .func_arg = opt_filter_complex },
2904         "create a complex filtergraph", "graph_description" },
2905     { "lavfi",          HAS_ARG | OPT_EXPERT,                        { .func_arg = opt_filter_complex },
2906         "create a complex filtergraph", "graph_description" },
2907     { "filter_complex_script", HAS_ARG | OPT_EXPERT,                 { .func_arg = opt_filter_complex_script },
2908         "read complex filtergraph description from a file", "filename" },
2909     { "stats",          OPT_BOOL,                                    { &print_stats },
2910         "print progress report during encoding", },
2911     { "attach",         HAS_ARG | OPT_PERFILE | OPT_EXPERT |
2912                         OPT_OUTPUT,                                  { .func_arg = opt_attach },
2913         "add an attachment to the output file", "filename" },
2914     { "dump_attachment", HAS_ARG | OPT_STRING | OPT_SPEC |
2915                          OPT_EXPERT | OPT_INPUT,                     { .off = OFFSET(dump_attachment) },
2916         "extract an attachment into a file", "filename" },
2917     { "debug_ts",       OPT_BOOL | OPT_EXPERT,                       { &debug_ts },
2918         "print timestamp debugging info" },
2919     { "max_error_rate",  HAS_ARG | OPT_FLOAT,                        { &max_error_rate },
2920         "maximum error rate", "ratio of errors (0.0: no errors, 1.0: 100% errors) above which ffmpeg returns an error instead of success." },
2921     { "discard",        OPT_STRING | HAS_ARG | OPT_SPEC |
2922                         OPT_INPUT,                                   { .off = OFFSET(discard) },
2923         "discard", "" },
2924
2925     /* video options */
2926     { "vframes",      OPT_VIDEO | HAS_ARG  | OPT_PERFILE | OPT_OUTPUT,           { .func_arg = opt_video_frames },
2927         "set the number of video frames to output", "number" },
2928     { "r",            OPT_VIDEO | HAS_ARG  | OPT_STRING | OPT_SPEC |
2929                       OPT_INPUT | OPT_OUTPUT,                                    { .off = OFFSET(frame_rates) },
2930         "set frame rate (Hz value, fraction or abbreviation)", "rate" },
2931     { "s",            OPT_VIDEO | HAS_ARG | OPT_SUBTITLE | OPT_STRING | OPT_SPEC |
2932                       OPT_INPUT | OPT_OUTPUT,                                    { .off = OFFSET(frame_sizes) },
2933         "set frame size (WxH or abbreviation)", "size" },
2934     { "aspect",       OPT_VIDEO | HAS_ARG  | OPT_STRING | OPT_SPEC |
2935                       OPT_OUTPUT,                                                { .off = OFFSET(frame_aspect_ratios) },
2936         "set aspect ratio (4:3, 16:9 or 1.3333, 1.7777)", "aspect" },
2937     { "pix_fmt",      OPT_VIDEO | HAS_ARG | OPT_EXPERT  | OPT_STRING | OPT_SPEC |
2938                       OPT_INPUT | OPT_OUTPUT,                                    { .off = OFFSET(frame_pix_fmts) },
2939         "set pixel format", "format" },
2940     { "bits_per_raw_sample", OPT_VIDEO | OPT_INT | HAS_ARG,                      { &frame_bits_per_raw_sample },
2941         "set the number of bits per raw sample", "number" },
2942     { "intra",        OPT_VIDEO | OPT_BOOL | OPT_EXPERT,                         { &intra_only },
2943         "deprecated use -g 1" },
2944     { "vn",           OPT_VIDEO | OPT_BOOL  | OPT_OFFSET | OPT_INPUT | OPT_OUTPUT,{ .off = OFFSET(video_disable) },
2945         "disable video" },
2946     { "rc_override",  OPT_VIDEO | HAS_ARG | OPT_EXPERT  | OPT_STRING | OPT_SPEC |
2947                       OPT_OUTPUT,                                                { .off = OFFSET(rc_overrides) },
2948         "rate control override for specific intervals", "override" },
2949     { "vcodec",       OPT_VIDEO | HAS_ARG  | OPT_PERFILE | OPT_INPUT |
2950                       OPT_OUTPUT,                                                { .func_arg = opt_video_codec },
2951         "force video codec ('copy' to copy stream)", "codec" },
2952     { "sameq",        OPT_VIDEO | OPT_EXPERT ,                                   { .func_arg = opt_sameq },
2953         "Removed" },
2954     { "same_quant",   OPT_VIDEO | OPT_EXPERT ,                                   { .func_arg = opt_sameq },
2955         "Removed" },
2956     { "timecode",     OPT_VIDEO | HAS_ARG | OPT_PERFILE | OPT_OUTPUT,            { .func_arg = opt_timecode },
2957         "set initial TimeCode value.", "hh:mm:ss[:;.]ff" },
2958     { "pass",         OPT_VIDEO | HAS_ARG | OPT_SPEC | OPT_INT | OPT_OUTPUT,     { .off = OFFSET(pass) },
2959         "select the pass number (1 to 3)", "n" },
2960     { "passlogfile",  OPT_VIDEO | HAS_ARG | OPT_STRING | OPT_EXPERT | OPT_SPEC |
2961                       OPT_OUTPUT,                                                { .off = OFFSET(passlogfiles) },
2962         "select two pass log file name prefix", "prefix" },
2963     { "deinterlace",  OPT_VIDEO | OPT_BOOL | OPT_EXPERT,                         { &do_deinterlace },
2964         "this option is deprecated, use the yadif filter instead" },
2965     { "psnr",         OPT_VIDEO | OPT_BOOL | OPT_EXPERT,                         { &do_psnr },
2966         "calculate PSNR of compressed frames" },
2967     { "vstats",       OPT_VIDEO | OPT_EXPERT ,                                   { &opt_vstats },
2968         "dump video coding statistics to file" },
2969     { "vstats_file",  OPT_VIDEO | HAS_ARG | OPT_EXPERT ,                         { opt_vstats_file },
2970         "dump video coding statistics to file", "file" },
2971     { "vf",           OPT_VIDEO | HAS_ARG  | OPT_PERFILE | OPT_OUTPUT,           { .func_arg = opt_video_filters },
2972         "set video filters", "filter_graph" },
2973     { "intra_matrix", OPT_VIDEO | HAS_ARG | OPT_EXPERT  | OPT_STRING | OPT_SPEC |
2974                       OPT_OUTPUT,                                                { .off = OFFSET(intra_matrices) },
2975         "specify intra matrix coeffs", "matrix" },
2976     { "inter_matrix", OPT_VIDEO | HAS_ARG | OPT_EXPERT  | OPT_STRING | OPT_SPEC |
2977                       OPT_OUTPUT,                                                { .off = OFFSET(inter_matrices) },
2978         "specify inter matrix coeffs", "matrix" },
2979     { "chroma_intra_matrix", OPT_VIDEO | HAS_ARG | OPT_EXPERT  | OPT_STRING | OPT_SPEC |
2980                       OPT_OUTPUT,                                                { .off = OFFSET(chroma_intra_matrices) },
2981         "specify intra matrix coeffs", "matrix" },
2982     { "top",          OPT_VIDEO | HAS_ARG | OPT_EXPERT  | OPT_INT| OPT_SPEC |
2983                       OPT_INPUT | OPT_OUTPUT,                                    { .off = OFFSET(top_field_first) },
2984         "top=1/bottom=0/auto=-1 field first", "" },
2985     { "vtag",         OPT_VIDEO | HAS_ARG | OPT_EXPERT  | OPT_PERFILE |
2986                       OPT_OUTPUT,                                                { .func_arg = opt_old2new },
2987         "force video tag/fourcc", "fourcc/tag" },
2988     { "qphist",       OPT_VIDEO | OPT_BOOL | OPT_EXPERT ,                        { &qp_hist },
2989         "show QP histogram" },
2990     { "force_fps",    OPT_VIDEO | OPT_BOOL | OPT_EXPERT  | OPT_SPEC |
2991                       OPT_OUTPUT,                                                { .off = OFFSET(force_fps) },
2992         "force the selected framerate, disable the best supported framerate selection" },
2993     { "streamid",     OPT_VIDEO | HAS_ARG | OPT_EXPERT | OPT_PERFILE |
2994                       OPT_OUTPUT,                                                { .func_arg = opt_streamid },
2995         "set the value of an outfile streamid", "streamIndex:value" },
2996     { "force_key_frames", OPT_VIDEO | OPT_STRING | HAS_ARG | OPT_EXPERT |
2997                           OPT_SPEC | OPT_OUTPUT,                                 { .off = OFFSET(forced_key_frames) },
2998         "force key frames at specified timestamps", "timestamps" },
2999     { "ab",           OPT_VIDEO | HAS_ARG | OPT_PERFILE | OPT_OUTPUT,            { .func_arg = opt_bitrate },
3000         "audio bitrate (please use -b:a)", "bitrate" },
3001     { "b",            OPT_VIDEO | HAS_ARG | OPT_PERFILE | OPT_OUTPUT,            { .func_arg = opt_bitrate },
3002         "video bitrate (please use -b:v)", "bitrate" },
3003     { "hwaccel",          OPT_VIDEO | OPT_STRING | HAS_ARG | OPT_EXPERT |
3004                           OPT_SPEC | OPT_INPUT,                                  { .off = OFFSET(hwaccels) },
3005         "use HW accelerated decoding", "hwaccel name" },
3006     { "hwaccel_device",   OPT_VIDEO | OPT_STRING | HAS_ARG | OPT_EXPERT |
3007                           OPT_SPEC | OPT_INPUT,                                  { .off = OFFSET(hwaccel_devices) },
3008         "select a device for HW acceleration" "devicename" },
3009 #if HAVE_VDPAU_X11
3010     { "vdpau_api_ver", HAS_ARG | OPT_INT | OPT_EXPERT, { &vdpau_api_ver }, "" },
3011 #endif
3012
3013     /* audio options */
3014     { "aframes",        OPT_AUDIO | HAS_ARG  | OPT_PERFILE | OPT_OUTPUT,           { .func_arg = opt_audio_frames },
3015         "set the number of audio frames to output", "number" },
3016     { "aq",             OPT_AUDIO | HAS_ARG  | OPT_PERFILE | OPT_OUTPUT,           { .func_arg = opt_audio_qscale },
3017         "set audio quality (codec-specific)", "quality", },
3018     { "ar",             OPT_AUDIO | HAS_ARG  | OPT_INT | OPT_SPEC |
3019                         OPT_INPUT | OPT_OUTPUT,                                    { .off = OFFSET(audio_sample_rate) },
3020         "set audio sampling rate (in Hz)", "rate" },
3021     { "ac",             OPT_AUDIO | HAS_ARG  | OPT_INT | OPT_SPEC |
3022                         OPT_INPUT | OPT_OUTPUT,                                    { .off = OFFSET(audio_channels) },
3023         "set number of audio channels", "channels" },
3024     { "an",             OPT_AUDIO | OPT_BOOL | OPT_OFFSET | OPT_INPUT | OPT_OUTPUT,{ .off = OFFSET(audio_disable) },
3025         "disable audio" },
3026     { "acodec",         OPT_AUDIO | HAS_ARG  | OPT_PERFILE |
3027                         OPT_INPUT | OPT_OUTPUT,                                    { .func_arg = opt_audio_codec },
3028         "force audio codec ('copy' to copy stream)", "codec" },
3029     { "atag",           OPT_AUDIO | HAS_ARG  | OPT_EXPERT | OPT_PERFILE |
3030                         OPT_OUTPUT,                                                { .func_arg = opt_old2new },
3031         "force audio tag/fourcc", "fourcc/tag" },
3032     { "vol",            OPT_AUDIO | HAS_ARG  | OPT_INT,                            { &audio_volume },
3033         "change audio volume (256=normal)" , "volume" },
3034     { "sample_fmt",     OPT_AUDIO | HAS_ARG  | OPT_EXPERT | OPT_SPEC |
3035                         OPT_STRING | OPT_INPUT | OPT_OUTPUT,                       { .off = OFFSET(sample_fmts) },
3036         "set sample format", "format" },
3037     { "channel_layout", OPT_AUDIO | HAS_ARG  | OPT_EXPERT | OPT_PERFILE |
3038                         OPT_INPUT | OPT_OUTPUT,                                    { .func_arg = opt_channel_layout },
3039         "set channel layout", "layout" },
3040     { "af",             OPT_AUDIO | HAS_ARG  | OPT_PERFILE | OPT_OUTPUT,           { .func_arg = opt_audio_filters },
3041         "set audio filters", "filter_graph" },
3042     { "guess_layout_max", OPT_AUDIO | HAS_ARG | OPT_INT | OPT_SPEC | OPT_EXPERT | OPT_INPUT, { .off = OFFSET(guess_layout_max) },
3043       "set the maximum number of channels to try to guess the channel layout" },
3044
3045     /* subtitle options */
3046     { "sn",     OPT_SUBTITLE | OPT_BOOL | OPT_OFFSET | OPT_INPUT | OPT_OUTPUT, { .off = OFFSET(subtitle_disable) },
3047         "disable subtitle" },
3048     { "scodec", OPT_SUBTITLE | HAS_ARG  | OPT_PERFILE | OPT_INPUT | OPT_OUTPUT, { .func_arg = opt_subtitle_codec },
3049         "force subtitle codec ('copy' to copy stream)", "codec" },
3050     { "stag",   OPT_SUBTITLE | HAS_ARG  | OPT_EXPERT  | OPT_PERFILE | OPT_OUTPUT, { .func_arg = opt_old2new }
3051         , "force subtitle tag/fourcc", "fourcc/tag" },
3052     { "fix_sub_duration", OPT_BOOL | OPT_EXPERT | OPT_SUBTITLE | OPT_SPEC | OPT_INPUT, { .off = OFFSET(fix_sub_duration) },
3053         "fix subtitles duration" },
3054     { "canvas_size", OPT_SUBTITLE | HAS_ARG | OPT_STRING | OPT_SPEC | OPT_INPUT, { .off = OFFSET(canvas_sizes) },
3055         "set canvas size (WxH or abbreviation)", "size" },
3056
3057     /* grab options */
3058     { "vc", HAS_ARG | OPT_EXPERT | OPT_VIDEO, { .func_arg = opt_video_channel },
3059         "deprecated, use -channel", "channel" },
3060     { "tvstd", HAS_ARG | OPT_EXPERT | OPT_VIDEO, { .func_arg = opt_video_standard },
3061         "deprecated, use -standard", "standard" },
3062     { "isync", OPT_BOOL | OPT_EXPERT, { &input_sync }, "this option is deprecated and does nothing", "" },
3063
3064     /* muxer options */
3065     { "muxdelay",   OPT_FLOAT | HAS_ARG | OPT_EXPERT | OPT_OFFSET | OPT_OUTPUT, { .off = OFFSET(mux_max_delay) },
3066         "set the maximum demux-decode delay", "seconds" },
3067     { "muxpreload", OPT_FLOAT | HAS_ARG | OPT_EXPERT | OPT_OFFSET | OPT_OUTPUT, { .off = OFFSET(mux_preload) },
3068         "set the initial demux-decode delay", "seconds" },
3069     { "override_ffserver", OPT_BOOL | OPT_EXPERT | OPT_OUTPUT, { &override_ffserver },
3070         "override the options from ffserver", "" },
3071
3072     { "bsf", HAS_ARG | OPT_STRING | OPT_SPEC | OPT_EXPERT | OPT_OUTPUT, { .off = OFFSET(bitstream_filters) },
3073         "A comma-separated list of bitstream filters", "bitstream_filters" },
3074     { "absf", HAS_ARG | OPT_AUDIO | OPT_EXPERT| OPT_PERFILE | OPT_OUTPUT, { .func_arg = opt_old2new },
3075         "deprecated", "audio bitstream_filters" },
3076     { "vbsf", OPT_VIDEO | HAS_ARG | OPT_EXPERT| OPT_PERFILE | OPT_OUTPUT, { .func_arg = opt_old2new },
3077         "deprecated", "video bitstream_filters" },
3078
3079     { "apre", HAS_ARG | OPT_AUDIO | OPT_EXPERT| OPT_PERFILE | OPT_OUTPUT,    { .func_arg = opt_preset },
3080         "set the audio options to the indicated preset", "preset" },
3081     { "vpre", OPT_VIDEO | HAS_ARG | OPT_EXPERT| OPT_PERFILE | OPT_OUTPUT,    { .func_arg = opt_preset },
3082         "set the video options to the indicated preset", "preset" },
3083     { "spre", HAS_ARG | OPT_SUBTITLE | OPT_EXPERT| OPT_PERFILE | OPT_OUTPUT, { .func_arg = opt_preset },
3084         "set the subtitle options to the indicated preset", "preset" },
3085     { "fpre", HAS_ARG | OPT_EXPERT| OPT_PERFILE | OPT_OUTPUT,                { .func_arg = opt_preset },
3086         "set options from indicated preset file", "filename" },
3087     /* data codec support */
3088     { "dcodec", HAS_ARG | OPT_DATA | OPT_PERFILE | OPT_EXPERT | OPT_INPUT | OPT_OUTPUT, { .func_arg = opt_data_codec },
3089         "force data codec ('copy' to copy stream)", "codec" },
3090     { "dn", OPT_BOOL | OPT_VIDEO | OPT_OFFSET | OPT_INPUT | OPT_OUTPUT, { .off = OFFSET(data_disable) },
3091         "disable data" },
3092
3093     { NULL, },
3094 };