merge with 1.9.2b
[pspp] / lib / getopt.c
1 /* 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 roland@gnu.ai.mit.edu
4    before changing it!
5
6    Copyright (C) 1987, 88, 89, 90, 91, 92, 1993
7         Free Software Foundation, Inc.
8
9    This program is free software; you can redistribute it and/or modify it
10    under the terms of the GNU General Public License as published by the
11    Free Software Foundation; either version 2, or (at your option) any
12    later version.
13
14    This program is distributed in the hope that it will be useful,
15    but WITHOUT ANY WARRANTY; without even the implied warranty of
16    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17    GNU General Public License for more details.
18
19    You should have received a copy of the GNU General Public License
20    along with this program; if not, write to the Free Software
21    Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.  */
22 \f
23 /* 
24  * This tells Alpha OSF/1 not to define a getopt prototype in <stdio.h>.
25  * Ditto for AIX 3.2 and <stdlib.h>.
26  */
27 #ifndef _NO_PROTO
28 #define _NO_PROTO
29 #endif
30
31 #ifdef HAVE_CONFIG_H
32 #if defined (emacs) || defined (CONFIG_BROKETS)
33 /* We use <config.h> instead of "config.h" so that a compilation
34    using -I. -I$srcdir will use ./config.h rather than $srcdir/config.h
35    (which it would do because it found this file in $srcdir).  */
36 #include <config.h>
37 #else
38 #include "config.h"
39 #endif
40 #endif
41
42 #ifndef __STDC__
43 /* This is a separate conditional since some stdc systems
44    reject `defined (const)'.  */
45 #ifndef const
46 #define const
47 #endif
48 #endif
49
50 #include <stdio.h>
51
52 /* Comment out all this code if we are using the GNU C Library, and are not
53    actually compiling the library itself.  This code is part of the GNU C
54    Library, but also included in many other GNU distributions.  Compiling
55    and linking in this code is a waste when using the GNU C library
56    (especially if it is a shared library).  Rather than having every GNU
57    program understand `configure --with-gnu-libc' and omit the object files,
58    it is simpler to just do this in the source for each such file.  */
59
60 #if defined (_LIBC) || !defined (__GNU_LIBRARY__)
61
62
63 /* This needs to come after some library #include
64    to get __GNU_LIBRARY__ defined.  */
65 #ifdef  __GNU_LIBRARY__
66 /* Don't include stdlib.h for non-GNU C libraries because some of them
67    contain conflicting prototypes for getopt.  */
68 #include <stdlib.h>
69 #endif  /* GNU C library.  */
70
71 /* If GETOPT_COMPAT is defined, `+' as well as `--' can introduce a
72    long-named option.  Because this is not POSIX.2 compliant, it is
73    being phased out.  */
74 /* #define GETOPT_COMPAT */
75
76 /* This version of `getopt' appears to the caller like standard Unix `getopt'
77    but it behaves differently for the user, since it allows the user
78    to intersperse the options with the other arguments.
79
80    As `getopt' works, it permutes the elements of ARGV so that,
81    when it is done, all the options precede everything else.  Thus
82    all application programs are extended to handle flexible argument order.
83
84    Setting the environment variable POSIXLY_CORRECT disables permutation.
85    Then the behavior is completely standard.
86
87    GNU application programs can use a third alternative mode in which
88    they can distinguish the relative order of options and other arguments.  */
89
90 #include "getopt.h"
91
92 /* For communication from `getopt' to the caller.
93    When `getopt' finds an option that takes an argument,
94    the argument value is returned here.
95    Also, when `ordering' is RETURN_IN_ORDER,
96    each non-option ARGV-element is returned here.  */
97
98 char *optarg = 0;
99
100 /* Index in ARGV of the next element to be scanned.
101    This is used for communication to and from the caller
102    and for communication between successive calls to `getopt'.
103
104    On entry to `getopt', zero means this is the first call; initialize.
105
106    When `getopt' returns EOF, this is the index of the first of the
107    non-option elements that the caller should itself scan.
108
109    Otherwise, `optind' communicates from one call to the next
110    how much of ARGV has been scanned so far.  */
111
112 /* XXX 1003.2 says this must be 1 before any call.  */
113 int optind = 0;
114
115 /* The next char to be scanned in the option-element
116    in which the last option character we returned was found.
117    This allows us to pick up the scan where we left off.
118
119    If this is zero, or a null string, it means resume the scan
120    by advancing to the next ARGV-element.  */
121
122 static char *nextchar;
123
124 /* Callers store zero here to inhibit the error message
125    for unrecognized options.  */
126
127 int opterr = 1;
128
129 /* Set to an option character which was unrecognized.
130    This must be initialized on some systems to avoid linking in the
131    system's own getopt implementation.  */
132
133 int optopt = '?';
134
135 /* Describe how to deal with options that follow non-option ARGV-elements.
136
137    If the caller did not specify anything,
138    the default is REQUIRE_ORDER if the environment variable
139    POSIXLY_CORRECT is defined, PERMUTE otherwise.
140
141    REQUIRE_ORDER means don't recognize them as options;
142    stop option processing when the first non-option is seen.
143    This is what Unix does.
144    This mode of operation is selected by either setting the environment
145    variable POSIXLY_CORRECT, or using `+' as the first character
146    of the list of option characters.
147
148    PERMUTE is the default.  We permute the contents of ARGV as we scan,
149    so that eventually all the non-options are at the end.  This allows options
150    to be given in any order, even with programs that were not written to
151    expect this.
152
153    RETURN_IN_ORDER is an option available to programs that were written
154    to expect options and other ARGV-elements in any order and that care about
155    the ordering of the two.  We describe each non-option ARGV-element
156    as if it were the argument of an option with character code 1.
157    Using `-' as the first character of the list of option characters
158    selects this mode of operation.
159
160    The special argument `--' forces an end of option-scanning regardless
161    of the value of `ordering'.  In the case of RETURN_IN_ORDER, only
162    `--' can cause `getopt' to return EOF with `optind' != ARGC.  */
163
164 static enum
165 {
166   REQUIRE_ORDER, PERMUTE, RETURN_IN_ORDER
167 } ordering;
168 \f
169 #ifdef  __GNU_LIBRARY__
170 /* We want to avoid inclusion of string.h with non-GNU libraries
171    because there are many ways it can cause trouble.
172    On some systems, it contains special magic macros that don't work
173    in GCC.  */
174 #include <string.h>
175 #define my_index        strchr
176 #else
177
178 /* Avoid depending on library functions or files
179    whose names are inconsistent.  */
180
181 char *getenv ();
182
183 static char *
184 my_index (str, chr)
185      const char *str;
186      int chr;
187 {
188   while (*str)
189     {
190       if (*str == chr)
191         return (char *) str;
192       str++;
193     }
194   return 0;
195 }
196
197 /* If using GCC, we can safely declare strlen this way.
198    If not using GCC, it is ok not to declare it.
199    (Supposedly there are some machines where it might get a warning,
200    but changing this conditional to __STDC__ is too risky.)  */
201 #ifdef __GNUC__
202 #ifdef IN_GCC
203 #include "gstddef.h"
204 #else
205 #include <stddef.h>
206 #endif
207 extern size_t strlen (const char *);
208 #endif
209
210 #endif                          /* GNU C library.  */
211 \f
212 /* Handle permutation of arguments.  */
213
214 /* Describe the part of ARGV that contains non-options that have
215    been skipped.  `first_nonopt' is the index in ARGV of the first of them;
216    `last_nonopt' is the index after the last of them.  */
217
218 static int first_nonopt;
219 static int last_nonopt;
220
221 /* Exchange two adjacent subsequences of ARGV.
222    One subsequence is elements [first_nonopt,last_nonopt)
223    which contains all the non-options that have been skipped so far.
224    The other is elements [last_nonopt,optind), which contains all
225    the options processed since those non-options were skipped.
226
227    `first_nonopt' and `last_nonopt' are relocated so that they describe
228    the new indices of the non-options in ARGV after they are moved.  */
229
230 static void
231 exchange (argv)
232      char **argv;
233 {
234   int bottom = first_nonopt;
235   int middle = last_nonopt;
236   int top = optind;
237   char *tem;
238
239   /* Exchange the shorter segment with the far end of the longer segment.
240      That puts the shorter segment into the right place.
241      It leaves the longer segment in the right place overall,
242      but it consists of two parts that need to be swapped next.  */
243
244   while (top > middle && middle > bottom)
245     {
246       if (top - middle > middle - bottom)
247         {
248           /* Bottom segment is the short one.  */
249           int len = middle - bottom;
250           register int i;
251
252           /* Swap it with the top part of the top segment.  */
253           for (i = 0; i < len; i++)
254             {
255               tem = argv[bottom + i];
256               argv[bottom + i] = argv[top - (middle - bottom) + i];
257               argv[top - (middle - bottom) + i] = tem;
258             }
259           /* Exclude the moved bottom segment from further swapping.  */
260           top -= len;
261         }
262       else
263         {
264           /* Top segment is the short one.  */
265           int len = top - middle;
266           register int i;
267
268           /* Swap it with the bottom part of the bottom segment.  */
269           for (i = 0; i < len; i++)
270             {
271               tem = argv[bottom + i];
272               argv[bottom + i] = argv[middle + i];
273               argv[middle + i] = tem;
274             }
275           /* Exclude the moved top segment from further swapping.  */
276           bottom += len;
277         }
278     }
279
280   /* Update records for the slots the non-options now occupy.  */
281
282   first_nonopt += (optind - last_nonopt);
283   last_nonopt = optind;
284 }
285 \f
286 /* Scan elements of ARGV (whose length is ARGC) for option characters
287    given in OPTSTRING.
288
289    If an element of ARGV starts with '-', and is not exactly "-" or "--",
290    then it is an option element.  The characters of this element
291    (aside from the initial '-') are option characters.  If `getopt'
292    is called repeatedly, it returns successively each of the option characters
293    from each of the option elements.
294
295    If `getopt' finds another option character, it returns that character,
296    updating `optind' and `nextchar' so that the next call to `getopt' can
297    resume the scan with the following option character or ARGV-element.
298
299    If there are no more option characters, `getopt' returns `EOF'.
300    Then `optind' is the index in ARGV of the first ARGV-element
301    that is not an option.  (The ARGV-elements have been permuted
302    so that those that are not options now come last.)
303
304    OPTSTRING is a string containing the legitimate option characters.
305    If an option character is seen that is not listed in OPTSTRING,
306    return '?' after printing an error message.  If you set `opterr' to
307    zero, the error message is suppressed but we still return '?'.
308
309    If a char in OPTSTRING is followed by a colon, that means it wants an arg,
310    so the following text in the same ARGV-element, or the text of the following
311    ARGV-element, is returned in `optarg'.  Two colons mean an option that
312    wants an optional arg; if there is text in the current ARGV-element,
313    it is returned in `optarg', otherwise `optarg' is set to zero.
314
315    If OPTSTRING starts with `-' or `+', it requests different methods of
316    handling the non-option ARGV-elements.
317    See the comments about RETURN_IN_ORDER and REQUIRE_ORDER, above.
318
319    Long-named options begin with `--' instead of `-'.
320    Their names may be abbreviated as long as the abbreviation is unique
321    or is an exact match for some defined option.  If they have an
322    argument, it follows the option name in the same ARGV-element, separated
323    from the option name by a `=', or else the in next ARGV-element.
324    When `getopt' finds a long-named option, it returns 0 if that option's
325    `flag' field is nonzero, the value of the option's `val' field
326    if the `flag' field is zero.
327
328    The elements of ARGV aren't really const, because we permute them.
329    But we pretend they're const in the prototype to be compatible
330    with other systems.
331
332    LONGOPTS is a vector of `struct option' terminated by an
333    element containing a name which is zero.
334
335    LONGIND returns the index in LONGOPT of the long-named option found.
336    It is only valid when a long-named option has been found by the most
337    recent call.
338
339    If LONG_ONLY is nonzero, '-' as well as '--' can introduce
340    long-named options.  */
341
342 int
343 _getopt_internal (argc, argv, optstring, longopts, longind, long_only)
344      int argc;
345      char *const *argv;
346      const char *optstring;
347      const struct option *longopts;
348      int *longind;
349      int long_only;
350 {
351   int option_index;
352
353   optarg = 0;
354
355   /* Initialize the internal data when the first call is made.
356      Start processing options with ARGV-element 1 (since ARGV-element 0
357      is the program name); the sequence of previously skipped
358      non-option ARGV-elements is empty.  */
359
360   if (optind == 0)
361     {
362       first_nonopt = last_nonopt = optind = 1;
363
364       nextchar = NULL;
365
366       /* Determine how to handle the ordering of options and nonoptions.  */
367
368       if (optstring[0] == '-')
369         {
370           ordering = RETURN_IN_ORDER;
371           ++optstring;
372         }
373       else if (optstring[0] == '+')
374         {
375           ordering = REQUIRE_ORDER;
376           ++optstring;
377         }
378       else if (getenv ("POSIXLY_CORRECT") != NULL)
379         ordering = REQUIRE_ORDER;
380       else
381         ordering = PERMUTE;
382     }
383
384   if (nextchar == NULL || *nextchar == '\0')
385     {
386       if (ordering == PERMUTE)
387         {
388           /* If we have just processed some options following some non-options,
389              exchange them so that the options come first.  */
390
391           if (first_nonopt != last_nonopt && last_nonopt != optind)
392             exchange ((char **) argv);
393           else if (last_nonopt != optind)
394             first_nonopt = optind;
395
396           /* Now skip any additional non-options
397              and extend the range of non-options previously skipped.  */
398
399           while (optind < argc
400                  && (argv[optind][0] != '-' || argv[optind][1] == '\0')
401 #ifdef GETOPT_COMPAT
402                  && (longopts == NULL
403                      || argv[optind][0] != '+' || argv[optind][1] == '\0')
404 #endif                          /* GETOPT_COMPAT */
405                  )
406             optind++;
407           last_nonopt = optind;
408         }
409
410       /* Special ARGV-element `--' means premature end of options.
411          Skip it like a null option,
412          then exchange with previous non-options as if it were an option,
413          then skip everything else like a non-option.  */
414
415       if (optind != argc && !strcmp (argv[optind], "--"))
416         {
417           optind++;
418
419           if (first_nonopt != last_nonopt && last_nonopt != optind)
420             exchange ((char **) argv);
421           else if (first_nonopt == last_nonopt)
422             first_nonopt = optind;
423           last_nonopt = argc;
424
425           optind = argc;
426         }
427
428       /* If we have done all the ARGV-elements, stop the scan
429          and back over any non-options that we skipped and permuted.  */
430
431       if (optind == argc)
432         {
433           /* Set the next-arg-index to point at the non-options
434              that we previously skipped, so the caller will digest them.  */
435           if (first_nonopt != last_nonopt)
436             optind = first_nonopt;
437           return EOF;
438         }
439
440       /* If we have come to a non-option and did not permute it,
441          either stop the scan or describe it to the caller and pass it by.  */
442
443       if ((argv[optind][0] != '-' || argv[optind][1] == '\0')
444 #ifdef GETOPT_COMPAT
445           && (longopts == NULL
446               || argv[optind][0] != '+' || argv[optind][1] == '\0')
447 #endif                          /* GETOPT_COMPAT */
448           )
449         {
450           if (ordering == REQUIRE_ORDER)
451             return EOF;
452           optarg = argv[optind++];
453           return 1;
454         }
455
456       /* We have found another option-ARGV-element.
457          Start decoding its characters.  */
458
459       nextchar = (argv[optind] + 1
460                   + (longopts != NULL && argv[optind][1] == '-'));
461     }
462
463   if (longopts != NULL
464       && ((argv[optind][0] == '-'
465            && (argv[optind][1] == '-' || long_only))
466 #ifdef GETOPT_COMPAT
467           || argv[optind][0] == '+'
468 #endif                          /* GETOPT_COMPAT */
469           ))
470     {
471       const struct option *p;
472       char *s = nextchar;
473       int exact = 0;
474       int ambig = 0;
475       const struct option *pfound = NULL;
476       int indfound;
477
478       while (*s && *s != '=')
479         s++;
480
481       /* Test all options for either exact match or abbreviated matches.  */
482       for (p = longopts, option_index = 0; p->name;
483            p++, option_index++)
484         if (!strncmp (p->name, nextchar, s - nextchar))
485           {
486             if (s - nextchar == strlen (p->name))
487               {
488                 /* Exact match found.  */
489                 pfound = p;
490                 indfound = option_index;
491                 exact = 1;
492                 break;
493               }
494             else if (pfound == NULL)
495               {
496                 /* First nonexact match found.  */
497                 pfound = p;
498                 indfound = option_index;
499               }
500             else
501               /* Second nonexact match found.  */
502               ambig = 1;
503           }
504
505       if (ambig && !exact)
506         {
507           if (opterr)
508             fprintf (stderr, "%s: option `%s' is ambiguous\n",
509                      argv[0], argv[optind]);
510           nextchar += strlen (nextchar);
511           optind++;
512           return '?';
513         }
514
515       if (pfound != NULL)
516         {
517           option_index = indfound;
518           optind++;
519           if (*s)
520             {
521               /* Don't test has_arg with >, because some C compilers don't
522                  allow it to be used on enums.  */
523               if (pfound->has_arg)
524                 optarg = s + 1;
525               else
526                 {
527                   if (opterr)
528                     {
529                       if (argv[optind - 1][1] == '-')
530                         /* --option */
531                         fprintf (stderr,
532                                  "%s: option `--%s' doesn't allow an argument\n",
533                                  argv[0], pfound->name);
534                       else
535                         /* +option or -option */
536                         fprintf (stderr,
537                              "%s: option `%c%s' doesn't allow an argument\n",
538                              argv[0], argv[optind - 1][0], pfound->name);
539                     }
540                   nextchar += strlen (nextchar);
541                   return '?';
542                 }
543             }
544           else if (pfound->has_arg == 1)
545             {
546               if (optind < argc)
547                 optarg = argv[optind++];
548               else
549                 {
550                   if (opterr)
551                     fprintf (stderr, "%s: option `%s' requires an argument\n",
552                              argv[0], argv[optind - 1]);
553                   nextchar += strlen (nextchar);
554                   return optstring[0] == ':' ? ':' : '?';
555                 }
556             }
557           nextchar += strlen (nextchar);
558           if (longind != NULL)
559             *longind = option_index;
560           if (pfound->flag)
561             {
562               *(pfound->flag) = pfound->val;
563               return 0;
564             }
565           return pfound->val;
566         }
567       /* Can't find it as a long option.  If this is not getopt_long_only,
568          or the option starts with '--' or is not a valid short
569          option, then it's an error.
570          Otherwise interpret it as a short option.  */
571       if (!long_only || argv[optind][1] == '-'
572 #ifdef GETOPT_COMPAT
573           || argv[optind][0] == '+'
574 #endif                          /* GETOPT_COMPAT */
575           || my_index (optstring, *nextchar) == NULL)
576         {
577           if (opterr)
578             {
579               if (argv[optind][1] == '-')
580                 /* --option */
581                 fprintf (stderr, "%s: unrecognized option `--%s'\n",
582                          argv[0], nextchar);
583               else
584                 /* +option or -option */
585                 fprintf (stderr, "%s: unrecognized option `%c%s'\n",
586                          argv[0], argv[optind][0], nextchar);
587             }
588           nextchar = (char *) "";
589           optind++;
590           return '?';
591         }
592     }
593
594   /* Look at and handle the next option-character.  */
595
596   {
597     char c = *nextchar++;
598     char *temp = my_index (optstring, c);
599
600     /* Increment `optind' when we start to process its last character.  */
601     if (*nextchar == '\0')
602       ++optind;
603
604     if (temp == NULL || c == ':')
605       {
606         if (opterr)
607           {
608 #if 0
609             if (c < 040 || c >= 0177)
610               fprintf (stderr, "%s: unrecognized option, character code 0%o\n",
611                        argv[0], c);
612             else
613               fprintf (stderr, "%s: unrecognized option `-%c'\n", argv[0], c);
614 #else
615             /* 1003.2 specifies the format of this message.  */
616             fprintf (stderr, "%s: illegal option -- %c\n", argv[0], c);
617 #endif
618           }
619         optopt = c;
620         return '?';
621       }
622     if (temp[1] == ':')
623       {
624         if (temp[2] == ':')
625           {
626             /* This is an option that accepts an argument optionally.  */
627             if (*nextchar != '\0')
628               {
629                 optarg = nextchar;
630                 optind++;
631               }
632             else
633               optarg = 0;
634             nextchar = NULL;
635           }
636         else
637           {
638             /* This is an option that requires an argument.  */
639             if (*nextchar != '\0')
640               {
641                 optarg = nextchar;
642                 /* If we end this ARGV-element by taking the rest as an arg,
643                    we must advance to the next element now.  */
644                 optind++;
645               }
646             else if (optind == argc)
647               {
648                 if (opterr)
649                   {
650 #if 0
651                     fprintf (stderr, "%s: option `-%c' requires an argument\n",
652                              argv[0], c);
653 #else
654                     /* 1003.2 specifies the format of this message.  */
655                     fprintf (stderr, "%s: option requires an argument -- %c\n",
656                              argv[0], c);
657 #endif
658                   }
659                 optopt = c;
660                 if (optstring[0] == ':')
661                   c = ':';
662                 else
663                   c = '?';
664               }
665             else
666               /* We already incremented `optind' once;
667                  increment it again when taking next ARGV-elt as argument.  */
668               optarg = argv[optind++];
669             nextchar = NULL;
670           }
671       }
672     return c;
673   }
674 }
675
676 int
677 getopt (argc, argv, optstring)
678      int argc;
679      char *const *argv;
680      const char *optstring;
681 {
682   return _getopt_internal (argc, argv, optstring,
683                            (const struct option *) 0,
684                            (int *) 0,
685                            0);
686 }
687
688 #endif  /* _LIBC or not __GNU_LIBRARY__.  */
689 \f
690 #ifdef TEST
691
692 /* Compile with -DTEST to make an executable for use in testing
693    the above definition of `getopt'.  */
694
695 int
696 main (argc, argv)
697      int argc;
698      char **argv;
699 {
700   int c;
701   int digit_optind = 0;
702
703   while (1)
704     {
705       int this_option_optind = optind ? optind : 1;
706
707       c = getopt (argc, argv, "abc:d:0123456789");
708       if (c == EOF)
709         break;
710
711       switch (c)
712         {
713         case '0':
714         case '1':
715         case '2':
716         case '3':
717         case '4':
718         case '5':
719         case '6':
720         case '7':
721         case '8':
722         case '9':
723           if (digit_optind != 0 && digit_optind != this_option_optind)
724             printf ("digits occur in two different argv-elements.\n");
725           digit_optind = this_option_optind;
726           printf ("option %c\n", c);
727           break;
728
729         case 'a':
730           printf ("option a\n");
731           break;
732
733         case 'b':
734           printf ("option b\n");
735           break;
736
737         case 'c':
738           printf ("option c with value `%s'\n", optarg);
739           break;
740
741         case '?':
742           break;
743
744         default:
745           printf ("?? getopt returned character code 0%o ??\n", c);
746         }
747     }
748
749   if (optind < argc)
750     {
751       printf ("non-option ARGV-elements: ");
752       while (optind < argc)
753         printf ("%s ", argv[optind++]);
754       printf ("\n");
755     }
756
757   exit (0);
758 }
759
760 #endif /* TEST */