]> CyberLeo.Net >> Repos - FreeBSD/releng/10.0.git/blob - contrib/libreadline/util.c
- Copy stable/10 (r259064) to releng/10.0 as part of the
[FreeBSD/releng/10.0.git] / contrib / libreadline / util.c
1 /* $FreeBSD$ */
2 /* util.c -- readline utility functions */
3
4 /* Copyright (C) 1987-2005 Free Software Foundation, Inc.
5
6    This file is part of the GNU Readline Library, a library for
7    reading lines of text with interactive input and history editing.
8
9    The GNU Readline Library is free software; you can redistribute it
10    and/or modify it under the terms of the GNU General Public License
11    as published by the Free Software Foundation; either version 2, or
12    (at your option) any later version.
13
14    The GNU Readline Library is distributed in the hope that it will be
15    useful, but WITHOUT ANY WARRANTY; without even the implied warranty
16    of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17    GNU General Public License for more details.
18
19    The GNU General Public License is often shipped with GNU software, and
20    is generally kept in a file called COPYING or LICENSE.  If you do not
21    have a copy of the license, write to the Free Software Foundation,
22    59 Temple Place, Suite 330, Boston, MA 02111 USA. */
23 #define READLINE_LIBRARY
24
25 #if defined (HAVE_CONFIG_H)
26 #  include <config.h>
27 #endif
28
29 #include <sys/types.h>
30 #include <fcntl.h>
31 #include "posixjmp.h"
32
33 #if defined (HAVE_UNISTD_H)
34 #  include <unistd.h>           /* for _POSIX_VERSION */
35 #endif /* HAVE_UNISTD_H */
36
37 #if defined (HAVE_STDLIB_H)
38 #  include <stdlib.h>
39 #else
40 #  include "ansi_stdlib.h"
41 #endif /* HAVE_STDLIB_H */
42
43 #include <stdio.h>
44 #include <ctype.h>
45
46 /* System-specific feature definitions and include files. */
47 #include "rldefs.h"
48 #include "rlmbutil.h"
49
50 #if defined (TIOCSTAT_IN_SYS_IOCTL)
51 #  include <sys/ioctl.h>
52 #endif /* TIOCSTAT_IN_SYS_IOCTL */
53
54 /* Some standard library routines. */
55 #include "readline.h"
56
57 #include "rlprivate.h"
58 #include "xmalloc.h"
59
60 /* **************************************************************** */
61 /*                                                                  */
62 /*                      Utility Functions                           */
63 /*                                                                  */
64 /* **************************************************************** */
65
66 /* Return 0 if C is not a member of the class of characters that belong
67    in words, or 1 if it is. */
68
69 int _rl_allow_pathname_alphabetic_chars = 0;
70 static const char *pathname_alphabetic_chars = "/-_=~.#$";
71
72 int
73 rl_alphabetic (c)
74      int c;
75 {
76   if (ALPHABETIC (c))
77     return (1);
78
79   return (_rl_allow_pathname_alphabetic_chars &&
80             strchr (pathname_alphabetic_chars, c) != NULL);
81 }
82
83 #if defined (HANDLE_MULTIBYTE)
84 int
85 _rl_walphabetic (wc)
86      wchar_t wc;
87 {
88   int c;
89
90   if (iswalnum (wc))
91     return (1);     
92
93   c = wc & 0177;
94   return (_rl_allow_pathname_alphabetic_chars &&
95             strchr (pathname_alphabetic_chars, c) != NULL);
96 }
97 #endif
98
99 /* How to abort things. */
100 int
101 _rl_abort_internal ()
102 {
103   rl_ding ();
104   rl_clear_message ();
105   _rl_reset_argument ();
106   rl_clear_pending_input ();
107
108   RL_UNSETSTATE (RL_STATE_MACRODEF);
109   while (rl_executing_macro)
110     _rl_pop_executing_macro ();
111
112   rl_last_func = (rl_command_func_t *)NULL;
113   longjmp (readline_top_level, 1);
114   return (0);
115 }
116
117 int
118 rl_abort (count, key)
119      int count, key;
120 {
121   return (_rl_abort_internal ());
122 }
123
124 int
125 rl_tty_status (count, key)
126      int count, key;
127 {
128 #if defined (TIOCSTAT)
129   ioctl (1, TIOCSTAT, (char *)0);
130   rl_refresh_line (count, key);
131 #else
132   rl_ding ();
133 #endif
134   return 0;
135 }
136
137 /* Return a copy of the string between FROM and TO.
138    FROM is inclusive, TO is not. */
139 char *
140 rl_copy_text (from, to)
141      int from, to;
142 {
143   register int length;
144   char *copy;
145
146   /* Fix it if the caller is confused. */
147   if (from > to)
148     SWAP (from, to);
149
150   length = to - from;
151   copy = (char *)xmalloc (1 + length);
152   strncpy (copy, rl_line_buffer + from, length);
153   copy[length] = '\0';
154   return (copy);
155 }
156
157 /* Increase the size of RL_LINE_BUFFER until it has enough space to hold
158    LEN characters. */
159 void
160 rl_extend_line_buffer (len)
161      int len;
162 {
163   while (len >= rl_line_buffer_len)
164     {
165       rl_line_buffer_len += DEFAULT_BUFFER_SIZE;
166       rl_line_buffer = (char *)xrealloc (rl_line_buffer, rl_line_buffer_len);
167     }
168
169   _rl_set_the_line ();
170 }
171
172
173 /* A function for simple tilde expansion. */
174 int
175 rl_tilde_expand (ignore, key)
176      int ignore, key;
177 {
178   register int start, end;
179   char *homedir, *temp;
180   int len;
181
182   end = rl_point;
183   start = end - 1;
184
185   if (rl_point == rl_end && rl_line_buffer[rl_point] == '~')
186     {
187       homedir = tilde_expand ("~");
188       _rl_replace_text (homedir, start, end);
189       return (0);
190     }
191   else if (rl_line_buffer[start] != '~')
192     {
193       for (; !whitespace (rl_line_buffer[start]) && start >= 0; start--)
194         ;
195       start++;
196     }
197
198   end = start;
199   do
200     end++;
201   while (whitespace (rl_line_buffer[end]) == 0 && end < rl_end);
202
203   if (whitespace (rl_line_buffer[end]) || end >= rl_end)
204     end--;
205
206   /* If the first character of the current word is a tilde, perform
207      tilde expansion and insert the result.  If not a tilde, do
208      nothing. */
209   if (rl_line_buffer[start] == '~')
210     {
211       len = end - start + 1;
212       temp = (char *)xmalloc (len + 1);
213       strncpy (temp, rl_line_buffer + start, len);
214       temp[len] = '\0';
215       homedir = tilde_expand (temp);
216       free (temp);
217
218       _rl_replace_text (homedir, start, end);
219     }
220
221   return (0);
222 }
223
224 /* **************************************************************** */
225 /*                                                                  */
226 /*                      String Utility Functions                    */
227 /*                                                                  */
228 /* **************************************************************** */
229
230 /* Determine if s2 occurs in s1.  If so, return a pointer to the
231    match in s1.  The compare is case insensitive. */
232 char *
233 _rl_strindex (s1, s2)
234      register const char *s1, *s2;
235 {
236   register int i, l, len;
237
238   for (i = 0, l = strlen (s2), len = strlen (s1); (len - i) >= l; i++)
239     if (_rl_strnicmp (s1 + i, s2, l) == 0)
240       return ((char *) (s1 + i));
241   return ((char *)NULL);
242 }
243
244 #ifndef HAVE_STRPBRK
245 /* Find the first occurrence in STRING1 of any character from STRING2.
246    Return a pointer to the character in STRING1. */
247 char *
248 _rl_strpbrk (string1, string2)
249      const char *string1, *string2;
250 {
251   register const char *scan;
252 #if defined (HANDLE_MULTIBYTE)
253   mbstate_t ps;
254   register int i, v;
255
256   memset (&ps, 0, sizeof (mbstate_t));
257 #endif
258
259   for (; *string1; string1++)
260     {
261       for (scan = string2; *scan; scan++)
262         {
263           if (*string1 == *scan)
264             return ((char *)string1);
265         }
266 #if defined (HANDLE_MULTIBYTE)
267       if (MB_CUR_MAX > 1 && rl_byte_oriented == 0)
268         {
269           v = _rl_get_char_len (string1, &ps);
270           if (v > 1)
271             string1 += v - 1;   /* -1 to account for auto-increment in loop */
272         }
273 #endif
274     }
275   return ((char *)NULL);
276 }
277 #endif
278
279 #if !defined (HAVE_STRCASECMP)
280 /* Compare at most COUNT characters from string1 to string2.  Case
281    doesn't matter. */
282 int
283 _rl_strnicmp (string1, string2, count)
284      char *string1, *string2;
285      int count;
286 {
287   register char ch1, ch2;
288
289   while (count)
290     {
291       ch1 = *string1++;
292       ch2 = *string2++;
293       if (_rl_to_upper(ch1) == _rl_to_upper(ch2))
294         count--;
295       else
296         break;
297     }
298   return (count);
299 }
300
301 /* strcmp (), but caseless. */
302 int
303 _rl_stricmp (string1, string2)
304      char *string1, *string2;
305 {
306   register char ch1, ch2;
307
308   while (*string1 && *string2)
309     {
310       ch1 = *string1++;
311       ch2 = *string2++;
312       if (_rl_to_upper(ch1) != _rl_to_upper(ch2))
313         return (1);
314     }
315   return (*string1 - *string2);
316 }
317 #endif /* !HAVE_STRCASECMP */
318
319 /* Stupid comparison routine for qsort () ing strings. */
320 int
321 _rl_qsort_string_compare (s1, s2)
322   char **s1, **s2;
323 {
324 #if defined (HAVE_STRCOLL)
325   return (strcoll (*s1, *s2));
326 #else
327   int result;
328
329   result = **s1 - **s2;
330   if (result == 0)
331     result = strcmp (*s1, *s2);
332
333   return result;
334 #endif
335 }
336
337 /* Function equivalents for the macros defined in chardefs.h. */
338 #define FUNCTION_FOR_MACRO(f)   int (f) (c) int c; { return f (c); }
339
340 FUNCTION_FOR_MACRO (_rl_digit_p)
341 FUNCTION_FOR_MACRO (_rl_digit_value)
342 FUNCTION_FOR_MACRO (_rl_lowercase_p)
343 FUNCTION_FOR_MACRO (_rl_pure_alphabetic)
344 FUNCTION_FOR_MACRO (_rl_to_lower)
345 FUNCTION_FOR_MACRO (_rl_to_upper)
346 FUNCTION_FOR_MACRO (_rl_uppercase_p)
347
348 /* Backwards compatibility, now that savestring has been removed from
349    all `public' readline header files. */
350 #undef _rl_savestring
351 char *
352 _rl_savestring (s)
353      const char *s;
354 {
355   return (strcpy ((char *)xmalloc (1 + (int)strlen (s)), (s)));
356 }