]> git.sesse.net Git - ffmpeg/blob - cmdutils.c
Merge remote-tracking branch 'qatar/master'
[ffmpeg] / cmdutils.c
1 /*
2  * Various utilities for command line tools
3  * Copyright (c) 2000-2003 Fabrice Bellard
4  *
5  * This file is part of FFmpeg.
6  *
7  * FFmpeg is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU Lesser General Public
9  * License as published by the Free Software Foundation; either
10  * version 2.1 of the License, or (at your option) any later version.
11  *
12  * FFmpeg is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15  * Lesser General Public License for more details.
16  *
17  * You should have received a copy of the GNU Lesser General Public
18  * License along with FFmpeg; if not, write to the Free Software
19  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
20  */
21
22 #include <string.h>
23 #include <stdlib.h>
24 #include <errno.h>
25 #include <math.h>
26
27 /* Include only the enabled headers since some compilers (namely, Sun
28    Studio) will not omit unused inline functions and create undefined
29    references to libraries that are not being built. */
30
31 #include "config.h"
32 #include "libavformat/avformat.h"
33 #include "libavfilter/avfilter.h"
34 #include "libavdevice/avdevice.h"
35 #include "libswscale/swscale.h"
36 #include "libpostproc/postprocess.h"
37 #include "libavutil/avstring.h"
38 #include "libavutil/parseutils.h"
39 #include "libavutil/pixdesc.h"
40 #include "libavutil/eval.h"
41 #include "libavutil/dict.h"
42 #include "libavutil/opt.h"
43 #include "cmdutils.h"
44 #include "version.h"
45 #if CONFIG_NETWORK
46 #include "libavformat/network.h"
47 #endif
48 #if HAVE_SYS_RESOURCE_H
49 #include <sys/resource.h>
50 #endif
51
52 struct SwsContext *sws_opts;
53 AVDictionary *format_opts, *codec_opts;
54
55 static const int this_year = 2011;
56
57 void init_opts(void)
58 {
59 #if CONFIG_SWSCALE
60     sws_opts = sws_getContext(16, 16, 0, 16, 16, 0, SWS_BICUBIC, NULL, NULL, NULL);
61 #endif
62 }
63
64 void uninit_opts(void)
65 {
66 #if CONFIG_SWSCALE
67     sws_freeContext(sws_opts);
68     sws_opts = NULL;
69 #endif
70     av_dict_free(&format_opts);
71     av_dict_free(&codec_opts);
72 }
73
74 void log_callback_help(void* ptr, int level, const char* fmt, va_list vl)
75 {
76     vfprintf(stdout, fmt, vl);
77 }
78
79 double parse_number_or_die(const char *context, const char *numstr, int type, double min, double max)
80 {
81     char *tail;
82     const char *error;
83     double d = av_strtod(numstr, &tail);
84     if (*tail)
85         error= "Expected number for %s but found: %s\n";
86     else if (d < min || d > max)
87         error= "The value for %s was %s which is not within %f - %f\n";
88     else if(type == OPT_INT64 && (int64_t)d != d)
89         error= "Expected int64 for %s but found %s\n";
90     else if (type == OPT_INT && (int)d != d)
91         error= "Expected int for %s but found %s\n";
92     else
93         return d;
94     av_log(NULL, AV_LOG_FATAL, error, context, numstr, min, max);
95     exit_program(1);
96     return 0;
97 }
98
99 int64_t parse_time_or_die(const char *context, const char *timestr, int is_duration)
100 {
101     int64_t us;
102     if (av_parse_time(&us, timestr, is_duration) < 0) {
103         av_log(NULL, AV_LOG_FATAL, "Invalid %s specification for %s: %s\n",
104                is_duration ? "duration" : "date", context, timestr);
105         exit_program(1);
106     }
107     return us;
108 }
109
110 void show_help_options(const OptionDef *options, const char *msg, int mask, int value)
111 {
112     const OptionDef *po;
113     int first;
114
115     first = 1;
116     for(po = options; po->name != NULL; po++) {
117         char buf[64];
118         if ((po->flags & mask) == value) {
119             if (first) {
120                 printf("%s", msg);
121                 first = 0;
122             }
123             av_strlcpy(buf, po->name, sizeof(buf));
124             if (po->flags & HAS_ARG) {
125                 av_strlcat(buf, " ", sizeof(buf));
126                 av_strlcat(buf, po->argname, sizeof(buf));
127             }
128             printf("-%-17s  %s\n", buf, po->help);
129         }
130     }
131 }
132
133 void show_help_children(const AVClass *class, int flags)
134 {
135     const AVClass *child = NULL;
136     av_opt_show2(&class, NULL, flags, 0);
137     printf("\n");
138
139     while (child = av_opt_child_class_next(class, child))
140         show_help_children(child, flags);
141 }
142
143 static const OptionDef* find_option(const OptionDef *po, const char *name){
144     const char *p = strchr(name, ':');
145     int len = p ? p - name : strlen(name);
146
147     while (po->name != NULL) {
148         if (!strncmp(name, po->name, len) && strlen(po->name) == len)
149             break;
150         po++;
151     }
152     return po;
153 }
154
155 #if defined(_WIN32) && !defined(__MINGW32CE__)
156 #include <windows.h>
157 /* Will be leaked on exit */
158 static char** win32_argv_utf8 = NULL;
159 static int win32_argc = 0;
160
161 /**
162  * Prepare command line arguments for executable.
163  * For Windows - perform wide-char to UTF-8 conversion.
164  * Input arguments should be main() function arguments.
165  * @param argc_ptr Arguments number (including executable)
166  * @param argv_ptr Arguments list.
167  */
168 static void prepare_app_arguments(int *argc_ptr, char ***argv_ptr)
169 {
170     char *argstr_flat;
171     wchar_t **argv_w;
172     int i, buffsize = 0, offset = 0;
173
174     if (win32_argv_utf8) {
175         *argc_ptr = win32_argc;
176         *argv_ptr = win32_argv_utf8;
177         return;
178     }
179
180     win32_argc = 0;
181     argv_w = CommandLineToArgvW(GetCommandLineW(), &win32_argc);
182     if (win32_argc <= 0 || !argv_w)
183         return;
184
185     /* determine the UTF-8 buffer size (including NULL-termination symbols) */
186     for (i = 0; i < win32_argc; i++)
187         buffsize += WideCharToMultiByte(CP_UTF8, 0, argv_w[i], -1,
188                                         NULL, 0, NULL, NULL);
189
190     win32_argv_utf8 = av_mallocz(sizeof(char*) * (win32_argc + 1) + buffsize);
191     argstr_flat     = (char*)win32_argv_utf8 + sizeof(char*) * (win32_argc + 1);
192     if (win32_argv_utf8 == NULL) {
193         LocalFree(argv_w);
194         return;
195     }
196
197     for (i = 0; i < win32_argc; i++) {
198         win32_argv_utf8[i] = &argstr_flat[offset];
199         offset += WideCharToMultiByte(CP_UTF8, 0, argv_w[i], -1,
200                                       &argstr_flat[offset],
201                                       buffsize - offset, NULL, NULL);
202     }
203     win32_argv_utf8[i] = NULL;
204     LocalFree(argv_w);
205
206     *argc_ptr = win32_argc;
207     *argv_ptr = win32_argv_utf8;
208 }
209 #else
210 static inline void prepare_app_arguments(int *argc_ptr, char ***argv_ptr)
211 {
212     /* nothing to do */
213 }
214 #endif /* WIN32 && !__MINGW32CE__ */
215
216
217 int parse_option(void *optctx, const char *opt, const char *arg, const OptionDef *options)
218 {
219     const OptionDef *po;
220     int bool_val = 1;
221     int *dstcount;
222     void *dst;
223
224     po = find_option(options, opt);
225     if (!po->name && opt[0] == 'n' && opt[1] == 'o') {
226         /* handle 'no' bool option */
227         po = find_option(options, opt + 2);
228         if (!(po->name && (po->flags & OPT_BOOL)))
229             goto unknown_opt;
230         bool_val = 0;
231     }
232     if (!po->name)
233         po = find_option(options, "default");
234     if (!po->name) {
235 unknown_opt:
236         av_log(NULL, AV_LOG_ERROR, "Unrecognized option '%s'\n", opt);
237         return AVERROR(EINVAL);
238     }
239     if (po->flags & HAS_ARG && !arg) {
240         av_log(NULL, AV_LOG_ERROR, "Missing argument for option '%s'\n", opt);
241         return AVERROR(EINVAL);
242     }
243
244     /* new-style options contain an offset into optctx, old-style address of
245      * a global var*/
246     dst = po->flags & (OPT_OFFSET|OPT_SPEC) ? (uint8_t*)optctx + po->u.off : po->u.dst_ptr;
247
248     if (po->flags & OPT_SPEC) {
249         SpecifierOpt **so = dst;
250         char *p = strchr(opt, ':');
251
252         dstcount = (int*)(so + 1);
253         *so = grow_array(*so, sizeof(**so), dstcount, *dstcount + 1);
254         (*so)[*dstcount - 1].specifier = av_strdup(p ? p + 1 : "");
255         dst = &(*so)[*dstcount - 1].u;
256     }
257
258     if (po->flags & OPT_STRING) {
259         char *str;
260         str = av_strdup(arg);
261         *(char**)dst = str;
262     } else if (po->flags & OPT_BOOL) {
263         *(int*)dst = bool_val;
264     } else if (po->flags & OPT_INT) {
265         *(int*)dst = parse_number_or_die(opt, arg, OPT_INT64, INT_MIN, INT_MAX);
266     } else if (po->flags & OPT_INT64) {
267         *(int64_t*)dst = parse_number_or_die(opt, arg, OPT_INT64, INT64_MIN, INT64_MAX);
268     } else if (po->flags & OPT_TIME) {
269         *(int64_t*)dst = parse_time_or_die(opt, arg, 1);
270     } else if (po->flags & OPT_FLOAT) {
271         *(float*)dst = parse_number_or_die(opt, arg, OPT_FLOAT, -INFINITY, INFINITY);
272     } else if (po->flags & OPT_DOUBLE) {
273         *(double*)dst = parse_number_or_die(opt, arg, OPT_DOUBLE, -INFINITY, INFINITY);
274     } else if (po->u.func_arg) {
275         int ret = po->flags & OPT_FUNC2 ? po->u.func2_arg(optctx, opt, arg) :
276                                           po->u.func_arg(opt, arg);
277         if (ret < 0) {
278             av_log(NULL, AV_LOG_ERROR, "Failed to set value '%s' for option '%s'\n", arg, opt);
279             return ret;
280         }
281     }
282     if (po->flags & OPT_EXIT)
283         exit_program(0);
284     return !!(po->flags & HAS_ARG);
285 }
286
287 void parse_options(void *optctx, int argc, char **argv, const OptionDef *options,
288                    void (* parse_arg_function)(void *, const char*))
289 {
290     const char *opt;
291     int optindex, handleoptions = 1, ret;
292
293     /* perform system-dependent conversions for arguments list */
294     prepare_app_arguments(&argc, &argv);
295
296     /* parse options */
297     optindex = 1;
298     while (optindex < argc) {
299         opt = argv[optindex++];
300
301         if (handleoptions && opt[0] == '-' && opt[1] != '\0') {
302             if (opt[1] == '-' && opt[2] == '\0') {
303                 handleoptions = 0;
304                 continue;
305             }
306             opt++;
307
308             if ((ret = parse_option(optctx, opt, argv[optindex], options)) < 0)
309                 exit_program(1);
310             optindex += ret;
311         } else {
312             if (parse_arg_function)
313                 parse_arg_function(optctx, opt);
314         }
315     }
316 }
317
318 /*
319  * Return index of option opt in argv or 0 if not found.
320  */
321 static int locate_option(int argc, char **argv, const OptionDef *options, const char *optname)
322 {
323     const OptionDef *po;
324     int i;
325
326     for (i = 1; i < argc; i++) {
327         const char *cur_opt = argv[i];
328
329         if (*cur_opt++ != '-')
330             continue;
331
332         po = find_option(options, cur_opt);
333         if (!po->name && cur_opt[0] == 'n' && cur_opt[1] == 'o')
334             po = find_option(options, cur_opt + 2);
335
336         if ((!po->name && !strcmp(cur_opt, optname)) ||
337              (po->name && !strcmp(optname, po->name)))
338             return i;
339
340         if (!po || po->flags & HAS_ARG)
341             i++;
342     }
343     return 0;
344 }
345
346 void parse_loglevel(int argc, char **argv, const OptionDef *options)
347 {
348     int idx = locate_option(argc, argv, options, "loglevel");
349     if (!idx)
350         idx = locate_option(argc, argv, options, "v");
351     if (idx && argv[idx + 1])
352         opt_loglevel("loglevel", argv[idx + 1]);
353 }
354
355 #define FLAGS(o) ((o)->type == AV_OPT_TYPE_FLAGS) ? AV_DICT_APPEND : 0
356 int opt_default(const char *opt, const char *arg)
357 {
358     const AVOption *oc, *of, *os;
359     char opt_stripped[128];
360     const char *p;
361     const AVClass *cc = avcodec_get_class(), *fc = avformat_get_class(), *sc;
362
363     if (!(p = strchr(opt, ':')))
364         p = opt + strlen(opt);
365     av_strlcpy(opt_stripped, opt, FFMIN(sizeof(opt_stripped), p - opt + 1));
366
367     if ((oc = av_opt_find(&cc, opt_stripped, NULL, 0, AV_OPT_SEARCH_CHILDREN|AV_OPT_SEARCH_FAKE_OBJ)) ||
368          ((opt[0] == 'v' || opt[0] == 'a' || opt[0] == 's') &&
369           (oc = av_opt_find(&cc, opt+1, NULL, 0, AV_OPT_SEARCH_FAKE_OBJ))))
370         av_dict_set(&codec_opts, opt, arg, FLAGS(oc));
371     if ((of = av_opt_find(&fc, opt, NULL, 0, AV_OPT_SEARCH_CHILDREN | AV_OPT_SEARCH_FAKE_OBJ)))
372         av_dict_set(&format_opts, opt, arg, FLAGS(of));
373 #if CONFIG_SWSCALE
374     sc = sws_get_class();
375     if ((os = av_opt_find(&sc, opt, NULL, 0, AV_OPT_SEARCH_CHILDREN | AV_OPT_SEARCH_FAKE_OBJ))) {
376         // XXX we only support sws_flags, not arbitrary sws options
377         int ret = av_opt_set(sws_opts, opt, arg, 0);
378         if (ret < 0) {
379             av_log(NULL, AV_LOG_ERROR, "Error setting option %s.\n", opt);
380             return ret;
381         }
382     }
383 #endif
384
385     if (oc || of || os)
386         return 0;
387     av_log(NULL, AV_LOG_ERROR, "Unrecognized option '%s'\n", opt);
388     return AVERROR_OPTION_NOT_FOUND;
389 }
390
391 int opt_loglevel(const char *opt, const char *arg)
392 {
393     const struct { const char *name; int level; } log_levels[] = {
394         { "quiet"  , AV_LOG_QUIET   },
395         { "panic"  , AV_LOG_PANIC   },
396         { "fatal"  , AV_LOG_FATAL   },
397         { "error"  , AV_LOG_ERROR   },
398         { "warning", AV_LOG_WARNING },
399         { "info"   , AV_LOG_INFO    },
400         { "verbose", AV_LOG_VERBOSE },
401         { "debug"  , AV_LOG_DEBUG   },
402     };
403     char *tail;
404     int level;
405     int i;
406
407     for (i = 0; i < FF_ARRAY_ELEMS(log_levels); i++) {
408         if (!strcmp(log_levels[i].name, arg)) {
409             av_log_set_level(log_levels[i].level);
410             return 0;
411         }
412     }
413
414     level = strtol(arg, &tail, 10);
415     if (*tail) {
416         av_log(NULL, AV_LOG_FATAL, "Invalid loglevel \"%s\". "
417                "Possible levels are numbers or:\n", arg);
418         for (i = 0; i < FF_ARRAY_ELEMS(log_levels); i++)
419             av_log(NULL, AV_LOG_FATAL, "\"%s\"\n", log_levels[i].name);
420         exit_program(1);
421     }
422     av_log_set_level(level);
423     return 0;
424 }
425
426 int opt_codec_debug(const char *opt, const char *arg)
427 {
428     av_log_set_level(AV_LOG_DEBUG);
429     return opt_default(opt, arg);
430 }
431
432 int opt_timelimit(const char *opt, const char *arg)
433 {
434 #if HAVE_SETRLIMIT
435     int lim = parse_number_or_die(opt, arg, OPT_INT64, 0, INT_MAX);
436     struct rlimit rl = { lim, lim + 1 };
437     if (setrlimit(RLIMIT_CPU, &rl))
438         perror("setrlimit");
439 #else
440     av_log(NULL, AV_LOG_WARNING, "-%s not implemented on this OS\n", opt);
441 #endif
442     return 0;
443 }
444
445 void print_error(const char *filename, int err)
446 {
447     char errbuf[128];
448     const char *errbuf_ptr = errbuf;
449
450     if (av_strerror(err, errbuf, sizeof(errbuf)) < 0)
451         errbuf_ptr = strerror(AVUNERROR(err));
452     av_log(NULL, AV_LOG_ERROR, "%s: %s\n", filename, errbuf_ptr);
453 }
454
455 static int warned_cfg = 0;
456
457 #define INDENT        1
458 #define SHOW_VERSION  2
459 #define SHOW_CONFIG   4
460
461 #define PRINT_LIB_INFO(libname, LIBNAME, flags, level)                  \
462     if (CONFIG_##LIBNAME) {                                             \
463         const char *indent = flags & INDENT? "  " : "";                 \
464         if (flags & SHOW_VERSION) {                                     \
465             unsigned int version = libname##_version();                 \
466             av_log(NULL, level, "%slib%-9s %2d.%3d.%2d / %2d.%3d.%2d\n",\
467                    indent, #libname,                                    \
468                    LIB##LIBNAME##_VERSION_MAJOR,                        \
469                    LIB##LIBNAME##_VERSION_MINOR,                        \
470                    LIB##LIBNAME##_VERSION_MICRO,                        \
471                    version >> 16, version >> 8 & 0xff, version & 0xff); \
472         }                                                               \
473         if (flags & SHOW_CONFIG) {                                      \
474             const char *cfg = libname##_configuration();                \
475             if (strcmp(FFMPEG_CONFIGURATION, cfg)) {                    \
476                 if (!warned_cfg) {                                      \
477                     av_log(NULL, level,                                 \
478                             "%sWARNING: library configuration mismatch\n", \
479                             indent);                                    \
480                     warned_cfg = 1;                                     \
481                 }                                                       \
482                 av_log(NULL, level, "%s%-11s configuration: %s\n",      \
483                         indent, #libname, cfg);                         \
484             }                                                           \
485         }                                                               \
486     }                                                                   \
487
488 static void print_all_libs_info(int flags, int level)
489 {
490     PRINT_LIB_INFO(avutil,   AVUTIL,   flags, level);
491     PRINT_LIB_INFO(avcodec,  AVCODEC,  flags, level);
492     PRINT_LIB_INFO(avformat, AVFORMAT, flags, level);
493     PRINT_LIB_INFO(avdevice, AVDEVICE, flags, level);
494     PRINT_LIB_INFO(avfilter, AVFILTER, flags, level);
495     PRINT_LIB_INFO(swscale,  SWSCALE,  flags, level);
496     PRINT_LIB_INFO(postproc, POSTPROC, flags, level);
497 }
498
499 void show_banner(void)
500 {
501     av_log(NULL, AV_LOG_INFO, "%s version " FFMPEG_VERSION ", Copyright (c) %d-%d the FFmpeg developers\n",
502            program_name, program_birth_year, this_year);
503     av_log(NULL, AV_LOG_INFO, "  built on %s %s with %s %s\n",
504            __DATE__, __TIME__, CC_TYPE, CC_VERSION);
505     av_log(NULL, AV_LOG_INFO, "  configuration: " FFMPEG_CONFIGURATION "\n");
506     print_all_libs_info(INDENT|SHOW_CONFIG,  AV_LOG_INFO);
507     print_all_libs_info(INDENT|SHOW_VERSION, AV_LOG_INFO);
508 }
509
510 int opt_version(const char *opt, const char *arg) {
511     av_log_set_callback(log_callback_help);
512     printf("%s " FFMPEG_VERSION "\n", program_name);
513     print_all_libs_info(SHOW_VERSION, AV_LOG_INFO);
514     return 0;
515 }
516
517 int opt_license(const char *opt, const char *arg)
518 {
519     printf(
520 #if CONFIG_NONFREE
521     "This version of %s has nonfree parts compiled in.\n"
522     "Therefore it is not legally redistributable.\n",
523     program_name
524 #elif CONFIG_GPLV3
525     "%s is free software; you can redistribute it and/or modify\n"
526     "it under the terms of the GNU General Public License as published by\n"
527     "the Free Software Foundation; either version 3 of the License, or\n"
528     "(at your option) any later version.\n"
529     "\n"
530     "%s is distributed in the hope that it will be useful,\n"
531     "but WITHOUT ANY WARRANTY; without even the implied warranty of\n"
532     "MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n"
533     "GNU General Public License for more details.\n"
534     "\n"
535     "You should have received a copy of the GNU General Public License\n"
536     "along with %s.  If not, see <http://www.gnu.org/licenses/>.\n",
537     program_name, program_name, program_name
538 #elif CONFIG_GPL
539     "%s is free software; you can redistribute it and/or modify\n"
540     "it under the terms of the GNU General Public License as published by\n"
541     "the Free Software Foundation; either version 2 of the License, or\n"
542     "(at your option) any later version.\n"
543     "\n"
544     "%s is distributed in the hope that it will be useful,\n"
545     "but WITHOUT ANY WARRANTY; without even the implied warranty of\n"
546     "MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n"
547     "GNU General Public License for more details.\n"
548     "\n"
549     "You should have received a copy of the GNU General Public License\n"
550     "along with %s; if not, write to the Free Software\n"
551     "Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA\n",
552     program_name, program_name, program_name
553 #elif CONFIG_LGPLV3
554     "%s is free software; you can redistribute it and/or modify\n"
555     "it under the terms of the GNU Lesser General Public License as published by\n"
556     "the Free Software Foundation; either version 3 of the License, or\n"
557     "(at your option) any later version.\n"
558     "\n"
559     "%s is distributed in the hope that it will be useful,\n"
560     "but WITHOUT ANY WARRANTY; without even the implied warranty of\n"
561     "MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n"
562     "GNU Lesser General Public License for more details.\n"
563     "\n"
564     "You should have received a copy of the GNU Lesser General Public License\n"
565     "along with %s.  If not, see <http://www.gnu.org/licenses/>.\n",
566     program_name, program_name, program_name
567 #else
568     "%s is free software; you can redistribute it and/or\n"
569     "modify it under the terms of the GNU Lesser General Public\n"
570     "License as published by the Free Software Foundation; either\n"
571     "version 2.1 of the License, or (at your option) any later version.\n"
572     "\n"
573     "%s is distributed in the hope that it will be useful,\n"
574     "but WITHOUT ANY WARRANTY; without even the implied warranty of\n"
575     "MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n"
576     "Lesser General Public License for more details.\n"
577     "\n"
578     "You should have received a copy of the GNU Lesser General Public\n"
579     "License along with %s; if not, write to the Free Software\n"
580     "Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA\n",
581     program_name, program_name, program_name
582 #endif
583     );
584     return 0;
585 }
586
587 int opt_formats(const char *opt, const char *arg)
588 {
589     AVInputFormat *ifmt=NULL;
590     AVOutputFormat *ofmt=NULL;
591     const char *last_name;
592
593     printf(
594         "File formats:\n"
595         " D. = Demuxing supported\n"
596         " .E = Muxing supported\n"
597         " --\n");
598     last_name= "000";
599     for(;;){
600         int decode=0;
601         int encode=0;
602         const char *name=NULL;
603         const char *long_name=NULL;
604
605         while((ofmt= av_oformat_next(ofmt))) {
606             if((name == NULL || strcmp(ofmt->name, name)<0) &&
607                 strcmp(ofmt->name, last_name)>0){
608                 name= ofmt->name;
609                 long_name= ofmt->long_name;
610                 encode=1;
611             }
612         }
613         while((ifmt= av_iformat_next(ifmt))) {
614             if((name == NULL || strcmp(ifmt->name, name)<0) &&
615                 strcmp(ifmt->name, last_name)>0){
616                 name= ifmt->name;
617                 long_name= ifmt->long_name;
618                 encode=0;
619             }
620             if(name && strcmp(ifmt->name, name)==0)
621                 decode=1;
622         }
623         if(name==NULL)
624             break;
625         last_name= name;
626
627         printf(
628             " %s%s %-15s %s\n",
629             decode ? "D":" ",
630             encode ? "E":" ",
631             name,
632             long_name ? long_name:" ");
633     }
634     return 0;
635 }
636
637 int opt_codecs(const char *opt, const char *arg)
638 {
639     AVCodec *p=NULL, *p2;
640     const char *last_name;
641     printf(
642         "Codecs:\n"
643         " D..... = Decoding supported\n"
644         " .E.... = Encoding supported\n"
645         " ..V... = Video codec\n"
646         " ..A... = Audio codec\n"
647         " ..S... = Subtitle codec\n"
648         " ...S.. = Supports draw_horiz_band\n"
649         " ....D. = Supports direct rendering method 1\n"
650         " .....T = Supports weird frame truncation\n"
651         " ------\n");
652     last_name= "000";
653     for(;;){
654         int decode=0;
655         int encode=0;
656         int cap=0;
657         const char *type_str;
658
659         p2=NULL;
660         while((p= av_codec_next(p))) {
661             if((p2==NULL || strcmp(p->name, p2->name)<0) &&
662                 strcmp(p->name, last_name)>0){
663                 p2= p;
664                 decode= encode= cap=0;
665             }
666             if(p2 && strcmp(p->name, p2->name)==0){
667                 if(p->decode) decode=1;
668                 if(p->encode) encode=1;
669                 cap |= p->capabilities;
670             }
671         }
672         if(p2==NULL)
673             break;
674         last_name= p2->name;
675
676         switch(p2->type) {
677         case AVMEDIA_TYPE_VIDEO:
678             type_str = "V";
679             break;
680         case AVMEDIA_TYPE_AUDIO:
681             type_str = "A";
682             break;
683         case AVMEDIA_TYPE_SUBTITLE:
684             type_str = "S";
685             break;
686         default:
687             type_str = "?";
688             break;
689         }
690         printf(
691             " %s%s%s%s%s%s %-15s %s",
692             decode ? "D": (/*p2->decoder ? "d":*/" "),
693             encode ? "E":" ",
694             type_str,
695             cap & CODEC_CAP_DRAW_HORIZ_BAND ? "S":" ",
696             cap & CODEC_CAP_DR1 ? "D":" ",
697             cap & CODEC_CAP_TRUNCATED ? "T":" ",
698             p2->name,
699             p2->long_name ? p2->long_name : "");
700        /* if(p2->decoder && decode==0)
701             printf(" use %s for decoding", p2->decoder->name);*/
702         printf("\n");
703     }
704     printf("\n");
705     printf(
706 "Note, the names of encoders and decoders do not always match, so there are\n"
707 "several cases where the above table shows encoder only or decoder only entries\n"
708 "even though both encoding and decoding are supported. For example, the h263\n"
709 "decoder corresponds to the h263 and h263p encoders, for file formats it is even\n"
710 "worse.\n");
711     return 0;
712 }
713
714 int opt_bsfs(const char *opt, const char *arg)
715 {
716     AVBitStreamFilter *bsf=NULL;
717
718     printf("Bitstream filters:\n");
719     while((bsf = av_bitstream_filter_next(bsf)))
720         printf("%s\n", bsf->name);
721     printf("\n");
722     return 0;
723 }
724
725 int opt_protocols(const char *opt, const char *arg)
726 {
727     URLProtocol *up=NULL;
728
729     printf("Supported file protocols:\n"
730            "I.. = Input  supported\n"
731            ".O. = Output supported\n"
732            "..S = Seek   supported\n"
733            "FLAGS NAME\n"
734            "----- \n");
735     while((up = av_protocol_next(up)))
736         printf("%c%c%c   %s\n",
737                up->url_read  ? 'I' : '.',
738                up->url_write ? 'O' : '.',
739                up->url_seek  ? 'S' : '.',
740                up->name);
741     return 0;
742 }
743
744 int opt_filters(const char *opt, const char *arg)
745 {
746     AVFilter av_unused(**filter) = NULL;
747
748     printf("Filters:\n");
749 #if CONFIG_AVFILTER
750     while ((filter = av_filter_next(filter)) && *filter)
751         printf("%-16s %s\n", (*filter)->name, (*filter)->description);
752 #endif
753     return 0;
754 }
755
756 int opt_pix_fmts(const char *opt, const char *arg)
757 {
758     enum PixelFormat pix_fmt;
759
760     printf(
761         "Pixel formats:\n"
762         "I.... = Supported Input  format for conversion\n"
763         ".O... = Supported Output format for conversion\n"
764         "..H.. = Hardware accelerated format\n"
765         "...P. = Paletted format\n"
766         "....B = Bitstream format\n"
767         "FLAGS NAME            NB_COMPONENTS BITS_PER_PIXEL\n"
768         "-----\n");
769
770 #if !CONFIG_SWSCALE
771 #   define sws_isSupportedInput(x)  0
772 #   define sws_isSupportedOutput(x) 0
773 #endif
774
775     for (pix_fmt = 0; pix_fmt < PIX_FMT_NB; pix_fmt++) {
776         const AVPixFmtDescriptor *pix_desc = &av_pix_fmt_descriptors[pix_fmt];
777         printf("%c%c%c%c%c %-16s       %d            %2d\n",
778                sws_isSupportedInput (pix_fmt)      ? 'I' : '.',
779                sws_isSupportedOutput(pix_fmt)      ? 'O' : '.',
780                pix_desc->flags & PIX_FMT_HWACCEL   ? 'H' : '.',
781                pix_desc->flags & PIX_FMT_PAL       ? 'P' : '.',
782                pix_desc->flags & PIX_FMT_BITSTREAM ? 'B' : '.',
783                pix_desc->name,
784                pix_desc->nb_components,
785                av_get_bits_per_pixel(pix_desc));
786     }
787     return 0;
788 }
789
790 int show_sample_fmts(const char *opt, const char *arg)
791 {
792     int i;
793     char fmt_str[128];
794     for (i = -1; i < AV_SAMPLE_FMT_NB; i++)
795         printf("%s\n", av_get_sample_fmt_string(fmt_str, sizeof(fmt_str), i));
796     return 0;
797 }
798
799 int read_yesno(void)
800 {
801     int c = getchar();
802     int yesno = (toupper(c) == 'Y');
803
804     while (c != '\n' && c != EOF)
805         c = getchar();
806
807     return yesno;
808 }
809
810 int cmdutils_read_file(const char *filename, char **bufptr, size_t *size)
811 {
812     int ret;
813     FILE *f = fopen(filename, "rb");
814
815     if (!f) {
816         av_log(NULL, AV_LOG_ERROR, "Cannot read file '%s': %s\n", filename, strerror(errno));
817         return AVERROR(errno);
818     }
819     fseek(f, 0, SEEK_END);
820     *size = ftell(f);
821     fseek(f, 0, SEEK_SET);
822     *bufptr = av_malloc(*size + 1);
823     if (!*bufptr) {
824         av_log(NULL, AV_LOG_ERROR, "Could not allocate file buffer\n");
825         fclose(f);
826         return AVERROR(ENOMEM);
827     }
828     ret = fread(*bufptr, 1, *size, f);
829     if (ret < *size) {
830         av_free(*bufptr);
831         if (ferror(f)) {
832             av_log(NULL, AV_LOG_ERROR, "Error while reading file '%s': %s\n",
833                    filename, strerror(errno));
834             ret = AVERROR(errno);
835         } else
836             ret = AVERROR_EOF;
837     } else {
838         ret = 0;
839         (*bufptr)[*size++] = '\0';
840     }
841
842     fclose(f);
843     return ret;
844 }
845
846 FILE *get_preset_file(char *filename, size_t filename_size,
847                       const char *preset_name, int is_path, const char *codec_name)
848 {
849     FILE *f = NULL;
850     int i;
851     const char *base[3]= { getenv("FFMPEG_DATADIR"),
852                            getenv("HOME"),
853                            FFMPEG_DATADIR,
854                          };
855
856     if (is_path) {
857         av_strlcpy(filename, preset_name, filename_size);
858         f = fopen(filename, "r");
859     } else {
860 #ifdef _WIN32
861         char datadir[MAX_PATH], *ls;
862         base[2] = NULL;
863
864         if (GetModuleFileNameA(GetModuleHandleA(NULL), datadir, sizeof(datadir) - 1))
865         {
866             for (ls = datadir; ls < datadir + strlen(datadir); ls++)
867                 if (*ls == '\\') *ls = '/';
868
869             if (ls = strrchr(datadir, '/'))
870             {
871                 *ls = 0;
872                 strncat(datadir, "/ffpresets",  sizeof(datadir) - 1 - strlen(datadir));
873                 base[2] = datadir;
874             }
875         }
876 #endif
877         for (i = 0; i < 3 && !f; i++) {
878             if (!base[i])
879                 continue;
880             snprintf(filename, filename_size, "%s%s/%s.ffpreset", base[i], i != 1 ? "" : "/.ffmpeg", preset_name);
881             f = fopen(filename, "r");
882             if (!f && codec_name) {
883                 snprintf(filename, filename_size,
884                          "%s%s/%s-%s.ffpreset", base[i],  i != 1 ? "" : "/.ffmpeg", codec_name, preset_name);
885                 f = fopen(filename, "r");
886             }
887         }
888     }
889
890     return f;
891 }
892
893 int check_stream_specifier(AVFormatContext *s, AVStream *st, const char *spec)
894 {
895     if (*spec <= '9' && *spec >= '0')                                        /* opt:index */
896         return strtol(spec, NULL, 0) == st->index;
897     else if (*spec == 'v' || *spec == 'a' || *spec == 's' || *spec == 'd' || *spec == 't') { /* opt:[vasdt] */
898         enum AVMediaType type;
899
900         switch (*spec++) {
901         case 'v': type = AVMEDIA_TYPE_VIDEO;    break;
902         case 'a': type = AVMEDIA_TYPE_AUDIO;    break;
903         case 's': type = AVMEDIA_TYPE_SUBTITLE; break;
904         case 'd': type = AVMEDIA_TYPE_DATA;     break;
905         case 't': type = AVMEDIA_TYPE_ATTACHMENT; break;
906         default: abort(); // never reached, silence warning
907         }
908         if (type != st->codec->codec_type)
909             return 0;
910         if (*spec++ == ':') {                                   /* possibly followed by :index */
911             int i, index = strtol(spec, NULL, 0);
912             for (i = 0; i < s->nb_streams; i++)
913                 if (s->streams[i]->codec->codec_type == type && index-- == 0)
914                    return i == st->index;
915             return 0;
916         }
917         return 1;
918     } else if (*spec == 'p' && *(spec + 1) == ':') {
919         int prog_id, i, j;
920         char *endptr;
921         spec += 2;
922         prog_id = strtol(spec, &endptr, 0);
923         for (i = 0; i < s->nb_programs; i++) {
924             if (s->programs[i]->id != prog_id)
925                 continue;
926
927             if (*endptr++ == ':') {
928                 int stream_idx = strtol(endptr, NULL, 0);
929                 return (stream_idx >= 0 && stream_idx < s->programs[i]->nb_stream_indexes &&
930                         st->index == s->programs[i]->stream_index[stream_idx]);
931             }
932
933             for (j = 0; j < s->programs[i]->nb_stream_indexes; j++)
934                 if (st->index == s->programs[i]->stream_index[j])
935                     return 1;
936         }
937         return 0;
938     } else if (!*spec) /* empty specifier, matches everything */
939         return 1;
940
941     av_log(s, AV_LOG_ERROR, "Invalid stream specifier: %s.\n", spec);
942     return AVERROR(EINVAL);
943 }
944
945 AVDictionary *filter_codec_opts(AVDictionary *opts, enum CodecID codec_id, AVFormatContext *s, AVStream *st)
946 {
947     AVDictionary    *ret = NULL;
948     AVDictionaryEntry *t = NULL;
949     AVCodec       *codec = s->oformat ? avcodec_find_encoder(codec_id) : avcodec_find_decoder(codec_id);
950     int            flags = s->oformat ? AV_OPT_FLAG_ENCODING_PARAM : AV_OPT_FLAG_DECODING_PARAM;
951     char          prefix = 0;
952     const AVClass    *cc = avcodec_get_class();
953
954     if (!codec)
955         return NULL;
956
957     switch (codec->type) {
958     case AVMEDIA_TYPE_VIDEO:    prefix = 'v'; flags |= AV_OPT_FLAG_VIDEO_PARAM;    break;
959     case AVMEDIA_TYPE_AUDIO:    prefix = 'a'; flags |= AV_OPT_FLAG_AUDIO_PARAM;    break;
960     case AVMEDIA_TYPE_SUBTITLE: prefix = 's'; flags |= AV_OPT_FLAG_SUBTITLE_PARAM; break;
961     }
962
963     while (t = av_dict_get(opts, "", t, AV_DICT_IGNORE_SUFFIX)) {
964         char *p = strchr(t->key, ':');
965
966         /* check stream specification in opt name */
967         if (p)
968             switch (check_stream_specifier(s, st, p + 1)) {
969             case  1: *p = 0; break;
970             case  0:         continue;
971             default:         return NULL;
972             }
973
974         if (av_opt_find(&cc, t->key, NULL, flags, AV_OPT_SEARCH_FAKE_OBJ) ||
975             (codec && codec->priv_class && av_opt_find(&codec->priv_class, t->key, NULL, flags, AV_OPT_SEARCH_FAKE_OBJ)))
976             av_dict_set(&ret, t->key, t->value, 0);
977         else if (t->key[0] == prefix && av_opt_find(&cc, t->key+1, NULL, flags, AV_OPT_SEARCH_FAKE_OBJ))
978             av_dict_set(&ret, t->key+1, t->value, 0);
979
980         if (p)
981             *p = ':';
982     }
983     return ret;
984 }
985
986 AVDictionary **setup_find_stream_info_opts(AVFormatContext *s, AVDictionary *codec_opts)
987 {
988     int i;
989     AVDictionary **opts;
990
991     if (!s->nb_streams)
992         return NULL;
993     opts = av_mallocz(s->nb_streams * sizeof(*opts));
994     if (!opts) {
995         av_log(NULL, AV_LOG_ERROR, "Could not alloc memory for stream options.\n");
996         return NULL;
997     }
998     for (i = 0; i < s->nb_streams; i++)
999         opts[i] = filter_codec_opts(codec_opts, s->streams[i]->codec->codec_id, s, s->streams[i]);
1000     return opts;
1001 }
1002
1003 void *grow_array(void *array, int elem_size, int *size, int new_size)
1004 {
1005     if (new_size >= INT_MAX / elem_size) {
1006         av_log(NULL, AV_LOG_ERROR, "Array too big.\n");
1007         exit_program(1);
1008     }
1009     if (*size < new_size) {
1010         uint8_t *tmp = av_realloc(array, new_size*elem_size);
1011         if (!tmp) {
1012             av_log(NULL, AV_LOG_ERROR, "Could not alloc buffer.\n");
1013             exit_program(1);
1014         }
1015         memset(tmp + *size*elem_size, 0, (new_size-*size) * elem_size);
1016         *size = new_size;
1017         return tmp;
1018     }
1019     return array;
1020 }