OpenCores
URL https://opencores.org/ocsvn/or1k/or1k/trunk

Subversion Repositories or1k

[/] [or1k/] [trunk/] [insight/] [libiberty/] [getopt.c] - Blame information for rev 1765

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 578 markom
/* Getopt for GNU.
2
   NOTE: getopt is now part of the C library, so if you don't know what
3
   "Keep this file name-space clean" means, talk to drepper@gnu.org
4
   before changing it!
5
 
6
   Copyright (C) 1987, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98
7
        Free Software Foundation, Inc.
8
 
9
   NOTE: This source is derived from an old version taken from the GNU C
10
   Library (glibc).
11
 
12
   This program is free software; you can redistribute it and/or modify it
13
   under the terms of the GNU General Public License as published by the
14
   Free Software Foundation; either version 2, or (at your option) any
15
   later version.
16
 
17
   This program is distributed in the hope that it will be useful,
18
   but WITHOUT ANY WARRANTY; without even the implied warranty of
19
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
20
   GNU General Public License for more details.
21
 
22
   You should have received a copy of the GNU General Public License
23
   along with this program; if not, write to the Free Software
24
   Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
25
   USA.  */
26
 
27
/* This tells Alpha OSF/1 not to define a getopt prototype in <stdio.h>.
28
   Ditto for AIX 3.2 and <stdlib.h>.  */
29
#ifndef _NO_PROTO
30
# define _NO_PROTO
31
#endif
32
 
33
#ifdef HAVE_CONFIG_H
34
# include <config.h>
35
#endif
36
 
37
#if !defined __STDC__ || !__STDC__
38
/* This is a separate conditional since some stdc systems
39
   reject `defined (const)'.  */
40
# ifndef const
41
#  define const
42
# endif
43
#endif
44
 
45
#include <stdio.h>
46
 
47
/* Comment out all this code if we are using the GNU C Library, and are not
48
   actually compiling the library itself.  This code is part of the GNU C
49
   Library, but also included in many other GNU distributions.  Compiling
50
   and linking in this code is a waste when using the GNU C library
51
   (especially if it is a shared library).  Rather than having every GNU
52
   program understand `configure --with-gnu-libc' and omit the object files,
53
   it is simpler to just do this in the source for each such file.  */
54
 
55
#define GETOPT_INTERFACE_VERSION 2
56
#if !defined _LIBC && defined __GLIBC__ && __GLIBC__ >= 2
57
# include <gnu-versions.h>
58
# if _GNU_GETOPT_INTERFACE_VERSION == GETOPT_INTERFACE_VERSION
59
#  define ELIDE_CODE
60
# endif
61
#endif
62
 
63
#ifndef ELIDE_CODE
64
 
65
 
66
/* This needs to come after some library #include
67
   to get __GNU_LIBRARY__ defined.  */
68
#ifdef  __GNU_LIBRARY__
69
/* Don't include stdlib.h for non-GNU C libraries because some of them
70
   contain conflicting prototypes for getopt.  */
71
# include <stdlib.h>
72
# include <unistd.h>
73
#endif  /* GNU C library.  */
74
 
75
#ifdef VMS
76
# include <unixlib.h>
77
# if HAVE_STRING_H - 0
78
#  include <string.h>
79
# endif
80
#endif
81
 
82
#ifndef _
83
/* This is for other GNU distributions with internationalized messages.
84
   When compiling libc, the _ macro is predefined.  */
85
# ifdef HAVE_LIBINTL_H
86
#  include <libintl.h>
87
#  define _(msgid)      gettext (msgid)
88
# else
89
#  define _(msgid)      (msgid)
90
# endif
91
#endif
92
 
93
/* This version of `getopt' appears to the caller like standard Unix `getopt'
94
   but it behaves differently for the user, since it allows the user
95
   to intersperse the options with the other arguments.
96
 
97
   As `getopt' works, it permutes the elements of ARGV so that,
98
   when it is done, all the options precede everything else.  Thus
99
   all application programs are extended to handle flexible argument order.
100
 
101
   Setting the environment variable POSIXLY_CORRECT disables permutation.
102
   Then the behavior is completely standard.
103
 
104
   GNU application programs can use a third alternative mode in which
105
   they can distinguish the relative order of options and other arguments.  */
106
 
107
#include "getopt.h"
108
 
109
/* For communication from `getopt' to the caller.
110
   When `getopt' finds an option that takes an argument,
111
   the argument value is returned here.
112
   Also, when `ordering' is RETURN_IN_ORDER,
113
   each non-option ARGV-element is returned here.  */
114
 
115
char *optarg = NULL;
116
 
