cmdutils.c

Go to the documentation of this file.
00001 /*
00002  * Various utilities for command line tools
00003  * Copyright (c) 2000-2003 Fabrice Bellard
00004  *
00005  * This file is part of FFmpeg.
00006  *
00007  * FFmpeg is free software; you can redistribute it and/or
00008  * modify it under the terms of the GNU Lesser General Public
00009  * License as published by the Free Software Foundation; either
00010  * version 2.1 of the License, or (at your option) any later version.
00011  *
00012  * FFmpeg is distributed in the hope that it will be useful,
00013  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00014  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00015  * Lesser General Public License for more details.
00016  *
00017  * You should have received a copy of the GNU Lesser General Public
00018  * License along with FFmpeg; if not, write to the Free Software
00019  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
00020  */
00021 
00022 #include <string.h>
00023 #include <stdlib.h>
00024 #include <errno.h>
00025 #include <math.h>
00026 
00027 #include "config.h"
00028 #include "libavformat/avformat.h"
00029 #include "libavfilter/avfilter.h"
00030 #include "libavdevice/avdevice.h"
00031 #include "libavutil/avstring.h"
00032 #include "cmdutils.h"
00033 #include "version.h"
00034 #ifdef CONFIG_NETWORK
00035 #include "libavformat/network.h"
00036 #endif
00037 
00038 #undef exit
00039 
00040 
00041 double parse_number_or_die(const char *context, const char *numstr, int type, double min, double max)
00042 {
00043     char *tail;
00044     const char *error;
00045     double d = strtod(numstr, &tail);
00046     if (*tail)
00047         error= "Expected number for %s but found: %s\n";
00048     else if (d < min || d > max)
00049         error= "The value for %s was %s which is not within %f - %f\n";
00050     else if(type == OPT_INT64 && (int64_t)d != d)
00051         error= "Expected int64 for %s but found %s\n";
00052     else
00053         return d;
00054     fprintf(stderr, error, context, numstr, min, max);
00055     exit(1);
00056 }
00057 
00058 int64_t parse_time_or_die(const char *context, const char *timestr, int is_duration)
00059 {
00060     int64_t us = parse_date(timestr, is_duration);
00061     if (us == INT64_MIN) {
00062         fprintf(stderr, "Invalid %s specification for %s: %s\n",
00063                 is_duration ? "duration" : "date", context, timestr);
00064         exit(1);
00065     }
00066     return us;
00067 }
00068 
00069 void show_help_options(const OptionDef *options, const char *msg, int mask, int value)
00070 {
00071     const OptionDef *po;
00072     int first;
00073 
00074     first = 1;
00075     for(po = options; po->name != NULL; po++) {
00076         char buf[64];
00077         if ((po->flags & mask) == value) {
00078             if (first) {
00079                 printf("%s", msg);
00080                 first = 0;
00081             }
00082             av_strlcpy(buf, po->name, sizeof(buf));
00083             if (po->flags & HAS_ARG) {
00084                 av_strlcat(buf, " ", sizeof(buf));
00085                 av_strlcat(buf, po->argname, sizeof(buf));
00086             }
00087             printf("-%-17s  %s\n", buf, po->help);
00088         }
00089     }
00090 }
00091 
00092 static const OptionDef* find_option(const OptionDef *po, const char *name){
00093     while (po->name != NULL) {
00094         if (!strcmp(name, po->name))
00095             break;
00096         po++;
00097     }
00098     return po;
00099 }
00100 
00101 void parse_options(int argc, char **argv, const OptionDef *options,
00102                    void (* parse_arg_function)(const char*))
00103 {
00104     const char *opt, *arg;
00105     int optindex, handleoptions=1;
00106     const OptionDef *po;
00107 
00108     /* parse options */
00109     optindex = 1;
00110     while (optindex < argc) {
00111         opt = argv[optindex++];
00112 
00113         if (handleoptions && opt[0] == '-' && opt[1] != '\0') {
00114           if (opt[1] == '-' && opt[2] == '\0') {
00115             handleoptions = 0;
00116             continue;
00117           }
00118             po= find_option(options, opt + 1);
00119             if (!po->name)
00120                 po= find_option(options, "default");
00121             if (!po->name) {
00122 unknown_opt:
00123                 fprintf(stderr, "%s: unrecognized option '%s'\n", argv[0], opt);
00124                 exit(1);
00125             }
00126             arg = NULL;
00127             if (po->flags & HAS_ARG) {
00128                 arg = argv[optindex++];
00129                 if (!arg) {
00130                     fprintf(stderr, "%s: missing argument for option '%s'\n", argv[0], opt);
00131                     exit(1);
00132                 }
00133             }
00134             if (po->flags & OPT_STRING) {
00135                 char *str;
00136                 str = av_strdup(arg);
00137                 *po->u.str_arg = str;
00138             } else if (po->flags & OPT_BOOL) {
00139                 *po->u.int_arg = 1;
00140             } else if (po->flags & OPT_INT) {
00141                 *po->u.int_arg = parse_number_or_die(opt+1, arg, OPT_INT64, INT_MIN, INT_MAX);
00142             } else if (po->flags & OPT_INT64) {
00143                 *po->u.int64_arg = parse_number_or_die(opt+1, arg, OPT_INT64, INT64_MIN, INT64_MAX);
00144             } else if (po->flags & OPT_FLOAT) {
00145                 *po->u.float_arg = parse_number_or_die(opt+1, arg, OPT_FLOAT, -1.0/0.0, 1.0/0.0);
00146             } else if (po->flags & OPT_FUNC2) {
00147                 if(po->u.func2_arg(opt+1, arg)<0)
00148                     goto unknown_opt;
00149             } else {
00150                 po->u.func_arg(arg);
00151             }
00152             if(po->flags & OPT_EXIT)
00153                 exit(0);
00154         } else {
00155             if (parse_arg_function)
00156                 parse_arg_function(opt);
00157         }
00158     }
00159 }
00160 
00161 void print_error(const char *filename, int err)
00162 {
00163     switch(err) {
00164     case AVERROR_NUMEXPECTED:
00165         fprintf(stderr, "%s: Incorrect image filename syntax.\n"
00166                 "Use '%%d' to specify the image number:\n"
00167                 "  for img1.jpg, img2.jpg, ..., use 'img%%d.jpg';\n"
00168                 "  for img001.jpg, img002.jpg, ..., use 'img%%03d.jpg'.\n",
00169                 filename);
00170         break;
00171     case AVERROR_INVALIDDATA:
00172         fprintf(stderr, "%s: Error while parsing header\n", filename);
00173         break;
00174     case AVERROR_NOFMT:
00175         fprintf(stderr, "%s: Unknown format\n", filename);
00176         break;
00177     case AVERROR(EIO):
00178         fprintf(stderr, "%s: I/O error occurred\n"
00179                 "Usually that means that input file is truncated and/or corrupted.\n",
00180                 filename);
00181         break;
00182     case AVERROR(ENOMEM):
00183         fprintf(stderr, "%s: memory allocation error occurred\n", filename);
00184         break;
00185     case AVERROR(ENOENT):
00186         fprintf(stderr, "%s: no such file or directory\n", filename);
00187         break;
00188 #ifdef CONFIG_NETWORK
00189     case AVERROR(FF_NETERROR(EPROTONOSUPPORT)):
00190         fprintf(stderr, "%s: Unsupported network protocol\n", filename);
00191         break;
00192 #endif
00193     default:
00194         fprintf(stderr, "%s: Error while opening file\n", filename);
00195         break;
00196     }
00197 }
00198 
00199 void show_banner(void)
00200 {
00201     fprintf(stderr, "%s version " FFMPEG_VERSION ", Copyright (c) %d-2008 Fabrice Bellard, et al.\n",
00202             program_name, program_birth_year);
00203     fprintf(stderr, "  configuration: " FFMPEG_CONFIGURATION "\n");
00204     fprintf(stderr, "  libavutil version: " AV_STRINGIFY(LIBAVUTIL_VERSION) "\n");
00205     fprintf(stderr, "  libavcodec version: " AV_STRINGIFY(LIBAVCODEC_VERSION) "\n");
00206     fprintf(stderr, "  libavformat version: " AV_STRINGIFY(LIBAVFORMAT_VERSION) "\n");
00207     fprintf(stderr, "  libavdevice version: " AV_STRINGIFY(LIBAVDEVICE_VERSION) "\n");
00208 #if ENABLE_AVFILTER
00209     fprintf(stderr, "  libavfilter version: " AV_STRINGIFY(LIBAVFILTER_VERSION) "\n");
00210 #endif
00211     fprintf(stderr, "  built on " __DATE__ " " __TIME__);
00212 #ifdef __GNUC__
00213     fprintf(stderr, ", gcc: " __VERSION__ "\n");
00214 #else
00215     fprintf(stderr, ", using a non-gcc compiler\n");
00216 #endif
00217 }
00218 
00219 void show_version(void) {
00220      /* TODO: add function interface to avutil and avformat avdevice*/
00221     printf("%s " FFMPEG_VERSION "\n", program_name);
00222     printf("libavutil   %d\n"
00223            "libavcodec  %d\n"
00224            "libavformat %d\n"
00225            "libavdevice %d\n",
00226            LIBAVUTIL_BUILD, avcodec_build(), LIBAVFORMAT_BUILD, LIBAVDEVICE_BUILD);
00227 }
00228 
00229 void show_license(void)
00230 {
00231 #ifdef CONFIG_NONFREE
00232     printf(
00233     "This version of %s has nonfree parts compiled in.\n"
00234     "Therefore it is not legally redistributable.\n",
00235     program_name
00236     );
00237 #elif CONFIG_GPL
00238     printf(
00239     "%s is free software; you can redistribute it and/or modify\n"
00240     "it under the terms of the GNU General Public License as published by\n"
00241     "the Free Software Foundation; either version 2 of the License, or\n"
00242     "(at your option) any later version.\n"
00243     "\n"
00244     "%s is distributed in the hope that it will be useful,\n"
00245     "but WITHOUT ANY WARRANTY; without even the implied warranty of\n"
00246     "MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n"
00247     "GNU General Public License for more details.\n"
00248     "\n"
00249     "You should have received a copy of the GNU General Public License\n"
00250     "along with %s; if not, write to the Free Software\n"
00251     "Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA\n",
00252     program_name, program_name, program_name
00253     );
00254 #else
00255     printf(
00256     "%s is free software; you can redistribute it and/or\n"
00257     "modify it under the terms of the GNU Lesser General Public\n"
00258     "License as published by the Free Software Foundation; either\n"
00259     "version 2.1 of the License, or (at your option) any later version.\n"
00260     "\n"
00261     "%s is distributed in the hope that it will be useful,\n"
00262     "but WITHOUT ANY WARRANTY; without even the implied warranty of\n"
00263     "MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n"
00264     "Lesser General Public License for more details.\n"
00265     "\n"
00266     "You should have received a copy of the GNU Lesser General Public\n"
00267     "License along with %s; if not, write to the Free Software\n"
00268     "Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA\n",
00269     program_name, program_name, program_name
00270     );
00271 #endif
00272 }
00273 
00274 void show_formats(void)
00275 {
00276     AVInputFormat *ifmt=NULL;
00277     AVOutputFormat *ofmt=NULL;
00278     URLProtocol *up=NULL;
00279     AVCodec *p=NULL, *p2;
00280     AVBitStreamFilter *bsf=NULL;
00281     const char *last_name;
00282 
00283     printf("File formats:\n");
00284     last_name= "000";
00285     for(;;){
00286         int decode=0;
00287         int encode=0;
00288         const char *name=NULL;
00289         const char *long_name=NULL;
00290 
00291         while((ofmt= av_oformat_next(ofmt))) {
00292             if((name == NULL || strcmp(ofmt->name, name)<0) &&
00293                 strcmp(ofmt->name, last_name)>0){
00294                 name= ofmt->name;
00295                 long_name= ofmt->long_name;
00296                 encode=1;
00297             }
00298         }
00299         while((ifmt= av_iformat_next(ifmt))) {
00300             if((name == NULL || strcmp(ifmt->name, name)<0) &&
00301                 strcmp(ifmt->name, last_name)>0){
00302                 name= ifmt->name;
00303                 long_name= ifmt->long_name;
00304                 encode=0;
00305             }
00306             if(name && strcmp(ifmt->name, name)==0)
00307                 decode=1;
00308         }
00309         if(name==NULL)
00310             break;
00311         last_name= name;
00312 
00313         printf(
00314             " %s%s %-15s %s\n",
00315             decode ? "D":" ",
00316             encode ? "E":" ",
00317             name,
00318             long_name ? long_name:" ");
00319     }
00320     printf("\n");
00321 
00322     printf("Codecs:\n");
00323     last_name= "000";
00324     for(;;){
00325         int decode=0;
00326         int encode=0;
00327         int cap=0;
00328         const char *type_str;
00329 
00330         p2=NULL;
00331         while((p= av_codec_next(p))) {
00332             if((p2==NULL || strcmp(p->name, p2->name)<0) &&
00333                 strcmp(p->name, last_name)>0){
00334                 p2= p;
00335                 decode= encode= cap=0;
00336             }
00337             if(p2 && strcmp(p->name, p2->name)==0){
00338                 if(p->decode) decode=1;
00339                 if(p->encode) encode=1;
00340                 cap |= p->capabilities;
00341             }
00342         }
00343         if(p2==NULL)
00344             break;
00345         last_name= p2->name;
00346 
00347         switch(p2->type) {
00348         case CODEC_TYPE_VIDEO:
00349             type_str = "V";
00350             break;
00351         case CODEC_TYPE_AUDIO:
00352             type_str = "A";
00353             break;
00354         case CODEC_TYPE_SUBTITLE:
00355             type_str = "S";
00356             break;
00357         default:
00358             type_str = "?";
00359             break;
00360         }
00361         printf(
00362             " %s%s%s%s%s%s %-15s %s",
00363             decode ? "D": (/*p2->decoder ? "d":*/" "),
00364             encode ? "E":" ",
00365             type_str,
00366             cap & CODEC_CAP_DRAW_HORIZ_BAND ? "S":" ",
00367             cap & CODEC_CAP_DR1 ? "D":" ",
00368             cap & CODEC_CAP_TRUNCATED ? "T":" ",
00369             p2->name,
00370             p2->long_name ? p2->long_name : "");
00371        /* if(p2->decoder && decode==0)
00372             printf(" use %s for decoding", p2->decoder->name);*/
00373         printf("\n");
00374     }
00375     printf("\n");
00376 
00377     printf("Bitstream filters:\n");
00378     while((bsf = av_bitstream_filter_next(bsf)))
00379         printf(" %s", bsf->name);
00380     printf("\n");
00381 
00382     printf("Supported file protocols:\n");
00383     while((up = av_protocol_next(up)))
00384         printf(" %s:", up->name);
00385     printf("\n");
00386 
00387     printf("Frame size, frame rate abbreviations:\n ntsc pal qntsc qpal sntsc spal film ntsc-film sqcif qcif cif 4cif\n");
00388     printf("\n");
00389     printf(
00390 "Note, the names of encoders and decoders do not always match, so there are\n"
00391 "several cases where the above table shows encoder only or decoder only entries\n"
00392 "even though both encoding and decoding are supported. For example, the h263\n"
00393 "decoder corresponds to the h263 and h263p encoders, for file formats it is even\n"
00394 "worse.\n");
00395 }

Generated on Fri Jan 9 12:44:25 2009 for libextractor by  doxygen 1.5.1