1 This file is getopts.def
, from which is created getopts.c.
2 It implements the builtin
"getopts" in Bush.
4 Copyright (C
) 1987-2019 Free Software Foundation
, Inc.
6 This file is part of GNU Bush
, the Bourne Again SHell.
8 Bush is free software
: you can redistribute it and
/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation
, either version
3 of the License
, or
11 (at your option
) any later version.
13 Bush is distributed in the hope that it will be useful
,
14 but WITHOUT ANY WARRANTY
; without even the implied warranty of
15 MERCHANTABILITY or FITNESS
FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with Bush. If not
, see
<http
://www.gnu.org
/licenses
/>.
24 $FUNCTION getopts_builtin
25 $SHORT_DOC getopts optstring name
[arg ...
]
26 Parse option arguments.
28 Getopts is used by shell procedures to parse positional parameters
31 OPTSTRING contains the option letters to be recognized
; if a letter
32 is followed by a colon
, the option is expected to have an argument
,
33 which should be separated from it by white space.
35 Each time it is invoked
, getopts will place the next option in the
36 shell variable $name
, initializing name if it does not exist
, and
37 the index of the next argument to be processed into the shell
38 variable OPTIND. OPTIND is initialized to
1 each time the shell or
39 a shell script is invoked. When an option requires an argument
,
40 getopts places that argument into the shell variable OPTARG.
42 getopts reports errors in one of two ways. If the first character
43 of OPTSTRING is a colon
, getopts uses silent error reporting. In
44 this mode
, no error messages are printed. If an invalid option is
45 seen
, getopts places the option character found into OPTARG. If a
46 required argument is not found
, getopts places a
':' into NAME and
47 sets OPTARG to the option character found. If getopts is not in
48 silent mode
, and an invalid option is seen
, getopts places
'?' into
49 NAME and unsets OPTARG. If a required argument is not found
, a
'?'
50 is placed in NAME
, OPTARG is unset
, and a diagnostic message is
53 If the shell variable OPTERR has the value
0, getopts disables the
54 printing of error messages
, even if the first character of
55 OPTSTRING is not a colon. OPTERR has the value
1 by default.
57 Getopts normally parses the positional parameters
, but if arguments
58 are supplied as ARG values
, they are parsed instead.
61 Returns success if an option is found
; fails if the end of options is
62 encountered or an error occurs.
69 #if
defined (HAVE_UNISTD_H
)
71 # include
<sys
/types.h
>
76 #include
"../src/bushansi.h"
77 #include
"../src/bushintl.h"
79 #include
"../src/shell.h"
80 #include
"../src/runner/execute_cmd.h"
82 #include
"bushgetopt.h"
86 #define G_INVALID_OPT
-2
87 #define G_ARG_MISSING
-3
89 static int getopts_unbind_variable
PARAMS((char *)
);
90 static int getopts_bind_variable
PARAMS((char
*, char *)
);
91 static int dogetopts
PARAMS((int
, char
**)
);
93 /* getopts_reset is magic code for when OPTIND is reset. N is the
94 value that has just been assigned to OPTIND.
*/
96 getopts_reset (newind
)
104 getopts_unbind_variable (name
)
108 return (unbind_variable (name
));
110 return (unbind_variable_noref (name
));
115 getopts_bind_variable (name
, value
)
120 if (legal_identifier (name
))
122 v
= bind_variable (name
, value
, 0);
123 if (v
&& (readonly_p (v
) ||
noassign_p (v
)))
124 return (EX_MISCERROR
);
125 return (v ? EXECUTION_SUCCESS
: EXECUTION_FAILURE
);
130 return (EXECUTION_FAILURE
);
134 /* Error handling is now performed as specified by Posix
.2, draft
11
135 (identical to that of ksh
-88). The special handling is enabled if
136 the first character of the option string is a colon
; this handling
137 disables diagnostic messages concerning missing option arguments
138 and invalid option characters. The handling is as follows.
142 if (special_error
) then
143 OPTARG
= option character found
150 MISSING OPTION ARGUMENT
;
151 if (special_error
) then
153 OPTARG
= option character found
162 dogetopts (argc
, argv
)
166 int ret
, special_error
, old_opterr
, i
, n
;
167 char strval
[2], numval
[16];
168 char
*optstr
; /* list of options
*/
169 char
*name
; /* variable to get flag val
*/
178 /* argv
[0] is
"getopts".
*/
185 special_error
= optstr
[0] == ':';
189 old_opterr
= sh_opterr
;
191 sh_opterr
= 0; /* suppress diagnostic messages
*/
196 sh_getopt_restore_state (argv
);
198 argv
[0] = dollar_vars
[0];
199 ret
= sh_getopt (argc
, argv
, optstr
);
202 else
if (rest_of_args
== (WORD_LIST *)NULL
)
204 for (i
= 0; i
< 10 && dollar_vars
[i
]; i
++)
207 sh_getopt_restore_state (dollar_vars
);
208 ret
= sh_getopt (i
, dollar_vars
, optstr
);
212 register WORD_LIST
*words
;
215 i
= number_of_args () + 1; /* +1 for $
0 */
216 v
= strvec_create (i
+ 1);
217 for (i
= 0; i
< 10 && dollar_vars
[i
]; i
++)
218 v
[i
] = dollar_vars
[i
];
219 for (words
= rest_of_args
; words
; words
= words
->next
, i
++)
220 v
[i
] = words
->word
->word
;
222 sh_getopt_restore_state (v
);
223 ret
= sh_getopt (i
, v
, optstr
);
228 sh_opterr
= old_opterr
;
230 /* Set the OPTIND variable in any case
, to handle
"--" skipping. It
's
231 highly unlikely that 14 digits will be too few. */
234 numval[14] = sh_optind + '0';
240 numval[i = 15] = '\
0';
244 numval[--i] = (n % 10) + '0';
248 bind_variable ("OPTIND", numval + i, 0);
250 /* If an error occurred, decide which one it is and set the return
251 code appropriately. In all cases, the option character in error
252 is in OPTOPT. If an invalid option was encountered, OPTARG is
253 NULL. If a required option argument was missing, OPTARG points
254 to a NULL string (that is, sh_optarg[0] == 0). */
257 if (sh_optarg == NULL)
259 else if (sh_optarg[0] == '\
0')
265 getopts_unbind_variable ("OPTARG");
266 getopts_bind_variable (name, "?");
267 return (EXECUTION_FAILURE);
270 if (ret == G_INVALID_OPT)
272 /* Invalid option encountered. */
273 ret = getopts_bind_variable (name, "?");
277 strval[0] = (char)sh_optopt;
279 bind_variable ("OPTARG", strval, 0);
282 getopts_unbind_variable ("OPTARG");
287 if (ret == G_ARG_MISSING)
289 /* Required argument missing. */
292 ret = getopts_bind_variable (name, ":");
294 strval[0] = (char)sh_optopt;
296 bind_variable ("OPTARG", strval, 0);
300 ret = getopts_bind_variable (name, "?");
301 getopts_unbind_variable ("OPTARG");
306 bind_variable ("OPTARG", sh_optarg, 0);
308 strval[0] = (char) ret;
310 return (getopts_bind_variable (name, strval));
313 /* The getopts builtin. Build an argv, and call dogetopts with it. */
315 getopts_builtin (list)
327 reset_internal_getopt ();
328 if ((ret = internal_getopt (list, "")) != -1)
330 if (ret == GETOPT_HELP)
338 av = make_builtin_argv (list, &ac);
339 ret = dogetopts (ac, av);