117
/* Index in ARGV of the next element to be scanned.
118
   This is used for communication to and from the caller
119
   and for communication between successive calls to `getopt'.
120
 
121
   On entry to `getopt', zero means this is the first call; initialize.
122
 
123
   When `getopt' returns -1, this is the index of the first of the
124
   non-option elements that the caller should itself scan.
125
 
126
   Otherwise, `optind' communicates from one call to the next
127
   how much of ARGV has been scanned so far.  */
128
 
129
/* 1003.2 says this must be 1 before any call.  */
130
int optind = 1;
131
 
132
/* Formerly, initialization of getopt depended on optind==0, which
133
   causes problems with re-calling getopt as programs generally don't
134
   know that. */
135
 
136
int __getopt_initialized = 0;
137
 
138
/* The next char to be scanned in the option-element
139
   in which the last option character we returned was found.
140
   This allows us to pick up the scan where we left off.
141
 
142
   If this is zero, or a null string, it means resume the scan
143
   by advancing to the next ARGV-element.  */
144
 
145
static char *nextchar;
146
 
147
/* Callers store zero here to inhibit the error message
148
   for unrecognized options.  */
149
 
150
int opterr = 1;
151
 
152
/* Set to an option character which was unrecognized.
153
   This must be initialized on some systems to avoid linking in the
154
   system's own getopt implementation.  */
155
 
156
int optopt = '?';
157
 
158
/* Describe how to deal with options that follow non-option ARGV-elements.
159
 
160
   If the caller did not specify anything,
161
   the default is REQUIRE_ORDER if the environment variable
162
   POSIXLY_CORRECT is defined, PERMUTE otherwise.
163
 
164
   REQUIRE_ORDER means don't recognize them as options;
165
   stop option processing when the first non-option is seen.
166
   This is what Unix does.
167
   This mode of operation is selected by either setting the environment
168
   variable POSIXLY_CORRECT, or using `+' as the first character
169
   of the list of option characters.
170
 
171
   PERMUTE is the default.  We permute the contents of ARGV as we scan,
172
   so that eventually all the non-options are at the end.  This allows options
173
   to be given in any order, even with programs that were not written to
174
   expect this.
175
 
176
   RETURN_IN_ORDER is an option available to programs that were written
177
   to expect options and other ARGV-elements in any order and that care about
178
   the ordering of the two.  We describe each non-option ARGV-element
179
   as if it were the argument of an option with character code 1.
180
   Using `-' as the first character of the list of option characters
181
   selects this mode of operation.
182
 
183
   The special argument `--' forces an end of option-scanning regardless
184
   of the value of `ordering'.  In the case of RETURN_IN_ORDER, only
185
   `--' can cause `getopt' to return -1 with `optind' != ARGC.  */
186
 
187
static enum
188
{
189
  REQUIRE_ORDER, PERMUTE, RETURN_IN_ORDER
190
} ordering;
191
 
192
/* Value of POSIXLY_CORRECT environment variable.  */
193
static char *posixly_correct;
194
 
195
#ifdef  __GNU_LIBRARY__
196
/* We want to avoid inclusion of string.h with non-GNU libraries
197
   because there are many ways it can cause trouble.
198
   On some systems, it contains special magic macros that don't work
199
   in GCC.  */
200
# include <string.h>
201
# define my_index       strchr
202
#else
203
 
204
# if HAVE_STRING_H
205
#  include <string.h>
206
# else
207
#  if HAVE_STRINGS_H
208
#   include <strings.h>
209
#  endif
210
# endif
211
 
212
/* Avoid depending on library functions or files
213
   whose names are inconsistent.  */
214
 
215
#ifndef getenv
216
extern char *getenv ();
217
#endif
218
 
219
static char *
220
my_index (str, chr)
221
     const char *str;
222
     int chr;
223
{
224
  while (*str)
225
    {
226
      if (*str == chr)
227
        return (char *) str;
228
      str++;
229
    }
230
  return 0;
231
}
232
 
233
/* If using GCC, we can safely declare strlen this way.
234
   If not using GCC, it is ok not to declare it.  */
235
#ifdef __GNUC__
236
/* Note that Motorola Delta 68k R3V7 comes with GCC but not stddef.h.
237
   That was relevant to code that was here before.  */
238
# if (!defined __STDC__ || !__STDC__) && !defined strlen
239
/* gcc with -traditional declares the built-in strlen to return int,
240
   and has done so at least since version 2.4.5. -- rms.  */
241
extern int strlen (const char *);
242
# endif /* not __STDC__ */
243
#endif /* __GNUC__ */
244
 
245
#endif /* not __GNU_LIBRARY__ */
246
 
