"Fossies" - the Fresh Open Source Software Archive

Member "libav-12.3/cmdutils.c" (12 Feb 2018, 56028 Bytes) of package /linux/misc/libav-12.3.tar.gz:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. For more information about "cmdutils.c" see the Fossies "Dox" file reference documentation and the latest Fossies "Diffs" side-by-side code changes report: 12.2_vs_12.3.

    1 /*
    2  * Various utilities for command line tools
    3  * Copyright (c) 2000-2003 Fabrice Bellard
    4  *
    5  * This file is part of Libav.
    6  *
    7  * Libav 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  * Libav 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 Libav; 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 <stdint.h>
   24 #include <stdlib.h>
   25 #include <errno.h>
   26 #include <math.h>
   27 
   28 /* Include only the enabled headers since some compilers (namely, Sun
   29    Studio) will not omit unused inline functions and create undefined
   30    references to libraries that are not being built. */
   31 
   32 #include "config.h"
   33 #include "libavformat/avformat.h"
   34 #include "libavfilter/avfilter.h"
   35 #include "libavdevice/avdevice.h"
   36 #include "libavresample/avresample.h"
   37 #include "libswscale/swscale.h"
   38 #include "libavutil/avassert.h"
   39 #include "libavutil/avstring.h"
   40 #include "libavutil/mathematics.h"
   41 #include "libavutil/imgutils.h"
   42 #include "libavutil/parseutils.h"
   43 #include "libavutil/pixdesc.h"
   44 #include "libavutil/eval.h"
   45 #include "libavutil/dict.h"
   46 #include "libavutil/opt.h"
   47 #include "libavutil/cpu.h"
   48 #include "avversion.h"
   49 #include "cmdutils.h"
   50 #if CONFIG_NETWORK
   51 #include "libavformat/network.h"
   52 #endif
   53 #if HAVE_SYS_RESOURCE_H
   54 #include <sys/time.h>
   55 #include <sys/resource.h>
   56 #endif
   57 
   58 struct SwsContext *sws_opts;
   59 AVDictionary *format_opts, *codec_opts, *resample_opts;
   60 
   61 static const int this_year = 2018;
   62 
   63 void init_opts(void)
   64 {
   65 #if CONFIG_SWSCALE
   66     sws_opts = sws_getContext(16, 16, 0, 16, 16, 0, SWS_BICUBIC,
   67                               NULL, NULL, NULL);
   68 #endif
   69 }
   70 
   71 void uninit_opts(void)
   72 {
   73 #if CONFIG_SWSCALE
   74     sws_freeContext(sws_opts);
   75     sws_opts = NULL;
   76 #endif
   77     av_dict_free(&format_opts);
   78     av_dict_free(&codec_opts);
   79     av_dict_free(&resample_opts);
   80 }
   81 
   82 void log_callback_help(void *ptr, int level, const char *fmt, va_list vl)
   83 {
   84     vfprintf(stdout, fmt, vl);
   85 }
   86 
   87 static void (*program_exit)(int ret);
   88 
   89 void register_exit(void (*cb)(int ret))
   90 {
   91     program_exit = cb;
   92 }
   93 
   94 void exit_program(int ret)
   95 {
   96     if (program_exit)
   97         program_exit(ret);
   98 
   99     exit(ret);
  100 }
  101 
  102 double parse_number_or_die(const char *context, const char *numstr, int type,
  103                            double min, double max)
  104 {
  105     char *tail;
  106     const char *error;
  107     double d = av_strtod(numstr, &tail);
  108     if (*tail)
  109         error = "Expected number for %s but found: %s\n";
  110     else if (d < min || d > max)
  111         error = "The value for %s was %s which is not within %f - %f\n";
  112     else if (type == OPT_INT64 && (int64_t)d != d)
  113         error = "Expected int64 for %s but found %s\n";
  114     else if (type == OPT_INT && (int)d != d)
  115         error = "Expected int for %s but found %s\n";
  116     else
  117         return d;
  118     av_log(NULL, AV_LOG_FATAL, error, context, numstr, min, max);
  119     exit_program(1);
  120     return 0;
  121 }
  122 
  123 int64_t parse_time_or_die(const char *context, const char *timestr,
  124                           int is_duration)
  125 {
  126     int64_t us;
  127     if (av_parse_time(&us, timestr, is_duration) < 0) {
  128         av_log(NULL, AV_LOG_FATAL, "Invalid %s specification for %s: %s\n",
  129                is_duration ? "duration" : "date", context, timestr);
  130         exit_program(1);
  131     }
  132     return us;
  133 }
  134 
  135 void show_help_options(const OptionDef *options, const char *msg, int req_flags,
  136                        int rej_flags, int alt_flags)
  137 {
  138     const OptionDef *po;
  139     int first;
  140 
  141     first = 1;
  142     for (po = options; po->name != NULL; po++) {
  143         char buf[64];
  144 
  145         if (((po->flags & req_flags) != req_flags) ||
  146             (alt_flags && !(po->flags & alt_flags)) ||
  147             (po->flags & rej_flags))
  148             continue;
  149 
  150         if (first) {
  151             printf("%s\n", msg);
  152             first = 0;
  153         }
  154         av_strlcpy(buf, po->name, sizeof(buf));
  155         if (po->argname) {
  156             av_strlcat(buf, " ", sizeof(buf));
  157             av_strlcat(buf, po->argname, sizeof(buf));
  158         }
  159         printf("-%-17s  %s\n", buf, po->help);
  160     }
  161     printf("\n");
  162 }
  163 
  164 void show_help_children(const AVClass *class, int flags)
  165 {
  166     const AVClass *child = NULL;
  167     av_opt_show2(&class, NULL, flags, 0);
  168     printf("\n");
  169 
  170     while (child = av_opt_child_class_next(class, child))
  171         show_help_children(child, flags);
  172 }
  173 
  174 static const OptionDef *find_option(const OptionDef *po, const char *name)
  175 {
  176     const char *p = strchr(name, ':');
  177     int len = p ? p - name : strlen(name);
  178 
  179     while (po->name) {
  180         if (!strncmp(name, po->name, len) && strlen(po->name) == len)
  181             break;
  182         po++;
  183     }
  184     return po;
  185 }
  186 
  187 /* _WIN32 means using the windows libc - cygwin doesn't define that
  188  * by default. HAVE_COMMANDLINETOARGVW is true on cygwin, while
  189  * it doesn't provide the actual command line via GetCommandLineW(). */
  190 #if HAVE_COMMANDLINETOARGVW && defined(_WIN32)
  191 #include <windows.h>
  192 #include <shellapi.h>
  193 /* Will be leaked on exit */
  194 static char** win32_argv_utf8 = NULL;
  195 static int win32_argc = 0;
  196 
  197 /**
  198  * Prepare command line arguments for executable.
  199  * For Windows - perform wide-char to UTF-8 conversion.
  200  * Input arguments should be main() function arguments.
  201  * @param argc_ptr Arguments number (including executable)
  202  * @param argv_ptr Arguments list.
  203  */
  204 static void prepare_app_arguments(int *argc_ptr, char ***argv_ptr)
  205 {
  206     char *argstr_flat;
  207     wchar_t **argv_w;
  208     int i, buffsize = 0, offset = 0;
  209 
  210     if (win32_argv_utf8) {
  211         *argc_ptr = win32_argc;
  212         *argv_ptr = win32_argv_utf8;
  213         return;
  214     }
  215 
  216     win32_argc = 0;
  217     argv_w = CommandLineToArgvW(GetCommandLineW(), &win32_argc);
  218     if (win32_argc <= 0 || !argv_w)
  219         return;
  220 
  221     /* determine the UTF-8 buffer size (including NULL-termination symbols) */
  222     for (i = 0; i < win32_argc; i++)
  223         buffsize += WideCharToMultiByte(CP_UTF8, 0, argv_w[i], -1,
  224                                         NULL, 0, NULL, NULL);
  225 
  226     win32_argv_utf8 = av_mallocz(sizeof(char *) * (win32_argc + 1) + buffsize);
  227     argstr_flat     = (char *)win32_argv_utf8 + sizeof(char *) * (win32_argc + 1);
  228     if (!win32_argv_utf8) {
  229         LocalFree(argv_w);
  230         return;
  231     }
  232 
  233     for (i = 0; i < win32_argc; i++) {
  234         win32_argv_utf8[i] = &argstr_flat[offset];
  235         offset += WideCharToMultiByte(CP_UTF8, 0, argv_w[i], -1,
  236                                       &argstr_flat[offset],
  237                                       buffsize - offset, NULL, NULL);
  238     }
  239     win32_argv_utf8[i] = NULL;
  240     LocalFree(argv_w);
  241 
  242     *argc_ptr = win32_argc;
  243     *argv_ptr = win32_argv_utf8;
  244 }
  245 #else
  246 static inline void prepare_app_arguments(int *argc_ptr, char ***argv_ptr)
  247 {
  248     /* nothing to do */
  249 }
  250 #endif /* HAVE_COMMANDLINETOARGVW */
  251 
  252 static int write_option(void *optctx, const OptionDef *po, const char *opt,
  253                         const char *arg)
  254 {
  255     /* new-style options contain an offset into optctx, old-style address of
  256      * a global var*/
  257     void *dst = po->flags & (OPT_OFFSET | OPT_SPEC) ?
  258                 (uint8_t *)optctx + po->u.off : po->u.dst_ptr;
  259     int *dstcount;
  260 
  261     if (po->flags & OPT_SPEC) {
  262         SpecifierOpt **so = dst;
  263         char *p = strchr(opt, ':');
  264         char *str;
  265 
  266         dstcount = (int *)(so + 1);
  267         *so = grow_array(*so, sizeof(**so), dstcount, *dstcount + 1);
  268         str = av_strdup(p ? p + 1 : "");
  269         if (!str)
  270             return AVERROR(ENOMEM);
  271         (*so)[*dstcount - 1].specifier = str;
  272         dst = &(*so)[*dstcount - 1].u;
  273     }
  274 
  275     if (po->flags & OPT_STRING) {
  276         char *str;
  277         str = av_strdup(arg);
  278         av_freep(dst);
  279         if (!str)
  280             return AVERROR(ENOMEM);
  281         *(char **)dst = str;
  282     } else if (po->flags & OPT_BOOL || po->flags & OPT_INT) {
  283         *(int *)dst = parse_number_or_die(opt, arg, OPT_INT64, INT_MIN, INT_MAX);
  284     } else if (po->flags & OPT_INT64) {
  285         *(int64_t *)dst = parse_number_or_die(opt, arg, OPT_INT64, INT64_MIN, INT64_MAX);
  286     } else if (po->flags & OPT_TIME) {
  287         *(int64_t *)dst = parse_time_or_die(opt, arg, 1);
  288     } else if (po->flags & OPT_FLOAT) {
  289         *(float *)dst = parse_number_or_die(opt, arg, OPT_FLOAT, -INFINITY, INFINITY);
  290     } else if (po->flags & OPT_DOUBLE) {
  291         *(double *)dst = parse_number_or_die(opt, arg, OPT_DOUBLE, -INFINITY, INFINITY);
  292     } else if (po->u.func_arg) {
  293         int ret = po->u.func_arg(optctx, opt, arg);
  294         if (ret < 0) {
  295             av_log(NULL, AV_LOG_ERROR,
  296                    "Failed to set value '%s' for option '%s'\n", arg, opt);
  297             return ret;
  298         }
  299     }
  300     if (po->flags & OPT_EXIT)
  301         exit_program(0);
  302 
  303     return 0;
  304 }
  305 
  306 int parse_option(void *optctx, const char *opt, const char *arg,
  307                  const OptionDef *options)
  308 {
  309     const OptionDef *po;
  310     int ret;
  311 
  312     po = find_option(options, opt);
  313     if (!po->name && opt[0] == 'n' && opt[1] == 'o') {
  314         /* handle 'no' bool option */
  315         po = find_option(options, opt + 2);
  316         if ((po->name && (po->flags & OPT_BOOL)))
  317             arg = "0";
  318     } else if (po->flags & OPT_BOOL)
  319         arg = "1";
  320 
  321     if (!po->name)
  322         po = find_option(options, "default");
  323     if (!po->name) {
  324         av_log(NULL, AV_LOG_ERROR, "Unrecognized option '%s'\n", opt);
  325         return AVERROR(EINVAL);
  326     }
  327     if (po->flags & HAS_ARG && !arg) {
  328         av_log(NULL, AV_LOG_ERROR, "Missing argument for option '%s'\n", opt);
  329         return AVERROR(EINVAL);
  330     }
  331 
  332     ret = write_option(optctx, po, opt, arg);
  333     if (ret < 0)
  334         return ret;
  335 
  336     return !!(po->flags & HAS_ARG);
  337 }
  338 
  339 void parse_options(void *optctx, int argc, char **argv, const OptionDef *options,
  340                    void (*parse_arg_function)(void *, const char*))
  341 {
  342     const char *opt;
  343     int optindex, handleoptions = 1, ret;
  344 
  345     /* perform system-dependent conversions for arguments list */
  346     prepare_app_arguments(&argc, &argv);
  347 
  348     /* parse options */
  349     optindex = 1;
  350     while (optindex < argc) {
  351         opt = argv[optindex++];
  352 
  353         if (handleoptions && opt[0] == '-' && opt[1] != '\0') {
  354             if (opt[1] == '-' && opt[2] == '\0') {
  355                 handleoptions = 0;
  356                 continue;
  357             }
  358             opt++;
  359 
  360             if ((ret = parse_option(optctx, opt, argv[optindex], options)) < 0)
  361                 exit_program(1);
  362             optindex += ret;
  363         } else {
  364             if (parse_arg_function)
  365                 parse_arg_function(optctx, opt);
  366         }
  367     }
  368 }
  369 
  370 int parse_optgroup(void *optctx, OptionGroup *g)
  371 {
  372     int i, ret;
  373 
  374     av_log(NULL, AV_LOG_DEBUG, "Parsing a group of options: %s %s.\n",
  375            g->group_def->name, g->arg);
  376 
  377     for (i = 0; i < g->nb_opts; i++) {
  378         Option *o = &g->opts[i];
  379 
  380         if (g->group_def->flags &&
  381             !(g->group_def->flags & o->opt->flags)) {
  382             av_log(NULL, AV_LOG_ERROR, "Option %s (%s) cannot be applied to "
  383                    "%s %s -- you are trying to apply an input option to an "
  384                    "output file or vice versa. Move this option before the "
  385                    "file it belongs to.\n", o->key, o->opt->help,
  386                    g->group_def->name, g->arg);
  387             return AVERROR(EINVAL);
  388         }
  389 
  390         av_log(NULL, AV_LOG_DEBUG, "Applying option %s (%s) with argument %s.\n",
  391                o->key, o->opt->help, o->val);
  392 
  393         ret = write_option(optctx, o->opt, o->key, o->val);
  394         if (ret < 0)
  395             return ret;
  396     }
  397 
  398     av_log(NULL, AV_LOG_DEBUG, "Successfully parsed a group of options.\n");
  399 
  400     return 0;
  401 }
  402 
  403 int locate_option(int argc, char **argv, const OptionDef *options,
  404                   const char *optname)
  405 {
  406     const OptionDef *po;
  407     int i;
  408 
  409     for (i = 1; i < argc; i++) {
  410         const char *cur_opt = argv[i];
  411 
  412         if (*cur_opt++ != '-')
  413             continue;
  414 
  415         po = find_option(options, cur_opt);
  416         if (!po->name && cur_opt[0] == 'n' && cur_opt[1] == 'o')
  417             po = find_option(options, cur_opt + 2);
  418 
  419         if ((!po->name && !strcmp(cur_opt, optname)) ||
  420              (po->name && !strcmp(optname, po->name)))
  421             return i;
  422 
  423         if (!po->name || po->flags & HAS_ARG)
  424             i++;
  425     }
  426     return 0;
  427 }
  428 
  429 void parse_loglevel(int argc, char **argv, const OptionDef *options)
  430 {
  431     int idx = locate_option(argc, argv, options, "loglevel");
  432     if (!idx)
  433         idx = locate_option(argc, argv, options, "v");
  434     if (idx && argv[idx + 1])
  435         opt_loglevel(NULL, "loglevel", argv[idx + 1]);
  436 }
  437 
  438 #define FLAGS (o->type == AV_OPT_TYPE_FLAGS) ? AV_DICT_APPEND : 0
  439 int opt_default(void *optctx, const char *opt, const char *arg)
  440 {
  441     const AVOption *o;
  442     char opt_stripped[128];
  443     const char *p;
  444     const AVClass *cc = avcodec_get_class(), *fc = avformat_get_class();
  445 #if CONFIG_AVRESAMPLE
  446     const AVClass *rc = avresample_get_class();
  447 #endif
  448 #if CONFIG_SWSCALE
  449     const AVClass *sc = sws_get_class();
  450 #endif
  451 
  452     if (!(p = strchr(opt, ':')))
  453         p = opt + strlen(opt);
  454     av_strlcpy(opt_stripped, opt, FFMIN(sizeof(opt_stripped), p - opt + 1));
  455 
  456     if ((o = av_opt_find(&cc, opt_stripped, NULL, 0,
  457                          AV_OPT_SEARCH_CHILDREN | AV_OPT_SEARCH_FAKE_OBJ)) ||
  458         ((opt[0] == 'v' || opt[0] == 'a' || opt[0] == 's') &&
  459          (o = av_opt_find(&cc, opt + 1, NULL, 0, AV_OPT_SEARCH_FAKE_OBJ))))
  460         av_dict_set(&codec_opts, opt, arg, FLAGS);
  461     else if ((o = av_opt_find(&fc, opt, NULL, 0,
  462                               AV_OPT_SEARCH_CHILDREN | AV_OPT_SEARCH_FAKE_OBJ)))
  463         av_dict_set(&format_opts, opt, arg, FLAGS);
  464 #if CONFIG_AVRESAMPLE
  465     else if ((o = av_opt_find(&rc, opt, NULL, 0,
  466                               AV_OPT_SEARCH_CHILDREN | AV_OPT_SEARCH_FAKE_OBJ)))
  467         av_dict_set(&resample_opts, opt, arg, FLAGS);
  468 #endif
  469 #if CONFIG_SWSCALE
  470     else if ((o = av_opt_find(&sc, opt, NULL, 0,
  471                               AV_OPT_SEARCH_CHILDREN | AV_OPT_SEARCH_FAKE_OBJ))) {
  472         // XXX we only support sws_flags, not arbitrary sws options
  473         int ret = av_opt_set(sws_opts, opt, arg, 0);
  474         if (ret < 0) {
  475             av_log(NULL, AV_LOG_ERROR, "Error setting option %s.\n", opt);
  476             return ret;
  477         }
  478     }
  479 #endif
  480 
  481     if (o)
  482         return 0;
  483     return AVERROR_OPTION_NOT_FOUND;
  484 }
  485 
  486 /*
  487  * Check whether given option is a group separator.
  488  *
  489  * @return index of the group definition that matched or -1 if none
  490  */
  491 static int match_group_separator(const OptionGroupDef *groups, int nb_groups,
  492                                  const char *opt)
  493 {
  494     int i;
  495 
  496     for (i = 0; i < nb_groups; i++) {
  497         const OptionGroupDef *p = &groups[i];
  498         if (p->sep && !strcmp(p->sep, opt))
  499             return i;
  500     }
  501 
  502     return -1;
  503 }
  504 
  505 /*
  506  * Finish parsing an option group.
  507  *
  508  * @param group_idx which group definition should this group belong to
  509  * @param arg argument of the group delimiting option
  510  */
  511 static void finish_group(OptionParseContext *octx, int group_idx,
  512                          const char *arg)
  513 {
  514     OptionGroupList *l = &octx->groups[group_idx];
  515     OptionGroup *g;
  516 
  517     GROW_ARRAY(l->groups, l->nb_groups);
  518     g = &l->groups[l->nb_groups - 1];
  519 
  520     *g             = octx->cur_group;
  521     g->arg         = arg;
  522     g->group_def   = l->group_def;
  523 #if CONFIG_SWSCALE
  524     g->sws_opts    = sws_opts;
  525 #endif
  526     g->codec_opts  = codec_opts;
  527     g->format_opts = format_opts;
  528     g->resample_opts = resample_opts;
  529 
  530     codec_opts  = NULL;
  531     format_opts = NULL;
  532     resample_opts = NULL;
  533 #if CONFIG_SWSCALE
  534     sws_opts    = NULL;
  535 #endif
  536     init_opts();
  537 
  538     memset(&octx->cur_group, 0, sizeof(octx->cur_group));
  539 }
  540 
  541 /*
  542  * Add an option instance to currently parsed group.
  543  */
  544 static void add_opt(OptionParseContext *octx, const OptionDef *opt,
  545                     const char *key, const char *val)
  546 {
  547     int global = !(opt->flags & (OPT_PERFILE | OPT_SPEC | OPT_OFFSET));
  548     OptionGroup *g = global ? &octx->global_opts : &octx->cur_group;
  549 
  550     GROW_ARRAY(g->opts, g->nb_opts);
  551     g->opts[g->nb_opts - 1].opt = opt;
  552     g->opts[g->nb_opts - 1].key = key;
  553     g->opts[g->nb_opts - 1].val = val;
  554 }
  555 
  556 static void init_parse_context(OptionParseContext *octx,
  557                                const OptionGroupDef *groups, int nb_groups)
  558 {
  559     static const OptionGroupDef global_group = { "global" };
  560     int i;
  561 
  562     memset(octx, 0, sizeof(*octx));
  563 
  564     octx->nb_groups = nb_groups;
  565     octx->groups    = av_mallocz(sizeof(*octx->groups) * octx->nb_groups);
  566     if (!octx->groups)
  567         exit_program(1);
  568 
  569     for (i = 0; i < octx->nb_groups; i++)
  570         octx->groups[i].group_def = &groups[i];
  571 
  572     octx->global_opts.group_def = &global_group;
  573     octx->global_opts.arg       = "";
  574 
  575     init_opts();
  576 }
  577 
  578 void uninit_parse_context(OptionParseContext *octx)
  579 {
  580     int i, j;
  581 
  582     for (i = 0; i < octx->nb_groups; i++) {
  583         OptionGroupList *l = &octx->groups[i];
  584 
  585         for (j = 0; j < l->nb_groups; j++) {
  586             av_freep(&l->groups[j].opts);
  587             av_dict_free(&l->groups[j].codec_opts);
  588             av_dict_free(&l->groups[j].format_opts);
  589             av_dict_free(&l->groups[j].resample_opts);
  590 #if CONFIG_SWSCALE
  591             sws_freeContext(l->groups[j].sws_opts);
  592 #endif
  593         }
  594         av_freep(&l->groups);
  595     }
  596     av_freep(&octx->groups);
  597 
  598     av_freep(&octx->cur_group.opts);
  599     av_freep(&octx->global_opts.opts);
  600 
  601     uninit_opts();
  602 }
  603 
  604 int split_commandline(OptionParseContext *octx, int argc, char *argv[],
  605                       const OptionDef *options,
  606                       const OptionGroupDef *groups, int nb_groups)
  607 {
  608     int optindex = 1;
  609 
  610     /* perform system-dependent conversions for arguments list */
  611     prepare_app_arguments(&argc, &argv);
  612 
  613     init_parse_context(octx, groups, nb_groups);
  614     av_log(NULL, AV_LOG_DEBUG, "Splitting the commandline.\n");
  615 
  616     while (optindex < argc) {
  617         const char *opt = argv[optindex++], *arg;
  618         const OptionDef *po;
  619         int ret;
  620 
  621         av_log(NULL, AV_LOG_DEBUG, "Reading option '%s' ...", opt);
  622 
  623         /* unnamed group separators, e.g. output filename */
  624         if (opt[0] != '-' || !opt[1]) {
  625             finish_group(octx, 0, opt);
  626             av_log(NULL, AV_LOG_DEBUG, " matched as %s.\n", groups[0].name);
  627             continue;
  628         }
  629         opt++;
  630 
  631 #define GET_ARG(arg)                                                           \
  632 do {                                                                           \
  633     arg = argv[optindex++];                                                    \
  634     if (!arg) {                                                                \
  635         av_log(NULL, AV_LOG_ERROR, "Missing argument for option '%s'.\n", opt);\
  636         return AVERROR(EINVAL);                                                \
  637     }                                                                          \
  638 } while (0)
  639 
  640         /* named group separators, e.g. -i */
  641         if ((ret = match_group_separator(groups, nb_groups, opt)) >= 0) {
  642             GET_ARG(arg);
  643             finish_group(octx, ret, arg);
  644             av_log(NULL, AV_LOG_DEBUG, " matched as %s with argument '%s'.\n",
  645                    groups[ret].name, arg);
  646             continue;
  647         }
  648 
  649         /* normal options */
  650         po = find_option(options, opt);
  651         if (po->name) {
  652             if (po->flags & OPT_EXIT) {
  653                 /* optional argument, e.g. -h */
  654                 arg = argv[optindex++];
  655             } else if (po->flags & HAS_ARG) {
  656                 GET_ARG(arg);
  657             } else {
  658                 arg = "1";
  659             }
  660 
  661             add_opt(octx, po, opt, arg);
  662             av_log(NULL, AV_LOG_DEBUG, " matched as option '%s' (%s) with "
  663                    "argument '%s'.\n", po->name, po->help, arg);
  664             continue;
  665         }
  666 
  667         /* AVOptions */
  668         if (argv[optindex]) {
  669             ret = opt_default(NULL, opt, argv[optindex]);
  670             if (ret >= 0) {
  671                 av_log(NULL, AV_LOG_DEBUG, " matched as AVOption '%s' with "
  672                        "argument '%s'.\n", opt, argv[optindex]);
  673                 optindex++;
  674                 continue;
  675             } else if (ret != AVERROR_OPTION_NOT_FOUND) {
  676                 av_log(NULL, AV_LOG_ERROR, "Error parsing option '%s' "
  677                        "with argument '%s'.\n", opt, argv[optindex]);
  678                 return ret;
  679             }
  680         }
  681 
  682         /* boolean -nofoo options */
  683         if (opt[0] == 'n' && opt[1] == 'o' &&
  684             (po = find_option(options, opt + 2)) &&
  685             po->name && po->flags & OPT_BOOL) {
  686             add_opt(octx, po, opt, "0");
  687             av_log(NULL, AV_LOG_DEBUG, " matched as option '%s' (%s) with "
  688                    "argument 0.\n", po->name, po->help);
  689             continue;
  690         }
  691 
  692         av_log(NULL, AV_LOG_ERROR, "Unrecognized option '%s'.\n", opt);
  693         return AVERROR_OPTION_NOT_FOUND;
  694     }
  695 
  696     if (octx->cur_group.nb_opts || codec_opts || format_opts || resample_opts)
  697         av_log(NULL, AV_LOG_WARNING, "Trailing options were found on the "
  698                "commandline.\n");
  699 
  700     av_log(NULL, AV_LOG_DEBUG, "Finished splitting the commandline.\n");
  701 
  702     return 0;
  703 }
  704 
  705 int opt_cpuflags(void *optctx, const char *opt, const char *arg)
  706 {
  707     int flags = av_parse_cpu_flags(arg);
  708 
  709     if (flags < 0)
  710         return flags;
  711 
  712     av_set_cpu_flags_mask(flags);
  713     return 0;
  714 }
  715 
  716 int opt_loglevel(void *optctx, const char *opt, const char *arg)
  717 {
  718     const struct { const char *name; int level; } log_levels[] = {
  719         { "quiet"  , AV_LOG_QUIET   },
  720         { "panic"  , AV_LOG_PANIC   },
  721         { "fatal"  , AV_LOG_FATAL   },
  722         { "error"  , AV_LOG_ERROR   },
  723         { "warning", AV_LOG_WARNING },
  724         { "info"   , AV_LOG_INFO    },
  725         { "verbose", AV_LOG_VERBOSE },
  726         { "debug"  , AV_LOG_DEBUG   },
  727         { "trace"  , AV_LOG_TRACE   },
  728     };
  729     char *tail;
  730     int level;
  731     int i;
  732 
  733     for (i = 0; i < FF_ARRAY_ELEMS(log_levels); i++) {
  734         if (!strcmp(log_levels[i].name, arg)) {
  735             av_log_set_level(log_levels[i].level);
  736             return 0;
  737         }
  738     }
  739 
  740     level = strtol(arg, &tail, 10);
  741     if (*tail) {
  742         av_log(NULL, AV_LOG_FATAL, "Invalid loglevel \"%s\". "
  743                "Possible levels are numbers or:\n", arg);
  744         for (i = 0; i < FF_ARRAY_ELEMS(log_levels); i++)
  745             av_log(NULL, AV_LOG_FATAL, "\"%s\"\n", log_levels[i].name);
  746         exit_program(1);
  747     }
  748     av_log_set_level(level);
  749     return 0;
  750 }
  751 
  752 int opt_timelimit(void *optctx, const char *opt, const char *arg)
  753 {
  754 #if HAVE_SETRLIMIT
  755     int lim = parse_number_or_die(opt, arg, OPT_INT64, 0, INT_MAX);
  756     struct rlimit rl = { lim, lim + 1 };
  757     if (setrlimit(RLIMIT_CPU, &rl))
  758         perror("setrlimit");
  759 #else
  760     av_log(NULL, AV_LOG_WARNING, "-%s not implemented on this OS\n", opt);
  761 #endif
  762     return 0;
  763 }
  764 
  765 void print_error(const char *filename, int err)
  766 {
  767     char errbuf[128];
  768     const char *errbuf_ptr = errbuf;
  769 
  770     if (av_strerror(err, errbuf, sizeof(errbuf)) < 0)
  771         errbuf_ptr = strerror(AVUNERROR(err));
  772     av_log(NULL, AV_LOG_ERROR, "%s: %s\n", filename, errbuf_ptr);
  773 }
  774 
  775 static int warned_cfg = 0;
  776 
  777 #define INDENT        1
  778 #define SHOW_VERSION  2
  779 #define SHOW_CONFIG   4
  780 
  781 #define PRINT_LIB_INFO(libname, LIBNAME, flags, level)                  \
  782     if (CONFIG_##LIBNAME) {                                             \
  783         const char *indent = flags & INDENT? "  " : "";                 \
  784         if (flags & SHOW_VERSION) {                                     \
  785             unsigned int version = libname##_version();                 \
  786             av_log(NULL, level,                                         \
  787                    "%slib%-10s %2d.%3d.%2d / %2d.%3d.%2d\n",            \
  788                    indent, #libname,                                    \
  789                    LIB##LIBNAME##_VERSION_MAJOR,                        \
  790                    LIB##LIBNAME##_VERSION_MINOR,                        \
  791                    LIB##LIBNAME##_VERSION_MICRO,                        \
  792                    version >> 16, version >> 8 & 0xff, version & 0xff); \
  793         }                                                               \
  794         if (flags & SHOW_CONFIG) {                                      \
  795             const char *cfg = libname##_configuration();                \
  796             if (strcmp(LIBAV_CONFIGURATION, cfg)) {                     \
  797                 if (!warned_cfg) {                                      \
  798                     av_log(NULL, level,                                 \
  799                             "%sWARNING: library configuration mismatch\n", \
  800                             indent);                                    \
  801                     warned_cfg = 1;                                     \
  802                 }                                                       \
  803                 av_log(NULL, level, "%s%-11s configuration: %s\n",      \
  804                         indent, #libname, cfg);                         \
  805             }                                                           \
  806         }                                                               \
  807     }                                                                   \
  808 
  809 static void print_all_libs_info(int flags, int level)
  810 {
  811     PRINT_LIB_INFO(avutil,   AVUTIL,   flags, level);
  812     PRINT_LIB_INFO(avcodec,  AVCODEC,  flags, level);
  813     PRINT_LIB_INFO(avformat, AVFORMAT, flags, level);
  814     PRINT_LIB_INFO(avdevice, AVDEVICE, flags, level);
  815     PRINT_LIB_INFO(avfilter, AVFILTER, flags, level);
  816     PRINT_LIB_INFO(avresample, AVRESAMPLE, flags, level);
  817     PRINT_LIB_INFO(swscale,  SWSCALE,  flags, level);
  818 }
  819 
  820 void show_banner(void)
  821 {
  822     av_log(NULL, AV_LOG_INFO,
  823            "%s version " LIBAV_VERSION ", Copyright (c) %d-%d the Libav developers\n",
  824            program_name, program_birth_year, this_year);
  825     av_log(NULL, AV_LOG_INFO, "  built on %s %s with %s\n",
  826            __DATE__, __TIME__, CC_IDENT);
  827     av_log(NULL, AV_LOG_VERBOSE, "  configuration: " LIBAV_CONFIGURATION "\n");
  828     print_all_libs_info(INDENT|SHOW_CONFIG,  AV_LOG_VERBOSE);
  829     print_all_libs_info(INDENT|SHOW_VERSION, AV_LOG_VERBOSE);
  830 }
  831 
  832 int show_version(void *optctx, const char *opt, const char *arg)
  833 {
  834     av_log_set_callback(log_callback_help);
  835     printf("%s " LIBAV_VERSION "\n", program_name);
  836     print_all_libs_info(SHOW_VERSION, AV_LOG_INFO);
  837 
  838     return 0;
  839 }
  840 
  841 int show_license(void *optctx, const char *opt, const char *arg)
  842 {
  843     printf(
  844 #if CONFIG_NONFREE
  845     "This version of %s has nonfree parts compiled in.\n"
  846     "Therefore it is not legally redistributable.\n",
  847     program_name
  848 #elif CONFIG_GPLV3
  849     "%s is free software; you can redistribute it and/or modify\n"
  850     "it under the terms of the GNU General Public License as published by\n"
  851     "the Free Software Foundation; either version 3 of the License, or\n"
  852     "(at your option) any later version.\n"
  853     "\n"
  854     "%s is distributed in the hope that it will be useful,\n"
  855     "but WITHOUT ANY WARRANTY; without even the implied warranty of\n"
  856     "MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n"
  857     "GNU General Public License for more details.\n"
  858     "\n"
  859     "You should have received a copy of the GNU General Public License\n"
  860     "along with %s.  If not, see <http://www.gnu.org/licenses/>.\n",
  861     program_name, program_name, program_name
  862 #elif CONFIG_GPL
  863     "%s is free software; you can redistribute it and/or modify\n"
  864     "it under the terms of the GNU General Public License as published by\n"
  865     "the Free Software Foundation; either version 2 of the License, or\n"
  866     "(at your option) any later version.\n"
  867     "\n"
  868     "%s is distributed in the hope that it will be useful,\n"
  869     "but WITHOUT ANY WARRANTY; without even the implied warranty of\n"
  870     "MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n"
  871     "GNU General Public License for more details.\n"
  872     "\n"
  873     "You should have received a copy of the GNU General Public License\n"
  874     "along with %s; if not, write to the Free Software\n"
  875     "Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA\n",
  876     program_name, program_name, program_name
  877 #elif CONFIG_LGPLV3
  878     "%s is free software; you can redistribute it and/or modify\n"
  879     "it under the terms of the GNU Lesser General Public License as published by\n"
  880     "the Free Software Foundation; either version 3 of the License, or\n"
  881     "(at your option) any later version.\n"
  882     "\n"
  883     "%s is distributed in the hope that it will be useful,\n"
  884     "but WITHOUT ANY WARRANTY; without even the implied warranty of\n"
  885     "MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n"
  886     "GNU Lesser General Public License for more details.\n"
  887     "\n"
  888     "You should have received a copy of the GNU Lesser General Public License\n"
  889     "along with %s.  If not, see <http://www.gnu.org/licenses/>.\n",
  890     program_name, program_name, program_name
  891 #else
  892     "%s is free software; you can redistribute it and/or\n"
  893     "modify it under the terms of the GNU Lesser General Public\n"
  894     "License as published by the Free Software Foundation; either\n"
  895     "version 2.1 of the License, or (at your option) any later version.\n"
  896     "\n"
  897     "%s is distributed in the hope that it will be useful,\n"
  898     "but WITHOUT ANY WARRANTY; without even the implied warranty of\n"
  899     "MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n"
  900     "Lesser General Public License for more details.\n"
  901     "\n"
  902     "You should have received a copy of the GNU Lesser General Public\n"
  903     "License along with %s; if not, write to the Free Software\n"
  904     "Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA\n",
  905     program_name, program_name, program_name
  906 #endif
  907     );
  908 
  909     return 0;
  910 }
  911 
  912 int show_formats(void *optctx, const char *opt, const char *arg)
  913 {
  914     AVInputFormat *ifmt  = NULL;
  915     AVOutputFormat *ofmt = NULL;
  916     const char *last_name;
  917 
  918     printf("File formats:\n"
  919            " D. = Demuxing supported\n"
  920            " .E = Muxing supported\n"
  921            " --\n");
  922     last_name = "000";
  923     for (;;) {
  924         int decode = 0;
  925         int encode = 0;
  926         const char *name      = NULL;
  927         const char *long_name = NULL;
  928 
  929         while ((ofmt = av_oformat_next(ofmt))) {
  930             if ((!name || strcmp(ofmt->name, name) < 0) &&
  931                 strcmp(ofmt->name, last_name) > 0) {
  932                 name      = ofmt->name;
  933                 long_name = ofmt->long_name;
  934                 encode    = 1;
  935             }
  936         }
  937         while ((ifmt = av_iformat_next(ifmt))) {
  938             if ((!name || strcmp(ifmt->name, name) < 0) &&
  939                 strcmp(ifmt->name, last_name) > 0) {
  940                 name      = ifmt->name;
  941                 long_name = ifmt->long_name;
  942                 encode    = 0;
  943             }
  944             if (name && strcmp(ifmt->name, name) == 0)
  945                 decode = 1;
  946         }
  947         if (!name)
  948             break;
  949         last_name = name;
  950 
  951         printf(" %s%s %-15s %s\n",
  952                decode ? "D" : " ",
  953                encode ? "E" : " ",
  954                name,
  955             long_name ? long_name:" ");
  956     }
  957     return 0;
  958 }
  959 
  960 #define PRINT_CODEC_SUPPORTED(codec, field, type, list_name, term, get_name) \
  961     if (codec->field) {                                                      \
  962         const type *p = c->field;                                            \
  963                                                                              \
  964         printf("    Supported " list_name ":");                              \
  965         while (*p != term) {                                                 \
  966             get_name(*p);                                                    \
  967             printf(" %s", name);                                             \
  968             p++;                                                             \
  969         }                                                                    \
  970         printf("\n");                                                        \
  971     }                                                                        \
  972 
  973 static void print_codec(const AVCodec *c)
  974 {
  975     int encoder = av_codec_is_encoder(c);
  976 
  977     printf("%s %s [%s]:\n", encoder ? "Encoder" : "Decoder", c->name,
  978            c->long_name ? c->long_name : "");
  979 
  980     printf("    General capabilities: ");
  981     if (c->capabilities & AV_CODEC_CAP_DRAW_HORIZ_BAND)
  982         printf("horizband ");
  983     if (c->capabilities & AV_CODEC_CAP_DR1)
  984         printf("dr1 ");
  985     if (c->capabilities & AV_CODEC_CAP_TRUNCATED)
  986         printf("trunc ");
  987     if (c->capabilities & AV_CODEC_CAP_DELAY)
  988         printf("delay ");
  989     if (c->capabilities & AV_CODEC_CAP_SMALL_LAST_FRAME)
  990         printf("small ");
  991     if (c->capabilities & AV_CODEC_CAP_SUBFRAMES)
  992         printf("subframes ");
  993     if (c->capabilities & AV_CODEC_CAP_EXPERIMENTAL)
  994         printf("exp ");
  995     if (c->capabilities & AV_CODEC_CAP_CHANNEL_CONF)
  996         printf("chconf ");
  997     if (c->capabilities & AV_CODEC_CAP_PARAM_CHANGE)
  998         printf("paramchange ");
  999     if (c->capabilities & AV_CODEC_CAP_VARIABLE_FRAME_SIZE)
 1000         printf("variable ");
 1001     if (c->capabilities & (AV_CODEC_CAP_FRAME_THREADS |
 1002                            AV_CODEC_CAP_SLICE_THREADS |
 1003                            AV_CODEC_CAP_AUTO_THREADS))
 1004         printf("threads ");
 1005     if (!c->capabilities)
 1006         printf("none");
 1007     printf("\n");
 1008 
 1009     if (c->type == AVMEDIA_TYPE_VIDEO) {
 1010         printf("    Threading capabilities: ");
 1011         switch (c->capabilities & (AV_CODEC_CAP_FRAME_THREADS |
 1012                                    AV_CODEC_CAP_SLICE_THREADS |
 1013                                    AV_CODEC_CAP_AUTO_THREADS)) {
 1014         case AV_CODEC_CAP_FRAME_THREADS |
 1015              AV_CODEC_CAP_SLICE_THREADS: printf("frame and slice"); break;
 1016         case AV_CODEC_CAP_FRAME_THREADS: printf("frame");           break;
 1017         case AV_CODEC_CAP_SLICE_THREADS: printf("slice");           break;
 1018         case AV_CODEC_CAP_AUTO_THREADS : printf("auto");            break;
 1019         default:                         printf("none");            break;
 1020         }
 1021         printf("\n");
 1022     }
 1023 
 1024     if (c->supported_framerates) {
 1025         const AVRational *fps = c->supported_framerates;
 1026 
 1027         printf("    Supported framerates:");
 1028         while (fps->num) {
 1029             printf(" %d/%d", fps->num, fps->den);
 1030             fps++;
 1031         }
 1032         printf("\n");
 1033     }
 1034     PRINT_CODEC_SUPPORTED(c, pix_fmts, enum AVPixelFormat, "pixel formats",
 1035                           AV_PIX_FMT_NONE, GET_PIX_FMT_NAME);
 1036     PRINT_CODEC_SUPPORTED(c, supported_samplerates, int, "sample rates", 0,
 1037                           GET_SAMPLE_RATE_NAME);
 1038     PRINT_CODEC_SUPPORTED(c, sample_fmts, enum AVSampleFormat, "sample formats",
 1039                           AV_SAMPLE_FMT_NONE, GET_SAMPLE_FMT_NAME);
 1040     PRINT_CODEC_SUPPORTED(c, channel_layouts, uint64_t, "channel layouts",
 1041                           0, GET_CH_LAYOUT_DESC);
 1042 
 1043     if (c->priv_class) {
 1044         show_help_children(c->priv_class,
 1045                            AV_OPT_FLAG_ENCODING_PARAM |
 1046                            AV_OPT_FLAG_DECODING_PARAM);
 1047     }
 1048 }
 1049 
 1050 static char get_media_type_char(enum AVMediaType type)
 1051 {
 1052     switch (type) {
 1053         case AVMEDIA_TYPE_VIDEO:    return 'V';
 1054         case AVMEDIA_TYPE_AUDIO:    return 'A';
 1055         case AVMEDIA_TYPE_SUBTITLE: return 'S';
 1056         default:                    return '?';
 1057     }
 1058 }
 1059 
 1060 static const AVCodec *next_codec_for_id(enum AVCodecID id, const AVCodec *prev,
 1061                                         int encoder)
 1062 {
 1063     while ((prev = av_codec_next(prev))) {
 1064         if (prev->id == id &&
 1065             (encoder ? av_codec_is_encoder(prev) : av_codec_is_decoder(prev)))
 1066             return prev;
 1067     }
 1068     return NULL;
 1069 }
 1070 
 1071 static void print_codecs_for_id(enum AVCodecID id, int encoder)
 1072 {
 1073     const AVCodec *codec = NULL;
 1074 
 1075     printf(" (%s: ", encoder ? "encoders" : "decoders");
 1076 
 1077     while ((codec = next_codec_for_id(id, codec, encoder)))
 1078         printf("%s ", codec->name);
 1079 
 1080     printf(")");
 1081 }
 1082 
 1083 int show_codecs(void *optctx, const char *opt, const char *arg)
 1084 {
 1085     const AVCodecDescriptor *desc = NULL;
 1086 
 1087     printf("Codecs:\n"
 1088            " D..... = Decoding supported\n"
 1089            " .E.... = Encoding supported\n"
 1090            " ..V... = Video codec\n"
 1091            " ..A... = Audio codec\n"
 1092            " ..S... = Subtitle codec\n"
 1093            " ...I.. = Intra frame-only codec\n"
 1094            " ....L. = Lossy compression\n"
 1095            " .....S = Lossless compression\n"
 1096            " -------\n");
 1097     while ((desc = avcodec_descriptor_next(desc))) {
 1098         const AVCodec *codec = NULL;
 1099 
 1100         printf(avcodec_find_decoder(desc->id) ? "D" : ".");
 1101         printf(avcodec_find_encoder(desc->id) ? "E" : ".");
 1102 
 1103         printf("%c", get_media_type_char(desc->type));
 1104         printf((desc->props & AV_CODEC_PROP_INTRA_ONLY) ? "I" : ".");
 1105         printf((desc->props & AV_CODEC_PROP_LOSSY)      ? "L" : ".");
 1106         printf((desc->props & AV_CODEC_PROP_LOSSLESS)   ? "S" : ".");
 1107 
 1108         printf(" %-20s %s", desc->name, desc->long_name ? desc->long_name : "");
 1109 
 1110         /* print decoders/encoders when there's more than one or their
 1111          * names are different from codec name */
 1112         while ((codec = next_codec_for_id(desc->id, codec, 0))) {
 1113             if (strcmp(codec->name, desc->name)) {
 1114                 print_codecs_for_id(desc->id, 0);
 1115                 break;
 1116             }
 1117         }
 1118         codec = NULL;
 1119         while ((codec = next_codec_for_id(desc->id, codec, 1))) {
 1120             if (strcmp(codec->name, desc->name)) {
 1121                 print_codecs_for_id(desc->id, 1);
 1122                 break;
 1123             }
 1124         }
 1125 
 1126         printf("\n");
 1127     }
 1128     return 0;
 1129 }
 1130 
 1131 static void print_codecs(int encoder)
 1132 {
 1133     const AVCodecDescriptor *desc = NULL;
 1134 
 1135     printf("%s:\n"
 1136            " V... = Video\n"
 1137            " A... = Audio\n"
 1138            " S... = Subtitle\n"
 1139            " .F.. = Frame-level multithreading\n"
 1140            " ..S. = Slice-level multithreading\n"
 1141            " ...X = Codec is experimental\n"
 1142            " ---\n",
 1143            encoder ? "Encoders" : "Decoders");
 1144     while ((desc = avcodec_descriptor_next(desc))) {
 1145         const AVCodec *codec = NULL;
 1146 
 1147         while ((codec = next_codec_for_id(desc->id, codec, encoder))) {
 1148             printf("%c", get_media_type_char(desc->type));
 1149             printf((codec->capabilities & AV_CODEC_CAP_FRAME_THREADS) ? "F" : ".");
 1150             printf((codec->capabilities & AV_CODEC_CAP_SLICE_THREADS) ? "S" : ".");
 1151             printf((codec->capabilities & AV_CODEC_CAP_EXPERIMENTAL)  ? "X" : ".");
 1152 
 1153             printf(" %-20s %s", codec->name, codec->long_name ? codec->long_name : "");
 1154             if (strcmp(codec->name, desc->name))
 1155                 printf(" (codec %s)", desc->name);
 1156 
 1157             printf("\n");
 1158         }
 1159     }
 1160 }
 1161 
 1162 int show_decoders(void *optctx, const char *opt, const char *arg)
 1163 {
 1164     print_codecs(0);
 1165     return 0;
 1166 }
 1167 
 1168 int show_encoders(void *optctx, const char *opt, const char *arg)
 1169 {
 1170     print_codecs(1);
 1171     return 0;
 1172 }
 1173 
 1174 int show_bsfs(void *optctx, const char *opt, const char *arg)
 1175 {
 1176     const AVBitStreamFilter *bsf = NULL;
 1177     void *opaque = NULL;
 1178 
 1179     printf("Bitstream filters:\n");
 1180     while ((bsf = av_bsf_next(&opaque)))
 1181         printf("%s\n", bsf->name);
 1182     printf("\n");
 1183     return 0;
 1184 }
 1185 
 1186 int show_protocols(void *optctx, const char *opt, const char *arg)
 1187 {
 1188     void *opaque = NULL;
 1189     const char *name;
 1190 
 1191     printf("Supported file protocols:\n"
 1192            "Input:\n");
 1193     while ((name = avio_enum_protocols(&opaque, 0)))
 1194         printf("%s\n", name);
 1195     printf("Output:\n");
 1196     while ((name = avio_enum_protocols(&opaque, 1)))
 1197         printf("%s\n", name);
 1198     return 0;
 1199 }
 1200 
 1201 int show_filters(void *optctx, const char *opt, const char *arg)
 1202 {
 1203 #if CONFIG_AVFILTER
 1204     const AVFilter *filter = NULL;
 1205 
 1206     printf("Filters:\n");
 1207     while ((filter = avfilter_next(filter)))
 1208         printf("%-16s %s\n", filter->name, filter->description);
 1209 #else
 1210     printf("No filters available: libavfilter disabled\n");
 1211 #endif
 1212     return 0;
 1213 }
 1214 
 1215 int show_pix_fmts(void *optctx, const char *opt, const char *arg)
 1216 {
 1217     const AVPixFmtDescriptor *pix_desc = NULL;
 1218 
 1219     printf("Pixel formats:\n"
 1220            "I.... = Supported Input  format for conversion\n"
 1221            ".O... = Supported Output format for conversion\n"
 1222            "..H.. = Hardware accelerated format\n"
 1223            "...P. = Paletted format\n"
 1224            "....B = Bitstream format\n"
 1225            "FLAGS NAME            NB_COMPONENTS BITS_PER_PIXEL\n"
 1226            "-----\n");
 1227 
 1228 #if !CONFIG_SWSCALE
 1229 #   define sws_isSupportedInput(x)  0
 1230 #   define sws_isSupportedOutput(x) 0
 1231 #endif
 1232 
 1233     while ((pix_desc = av_pix_fmt_desc_next(pix_desc))) {
 1234         enum AVPixelFormat pix_fmt = av_pix_fmt_desc_get_id(pix_desc);
 1235         printf("%c%c%c%c%c %-16s       %d            %2d\n",
 1236                sws_isSupportedInput (pix_fmt)              ? 'I' : '.',
 1237                sws_isSupportedOutput(pix_fmt)              ? 'O' : '.',
 1238                pix_desc->flags & AV_PIX_FMT_FLAG_HWACCEL   ? 'H' : '.',
 1239                pix_desc->flags & AV_PIX_FMT_FLAG_PAL       ? 'P' : '.',
 1240                pix_desc->flags & AV_PIX_FMT_FLAG_BITSTREAM ? 'B' : '.',
 1241                pix_desc->name,
 1242                pix_desc->nb_components,
 1243                av_get_bits_per_pixel(pix_desc));
 1244     }
 1245     return 0;
 1246 }
 1247 
 1248 int show_sample_fmts(void *optctx, const char *opt, const char *arg)
 1249 {
 1250     int i;
 1251     char fmt_str[128];
 1252     for (i = -1; i < AV_SAMPLE_FMT_NB; i++)
 1253         printf("%s\n", av_get_sample_fmt_string(fmt_str, sizeof(fmt_str), i));
 1254     return 0;
 1255 }
 1256 
 1257 static void show_help_codec(const char *name, int encoder)
 1258 {
 1259     const AVCodecDescriptor *desc;
 1260     const AVCodec *codec;
 1261 
 1262     if (!name) {
 1263         av_log(NULL, AV_LOG_ERROR, "No codec name specified.\n");
 1264         return;
 1265     }
 1266 
 1267     codec = encoder ? avcodec_find_encoder_by_name(name) :
 1268                       avcodec_find_decoder_by_name(name);
 1269 
 1270     if (codec)
 1271         print_codec(codec);
 1272     else if ((desc = avcodec_descriptor_get_by_name(name))) {
 1273         int printed = 0;
 1274 
 1275         while ((codec = next_codec_for_id(desc->id, codec, encoder))) {
 1276             printed = 1;
 1277             print_codec(codec);
 1278         }
 1279 
 1280         if (!printed) {
 1281             av_log(NULL, AV_LOG_ERROR, "Codec '%s' is known to Libav, "
 1282                    "but no %s for it are available. Libav might need to be "
 1283                    "recompiled with additional external libraries.\n",
 1284                    name, encoder ? "encoders" : "decoders");
 1285         }
 1286     } else {
 1287         av_log(NULL, AV_LOG_ERROR, "Codec '%s' is not recognized by Libav.\n",
 1288                name);
 1289     }
 1290 }
 1291 
 1292 static void show_help_demuxer(const char *name)
 1293 {
 1294     const AVInputFormat *fmt = av_find_input_format(name);
 1295 
 1296     if (!fmt) {
 1297         av_log(NULL, AV_LOG_ERROR, "Unknown format '%s'.\n", name);
 1298         return;
 1299     }
 1300 
 1301     printf("Demuxer %s [%s]:\n", fmt->name, fmt->long_name);
 1302 
 1303     if (fmt->extensions)
 1304         printf("    Common extensions: %s.\n", fmt->extensions);
 1305 
 1306     if (fmt->priv_class)
 1307         show_help_children(fmt->priv_class, AV_OPT_FLAG_DECODING_PARAM);
 1308 }
 1309 
 1310 static void show_help_muxer(const char *name)
 1311 {
 1312     const AVCodecDescriptor *desc;
 1313     const AVOutputFormat *fmt = av_guess_format(name, NULL, NULL);
 1314 
 1315     if (!fmt) {
 1316         av_log(NULL, AV_LOG_ERROR, "Unknown format '%s'.\n", name);
 1317         return;
 1318     }
 1319 
 1320     printf("Muxer %s [%s]:\n", fmt->name, fmt->long_name);
 1321 
 1322     if (fmt->extensions)
 1323         printf("    Common extensions: %s.\n", fmt->extensions);
 1324     if (fmt->mime_type)
 1325         printf("    Mime type: %s.\n", fmt->mime_type);
 1326     if (fmt->video_codec != AV_CODEC_ID_NONE &&
 1327         (desc = avcodec_descriptor_get(fmt->video_codec))) {
 1328         printf("    Default video codec: %s.\n", desc->name);
 1329     }
 1330     if (fmt->audio_codec != AV_CODEC_ID_NONE &&
 1331         (desc = avcodec_descriptor_get(fmt->audio_codec))) {
 1332         printf("    Default audio codec: %s.\n", desc->name);
 1333     }
 1334     if (fmt->subtitle_codec != AV_CODEC_ID_NONE &&
 1335         (desc = avcodec_descriptor_get(fmt->subtitle_codec))) {
 1336         printf("    Default subtitle codec: %s.\n", desc->name);
 1337     }
 1338 
 1339     if (fmt->priv_class)
 1340         show_help_children(fmt->priv_class, AV_OPT_FLAG_ENCODING_PARAM);
 1341 }
 1342 
 1343 #if CONFIG_AVFILTER
 1344 static void show_help_filter(const char *name)
 1345 {
 1346     const AVFilter *f = avfilter_get_by_name(name);
 1347     int i, count;
 1348 
 1349     if (!name) {
 1350         av_log(NULL, AV_LOG_ERROR, "No filter name specified.\n");
 1351         return;
 1352     } else if (!f) {
 1353         av_log(NULL, AV_LOG_ERROR, "Unknown filter '%s'.\n", name);
 1354         return;
 1355     }
 1356 
 1357     printf("Filter %s [%s]:\n", f->name, f->description);
 1358 
 1359     if (f->flags & AVFILTER_FLAG_SLICE_THREADS)
 1360         printf("    slice threading supported\n");
 1361 
 1362     printf("    Inputs:\n");
 1363     count = avfilter_pad_count(f->inputs);
 1364     for (i = 0; i < count; i++) {
 1365         printf("        %d %s (%s)\n", i, avfilter_pad_get_name(f->inputs, i),
 1366                media_type_string(avfilter_pad_get_type(f->inputs, i)));
 1367     }
 1368     if (f->flags & AVFILTER_FLAG_DYNAMIC_INPUTS)
 1369         printf("        dynamic (depending on the options)\n");
 1370 
 1371     printf("    Outputs:\n");
 1372     count = avfilter_pad_count(f->outputs);
 1373     for (i = 0; i < count; i++) {
 1374         printf("        %d %s (%s)\n", i, avfilter_pad_get_name(f->outputs, i),
 1375                media_type_string(avfilter_pad_get_type(f->outputs, i)));
 1376     }
 1377     if (f->flags & AVFILTER_FLAG_DYNAMIC_OUTPUTS)
 1378         printf("        dynamic (depending on the options)\n");
 1379 
 1380     if (f->priv_class)
 1381         show_help_children(f->priv_class, AV_OPT_FLAG_VIDEO_PARAM |
 1382                                           AV_OPT_FLAG_AUDIO_PARAM);
 1383 }
 1384 #endif
 1385 
 1386 int show_help(void *optctx, const char *opt, const char *arg)
 1387 {
 1388     char *topic, *par;
 1389     av_log_set_callback(log_callback_help);
 1390 
 1391     topic = av_strdup(arg ? arg : "");
 1392     if (!topic)
 1393         return AVERROR(ENOMEM);
 1394     par = strchr(topic, '=');
 1395     if (par)
 1396         *par++ = 0;
 1397 
 1398     if (!*topic) {
 1399         show_help_default(topic, par);
 1400     } else if (!strcmp(topic, "decoder")) {
 1401         show_help_codec(par, 0);
 1402     } else if (!strcmp(topic, "encoder")) {
 1403         show_help_codec(par, 1);
 1404     } else if (!strcmp(topic, "demuxer")) {
 1405         show_help_demuxer(par);
 1406     } else if (!strcmp(topic, "muxer")) {
 1407         show_help_muxer(par);
 1408 #if CONFIG_AVFILTER
 1409     } else if (!strcmp(topic, "filter")) {
 1410         show_help_filter(par);
 1411 #endif
 1412     } else {
 1413         show_help_default(topic, par);
 1414     }
 1415 
 1416     av_freep(&topic);
 1417     return 0;
 1418 }
 1419 
 1420 int read_yesno(void)
 1421 {
 1422     int c = getchar();
 1423     int yesno = (av_toupper(c) == 'Y');
 1424 
 1425     while (c != '\n' && c != EOF)
 1426         c = getchar();
 1427 
 1428     return yesno;
 1429 }
 1430 
 1431 void init_pts_correction(PtsCorrectionContext *ctx)
 1432 {
 1433     ctx->num_faulty_pts = ctx->num_faulty_dts = 0;
 1434     ctx->last_pts = ctx->last_dts = INT64_MIN;
 1435 }
 1436 
 1437 int64_t guess_correct_pts(PtsCorrectionContext *ctx, int64_t reordered_pts,
 1438                           int64_t dts)
 1439 {
 1440     int64_t pts = AV_NOPTS_VALUE;
 1441 
 1442     if (dts != AV_NOPTS_VALUE) {
 1443         ctx->num_faulty_dts += dts <= ctx->last_dts;
 1444         ctx->last_dts = dts;
 1445     }
 1446     if (reordered_pts != AV_NOPTS_VALUE) {
 1447         ctx->num_faulty_pts += reordered_pts <= ctx->last_pts;
 1448         ctx->last_pts = reordered_pts;
 1449     }
 1450     if ((ctx->num_faulty_pts<=ctx->num_faulty_dts || dts == AV_NOPTS_VALUE)
 1451         && reordered_pts != AV_NOPTS_VALUE)
 1452         pts = reordered_pts;
 1453     else
 1454         pts = dts;
 1455 
 1456     return pts;
 1457 }
 1458 
 1459 FILE *get_preset_file(char *filename, size_t filename_size,
 1460                       const char *preset_name, int is_path,
 1461                       const char *codec_name)
 1462 {
 1463     FILE *f = NULL;
 1464     int i;
 1465     const char *base[3] = { getenv("AVCONV_DATADIR"),
 1466                             getenv("HOME"),
 1467                             AVCONV_DATADIR, };
 1468 
 1469     if (is_path) {
 1470         av_strlcpy(filename, preset_name, filename_size);
 1471         f = fopen(filename, "r");
 1472     } else {
 1473         for (i = 0; i < 3 && !f; i++) {
 1474             if (!base[i])
 1475                 continue;
 1476             snprintf(filename, filename_size, "%s%s/%s.avpreset", base[i],
 1477                      i != 1 ? "" : "/.avconv", preset_name);
 1478             f = fopen(filename, "r");
 1479             if (!f && codec_name) {
 1480                 snprintf(filename, filename_size,
 1481                          "%s%s/%s-%s.avpreset",
 1482                          base[i], i != 1 ? "" : "/.avconv", codec_name,
 1483                          preset_name);
 1484                 f = fopen(filename, "r");
 1485             }
 1486         }
 1487     }
 1488 
 1489     return f;
 1490 }
 1491 
 1492 int check_stream_specifier(AVFormatContext *s, AVStream *st, const char *spec)
 1493 {
 1494     if (*spec <= '9' && *spec >= '0') /* opt:index */
 1495         return strtol(spec, NULL, 0) == st->index;
 1496     else if (*spec == 'v' || *spec == 'a' || *spec == 's' || *spec == 'd' ||
 1497              *spec == 't') { /* opt:[vasdt] */
 1498         enum AVMediaType type;
 1499 
 1500         switch (*spec++) {
 1501         case 'v': type = AVMEDIA_TYPE_VIDEO;      break;
 1502         case 'a': type = AVMEDIA_TYPE_AUDIO;      break;
 1503         case 's': type = AVMEDIA_TYPE_SUBTITLE;   break;
 1504         case 'd': type = AVMEDIA_TYPE_DATA;       break;
 1505         case 't': type = AVMEDIA_TYPE_ATTACHMENT; break;
 1506         default:  av_assert0(0);
 1507         }
 1508         if (type != st->codecpar->codec_type)
 1509             return 0;
 1510         if (*spec++ == ':') { /* possibly followed by :index */
 1511             int i, index = strtol(spec, NULL, 0);
 1512             for (i = 0; i < s->nb_streams; i++)
 1513                 if (s->streams[i]->codecpar->codec_type == type && index-- == 0)
 1514                    return i == st->index;
 1515             return 0;
 1516         }
 1517         return 1;
 1518     } else if (*spec == 'p' && *(spec + 1) == ':') {
 1519         int prog_id, i, j;
 1520         char *endptr;
 1521         spec += 2;
 1522         prog_id = strtol(spec, &endptr, 0);
 1523         for (i = 0; i < s->nb_programs; i++) {
 1524             if (s->programs[i]->id != prog_id)
 1525                 continue;
 1526 
 1527             if (*endptr++ == ':') {
 1528                 int stream_idx = strtol(endptr, NULL, 0);
 1529                 return stream_idx >= 0 &&
 1530                     stream_idx < s->programs[i]->nb_stream_indexes &&
 1531                     st->index == s->programs[i]->stream_index[stream_idx];
 1532             }
 1533 
 1534             for (j = 0; j < s->programs[i]->nb_stream_indexes; j++)
 1535                 if (st->index == s->programs[i]->stream_index[j])
 1536                     return 1;
 1537         }
 1538         return 0;
 1539     } else if (*spec == 'i' && *(spec + 1) == ':') {
 1540         int stream_id;
 1541         char *endptr;
 1542         spec += 2;
 1543         stream_id = strtol(spec, &endptr, 0);
 1544         return stream_id == st->id;
 1545     } else if (*spec == 'm' && *(spec + 1) == ':') {
 1546         AVDictionaryEntry *tag;
 1547         char *key, *val;
 1548         int ret;
 1549 
 1550         spec += 2;
 1551         val = strchr(spec, ':');
 1552 
 1553         key = val ? av_strndup(spec, val - spec) : av_strdup(spec);
 1554         if (!key)
 1555             return AVERROR(ENOMEM);
 1556 
 1557         tag = av_dict_get(st->metadata, key, NULL, 0);
 1558         if (tag) {
 1559             if (!val || !strcmp(tag->value, val + 1))
 1560                 ret = 1;
 1561             else
 1562                 ret = 0;
 1563         } else
 1564             ret = 0;
 1565 
 1566         av_freep(&key);
 1567         return ret;
 1568     } else if (*spec == 'u') {
 1569         AVCodecParameters *par = st->codecpar;
 1570         int val;
 1571         switch (par->codec_type) {
 1572         case AVMEDIA_TYPE_AUDIO:
 1573             val = par->sample_rate && par->channels;
 1574             if (par->format == AV_SAMPLE_FMT_NONE)
 1575                 return 0;
 1576             break;
 1577         case AVMEDIA_TYPE_VIDEO:
 1578             val = par->width && par->height;
 1579             if (par->format == AV_PIX_FMT_NONE)
 1580                 return 0;
 1581             break;
 1582         case AVMEDIA_TYPE_UNKNOWN:
 1583             val = 0;
 1584             break;
 1585         default:
 1586             val = 1;
 1587             break;
 1588         }
 1589         return par->codec_id != AV_CODEC_ID_NONE && val != 0;
 1590     } else if (!*spec) /* empty specifier, matches everything */
 1591         return 1;
 1592 
 1593     av_log(s, AV_LOG_ERROR, "Invalid stream specifier: %s.\n", spec);
 1594     return AVERROR(EINVAL);
 1595 }
 1596 
 1597 AVDictionary *filter_codec_opts(AVDictionary *opts, enum AVCodecID codec_id,
 1598                                 AVFormatContext *s, AVStream *st, AVCodec *codec)
 1599 {
 1600     AVDictionary    *ret = NULL;
 1601     AVDictionaryEntry *t = NULL;
 1602     int            flags = s->oformat ? AV_OPT_FLAG_ENCODING_PARAM
 1603                                       : AV_OPT_FLAG_DECODING_PARAM;
 1604     char          prefix = 0;
 1605     const AVClass    *cc = avcodec_get_class();
 1606 
 1607     if (!codec)
 1608         codec            = s->oformat ? avcodec_find_encoder(codec_id)
 1609                                       : avcodec_find_decoder(codec_id);
 1610 
 1611     switch (st->codecpar->codec_type) {
 1612     case AVMEDIA_TYPE_VIDEO:
 1613         prefix  = 'v';
 1614         flags  |= AV_OPT_FLAG_VIDEO_PARAM;
 1615         break;
 1616     case AVMEDIA_TYPE_AUDIO:
 1617         prefix  = 'a';
 1618         flags  |= AV_OPT_FLAG_AUDIO_PARAM;
 1619         break;
 1620     case AVMEDIA_TYPE_SUBTITLE:
 1621         prefix  = 's';
 1622         flags  |= AV_OPT_FLAG_SUBTITLE_PARAM;
 1623         break;
 1624     }
 1625 
 1626     while (t = av_dict_get(opts, "", t, AV_DICT_IGNORE_SUFFIX)) {
 1627         char *p = strchr(t->key, ':');
 1628 
 1629         /* check stream specification in opt name */
 1630         if (p)
 1631             switch (check_stream_specifier(s, st, p + 1)) {
 1632             case  1: *p = 0; break;
 1633             case  0:         continue;
 1634             default:         return NULL;
 1635             }
 1636 
 1637         if (av_opt_find(&cc, t->key, NULL, flags, AV_OPT_SEARCH_FAKE_OBJ) ||
 1638             (codec && codec->priv_class &&
 1639              av_opt_find(&codec->priv_class, t->key, NULL, flags,
 1640                          AV_OPT_SEARCH_FAKE_OBJ)))
 1641             av_dict_set(&ret, t->key, t->value, 0);
 1642         else if (t->key[0] == prefix &&
 1643                  av_opt_find(&cc, t->key + 1, NULL, flags,
 1644                              AV_OPT_SEARCH_FAKE_OBJ))
 1645             av_dict_set(&ret, t->key + 1, t->value, 0);
 1646 
 1647         if (p)
 1648             *p = ':';
 1649     }
 1650     return ret;
 1651 }
 1652 
 1653 AVDictionary **setup_find_stream_info_opts(AVFormatContext *s,
 1654                                            AVDictionary *codec_opts)
 1655 {
 1656     int i;
 1657     AVDictionary **opts;
 1658 
 1659     if (!s->nb_streams)
 1660         return NULL;
 1661     opts = av_mallocz(s->nb_streams * sizeof(*opts));
 1662     if (!opts) {
 1663         av_log(NULL, AV_LOG_ERROR,
 1664                "Could not alloc memory for stream options.\n");
 1665         return NULL;
 1666     }
 1667     for (i = 0; i < s->nb_streams; i++)
 1668         opts[i] = filter_codec_opts(codec_opts, s->streams[i]->codecpar->codec_id,
 1669                                     s, s->streams[i], NULL);
 1670     return opts;
 1671 }
 1672 
 1673 void *grow_array(void *array, int elem_size, int *size, int new_size)
 1674 {
 1675     if (new_size >= INT_MAX / elem_size) {
 1676         av_log(NULL, AV_LOG_ERROR, "Array too big.\n");
 1677         exit_program(1);
 1678     }
 1679     if (*size < new_size) {
 1680         uint8_t *tmp = av_realloc(array, new_size*elem_size);
 1681         if (!tmp) {
 1682             av_log(NULL, AV_LOG_ERROR, "Could not alloc buffer.\n");
 1683             exit_program(1);
 1684         }
 1685         memset(tmp + *size*elem_size, 0, (new_size-*size) * elem_size);
 1686         *size = new_size;
 1687         return tmp;
 1688     }
 1689     return array;
 1690 }
 1691 
 1692 const char *media_type_string(enum AVMediaType media_type)
 1693 {
 1694     switch (media_type) {
 1695     case AVMEDIA_TYPE_VIDEO:      return "video";
 1696     case AVMEDIA_TYPE_AUDIO:      return "audio";
 1697     case AVMEDIA_TYPE_DATA:       return "data";
 1698     case AVMEDIA_TYPE_SUBTITLE:   return "subtitle";
 1699     case AVMEDIA_TYPE_ATTACHMENT: return "attachment";
 1700     default:                      return "unknown";
 1701     }
 1702 }