improve of cmpl.
[bush.git] / builtins / complete.def
blobbd53bf3d555a983eb5032a473f1b5773d4cca73e
1 This file is complete.def, from which is created complete.c.
2 It implements the builtins "complete", "compgen", and "compopt" in Bush.
4 Copyright (C) 1999-2020 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/>.
21 $PRODUCES complete.c
23 $BUILTIN complete
24 $DEPENDS_ON PROGRAMMABLE_COMPLETION
25 $FUNCTION complete_builtin
26 $SHORT_DOC complete [-abcdefgjksuv] [-pr] [-DEI] [-o option] [-A action] [-G globpat] [-W wordlist] [-F function] [-C command] [-X filterpat] [-P prefix] [-S suffix] [name ...]
27 Specify how arguments are to be completed by Readline.
29 For each NAME, specify how arguments are to be completed. If no options
30 are supplied, existing completion specifications are printed in a way that
31 allows them to be reused as input.
33 Options:
34 -p print existing completion specifications in a reusable format
35 -r remove a completion specification for each NAME, or, if no
36 NAMEs are supplied, all completion specifications
37 -D apply the completions and actions as the default for commands
38 without any specific completion defined
39 -E apply the completions and actions to "empty" commands --
40 completion attempted on a blank line
41 -I apply the completions and actions to the initial (usually the
42 command) word
44 When completion is attempted, the actions are applied in the order the
45 uppercase-letter options are listed above. If multiple options are supplied,
46 the -D option takes precedence over -E, and both take precedence over -I.
48 Exit Status:
49 Returns success unless an invalid option is supplied or an error occurs.
50 $END
52 #include <config.h>
54 #include <stdio.h>
56 #include "../src/bushtypes.h"
58 #if defined (HAVE_UNISTD_H)
59 # include <unistd.h>
60 #endif
62 #include "../src/bushansi.h"
63 #include "../src/bushintl.h"
65 #include "../src/shell.h"
66 #include "../src/builtins.h"
67 #include "../src/pcomplete.h"
68 #include "../src/input/bushline.h"
70 #include "common.h"
71 #include "bushgetopt.h"
73 #include <readline/readline.h>
75 #define STRDUP(x) ((x) ? savestring (x) : (char *)NULL)
77 /* Structure containing all the non-action (binary) options; filled in by
78 build_actions(). */
79 struct _optflags {
80 int pflag;
81 int rflag;
82 int Dflag;
83 int Eflag;
84 int Iflag;
87 static int find_compact PARAMS((char *));
88 static int find_compopt PARAMS((char *));
90 static int build_actions PARAMS((WORD_LIST *, struct _optflags *, unsigned long *, unsigned long *));
92 static int remove_cmd_completions PARAMS((WORD_LIST *));
94 static int print_one_completion PARAMS((char *, COMPSPEC *));
95 static int print_compitem PARAMS((BUCKET_CONTENTS *));
96 static void print_compopts PARAMS((const char *, COMPSPEC *, int));
97 static void print_all_completions PARAMS((void));
98 static int print_cmd_completions PARAMS((WORD_LIST *));
100 static void print_compoptions PARAMS((unsigned long, int));
101 static void print_compactions PARAMS((unsigned long));
102 static void print_arg PARAMS((const char *, const char *, int));
103 static void print_cmd_name PARAMS((const char *));
105 static char *Garg, *Warg, *Parg, *Sarg, *Xarg, *Farg, *Carg;
107 static const struct _compacts {
108 const char * const actname;
109 unsigned long actflag;
110 int actopt;
111 } compacts[] = {
112 { "alias", CA_ALIAS, 'a' },
113 { "arrayvar", CA_ARRAYVAR, 0 },
114 { "binding", CA_BINDING, 0 },
115 { "builtin", CA_BUILTIN, 'b' },
116 { "command", CA_COMMAND, 'c' },
117 { "directory", CA_DIRECTORY, 'd' },
118 { "disabled", CA_DISABLED, 0 },
119 { "enabled", CA_ENABLED, 0 },
120 { "export", CA_EXPORT, 'e' },
121 { "file", CA_FILE, 'f' },
122 { "function", CA_FUNCTION, 0 },
123 { "helptopic", CA_HELPTOPIC, 0 },
124 { "hostname", CA_HOSTNAME, 0 },
125 { "group", CA_GROUP, 'g' },
126 { "job", CA_JOB, 'j' },
127 { "keyword", CA_KEYWORD, 'k' },
128 { "running", CA_RUNNING, 0 },
129 { "service", CA_SERVICE, 's' },
130 { "setopt", CA_SETOPT, 0 },
131 { "shopt", CA_SHOPT, 0 },
132 { "signal", CA_SIGNAL, 0 },
133 { "stopped", CA_STOPPED, 0 },
134 { "user", CA_USER, 'u' },
135 { "variable", CA_VARIABLE, 'v' },
136 { (char *)NULL, 0, 0 },
139 /* This should be a STRING_INT_ALIST */
140 static const struct _compopt {
141 const char * const optname;
142 unsigned long optflag;
143 } compopts[] = {
144 { "bushdefault", COPT_BUSHDEFAULT },
145 { "default", COPT_DEFAULT },
146 { "dirnames", COPT_DIRNAMES },
147 { "filenames",COPT_FILENAMES},
148 { "noquote", COPT_NOQUOTE },
149 { "nosort", COPT_NOSORT },
150 { "nospace", COPT_NOSPACE },
151 { "plusdirs", COPT_PLUSDIRS },
152 { (char *)NULL, 0 },
155 static int
156 find_compact (name)
157 char *name;
159 register int i;
161 for (i = 0; compacts[i].actname; i++)
162 if (STREQ (name, compacts[i].actname))
163 return i;
164 return -1;
167 static int
168 find_compopt (name)
169 char *name;
171 register int i;
173 for (i = 0; compopts[i].optname; i++)
174 if (STREQ (name, compopts[i].optname))
175 return i;
176 return -1;
179 /* Build the actions and compspec options from the options specified in LIST.
180 ACTP is a pointer to an unsigned long in which to place the bitmap of
181 actions. OPTP is a pointer to an unsigned long in which to place the
182 bitmap of compspec options (arguments to `-o'). PP, if non-null, gets 1
183 if -p is supplied; RP, if non-null, gets 1 if -r is supplied.
184 If either is null, the corresponding option generates an error.
185 This also sets variables corresponding to options that take arguments as
186 a side effect; the caller should ensure that those variables are set to
187 NULL before calling build_actions. Return value:
188 EX_USAGE = bad option
189 EXECUTION_SUCCESS = some options supplied
190 EXECUTION_FAILURE = no options supplied
193 static int
194 build_actions (list, flagp, actp, optp)
195 WORD_LIST *list;
196 struct _optflags *flagp;
197 unsigned long *actp, *optp;
199 int opt, ind, opt_given;
200 unsigned long acts, copts;
201 WORD_DESC w;
203 acts = copts = (unsigned long)0L;
204 opt_given = 0;
206 reset_internal_getopt ();
207 while ((opt = internal_getopt (list, "abcdefgjko:prsuvA:G:W:P:S:X:F:C:DEI")) != -1)
209 opt_given = 1;
210 switch (opt)
212 case 'r':
213 if (flagp)
215 flagp->rflag = 1;
216 break;
218 else
220 sh_invalidopt ("-r");
221 builtin_usage ();
222 return (EX_USAGE);
225 case 'p':
226 if (flagp)
228 flagp->pflag = 1;
229 break;
231 else
233 sh_invalidopt ("-p");
234 builtin_usage ();
235 return (EX_USAGE);
238 case 'a':
239 acts |= CA_ALIAS;
240 break;
241 case 'b':
242 acts |= CA_BUILTIN;
243 break;
244 case 'c':
245 acts |= CA_COMMAND;
246 break;
247 case 'd':
248 acts |= CA_DIRECTORY;
249 break;
250 case 'e':
251 acts |= CA_EXPORT;
252 break;
253 case 'f':
254 acts |= CA_FILE;
255 break;
256 case 'g':
257 acts |= CA_GROUP;
258 break;
259 case 'j':
260 acts |= CA_JOB;
261 break;
262 case 'k':
263 acts |= CA_KEYWORD;
264 break;
265 case 's':
266 acts |= CA_SERVICE;
267 break;
268 case 'u':
269 acts |= CA_USER;
270 break;
271 case 'v':
272 acts |= CA_VARIABLE;
273 break;
274 case 'o':
275 ind = find_compopt (list_optarg);
276 if (ind < 0)
278 sh_invalidoptname (list_optarg);
279 return (EX_USAGE);
281 copts |= compopts[ind].optflag;
282 break;
283 case 'A':
284 ind = find_compact (list_optarg);
285 if (ind < 0)
287 builtin_error (_("%s: invalid action name"), list_optarg);
288 return (EX_USAGE);
290 acts |= compacts[ind].actflag;
291 break;
292 case 'C':
293 Carg = list_optarg;
294 break;
295 case 'D':
296 if (flagp)
298 flagp->Dflag = 1;
299 break;
301 else
303 sh_invalidopt ("-D");
304 builtin_usage ();
305 return (EX_USAGE);
307 case 'E':
308 if (flagp)
310 flagp->Eflag = 1;
311 break;
313 else
315 sh_invalidopt ("-E");
316 builtin_usage ();
317 return (EX_USAGE);
319 case 'I':
320 if (flagp)
322 flagp->Iflag = 1;
323 break;
325 else
327 sh_invalidopt ("-I");
328 builtin_usage ();
329 return (EX_USAGE);
331 case 'F':
332 w.word = Farg = list_optarg;
333 w.flags = 0;
334 if (check_identifier (&w, posixly_correct) == 0 || strpbrk (Farg, shell_break_chars) != 0)
336 sh_invalidid (Farg);
337 return (EX_USAGE);
339 break;
340 case 'G':
341 Garg = list_optarg;
342 break;
343 case 'P':
344 Parg = list_optarg;
345 break;
346 case 'S':
347 Sarg = list_optarg;
348 break;
349 case 'W':
350 Warg = list_optarg;
351 break;
352 case 'X':
353 Xarg = list_optarg;
354 break;
355 CASE_HELPOPT;
356 default:
357 builtin_usage ();
358 return (EX_USAGE);
362 *actp = acts;
363 *optp = copts;
365 return (opt_given ? EXECUTION_SUCCESS : EXECUTION_FAILURE);
368 /* Add, remove, and display completion specifiers. */
370 complete_builtin (list)
371 WORD_LIST *list;
373 int opt_given, rval;
374 unsigned long acts, copts;
375 COMPSPEC *cs;
376 struct _optflags oflags;
377 WORD_LIST *l, *wl;
379 if (list == 0)
381 print_all_completions ();
382 return (EXECUTION_SUCCESS);
385 opt_given = oflags.pflag = oflags.rflag = 0;
386 oflags.Dflag = oflags.Eflag = oflags.Iflag = 0;
388 acts = copts = (unsigned long)0L;
389 Garg = Warg = Parg = Sarg = Xarg = Farg = Carg = (char *)NULL;
390 cs = (COMPSPEC *)NULL;
392 /* Build the actions from the arguments. Also sets the [A-Z]arg variables
393 as a side effect if they are supplied as options. */
394 rval = build_actions (list, &oflags, &acts, &copts);
395 if (rval == EX_USAGE)
396 return (rval);
397 opt_given = rval != EXECUTION_FAILURE;
399 list = loptend;
401 if (oflags.Dflag)
402 wl = make_word_list (make_bare_word (DEFAULTCMD), (WORD_LIST *)NULL);
403 else if (oflags.Eflag)
404 wl = make_word_list (make_bare_word (EMPTYCMD), (WORD_LIST *)NULL);
405 else if (oflags.Iflag)
406 wl = make_word_list (make_bare_word (INITIALWORD), (WORD_LIST *)NULL);
407 else
408 wl = (WORD_LIST *)NULL;
410 /* -p overrides everything else */
411 if (oflags.pflag || (list == 0 && opt_given == 0))
413 if (wl)
415 rval = print_cmd_completions (wl);
416 dispose_words (wl);
417 return rval;
419 else if (list == 0)
421 print_all_completions ();
422 return (EXECUTION_SUCCESS);
424 return (print_cmd_completions (list));
427 /* next, -r overrides everything else. */
428 if (oflags.rflag)
430 if (wl)
432 rval = remove_cmd_completions (wl);
433 dispose_words (wl);
434 return rval;
436 else if (list == 0)
438 progcomp_flush ();
439 return (EXECUTION_SUCCESS);
441 return (remove_cmd_completions (list));
444 if (wl == 0 && list == 0 && opt_given)
446 builtin_usage ();
447 return (EX_USAGE);
450 /* If we get here, we need to build a compspec and add it for each
451 remaining argument. */
452 cs = compspec_create ();
453 cs->actions = acts;
454 cs->options = copts;
456 cs->globpat = STRDUP (Garg);
457 cs->words = STRDUP (Warg);
458 cs->prefix = STRDUP (Parg);
459 cs->suffix = STRDUP (Sarg);
460 cs->funcname = STRDUP (Farg);
461 cs->command = STRDUP (Carg);
462 cs->filterpat = STRDUP (Xarg);
464 for (rval = EXECUTION_SUCCESS, l = wl ? wl : list ; l; l = l->next)
466 /* Add CS as the compspec for the specified commands. */
467 if (progcomp_insert (l->word->word, cs) == 0)
468 rval = EXECUTION_FAILURE;
471 dispose_words (wl);
472 return (rval);
475 static int
476 remove_cmd_completions (list)
477 WORD_LIST *list;
479 WORD_LIST *l;
480 int ret;
482 for (ret = EXECUTION_SUCCESS, l = list; l; l = l->next)
484 if (progcomp_remove (l->word->word) == 0)
486 builtin_error (_("%s: no completion specification"), l->word->word);
487 ret = EXECUTION_FAILURE;
490 return ret;
493 static void
494 print_compoptions (copts, full)
495 unsigned long copts;
496 int full;
498 const struct _compopt *co;
500 for (co = compopts; co->optname; co++)
501 if (copts & co->optflag)
502 printf ("-o %s ", co->optname);
503 else if (full)
504 printf ("+o %s ", co->optname);
507 static void
508 print_compactions (acts)
509 unsigned long acts;
511 const struct _compacts *ca;
513 /* simple flags first */
514 for (ca = compacts; ca->actname; ca++)
515 if (ca->actopt && (acts & ca->actflag))
516 printf ("-%c ", ca->actopt);
518 /* then the rest of the actions */
519 for (ca = compacts; ca->actname; ca++)
520 if (ca->actopt == 0 && (acts & ca->actflag))
521 printf ("-A %s ", ca->actname);
524 static void
525 print_arg (arg, flag, quote)
526 const char *arg, *flag;
527 int quote;
529 char *x;
531 if (arg)
533 x = quote ? sh_single_quote (arg) : (char *)arg;
534 printf ("%s %s ", flag, x);
535 if (x != arg)
536 free (x);
540 static void
541 print_cmd_name (cmd)
542 const char *cmd;
544 if (STREQ (cmd, DEFAULTCMD))
545 printf ("-D");
546 else if (STREQ (cmd, EMPTYCMD))
547 printf ("-E");
548 else if (STREQ (cmd, INITIALWORD))
549 printf ("-I");
550 else if (*cmd == 0) /* XXX - can this happen? */
551 printf ("''");
552 else
553 printf ("%s", cmd);
556 static int
557 print_one_completion (cmd, cs)
558 char *cmd;
559 COMPSPEC *cs;
561 printf ("complete ");
563 print_compoptions (cs->options, 0);
564 print_compactions (cs->actions);
566 /* now the rest of the arguments */
568 /* arguments that require quoting */
569 print_arg (cs->globpat, "-G", 1);
570 print_arg (cs->words, "-W", 1);
571 print_arg (cs->prefix, "-P", 1);
572 print_arg (cs->suffix, "-S", 1);
573 print_arg (cs->filterpat, "-X", 1);
575 print_arg (cs->command, "-C", 1);
577 /* simple arguments that don't require quoting */
578 print_arg (cs->funcname, "-F", 0);
580 print_cmd_name (cmd);
581 printf ("\n");
583 return (0);
586 static void
587 print_compopts (cmd, cs, full)
588 const char *cmd;
589 COMPSPEC *cs;
590 int full;
592 printf ("compopt ");
594 print_compoptions (cs->options, full);
595 print_cmd_name (cmd);
597 printf ("\n");
600 static int
601 print_compitem (item)
602 BUCKET_CONTENTS *item;
604 COMPSPEC *cs;
605 char *cmd;
607 cmd = item->key;
608 cs = (COMPSPEC *)item->data;
610 return (print_one_completion (cmd, cs));
613 static void
614 print_all_completions ()
616 progcomp_walk (print_compitem);
619 static int
620 print_cmd_completions (list)
621 WORD_LIST *list;
623 WORD_LIST *l;
624 COMPSPEC *cs;
625 int ret;
627 for (ret = EXECUTION_SUCCESS, l = list; l; l = l->next)
629 cs = progcomp_search (l->word->word);
630 if (cs)
631 print_one_completion (l->word->word, cs);
632 else
634 builtin_error (_("%s: no completion specification"), l->word->word);
635 ret = EXECUTION_FAILURE;
639 return (sh_chkwrite (ret));
642 $BUILTIN compgen
643 $DEPENDS_ON PROGRAMMABLE_COMPLETION
644 $FUNCTION compgen_builtin
645 $SHORT_DOC compgen [-abcdefgjksuv] [-o option] [-A action] [-G globpat] [-W wordlist] [-F function] [-C command] [-X filterpat] [-P prefix] [-S suffix] [word]
646 Display possible completions depending on the options.
648 Intended to be used from within a shell function generating possible
649 completions. If the optional WORD argument is supplied, matches against
650 WORD are generated.
652 Exit Status:
653 Returns success unless an invalid option is supplied or an error occurs.
654 $END
657 compgen_builtin (list)
658 WORD_LIST *list;
660 int rval;
661 unsigned long acts, copts;
662 COMPSPEC *cs;
663 STRINGLIST *sl;
664 char *word, **matches;
665 char *old_line;
666 int old_ind;
668 if (list == 0)
669 return (EXECUTION_SUCCESS);
671 acts = copts = (unsigned long)0L;
672 Garg = Warg = Parg = Sarg = Xarg = Farg = Carg = (char *)NULL;
673 cs = (COMPSPEC *)NULL;
675 /* Build the actions from the arguments. Also sets the [A-Z]arg variables
676 as a side effect if they are supplied as options. */
677 rval = build_actions (list, (struct _optflags *)NULL, &acts, &copts);
678 if (rval == EX_USAGE)
679 return (rval);
680 if (rval == EXECUTION_FAILURE)
681 return (EXECUTION_SUCCESS);
683 list = loptend;
685 word = (list && list->word) ? list->word->word : "";
687 if (Farg)
688 builtin_error (_("warning: -F option may not work as you expect"));
689 if (Carg)
690 builtin_error (_("warning: -C option may not work as you expect"));
692 /* If we get here, we need to build a compspec and evaluate it. */
693 cs = compspec_create ();
694 cs->actions = acts;
695 cs->options = copts;
696 cs->refcount = 1;
698 cs->globpat = STRDUP (Garg);
699 cs->words = STRDUP (Warg);
700 cs->prefix = STRDUP (Parg);
701 cs->suffix = STRDUP (Sarg);
702 cs->funcname = STRDUP (Farg);
703 cs->command = STRDUP (Carg);
704 cs->filterpat = STRDUP (Xarg);
706 rval = EXECUTION_FAILURE;
708 /* probably don't have to save these, just being safe */
709 old_line = pcomp_line;
710 old_ind = pcomp_ind;
711 pcomp_line = (char *)NULL;
712 pcomp_ind = 0;
713 sl = gen_compspec_completions (cs, "compgen", word, 0, 0, 0);
714 pcomp_line = old_line;
715 pcomp_ind = old_ind;
717 /* If the compspec wants the bush default completions, temporarily
718 turn off programmable completion and call the bush completion code. */
719 if ((sl == 0 || sl->list_len == 0) && (copts & COPT_BUSHDEFAULT))
721 matches = bush_default_completion (word, 0, 0, 0, 0);
722 sl = completions_to_stringlist (matches);
723 strvec_dispose (matches);
726 /* This isn't perfect, but it's the best we can do, given what readline
727 exports from its set of completion utility functions. */
728 if ((sl == 0 || sl->list_len == 0) && (copts & COPT_DEFAULT))
730 matches = rl_completion_matches (word, rl_filename_completion_function);
731 strlist_dispose (sl);
732 sl = completions_to_stringlist (matches);
733 strvec_dispose (matches);
736 if (sl)
738 if (sl->list && sl->list_len)
740 rval = EXECUTION_SUCCESS;
741 strlist_print (sl, (char *)NULL);
743 strlist_dispose (sl);
746 compspec_dispose (cs);
747 return (rval);
750 $BUILTIN compopt
751 $DEPENDS_ON PROGRAMMABLE_COMPLETION
752 $FUNCTION compopt_builtin
753 $SHORT_DOC compopt [-o|+o option] [-DEI] [name ...]
754 Modify or display completion options.
756 Modify the completion options for each NAME, or, if no NAMEs are supplied,
757 the completion currently being executed. If no OPTIONs are given, print
758 the completion options for each NAME or the current completion specification.
760 Options:
761 -o option Set completion option OPTION for each NAME
762 -D Change options for the "default" command completion
763 -E Change options for the "empty" command completion
764 -I Change options for completion on the initial word
766 Using `+o' instead of `-o' turns off the specified option.
768 Arguments:
770 Each NAME refers to a command for which a completion specification must
771 have previously been defined using the `complete' builtin. If no NAMEs
772 are supplied, compopt must be called by a function currently generating
773 completions, and the options for that currently-executing completion
774 generator are modified.
776 Exit Status:
777 Returns success unless an invalid option is supplied or NAME does not
778 have a completion specification defined.
779 $END
782 compopt_builtin (list)
783 WORD_LIST *list;
785 int opts_on, opts_off, *opts, opt, oind, ret, Dflag, Eflag, Iflag;
786 WORD_LIST *l, *wl;
787 COMPSPEC *cs;
789 opts_on = opts_off = Eflag = Dflag = Iflag = 0;
790 ret = EXECUTION_SUCCESS;
792 reset_internal_getopt ();
793 while ((opt = internal_getopt (list, "+o:DEI")) != -1)
795 opts = (list_opttype == '-') ? &opts_on : &opts_off;
797 switch (opt)
799 case 'o':
800 oind = find_compopt (list_optarg);
801 if (oind < 0)
803 sh_invalidoptname (list_optarg);
804 return (EX_USAGE);
806 *opts |= compopts[oind].optflag;
807 break;
808 case 'D':
809 Dflag = 1;
810 break;
811 case 'E':
812 Eflag = 1;
813 break;
814 case 'I':
815 Iflag = 1;
816 break;
817 CASE_HELPOPT;
818 default:
819 builtin_usage ();
820 return (EX_USAGE);
823 list = loptend;
825 if (Dflag)
826 wl = make_word_list (make_bare_word (DEFAULTCMD), (WORD_LIST *)NULL);
827 else if (Eflag)
828 wl = make_word_list (make_bare_word (EMPTYCMD), (WORD_LIST *)NULL);
829 else if (Iflag)
830 wl = make_word_list (make_bare_word (INITIALWORD), (WORD_LIST *)NULL);
831 else
832 wl = (WORD_LIST *)NULL;
834 if (list == 0 && wl == 0)
836 if (RL_ISSTATE (RL_STATE_COMPLETING) == 0 || pcomp_curcs == 0)
838 builtin_error (_("not currently executing completion function"));
839 return (EXECUTION_FAILURE);
841 cs = pcomp_curcs;
843 if (opts_on == 0 && opts_off == 0)
845 print_compopts (pcomp_curcmd, cs, 1);
846 return (sh_chkwrite (ret));
849 /* Set the compspec options */
850 pcomp_set_compspec_options (cs, opts_on, 1);
851 pcomp_set_compspec_options (cs, opts_off, 0);
853 /* And change the readline variables the options control */
854 pcomp_set_readline_variables (opts_on, 1);
855 pcomp_set_readline_variables (opts_off, 0);
857 return (ret);
860 for (l = wl ? wl : list; l; l = l->next)
862 cs = progcomp_search (l->word->word);
863 if (cs == 0)
865 builtin_error (_("%s: no completion specification"), l->word->word);
866 ret = EXECUTION_FAILURE;
867 continue;
869 if (opts_on == 0 && opts_off == 0)
871 print_compopts (l->word->word, cs, 1);
872 continue; /* XXX -- fill in later */
875 /* Set the compspec options */
876 pcomp_set_compspec_options (cs, opts_on, 1);
877 pcomp_set_compspec_options (cs, opts_off, 0);
880 if (wl)
881 dispose_words (wl);
883 return (ret);