247
/* Handle permutation of arguments.  */
248
 
249
/* Describe the part of ARGV that contains non-options that have
250
   been skipped.  `first_nonopt' is the index in ARGV of the first of them;
251
   `last_nonopt' is the index after the last of them.  */
252
 
253
static int first_nonopt;
254
static int last_nonopt;
255
 
256
#ifdef _LIBC
257
/* Bash 2.0 gives us an environment variable containing flags
258
   indicating ARGV elements that should not be considered arguments.  */
259
 
260
/* Defined in getopt_init.c  */
261
extern char *__getopt_nonoption_flags;
262
 
263
static int nonoption_flags_max_len;
264
static int nonoption_flags_len;
265
 
266
static int original_argc;
267
static char *const *original_argv;
268
 
269
/* Make sure the environment variable bash 2.0 puts in the environment
270
   is valid for the getopt call we must make sure that the ARGV passed
271
   to getopt is that one passed to the process.  */
272
static void
273
__attribute__ ((unused))
274
store_args_and_env (int argc, char *const *argv)
275
{
276
  /* XXX This is no good solution.  We should rather copy the args so
277
     that we can compare them later.  But we must not use malloc(3).  */
278
  original_argc = argc;
279
  original_argv = argv;
280
}
281
# ifdef text_set_element
282
text_set_element (__libc_subinit, store_args_and_env);
283
# endif /* text_set_element */
284
 
285
# define SWAP_FLAGS(ch1, ch2) \
286
  if (nonoption_flags_len > 0)                                                 \
287
    {                                                                         \
288
      char __tmp = __getopt_nonoption_flags[ch1];                             \
289
      __getopt_nonoption_flags[ch1] = __getopt_nonoption_flags[ch2];          \
290
      __getopt_nonoption_flags[ch2] = __tmp;                                  \
291
    }
292
#else   /* !_LIBC */
293
# define SWAP_FLAGS(ch1, ch2)
294
#endif  /* _LIBC */
295
 
296
/* Exchange two adjacent subsequences of ARGV.
297
   One subsequence is elements [first_nonopt,last_nonopt)
298
   which contains all the non-options that have been skipped so far.
299
   The other is elements [last_nonopt,optind), which contains all
300
   the options processed since those non-options were skipped.
301
 
302
   `first_nonopt' and `last_nonopt' are relocated so that they describe
303
   the new indices of the non-options in ARGV after they are moved.  */
304
 
305
#if defined __STDC__ && __STDC__
306
static void exchange (char **);
307
#endif
308
 
309
static void
310
exchange (argv)
311
     char **argv;
312
{
313
  int bottom = first_nonopt;
314
  int middle = last_nonopt;
315
  int top = optind;
316
  char *tem;
317
 
318
  /* Exchange the shorter segment with the far end of the longer segment.
319
     That puts the shorter segment into the right place.
320
     It leaves the longer segment in the right place overall,
321
     but it consists of two parts that need to be swapped next.  */
322
 
323
#ifdef _LIBC
324
  /* First make sure the handling of the `__getopt_nonoption_flags'
325
     string can work normally.  Our top argument must be in the range
326
     of the string.  */
327
  if (nonoption_flags_len > 0 && top >= nonoption_flags_max_len)
328
    {
329
      /* We must extend the array.  The user plays games with us and
330
         presents new arguments.  */
331
      char *new_str = malloc (top + 1);
332
      if (new_str == NULL)
333
        nonoption_flags_len = nonoption_flags_max_len = 0;
334
      else
335
        {
336
          memset (__mempcpy (new_str, __getopt_nonoption_flags,
337
                             nonoption_flags_max_len),
338
                  '\0', top + 1 - nonoption_flags_max_len);
339
          nonoption_flags_max_len = top + 1;
340
          __getopt_nonoption_flags = new_str;
341
        }
342
    }
343
#endif
344
 
345
  while (top > middle && middle > bottom)
346
    {
347
      if (top - middle > middle - bottom)
348
        {
349
          /* Bottom segment is the short one.  */
350
          int len = middle - bottom;
351
          register int i;
352
 
353
          /* Swap it with the top part of the top segment.  */
354
          for (i = 0; i < len; i++)
355
            {
356
              tem = argv[bottom + i];
357
              argv[bottom + i] = argv[top - (middle - bottom) + i];
358
              argv[top - (middle - bottom) + i] = tem;
359
              SWAP_FLAGS (bottom + i, top - (middle - bottom) + i);
360
            }
361
          /* Exclude the moved bottom segment from further swapping.  */
362
          top -= len;
363
        }
364
      else
365
        {
366
          /* Top segment is the short one.  */
367
          int len = top - middle;
368
          register int i;
369
 
370
          /* Swap it with the bottom part of the bottom segment.  */
371
          for (i = 0; i < len; i++)
372
            {
373
              tem = argv[bottom + i];
374
              argv[bottom + i] = argv[middle + i];
375
              argv[middle + i] = tem;
376
              SWAP_FLAGS (bottom + i, middle + i);
377
            }
378
          /* Exclude the moved top segment from further swapping.  */
379
          bottom += len;
380
        }
381
    }
382
 
383
  /* Update records for the slots the non-options now occupy.  */
384
 
385
  first_nonopt += (optind - last_nonopt);
386
  last_nonopt = optind;
387
}
388
 
