Main Page   Namespace List   Class Hierarchy   Alphabetical List   Compound List   File List   Compound Members   File Members  

options.cpp

Go to the documentation of this file.
00001 /*
00002 PeRdr - PE file disassembler
00003 Copyright (C) 1999-2002 Frediano Ziglio
00004 -----
00005 
00006 This program is free software; you can redistribute it and/or modify
00007 it under the terms of the GNU General Public License as published by
00008 the Free Software Foundation; either version 2 of the License, or
00009 (at your option) any later version.
00010 
00011 This program is distributed in the hope that it will be useful,
00012 but WITHOUT ANY WARRANTY; without even the implied warranty of
00013 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00014 GNU General Public License for more details.
00015 
00016 You should have received a copy of the GNU General Public License
00017 along with this program; if not, write to the Free Software
00018 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
00019 -----
00020 
00021 INFORMATION
00022   www: https://freddy77.tripod.com/perdr/
00023   e-mail: freddy77@angelfire.com
00024 */
00025 /*
00026 opzioni:
00027 corta: un carattere
00028  tipi: booleano (senza parametro), con parametro, se con parametro deve essere l'ultimo
00029 lunga: piu' caratteri, puo' essere la stessa di un carattere solo
00030 
00031 opzione carattere/i singoli \0 stringhe (opzioni lunghe) \0
00032 tipo (booleano, stringa)
00033 puntatore a dato
00034 */
00035 #include <cstdlib>
00036 #include <cctype>
00037 #include <cstring>
00038 #include "utils/bitcompat.h"
00039 #include "options.h"
00040 
00041 // ritorna indica parametro se risultato ok
00042 // ritorna -indice se parametro sconosciuto
00043 int get_options(int argc, char** argv,option* opttable)
00044 {
00045   option *opt;
00046   char *p, *next_char;
00047   // prima non opzione e inizio indice opzioni
00048   int optind, optno, optfirstind;
00049   optno = optind = 1;
00050   for ( ; optind<argc; )
00051   {
00052     // se non e' un'opzione ritorna
00053     while( argv[optind][0] != '-' )
00054       if ( ++optind == argc )
00055         return optno;
00056 
00057     optfirstind = optind;
00058 
00059     if ( argv[optind][1] == '-' )
00060     {
00061       // caso '--' ritorna indica successivo elemento
00062       if (argv[optind][2] == '\0' )
00063         return optind+1;
00064       for(opt = opttable; ; ++opt)
00065       {
00066         if ( opt->names == NULL )
00067             return -optind;
00068         p = opt->names;
00069 
00070         // caso parametri lunghi
00071         for( ;*(p=p+strlen(p)+1); )
00072         {
00073           int l = strlen(p);
00074           if ( strncmp(p,argv[optind]+2,l) == 0 )
00075           {
00076             next_char = &argv[optind][2+l];
00077             if ( opt->type != optionBool && *next_char == '=' )
00078             {
00079               // --arg=value
00080               p = next_char+1;
00081               goto param_value;
00082             }
00083             // prova con un'altra opzione
00084             if (*next_char != '\0')
00085               break;
00086             if ( opt->type == optionBool)
00087               goto param_value;
00088             // --arg value
00089             goto param_found;
00090           }
00091         }
00092       }
00093       // non raggiunge mai questo punto
00094     }
00095     else
00096     {
00097       for(p = argv[optind]+1; *p != '\0' ;++p)
00098       {
00099         for( opt = opttable; ; ++opt)
00100         {
00101           if ( opt->names == NULL )
00102             return -optind;
00103 
00104           // caso parametri a caratteri singoli
00105           if ( strchr(opt->names,*p) != NULL )
00106           {
00107             if ( opt->type != optionBool )
00108             {
00109               // -a value
00110               next_char = p+1;
00111               goto param_found;
00112             }
00113             *(bool*)(opt->val) = true;
00114             break;
00115           }
00116         }
00117       }
00118       goto option_found;
00119     }
00120 
00121 param_found:
00122     // il valore dell'opzione e' il successivo parametro
00123     if (*next_char != '\0' || ++optind == argc)
00124       return -optind;
00125     p = argv[optind];
00126 param_value:
00127     // scrivi dati in output
00128     switch(opt->type)
00129     {
00130       case optionBool:
00131         *(bool*)(opt->val) = true;
00132         break;
00133       case optionString:
00134         *(const char**)(opt->val) = p;
00135         break;
00136       case optionLong:
00137         {
00138         char *pend;
00139         if ( !isdigit(*p) )
00140           return -optind;
00141         *(long*)(opt->val) = strtol(p,&pend,0);
00142         if ( *pend != '\0' )
00143           return -optind;
00144         }
00145       break;
00146     }
00147 
00148 option_found:
00149     ++optind;
00150     // sposta in fondo gli argomenti non flag
00151     if (optfirstind != optno)
00152     {
00153       // shifta num volte opzioni all'inizio
00154       for (;optind != optfirstind;)
00155       {
00156         int n = optfirstind;
00157         char *temp = argv[n];
00158         for(;--n >= optno;)
00159           argv[n+1] = argv[n];
00160         argv[optno] = temp;
00161         ++optno;
00162         ++optfirstind;
00163       }
00164     }
00165     else
00166       optno = optind;
00167 
00168   }
00169   return optno;
00170 }

Generated on Mon Jan 13 22:20:34 2003 for perdr by doxygen1.2.15