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