389
/* Initialize the internal data when the first call is made.  */
390
 
391
#if defined __STDC__ && __STDC__
392
static const char *_getopt_initialize (int, char *const *, const char *);
393
#endif
394
static const char *
395
_getopt_initialize (argc, argv, optstring)
396
     int argc;
397
     char *const *argv;
398
     const char *optstring;
399
{
400
  /* Start processing options with ARGV-element 1 (since ARGV-element 0
401
     is the program name); the sequence of previously skipped
402
     non-option ARGV-elements is empty.  */
403
 
404
  first_nonopt = last_nonopt = optind;
405
 
406
  nextchar = NULL;
407
 
408
  posixly_correct = getenv ("POSIXLY_CORRECT");
409
 
410
  /* Determine how to handle the ordering of options and nonoptions.  */
411
 
412
  if (optstring[0] == '-')
413
    {
414
      ordering = RETURN_IN_ORDER;
415
      ++optstring;
416
    }
417
  else if (optstring[0] == '+')
418
    {
419
      ordering = REQUIRE_ORDER;
420
      ++optstring;
421
    }
422
  else if (posixly_correct != NULL)
423
    ordering = REQUIRE_ORDER;
424
  else
425
    ordering = PERMUTE;
426
 
427
#ifdef _LIBC
428
  if (posixly_correct == NULL
429
      && argc == original_argc && argv == original_argv)
430
    {
431
      if (nonoption_flags_max_len == 0)
432
        {
433
          if (__getopt_nonoption_flags == NULL
434
              || __getopt_nonoption_flags[0] == '\0')
435
            nonoption_flags_max_len = -1;
436
          else
437
            {
438
              const char *orig_str = __getopt_nonoption_flags;
439
              int len = nonoption_flags_max_len = strlen (orig_str);
440
              if (nonoption_flags_max_len < argc)
441
                nonoption_flags_max_len = argc;
442
              __getopt_nonoption_flags =
443
                (char *) malloc (nonoption_flags_max_len);
444
              if (__getopt_nonoption_flags == NULL)
445
                nonoption_flags_max_len = -1;
446
              else
447
                memset (__mempcpy (__getopt_nonoption_flags, orig_str, len),
448
                        '\0', nonoption_flags_max_len - len);
449
            }
450
        }
451
      nonoption_flags_len = nonoption_flags_max_len;
452
    }
453
  else
454
    nonoption_flags_len = 0;
455
#endif
456
 
457
  return optstring;
458
}
459
 
460
/* Scan elements of ARGV (whose length is ARGC) for option characters
461
   given in OPTSTRING.
462
 
463
   If an element of ARGV starts with '-', and is not exactly "-" or "--",
464
   then it is an option element.  The characters of this element
465
   (aside from the initial '-') are option characters.  If `getopt'
466
   is called repeatedly, it returns successively each of the option characters
467
   from each of the option elements.
468
 
469
   If `getopt' finds another option character, it returns that character,
470
   updating `optind' and `nextchar' so that the next call to `getopt' can
471
   resume the scan with the following option character or ARGV-element.
472
 
473
   If there are no more option characters, `getopt' returns -1.
474
   Then `optind' is the index in ARGV of the first ARGV-element
475
   that is not an option.  (The ARGV-elements have been permuted
476
   so that those that are not options now come last.)
477
 
478
   OPTSTRING is a string containing the legitimate option characters.
479
   If an option character is seen that is not listed in OPTSTRING,
480
   return '?' after printing an error message.  If you set `opterr' to
481
   zero, the error message is suppressed but we still return '?'.
482
 
483
   If a char in OPTSTRING is followed by a colon, that means it wants an arg,
484
   so the following text in the same ARGV-element, or the text of the following
485
   ARGV-element, is returned in `optarg'.  Two colons mean an option that
486
   wants an optional arg; if there is text in the current ARGV-element,
487
   it is returned in `optarg', otherwise `optarg' is set to zero.
488
 
489
   If OPTSTRING starts with `-' or `+', it requests different methods of
490
   handling the non-option ARGV-elements.
491
   See the comments about RETURN_IN_ORDER and REQUIRE_ORDER, above.
492
 
493
   Long-named options begin with `--' instead of `-'.
494
   Their names may be abbreviated as long as the abbreviation is unique
495
   or is an exact match for some defined option.  If they have an
496
   argument, it follows the option name in the same ARGV-element, separated
497
   from the option name by a `=', or else the in next ARGV-element.
498
   When `getopt' finds a long-named option, it returns 0 if that option's
499
   `flag' field is nonzero, the value of the option's `val' field
500
   if the `flag' field is zero.
501
 
502
   The elements of ARGV aren't really const, because we permute them.
503
   But we pretend they're const in the prototype to be compatible
504
   with other systems.
505
 
506
   LONGOPTS is a vector of `struct option' terminated by an
507
   element containing a name which is zero.
508
 
509
   LONGIND returns the index in LONGOPT of the long-named option found.
510
   It is only valid when a long-named option has been found by the most
511
   recent call.
512
 
513
   If LONG_ONLY is nonzero, '-' as well as '--' can introduce
514
   long-named options.  */
