Imported from ../bash-3.1.tar.gz.
[platform/upstream/bash.git] / lib / readline / misc.c
1 /* misc.c -- miscellaneous bindable readline functions. */
2
3 /* Copyright (C) 1987-2005 Free Software Foundation, Inc.
4
5    This file is part of the GNU Readline Library, a library for
6    reading lines of text with interactive input and history editing.
7
8    The GNU Readline Library is free software; you can redistribute it
9    and/or modify it under the terms of the GNU General Public License
10    as published by the Free Software Foundation; either version 2, or
11    (at your option) any later version.
12
13    The GNU Readline Library is distributed in the hope that it will be
14    useful, but WITHOUT ANY WARRANTY; without even the implied warranty
15    of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16    GNU General Public License for more details.
17
18    The GNU General Public License is often shipped with GNU software, and
19    is generally kept in a file called COPYING or LICENSE.  If you do not
20    have a copy of the license, write to the Free Software Foundation,
21    59 Temple Place, Suite 330, Boston, MA 02111 USA. */
22 #define READLINE_LIBRARY
23
24 #if defined (HAVE_CONFIG_H)
25 #  include <config.h>
26 #endif
27
28 #if defined (HAVE_UNISTD_H)
29 #  include <unistd.h>
30 #endif /* HAVE_UNISTD_H */
31
32 #if defined (HAVE_STDLIB_H)
33 #  include <stdlib.h>
34 #else
35 #  include "ansi_stdlib.h"
36 #endif /* HAVE_STDLIB_H */
37
38 #if defined (HAVE_LOCALE_H)
39 #  include <locale.h>
40 #endif
41
42 #include <stdio.h>
43
44 /* System-specific feature definitions and include files. */
45 #include "rldefs.h"
46 #include "rlmbutil.h"
47
48 /* Some standard library routines. */
49 #include "readline.h"
50 #include "history.h"
51
52 #include "rlprivate.h"
53 #include "rlshell.h"
54 #include "xmalloc.h"
55
56 static int rl_digit_loop PARAMS((void));
57 static void _rl_history_set_point PARAMS((void));
58
59 /* Forward declarations used in this file */
60 void _rl_free_history_entry PARAMS((HIST_ENTRY *));
61
62 /* If non-zero, rl_get_previous_history and rl_get_next_history attempt
63    to preserve the value of rl_point from line to line. */
64 int _rl_history_preserve_point = 0;
65
66 _rl_arg_cxt _rl_argcxt;
67
68 /* Saved target point for when _rl_history_preserve_point is set.  Special
69    value of -1 means that point is at the end of the line. */
70 int _rl_history_saved_point = -1;
71
72 /* **************************************************************** */
73 /*                                                                  */
74 /*                      Numeric Arguments                           */
75 /*                                                                  */
76 /* **************************************************************** */
77
78 int
79 _rl_arg_overflow ()
80 {
81   if (rl_numeric_arg > 1000000)
82     {
83       _rl_argcxt = 0;
84       rl_explicit_arg = rl_numeric_arg = 0;
85       rl_ding ();
86       rl_restore_prompt ();
87       rl_clear_message ();
88       RL_UNSETSTATE(RL_STATE_NUMERICARG);
89       return 1;
90     }
91   return 0;
92 }
93
94 void
95 _rl_arg_init ()
96 {
97   rl_save_prompt ();
98   _rl_argcxt = 0;
99   RL_SETSTATE(RL_STATE_NUMERICARG);
100 }
101
102 int
103 _rl_arg_getchar ()
104 {
105   int c;
106
107   rl_message ("(arg: %d) ", rl_arg_sign * rl_numeric_arg);
108   RL_SETSTATE(RL_STATE_MOREINPUT);
109   c = rl_read_key ();
110   RL_UNSETSTATE(RL_STATE_MOREINPUT);
111
112   return c;
113 }
114
115 /* Process C as part of the current numeric argument.  Return -1 if the
116    argument should be aborted, 0 if we should not read any more chars, and
117    1 if we should continue to read chars. */
118 int
119 _rl_arg_dispatch (cxt, c)
120      _rl_arg_cxt cxt;
121      int c;
122 {
123   int key, r;
124
125   key = c;
126
127   /* If we see a key bound to `universal-argument' after seeing digits,
128       it ends the argument but is otherwise ignored. */
129   if (_rl_keymap[c].type == ISFUNC && _rl_keymap[c].function == rl_universal_argument)
130     {
131       if ((cxt & NUM_SAWDIGITS) == 0)
132         {
133           rl_numeric_arg *= 4;
134           return 1;
135         }
136       else if (RL_ISSTATE (RL_STATE_CALLBACK))
137         {
138           _rl_argcxt |= NUM_READONE;
139           return 0;     /* XXX */
140         }
141       else
142         {
143           RL_SETSTATE(RL_STATE_MOREINPUT);
144           key = rl_read_key ();
145           RL_UNSETSTATE(RL_STATE_MOREINPUT);
146           rl_restore_prompt ();
147           rl_clear_message ();
148           RL_UNSETSTATE(RL_STATE_NUMERICARG);
149           return (_rl_dispatch (key, _rl_keymap));
150         }
151     }
152
153   c = UNMETA (c);
154
155   if (_rl_digit_p (c))
156     {
157       r = _rl_digit_value (c);          
158       rl_numeric_arg = rl_explicit_arg ? (rl_numeric_arg * 10) +  r : r;
159       rl_explicit_arg = 1;
160       _rl_argcxt |= NUM_SAWDIGITS;
161     }
162   else if (c == '-' && rl_explicit_arg == 0)
163     {
164       rl_numeric_arg = 1;
165       _rl_argcxt |= NUM_SAWMINUS;
166       rl_arg_sign = -1;
167     }
168   else
169     {
170       /* Make M-- command equivalent to M--1 command. */
171       if ((_rl_argcxt & NUM_SAWMINUS) && rl_numeric_arg == 1 && rl_explicit_arg == 0)
172         rl_explicit_arg = 1;
173       rl_restore_prompt ();
174       rl_clear_message ();
175       RL_UNSETSTATE(RL_STATE_NUMERICARG);
176
177       r = _rl_dispatch (key, _rl_keymap);
178       if (RL_ISSTATE (RL_STATE_CALLBACK))
179         {
180           /* At worst, this will cause an extra redisplay.  Otherwise,
181              we have to wait until the next character comes in. */
182           if (rl_done == 0)
183             (*rl_redisplay_function) ();
184           r = 0;
185         }
186       return r;
187     }
188
189   return 1;
190 }
191
192 /* Handle C-u style numeric args, as well as M--, and M-digits. */
193 static int
194 rl_digit_loop ()
195 {
196   int c, r;
197
198   while (1)
199     {
200       if (_rl_arg_overflow ())
201         return 1;
202
203       c = _rl_arg_getchar ();
204
205       if (c < 0)
206         {
207           _rl_abort_internal ();
208           return -1;
209         }
210
211       r = _rl_arg_dispatch (_rl_argcxt, c);
212       if (r <= 0 || (RL_ISSTATE (RL_STATE_NUMERICARG) == 0))
213         break;
214     }
215 }
216
217 /* Create a default argument. */
218 void
219 _rl_reset_argument ()
220 {
221   rl_numeric_arg = rl_arg_sign = 1;
222   rl_explicit_arg = 0;
223   _rl_argcxt = 0;
224 }
225
226 /* Start a numeric argument with initial value KEY */
227 int
228 rl_digit_argument (ignore, key)
229      int ignore, key;
230 {
231   _rl_arg_init ();
232   if (RL_ISSTATE (RL_STATE_CALLBACK))
233     {
234       _rl_arg_dispatch (_rl_argcxt, key);
235       rl_message ("(arg: %d) ", rl_arg_sign * rl_numeric_arg);
236       return 0;
237     }
238   else
239     {
240       rl_execute_next (key);
241       return (rl_digit_loop ());
242     }
243 }
244
245 /* C-u, universal argument.  Multiply the current argument by 4.
246    Read a key.  If the key has nothing to do with arguments, then
247    dispatch on it.  If the key is the abort character then abort. */
248 int
249 rl_universal_argument (count, key)
250      int count, key;
251 {
252   _rl_arg_init ();
253   rl_numeric_arg *= 4;
254
255   return (RL_ISSTATE (RL_STATE_CALLBACK) ? 0 : rl_digit_loop ());
256 }
257
258 int
259 _rl_arg_callback (cxt)
260      _rl_arg_cxt cxt;
261 {
262   int c, r;
263
264   c = _rl_arg_getchar ();
265
266   if (_rl_argcxt & NUM_READONE)
267     {
268       _rl_argcxt &= ~NUM_READONE;
269       rl_restore_prompt ();
270       rl_clear_message ();
271       RL_UNSETSTATE(RL_STATE_NUMERICARG);
272       rl_execute_next (c);
273       return 0;
274     }
275
276   r = _rl_arg_dispatch (cxt, c);
277   return (r != 1);
278 }
279
280 /* What to do when you abort reading an argument. */
281 int
282 rl_discard_argument ()
283 {
284   rl_ding ();
285   rl_clear_message ();
286   _rl_reset_argument ();
287
288   return 0;
289 }
290
291 /* **************************************************************** */
292 /*                                                                  */
293 /*                      History Utilities                           */
294 /*                                                                  */
295 /* **************************************************************** */
296
297 /* We already have a history library, and that is what we use to control
298    the history features of readline.  This is our local interface to
299    the history mechanism. */
300
301 /* While we are editing the history, this is the saved
302    version of the original line. */
303 HIST_ENTRY *_rl_saved_line_for_history = (HIST_ENTRY *)NULL;
304
305 /* Set the history pointer back to the last entry in the history. */
306 void
307 _rl_start_using_history ()
308 {
309   using_history ();
310   if (_rl_saved_line_for_history)
311     _rl_free_history_entry (_rl_saved_line_for_history);
312
313   _rl_saved_line_for_history = (HIST_ENTRY *)NULL;
314 }
315
316 /* Free the contents (and containing structure) of a HIST_ENTRY. */
317 void
318 _rl_free_history_entry (entry)
319      HIST_ENTRY *entry;
320 {
321   if (entry == 0)
322     return;
323
324   FREE (entry->line);
325   FREE (entry->timestamp);
326
327   free (entry);
328 }
329
330 /* Perhaps put back the current line if it has changed. */
331 int
332 rl_maybe_replace_line ()
333 {
334   HIST_ENTRY *temp;
335
336   temp = current_history ();
337   /* If the current line has changed, save the changes. */
338   if (temp && ((UNDO_LIST *)(temp->data) != rl_undo_list))
339     {
340       temp = replace_history_entry (where_history (), rl_line_buffer, (histdata_t)rl_undo_list);
341       free (temp->line);
342       FREE (temp->timestamp);
343       free (temp);
344     }
345   return 0;
346 }
347
348 /* Restore the _rl_saved_line_for_history if there is one. */
349 int
350 rl_maybe_unsave_line ()
351 {
352   if (_rl_saved_line_for_history)
353     {
354       /* Can't call with `1' because rl_undo_list might point to an undo
355          list from a history entry, as in rl_replace_from_history() below. */
356       rl_replace_line (_rl_saved_line_for_history->line, 0);
357       rl_undo_list = (UNDO_LIST *)_rl_saved_line_for_history->data;
358       _rl_free_history_entry (_rl_saved_line_for_history);
359       _rl_saved_line_for_history = (HIST_ENTRY *)NULL;
360       rl_point = rl_end;        /* rl_replace_line sets rl_end */
361     }
362   else
363     rl_ding ();
364   return 0;
365 }
366
367 /* Save the current line in _rl_saved_line_for_history. */
368 int
369 rl_maybe_save_line ()
370 {
371   if (_rl_saved_line_for_history == 0)
372     {
373       _rl_saved_line_for_history = (HIST_ENTRY *)xmalloc (sizeof (HIST_ENTRY));
374       _rl_saved_line_for_history->line = savestring (rl_line_buffer);
375       _rl_saved_line_for_history->timestamp = (char *)NULL;
376       _rl_saved_line_for_history->data = (char *)rl_undo_list;
377     }
378
379   return 0;
380 }
381
382 int
383 _rl_free_saved_history_line ()
384 {
385   if (_rl_saved_line_for_history)
386     {
387       _rl_free_history_entry (_rl_saved_line_for_history);
388       _rl_saved_line_for_history = (HIST_ENTRY *)NULL;
389     }
390   return 0;
391 }
392
393 static void
394 _rl_history_set_point ()
395 {
396   rl_point = (_rl_history_preserve_point && _rl_history_saved_point != -1)
397                 ? _rl_history_saved_point
398                 : rl_end;
399   if (rl_point > rl_end)
400     rl_point = rl_end;
401
402 #if defined (VI_MODE)
403   if (rl_editing_mode == vi_mode && _rl_keymap != vi_insertion_keymap)
404     rl_point = 0;
405 #endif /* VI_MODE */
406
407   if (rl_editing_mode == emacs_mode)
408     rl_mark = (rl_point == rl_end ? 0 : rl_end);
409 }
410
411 void
412 rl_replace_from_history (entry, flags)
413      HIST_ENTRY *entry;
414      int flags;                 /* currently unused */
415 {
416   /* Can't call with `1' because rl_undo_list might point to an undo list
417      from a history entry, just like we're setting up here. */
418   rl_replace_line (entry->line, 0);
419   rl_undo_list = (UNDO_LIST *)entry->data;
420   rl_point = rl_end;
421   rl_mark = 0;
422
423 #if defined (VI_MODE)
424   if (rl_editing_mode == vi_mode)
425     {
426       rl_point = 0;
427       rl_mark = rl_end;
428     }
429 #endif
430 }  
431
432 /* **************************************************************** */
433 /*                                                                  */
434 /*                      History Commands                            */
435 /*                                                                  */
436 /* **************************************************************** */
437
438 /* Meta-< goes to the start of the history. */
439 int
440 rl_beginning_of_history (count, key)
441      int count, key;
442 {
443   return (rl_get_previous_history (1 + where_history (), key));
444 }
445
446 /* Meta-> goes to the end of the history.  (The current line). */
447 int
448 rl_end_of_history (count, key)
449      int count, key;
450 {
451   rl_maybe_replace_line ();
452   using_history ();
453   rl_maybe_unsave_line ();
454   return 0;
455 }
456
457 /* Move down to the next history line. */
458 int
459 rl_get_next_history (count, key)
460      int count, key;
461 {
462   HIST_ENTRY *temp;
463
464   if (count < 0)
465     return (rl_get_previous_history (-count, key));
466
467   if (count == 0)
468     return 0;
469
470   rl_maybe_replace_line ();
471
472   /* either not saved by rl_newline or at end of line, so set appropriately. */
473   if (_rl_history_saved_point == -1 && (rl_point || rl_end))
474     _rl_history_saved_point = (rl_point == rl_end) ? -1 : rl_point;
475
476   temp = (HIST_ENTRY *)NULL;
477   while (count)
478     {
479       temp = next_history ();
480       if (!temp)
481         break;
482       --count;
483     }
484
485   if (temp == 0)
486     rl_maybe_unsave_line ();
487   else
488     {
489       rl_replace_from_history (temp, 0);
490       _rl_history_set_point ();
491     }
492   return 0;
493 }
494
495 /* Get the previous item out of our interactive history, making it the current
496    line.  If there is no previous history, just ding. */
497 int
498 rl_get_previous_history (count, key)
499      int count, key;
500 {
501   HIST_ENTRY *old_temp, *temp;
502
503   if (count < 0)
504     return (rl_get_next_history (-count, key));
505
506   if (count == 0)
507     return 0;
508
509   /* either not saved by rl_newline or at end of line, so set appropriately. */
510   if (_rl_history_saved_point == -1 && (rl_point || rl_end))
511     _rl_history_saved_point = (rl_point == rl_end) ? -1 : rl_point;
512
513   /* If we don't have a line saved, then save this one. */
514   rl_maybe_save_line ();
515
516   /* If the current line has changed, save the changes. */
517   rl_maybe_replace_line ();
518
519   temp = old_temp = (HIST_ENTRY *)NULL;
520   while (count)
521     {
522       temp = previous_history ();
523       if (temp == 0)
524         break;
525
526       old_temp = temp;
527       --count;
528     }
529
530   /* If there was a large argument, and we moved back to the start of the
531      history, that is not an error.  So use the last value found. */
532   if (!temp && old_temp)
533     temp = old_temp;
534
535   if (temp == 0)
536     rl_ding ();
537   else
538     {
539       rl_replace_from_history (temp, 0);
540       _rl_history_set_point ();
541     }
542
543   return 0;
544 }
545
546 /* **************************************************************** */
547 /*                                                                  */
548 /*                          Editing Modes                           */
549 /*                                                                  */
550 /* **************************************************************** */
551 /* How to toggle back and forth between editing modes. */
552 int
553 rl_vi_editing_mode (count, key)
554      int count, key;
555 {
556 #if defined (VI_MODE)
557   _rl_set_insert_mode (RL_IM_INSERT, 1);        /* vi mode ignores insert mode */
558   rl_editing_mode = vi_mode;
559   rl_vi_insertion_mode (1, key);
560 #endif /* VI_MODE */
561
562   return 0;
563 }
564
565 int
566 rl_emacs_editing_mode (count, key)
567      int count, key;
568 {
569   rl_editing_mode = emacs_mode;
570   _rl_set_insert_mode (RL_IM_INSERT, 1); /* emacs mode default is insert mode */
571   _rl_keymap = emacs_standard_keymap;
572   return 0;
573 }
574
575 /* Function for the rest of the library to use to set insert/overwrite mode. */
576 void
577 _rl_set_insert_mode (im, force)
578      int im, force;
579 {
580 #ifdef CURSOR_MODE
581   _rl_set_cursor (im, force);
582 #endif
583
584   rl_insert_mode = im;
585 }
586
587 /* Toggle overwrite mode.  A positive explicit argument selects overwrite
588    mode.  A negative or zero explicit argument selects insert mode. */
589 int
590 rl_overwrite_mode (count, key)
591      int count, key;
592 {
593   if (rl_explicit_arg == 0)
594     _rl_set_insert_mode (rl_insert_mode ^ 1, 0);
595   else if (count > 0)
596     _rl_set_insert_mode (RL_IM_OVERWRITE, 0);
597   else
598     _rl_set_insert_mode (RL_IM_INSERT, 0);
599
600   return 0;
601 }