Home | History | Annotate | Download | only in src
      1 
      2 /* -----------------------------------------------------------------------------------------------------------
      3 Software License for The Fraunhofer FDK AAC Codec Library for Android
      4 
      5  Copyright  1995 - 2012 Fraunhofer-Gesellschaft zur Frderung der angewandten Forschung e.V.
      6   All rights reserved.
      7 
      8  1.    INTRODUCTION
      9 The Fraunhofer FDK AAC Codec Library for Android ("FDK AAC Codec") is software that implements
     10 the MPEG Advanced Audio Coding ("AAC") encoding and decoding scheme for digital audio.
     11 This FDK AAC Codec software is intended to be used on a wide variety of Android devices.
     12 
     13 AAC's HE-AAC and HE-AAC v2 versions are regarded as today's most efficient general perceptual
     14 audio codecs. AAC-ELD is considered the best-performing full-bandwidth communications codec by
     15 independent studies and is widely deployed. AAC has been standardized by ISO and IEC as part
     16 of the MPEG specifications.
     17 
     18 Patent licenses for necessary patent claims for the FDK AAC Codec (including those of Fraunhofer)
     19 may be obtained through Via Licensing (www.vialicensing.com) or through the respective patent owners
     20 individually for the purpose of encoding or decoding bit streams in products that are compliant with
     21 the ISO/IEC MPEG audio standards. Please note that most manufacturers of Android devices already license
     22 these patent claims through Via Licensing or directly from the patent owners, and therefore FDK AAC Codec
     23 software may already be covered under those patent licenses when it is used for those licensed purposes only.
     24 
     25 Commercially-licensed AAC software libraries, including floating-point versions with enhanced sound quality,
     26 are also available from Fraunhofer. Users are encouraged to check the Fraunhofer website for additional
     27 applications information and documentation.
     28 
     29 2.    COPYRIGHT LICENSE
     30 
     31 Redistribution and use in source and binary forms, with or without modification, are permitted without
     32 payment of copyright license fees provided that you satisfy the following conditions:
     33 
     34 You must retain the complete text of this software license in redistributions of the FDK AAC Codec or
     35 your modifications thereto in source code form.
     36 
     37 You must retain the complete text of this software license in the documentation and/or other materials
     38 provided with redistributions of the FDK AAC Codec or your modifications thereto in binary form.
     39 You must make available free of charge copies of the complete source code of the FDK AAC Codec and your
     40 modifications thereto to recipients of copies in binary form.
     41 
     42 The name of Fraunhofer may not be used to endorse or promote products derived from this library without
     43 prior written permission.
     44 
     45 You may not charge copyright license fees for anyone to use, copy or distribute the FDK AAC Codec
     46 software or your modifications thereto.
     47 
     48 Your modified versions of the FDK AAC Codec must carry prominent notices stating that you changed the software
     49 and the date of any change. For modified versions of the FDK AAC Codec, the term
     50 "Fraunhofer FDK AAC Codec Library for Android" must be replaced by the term
     51 "Third-Party Modified Version of the Fraunhofer FDK AAC Codec Library for Android."
     52 
     53 3.    NO PATENT LICENSE
     54 
     55 NO EXPRESS OR IMPLIED LICENSES TO ANY PATENT CLAIMS, including without limitation the patents of Fraunhofer,
     56 ARE GRANTED BY THIS SOFTWARE LICENSE. Fraunhofer provides no warranty of patent non-infringement with
     57 respect to this software.
     58 
     59 You may use this FDK AAC Codec software or modifications thereto only for purposes that are authorized
     60 by appropriate patent licenses.
     61 
     62 4.    DISCLAIMER
     63 
     64 This FDK AAC Codec software is provided by Fraunhofer on behalf of the copyright holders and contributors
     65 "AS IS" and WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES, including but not limited to the implied warranties
     66 of merchantability and fitness for a particular purpose. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
     67 CONTRIBUTORS BE LIABLE for any direct, indirect, incidental, special, exemplary, or consequential damages,
     68 including but not limited to procurement of substitute goods or services; loss of use, data, or profits,
     69 or business interruption, however caused and on any theory of liability, whether in contract, strict
     70 liability, or tort (including negligence), arising in any way out of the use of this software, even if
     71 advised of the possibility of such damage.
     72 
     73 5.    CONTACT INFORMATION
     74 
     75 Fraunhofer Institute for Integrated Circuits IIS
     76 Attention: Audio and Multimedia Departments - FDK AAC LL
     77 Am Wolfsmantel 33
     78 91058 Erlangen, Germany
     79 
     80 www.iis.fraunhofer.de/amm
     81 amm-info (at) iis.fraunhofer.de
     82 ----------------------------------------------------------------------------------------------------------- */
     83 
     84 /**************************  Fraunhofer IIS FDK SysLib  **********************
     85 
     86    Author(s):
     87    Description: command line parser
     88 
     89 ******************************************************************************/
     90 
     91 
     92 
     93 #define _CRT_SECURE_NO_WARNINGS
     94 
     95 /* Work around for broken android toolchain: sys/types.h:137: error: 'uint64_t' does not name a type */
     96 #define _SYS_TYPES_H_
     97 
     98 #include <stdarg.h>
     99 #include <stdio.h>
    100 #include <string.h>
    101 #include <stdlib.h>
    102 #include <ctype.h>
    103 
    104 #include "cmdl_parser.h"
    105 #include "genericStds.h"
    106 
    107 
    108 
    109 /************************ interface ************************/
    110 
    111 static INT  GetArgFromString(INT argc, TEXTCHAR* argv[], TEXTCHAR* search_string, TEXTCHAR type, TEXTCHAR* found_string , INT* switches_used);
    112 static void RemoveWhiteSpace(const TEXTCHAR* pReqArgs, TEXTCHAR* Removed);
    113 static INT CheckArg(TEXTCHAR* arg,  TEXTCHAR* str, UINT numArgs, TEXTCHAR type, TEXTCHAR* current_str);
    114 static INT CheckForUnusedSwitches(INT argc, /*TEXTCHAR* argv[],*/ INT* switches_used);
    115 static INT ParseString(TEXTCHAR* str, INT*, TEXTCHAR*, TEXTCHAR*);
    116 static void GetNumberOfArgs(TEXTCHAR* str, INT* nArgs);
    117 
    118 static
    119 void removeQuotes(char *str)
    120 {
    121   if (str[0] == '"') {
    122     FDKstrcpy(str, str+1);
    123     str[FDKstrlen(str)-1] = 0;
    124   }
    125 }
    126 
    127 
    128 /********************** implementation *********************/
    129 
    130 INT IIS_ScanCmdl(INT argc, TEXTCHAR* argv[], const TEXTCHAR* str, ...)
    131 {
    132   INT i              = 0;
    133   INT found_and_set  = 0;
    134   INT nArgs          = 0;
    135   INT* switches_used = 0;
    136   INT*   b_str_opt   = 0;
    137   TEXTCHAR*  s_str       = 0;
    138   TEXTCHAR*  c_str_type  = 0;
    139   TEXTCHAR*  str_clean   = 0;
    140 
    141   va_list ap;
    142 
    143   if (argc == 0 || argc == 1)
    144   {
    145     FDKprintf("No command line arguments\n");
    146     goto bail;
    147   }
    148 
    149   str_clean  = (TEXTCHAR*)  FDKcalloc((unsigned int)_tcslen(str), sizeof(TEXTCHAR));
    150   if (str_clean == NULL) {
    151     FDKprintf("Error allocating memory line %d, file %s\n",  __LINE__, __FILE__);
    152     return 0;
    153   }
    154 
    155   RemoveWhiteSpace(str, str_clean );
    156   GetNumberOfArgs(str_clean, &nArgs);
    157 
    158   b_str_opt  = (INT*)   FDKcalloc(nArgs,    sizeof(INT));
    159   s_str      = (TEXTCHAR*)  FDKcalloc(nArgs*CMDL_MAX_ARGC, sizeof(TEXTCHAR) );
    160   c_str_type = (TEXTCHAR*)  FDKcalloc(nArgs,    sizeof(TEXTCHAR));
    161   switches_used = (INT*) FDKcalloc(argc, sizeof(INT));
    162 
    163   if (b_str_opt == NULL || s_str == NULL || c_str_type == NULL || switches_used == NULL) {
    164     FDKprintf("Error allocating memory line %d, file %s\n",  __LINE__, __FILE__);
    165     goto bail;
    166   }
    167 
    168   if ( ParseString( str_clean, b_str_opt, s_str, c_str_type )) {
    169     goto bail;
    170   }
    171 
    172   va_start(ap, str);
    173 
    174   for ( i = 0; i < nArgs; i++ )
    175     {
    176       TEXTCHAR arg[CMDL_MAX_STRLEN] = {L'\0'};
    177       TEXTCHAR* p_arg = arg;
    178       TEXTCHAR* current_str = &(s_str[i*CMDL_MAX_ARGC]);
    179 
    180       if (GetArgFromString(argc, argv, current_str, c_str_type[i], arg, switches_used )
    181           && !b_str_opt[i] )
    182         {
    183 #ifdef _UNICODE
    184           _ftprintf(stderr, _TEXT("\n\nError: Parsing argument for required switch '%ls'.\n" ), current_str);
    185 #else
    186           _ftprintf(stderr, _TEXT("\n\nError: Parsing argument for required switch '%s'.\n" ), current_str);
    187 #endif
    188           found_and_set = 0;
    189           goto bail;
    190         }
    191       if (CheckArg(p_arg, s_str, nArgs, c_str_type[i], current_str))
    192         {
    193           goto bail;
    194         }
    195 
    196       switch (c_str_type[i] )
    197         {
    198         case 's':
    199           {
    200             TEXTCHAR* tmp;
    201             tmp = va_arg(ap, TEXTCHAR*);
    202 
    203             if ( arg[0] == '\0' )
    204               break;
    205 
    206             _tcsncpy( tmp, arg, CMDL_MAX_STRLEN );
    207             /* Remove quotes. Windows Mobile Workaround. */
    208             removeQuotes(tmp);
    209             found_and_set++;
    210             break;
    211           }
    212         case 'd':
    213           {
    214             INT* tmp = va_arg(ap, INT*);
    215 
    216             if ( arg[0] == '\0' )
    217               break;
    218 
    219             *tmp = _tcstol(arg, NULL, 0);
    220             found_and_set++;
    221             break;
    222           }
    223         case 'c':
    224           {
    225             char* tmp = va_arg(ap, char*);
    226 
    227             if ( arg[0] == '\0' )
    228               break;
    229 
    230             *tmp = *arg;
    231             found_and_set++;
    232             break;
    233           }
    234         case 'u':
    235           {
    236             UCHAR* tmp = va_arg(ap, UCHAR*);
    237 
    238             if ( arg[0] == '\0' )
    239               break;
    240 
    241             *tmp = _tstoi(arg);
    242             found_and_set++;
    243             break;
    244           }
    245         case 'f':
    246           {
    247             float* tmp = (float*) va_arg( ap,double*);
    248 
    249             if ( arg[0] == '\0' )
    250               break;
    251 
    252             *tmp = (float) _tstof(arg);
    253             found_and_set++;
    254             break;
    255           }
    256         case 'y': // support 'data type double'
    257           {
    258             double* tmp = (double*) va_arg( ap,double*);
    259             // use sscanf instead _tstof because of gcc
    260             //_tstof(arg,"%lf",tmp); // '%lf' reads as double
    261             *tmp = _tstof(arg); // '%lf' reads as double
    262             found_and_set++;
    263             break;
    264           }
    265         case '1':
    266           {
    267 
    268             INT* tmp = va_arg( ap, INT*);
    269 
    270             if ( arg[0] == '\0' )
    271               break;
    272 
    273             *tmp = 1;
    274             found_and_set++;
    275             break;
    276           }
    277 
    278         default:
    279           FDKprintfErr("Bug: unsupported data identifier \"%c\"\n", c_str_type[i]);
    280           break;
    281 
    282         }
    283 
    284     }
    285 
    286   va_end(ap);
    287 
    288   CheckForUnusedSwitches(argc, /*argv,*/ switches_used);
    289 
    290 bail:
    291   if (b_str_opt)     FDKfree(b_str_opt);
    292   if (s_str)         FDKfree(s_str);
    293   if (c_str_type)    FDKfree(c_str_type);
    294   if (str_clean)     FDKfree(str_clean);
    295   if (switches_used) FDKfree(switches_used);
    296 
    297   return found_and_set;
    298 }
    299 
    300 
    301 void GetNumberOfArgs(TEXTCHAR* str, INT* nArgs)
    302 {
    303   UINT i = 0;
    304   for ( i = 0; i < _tcslen(str); ++i )
    305     {
    306       if ( str[i] == '%')
    307         *nArgs+= 1;
    308     }
    309 
    310 }
    311 
    312 INT ParseString(TEXTCHAR* str, INT* b_str_opt, TEXTCHAR* s_str, TEXTCHAR* c_str_type )
    313 {
    314     UINT i = 0;
    315     INT argCounter = 0;
    316 
    317     TEXTCHAR* str_start = 0;
    318     TEXTCHAR* str_stop = 0;
    319 
    320 
    321     str_start = str;
    322     str_stop = str_start;
    323 
    324     for ( i = 0; i < _tcslen(str) - 1; ++i )
    325       {
    326         if ( str[i] == '%' )  /* We have an Argument */
    327           {
    328             if ( argCounter )
    329               {
    330                 if ( b_str_opt[argCounter-1] )
    331                   str_start = str_stop + 3;
    332 
    333                 else
    334                   str_start = str_stop + 2;
    335               }
    336 
    337             /* Save Argument type */
    338             c_str_type[argCounter] = str[i+1];
    339 
    340             if ( *str_start == '(' ) /* Optional Argument */
    341               {
    342                 b_str_opt[argCounter] = 1;
    343                 str_start++;
    344               }
    345 
    346             /* Save Argument */
    347             str[i] = '\0';
    348 
    349             _tcsncpy(&(s_str[argCounter*CMDL_MAX_ARGC]), str_start, CMDL_MAX_ARGC );
    350 
    351             str[i] = '%';
    352 
    353             str_stop = &(str[i]);
    354 
    355             if ( b_str_opt[argCounter] )
    356               {
    357                 if ( i+2 > ( _tcslen(str) -1 ))
    358                   {
    359                     _ftprintf(stderr,_TEXT("\n\nInternal Parser Error: Strlen Problem\n") );
    360                     return 1;
    361                   }
    362                 if ( str[i+2] != ')' )
    363                   {
    364                     _ftprintf(stderr,_TEXT("\n\nInternal Parser Error: Missing bracket ')'\n") );
    365                     return 1;
    366                   }
    367 
    368               }
    369 
    370 
    371             argCounter++;
    372           }
    373 
    374 
    375       }
    376 
    377     return 0;
    378   }
    379 
    380 
    381 
    382 
    383 void RemoveWhiteSpace(const TEXTCHAR* pReqArgs, TEXTCHAR* pRemoved)
    384 {
    385   UINT i = 0;
    386   INT k = 0;
    387   UINT len = (UINT)_tcslen(pReqArgs);
    388 
    389 
    390   for ( i = 0; i < len; ++i )
    391     {
    392 
    393       if ( pReqArgs[i] != ' ' )
    394         {
    395           pRemoved[k] = pReqArgs[i];
    396           k++;
    397         }
    398     }
    399 }
    400 
    401 
    402 INT GetArgFromString(INT argc, TEXTCHAR* argv[], TEXTCHAR* search_string, TEXTCHAR type, TEXTCHAR* found_string, INT* sw_used )
    403 {
    404   INT i = 0;
    405 
    406   for (i = 1; i < argc; ++i ) {
    407     if ( !_tcscmp(search_string, argv[i]) ) /* Strings are equal */
    408       {
    409         if ( type == '1' ) /* Switch without argument */
    410         {
    411           _tcsncpy( found_string, _TEXT("1"), 1);
    412           sw_used[i] = 1;
    413           return 0;
    414 
    415         }
    416 
    417         if ( i == (argc - 1))  /* We have %s or %d but are finished*/
    418           return 1;
    419 
    420         if ( _tcslen(argv[i+1]) > CMDL_MAX_STRLEN )
    421           {
    422 #ifdef _UNICODE
    423             _ftprintf (stderr,_TEXT("Warning: Ignoring argument for switch '%ls'. "), search_string );
    424 #else
    425             _ftprintf (stderr,_TEXT("Warning: Ignoring argument for switch '%s'. "), search_string );
    426 #endif
    427             _ftprintf (stderr,_TEXT("Argument is too LONG.\n") );
    428             return 1;
    429           }
    430         else
    431         {
    432           _tcsncpy( found_string, argv[i+1], CMDL_MAX_STRLEN);
    433           sw_used[i] = 1;
    434           sw_used[i+1] = 1;
    435           return 0;
    436         }
    437       }
    438   }
    439   return 1;
    440 }
    441 
    442 
    443 
    444 INT CheckArg(TEXTCHAR* arg, TEXTCHAR* str, UINT numArgs, TEXTCHAR type, TEXTCHAR* cur_str)
    445 {
    446   UINT i = 0;
    447 
    448   /* No argument given-> return */
    449   if (arg[0] == '\0')
    450     return 0;
    451 
    452 
    453   /* Check if arg is switch */
    454   for ( i = 0; i < numArgs; ++i )
    455     {
    456       if (!_tcscmp(arg, &(str[i*CMDL_MAX_ARGC])))
    457         {
    458 #ifdef _UNICODE
    459           _ftprintf(stderr, _TEXT("\n\nError: Argument '%ls' for switch '%ls' is not valid \n" ), arg, cur_str );
    460 #else
    461           _ftprintf(stderr, _TEXT("\n\nError: Argument '%s' for switch '%s' is not valid \n" ), arg, cur_str );
    462 #endif
    463           return 1;
    464         }
    465 
    466     }
    467   /* Check if type is %d but a string is given */
    468 
    469   for ( i = 0; i < _tcslen(arg); ++i )
    470     {
    471       if ( (type == 'd') && !_istdigit(arg[i]) && arg[i] != 'x' )
    472         {
    473 #ifdef _UNICODE
    474           _ftprintf(stderr, _TEXT("\n\nError: Argument '%ls' for switch '%ls' is not a valid number.\n" ), arg, cur_str);
    475 #else
    476           _ftprintf(stderr, _TEXT("\n\nError: Argument '%s' for switch '%s' is not a valid number.\n" ), arg, cur_str);
    477 #endif
    478           return 1;
    479         }
    480     }
    481 
    482 
    483   return 0;
    484 }
    485 
    486 
    487 INT CheckForUnusedSwitches(INT argc, /*TEXTCHAR* argv[],*/ INT* switches_used)
    488 {
    489   INT i = 0;
    490 
    491   for( i = 1; i < argc; ++i )
    492     {
    493       if ( !switches_used[i] )
    494         {
    495           ++i;
    496         }
    497     }
    498 
    499   return 0;
    500 }
    501 
    502 
    503 
    504 static char line[CMDL_MAX_STRLEN*CMDL_MAX_ARGC];
    505 static char *argv_ptr[CMDL_MAX_ARGC];
    506 #ifdef CMDFILE_PREFIX
    507 static char tmp[256]; /* this array is used to store the prefix and the filepath/name */
    508 #endif
    509 
    510 int IIS_ProcessCmdlList(const char* param_filename, int (*pFunction)(int, TEXTCHAR**))
    511 {
    512   /* static to reduce required stack size */
    513 
    514   FDKFILE *config_fp;
    515   int argc;
    516   char *line_ptr;
    517 
    518 #ifdef CMDFILE_PREFIX
    519   FDKstrcpy(tmp, CMDFILE_PREFIX);
    520   FDKstrcpy(tmp+FDKstrlen(CMDFILE_PREFIX), param_filename);
    521   /* Open the file with command lines */
    522   config_fp = FDKfopen(tmp, "r");
    523 #else
    524   /* Open the file with command lines */
    525   config_fp = FDKfopen(param_filename, "r");
    526 #endif
    527 
    528   if(config_fp == NULL)
    529   {
    530 #ifdef CMDFILE_PREFIX
    531     FDKprintf("\ncould not open config file %s", tmp);
    532 #else
    533     FDKprintf("\ncould not open config file %s", param_filename);
    534 #endif
    535     return 1;
    536   }
    537 
    538   /* Obtain a command line from config file */
    539   while (FDKfgets(line, CMDL_MAX_STRLEN*CMDL_MAX_ARGC, config_fp) != NULL)
    540   {
    541     argc = 1;
    542 
    543     /* Eat \n */
    544     line_ptr =  (char*)FDKstrchr(line, '\n');
    545     if (line_ptr != NULL)
    546       *line_ptr = ' ';
    547 
    548     line_ptr = line;
    549 
    550     /* Scan the line and put the command line params into argv */
    551     do {
    552       /* Skip consecutive blanks. */
    553       while (*line_ptr == ' ' && line_ptr < line+CMDL_MAX_STRLEN)
    554         line_ptr++;
    555       /* Assign argument. TODO: maybe handle quotes */
    556       argv_ptr[argc] = line_ptr;
    557       /* Get pointer to next blank. */
    558       line_ptr = (char*)FDKstrchr(line_ptr, ' ');
    559       /*  */
    560       if (line_ptr != NULL) {
    561         /* Null terminate */
    562         *line_ptr = 0;
    563         /* Skip former blank (now null character) */
    564         line_ptr++;
    565         /* Advance argument counter */
    566       }
    567       argc++;
    568     } while ( line_ptr != NULL && argc < CMDL_MAX_ARGC);
    569 
    570     /* call "would be main()" */
    571     if (argc > 2 && *argv_ptr[1] != '#' && FDKstrlen(argv_ptr[1])>1)
    572     {
    573       int retval;
    574 
    575       retval = (*pFunction)(argc, argv_ptr);
    576 
    577       FDKprintf("main returned %d\n", retval);
    578     }
    579   }
    580 
    581   FDKfclose(config_fp);
    582   return 0;
    583 }
    584 
    585