515
 
516
int
517
_getopt_internal (argc, argv, optstring, longopts, longind, long_only)
518
     int argc;
519
     char *const *argv;
520
     const char *optstring;
521
     const struct option *longopts;
522
     int *longind;
523
     int long_only;
524
{
525
  optarg = NULL;
526
 
527
  if (optind == 0 || !__getopt_initialized)
528
    {
529
      if (optind == 0)
530
        optind = 1;     /* Don't scan ARGV[0], the program name.  */
531
      optstring = _getopt_initialize (argc, argv, optstring);
532
      __getopt_initialized = 1;
533
    }
534
 
535
  /* Test whether ARGV[optind] points to a non-option argument.
536
     Either it does not have option syntax, or there is an environment flag
537
     from the shell indicating it is not an option.  The later information
538
     is only used when the used in the GNU libc.  */
539
#ifdef _LIBC
540
# define NONOPTION_P (argv[optind][0] != '-' || argv[optind][1] == '\0'       \
541
                      || (optind < nonoption_flags_len                        \
542
                          && __getopt_nonoption_flags[optind] == '1'))
543
#else
544
# define NONOPTION_P (argv[optind][0] != '-' || argv[optind][1] == '\0')
545
#endif
546
 
547
  if (nextchar == NULL || *nextchar == '\0')
548
    {
549
      /* Advance to the next ARGV-element.  */
550
 
551
      /* Give FIRST_NONOPT & LAST_NONOPT rational values if OPTIND has been
552
         moved back by the user (who may also have changed the arguments).  */
553
      if (last_nonopt > optind)
554
        last_nonopt = optind;
555
      if (first_nonopt > optind)
556
        first_nonopt = optind;
557
 
558
      if (ordering == PERMUTE)
559
        {
560
          /* If we have just processed some options following some non-options,
561
             exchange them so that the options come first.  */
562
 
563
          if (first_nonopt != last_nonopt && last_nonopt != optind)
564
            exchange ((char **) argv);
565
          else if (last_nonopt != optind)
566
            first_nonopt = optind;
567
 
568
          /* Skip any additional non-options
569
             and extend the range of non-options previously skipped.  */
570
 
571
          while (optind < argc && NONOPTION_P)
572
            optind++;
573
          last_nonopt = optind;
574
        }
575
 
576
      /* The special ARGV-element `--' means premature end of options.
577
         Skip it like a null option,
578
         then exchange with previous non-options as if it were an option,
579
         then skip everything else like a non-option.  */
580
 
581
      if (optind != argc && !strcmp (argv[optind], "--"))
582
        {
583
          optind++;
584
 
585
          if (first_nonopt != last_nonopt && last_nonopt != optind)
586
            exchange ((char **) argv);
587
          else if (first_nonopt == last_nonopt)
588
            first_nonopt = optind;
589
          last_nonopt = argc;
590
 
591
          optind = argc;
592
        }
593
 
594
      /* If we have done all the ARGV-elements, stop the scan
595
         and back over any non-options that we skipped and permuted.  */
596
 
597
      if (optind == argc)
598
        {
599
          /* Set the next-arg-index to point at the non-options
600
             that we previously skipped, so the caller will digest them.  */
601
          if (first_nonopt != last_nonopt)
602
            optind = first_nonopt;
603
          return -1;
604
        }
605
 
606
      /* If we have come to a non-option and did not permute it,
607
         either stop the scan or describe it to the caller and pass it by.  */
608
 
609
      if (NONOPTION_P)
610
        {
611
          if (ordering == REQUIRE_ORDER)
612
            return -1;
613
          optarg = argv[optind++];
614
          return 1;
615
        }
616
 
617
      /* We have found another option-ARGV-element.
618
         Skip the initial punctuation.  */
619
 
620
      nextchar = (argv[optind] + 1
621
                  + (longopts != NULL && argv[optind][1] == '-'));
622
    }
