Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • libcfa/src/parseargs.cfa

    r54f70c6 ra4e1b09  
    7373//-----------------------------------------------------------------------------
    7474// Parsing args
    75 forall([opt_count])
    76 void parse_args( const array( cfa_option, opt_count ) & options, const char * usage, char ** & left ) {
    77         if ( 0p != &cfa_args_argc ) {
    78                 parse_args( cfa_args_argc, cfa_args_argv, options, usage, left );
    79         } else {
    80                 char * temp[1] = { 0p };
    81                 parse_args(0, temp, options, usage, left );
    82         }
    83 }
    84 
    85 forall([opt_count])
    86 void parse_args(
    87         int argc,
    88         char * argv[],
    89         const array( cfa_option, opt_count ) & options,
    90         const char * usage,
    91         char ** & left
    92 ) {
    93         check_args( options );
    94 
    95         int maxv = 'h';
    96         char optstring[(opt_count * 3) + 2] = { '\0' };
    97         {
    98                 int idx = 0;
    99                 for ( i; opt_count ) {
    100                         if ( options[i].short_name ) {
    101                                 maxv = max( options[i].short_name, maxv );
    102                                 optstring[idx] = options[i].short_name;
    103                                 idx++;
    104                                 if ( (intptr_t)options[i].parse != (intptr_t)parse_settrue
    105                                          && ((intptr_t)options[i].parse) != ((intptr_t)parse_setfalse) ) {
    106                                         optstring[idx] = ':';
     75forall([opt_count]) {
     76        void parse_args( const array( cfa_option, opt_count ) & options, const char * usage, char ** & left ) {
     77                if ( 0p != &cfa_args_argc ) {
     78                        parse_args( cfa_args_argc, cfa_args_argv, options, usage, left );
     79                } else {
     80                        char * temp[1] = { 0p };
     81                        parse_args(0, temp, options, usage, left );
     82                }
     83        }
     84
     85        void parse_args(
     86                int argc,
     87                char * argv[],
     88                const array( cfa_option, opt_count ) & options,
     89                const char * usage,
     90                char ** & left
     91        ) {
     92                check_args( options );
     93
     94                int maxv = 'h';
     95                char optstring[(opt_count * 3) + 2] = { '\0' };
     96                {
     97                        int idx = 0;
     98                        for ( i; opt_count ) {
     99                                if ( options[i].short_name ) {
     100                                        maxv = max( options[i].short_name, maxv );
     101                                        optstring[idx] = options[i].short_name;
     102                                        idx++;
     103                                        if ( (intptr_t)options[i].parse != (intptr_t)parse_settrue
     104                                                 && ((intptr_t)options[i].parse) != ((intptr_t)parse_setfalse) ) {
     105                                                optstring[idx] = ':';
     106                                                idx++;
     107                                        }
     108                                }
     109                        }
     110                        optstring[idx+0] = 'h';
     111                        optstring[idx+1] = '\0';
     112                }
     113
     114                struct option optarr[opt_count + 2];
     115                {
     116                        int idx = 0;
     117                        for ( i; opt_count ) {
     118                                if ( options[i].long_name ) {
     119                                        // we don't have the mutable keyword here, which is really what we would want
     120                                        int & val_ref = (int &)(const int &)options[i].val;
     121                                        val_ref = (options[i].short_name != '\0') ? ((int)options[i].short_name) : ++maxv;
     122
     123                                        optarr[idx].name = options[i].long_name;
     124                                        optarr[idx].flag = 0p;
     125                                        optarr[idx].val  = options[i].val;
     126                                        if ( ((intptr_t)options[i].parse) == ((intptr_t)parse_settrue)
     127                                                 || ((intptr_t)options[i].parse) == ((intptr_t)parse_setfalse) ) {
     128                                                optarr[idx].has_arg = no_argument;
     129                                        } else {
     130                                                optarr[idx].has_arg = required_argument;
     131                                        }
    107132                                        idx++;
    108133                                }
    109134                        }
    110                 }
    111                 optstring[idx+0] = 'h';
    112                 optstring[idx+1] = '\0';
    113         }
    114 
    115         struct option optarr[opt_count + 2];
    116         {
    117                 int idx = 0;
    118                 for ( i; opt_count ) {
    119                         if ( options[i].long_name ) {
    120                                 // we don't have the mutable keyword here, which is really what we would want
    121                                 int & val_ref = (int &)(const int &)options[i].val;
    122                                 val_ref = (options[i].short_name != '\0') ? ((int)options[i].short_name) : ++maxv;
    123 
    124                                 optarr[idx].name = options[i].long_name;
    125                                 optarr[idx].flag = 0p;
    126                                 optarr[idx].val  = options[i].val;
    127                                 if ( ((intptr_t)options[i].parse) == ((intptr_t)parse_settrue)
    128                                          || ((intptr_t)options[i].parse) == ((intptr_t)parse_setfalse) ) {
    129                                         optarr[idx].has_arg = no_argument;
    130                                 } else {
    131                                         optarr[idx].has_arg = required_argument;
    132                                 }
    133                                 idx++;
     135                        optarr[idx+0].[name, has_arg, flag, val] = ["help", no_argument, 0, 'h'];
     136                        optarr[idx+1].[name, has_arg, flag, val] = [0, no_argument, 0, 0];
     137                }
     138
     139                FILE * out = stderr;
     140                NEXT_ARG:
     141                for () {
     142                        int idx = 0;
     143                        int opt = getopt_long( argc, argv, optstring, optarr, &idx );
     144                        switch( opt ) {
     145                                case -1:
     146                                        if ( &left != 0p ) left = argv + optind;
     147                                        return;
     148                                case 'h':
     149                                        out = stdout;
     150                                case '?':
     151                                        usage( argv[0], options, usage, out );
     152                                default:
     153                                        for ( i; opt_count ) {
     154                                                if ( opt == options[i].val ) {
     155                                                        const char * arg = optarg ? optarg : "";
     156                                                        if ( arg[0] == '=' ) { arg++; }
     157                                                        // work around for some weird bug
     158                                                        void * variable = options[i].variable;
     159                                                        bool (*parse_func)(const char *, void * ) = options[i].parse;
     160                                                        bool success = parse_func( arg, variable );
     161                                                        if ( success ) continue NEXT_ARG;
     162
     163                                                        fprintf( out, "Argument '%s' for option %c could not be parsed\n\n", arg, (char)opt );
     164                                                        usage( argv[0], options, usage, out );
     165                                                }
     166                                        }
     167                                        abort( "Internal parse arg error\n" );
    134168                        }
    135                 }
    136                 optarr[idx+0].[name, has_arg, flag, val] = ["help", no_argument, 0, 'h'];
    137                 optarr[idx+1].[name, has_arg, flag, val] = [0, no_argument, 0, 0];
    138         }
    139 
    140         FILE * out = stderr;
    141         NEXT_ARG:
    142         for () {
    143                 int idx = 0;
    144                 int opt = getopt_long( argc, argv, optstring, optarr, &idx );
    145                 switch( opt ) {
    146                 case -1:
    147                         if ( &left != 0p ) left = argv + optind;
    148                         return;
    149                 case 'h':
    150                         out = stdout;
    151                 case '?':
    152                         usage( argv[0], options, usage, out );
    153                 default:
    154                         for ( i; opt_count ) {
    155                                 if ( opt == options[i].val ) {
    156                                         const char * arg = optarg ? optarg : "";
    157                                         if ( arg[0] == '=' ) { arg++; }
    158                                         // work around for some weird bug
    159                                         void * variable = options[i].variable;
    160                                         bool (*parse_func)(const char *, void * ) = options[i].parse;
    161                                         bool success = parse_func( arg, variable );
    162                                         if ( success ) continue NEXT_ARG;
    163 
    164                                         fprintf( out, "Argument '%s' for option %c could not be parsed\n\n", arg, (char)opt );
    165                                         usage( argv[0], options, usage, out );
    166                                 }
    167                         }
    168                         abort( "Internal parse arg error\n" );
     169
    169170                }
    170171        }
     
    239240}
    240241
    241 forall([N])
    242 void print_args_usage( const array(cfa_option, N ) & options, const char * usage, bool error ) {
    243         usage( cfa_args_argv[0], options, usage, error ? stderr : stdout );
    244 }
    245 
    246 forall([N])
    247 void print_args_usage( int argc, char * argv[], const array( cfa_option, N ) & options, const char * usage, bool error ) {
    248         usage( argv[0], options, usage, error ? stderr : stdout );
     242forall( [N] ) {
     243        void print_args_usage( const array(cfa_option, N ) & options, const char * usage, bool error ) {
     244                usage( cfa_args_argv[0], options, usage, error ? stderr : stdout );
     245        }
     246
     247        void print_args_usage( int argc, char * argv[], const array( cfa_option, N ) & options, const char * usage, bool error ) {
     248                usage( argv[0], options, usage, error ? stderr : stdout );
     249        }
    249250}
    250251
Note: See TracChangeset for help on using the changeset viewer.