]> git.ipfire.org Git - thirdparty/bash.git/blob - builtins/shopt.def
Imported from ../bash-4.0-rc1.tar.gz.
[thirdparty/bash.git] / builtins / shopt.def
1 This file is shopt.def, from which is created shopt.c.
2 It implements the Bash `shopt' builtin.
3
4 Copyright (C) 1994-2009 Free Software Foundation, Inc.
5
6 This file is part of GNU Bash, the Bourne Again SHell.
7
8 Bash 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.
12
13 Bash 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.
17
18 You should have received a copy of the GNU General Public License
19 along with Bash. If not, see <http://www.gnu.org/licenses/>.
20
21 $PRODUCES shopt.c
22
23 $BUILTIN shopt
24 $FUNCTION shopt_builtin
25 $SHORT_DOC shopt [-pqsu] [-o] [optname ...]
26 Set and unset shell options.
27
28 Change the setting of each shell option OPTNAME. Without any option
29 arguments, list all shell options with an indication of whether or not each
30 is set.
31
32 Options:
33 -o restrict OPTNAMEs to those defined for use with `set -o'
34 -p print each shell option with an indication of its status
35 -q suppress output
36 -s enable (set) each OPTNAME
37 -u disable (unset) each OPTNAME
38
39 Exit Status:
40 Returns success if OPTNAME is enabled; fails if an invalid option is
41 given or OPTNAME is disabled.
42 $END
43
44 #include <config.h>
45
46 #if defined (HAVE_UNISTD_H)
47 # ifdef _MINIX
48 # include <sys/types.h>
49 # endif
50 # include <unistd.h>
51 #endif
52
53 #include <stdio.h>
54
55 #include "version.h"
56
57 #include "../bashintl.h"
58
59 #include "../shell.h"
60 #include "../flags.h"
61 #include "common.h"
62 #include "bashgetopt.h"
63
64 #if defined (HISTORY)
65 # include "../bashhist.h"
66 #endif
67
68 #define UNSETOPT 0
69 #define SETOPT 1
70
71 #define OPTFMT "%-15s\t%s\n"
72
73 extern int allow_null_glob_expansion, fail_glob_expansion, glob_dot_filenames;
74 extern int cdable_vars, mail_warning, source_uses_path;
75 extern int no_exit_on_failed_exec, print_shift_error;
76 extern int check_hashed_filenames, promptvars;
77 extern int cdspelling, expand_aliases;
78 extern int extended_quote;
79 extern int check_window_size;
80 extern int glob_ignore_case, match_ignore_case;
81 extern int hup_on_exit;
82 extern int xpg_echo;
83 extern int gnu_error_format;
84 extern int check_jobs_at_exit;
85 extern int autocd;
86 extern int glob_star;
87
88 #if defined (EXTENDED_GLOB)
89 extern int extended_glob;
90 #endif
91
92 #if defined (READLINE)
93 extern int hist_verify, history_reediting, perform_hostname_completion;
94 extern int no_empty_command_completion;
95 extern int force_fignore;
96 extern int dircomplete_spelling;
97
98 extern int enable_hostname_completion __P((int));
99 #endif
100
101 #if defined (PROGRAMMABLE_COMPLETION)
102 extern int prog_completion_enabled;
103 #endif
104
105 #if defined (RESTRICTED_SHELL)
106 extern char *shell_name;
107 #endif
108
109 #if defined (DEBUGGER)
110 extern int debugging_mode;
111 #endif
112
113 static void shopt_error __P((char *));
114
115 static int set_shellopts_after_change __P((int));
116
117 static int set_compatibility_level __P((int));
118
119 #if defined (RESTRICTED_SHELL)
120 static int set_restricted_shell __P((int));
121 #endif
122
123 static int shopt_login_shell;
124 static int shopt_compat31;
125 static int shopt_compat32;
126
127 typedef int shopt_set_func_t __P((int));
128
129 static struct {
130 char *name;
131 int *value;
132 shopt_set_func_t *set_func;
133 } shopt_vars[] = {
134 { "autocd", &autocd, (shopt_set_func_t *)NULL },
135 { "cdable_vars", &cdable_vars, (shopt_set_func_t *)NULL },
136 { "cdspell", &cdspelling, (shopt_set_func_t *)NULL },
137 { "checkhash", &check_hashed_filenames, (shopt_set_func_t *)NULL },
138 #if defined (JOB_CONTROL)
139 { "checkjobs", &check_jobs_at_exit, (shopt_set_func_t *)NULL },
140 #endif
141 { "checkwinsize", &check_window_size, (shopt_set_func_t *)NULL },
142 #if defined (HISTORY)
143 { "cmdhist", &command_oriented_history, (shopt_set_func_t *)NULL },
144 #endif
145 { "compat31", &shopt_compat31, set_compatibility_level },
146 { "compat32", &shopt_compat32, set_compatibility_level },
147 #if defined (READLINE)
148 { "dirspell", &dircomplete_spelling, (shopt_set_func_t *)NULL },
149 #endif
150 { "dotglob", &glob_dot_filenames, (shopt_set_func_t *)NULL },
151 { "execfail", &no_exit_on_failed_exec, (shopt_set_func_t *)NULL },
152 { "expand_aliases", &expand_aliases, (shopt_set_func_t *)NULL },
153 #if defined (DEBUGGER)
154 { "extdebug", &debugging_mode, (shopt_set_func_t *)NULL },
155 #endif
156 #if defined (EXTENDED_GLOB)
157 { "extglob", &extended_glob, (shopt_set_func_t *)NULL },
158 #endif
159 { "extquote", &extended_quote, (shopt_set_func_t *)NULL },
160 { "failglob", &fail_glob_expansion, (shopt_set_func_t *)NULL },
161 #if defined (READLINE)
162 { "force_fignore", &force_fignore, (shopt_set_func_t *)NULL },
163 #endif
164 { "globstar", &glob_star, (shopt_set_func_t *)NULL },
165 { "gnu_errfmt", &gnu_error_format, (shopt_set_func_t *)NULL },
166 #if defined (HISTORY)
167 { "histappend", &force_append_history, (shopt_set_func_t *)NULL },
168 #endif
169 #if defined (READLINE)
170 { "histreedit", &history_reediting, (shopt_set_func_t *)NULL },
171 { "histverify", &hist_verify, (shopt_set_func_t *)NULL },
172 { "hostcomplete", &perform_hostname_completion, enable_hostname_completion },
173 #endif
174 { "huponexit", &hup_on_exit, (shopt_set_func_t *)NULL },
175 { "interactive_comments", &interactive_comments, set_shellopts_after_change },
176 #if defined (HISTORY)
177 { "lithist", &literal_history, (shopt_set_func_t *)NULL },
178 #endif
179 { "login_shell", &shopt_login_shell, set_login_shell },
180 { "mailwarn", &mail_warning, (shopt_set_func_t *)NULL },
181 #if defined (READLINE)
182 { "no_empty_cmd_completion", &no_empty_command_completion, (shopt_set_func_t *)NULL },
183 #endif
184 { "nocaseglob", &glob_ignore_case, (shopt_set_func_t *)NULL },
185 { "nocasematch", &match_ignore_case, (shopt_set_func_t *)NULL },
186 { "nullglob", &allow_null_glob_expansion, (shopt_set_func_t *)NULL },
187 #if defined (PROGRAMMABLE_COMPLETION)
188 { "progcomp", &prog_completion_enabled, (shopt_set_func_t *)NULL },
189 #endif
190 { "promptvars", &promptvars, (shopt_set_func_t *)NULL },
191 #if defined (RESTRICTED_SHELL)
192 { "restricted_shell", &restricted_shell, set_restricted_shell },
193 #endif
194 { "shift_verbose", &print_shift_error, (shopt_set_func_t *)NULL },
195 { "sourcepath", &source_uses_path, (shopt_set_func_t *)NULL },
196 { "xpg_echo", &xpg_echo, (shopt_set_func_t *)NULL },
197 { (char *)0, (int *)0, (shopt_set_func_t *)NULL }
198 };
199
200 static const char * const on = "on";
201 static const char * const off = "off";
202
203 static int find_shopt __P((char *));
204 static int toggle_shopts __P((int, WORD_LIST *, int));
205 static void print_shopt __P((char *, int, int));
206 static int list_shopts __P((WORD_LIST *, int));
207 static int list_some_shopts __P((int, int));
208 static int list_shopt_o_options __P((WORD_LIST *, int));
209 static int list_some_o_options __P((int, int));
210 static int set_shopt_o_options __P((int, WORD_LIST *, int));
211
212 #define SFLAG 0x01
213 #define UFLAG 0x02
214 #define QFLAG 0x04
215 #define OFLAG 0x08
216 #define PFLAG 0x10
217
218 int
219 shopt_builtin (list)
220 WORD_LIST *list;
221 {
222 int opt, flags, rval;
223
224 flags = 0;
225 reset_internal_getopt ();
226 while ((opt = internal_getopt (list, "psuoq")) != -1)
227 {
228 switch (opt)
229 {
230 case 's':
231 flags |= SFLAG;
232 break;
233 case 'u':
234 flags |= UFLAG;
235 break;
236 case 'q':
237 flags |= QFLAG;
238 break;
239 case 'o':
240 flags |= OFLAG;
241 break;
242 case 'p':
243 flags |= PFLAG;
244 break;
245 default:
246 builtin_usage ();
247 return (EX_USAGE);
248 }
249 }
250 list = loptend;
251
252 if ((flags & (SFLAG|UFLAG)) == (SFLAG|UFLAG))
253 {
254 builtin_error (_("cannot set and unset shell options simultaneously"));
255 return (EXECUTION_FAILURE);
256 }
257
258 rval = EXECUTION_SUCCESS;
259 if ((flags & OFLAG) && ((flags & (SFLAG|UFLAG)) == 0)) /* shopt -o */
260 rval = list_shopt_o_options (list, flags);
261 else if (list && (flags & OFLAG)) /* shopt -so args */
262 rval = set_shopt_o_options ((flags & SFLAG) ? FLAG_ON : FLAG_OFF, list, flags & QFLAG);
263 else if (flags & OFLAG) /* shopt -so */
264 rval = list_some_o_options ((flags & SFLAG) ? 1 : 0, flags);
265 else if (list && (flags & (SFLAG|UFLAG))) /* shopt -su args */
266 rval = toggle_shopts ((flags & SFLAG) ? SETOPT : UNSETOPT, list, flags & QFLAG);
267 else if ((flags & (SFLAG|UFLAG)) == 0) /* shopt [args] */
268 rval = list_shopts (list, flags);
269 else /* shopt -su */
270 rval = list_some_shopts ((flags & SFLAG) ? SETOPT : UNSETOPT, flags);
271 return (rval);
272 }
273
274 /* Reset the options managed by `shopt' to the values they would have at
275 shell startup. */
276 void
277 reset_shopt_options ()
278 {
279 allow_null_glob_expansion = glob_dot_filenames = 0;
280 cdable_vars = mail_warning = 0;
281 no_exit_on_failed_exec = print_shift_error = 0;
282 check_hashed_filenames = cdspelling = expand_aliases = check_window_size = 0;
283
284 source_uses_path = promptvars = 1;
285
286 #if defined (EXTENDED_GLOB)
287 extended_glob = 0;
288 #endif
289
290 #if defined (HISTORY)
291 literal_history = force_append_history = 0;
292 command_oriented_history = 1;
293 #endif
294
295 #if defined (READLINE)
296 hist_verify = history_reediting = 0;
297 perform_hostname_completion = 1;
298 #endif
299
300 shopt_login_shell = login_shell;
301 }
302
303 static int
304 find_shopt (name)
305 char *name;
306 {
307 int i;
308
309 for (i = 0; shopt_vars[i].name; i++)
310 if (STREQ (name, shopt_vars[i].name))
311 return i;
312 return -1;
313 }
314
315 static void
316 shopt_error (s)
317 char *s;
318 {
319 builtin_error (_("%s: invalid shell option name"), s);
320 }
321
322 static int
323 toggle_shopts (mode, list, quiet)
324 int mode;
325 WORD_LIST *list;
326 int quiet;
327 {
328 WORD_LIST *l;
329 int ind, rval;
330
331 for (l = list, rval = EXECUTION_SUCCESS; l; l = l->next)
332 {
333 ind = find_shopt (l->word->word);
334 if (ind < 0)
335 {
336 shopt_error (l->word->word);
337 rval = EXECUTION_FAILURE;
338 }
339 else
340 {
341 *shopt_vars[ind].value = mode; /* 1 for set, 0 for unset */
342 if (shopt_vars[ind].set_func)
343 (*shopt_vars[ind].set_func) (mode);
344 }
345 }
346 return (rval);
347 }
348
349 static void
350 print_shopt (name, val, flags)
351 char *name;
352 int val, flags;
353 {
354 if (flags & PFLAG)
355 printf ("shopt %s %s\n", val ? "-s" : "-u", name);
356 else
357 printf (OPTFMT, name, val ? on : off);
358 }
359
360 /* List the values of all or any of the `shopt' options. Returns 0 if
361 all were listed or all variables queried were on; 1 otherwise. */
362 static int
363 list_shopts (list, flags)
364 WORD_LIST *list;
365 int flags;
366 {
367 WORD_LIST *l;
368 int i, val, rval;
369
370 if (list == 0)
371 {
372 for (i = 0; shopt_vars[i].name; i++)
373 {
374 val = *shopt_vars[i].value;
375 if ((flags & QFLAG) == 0)
376 print_shopt (shopt_vars[i].name, val, flags);
377 }
378 return (sh_chkwrite (EXECUTION_SUCCESS));
379 }
380
381 for (l = list, rval = EXECUTION_SUCCESS; l; l = l->next)
382 {
383 i = find_shopt (l->word->word);
384 if (i < 0)
385 {
386 shopt_error (l->word->word);
387 rval = EXECUTION_FAILURE;
388 continue;
389 }
390 val = *shopt_vars[i].value;
391 if (val == 0)
392 rval = EXECUTION_FAILURE;
393 if ((flags & QFLAG) == 0)
394 print_shopt (l->word->word, val, flags);
395 }
396
397 return (sh_chkwrite (rval));
398 }
399
400 static int
401 list_some_shopts (mode, flags)
402 int mode, flags;
403 {
404 int val, i;
405
406 for (i = 0; shopt_vars[i].name; i++)
407 {
408 val = *shopt_vars[i].value;
409 if (((flags & QFLAG) == 0) && mode == val)
410 print_shopt (shopt_vars[i].name, val, flags);
411 }
412 return (sh_chkwrite (EXECUTION_SUCCESS));
413 }
414
415 static int
416 list_shopt_o_options (list, flags)
417 WORD_LIST *list;
418 int flags;
419 {
420 WORD_LIST *l;
421 int val, rval;
422
423 if (list == 0)
424 {
425 if ((flags & QFLAG) == 0)
426 list_minus_o_opts (-1, (flags & PFLAG));
427 return (sh_chkwrite (EXECUTION_SUCCESS));
428 }
429
430 for (l = list, rval = EXECUTION_SUCCESS; l; l = l->next)
431 {
432 val = minus_o_option_value (l->word->word);
433 if (val == -1)
434 {
435 sh_invalidoptname (l->word->word);
436 rval = EXECUTION_FAILURE;
437 continue;
438 }
439 if (val == 0)
440 rval = EXECUTION_FAILURE;
441 if ((flags & QFLAG) == 0)
442 {
443 if (flags & PFLAG)
444 printf ("set %co %s\n", val ? '-' : '+', l->word->word);
445 else
446 printf (OPTFMT, l->word->word, val ? on : off);
447 }
448 }
449 return (sh_chkwrite (rval));
450 }
451
452 static int
453 list_some_o_options (mode, flags)
454 int mode, flags;
455 {
456 if ((flags & QFLAG) == 0)
457 list_minus_o_opts (mode, (flags & PFLAG));
458 return (sh_chkwrite (EXECUTION_SUCCESS));
459 }
460
461 static int
462 set_shopt_o_options (mode, list, quiet)
463 int mode;
464 WORD_LIST *list;
465 int quiet;
466 {
467 WORD_LIST *l;
468 int rval;
469
470 for (l = list, rval = EXECUTION_SUCCESS; l; l = l->next)
471 {
472 if (set_minus_o_option (mode, l->word->word) == EXECUTION_FAILURE)
473 rval = EXECUTION_FAILURE;
474 }
475 set_shellopts ();
476 return rval;
477 }
478
479 /* If we set or unset interactive_comments with shopt, make sure the
480 change is reflected in $SHELLOPTS. */
481 static int
482 set_shellopts_after_change (mode)
483 int mode;
484 {
485 set_shellopts ();
486 return (0);
487 }
488
489 static int
490 set_compatibility_level (mode)
491 int mode;
492 {
493 /* Need to change logic here as we add more compatibility levels */
494 if (shopt_compat31)
495 shell_compatibility_level = 31;
496 else if (shopt_compat32)
497 shell_compatibility_level = 32;
498 else
499 shell_compatibility_level = DEFAULT_COMPAT_LEVEL;
500 return 0;
501 }
502
503 #if defined (RESTRICTED_SHELL)
504 /* Don't allow the value of restricted_shell to be modified. */
505
506 static int
507 set_restricted_shell (mode)
508 int mode;
509 {
510 static int save_restricted = -1;
511
512 if (save_restricted == -1)
513 save_restricted = shell_is_restricted (shell_name);
514
515 restricted_shell = save_restricted;
516 return (0);
517 }
518 #endif /* RESTRICTED_SHELL */
519
520 /* Not static so shell.c can call it to initialize shopt_login_shell */
521 int
522 set_login_shell (mode)
523 int mode;
524 {
525 shopt_login_shell = login_shell != 0;
526 return (0);
527 }
528
529 char **
530 get_shopt_options ()
531 {
532 char **ret;
533 int n, i;
534
535 n = sizeof (shopt_vars) / sizeof (shopt_vars[0]);
536 ret = strvec_create (n + 1);
537 for (i = 0; shopt_vars[i].name; i++)
538 ret[i] = savestring (shopt_vars[i].name);
539 ret[i] = (char *)NULL;
540 return ret;
541 }
542
543 /*
544 * External interface for other parts of the shell. NAME is a string option;
545 * MODE is 0 if we want to unset an option; 1 if we want to set an option.
546 * REUSABLE is 1 if we want to print output in a form that may be reused.
547 */
548 int
549 shopt_setopt (name, mode)
550 char *name;
551 int mode;
552 {
553 WORD_LIST *wl;
554 int r;
555
556 wl = add_string_to_list (name, (WORD_LIST *)NULL);
557 r = toggle_shopts (mode, wl, 0);
558 dispose_words (wl);
559 return r;
560 }
561
562 int
563 shopt_listopt (name, reusable)
564 char *name;
565 int reusable;
566 {
567 int i;
568
569 if (name == 0)
570 return (list_shopts ((WORD_LIST *)NULL, reusable ? PFLAG : 0));
571
572 i = find_shopt (name);
573 if (i < 0)
574 {
575 shopt_error (name);
576 return (EXECUTION_FAILURE);
577 }
578
579 print_shopt (name, *shopt_vars[i].value, reusable ? PFLAG : 0);
580 return (sh_chkwrite (EXECUTION_SUCCESS));
581 }