623
 
624
  /* Decode the current option-ARGV-element.  */
625
 
626
  /* Check whether the ARGV-element is a long option.
627
 
628
     If long_only and the ARGV-element has the form "-f", where f is
629
     a valid short option, don't consider it an abbreviated form of
630
     a long option that starts with f.  Otherwise there would be no
631
     way to give the -f short option.
632
 
633
     On the other hand, if there's a long option "fubar" and
634
     the ARGV-element is "-fu", do consider that an abbreviation of
635
     the long option, just like "--fu", and not "-f" with arg "u".
636
 
637
     This distinction seems to be the most useful approach.  */
638
 
639
  if (longopts != NULL
640
      && (argv[optind][1] == '-'
641
          || (long_only && (argv[optind][2] || !my_index (optstring, argv[optind][1])))))
642
    {
643
      char *nameend;
644
      const struct option *p;
645
      const struct option *pfound = NULL;
646
      int exact = 0;
647
      int ambig = 0;
648
      int indfound = -1;
649
      int option_index;
650
 
651
      for (nameend = nextchar; *nameend && *nameend != '='; nameend++)
652
        /* Do nothing.  */ ;
653
 
654
      /* Test all long options for either exact match
655
         or abbreviated matches.  */
656
      for (p = longopts, option_index = 0; p->name; p++, option_index++)
657
        if (!strncmp (p->name, nextchar, nameend - nextchar))
658
          {
659
            if ((unsigned int) (nameend - nextchar)
660
                == (unsigned int) strlen (p->name))
661
              {
662
                /* Exact match found.  */
663
                pfound = p;
664
                indfound = option_index;
665
                exact = 1;
666
                break;
667
              }
668
            else if (pfound == NULL)
669
              {
670
                /* First nonexact match found.  */
671
                pfound = p;
672
                indfound = option_index;
673
              }
674
            else
675
              /* Second or later nonexact match found.  */
676
              ambig = 1;
677
          }
678
 
679
      if (ambig && !exact)
680
        {
681
          if (opterr)
682
            fprintf (stderr, _("%s: option `%s' is ambiguous\n"),
683
                     argv[0], argv[optind]);
684
          nextchar += strlen (nextchar);
685
          optind++;
686
          optopt = 0;
687
          return '?';
688
        }
689
 
690
      if (pfound != NULL)
691
        {
692
          option_index = indfound;
693
          optind++;
694
          if (*nameend)
695
            {
696
              /* Don't test has_arg with >, because some C compilers don't
697
                 allow it to be used on enums.  */
698
              if (pfound->has_arg)
699
                optarg = nameend + 1;
700
              else
701
                {
702
                  if (opterr)
703
                    {
704
                      if (argv[optind - 1][1] == '-')
705
                        /* --option */
706
                        fprintf (stderr,
707
                                 _("%s: option `--%s' doesn't allow an argument\n"),
708
                                 argv[0], pfound->name);
709
                      else
710
                        /* +option or -option */
711
                        fprintf (stderr,
712
                                 _("%s: option `%c%s' doesn't allow an argument\n"),
713
                                 argv[0], argv[optind - 1][0], pfound->name);
714
 
715
                      nextchar += strlen (nextchar);
716
 
717
                      optopt = pfound->val;
718
                      return '?';
719
                    }
720
                }
721
            }
722
          else if (pfound->has_arg == 1)
723
            {
724
              if (optind < argc)
725
                optarg = argv[optind++];
726
              else
727
                {
728
                  if (opterr)
729
                    fprintf (stderr,
730
                           _("%s: option `%s' requires an argument\n"),
731
                           argv[0], argv[optind - 1]);
732
                  nextchar += strlen (nextchar);
733
                  optopt = pfound->val;
734
                  return optstring[0] == ':' ? ':' : '?';
735
                }
736
            }
737
          nextchar += strlen (nextchar);
738
          if (longind != NULL)
739
            *longind = option_index;
740
          if (pfound->flag)
741
            {
742
              *(pfound->flag) = pfound->val;
743
              return 0;
744
            }
745
          return pfound->val;
746
        }
747
 
748
      /* Can't find it as a long option.  If this is not getopt_long_only,
749
         or the option starts with '--' or is not a valid short
750
         option, then it's an error.
751
         Otherwise interpret it as a short option.  */
752
      if (!long_only || argv[optind][1] == '-'
753
          || my_index (optstring, *nextchar) == NULL)
754
        {
755
          if (opterr)
756
            {
757
              if (argv[optind][1] == '-')
758
                /* --option */
759
                fprintf (stderr, _("%s: unrecognized option `--%s'\n"),
760
                         argv[0], nextchar);
761
              else
762
                /* +option or -option */
763
                fprintf (stderr, _("%s: unrecognized option `%c%s'\n"),
764
                         argv[0], argv[optind][0], nextchar);
765
            }
766
          nextchar = (char *) "";
767
          optind++;
768
          optopt = 0;
769
          return '?';
770
        }
771
    }
