Release 2.33.1
[external/binutils.git] / readline / histexpand.c
1 /* histexpand.c -- history expansion. */
2
3 /* Copyright (C) 1989-2018 Free Software Foundation, Inc.
4
5    This file contains the GNU History Library (History), a set of
6    routines for managing the text of previously typed lines.
7
8    History 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    History 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 History.  If not, see <http://www.gnu.org/licenses/>.
20 */
21
22 #define READLINE_LIBRARY
23
24 #if defined (HAVE_CONFIG_H)
25 #  include <config.h>
26 #endif
27
28 #include <stdio.h>
29
30 #if defined (HAVE_STDLIB_H)
31 #  include <stdlib.h>
32 #else
33 #  include "ansi_stdlib.h"
34 #endif /* HAVE_STDLIB_H */
35
36 #if defined (HAVE_UNISTD_H)
37 #  ifndef _MINIX
38 #    include <sys/types.h>
39 #  endif
40 #  include <unistd.h>
41 #endif
42
43 #include "rlmbutil.h"
44
45 #include "history.h"
46 #include "histlib.h"
47 #include "chardefs.h"
48
49 #include "rlshell.h"
50 #include "xmalloc.h"
51
52 #define HISTORY_WORD_DELIMITERS         " \t\n;&()|<>"
53 #define HISTORY_QUOTE_CHARACTERS        "\"'`"
54 #define HISTORY_EVENT_DELIMITERS        "^$*%-"
55
56 #define slashify_in_quotes "\\`\"$"
57
58 #define fielddelim(c)   (whitespace(c) || (c) == '\n')
59
60 typedef int _hist_search_func_t PARAMS((const char *, int));
61
62 static char error_pointer;
63
64 static char *subst_lhs;
65 static char *subst_rhs;
66 static int subst_lhs_len;
67 static int subst_rhs_len;
68
69 /* Characters that delimit history event specifications and separate event
70    specifications from word designators.  Static for now */
71 static char *history_event_delimiter_chars = HISTORY_EVENT_DELIMITERS;
72
73 static char *get_history_word_specifier PARAMS((char *, char *, int *));
74 static int history_tokenize_word PARAMS((const char *, int));
75 static char **history_tokenize_internal PARAMS((const char *, int, int *));
76 static char *history_substring PARAMS((const char *, int, int));
77 static void freewords PARAMS((char **, int));
78 static char *history_find_word PARAMS((char *, int));
79
80 static char *quote_breaks PARAMS((char *));
81
82 /* Variables exported by this file. */
83 /* The character that represents the start of a history expansion
84    request.  This is usually `!'. */
85 char history_expansion_char = '!';
86
87 /* The character that invokes word substitution if found at the start of
88    a line.  This is usually `^'. */
89 char history_subst_char = '^';
90
91 /* During tokenization, if this character is seen as the first character
92    of a word, then it, and all subsequent characters upto a newline are
93    ignored.  For a Bourne shell, this should be '#'.  Bash special cases
94    the interactive comment character to not be a comment delimiter. */
95 char history_comment_char = '\0';
96
97 /* The list of characters which inhibit the expansion of text if found
98    immediately following history_expansion_char. */
99 char *history_no_expand_chars = " \t\n\r=";
100
101 /* If set to a non-zero value, single quotes inhibit history expansion.
102    The default is 0. */
103 int history_quotes_inhibit_expansion = 0;
104
105 /* Used to split words by history_tokenize_internal. */
106 char *history_word_delimiters = HISTORY_WORD_DELIMITERS;
107
108 /* If set, this points to a function that is called to verify that a
109    particular history expansion should be performed. */
110 rl_linebuf_func_t *history_inhibit_expansion_function;
111
112 int history_quoting_state = 0;
113
114 /* **************************************************************** */
115 /*                                                                  */
116 /*                      History Expansion                           */
117 /*                                                                  */
118 /* **************************************************************** */
119
120 /* Hairy history expansion on text, not tokens.  This is of general
121    use, and thus belongs in this library. */
122
123 /* The last string searched for by a !?string? search. */
124 static char *search_string;
125 /* The last string matched by a !?string? search. */
126 static char *search_match;
127
128 /* Return the event specified at TEXT + OFFSET modifying OFFSET to
129    point to after the event specifier.  Just a pointer to the history
130    line is returned; NULL is returned in the event of a bad specifier.
131    You pass STRING with *INDEX equal to the history_expansion_char that
132    begins this specification.
133    DELIMITING_QUOTE is a character that is allowed to end the string
134    specification for what to search for in addition to the normal
135    characters `:', ` ', `\t', `\n', and sometimes `?'.
136    So you might call this function like:
137    line = get_history_event ("!echo:p", &index, 0);  */
138 char *
139 get_history_event (const char *string, int *caller_index, int delimiting_quote)
140 {
141   register int i;
142   register char c;
143   HIST_ENTRY *entry;
144   int which, sign, local_index, substring_okay;
145   _hist_search_func_t *search_func;
146   char *temp;
147
148   /* The event can be specified in a number of ways.
149
150      !!   the previous command
151      !n   command line N
152      !-n  current command-line minus N
153      !str the most recent command starting with STR
154      !?str[?]
155           the most recent command containing STR
156
157      All values N are determined via HISTORY_BASE. */
158
159   i = *caller_index;
160
161   if (string[i] != history_expansion_char)
162     return ((char *)NULL);
163
164   /* Move on to the specification. */
165   i++;
166
167   sign = 1;
168   substring_okay = 0;
169
170 #define RETURN_ENTRY(e, w) \
171         return ((e = history_get (w)) ? e->line : (char *)NULL)
172
173   /* Handle !! case. */
174   if (string[i] == history_expansion_char)
175     {
176       i++;
177       which = history_base + (history_length - 1);
178       *caller_index = i;
179       RETURN_ENTRY (entry, which);
180     }
181
182   /* Hack case of numeric line specification. */
183   if (string[i] == '-')
184     {
185       sign = -1;
186       i++;
187     }
188
189   if (_rl_digit_p (string[i]))
190     {
191       /* Get the extent of the digits and compute the value. */
192       for (which = 0; _rl_digit_p (string[i]); i++)
193         which = (which * 10) + _rl_digit_value (string[i]);
194
195       *caller_index = i;
196
197       if (sign < 0)
198         which = (history_length + history_base) - which;
199
200       RETURN_ENTRY (entry, which);
201     }
202
203   /* This must be something to search for.  If the spec begins with
204      a '?', then the string may be anywhere on the line.  Otherwise,
205      the string must be found at the start of a line. */
206   if (string[i] == '?')
207     {
208       substring_okay++;
209       i++;
210     }
211
212   /* Only a closing `?' or a newline delimit a substring search string. */
213   for (local_index = i; c = string[i]; i++)
214     {
215 #if defined (HANDLE_MULTIBYTE)
216       if (MB_CUR_MAX > 1 && rl_byte_oriented == 0)
217         {
218           int v;
219           mbstate_t ps;
220
221           memset (&ps, 0, sizeof (mbstate_t));
222           /* These produce warnings because we're passing a const string to a
223              function that takes a non-const string. */
224           _rl_adjust_point ((char *)string, i, &ps);
225           if ((v = _rl_get_char_len ((char *)string + i, &ps)) > 1)
226             {
227               i += v - 1;
228               continue;
229             }
230         }
231
232 #endif /* HANDLE_MULTIBYTE */
233       if ((!substring_okay && (whitespace (c) || c == ':' ||
234           (history_event_delimiter_chars && member (c, history_event_delimiter_chars)) ||
235           (history_search_delimiter_chars && member (c, history_search_delimiter_chars)) ||
236           string[i] == delimiting_quote)) ||
237           string[i] == '\n' ||
238           (substring_okay && string[i] == '?'))
239         break;
240     }
241
242   which = i - local_index;
243   temp = (char *)xmalloc (1 + which);
244   if (which)
245     strncpy (temp, string + local_index, which);
246   temp[which] = '\0';
247
248   if (substring_okay && string[i] == '?')
249     i++;
250
251   *caller_index = i;
252
253 #define FAIL_SEARCH() \
254   do { \
255     history_offset = history_length; xfree (temp) ; return (char *)NULL; \
256   } while (0)
257
258   /* If there is no search string, try to use the previous search string,
259      if one exists.  If not, fail immediately. */
260   if (*temp == '\0' && substring_okay)
261     {
262       if (search_string)
263         {
264           xfree (temp);
265           temp = savestring (search_string);
266         }
267       else
268         FAIL_SEARCH ();
269     }
270
271   search_func = substring_okay ? history_search : history_search_prefix;
272   while (1)
273     {
274       local_index = (*search_func) (temp, -1);
275
276       if (local_index < 0)
277         FAIL_SEARCH ();
278
279       if (local_index == 0 || substring_okay)
280         {
281           entry = current_history ();
282           if (entry == 0)
283             FAIL_SEARCH ();
284           history_offset = history_length;
285         
286           /* If this was a substring search, then remember the
287              string that we matched for word substitution. */
288           if (substring_okay)
289             {
290               FREE (search_string);
291               search_string = temp;
292
293               FREE (search_match);
294               search_match = history_find_word (entry->line, local_index);
295             }
296           else
297             xfree (temp);
298
299           return (entry->line);
300         }
301
302       if (history_offset)
303         history_offset--;
304       else
305         FAIL_SEARCH ();
306     }
307 #undef FAIL_SEARCH
308 #undef RETURN_ENTRY
309 }
310
311 /* Function for extracting single-quoted strings.  Used for inhibiting
312    history expansion within single quotes. */
313
314 /* Extract the contents of STRING as if it is enclosed in single quotes.
315    SINDEX, when passed in, is the offset of the character immediately
316    following the opening single quote; on exit, SINDEX is left pointing
317    to the closing single quote.  FLAGS currently used to allow backslash
318    to escape a single quote (e.g., for bash $'...'). */
319 static void
320 hist_string_extract_single_quoted (char *string, int *sindex, int flags)
321 {
322   register int i;
323
324   for (i = *sindex; string[i] && string[i] != '\''; i++)
325     {
326       if ((flags & 1) && string[i] == '\\' && string[i+1])
327         i++;
328     }
329
330   *sindex = i;
331 }
332
333 static char *
334 quote_breaks (char *s)
335 {
336   register char *p, *r;
337   char *ret;
338   int len = 3;
339
340   for (p = s; p && *p; p++, len++)
341     {
342       if (*p == '\'')
343         len += 3;
344       else if (whitespace (*p) || *p == '\n')
345         len += 2;
346     }
347
348   r = ret = (char *)xmalloc (len);
349   *r++ = '\'';
350   for (p = s; p && *p; )
351     {
352       if (*p == '\'')
353         {
354           *r++ = '\'';
355           *r++ = '\\';
356           *r++ = '\'';
357           *r++ = '\'';
358           p++;
359         }
360       else if (whitespace (*p) || *p == '\n')
361         {
362           *r++ = '\'';
363           *r++ = *p++;
364           *r++ = '\'';
365         }
366       else
367         *r++ = *p++;
368     }
369   *r++ = '\'';
370   *r = '\0';
371   return ret;
372 }
373
374 static char *
375 hist_error(char *s, int start, int current, int errtype)
376 {
377   char *temp;
378   const char *emsg;
379   int ll, elen;
380
381   ll = current - start;
382
383   switch (errtype)
384     {
385     case EVENT_NOT_FOUND:
386       emsg = "event not found";
387       elen = 15;
388       break;
389     case BAD_WORD_SPEC:
390       emsg = "bad word specifier";
391       elen = 18;
392       break;
393     case SUBST_FAILED:
394       emsg = "substitution failed";
395       elen = 19;
396       break;
397     case BAD_MODIFIER:
398       emsg = "unrecognized history modifier";
399       elen = 29;
400       break;
401     case NO_PREV_SUBST:
402       emsg = "no previous substitution";
403       elen = 24;
404       break;
405     default:
406       emsg = "unknown expansion error";
407       elen = 23;
408       break;
409     }
410
411   temp = (char *)xmalloc (ll + elen + 3);
412   strncpy (temp, s + start, ll);
413   temp[ll] = ':';
414   temp[ll + 1] = ' ';
415   strcpy (temp + ll + 2, emsg);
416   return (temp);
417 }
418
419 /* Get a history substitution string from STR starting at *IPTR
420    and return it.  The length is returned in LENPTR.
421
422    A backslash can quote the delimiter.  If the string is the
423    empty string, the previous pattern is used.  If there is
424    no previous pattern for the lhs, the last history search
425    string is used.
426
427    If IS_RHS is 1, we ignore empty strings and set the pattern
428    to "" anyway.  subst_lhs is not changed if the lhs is empty;
429    subst_rhs is allowed to be set to the empty string. */
430
431 static char *
432 get_subst_pattern (char *str, int *iptr, int delimiter, int is_rhs, int *lenptr)
433 {
434   register int si, i, j, k;
435   char *s;
436 #if defined (HANDLE_MULTIBYTE)
437   mbstate_t ps;
438 #endif
439
440   s = (char *)NULL;
441   i = *iptr;
442
443 #if defined (HANDLE_MULTIBYTE)
444   memset (&ps, 0, sizeof (mbstate_t));
445   _rl_adjust_point (str, i, &ps);
446 #endif
447
448   for (si = i; str[si] && str[si] != delimiter; si++)
449 #if defined (HANDLE_MULTIBYTE)
450     if (MB_CUR_MAX > 1 && rl_byte_oriented == 0)
451       {
452         int v;
453         if ((v = _rl_get_char_len (str + si, &ps)) > 1)
454           si += v - 1;
455         else if (str[si] == '\\' && str[si + 1] == delimiter)
456           si++;
457       }
458     else
459 #endif /* HANDLE_MULTIBYTE */
460       if (str[si] == '\\' && str[si + 1] == delimiter)
461         si++;
462
463   if (si > i || is_rhs)
464     {
465       s = (char *)xmalloc (si - i + 1);
466       for (j = 0, k = i; k < si; j++, k++)
467         {
468           /* Remove a backslash quoting the search string delimiter. */
469           if (str[k] == '\\' && str[k + 1] == delimiter)
470             k++;
471           s[j] = str[k];
472         }
473       s[j] = '\0';
474       if (lenptr)
475         *lenptr = j;
476     }
477
478   i = si;
479   if (str[i])
480     i++;
481   *iptr = i;
482
483   return s;
484 }
485
486 static void
487 postproc_subst_rhs (void)
488 {
489   char *new;
490   int i, j, new_size;
491
492   new = (char *)xmalloc (new_size = subst_rhs_len + subst_lhs_len);
493   for (i = j = 0; i < subst_rhs_len; i++)
494     {
495       if (subst_rhs[i] == '&')
496         {
497           if (j + subst_lhs_len >= new_size)
498             new = (char *)xrealloc (new, (new_size = new_size * 2 + subst_lhs_len));
499           strcpy (new + j, subst_lhs);
500           j += subst_lhs_len;
501         }
502       else
503         {
504           /* a single backslash protects the `&' from lhs interpolation */
505           if (subst_rhs[i] == '\\' && subst_rhs[i + 1] == '&')
506             i++;
507           if (j >= new_size)
508             new = (char *)xrealloc (new, new_size *= 2);
509           new[j++] = subst_rhs[i];
510         }
511     }
512   new[j] = '\0';
513   xfree (subst_rhs);
514   subst_rhs = new;
515   subst_rhs_len = j;
516 }
517
518 /* Expand the bulk of a history specifier starting at STRING[START].
519    Returns 0 if everything is OK, -1 if an error occurred, and 1
520    if the `p' modifier was supplied and the caller should just print
521    the returned string.  Returns the new index into string in
522    *END_INDEX_PTR, and the expanded specifier in *RET_STRING. */
523 /* need current line for !# */
524 static int
525 history_expand_internal (char *string, int start, int qc, int *end_index_ptr, char **ret_string, char *current_line)
526 {
527   int i, n, starting_index;
528   int substitute_globally, subst_bywords, want_quotes, print_only;
529   char *event, *temp, *result, *tstr, *t, c, *word_spec;
530   int result_len;
531 #if defined (HANDLE_MULTIBYTE)
532   mbstate_t ps;
533
534   memset (&ps, 0, sizeof (mbstate_t));
535 #endif
536
537   result = (char *)xmalloc (result_len = 128);
538
539   i = start;
540
541   /* If it is followed by something that starts a word specifier,
542      then !! is implied as the event specifier. */
543
544   if (member (string[i + 1], ":$*%^"))
545     {
546       char fake_s[3];
547       int fake_i = 0;
548       i++;
549       fake_s[0] = fake_s[1] = history_expansion_char;
550       fake_s[2] = '\0';
551       event = get_history_event (fake_s, &fake_i, 0);
552     }
553   else if (string[i + 1] == '#')
554     {
555       i += 2;
556       event = current_line;
557     }
558   else
559     event = get_history_event (string, &i, qc);
560           
561   if (event == 0)
562     {
563       *ret_string = hist_error (string, start, i, EVENT_NOT_FOUND);
564       xfree (result);
565       return (-1);
566     }
567
568   /* If a word specifier is found, then do what that requires. */
569   starting_index = i;
570   word_spec = get_history_word_specifier (string, event, &i);
571
572   /* There is no such thing as a `malformed word specifier'.  However,
573      it is possible for a specifier that has no match.  In that case,
574      we complain. */
575   if (word_spec == (char *)&error_pointer)
576     {
577       *ret_string = hist_error (string, starting_index, i, BAD_WORD_SPEC);
578       xfree (result);
579       return (-1);
580     }
581
582   /* If no word specifier, than the thing of interest was the event. */
583   temp = word_spec ? savestring (word_spec) : savestring (event);
584   FREE (word_spec);
585
586   /* Perhaps there are other modifiers involved.  Do what they say. */
587   want_quotes = substitute_globally = subst_bywords = print_only = 0;
588   starting_index = i;
589
590   while (string[i] == ':')
591     {
592       c = string[i + 1];
593
594       if (c == 'g' || c == 'a')
595         {
596           substitute_globally = 1;
597           i++;
598           c = string[i + 1];
599         }
600       else if (c == 'G')
601         {
602           subst_bywords = 1;
603           i++;
604           c = string[i + 1];
605         }
606
607       switch (c)
608         {
609         default:
610           *ret_string = hist_error (string, i+1, i+2, BAD_MODIFIER);
611           xfree (result);
612           xfree (temp);
613           return -1;
614
615         case 'q':
616           want_quotes = 'q';
617           break;
618
619         case 'x':
620           want_quotes = 'x';
621           break;
622
623           /* :p means make this the last executed line.  So we
624              return an error state after adding this line to the
625              history. */
626         case 'p':
627           print_only++;
628           break;
629
630           /* :t discards all but the last part of the pathname. */
631         case 't':
632           tstr = strrchr (temp, '/');
633           if (tstr)
634             {
635               tstr++;
636               t = savestring (tstr);
637               xfree (temp);
638               temp = t;
639             }
640           break;
641
642           /* :h discards the last part of a pathname. */
643         case 'h':
644           tstr = strrchr (temp, '/');
645           if (tstr)
646             *tstr = '\0';
647           break;
648
649           /* :r discards the suffix. */
650         case 'r':
651           tstr = strrchr (temp, '.');
652           if (tstr)
653             *tstr = '\0';
654           break;
655
656           /* :e discards everything but the suffix. */
657         case 'e':
658           tstr = strrchr (temp, '.');
659           if (tstr)
660             {
661               t = savestring (tstr);
662               xfree (temp);
663               temp = t;
664             }
665           break;
666
667         /* :s/this/that substitutes `that' for the first
668            occurrence of `this'.  :gs/this/that substitutes `that'
669            for each occurrence of `this'.  :& repeats the last
670            substitution.  :g& repeats the last substitution
671            globally. */
672
673         case '&':
674         case 's':
675           {
676             char *new_event;
677             int delimiter, failed, si, l_temp, ws, we;
678
679             if (c == 's')
680               {
681                 if (i + 2 < (int)strlen (string))
682                   {
683 #if defined (HANDLE_MULTIBYTE)
684                     if (MB_CUR_MAX > 1 && rl_byte_oriented == 0)
685                       {
686                         _rl_adjust_point (string, i + 2, &ps);
687                         if (_rl_get_char_len (string + i + 2, &ps) > 1)
688                           delimiter = 0;
689                         else
690                           delimiter = string[i + 2];
691                       }
692                     else
693 #endif /* HANDLE_MULTIBYTE */
694                       delimiter = string[i + 2];
695                   }
696                 else
697                   break;        /* no search delimiter */
698
699                 i += 3;
700
701                 t = get_subst_pattern (string, &i, delimiter, 0, &subst_lhs_len);
702                 /* An empty substitution lhs with no previous substitution
703                    uses the last search string as the lhs. */
704                 if (t)
705                   {
706                     FREE (subst_lhs);
707                     subst_lhs = t;
708                   }
709                 else if (!subst_lhs)
710                   {
711                     if (search_string && *search_string)
712                       {
713                         subst_lhs = savestring (search_string);
714                         subst_lhs_len = strlen (subst_lhs);
715                       }
716                     else
717                       {
718                         subst_lhs = (char *) NULL;
719                         subst_lhs_len = 0;
720                       }
721                   }
722
723                 FREE (subst_rhs);
724                 subst_rhs = get_subst_pattern (string, &i, delimiter, 1, &subst_rhs_len);
725
726                 /* If `&' appears in the rhs, it's supposed to be replaced
727                    with the lhs. */
728                 if (member ('&', subst_rhs))
729                   postproc_subst_rhs ();
730               }
731             else
732               i += 2;
733
734             /* If there is no lhs, the substitution can't succeed. */
735             if (subst_lhs_len == 0)
736               {
737                 *ret_string = hist_error (string, starting_index, i, NO_PREV_SUBST);
738                 xfree (result);
739                 xfree (temp);
740                 return -1;
741               }
742
743             l_temp = strlen (temp);
744             /* Ignore impossible cases. */
745             if (subst_lhs_len > l_temp)
746               {
747                 *ret_string = hist_error (string, starting_index, i, SUBST_FAILED);
748                 xfree (result);
749                 xfree (temp);
750                 return (-1);
751               }
752
753             /* Find the first occurrence of THIS in TEMP. */
754             /* Substitute SUBST_RHS for SUBST_LHS in TEMP.  There are three
755                cases to consider:
756
757                  1.  substitute_globally == subst_bywords == 0
758                  2.  substitute_globally == 1 && subst_bywords == 0
759                  3.  substitute_globally == 0 && subst_bywords == 1
760
761                In the first case, we substitute for the first occurrence only.
762                In the second case, we substitute for every occurrence.
763                In the third case, we tokenize into words and substitute the
764                first occurrence of each word. */
765
766             si = we = 0;
767             for (failed = 1; (si + subst_lhs_len) <= l_temp; si++)
768               {
769                 /* First skip whitespace and find word boundaries if
770                    we're past the end of the word boundary we found
771                    the last time. */
772                 if (subst_bywords && si > we)
773                   {
774                     for (; temp[si] && fielddelim (temp[si]); si++)
775                       ;
776                     ws = si;
777                     we = history_tokenize_word (temp, si);
778                   }
779
780                 if (STREQN (temp+si, subst_lhs, subst_lhs_len))
781                   {
782                     int len = subst_rhs_len - subst_lhs_len + l_temp;
783                     new_event = (char *)xmalloc (1 + len);
784                     strncpy (new_event, temp, si);
785                     strncpy (new_event + si, subst_rhs, subst_rhs_len);
786                     strncpy (new_event + si + subst_rhs_len,
787                              temp + si + subst_lhs_len,
788                              l_temp - (si + subst_lhs_len));
789                     new_event[len] = '\0';
790                     xfree (temp);
791                     temp = new_event;
792
793                     failed = 0;
794
795                     if (substitute_globally)
796                       {
797                         /* Reported to fix a bug that causes it to skip every
798                            other match when matching a single character.  Was
799                            si += subst_rhs_len previously. */
800                         si += subst_rhs_len - 1;
801                         l_temp = strlen (temp);
802                         substitute_globally++;
803                         continue;
804                       }
805                     else if (subst_bywords)
806                       {
807                         si = we;
808                         l_temp = strlen (temp);
809                         continue;
810                       }
811                     else
812                       break;
813                   }
814               }
815
816             if (substitute_globally > 1)
817               {
818                 substitute_globally = 0;
819                 continue;       /* don't want to increment i */
820               }
821
822             if (failed == 0)
823               continue;         /* don't want to increment i */
824
825             *ret_string = hist_error (string, starting_index, i, SUBST_FAILED);
826             xfree (result);
827             xfree (temp);
828             return (-1);
829           }
830         }
831       i += 2;
832     }
833   /* Done with modifiers. */
834   /* Believe it or not, we have to back the pointer up by one. */
835   --i;
836
837   if (want_quotes)
838     {
839       char *x;
840
841       if (want_quotes == 'q')
842         x = sh_single_quote (temp);
843       else if (want_quotes == 'x')
844         x = quote_breaks (temp);
845       else
846         x = savestring (temp);
847
848       xfree (temp);
849       temp = x;
850     }
851
852   n = strlen (temp);
853   if (n >= result_len)
854     result = (char *)xrealloc (result, n + 2);
855   strcpy (result, temp);
856   xfree (temp);
857
858   *end_index_ptr = i;
859   *ret_string = result;
860   return (print_only);
861 }
862
863 /* Expand the string STRING, placing the result into OUTPUT, a pointer
864    to a string.  Returns:
865
866   -1) If there was an error in expansion.
867    0) If no expansions took place (or, if the only change in
868       the text was the de-slashifying of the history expansion
869       character)
870    1) If expansions did take place
871    2) If the `p' modifier was given and the caller should print the result
872
873   If an error occurred in expansion, then OUTPUT contains a descriptive
874   error message. */
875
876 #define ADD_STRING(s) \
877         do \
878           { \
879             int sl = strlen (s); \
880             j += sl; \
881             if (j >= result_len) \
882               { \
883                 while (j >= result_len) \
884                   result_len += 128; \
885                 result = (char *)xrealloc (result, result_len); \
886               } \
887             strcpy (result + j - sl, s); \
888           } \
889         while (0)
890
891 #define ADD_CHAR(c) \
892         do \
893           { \
894             if (j >= result_len - 1) \
895               result = (char *)xrealloc (result, result_len += 64); \
896             result[j++] = c; \
897             result[j] = '\0'; \
898           } \
899         while (0)
900
901 int
902 history_expand (char *hstring, char **output)
903 {
904   register int j;
905   int i, r, l, passc, cc, modified, eindex, only_printing, dquote, squote, flag;
906   char *string;
907
908   /* The output string, and its length. */
909   int result_len;
910   char *result;
911
912 #if defined (HANDLE_MULTIBYTE)
913   char mb[MB_LEN_MAX];
914   mbstate_t ps;
915 #endif
916
917   /* Used when adding the string. */
918   char *temp;
919
920   if (output == 0)
921     return 0;
922
923   /* Setting the history expansion character to 0 inhibits all
924      history expansion. */
925   if (history_expansion_char == 0)
926     {
927       *output = savestring (hstring);
928       return (0);
929     }
930     
931   /* Prepare the buffer for printing error messages. */
932   result = (char *)xmalloc (result_len = 256);
933   result[0] = '\0';
934
935   only_printing = modified = 0;
936   l = strlen (hstring);
937
938   /* Grovel the string.  Only backslash and single quotes can quote the
939      history escape character.  We also handle arg specifiers. */
940
941   /* Before we grovel forever, see if the history_expansion_char appears
942      anywhere within the text. */
943
944   /* The quick substitution character is a history expansion all right.  That
945      is to say, "^this^that^" is equivalent to "!!:s^this^that^", and in fact,
946      that is the substitution that we do. */
947   if (hstring[0] == history_subst_char)
948     {
949       string = (char *)xmalloc (l + 5);
950
951       string[0] = string[1] = history_expansion_char;
952       string[2] = ':';
953       string[3] = 's';
954       strcpy (string + 4, hstring);
955       l += 4;
956     }
957   else
958     {
959 #if defined (HANDLE_MULTIBYTE)
960       memset (&ps, 0, sizeof (mbstate_t));
961 #endif
962
963       string = hstring;
964       /* If not quick substitution, still maybe have to do expansion. */
965
966       /* `!' followed by one of the characters in history_no_expand_chars
967          is NOT an expansion. */
968       dquote = history_quoting_state == '"';
969       squote = history_quoting_state == '\'';
970
971       /* If the calling application tells us we are already reading a
972          single-quoted string, consume the rest of the string right now
973          and then go on. */
974       i = 0;
975       if (squote && history_quotes_inhibit_expansion)
976         {
977           hist_string_extract_single_quoted (string, &i, 0);
978           squote = 0;
979           if (string[i])
980             i++;
981         }
982
983       for ( ; string[i]; i++)
984         {
985 #if defined (HANDLE_MULTIBYTE)
986           if (MB_CUR_MAX > 1 && rl_byte_oriented == 0)
987             {
988               int v;
989               v = _rl_get_char_len (string + i, &ps);
990               if (v > 1)
991                 {
992                   i += v - 1;
993                   continue;
994                 }
995             }
996 #endif /* HANDLE_MULTIBYTE */
997
998           cc = string[i + 1];
999           /* The history_comment_char, if set, appearing at the beginning
1000              of a word signifies that the rest of the line should not have
1001              history expansion performed on it.
1002              Skip the rest of the line and break out of the loop. */
1003           if (history_comment_char && string[i] == history_comment_char &&
1004               dquote == 0 &&
1005               (i == 0 || member (string[i - 1], history_word_delimiters)))
1006             {
1007               while (string[i])
1008                 i++;
1009               break;
1010             }
1011           else if (string[i] == history_expansion_char)
1012             {
1013               if (cc == 0 || member (cc, history_no_expand_chars))
1014                 continue;
1015               /* DQUOTE won't be set unless history_quotes_inhibit_expansion
1016                  is set.  The idea here is to treat double-quoted strings the
1017                  same as the word outside double quotes; in effect making the
1018                  double quote part of history_no_expand_chars when DQUOTE is
1019                  set. */
1020               else if (dquote && cc == '"')
1021                 continue;
1022               /* If the calling application has set
1023                  history_inhibit_expansion_function to a function that checks
1024                  for special cases that should not be history expanded,
1025                  call the function and skip the expansion if it returns a
1026                  non-zero value. */
1027               else if (history_inhibit_expansion_function &&
1028                         (*history_inhibit_expansion_function) (string, i))
1029                 continue;
1030               else
1031                 break;
1032             }
1033           /* Shell-like quoting: allow backslashes to quote double quotes
1034              inside a double-quoted string. */
1035           else if (dquote && string[i] == '\\' && cc == '"')
1036             i++;
1037           /* More shell-like quoting:  if we're paying attention to single
1038              quotes and letting them quote the history expansion character,
1039              then we need to pay attention to double quotes, because single
1040              quotes are not special inside double-quoted strings. */
1041           else if (history_quotes_inhibit_expansion && string[i] == '"')
1042             {
1043               dquote = 1 - dquote;
1044             }
1045           else if (dquote == 0 && history_quotes_inhibit_expansion && string[i] == '\'')
1046             {
1047               /* If this is bash, single quotes inhibit history expansion. */
1048               flag = (i > 0 && string[i - 1] == '$');
1049               i++;
1050               hist_string_extract_single_quoted (string, &i, flag);
1051             }
1052           else if (history_quotes_inhibit_expansion && string[i] == '\\')
1053             {
1054               /* If this is bash, allow backslashes to quote single
1055                  quotes and the history expansion character. */
1056               if (cc == '\'' || cc == history_expansion_char)
1057                 i++;
1058             }
1059           
1060         }
1061           
1062       if (string[i] != history_expansion_char)
1063         {
1064           xfree (result);
1065           *output = savestring (string);
1066           return (0);
1067         }
1068     }
1069
1070   /* Extract and perform the substitution. */
1071   dquote = history_quoting_state == '"';
1072   squote = history_quoting_state == '\'';
1073
1074   /* If the calling application tells us we are already reading a
1075      single-quoted string, consume the rest of the string right now
1076      and then go on. */
1077   i = j = 0;
1078   if (squote && history_quotes_inhibit_expansion)
1079     {
1080       int c;
1081
1082       hist_string_extract_single_quoted (string, &i, 0);
1083       squote = 0;
1084       for (c = 0; c < i; c++)
1085         ADD_CHAR (string[c]);      
1086       if (string[i])
1087         {
1088           ADD_CHAR (string[i]);
1089           i++;
1090         }
1091     }
1092
1093   for (passc = 0; i < l; i++)
1094     {
1095       int qc, tchar = string[i];
1096
1097       if (passc)
1098         {
1099           passc = 0;
1100           ADD_CHAR (tchar);
1101           continue;
1102         }
1103
1104 #if defined (HANDLE_MULTIBYTE)
1105       if (MB_CUR_MAX > 1 && rl_byte_oriented == 0)
1106         {
1107           int k, c;
1108
1109           c = tchar;
1110           memset (mb, 0, sizeof (mb));
1111           for (k = 0; k < MB_LEN_MAX; k++)
1112             {
1113               mb[k] = (char)c;
1114               memset (&ps, 0, sizeof (mbstate_t));
1115               if (_rl_get_char_len (mb, &ps) == -2)
1116                 c = string[++i];
1117               else
1118                 break;
1119             }
1120           if (strlen (mb) > 1)
1121             {
1122               ADD_STRING (mb);
1123               continue;
1124             }
1125         }
1126 #endif /* HANDLE_MULTIBYTE */
1127
1128       if (tchar == history_expansion_char)
1129         tchar = -3;
1130       else if (tchar == history_comment_char)
1131         tchar = -2;
1132
1133       switch (tchar)
1134         {
1135         default:
1136           ADD_CHAR (string[i]);
1137           break;
1138
1139         case '\\':
1140           passc++;
1141           ADD_CHAR (tchar);
1142           break;
1143
1144         case '"':
1145           dquote = 1 - dquote;
1146           ADD_CHAR (tchar);
1147           break;
1148           
1149         case '\'':
1150           {
1151             /* If history_quotes_inhibit_expansion is set, single quotes
1152                inhibit history expansion, otherwise they are treated like
1153                double quotes. */
1154             if (squote)
1155               {
1156                 squote = 0;
1157                 ADD_CHAR (tchar);
1158               }
1159             else if (dquote == 0 && history_quotes_inhibit_expansion)
1160               {
1161                 int quote, slen;
1162
1163                 flag = (i > 0 && string[i - 1] == '$');
1164                 quote = i++;
1165                 hist_string_extract_single_quoted (string, &i, flag);
1166
1167                 slen = i - quote + 2;
1168                 temp = (char *)xmalloc (slen);
1169                 strncpy (temp, string + quote, slen);
1170                 temp[slen - 1] = '\0';
1171                 ADD_STRING (temp);
1172                 xfree (temp);
1173               }
1174             else if (dquote == 0 && squote == 0 && history_quotes_inhibit_expansion == 0)
1175               {
1176                 squote = 1;
1177                 ADD_CHAR (string[i]);
1178               }
1179             else
1180               ADD_CHAR (string[i]);
1181             break;
1182           }
1183
1184         case -2:                /* history_comment_char */
1185           if ((dquote == 0 || history_quotes_inhibit_expansion == 0) &&
1186               (i == 0 || member (string[i - 1], history_word_delimiters)))
1187             {
1188               temp = (char *)xmalloc (l - i + 1);
1189               strcpy (temp, string + i);
1190               ADD_STRING (temp);
1191               xfree (temp);
1192               i = l;
1193             }
1194           else
1195             ADD_CHAR (string[i]);
1196           break;
1197
1198         case -3:                /* history_expansion_char */
1199           cc = string[i + 1];
1200
1201           /* If the history_expansion_char is followed by one of the
1202              characters in history_no_expand_chars, then it is not a
1203              candidate for expansion of any kind. */
1204           if (cc == 0 || member (cc, history_no_expand_chars) ||
1205                          (dquote && cc == '"') ||
1206                          (history_inhibit_expansion_function && (*history_inhibit_expansion_function) (string, i)))
1207             {
1208               ADD_CHAR (string[i]);
1209               break;
1210             }
1211
1212 #if defined (NO_BANG_HASH_MODIFIERS)
1213           /* There is something that is listed as a `word specifier' in csh
1214              documentation which means `the expanded text to this point'.
1215              That is not a word specifier, it is an event specifier.  If we
1216              don't want to allow modifiers with `!#', just stick the current
1217              output line in again. */
1218           if (cc == '#')
1219             {
1220               if (result)
1221                 {
1222                   temp = (char *)xmalloc (1 + strlen (result));
1223                   strcpy (temp, result);
1224                   ADD_STRING (temp);
1225                   xfree (temp);
1226                 }
1227               i++;
1228               break;
1229             }
1230 #endif
1231           qc = squote ? '\'' : (dquote ? '"' : 0);
1232           r = history_expand_internal (string, i, qc, &eindex, &temp, result);
1233           if (r < 0)
1234             {
1235               *output = temp;
1236               xfree (result);
1237               if (string != hstring)
1238                 xfree (string);
1239               return -1;
1240             }
1241           else
1242             {
1243               if (temp)
1244                 {
1245                   modified++;
1246                   if (*temp)
1247                     ADD_STRING (temp);
1248                   xfree (temp);
1249                 }
1250               only_printing += r == 1;
1251               i = eindex;
1252             }
1253           break;
1254         }
1255     }
1256
1257   *output = result;
1258   if (string != hstring)
1259     xfree (string);
1260
1261   if (only_printing)
1262     {
1263 #if 0
1264       add_history (result);
1265 #endif
1266       return (2);
1267     }
1268
1269   return (modified != 0);
1270 }
1271
1272 /* Return a consed string which is the word specified in SPEC, and found
1273    in FROM.  NULL is returned if there is no spec.  The address of
1274    ERROR_POINTER is returned if the word specified cannot be found.
1275    CALLER_INDEX is the offset in SPEC to start looking; it is updated
1276    to point to just after the last character parsed. */
1277 static char *
1278 get_history_word_specifier (char *spec, char *from, int *caller_index)
1279 {
1280   register int i = *caller_index;
1281   int first, last;
1282   int expecting_word_spec = 0;
1283   char *result;
1284
1285   /* The range of words to return doesn't exist yet. */
1286   first = last = 0;
1287   result = (char *)NULL;
1288
1289   /* If we found a colon, then this *must* be a word specification.  If
1290      it isn't, then it is an error. */
1291   if (spec[i] == ':')
1292     {
1293       i++;
1294       expecting_word_spec++;
1295     }
1296
1297   /* Handle special cases first. */
1298
1299   /* `%' is the word last searched for. */
1300   if (spec[i] == '%')
1301     {
1302       *caller_index = i + 1;
1303       return (search_match ? savestring (search_match) : savestring (""));
1304     }
1305
1306   /* `*' matches all of the arguments, but not the command. */
1307   if (spec[i] == '*')
1308     {
1309       *caller_index = i + 1;
1310       result = history_arg_extract (1, '$', from);
1311       return (result ? result : savestring (""));
1312     }
1313
1314   /* `$' is last arg. */
1315   if (spec[i] == '$')
1316     {
1317       *caller_index = i + 1;
1318       return (history_arg_extract ('$', '$', from));
1319     }
1320
1321   /* Try to get FIRST and LAST figured out. */
1322
1323   if (spec[i] == '-')
1324     first = 0;
1325   else if (spec[i] == '^')
1326     {
1327       first = 1;
1328       i++;
1329     }
1330   else if (_rl_digit_p (spec[i]) && expecting_word_spec)
1331     {
1332       for (first = 0; _rl_digit_p (spec[i]); i++)
1333         first = (first * 10) + _rl_digit_value (spec[i]);
1334     }
1335   else
1336     return ((char *)NULL);      /* no valid `first' for word specifier */
1337
1338   if (spec[i] == '^' || spec[i] == '*')
1339     {
1340       last = (spec[i] == '^') ? 1 : '$';        /* x* abbreviates x-$ */
1341       i++;
1342     }
1343   else if (spec[i] != '-')
1344     last = first;
1345   else
1346     {
1347       i++;
1348
1349       if (_rl_digit_p (spec[i]))
1350         {
1351           for (last = 0; _rl_digit_p (spec[i]); i++)
1352             last = (last * 10) + _rl_digit_value (spec[i]);
1353         }
1354       else if (spec[i] == '$')
1355         {
1356           i++;
1357           last = '$';
1358         }
1359 #if 0
1360       else if (!spec[i] || spec[i] == ':')
1361         /* check against `:' because there could be a modifier separator */
1362 #else
1363       else
1364         /* csh seems to allow anything to terminate the word spec here,
1365            leaving it as an abbreviation. */
1366 #endif
1367         last = -1;              /* x- abbreviates x-$ omitting word `$' */
1368     }
1369
1370   *caller_index = i;
1371
1372   if (last >= first || last == '$' || last < 0)
1373     result = history_arg_extract (first, last, from);
1374
1375   return (result ? result : (char *)&error_pointer);
1376 }
1377
1378 /* Extract the args specified, starting at FIRST, and ending at LAST.
1379    The args are taken from STRING.  If either FIRST or LAST is < 0,
1380    then make that arg count from the right (subtract from the number of
1381    tokens, so that FIRST = -1 means the next to last token on the line).
1382    If LAST is `$' the last arg from STRING is used. */
1383 char *
1384 history_arg_extract (int first, int last, const char *string)
1385 {
1386   register int i, len;
1387   char *result;
1388   int size, offset;
1389   char **list;
1390
1391   /* XXX - think about making history_tokenize return a struct array,
1392      each struct in array being a string and a length to avoid the
1393      calls to strlen below. */
1394   if ((list = history_tokenize (string)) == NULL)
1395     return ((char *)NULL);
1396
1397   for (len = 0; list[len]; len++)
1398     ;
1399
1400   if (last < 0)
1401     last = len + last - 1;
1402
1403   if (first < 0)
1404     first = len + first - 1;
1405
1406   if (last == '$')
1407     last = len - 1;
1408
1409   if (first == '$')
1410     first = len - 1;
1411
1412   last++;
1413
1414   if (first >= len || last > len || first < 0 || last < 0 || first > last)
1415     result = ((char *)NULL);
1416   else
1417     {
1418       for (size = 0, i = first; i < last; i++)
1419         size += strlen (list[i]) + 1;
1420       result = (char *)xmalloc (size + 1);
1421       result[0] = '\0';
1422
1423       for (i = first, offset = 0; i < last; i++)
1424         {
1425           strcpy (result + offset, list[i]);
1426           offset += strlen (list[i]);
1427           if (i + 1 < last)
1428             {
1429               result[offset++] = ' ';
1430               result[offset] = 0;
1431             }
1432         }
1433     }
1434
1435   for (i = 0; i < len; i++)
1436     xfree (list[i]);
1437   xfree (list);
1438
1439   return (result);
1440 }
1441
1442 static int
1443 history_tokenize_word (const char *string, int ind)
1444 {
1445   register int i, j;
1446   int delimiter, nestdelim, delimopen;
1447
1448   i = ind;
1449   delimiter = nestdelim = 0;
1450
1451   if (member (string[i], "()\n"))       /* XXX - included \n, but why? been here forever */
1452     {
1453       i++;
1454       return i;
1455     }
1456
1457   if (ISDIGIT (string[i]))
1458     {
1459       j = i;
1460       while (string[j] && ISDIGIT (string[j]))
1461         j++;
1462       if (string[j] == 0)
1463         return (j);
1464       if (string[j] == '<' || string[j] == '>')
1465         i = j;                  /* digit sequence is a file descriptor */
1466       else
1467         {
1468           i = j;
1469           goto get_word;        /* digit sequence is part of a word */
1470         }
1471     }
1472
1473   if (member (string[i], "<>;&|"))
1474     {
1475       int peek = string[i + 1];
1476
1477       if (peek == string[i])
1478         {
1479           if (peek == '<' && string[i + 2] == '-')
1480             i++;
1481           else if (peek == '<' && string[i + 2] == '<')
1482             i++;
1483           i += 2;
1484           return i;
1485         }
1486       else if (peek == '&' && (string[i] == '>' || string[i] == '<'))
1487         {
1488           j = i + 2;
1489           while (string[j] && ISDIGIT (string[j]))      /* file descriptor */
1490             j++;
1491           if (string[j] =='-')          /* <&[digits]-, >&[digits]- */
1492             j++;
1493           return j;
1494         }
1495       else if ((peek == '>' && string[i] == '&') || (peek == '|' && string[i] == '>'))
1496         {
1497           i += 2;
1498           return i;
1499         }
1500       /* XXX - process substitution -- separated out for later -- bash-4.2 */
1501       else if (peek == '(' && (string[i] == '>' || string[i] == '<')) /*)*/
1502         {
1503           i += 2;
1504           delimopen = '(';
1505           delimiter = ')';
1506           nestdelim = 1;
1507           goto get_word;
1508         }
1509
1510       i++;
1511       return i;
1512     }
1513
1514 get_word:
1515   /* Get word from string + i; */
1516
1517   if (delimiter == 0 && member (string[i], HISTORY_QUOTE_CHARACTERS))
1518     delimiter = string[i++];
1519
1520   for (; string[i]; i++)
1521     {
1522       if (string[i] == '\\' && string[i + 1] == '\n')
1523         {
1524           i++;
1525           continue;
1526         }
1527
1528       if (string[i] == '\\' && delimiter != '\'' &&
1529           (delimiter != '"' || member (string[i], slashify_in_quotes)))
1530         {
1531           i++;
1532           continue;
1533         }
1534
1535       /* delimiter must be set and set to something other than a quote if
1536          nestdelim is set, so these tests are safe. */
1537       if (nestdelim && string[i] == delimopen)
1538         {
1539           nestdelim++;
1540           continue;
1541         }
1542       if (nestdelim && string[i] == delimiter)
1543         {
1544           nestdelim--;
1545           if (nestdelim == 0)
1546             delimiter = 0;
1547           continue;
1548         }
1549       
1550       if (delimiter && string[i] == delimiter)
1551         {
1552           delimiter = 0;
1553           continue;
1554         }
1555
1556       /* Command and process substitution; shell extended globbing patterns */
1557       if (nestdelim == 0 && delimiter == 0 && member (string[i], "<>$!@?+*") && string[i+1] == '(') /*)*/
1558         {
1559           i += 2;
1560           delimopen = '(';
1561           delimiter = ')';
1562           nestdelim = 1;
1563           continue;
1564         }
1565       
1566       if (delimiter == 0 && (member (string[i], history_word_delimiters)))
1567         break;
1568
1569       if (delimiter == 0 && member (string[i], HISTORY_QUOTE_CHARACTERS))
1570         delimiter = string[i];
1571     }
1572
1573   return i;
1574 }
1575
1576 static char *
1577 history_substring (const char *string, int start, int end)
1578 {
1579   register int len;
1580   register char *result;
1581
1582   len = end - start;
1583   result = (char *)xmalloc (len + 1);
1584   strncpy (result, string + start, len);
1585   result[len] = '\0';
1586   return result;
1587 }
1588
1589 /* Parse STRING into tokens and return an array of strings.  If WIND is
1590    not -1 and INDP is not null, we also want the word surrounding index
1591    WIND.  The position in the returned array of strings is returned in
1592    *INDP. */
1593 static char **
1594 history_tokenize_internal (const char *string, int wind, int *indp)
1595 {
1596   char **result;
1597   register int i, start, result_index, size;
1598
1599   /* If we're searching for a string that's not part of a word (e.g., " "),
1600      make sure we set *INDP to a reasonable value. */
1601   if (indp && wind != -1)
1602     *indp = -1;
1603
1604   /* Get a token, and stuff it into RESULT.  The tokens are split
1605      exactly where the shell would split them. */
1606   for (i = result_index = size = 0, result = (char **)NULL; string[i]; )
1607     {
1608       /* Skip leading whitespace. */
1609       for (; string[i] && fielddelim (string[i]); i++)
1610         ;
1611       if (string[i] == 0 || string[i] == history_comment_char)
1612         return (result);
1613
1614       start = i;
1615
1616       i = history_tokenize_word (string, start);
1617
1618       /* If we have a non-whitespace delimiter character (which would not be
1619          skipped by the loop above), use it and any adjacent delimiters to
1620          make a separate field.  Any adjacent white space will be skipped the
1621          next time through the loop. */
1622       if (i == start && history_word_delimiters)
1623         {
1624           i++;
1625           while (string[i] && member (string[i], history_word_delimiters))
1626             i++;
1627         }
1628
1629       /* If we are looking for the word in which the character at a
1630          particular index falls, remember it. */
1631       if (indp && wind != -1 && wind >= start && wind < i)
1632         *indp = result_index;
1633
1634       if (result_index + 2 >= size)
1635         result = (char **)xrealloc (result, ((size += 10) * sizeof (char *)));
1636
1637       result[result_index++] = history_substring (string, start, i);
1638       result[result_index] = (char *)NULL;
1639     }
1640
1641   return (result);
1642 }
1643
1644 /* Return an array of tokens, much as the shell might.  The tokens are
1645    parsed out of STRING. */
1646 char **
1647 history_tokenize (const char *string)
1648 {
1649   return (history_tokenize_internal (string, -1, (int *)NULL));
1650 }
1651
1652 /* Free members of WORDS from START to an empty string */
1653 static void
1654 freewords (char **words, int start)
1655 {
1656   register int i;
1657
1658   for (i = start; words[i]; i++)
1659     xfree (words[i]);
1660 }
1661
1662 /* Find and return the word which contains the character at index IND
1663    in the history line LINE.  Used to save the word matched by the
1664    last history !?string? search. */
1665 static char *
1666 history_find_word (char *line, int ind)
1667 {
1668   char **words, *s;
1669   int i, wind;
1670
1671   words = history_tokenize_internal (line, ind, &wind);
1672   if (wind == -1 || words == 0)
1673     {
1674       if (words)
1675         freewords (words, 0);
1676       FREE (words);
1677       return ((char *)NULL);
1678     }
1679   s = words[wind];
1680   for (i = 0; i < wind; i++)
1681     xfree (words[i]);
1682   freewords (words, wind + 1);
1683   xfree (words);
1684   return s;
1685 }