772
 
773
  /* Look at and handle the next short option-character.  */
774
 
775
  {
776
    char c = *nextchar++;
777
    char *temp = my_index (optstring, c);
778
 
779
    /* Increment `optind' when we start to process its last character.  */
780
    if (*nextchar == '\0')
781
      ++optind;
782
 
783
    if (temp == NULL || c == ':')
784
      {
785
        if (opterr)
786
          {
787
            if (posixly_correct)
788
              /* 1003.2 specifies the format of this message.  */
789
              fprintf (stderr, _("%s: illegal option -- %c\n"),
790
                       argv[0], c);
791
            else
792
              fprintf (stderr, _("%s: invalid option -- %c\n"),
793
                       argv[0], c);
794
          }
795
        optopt = c;
796
        return '?';
797
      }
798
    /* Convenience. Treat POSIX -W foo same as long option --foo */
799
    if (temp[0] == 'W' && temp[1] == ';')
800
      {
801
        char *nameend;
802
        const struct option *p;
803
        const struct option *pfound = NULL;
804
        int exact = 0;
805
        int ambig = 0;
806
        int indfound = 0;
807
        int option_index;
808
 
809
        /* This is an option that requires an argument.  */
810
        if (*nextchar != '\0')
811
          {
812
            optarg = nextchar;
813
            /* If we end this ARGV-element by taking the rest as an arg,
814
               we must advance to the next element now.  */
815
            optind++;
816
          }
817
        else if (optind == argc)
818
          {
819
            if (opterr)
820
              {
821
                /* 1003.2 specifies the format of this message.  */
822
                fprintf (stderr, _("%s: option requires an argument -- %c\n"),
823
                         argv[0], c);
824
              }
825
            optopt = c;
826
            if (optstring[0] == ':')
827
              c = ':';
828
            else
829
              c = '?';
830
            return c;
831
          }
832
        else
833
          /* We already incremented `optind' once;
834
             increment it again when taking next ARGV-elt as argument.  */
835
          optarg = argv[optind++];
836
 
837
        /* optarg is now the argument, see if it's in the
838
           table of longopts.  */
839
 
840
        for (nextchar = nameend = optarg; *nameend && *nameend != '='; nameend++)
841
          /* Do nothing.  */ ;
842
 
843
        /* Test all long options for either exact match
844
           or abbreviated matches.  */
845
        for (p = longopts, option_index = 0; p->name; p++, option_index++)
846
          if (!strncmp (p->name, nextchar, nameend - nextchar))
847
            {
848
              if ((unsigned int) (nameend - nextchar) == strlen (p->name))
849
                {
850
                  /* Exact match found.  */
851
                  pfound = p;
852
                  indfound = option_index;
853
                  exact = 1;
854
                  break;
855
                }
856
              else if (pfound == NULL)
857
                {
858
                  /* First nonexact match found.  */
859
                  pfound = p;
860
                  indfound = option_index;
861
                }
862
              else
863
                /* Second or later nonexact match found.  */
864
                ambig = 1;
865
            }
866
        if (ambig && !exact)
867
          {
868
            if (opterr)
869
              fprintf (stderr, _("%s: option `-W %s' is ambiguous\n"),
870
                       argv[0], argv[optind]);
871
            nextchar += strlen (nextchar);
872
            optind++;
873
            return '?';
874
          }
875
        if (pfound != NULL)
876
          {
877
            option_index = indfound;
878
            if (*nameend)
879
              {
880
                /* Don't test has_arg with >, because some C compilers don't
881
                   allow it to be used on enums.  */
882
                if (pfound->has_arg)
883
                  optarg = nameend + 1;
884
                else
885
                  {
886
                    if (opterr)
887
                      fprintf (stderr, _("\
888
%s: option `-W %s' doesn't allow an argument\n"),
889
                               argv[0], pfound->name);
890
 
891
                    nextchar += strlen (nextchar);
892
                    return '?';
893
                  }
894
              }
895
            else if (pfound->has_arg == 1)
896
              {
897
                if (optind < argc)
898
                  optarg = argv[optind++];
899
                else
900
                  {
901
                    if (opterr)
902
                      fprintf (stderr,
903
                               _("%s: option `%s' requires an argument\n"),
904
                               argv[0], argv[optind - 1]);
905
                    nextchar += strlen (nextchar);
906
                    return optstring[0] == ':' ? ':' : '?';
907
                  }
908
              }
909
            nextchar += strlen (nextchar);
910
            if (longind != NULL)
911
              *longind = option_index;
912
            if (pfound->flag)
913
              {
914
                *(pfound->flag) = pfound->val;
915
                return 0;
916
              }
917
            return pfound->val;
918
          }
919
          nextchar = NULL;
920
          return 'W';   /* Let the application handle it.   */
921
      }
922
    if (temp[1] == ':')
923
      {
924
        if (temp[2] == ':')
925
          {
926
            /* This is an option that accepts an argument optionally.  */
927
            if (*nextchar != '\0')
928
              {
929
                optarg = nextchar;
930
                optind++;
931
              }
932
            else
933
              optarg = NULL;
934
            nextchar = NULL;
935
          }
936
        else
937
          {
938
            /* This is an option that requires an argument.  */
939
            if (*nextchar != '\0')
940
              {
941
                optarg = nextchar;
942
                /* If we end this ARGV-element by taking the rest as an arg,
943
                   we must advance to the next element now.  */
944
                optind++;
945
              }
946
            else if (optind == argc)
947
              {
948
                if (opterr)
949
                  {
950
                    /* 1003.2 specifies the format of this message.  */
951
                    fprintf (stderr,
952
                           _("%s: option requires an argument -- %c\n"),
953
                           argv[0], c);
954
                  }
955
                optopt = c;
956
                if (optstring[0] == ':')
957
                  c = ':';
958
                else
959
                  c = '?';
960
              }
961
            else
962
              /* We already incremented `optind' once;
963
                 increment it again when taking next ARGV-elt as argument.  */
964
              optarg = argv[optind++];
965
            nextchar = NULL;
966
          }
967
      }
968
    return c;
969
  }
970
}
971
 
972
int
973
getopt (argc, argv, optstring)
974
     int argc;
975
     char *const *argv;
976
     const char *optstring;
977
{
978
  return _getopt_internal (argc, argv, optstring,
979
                           (const struct option *) 0,
980
                           (int *) 0,
981
                           0);
982
}
983
 
984
#endif  /* Not ELIDE_CODE.  */
985
 
986
#ifdef TEST
987
 
988
/* Compile with -DTEST to make an executable for use in testing
989
   the above definition of `getopt'.  */
990
 
991
int
992
main (argc, argv)
993
     int argc;
994
     char **argv;
995
{
996
  int c;
997
  int digit_optind = 0;
998
 
999
  while (1)
1000
    {
1001
      int this_option_optind = optind ? optind : 1;
1002
 
1003
      c = getopt (argc, argv, "abc:d:0123456789");
1004
      if (c == -1)
1005
        break;
1006
 
1007
      switch (c)
1008
        {
1009
        case '0':
1010
        case '1':
1011
        case '2':
1012
        case '3':
1013
        case '4':
1014
        case '5':
1015
        case '6':
1016
        case '7':
1017
        case '8':
1018
        case '9':
1019
          if (digit_optind != 0 && digit_optind != this_option_optind)
1020
            printf ("digits occur in two different argv-elements.\n");
1021
          digit_optind = this_option_optind;
1022
          printf ("option %c\n", c);
1023
          break;
1024
 
1025
        case 'a':
1026
          printf ("option a\n");
1027
          break;
1028
 
1029
        case 'b':
1030
          printf ("option b\n");
1031
          break;
1032
 
1033
        case 'c':
1034
          printf ("option c with value `%s'\n", optarg);
1035
          break;
1036
 
1037
        case '?':
1038
          break;
1039
 
1040
        default:
1041
          printf ("?? getopt returned character code 0%o ??\n", c);
1042
        }
1043
    }
1044
 
1045
  if (optind < argc)
1046
    {
1047
      printf ("non-option ARGV-elements: ");
1048
      while (optind < argc)
1049
        printf ("%s ", argv[optind++]);
1050
      printf ("\n");
1051
    }
1052
 
1053
  exit (0);
1054
}
1055
 
1056
#endif /* TEST */

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.