Annotation of embedaddon/readline/bind.c, revision 1.1.1.1

1.1       misho       1: /* bind.c -- key binding and startup file support for the readline library. */
                      2: 
                      3: /* Copyright (C) 1987-2012 Free Software Foundation, Inc.
                      4: 
                      5:    This file is part of the GNU Readline Library (Readline), a library
                      6:    for reading lines of text with interactive input and history editing.
                      7: 
                      8:    Readline 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:    Readline 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 Readline.  If not, see <http://www.gnu.org/licenses/>.
                     20: */
                     21: 
                     22: #define READLINE_LIBRARY
                     23: 
                     24: #if defined (__TANDEM)
                     25: #  include <floss.h>
                     26: #endif
                     27: 
                     28: #if defined (HAVE_CONFIG_H)
                     29: #  include <config.h>
                     30: #endif
                     31: 
                     32: #include <stdio.h>
                     33: #include <sys/types.h>
                     34: #include <fcntl.h>
                     35: #if defined (HAVE_SYS_FILE_H)
                     36: #  include <sys/file.h>
                     37: #endif /* HAVE_SYS_FILE_H */
                     38: 
                     39: #if defined (HAVE_UNISTD_H)
                     40: #  include <unistd.h>
                     41: #endif /* HAVE_UNISTD_H */
                     42: 
                     43: #if defined (HAVE_STDLIB_H)
                     44: #  include <stdlib.h>
                     45: #else
                     46: #  include "ansi_stdlib.h"
                     47: #endif /* HAVE_STDLIB_H */
                     48: 
                     49: #include <errno.h>
                     50: 
                     51: #if !defined (errno)
                     52: extern int errno;
                     53: #endif /* !errno */
                     54: 
                     55: #include "posixstat.h"
                     56: 
                     57: /* System-specific feature definitions and include files. */
                     58: #include "rldefs.h"
                     59: 
                     60: /* Some standard library routines. */
                     61: #include "readline.h"
                     62: #include "history.h"
                     63: 
                     64: #include "rlprivate.h"
                     65: #include "rlshell.h"
                     66: #include "xmalloc.h"
                     67: 
                     68: #if !defined (strchr) && !defined (__STDC__)
                     69: extern char *strchr (), *strrchr ();
                     70: #endif /* !strchr && !__STDC__ */
                     71: 
                     72: /* Variables exported by this file. */
                     73: Keymap rl_binding_keymap;
                     74: 
                     75: static int _rl_skip_to_delim PARAMS((char *, int, int));
                     76: 
                     77: static char *_rl_read_file PARAMS((char *, size_t *));
                     78: static void _rl_init_file_error PARAMS((const char *));
                     79: static int _rl_read_init_file PARAMS((const char *, int));
                     80: static int glean_key_from_name PARAMS((char *));
                     81: 
                     82: static int find_boolean_var PARAMS((const char *));
                     83: static int find_string_var PARAMS((const char *));
                     84: 
                     85: static char *_rl_get_string_variable_value PARAMS((const char *));
                     86: static int substring_member_of_array PARAMS((const char *, const char * const *));
                     87: 
                     88: static int currently_reading_init_file;
                     89: 
                     90: /* used only in this file */
                     91: static int _rl_prefer_visible_bell = 1;
                     92: 
                     93: /* **************************************************************** */
                     94: /*                                                                 */
                     95: /*                     Binding keys                                */
                     96: /*                                                                 */
                     97: /* **************************************************************** */
                     98: 
                     99: /* rl_add_defun (char *name, rl_command_func_t *function, int key)
                    100:    Add NAME to the list of named functions.  Make FUNCTION be the function
                    101:    that gets called.  If KEY is not -1, then bind it. */
                    102: int
                    103: rl_add_defun (name, function, key)
                    104:      const char *name;
                    105:      rl_command_func_t *function;
                    106:      int key;
                    107: {
                    108:   if (key != -1)
                    109:     rl_bind_key (key, function);
                    110:   rl_add_funmap_entry (name, function);
                    111:   return 0;
                    112: }
                    113: 
                    114: /* Bind KEY to FUNCTION.  Returns non-zero if KEY is out of range. */
                    115: int
                    116: rl_bind_key (key, function)
                    117:      int key;
                    118:      rl_command_func_t *function;
                    119: {
                    120:   if (key < 0)
                    121:     return (key);
                    122: 
                    123:   if (META_CHAR (key) && _rl_convert_meta_chars_to_ascii)
                    124:     {
                    125:       if (_rl_keymap[ESC].type == ISKMAP)
                    126:        {
                    127:          Keymap escmap;
                    128: 
                    129:          escmap = FUNCTION_TO_KEYMAP (_rl_keymap, ESC);
                    130:          key = UNMETA (key);
                    131:          escmap[key].type = ISFUNC;
                    132:          escmap[key].function = function;
                    133:          return (0);
                    134:        }
                    135:       return (key);
                    136:     }
                    137: 
                    138:   _rl_keymap[key].type = ISFUNC;
                    139:   _rl_keymap[key].function = function;
                    140:   rl_binding_keymap = _rl_keymap;
                    141:   return (0);
                    142: }
                    143: 
                    144: /* Bind KEY to FUNCTION in MAP.  Returns non-zero in case of invalid
                    145:    KEY. */
                    146: int
                    147: rl_bind_key_in_map (key, function, map)
                    148:      int key;
                    149:      rl_command_func_t *function;
                    150:      Keymap map;
                    151: {
                    152:   int result;
                    153:   Keymap oldmap;
                    154: 
                    155:   oldmap = _rl_keymap;
                    156:   _rl_keymap = map;
                    157:   result = rl_bind_key (key, function);
                    158:   _rl_keymap = oldmap;
                    159:   return (result);
                    160: }
                    161: 
                    162: /* Bind key sequence KEYSEQ to DEFAULT_FUNC if KEYSEQ is unbound.  Right
                    163:    now, this is always used to attempt to bind the arrow keys, hence the
                    164:    check for rl_vi_movement_mode. */
                    165: int
                    166: rl_bind_key_if_unbound_in_map (key, default_func, kmap)
                    167:      int key;
                    168:      rl_command_func_t *default_func;
                    169:      Keymap kmap;
                    170: {
                    171:   char keyseq[2];
                    172: 
                    173:   keyseq[0] = (unsigned char)key;
                    174:   keyseq[1] = '\0';
                    175:   return (rl_bind_keyseq_if_unbound_in_map (keyseq, default_func, kmap));
                    176: }
                    177: 
                    178: int
                    179: rl_bind_key_if_unbound (key, default_func)
                    180:      int key;
                    181:      rl_command_func_t *default_func;
                    182: {
                    183:   char keyseq[2];
                    184: 
                    185:   keyseq[0] = (unsigned char)key;
                    186:   keyseq[1] = '\0';
                    187:   return (rl_bind_keyseq_if_unbound_in_map (keyseq, default_func, _rl_keymap));
                    188: }
                    189: 
                    190: /* Make KEY do nothing in the currently selected keymap.
                    191:    Returns non-zero in case of error. */
                    192: int
                    193: rl_unbind_key (key)
                    194:      int key;
                    195: {
                    196:   return (rl_bind_key (key, (rl_command_func_t *)NULL));
                    197: }
                    198: 
                    199: /* Make KEY do nothing in MAP.
                    200:    Returns non-zero in case of error. */
                    201: int
                    202: rl_unbind_key_in_map (key, map)
                    203:      int key;
                    204:      Keymap map;
                    205: {
                    206:   return (rl_bind_key_in_map (key, (rl_command_func_t *)NULL, map));
                    207: }
                    208: 
                    209: /* Unbind all keys bound to FUNCTION in MAP. */
                    210: int
                    211: rl_unbind_function_in_map (func, map)
                    212:      rl_command_func_t *func;
                    213:      Keymap map;
                    214: {
                    215:   register int i, rval;
                    216: 
                    217:   for (i = rval = 0; i < KEYMAP_SIZE; i++)
                    218:     {
                    219:       if (map[i].type == ISFUNC && map[i].function == func)
                    220:        {
                    221:          map[i].function = (rl_command_func_t *)NULL;
                    222:          rval = 1;
                    223:        }
                    224:     }
                    225:   return rval;
                    226: }
                    227: 
                    228: int
                    229: rl_unbind_command_in_map (command, map)
                    230:      const char *command;
                    231:      Keymap map;
                    232: {
                    233:   rl_command_func_t *func;
                    234: 
                    235:   func = rl_named_function (command);
                    236:   if (func == 0)
                    237:     return 0;
                    238:   return (rl_unbind_function_in_map (func, map));
                    239: }
                    240: 
                    241: /* Bind the key sequence represented by the string KEYSEQ to
                    242:    FUNCTION, starting in the current keymap.  This makes new
                    243:    keymaps as necessary. */
                    244: int
                    245: rl_bind_keyseq (keyseq, function)
                    246:      const char *keyseq;
                    247:      rl_command_func_t *function;
                    248: {
                    249:   return (rl_generic_bind (ISFUNC, keyseq, (char *)function, _rl_keymap));
                    250: }
                    251: 
                    252: /* Bind the key sequence represented by the string KEYSEQ to
                    253:    FUNCTION.  This makes new keymaps as necessary.  The initial
                    254:    place to do bindings is in MAP. */
                    255: int
                    256: rl_bind_keyseq_in_map (keyseq, function, map)
                    257:      const char *keyseq;
                    258:      rl_command_func_t *function;
                    259:      Keymap map;
                    260: {
                    261:   return (rl_generic_bind (ISFUNC, keyseq, (char *)function, map));
                    262: }
                    263: 
                    264: /* Backwards compatibility; equivalent to rl_bind_keyseq_in_map() */
                    265: int
                    266: rl_set_key (keyseq, function, map)
                    267:      const char *keyseq;
                    268:      rl_command_func_t *function;
                    269:      Keymap map;
                    270: {
                    271:   return (rl_generic_bind (ISFUNC, keyseq, (char *)function, map));
                    272: }
                    273: 
                    274: /* Bind key sequence KEYSEQ to DEFAULT_FUNC if KEYSEQ is unbound.  Right
                    275:    now, this is always used to attempt to bind the arrow keys, hence the
                    276:    check for rl_vi_movement_mode. */
                    277: int
                    278: rl_bind_keyseq_if_unbound_in_map (keyseq, default_func, kmap)
                    279:      const char *keyseq;
                    280:      rl_command_func_t *default_func;
                    281:      Keymap kmap;
                    282: {
                    283:   rl_command_func_t *func;
                    284: 
                    285:   if (keyseq)
                    286:     {
                    287:       func = rl_function_of_keyseq (keyseq, kmap, (int *)NULL);
                    288: #if defined (VI_MODE)
                    289:       if (!func || func == rl_do_lowercase_version || func == rl_vi_movement_mode)
                    290: #else
                    291:       if (!func || func == rl_do_lowercase_version)
                    292: #endif
                    293:        return (rl_bind_keyseq_in_map (keyseq, default_func, kmap));
                    294:       else
                    295:        return 1;
                    296:     }
                    297:   return 0;
                    298: }
                    299: 
                    300: int
                    301: rl_bind_keyseq_if_unbound (keyseq, default_func)
                    302:      const char *keyseq;
                    303:      rl_command_func_t *default_func;
                    304: {
                    305:   return (rl_bind_keyseq_if_unbound_in_map (keyseq, default_func, _rl_keymap));
                    306: }
                    307: 
                    308: /* Bind the key sequence represented by the string KEYSEQ to
                    309:    the string of characters MACRO.  This makes new keymaps as
                    310:    necessary.  The initial place to do bindings is in MAP. */
                    311: int
                    312: rl_macro_bind (keyseq, macro, map)
                    313:      const char *keyseq, *macro;
                    314:      Keymap map;
                    315: {
                    316:   char *macro_keys;
                    317:   int macro_keys_len;
                    318: 
                    319:   macro_keys = (char *)xmalloc ((2 * strlen (macro)) + 1);
                    320: 
                    321:   if (rl_translate_keyseq (macro, macro_keys, &macro_keys_len))
                    322:     {
                    323:       xfree (macro_keys);
                    324:       return -1;
                    325:     }
                    326:   rl_generic_bind (ISMACR, keyseq, macro_keys, map);
                    327:   return 0;
                    328: }
                    329: 
                    330: /* Bind the key sequence represented by the string KEYSEQ to
                    331:    the arbitrary pointer DATA.  TYPE says what kind of data is
                    332:    pointed to by DATA, right now this can be a function (ISFUNC),
                    333:    a macro (ISMACR), or a keymap (ISKMAP).  This makes new keymaps
                    334:    as necessary.  The initial place to do bindings is in MAP. */
                    335: int
                    336: rl_generic_bind (type, keyseq, data, map)
                    337:      int type;
                    338:      const char *keyseq;
                    339:      char *data;
                    340:      Keymap map;
                    341: {
                    342:   char *keys;
                    343:   int keys_len;
                    344:   register int i;
                    345:   KEYMAP_ENTRY k;
                    346: 
                    347:   k.function = 0;
                    348: 
                    349:   /* If no keys to bind to, exit right away. */
                    350:   if (keyseq == 0 || *keyseq == 0)
                    351:     {
                    352:       if (type == ISMACR)
                    353:        xfree (data);
                    354:       return -1;
                    355:     }
                    356: 
                    357:   keys = (char *)xmalloc (1 + (2 * strlen (keyseq)));
                    358: 
                    359:   /* Translate the ASCII representation of KEYSEQ into an array of
                    360:      characters.  Stuff the characters into KEYS, and the length of
                    361:      KEYS into KEYS_LEN. */
                    362:   if (rl_translate_keyseq (keyseq, keys, &keys_len))
                    363:     {
                    364:       xfree (keys);
                    365:       return -1;
                    366:     }
                    367: 
                    368:   /* Bind keys, making new keymaps as necessary. */
                    369:   for (i = 0; i < keys_len; i++)
                    370:     {
                    371:       unsigned char uc = keys[i];
                    372:       int ic;
                    373: 
                    374:       ic = uc;
                    375:       if (ic < 0 || ic >= KEYMAP_SIZE)
                    376:         {
                    377:           xfree (keys);
                    378:          return -1;
                    379:         }
                    380: 
                    381:       if (META_CHAR (ic) && _rl_convert_meta_chars_to_ascii)
                    382:        {
                    383:          ic = UNMETA (ic);
                    384:          if (map[ESC].type == ISKMAP)
                    385:            map = FUNCTION_TO_KEYMAP (map, ESC);
                    386:        }
                    387: 
                    388:       if ((i + 1) < keys_len)
                    389:        {
                    390:          if (map[ic].type != ISKMAP)
                    391:            {
                    392:              /* We allow subsequences of keys.  If a keymap is being
                    393:                 created that will `shadow' an existing function or macro
                    394:                 key binding, we save that keybinding into the ANYOTHERKEY
                    395:                 index in the new map.  The dispatch code will look there
                    396:                 to find the function to execute if the subsequence is not
                    397:                 matched.  ANYOTHERKEY was chosen to be greater than
                    398:                 UCHAR_MAX. */
                    399:              k = map[ic];
                    400: 
                    401:              map[ic].type = ISKMAP;
                    402:              map[ic].function = KEYMAP_TO_FUNCTION (rl_make_bare_keymap());
                    403:            }
                    404:          map = FUNCTION_TO_KEYMAP (map, ic);
                    405:          /* The dispatch code will return this function if no matching
                    406:             key sequence is found in the keymap.  This (with a little
                    407:             help from the dispatch code in readline.c) allows `a' to be
                    408:             mapped to something, `abc' to be mapped to something else,
                    409:             and the function bound  to `a' to be executed when the user
                    410:             types `abx', leaving `bx' in the input queue. */
                    411:          if (k.function && ((k.type == ISFUNC && k.function != rl_do_lowercase_version) || k.type == ISMACR))
                    412:            {
                    413:              map[ANYOTHERKEY] = k;
                    414:              k.function = 0;
                    415:            }
                    416:        }
                    417:       else
                    418:        {
                    419:          if (map[ic].type == ISMACR)
                    420:            xfree ((char *)map[ic].function);
                    421:          else if (map[ic].type == ISKMAP)
                    422:            {
                    423:              map = FUNCTION_TO_KEYMAP (map, ic);
                    424:              ic = ANYOTHERKEY;
                    425:              /* If we're trying to override a keymap with a null function
                    426:                 (e.g., trying to unbind it), we can't use a null pointer
                    427:                 here because that's indistinguishable from having not been
                    428:                 overridden.  We use a special bindable function that does
                    429:                 nothing. */
                    430:              if (type == ISFUNC && data == 0)
                    431:                data = (char *)_rl_null_function;
                    432:            }
                    433: 
                    434:          map[ic].function = KEYMAP_TO_FUNCTION (data);
                    435:          map[ic].type = type;
                    436:        }
                    437: 
                    438:       rl_binding_keymap = map;
                    439:     }
                    440:   xfree (keys);
                    441:   return 0;
                    442: }
                    443: 
                    444: /* Translate the ASCII representation of SEQ, stuffing the values into ARRAY,
                    445:    an array of characters.  LEN gets the final length of ARRAY.  Return
                    446:    non-zero if there was an error parsing SEQ. */
                    447: int
                    448: rl_translate_keyseq (seq, array, len)
                    449:      const char *seq;
                    450:      char *array;
                    451:      int *len;
                    452: {
                    453:   register int i, c, l, temp;
                    454: 
                    455:   for (i = l = 0; c = seq[i]; i++)
                    456:     {
                    457:       if (c == '\\')
                    458:        {
                    459:          c = seq[++i];
                    460: 
                    461:          if (c == 0)
                    462:            break;
                    463: 
                    464:          /* Handle \C- and \M- prefixes. */
                    465:          if ((c == 'C' || c == 'M') && seq[i + 1] == '-')
                    466:            {
                    467:              /* Handle special case of backwards define. */
                    468:              if (strncmp (&seq[i], "C-\\M-", 5) == 0)
                    469:                {
                    470:                  array[l++] = ESC;     /* ESC is meta-prefix */
                    471:                  i += 5;
                    472:                  array[l++] = CTRL (_rl_to_upper (seq[i]));
                    473:                  if (seq[i] == '\0')
                    474:                    i--;
                    475:                }
                    476:              else if (c == 'M')
                    477:                {
                    478:                  i++;          /* seq[i] == '-' */
                    479:                  /* XXX - obey convert-meta setting */
                    480:                  if (_rl_convert_meta_chars_to_ascii && _rl_keymap[ESC].type == ISKMAP)
                    481:                    array[l++] = ESC;   /* ESC is meta-prefix */
                    482:                  else if (seq[i+1] == '\\' && seq[i+2] == 'C' && seq[i+3] == '-')
                    483:                    {
                    484:                      i += 4;
                    485:                      temp = (seq[i] == '?') ? RUBOUT : CTRL (_rl_to_upper (seq[i]));
                    486:                      array[l++] = META (temp);
                    487:                    }
                    488:                  else
                    489:                    {
                    490:                      /* This doesn't yet handle things like \M-\a, which may
                    491:                         or may not have any reasonable meaning.  You're
                    492:                         probably better off using straight octal or hex. */
                    493:                      i++;
                    494:                      array[l++] = META (seq[i]);
                    495:                    }
                    496:                }
                    497:              else if (c == 'C')
                    498:                {
                    499:                  i += 2;
                    500:                  /* Special hack for C-?... */
                    501:                  array[l++] = (seq[i] == '?') ? RUBOUT : CTRL (_rl_to_upper (seq[i]));
                    502:                }
                    503:              continue;
                    504:            }         
                    505: 
                    506:          /* Translate other backslash-escaped characters.  These are the
                    507:             same escape sequences that bash's `echo' and `printf' builtins
                    508:             handle, with the addition of \d -> RUBOUT.  A backslash
                    509:             preceding a character that is not special is stripped. */
                    510:          switch (c)
                    511:            {
                    512:            case 'a':
                    513:              array[l++] = '\007';
                    514:              break;
                    515:            case 'b':
                    516:              array[l++] = '\b';
                    517:              break;
                    518:            case 'd':
                    519:              array[l++] = RUBOUT;      /* readline-specific */
                    520:              break;
                    521:            case 'e':
                    522:              array[l++] = ESC;
                    523:              break;
                    524:            case 'f':
                    525:              array[l++] = '\f';
                    526:              break;
                    527:            case 'n':
                    528:              array[l++] = NEWLINE;
                    529:              break;
                    530:            case 'r':
                    531:              array[l++] = RETURN;
                    532:              break;
                    533:            case 't':
                    534:              array[l++] = TAB;
                    535:              break;
                    536:            case 'v':
                    537:              array[l++] = 0x0B;
                    538:              break;
                    539:            case '\\':
                    540:              array[l++] = '\\';
                    541:              break;
                    542:            case '0': case '1': case '2': case '3':
                    543:            case '4': case '5': case '6': case '7':
                    544:              i++;
                    545:              for (temp = 2, c -= '0'; ISOCTAL (seq[i]) && temp--; i++)
                    546:                c = (c * 8) + OCTVALUE (seq[i]);
                    547:              i--;      /* auto-increment in for loop */
                    548:              array[l++] = c & largest_char;
                    549:              break;
                    550:            case 'x':
                    551:              i++;
                    552:              for (temp = 2, c = 0; ISXDIGIT ((unsigned char)seq[i]) && temp--; i++)
                    553:                c = (c * 16) + HEXVALUE (seq[i]);
                    554:              if (temp == 2)
                    555:                c = 'x';
                    556:              i--;      /* auto-increment in for loop */
                    557:              array[l++] = c & largest_char;
                    558:              break;
                    559:            default:    /* backslashes before non-special chars just add the char */
                    560:              array[l++] = c;
                    561:              break;    /* the backslash is stripped */
                    562:            }
                    563:          continue;
                    564:        }
                    565: 
                    566:       array[l++] = c;
                    567:     }
                    568: 
                    569:   *len = l;
                    570:   array[l] = '\0';
                    571:   return (0);
                    572: }
                    573: 
                    574: static int
                    575: _rl_isescape (c)
                    576:      int c;
                    577: {
                    578:   switch (c)
                    579:     {
                    580:     case '\007':
                    581:     case '\b':
                    582:     case '\f':
                    583:     case '\n':
                    584:     case '\r':
                    585:     case TAB:
                    586:     case 0x0b:  return (1);
                    587:     default: return (0);
                    588:     }
                    589: }
                    590: 
                    591: static int
                    592: _rl_escchar (c)
                    593:      int c;
                    594: {
                    595:   switch (c)
                    596:     {
                    597:     case '\007':  return ('a');
                    598:     case '\b':  return ('b');
                    599:     case '\f':  return ('f');
                    600:     case '\n':  return ('n');
                    601:     case '\r':  return ('r');
                    602:     case TAB:  return ('t');
                    603:     case 0x0b:  return ('v');
                    604:     default: return (c);
                    605:     }
                    606: }
                    607: 
                    608: char *
                    609: rl_untranslate_keyseq (seq)
                    610:      int seq;
                    611: {
                    612:   static char kseq[16];
                    613:   int i, c;
                    614: 
                    615:   i = 0;
                    616:   c = seq;
                    617:   if (META_CHAR (c))
                    618:     {
                    619:       kseq[i++] = '\\';
                    620:       kseq[i++] = 'M';
                    621:       kseq[i++] = '-';
                    622:       c = UNMETA (c);
                    623:     }
                    624:   else if (c == ESC)
                    625:     {
                    626:       kseq[i++] = '\\';
                    627:       c = 'e';
                    628:     }
                    629:   else if (CTRL_CHAR (c))
                    630:     {
                    631:       kseq[i++] = '\\';
                    632:       kseq[i++] = 'C';
                    633:       kseq[i++] = '-';
                    634:       c = _rl_to_lower (UNCTRL (c));
                    635:     }
                    636:   else if (c == RUBOUT)
                    637:     {
                    638:       kseq[i++] = '\\';
                    639:       kseq[i++] = 'C';
                    640:       kseq[i++] = '-';
                    641:       c = '?';
                    642:     }
                    643: 
                    644:   if (c == ESC)
                    645:     {
                    646:       kseq[i++] = '\\';
                    647:       c = 'e';
                    648:     }
                    649:   else if (c == '\\' || c == '"')
                    650:     {
                    651:       kseq[i++] = '\\';
                    652:     }
                    653: 
                    654:   kseq[i++] = (unsigned char) c;
                    655:   kseq[i] = '\0';
                    656:   return kseq;
                    657: }
                    658: 
                    659: char *
                    660: _rl_untranslate_macro_value (seq, use_escapes)
                    661:      char *seq;
                    662:      int use_escapes;
                    663: {
                    664:   char *ret, *r, *s;
                    665:   int c;
                    666: 
                    667:   r = ret = (char *)xmalloc (7 * strlen (seq) + 1);
                    668:   for (s = seq; *s; s++)
                    669:     {
                    670:       c = *s;
                    671:       if (META_CHAR (c))
                    672:        {
                    673:          *r++ = '\\';
                    674:          *r++ = 'M';
                    675:          *r++ = '-';
                    676:          c = UNMETA (c);
                    677:        }
                    678:       else if (c == ESC)
                    679:        {
                    680:          *r++ = '\\';
                    681:          c = 'e';
                    682:        }
                    683:       else if (CTRL_CHAR (c))
                    684:        {
                    685:          *r++ = '\\';
                    686:          if (use_escapes && _rl_isescape (c))
                    687:            c = _rl_escchar (c);
                    688:          else
                    689:            {
                    690:              *r++ = 'C';
                    691:              *r++ = '-';
                    692:              c = _rl_to_lower (UNCTRL (c));
                    693:            }
                    694:        }
                    695:       else if (c == RUBOUT)
                    696:        {
                    697:          *r++ = '\\';
                    698:          *r++ = 'C';
                    699:          *r++ = '-';
                    700:          c = '?';
                    701:        }
                    702: 
                    703:       if (c == ESC)
                    704:        {
                    705:          *r++ = '\\';
                    706:          c = 'e';
                    707:        }
                    708:       else if (c == '\\' || c == '"')
                    709:        *r++ = '\\';
                    710: 
                    711:       *r++ = (unsigned char)c;
                    712:     }
                    713:   *r = '\0';
                    714:   return ret;
                    715: }
                    716: 
                    717: /* Return a pointer to the function that STRING represents.
                    718:    If STRING doesn't have a matching function, then a NULL pointer
                    719:    is returned. */
                    720: rl_command_func_t *
                    721: rl_named_function (string)
                    722:      const char *string;
                    723: {
                    724:   register int i;
                    725: 
                    726:   rl_initialize_funmap ();
                    727: 
                    728:   for (i = 0; funmap[i]; i++)
                    729:     if (_rl_stricmp (funmap[i]->name, string) == 0)
                    730:       return (funmap[i]->function);
                    731:   return ((rl_command_func_t *)NULL);
                    732: }
                    733: 
                    734: /* Return the function (or macro) definition which would be invoked via
                    735:    KEYSEQ if executed in MAP.  If MAP is NULL, then the current keymap is
                    736:    used.  TYPE, if non-NULL, is a pointer to an int which will receive the
                    737:    type of the object pointed to.  One of ISFUNC (function), ISKMAP (keymap),
                    738:    or ISMACR (macro). */
                    739: rl_command_func_t *
                    740: rl_function_of_keyseq (keyseq, map, type)
                    741:      const char *keyseq;
                    742:      Keymap map;
                    743:      int *type;
                    744: {
                    745:   register int i;
                    746: 
                    747:   if (map == 0)
                    748:     map = _rl_keymap;
                    749: 
                    750:   for (i = 0; keyseq && keyseq[i]; i++)
                    751:     {
                    752:       unsigned char ic = keyseq[i];
                    753: 
                    754:       if (META_CHAR (ic) && _rl_convert_meta_chars_to_ascii)
                    755:        {
                    756:          if (map[ESC].type == ISKMAP)
                    757:            {
                    758:              map = FUNCTION_TO_KEYMAP (map, ESC);
                    759:              ic = UNMETA (ic);
                    760:            }
                    761:          /* XXX - should we just return NULL here, since this obviously
                    762:             doesn't match? */
                    763:          else
                    764:            {
                    765:              if (type)
                    766:                *type = map[ESC].type;
                    767: 
                    768:              return (map[ESC].function);
                    769:            }
                    770:        }
                    771: 
                    772:       if (map[ic].type == ISKMAP)
                    773:        {
                    774:          /* If this is the last key in the key sequence, return the
                    775:             map. */
                    776:          if (keyseq[i + 1] == '\0')
                    777:            {
                    778:              if (type)
                    779:                *type = ISKMAP;
                    780: 
                    781:              return (map[ic].function);
                    782:            }
                    783:          else
                    784:            map = FUNCTION_TO_KEYMAP (map, ic);
                    785:        }
                    786:       /* If we're not at the end of the key sequence, and the current key
                    787:         is bound to something other than a keymap, then the entire key
                    788:         sequence is not bound. */
                    789:       else if (map[ic].type != ISKMAP && keyseq[i+1])
                    790:        return ((rl_command_func_t *)NULL);
                    791:       else     /* map[ic].type != ISKMAP && keyseq[i+1] == 0 */
                    792:        {
                    793:          if (type)
                    794:            *type = map[ic].type;
                    795: 
                    796:          return (map[ic].function);
                    797:        }
                    798:     }
                    799:   return ((rl_command_func_t *) NULL);
                    800: }
                    801: 
                    802: /* The last key bindings file read. */
                    803: static char *last_readline_init_file = (char *)NULL;
                    804: 
                    805: /* The file we're currently reading key bindings from. */
                    806: static const char *current_readline_init_file;
                    807: static int current_readline_init_include_level;
                    808: static int current_readline_init_lineno;
                    809: 
                    810: /* Read FILENAME into a locally-allocated buffer and return the buffer.
                    811:    The size of the buffer is returned in *SIZEP.  Returns NULL if any
                    812:    errors were encountered. */
                    813: static char *
                    814: _rl_read_file (filename, sizep)
                    815:      char *filename;
                    816:      size_t *sizep;
                    817: {
                    818:   struct stat finfo;
                    819:   size_t file_size;
                    820:   char *buffer;
                    821:   int i, file;
                    822: 
                    823:   if ((stat (filename, &finfo) < 0) || (file = open (filename, O_RDONLY, 0666)) < 0)
                    824:     return ((char *)NULL);
                    825: 
                    826:   file_size = (size_t)finfo.st_size;
                    827: 
                    828:   /* check for overflow on very large files */
                    829:   if (file_size != finfo.st_size || file_size + 1 < file_size)
                    830:     {
                    831:       if (file >= 0)
                    832:        close (file);
                    833: #if defined (EFBIG)
                    834:       errno = EFBIG;
                    835: #endif
                    836:       return ((char *)NULL);
                    837:     }
                    838: 
                    839:   /* Read the file into BUFFER. */
                    840:   buffer = (char *)xmalloc (file_size + 1);
                    841:   i = read (file, buffer, file_size);
                    842:   close (file);
                    843: 
                    844:   if (i < 0)
                    845:     {
                    846:       xfree (buffer);
                    847:       return ((char *)NULL);
                    848:     }
                    849: 
                    850:   RL_CHECK_SIGNALS ();
                    851: 
                    852:   buffer[i] = '\0';
                    853:   if (sizep)
                    854:     *sizep = i;
                    855: 
                    856:   return (buffer);
                    857: }
                    858: 
                    859: /* Re-read the current keybindings file. */
                    860: int
                    861: rl_re_read_init_file (count, ignore)
                    862:      int count, ignore;
                    863: {
                    864:   int r;
                    865:   r = rl_read_init_file ((const char *)NULL);
                    866:   rl_set_keymap_from_edit_mode ();
                    867:   return r;
                    868: }
                    869: 
                    870: /* Do key bindings from a file.  If FILENAME is NULL it defaults
                    871:    to the first non-null filename from this list:
                    872:      1. the filename used for the previous call
                    873:      2. the value of the shell variable `INPUTRC'
                    874:      3. ~/.inputrc
                    875:      4. /etc/inputrc
                    876:    If the file existed and could be opened and read, 0 is returned,
                    877:    otherwise errno is returned. */
                    878: int
                    879: rl_read_init_file (filename)
                    880:      const char *filename;
                    881: {
                    882:   /* Default the filename. */
                    883:   if (filename == 0)
                    884:     filename = last_readline_init_file;
                    885:   if (filename == 0)
                    886:     filename = sh_get_env_value ("INPUTRC");
                    887:   if (filename == 0 || *filename == 0)
                    888:     {
                    889:       filename = DEFAULT_INPUTRC;
                    890:       /* Try to read DEFAULT_INPUTRC; fall back to SYS_INPUTRC on failure */
                    891:       if (_rl_read_init_file (filename, 0) == 0)
                    892:        return 0;
                    893:       filename = SYS_INPUTRC;
                    894:     }
                    895: 
                    896: #if defined (__MSDOS__)
                    897:   if (_rl_read_init_file (filename, 0) == 0)
                    898:     return 0;
                    899:   filename = "~/_inputrc";
                    900: #endif
                    901:   return (_rl_read_init_file (filename, 0));
                    902: }
                    903: 
                    904: static int
                    905: _rl_read_init_file (filename, include_level)
                    906:      const char *filename;
                    907:      int include_level;
                    908: {
                    909:   register int i;
                    910:   char *buffer, *openname, *line, *end;
                    911:   size_t file_size;
                    912: 
                    913:   current_readline_init_file = filename;
                    914:   current_readline_init_include_level = include_level;
                    915: 
                    916:   openname = tilde_expand (filename);
                    917:   buffer = _rl_read_file (openname, &file_size);
                    918:   xfree (openname);
                    919: 
                    920:   RL_CHECK_SIGNALS ();
                    921:   if (buffer == 0)
                    922:     return (errno);
                    923:   
                    924:   if (include_level == 0 && filename != last_readline_init_file)
                    925:     {
                    926:       FREE (last_readline_init_file);
                    927:       last_readline_init_file = savestring (filename);
                    928:     }
                    929: 
                    930:   currently_reading_init_file = 1;
                    931: 
                    932:   /* Loop over the lines in the file.  Lines that start with `#' are
                    933:      comments; all other lines are commands for readline initialization. */
                    934:   current_readline_init_lineno = 1;
                    935:   line = buffer;
                    936:   end = buffer + file_size;
                    937:   while (line < end)
                    938:     {
                    939:       /* Find the end of this line. */
                    940:       for (i = 0; line + i != end && line[i] != '\n'; i++);
                    941: 
                    942: #if defined (__CYGWIN__)
                    943:       /* ``Be liberal in what you accept.'' */
                    944:       if (line[i] == '\n' && line[i-1] == '\r')
                    945:        line[i - 1] = '\0';
                    946: #endif
                    947: 
                    948:       /* Mark end of line. */
                    949:       line[i] = '\0';
                    950: 
                    951:       /* Skip leading whitespace. */
                    952:       while (*line && whitespace (*line))
                    953:         {
                    954:          line++;
                    955:          i--;
                    956:         }
                    957: 
                    958:       /* If the line is not a comment, then parse it. */
                    959:       if (*line && *line != '#')
                    960:        rl_parse_and_bind (line);
                    961: 
                    962:       /* Move to the next line. */
                    963:       line += i + 1;
                    964:       current_readline_init_lineno++;
                    965:     }
                    966: 
                    967:   xfree (buffer);
                    968:   currently_reading_init_file = 0;
                    969:   return (0);
                    970: }
                    971: 
                    972: static void
                    973: _rl_init_file_error (msg)
                    974:      const char *msg;
                    975: {
                    976:   if (currently_reading_init_file)
                    977:     _rl_errmsg ("%s: line %d: %s\n", current_readline_init_file,
                    978:                     current_readline_init_lineno, msg);
                    979:   else
                    980:     _rl_errmsg ("%s", msg);
                    981: }
                    982: 
                    983: /* **************************************************************** */
                    984: /*                                                                 */
                    985: /*                     Parser Directives                           */
                    986: /*                                                                 */
                    987: /* **************************************************************** */
                    988: 
                    989: typedef int _rl_parser_func_t PARAMS((char *));
                    990: 
                    991: /* Things that mean `Control'. */
                    992: const char * const _rl_possible_control_prefixes[] = {
                    993:   "Control-", "C-", "CTRL-", (const char *)NULL
                    994: };
                    995: 
                    996: const char * const _rl_possible_meta_prefixes[] = {
                    997:   "Meta", "M-", (const char *)NULL
                    998: };
                    999: 
                   1000: /* Conditionals. */
                   1001: 
                   1002: /* Calling programs set this to have their argv[0]. */
                   1003: const char *rl_readline_name = "other";
                   1004: 
                   1005: /* Stack of previous values of parsing_conditionalized_out. */
                   1006: static unsigned char *if_stack = (unsigned char *)NULL;
                   1007: static int if_stack_depth;
                   1008: static int if_stack_size;
                   1009: 
                   1010: /* Push _rl_parsing_conditionalized_out, and set parser state based
                   1011:    on ARGS. */
                   1012: static int
                   1013: parser_if (args)
                   1014:      char *args;
                   1015: {
                   1016:   register int i;
                   1017: 
                   1018:   /* Push parser state. */
                   1019:   if (if_stack_depth + 1 >= if_stack_size)
                   1020:     {
                   1021:       if (!if_stack)
                   1022:        if_stack = (unsigned char *)xmalloc (if_stack_size = 20);
                   1023:       else
                   1024:        if_stack = (unsigned char *)xrealloc (if_stack, if_stack_size += 20);
                   1025:     }
                   1026:   if_stack[if_stack_depth++] = _rl_parsing_conditionalized_out;
                   1027: 
                   1028:   /* If parsing is turned off, then nothing can turn it back on except
                   1029:      for finding the matching endif.  In that case, return right now. */
                   1030:   if (_rl_parsing_conditionalized_out)
                   1031:     return 0;
                   1032: 
                   1033:   /* Isolate first argument. */
                   1034:   for (i = 0; args[i] && !whitespace (args[i]); i++);
                   1035: 
                   1036:   if (args[i])
                   1037:     args[i++] = '\0';
                   1038: 
                   1039:   /* Handle "$if term=foo" and "$if mode=emacs" constructs.  If this
                   1040:      isn't term=foo, or mode=emacs, then check to see if the first
                   1041:      word in ARGS is the same as the value stored in rl_readline_name. */
                   1042:   if (rl_terminal_name && _rl_strnicmp (args, "term=", 5) == 0)
                   1043:     {
                   1044:       char *tem, *tname;
                   1045: 
                   1046:       /* Terminals like "aaa-60" are equivalent to "aaa". */
                   1047:       tname = savestring (rl_terminal_name);
                   1048:       tem = strchr (tname, '-');
                   1049:       if (tem)
                   1050:        *tem = '\0';
                   1051: 
                   1052:       /* Test the `long' and `short' forms of the terminal name so that
                   1053:         if someone has a `sun-cmd' and does not want to have bindings
                   1054:         that will be executed if the terminal is a `sun', they can put
                   1055:         `$if term=sun-cmd' into their .inputrc. */
                   1056:       _rl_parsing_conditionalized_out = _rl_stricmp (args + 5, tname) &&
                   1057:                                        _rl_stricmp (args + 5, rl_terminal_name);
                   1058:       xfree (tname);
                   1059:     }
                   1060: #if defined (VI_MODE)
                   1061:   else if (_rl_strnicmp (args, "mode=", 5) == 0)
                   1062:     {
                   1063:       int mode;
                   1064: 
                   1065:       if (_rl_stricmp (args + 5, "emacs") == 0)
                   1066:        mode = emacs_mode;
                   1067:       else if (_rl_stricmp (args + 5, "vi") == 0)
                   1068:        mode = vi_mode;
                   1069:       else
                   1070:        mode = no_mode;
                   1071: 
                   1072:       _rl_parsing_conditionalized_out = mode != rl_editing_mode;
                   1073:     }
                   1074: #endif /* VI_MODE */
                   1075:   /* Check to see if the first word in ARGS is the same as the
                   1076:      value stored in rl_readline_name. */
                   1077:   else if (_rl_stricmp (args, rl_readline_name) == 0)
                   1078:     _rl_parsing_conditionalized_out = 0;
                   1079:   else
                   1080:     _rl_parsing_conditionalized_out = 1;
                   1081:   return 0;
                   1082: }
                   1083: 
                   1084: /* Invert the current parser state if there is anything on the stack. */
                   1085: static int
                   1086: parser_else (args)
                   1087:      char *args;
                   1088: {
                   1089:   register int i;
                   1090: 
                   1091:   if (if_stack_depth == 0)
                   1092:     {
                   1093:       _rl_init_file_error ("$else found without matching $if");
                   1094:       return 0;
                   1095:     }
                   1096: 
                   1097: #if 0
                   1098:   /* Check the previous (n - 1) levels of the stack to make sure that
                   1099:      we haven't previously turned off parsing. */
                   1100:   for (i = 0; i < if_stack_depth - 1; i++)
                   1101: #else
                   1102:   /* Check the previous (n) levels of the stack to make sure that
                   1103:      we haven't previously turned off parsing. */
                   1104:   for (i = 0; i < if_stack_depth; i++)
                   1105: #endif
                   1106:     if (if_stack[i] == 1)
                   1107:       return 0;
                   1108: 
                   1109:   /* Invert the state of parsing if at top level. */
                   1110:   _rl_parsing_conditionalized_out = !_rl_parsing_conditionalized_out;
                   1111:   return 0;
                   1112: }
                   1113: 
                   1114: /* Terminate a conditional, popping the value of
                   1115:    _rl_parsing_conditionalized_out from the stack. */
                   1116: static int
                   1117: parser_endif (args)
                   1118:      char *args;
                   1119: {
                   1120:   if (if_stack_depth)
                   1121:     _rl_parsing_conditionalized_out = if_stack[--if_stack_depth];
                   1122:   else
                   1123:     _rl_init_file_error ("$endif without matching $if");
                   1124:   return 0;
                   1125: }
                   1126: 
                   1127: static int
                   1128: parser_include (args)
                   1129:      char *args;
                   1130: {
                   1131:   const char *old_init_file;
                   1132:   char *e;
                   1133:   int old_line_number, old_include_level, r;
                   1134: 
                   1135:   if (_rl_parsing_conditionalized_out)
                   1136:     return (0);
                   1137: 
                   1138:   old_init_file = current_readline_init_file;
                   1139:   old_line_number = current_readline_init_lineno;
                   1140:   old_include_level = current_readline_init_include_level;
                   1141: 
                   1142:   e = strchr (args, '\n');
                   1143:   if (e)
                   1144:     *e = '\0';
                   1145:   r = _rl_read_init_file ((const char *)args, old_include_level + 1);
                   1146: 
                   1147:   current_readline_init_file = old_init_file;
                   1148:   current_readline_init_lineno = old_line_number;
                   1149:   current_readline_init_include_level = old_include_level;
                   1150: 
                   1151:   return r;
                   1152: }
                   1153:   
                   1154: /* Associate textual names with actual functions. */
                   1155: static const struct {
                   1156:   const char * const name;
                   1157:   _rl_parser_func_t *function;
                   1158: } parser_directives [] = {
                   1159:   { "if", parser_if },
                   1160:   { "endif", parser_endif },
                   1161:   { "else", parser_else },
                   1162:   { "include", parser_include },
                   1163:   { (char *)0x0, (_rl_parser_func_t *)0x0 }
                   1164: };
                   1165: 
                   1166: /* Handle a parser directive.  STATEMENT is the line of the directive
                   1167:    without any leading `$'. */
                   1168: static int
                   1169: handle_parser_directive (statement)
                   1170:      char *statement;
                   1171: {
                   1172:   register int i;
                   1173:   char *directive, *args;
                   1174: 
                   1175:   /* Isolate the actual directive. */
                   1176: 
                   1177:   /* Skip whitespace. */
                   1178:   for (i = 0; whitespace (statement[i]); i++);
                   1179: 
                   1180:   directive = &statement[i];
                   1181: 
                   1182:   for (; statement[i] && !whitespace (statement[i]); i++);
                   1183: 
                   1184:   if (statement[i])
                   1185:     statement[i++] = '\0';
                   1186: 
                   1187:   for (; statement[i] && whitespace (statement[i]); i++);
                   1188: 
                   1189:   args = &statement[i];
                   1190: 
                   1191:   /* Lookup the command, and act on it. */
                   1192:   for (i = 0; parser_directives[i].name; i++)
                   1193:     if (_rl_stricmp (directive, parser_directives[i].name) == 0)
                   1194:       {
                   1195:        (*parser_directives[i].function) (args);
                   1196:        return (0);
                   1197:       }
                   1198: 
                   1199:   /* display an error message about the unknown parser directive */
                   1200:   _rl_init_file_error ("unknown parser directive");
                   1201:   return (1);
                   1202: }
                   1203: 
                   1204: /* Start at STRING[START] and look for DELIM.  Return I where STRING[I] ==
                   1205:    DELIM or STRING[I] == 0.  DELIM is usually a double quote. */
                   1206: static int
                   1207: _rl_skip_to_delim (string, start, delim)
                   1208:      char *string;
                   1209:      int start, delim;
                   1210: {
                   1211:   int i, c, passc;
                   1212: 
                   1213:   for (i = start,passc = 0; c = string[i]; i++)
                   1214:     {
                   1215:       if (passc)
                   1216:        {
                   1217:          passc = 0;
                   1218:          if (c == 0)
                   1219:            break;
                   1220:          continue;
                   1221:        }
                   1222: 
                   1223:       if (c == '\\')
                   1224:        {
                   1225:          passc = 1;
                   1226:          continue;
                   1227:        }
                   1228: 
                   1229:       if (c == delim)
                   1230:        break;
                   1231:     }
                   1232: 
                   1233:   return i;
                   1234: }
                   1235: 
                   1236: /* Read the binding command from STRING and perform it.
                   1237:    A key binding command looks like: Keyname: function-name\0,
                   1238:    a variable binding command looks like: set variable value.
                   1239:    A new-style keybinding looks like "\C-x\C-x": exchange-point-and-mark. */
                   1240: int
                   1241: rl_parse_and_bind (string)
                   1242:      char *string;
                   1243: {
                   1244:   char *funname, *kname;
                   1245:   register int c, i;
                   1246:   int key, equivalency;
                   1247: 
                   1248:   while (string && whitespace (*string))
                   1249:     string++;
                   1250: 
                   1251:   if (string == 0 || *string == 0 || *string == '#')
                   1252:     return 0;
                   1253: 
                   1254:   /* If this is a parser directive, act on it. */
                   1255:   if (*string == '$')
                   1256:     {
                   1257:       handle_parser_directive (&string[1]);
                   1258:       return 0;
                   1259:     }
                   1260: 
                   1261:   /* If we aren't supposed to be parsing right now, then we're done. */
                   1262:   if (_rl_parsing_conditionalized_out)
                   1263:     return 0;
                   1264: 
                   1265:   i = 0;
                   1266:   /* If this keyname is a complex key expression surrounded by quotes,
                   1267:      advance to after the matching close quote.  This code allows the
                   1268:      backslash to quote characters in the key expression. */
                   1269:   if (*string == '"')
                   1270:     {
                   1271:       i = _rl_skip_to_delim (string, 1, '"');
                   1272: 
                   1273:       /* If we didn't find a closing quote, abort the line. */
                   1274:       if (string[i] == '\0')
                   1275:         {
                   1276:           _rl_init_file_error ("no closing `\"' in key binding");
                   1277:           return 1;
                   1278:         }
                   1279:       else
                   1280:         i++;   /* skip past closing double quote */
                   1281:     }
                   1282: 
                   1283:   /* Advance to the colon (:) or whitespace which separates the two objects. */
                   1284:   for (; (c = string[i]) && c != ':' && c != ' ' && c != '\t'; i++ );
                   1285: 
                   1286:   equivalency = (c == ':' && string[i + 1] == '=');
                   1287: 
                   1288:   /* Mark the end of the command (or keyname). */
                   1289:   if (string[i])
                   1290:     string[i++] = '\0';
                   1291: 
                   1292:   /* If doing assignment, skip the '=' sign as well. */
                   1293:   if (equivalency)
                   1294:     string[i++] = '\0';
                   1295: 
                   1296:   /* If this is a command to set a variable, then do that. */
                   1297:   if (_rl_stricmp (string, "set") == 0)
                   1298:     {
                   1299:       char *var, *value, *e;
                   1300:       int s;
                   1301: 
                   1302:       var = string + i;
                   1303:       /* Make VAR point to start of variable name. */
                   1304:       while (*var && whitespace (*var)) var++;
                   1305: 
                   1306:       /* Make VALUE point to start of value string. */
                   1307:       value = var;
                   1308:       while (*value && whitespace (*value) == 0) value++;
                   1309:       if (*value)
                   1310:        *value++ = '\0';
                   1311:       while (*value && whitespace (*value)) value++;
                   1312: 
                   1313:       /* Strip trailing whitespace from values of boolean variables. */
                   1314:       if (find_boolean_var (var) >= 0)
                   1315:        {
                   1316:          /* remove trailing whitespace */
                   1317: remove_trailing:
                   1318:          e = value + strlen (value) - 1;
                   1319:          while (e >= value && whitespace (*e))
                   1320:            e--;
                   1321:          e++;          /* skip back to whitespace or EOS */
                   1322:          
                   1323:          if (*e && e >= value)
                   1324:            *e = '\0';
                   1325:        }
                   1326:       else if ((i = find_string_var (var)) >= 0)
                   1327:        {
                   1328:          /* Allow quoted strings in variable values */
                   1329:          if (*value == '"')
                   1330:            {
                   1331:              i = _rl_skip_to_delim (value, 1, *value);
                   1332:              value[i] = '\0';
                   1333:              value++;  /* skip past the quote */
                   1334:            }
                   1335:          else
                   1336:            goto remove_trailing;
                   1337:        }
                   1338:        
                   1339:       rl_variable_bind (var, value);
                   1340:       return 0;
                   1341:     }
                   1342: 
                   1343:   /* Skip any whitespace between keyname and funname. */
                   1344:   for (; string[i] && whitespace (string[i]); i++);
                   1345:   funname = &string[i];
                   1346: 
                   1347:   /* Now isolate funname.
                   1348:      For straight function names just look for whitespace, since
                   1349:      that will signify the end of the string.  But this could be a
                   1350:      macro definition.  In that case, the string is quoted, so skip
                   1351:      to the matching delimiter.  We allow the backslash to quote the
                   1352:      delimiter characters in the macro body. */
                   1353:   /* This code exists to allow whitespace in macro expansions, which
                   1354:      would otherwise be gobbled up by the next `for' loop.*/
                   1355:   /* XXX - it may be desirable to allow backslash quoting only if " is
                   1356:      the quoted string delimiter, like the shell. */
                   1357:   if (*funname == '\'' || *funname == '"')
                   1358:     {
                   1359:       i = _rl_skip_to_delim (string, i+1, *funname);
                   1360:       if (string[i])
                   1361:        i++;
                   1362:     }
                   1363: 
                   1364:   /* Advance to the end of the string.  */
                   1365:   for (; string[i] && whitespace (string[i]) == 0; i++);
                   1366: 
                   1367:   /* No extra whitespace at the end of the string. */
                   1368:   string[i] = '\0';
                   1369: 
                   1370:   /* Handle equivalency bindings here.  Make the left-hand side be exactly
                   1371:      whatever the right-hand evaluates to, including keymaps. */
                   1372:   if (equivalency)
                   1373:     {
                   1374:       return 0;
                   1375:     }
                   1376: 
                   1377:   /* If this is a new-style key-binding, then do the binding with
                   1378:      rl_bind_keyseq ().  Otherwise, let the older code deal with it. */
                   1379:   if (*string == '"')
                   1380:     {
                   1381:       char *seq;
                   1382:       register int j, k, passc;
                   1383: 
                   1384:       seq = (char *)xmalloc (1 + strlen (string));
                   1385:       for (j = 1, k = passc = 0; string[j]; j++)
                   1386:        {
                   1387:          /* Allow backslash to quote characters, but leave them in place.
                   1388:             This allows a string to end with a backslash quoting another
                   1389:             backslash, or with a backslash quoting a double quote.  The
                   1390:             backslashes are left in place for rl_translate_keyseq (). */
                   1391:          if (passc || (string[j] == '\\'))
                   1392:            {
                   1393:              seq[k++] = string[j];
                   1394:              passc = !passc;
                   1395:              continue;
                   1396:            }
                   1397: 
                   1398:          if (string[j] == '"')
                   1399:            break;
                   1400: 
                   1401:          seq[k++] = string[j];
                   1402:        }
                   1403:       seq[k] = '\0';
                   1404: 
                   1405:       /* Binding macro? */
                   1406:       if (*funname == '\'' || *funname == '"')
                   1407:        {
                   1408:          j = strlen (funname);
                   1409: 
                   1410:          /* Remove the delimiting quotes from each end of FUNNAME. */
                   1411:          if (j && funname[j - 1] == *funname)
                   1412:            funname[j - 1] = '\0';
                   1413: 
                   1414:          rl_macro_bind (seq, &funname[1], _rl_keymap);
                   1415:        }
                   1416:       else
                   1417:        rl_bind_keyseq (seq, rl_named_function (funname));
                   1418: 
                   1419:       xfree (seq);
                   1420:       return 0;
                   1421:     }
                   1422: 
                   1423:   /* Get the actual character we want to deal with. */
                   1424:   kname = strrchr (string, '-');
                   1425:   if (kname == 0)
                   1426:     kname = string;
                   1427:   else
                   1428:     kname++;
                   1429: 
                   1430:   key = glean_key_from_name (kname);
                   1431: 
                   1432:   /* Add in control and meta bits. */
                   1433:   if (substring_member_of_array (string, _rl_possible_control_prefixes))
                   1434:     key = CTRL (_rl_to_upper (key));
                   1435: 
                   1436:   if (substring_member_of_array (string, _rl_possible_meta_prefixes))
                   1437:     key = META (key);
                   1438: 
                   1439:   /* Temporary.  Handle old-style keyname with macro-binding. */
                   1440:   if (*funname == '\'' || *funname == '"')
                   1441:     {
                   1442:       char useq[2];
                   1443:       int fl = strlen (funname);
                   1444: 
                   1445:       useq[0] = key; useq[1] = '\0';
                   1446:       if (fl && funname[fl - 1] == *funname)
                   1447:        funname[fl - 1] = '\0';
                   1448: 
                   1449:       rl_macro_bind (useq, &funname[1], _rl_keymap);
                   1450:     }
                   1451: #if defined (PREFIX_META_HACK)
                   1452:   /* Ugly, but working hack to keep prefix-meta around. */
                   1453:   else if (_rl_stricmp (funname, "prefix-meta") == 0)
                   1454:     {
                   1455:       char seq[2];
                   1456: 
                   1457:       seq[0] = key;
                   1458:       seq[1] = '\0';
                   1459:       rl_generic_bind (ISKMAP, seq, (char *)emacs_meta_keymap, _rl_keymap);
                   1460:     }
                   1461: #endif /* PREFIX_META_HACK */
                   1462:   else
                   1463:     rl_bind_key (key, rl_named_function (funname));
                   1464:   return 0;
                   1465: }
                   1466: 
                   1467: /* Simple structure for boolean readline variables (i.e., those that can
                   1468:    have one of two values; either "On" or 1 for truth, or "Off" or 0 for
                   1469:    false. */
                   1470: 
                   1471: #define V_SPECIAL      0x1
                   1472: 
                   1473: static const struct {
                   1474:   const char * const name;
                   1475:   int *value;
                   1476:   int flags;
                   1477: } boolean_varlist [] = {
                   1478:   { "bind-tty-special-chars",  &_rl_bind_stty_chars,           0 },
                   1479:   { "blink-matching-paren",    &rl_blink_matching_paren,       V_SPECIAL },
                   1480:   { "byte-oriented",           &rl_byte_oriented,              0 },
                   1481: #if defined (COLOR_SUPPORT)
                   1482:   { "colored-stats",           &_rl_colored_stats,             0 },
                   1483: #endif
                   1484:   { "completion-ignore-case",  &_rl_completion_case_fold,      0 },
                   1485:   { "completion-map-case",     &_rl_completion_case_map,       0 },
                   1486:   { "convert-meta",            &_rl_convert_meta_chars_to_ascii, 0 },
                   1487:   { "disable-completion",      &rl_inhibit_completion,         0 },
                   1488:   { "echo-control-characters", &_rl_echo_control_chars,        0 },
                   1489:   { "enable-keypad",           &_rl_enable_keypad,             0 },
                   1490:   { "enable-meta-key",         &_rl_enable_meta,               0 },
                   1491:   { "expand-tilde",            &rl_complete_with_tilde_expansion, 0 },
                   1492:   { "history-preserve-point",  &_rl_history_preserve_point,    0 },
                   1493:   { "horizontal-scroll-mode",  &_rl_horizontal_scroll_mode,    0 },
                   1494:   { "input-meta",              &_rl_meta_flag,                 0 },
                   1495:   { "mark-directories",                &_rl_complete_mark_directories, 0 },
                   1496:   { "mark-modified-lines",     &_rl_mark_modified_lines,       0 },
                   1497:   { "mark-symlinked-directories", &_rl_complete_mark_symlink_dirs, 0 },
                   1498:   { "match-hidden-files",      &_rl_match_hidden_files,        0 },
                   1499:   { "menu-complete-display-prefix", &_rl_menu_complete_prefix_first, 0 },
                   1500:   { "meta-flag",               &_rl_meta_flag,                 0 },
                   1501:   { "output-meta",             &_rl_output_meta_chars,         0 },
                   1502:   { "page-completions",                &_rl_page_completions,          0 },
                   1503:   { "prefer-visible-bell",     &_rl_prefer_visible_bell,       V_SPECIAL },
                   1504:   { "print-completions-horizontally", &_rl_print_completions_horizontally, 0 },
                   1505:   { "revert-all-at-newline",   &_rl_revert_all_at_newline,     0 },
                   1506:   { "show-all-if-ambiguous",   &_rl_complete_show_all,         0 },
                   1507:   { "show-all-if-unmodified",  &_rl_complete_show_unmodified,  0 },
                   1508:   { "show-mode-in-prompt",     &_rl_show_mode_in_prompt,       0 },
                   1509:   { "skip-completed-text",     &_rl_skip_completed_text,       0 },
                   1510: #if defined (VISIBLE_STATS)
                   1511:   { "visible-stats",           &rl_visible_stats,              0 },
                   1512: #endif /* VISIBLE_STATS */
                   1513:   { (char *)NULL, (int *)NULL, 0 }
                   1514: };
                   1515: 
                   1516: static int
                   1517: find_boolean_var (name)
                   1518:      const char *name;
                   1519: {
                   1520:   register int i;
                   1521: 
                   1522:   for (i = 0; boolean_varlist[i].name; i++)
                   1523:     if (_rl_stricmp (name, boolean_varlist[i].name) == 0)
                   1524:       return i;
                   1525:   return -1;
                   1526: }
                   1527: 
                   1528: /* Hooks for handling special boolean variables, where a
                   1529:    function needs to be called or another variable needs
                   1530:    to be changed when they're changed. */
                   1531: static void
                   1532: hack_special_boolean_var (i)
                   1533:      int i;
                   1534: {
                   1535:   const char *name;
                   1536: 
                   1537:   name = boolean_varlist[i].name;
                   1538: 
                   1539:   if (_rl_stricmp (name, "blink-matching-paren") == 0)
                   1540:     _rl_enable_paren_matching (rl_blink_matching_paren);
                   1541:   else if (_rl_stricmp (name, "prefer-visible-bell") == 0)
                   1542:     {
                   1543:       if (_rl_prefer_visible_bell)
                   1544:        _rl_bell_preference = VISIBLE_BELL;
                   1545:       else
                   1546:        _rl_bell_preference = AUDIBLE_BELL;
                   1547:     }
                   1548:   else if (_rl_stricmp (name, "show-mode-in-prompt") == 0)
                   1549:     _rl_reset_prompt ();
                   1550: }
                   1551: 
                   1552: typedef int _rl_sv_func_t PARAMS((const char *));
                   1553: 
                   1554: /* These *must* correspond to the array indices for the appropriate
                   1555:    string variable.  (Though they're not used right now.) */
                   1556: #define V_BELLSTYLE    0
                   1557: #define V_COMBEGIN     1
                   1558: #define V_EDITMODE     2
                   1559: #define V_ISRCHTERM    3
                   1560: #define V_KEYMAP       4
                   1561: 
                   1562: #define        V_STRING        1
                   1563: #define V_INT          2
                   1564: 
                   1565: /* Forward declarations */
                   1566: static int sv_bell_style PARAMS((const char *));
                   1567: static int sv_combegin PARAMS((const char *));
                   1568: static int sv_dispprefix PARAMS((const char *));
                   1569: static int sv_compquery PARAMS((const char *));
                   1570: static int sv_compwidth PARAMS((const char *));
                   1571: static int sv_editmode PARAMS((const char *));
                   1572: static int sv_histsize PARAMS((const char *));
                   1573: static int sv_isrchterm PARAMS((const char *));
                   1574: static int sv_keymap PARAMS((const char *));
                   1575: static int sv_seqtimeout PARAMS((const char *));
                   1576: 
                   1577: static const struct {
                   1578:   const char * const name;
                   1579:   int flags;
                   1580:   _rl_sv_func_t *set_func;
                   1581: } string_varlist[] = {
                   1582:   { "bell-style",      V_STRING,       sv_bell_style },
                   1583:   { "comment-begin",   V_STRING,       sv_combegin },
                   1584:   { "completion-display-width", V_INT, sv_compwidth },
                   1585:   { "completion-prefix-display-length", V_INT, sv_dispprefix },
                   1586:   { "completion-query-items", V_INT,   sv_compquery },
                   1587:   { "editing-mode",    V_STRING,       sv_editmode },
                   1588:   { "history-size",    V_INT,          sv_histsize },
                   1589:   { "isearch-terminators", V_STRING,   sv_isrchterm },
                   1590:   { "keymap",          V_STRING,       sv_keymap },
                   1591:   { "keyseq-timeout",  V_INT,          sv_seqtimeout },
                   1592:   { (char *)NULL,      0, (_rl_sv_func_t *)0 }
                   1593: };
                   1594: 
                   1595: static int
                   1596: find_string_var (name)
                   1597:      const char *name;
                   1598: {
                   1599:   register int i;
                   1600: 
                   1601:   for (i = 0; string_varlist[i].name; i++)
                   1602:     if (_rl_stricmp (name, string_varlist[i].name) == 0)
                   1603:       return i;
                   1604:   return -1;
                   1605: }
                   1606: 
                   1607: /* A boolean value that can appear in a `set variable' command is true if
                   1608:    the value is null or empty, `on' (case-insenstive), or "1".  Any other
                   1609:    values result in 0 (false). */
                   1610: static int
                   1611: bool_to_int (value)
                   1612:      const char *value;
                   1613: {
                   1614:   return (value == 0 || *value == '\0' ||
                   1615:                (_rl_stricmp (value, "on") == 0) ||
                   1616:                (value[0] == '1' && value[1] == '\0'));
                   1617: }
                   1618: 
                   1619: char *
                   1620: rl_variable_value (name)
                   1621:      const char *name;
                   1622: {
                   1623:   register int i;
                   1624: 
                   1625:   /* Check for simple variables first. */
                   1626:   i = find_boolean_var (name);
                   1627:   if (i >= 0)
                   1628:     return (*boolean_varlist[i].value ? "on" : "off");
                   1629: 
                   1630:   i = find_string_var (name);
                   1631:   if (i >= 0)
                   1632:     return (_rl_get_string_variable_value (string_varlist[i].name));
                   1633: 
                   1634:   /* Unknown variable names return NULL. */
                   1635:   return 0;
                   1636: }
                   1637: 
                   1638: int
                   1639: rl_variable_bind (name, value)
                   1640:      const char *name, *value;
                   1641: {
                   1642:   register int i;
                   1643:   int  v;
                   1644: 
                   1645:   /* Check for simple variables first. */
                   1646:   i = find_boolean_var (name);
                   1647:   if (i >= 0)
                   1648:     {
                   1649:       *boolean_varlist[i].value = bool_to_int (value);
                   1650:       if (boolean_varlist[i].flags & V_SPECIAL)
                   1651:        hack_special_boolean_var (i);
                   1652:       return 0;
                   1653:     }
                   1654: 
                   1655:   i = find_string_var (name);
                   1656: 
                   1657:   /* For the time being, unknown variable names or string names without a
                   1658:      handler function are simply ignored. */
                   1659:   if (i < 0 || string_varlist[i].set_func == 0)
                   1660:     return 0;
                   1661: 
                   1662:   v = (*string_varlist[i].set_func) (value);
                   1663:   return v;
                   1664: }
                   1665: 
                   1666: static int
                   1667: sv_editmode (value)
                   1668:      const char *value;
                   1669: {
                   1670:   if (_rl_strnicmp (value, "vi", 2) == 0)
                   1671:     {
                   1672: #if defined (VI_MODE)
                   1673:       _rl_keymap = vi_insertion_keymap;
                   1674:       rl_editing_mode = vi_mode;
                   1675: #endif /* VI_MODE */
                   1676:       return 0;
                   1677:     }
                   1678:   else if (_rl_strnicmp (value, "emacs", 5) == 0)
                   1679:     {
                   1680:       _rl_keymap = emacs_standard_keymap;
                   1681:       rl_editing_mode = emacs_mode;
                   1682:       return 0;
                   1683:     }
                   1684:   return 1;
                   1685: }
                   1686: 
                   1687: static int
                   1688: sv_combegin (value)
                   1689:      const char *value;
                   1690: {
                   1691:   if (value && *value)
                   1692:     {
                   1693:       FREE (_rl_comment_begin);
                   1694:       _rl_comment_begin = savestring (value);
                   1695:       return 0;
                   1696:     }
                   1697:   return 1;
                   1698: }
                   1699: 
                   1700: static int
                   1701: sv_dispprefix (value)
                   1702:      const char *value;
                   1703: {
                   1704:   int nval = 0;
                   1705: 
                   1706:   if (value && *value)
                   1707:     {
                   1708:       nval = atoi (value);
                   1709:       if (nval < 0)
                   1710:        nval = 0;
                   1711:     }
                   1712:   _rl_completion_prefix_display_length = nval;
                   1713:   return 0;
                   1714: }
                   1715: 
                   1716: static int
                   1717: sv_compquery (value)
                   1718:      const char *value;
                   1719: {
                   1720:   int nval = 100;
                   1721: 
                   1722:   if (value && *value)
                   1723:     {
                   1724:       nval = atoi (value);
                   1725:       if (nval < 0)
                   1726:        nval = 0;
                   1727:     }
                   1728:   rl_completion_query_items = nval;
                   1729:   return 0;
                   1730: }
                   1731: 
                   1732: static int
                   1733: sv_compwidth (value)
                   1734:      const char *value;
                   1735: {
                   1736:   int nval = -1;
                   1737: 
                   1738:   if (value && *value)
                   1739:     nval = atoi (value);
                   1740: 
                   1741:   _rl_completion_columns = nval;
                   1742:   return 0;
                   1743: }
                   1744: 
                   1745: static int
                   1746: sv_histsize (value)
                   1747:      const char *value;
                   1748: {
                   1749:   int nval;
                   1750: 
                   1751:   nval = 500;
                   1752:   if (value && *value)
                   1753:     {
                   1754:       nval = atoi (value);
                   1755:       if (nval < 0)
                   1756:        {
                   1757:          unstifle_history ();
                   1758:          return 0;
                   1759:        }
                   1760:     }
                   1761:   stifle_history (nval);
                   1762:   return 0;
                   1763: }
                   1764: 
                   1765: static int
                   1766: sv_keymap (value)
                   1767:      const char *value;
                   1768: {
                   1769:   Keymap kmap;
                   1770: 
                   1771:   kmap = rl_get_keymap_by_name (value);
                   1772:   if (kmap)
                   1773:     {
                   1774:       rl_set_keymap (kmap);
                   1775:       return 0;
                   1776:     }
                   1777:   return 1;
                   1778: }
                   1779: 
                   1780: static int
                   1781: sv_seqtimeout (value)
                   1782:      const char *value;
                   1783: {
                   1784:   int nval;
                   1785: 
                   1786:   nval = 0;
                   1787:   if (value && *value)
                   1788:     {
                   1789:       nval = atoi (value);
                   1790:       if (nval < 0)
                   1791:        nval = 0;
                   1792:     }
                   1793:   _rl_keyseq_timeout = nval;
                   1794:   return 0;
                   1795: }
                   1796: 
                   1797: static int
                   1798: sv_bell_style (value)
                   1799:      const char *value;
                   1800: {
                   1801:   if (value == 0 || *value == '\0')
                   1802:     _rl_bell_preference = AUDIBLE_BELL;
                   1803:   else if (_rl_stricmp (value, "none") == 0 || _rl_stricmp (value, "off") == 0)
                   1804:     _rl_bell_preference = NO_BELL;
                   1805:   else if (_rl_stricmp (value, "audible") == 0 || _rl_stricmp (value, "on") == 0)
                   1806:     _rl_bell_preference = AUDIBLE_BELL;
                   1807:   else if (_rl_stricmp (value, "visible") == 0)
                   1808:     _rl_bell_preference = VISIBLE_BELL;
                   1809:   else
                   1810:     return 1;
                   1811:   return 0;
                   1812: }
                   1813: 
                   1814: static int
                   1815: sv_isrchterm (value)
                   1816:      const char *value;
                   1817: {
                   1818:   int beg, end, delim;
                   1819:   char *v;
                   1820: 
                   1821:   if (value == 0)
                   1822:     return 1;
                   1823: 
                   1824:   /* Isolate the value and translate it into a character string. */
                   1825:   v = savestring (value);
                   1826:   FREE (_rl_isearch_terminators);
                   1827:   if (v[0] == '"' || v[0] == '\'')
                   1828:     {
                   1829:       delim = v[0];
                   1830:       for (beg = end = 1; v[end] && v[end] != delim; end++)
                   1831:        ;
                   1832:     }
                   1833:   else
                   1834:     {
                   1835:       for (beg = end = 0; whitespace (v[end]) == 0; end++)
                   1836:        ;
                   1837:     }
                   1838: 
                   1839:   v[end] = '\0';
                   1840: 
                   1841:   /* The value starts at v + beg.  Translate it into a character string. */
                   1842:   _rl_isearch_terminators = (char *)xmalloc (2 * strlen (v) + 1);
                   1843:   rl_translate_keyseq (v + beg, _rl_isearch_terminators, &end);
                   1844:   _rl_isearch_terminators[end] = '\0';
                   1845: 
                   1846:   xfree (v);
                   1847:   return 0;
                   1848: }
                   1849:       
                   1850: /* Return the character which matches NAME.
                   1851:    For example, `Space' returns ' '. */
                   1852: 
                   1853: typedef struct {
                   1854:   const char * const name;
                   1855:   int value;
                   1856: } assoc_list;
                   1857: 
                   1858: static const assoc_list name_key_alist[] = {
                   1859:   { "DEL", 0x7f },
                   1860:   { "ESC", '\033' },
                   1861:   { "Escape", '\033' },
                   1862:   { "LFD", '\n' },
                   1863:   { "Newline", '\n' },
                   1864:   { "RET", '\r' },
                   1865:   { "Return", '\r' },
                   1866:   { "Rubout", 0x7f },
                   1867:   { "SPC", ' ' },
                   1868:   { "Space", ' ' },
                   1869:   { "Tab", 0x09 },
                   1870:   { (char *)0x0, 0 }
                   1871: };
                   1872: 
                   1873: static int
                   1874: glean_key_from_name (name)
                   1875:      char *name;
                   1876: {
                   1877:   register int i;
                   1878: 
                   1879:   for (i = 0; name_key_alist[i].name; i++)
                   1880:     if (_rl_stricmp (name, name_key_alist[i].name) == 0)
                   1881:       return (name_key_alist[i].value);
                   1882: 
                   1883:   return (*(unsigned char *)name);     /* XXX was return (*name) */
                   1884: }
                   1885: 
                   1886: /* Auxiliary functions to manage keymaps. */
                   1887: static const struct {
                   1888:   const char * const name;
                   1889:   Keymap map;
                   1890: } keymap_names[] = {
                   1891:   { "emacs", emacs_standard_keymap },
                   1892:   { "emacs-standard", emacs_standard_keymap },
                   1893:   { "emacs-meta", emacs_meta_keymap },
                   1894:   { "emacs-ctlx", emacs_ctlx_keymap },
                   1895: #if defined (VI_MODE)
                   1896:   { "vi", vi_movement_keymap },
                   1897:   { "vi-move", vi_movement_keymap },
                   1898:   { "vi-command", vi_movement_keymap },
                   1899:   { "vi-insert", vi_insertion_keymap },
                   1900: #endif /* VI_MODE */
                   1901:   { (char *)0x0, (Keymap)0x0 }
                   1902: };
                   1903: 
                   1904: Keymap
                   1905: rl_get_keymap_by_name (name)
                   1906:      const char *name;
                   1907: {
                   1908:   register int i;
                   1909: 
                   1910:   for (i = 0; keymap_names[i].name; i++)
                   1911:     if (_rl_stricmp (name, keymap_names[i].name) == 0)
                   1912:       return (keymap_names[i].map);
                   1913:   return ((Keymap) NULL);
                   1914: }
                   1915: 
                   1916: char *
                   1917: rl_get_keymap_name (map)
                   1918:      Keymap map;
                   1919: {
                   1920:   register int i;
                   1921:   for (i = 0; keymap_names[i].name; i++)
                   1922:     if (map == keymap_names[i].map)
                   1923:       return ((char *)keymap_names[i].name);
                   1924:   return ((char *)NULL);
                   1925: }
                   1926:   
                   1927: void
                   1928: rl_set_keymap (map)
                   1929:      Keymap map;
                   1930: {
                   1931:   if (map)
                   1932:     _rl_keymap = map;
                   1933: }
                   1934: 
                   1935: Keymap
                   1936: rl_get_keymap ()
                   1937: {
                   1938:   return (_rl_keymap);
                   1939: }
                   1940: 
                   1941: void
                   1942: rl_set_keymap_from_edit_mode ()
                   1943: {
                   1944:   if (rl_editing_mode == emacs_mode)
                   1945:     _rl_keymap = emacs_standard_keymap;
                   1946: #if defined (VI_MODE)
                   1947:   else if (rl_editing_mode == vi_mode)
                   1948:     _rl_keymap = vi_insertion_keymap;
                   1949: #endif /* VI_MODE */
                   1950: }
                   1951: 
                   1952: char *
                   1953: rl_get_keymap_name_from_edit_mode ()
                   1954: {
                   1955:   if (rl_editing_mode == emacs_mode)
                   1956:     return "emacs";
                   1957: #if defined (VI_MODE)
                   1958:   else if (rl_editing_mode == vi_mode)
                   1959:     return "vi";
                   1960: #endif /* VI_MODE */
                   1961:   else
                   1962:     return "none";
                   1963: }
                   1964: 
                   1965: /* **************************************************************** */
                   1966: /*                                                                 */
                   1967: /*               Key Binding and Function Information              */
                   1968: /*                                                                 */
                   1969: /* **************************************************************** */
                   1970: 
                   1971: /* Each of the following functions produces information about the
                   1972:    state of keybindings and functions known to Readline.  The info
                   1973:    is always printed to rl_outstream, and in such a way that it can
                   1974:    be read back in (i.e., passed to rl_parse_and_bind ()). */
                   1975: 
                   1976: /* Print the names of functions known to Readline. */
                   1977: void
                   1978: rl_list_funmap_names ()
                   1979: {
                   1980:   register int i;
                   1981:   const char **funmap_names;
                   1982: 
                   1983:   funmap_names = rl_funmap_names ();
                   1984: 
                   1985:   if (!funmap_names)
                   1986:     return;
                   1987: 
                   1988:   for (i = 0; funmap_names[i]; i++)
                   1989:     fprintf (rl_outstream, "%s\n", funmap_names[i]);
                   1990: 
                   1991:   xfree (funmap_names);
                   1992: }
                   1993: 
                   1994: static char *
                   1995: _rl_get_keyname (key)
                   1996:      int key;
                   1997: {
                   1998:   char *keyname;
                   1999:   int i, c;
                   2000: 
                   2001:   keyname = (char *)xmalloc (8);
                   2002: 
                   2003:   c = key;
                   2004:   /* Since this is going to be used to write out keysequence-function
                   2005:      pairs for possible inclusion in an inputrc file, we don't want to
                   2006:      do any special meta processing on KEY. */
                   2007: 
                   2008: #if 1
                   2009:   /* XXX - Experimental */
                   2010:   /* We might want to do this, but the old version of the code did not. */
                   2011: 
                   2012:   /* If this is an escape character, we don't want to do any more processing.
                   2013:      Just add the special ESC key sequence and return. */
                   2014:   if (c == ESC)
                   2015:     {
                   2016:       keyname[0] = '\\';
                   2017:       keyname[1] = 'e';
                   2018:       keyname[2] = '\0';
                   2019:       return keyname;
                   2020:     }
                   2021: #endif
                   2022: 
                   2023:   /* RUBOUT is translated directly into \C-? */
                   2024:   if (key == RUBOUT)
                   2025:     {
                   2026:       keyname[0] = '\\';
                   2027:       keyname[1] = 'C';
                   2028:       keyname[2] = '-';
                   2029:       keyname[3] = '?';
                   2030:       keyname[4] = '\0';
                   2031:       return keyname;
                   2032:     }
                   2033: 
                   2034:   i = 0;
                   2035:   /* Now add special prefixes needed for control characters.  This can
                   2036:      potentially change C. */
                   2037:   if (CTRL_CHAR (c))
                   2038:     {
                   2039:       keyname[i++] = '\\';
                   2040:       keyname[i++] = 'C';
                   2041:       keyname[i++] = '-';
                   2042:       c = _rl_to_lower (UNCTRL (c));
                   2043:     }
                   2044: 
                   2045:   /* XXX experimental code.  Turn the characters that are not ASCII or
                   2046:      ISO Latin 1 (128 - 159) into octal escape sequences (\200 - \237).
                   2047:      This changes C. */
                   2048:   if (c >= 128 && c <= 159)
                   2049:     {
                   2050:       keyname[i++] = '\\';
                   2051:       keyname[i++] = '2';
                   2052:       c -= 128;
                   2053:       keyname[i++] = (c / 8) + '0';
                   2054:       c = (c % 8) + '0';
                   2055:     }
                   2056: 
                   2057:   /* Now, if the character needs to be quoted with a backslash, do that. */
                   2058:   if (c == '\\' || c == '"')
                   2059:     keyname[i++] = '\\';
                   2060: 
                   2061:   /* Now add the key, terminate the string, and return it. */
                   2062:   keyname[i++] = (char) c;
                   2063:   keyname[i] = '\0';
                   2064: 
                   2065:   return keyname;
                   2066: }
                   2067: 
                   2068: /* Return a NULL terminated array of strings which represent the key
                   2069:    sequences that are used to invoke FUNCTION in MAP. */
                   2070: char **
                   2071: rl_invoking_keyseqs_in_map (function, map)
                   2072:      rl_command_func_t *function;
                   2073:      Keymap map;
                   2074: {
                   2075:   register int key;
                   2076:   char **result;
                   2077:   int result_index, result_size;
                   2078: 
                   2079:   result = (char **)NULL;
                   2080:   result_index = result_size = 0;
                   2081: 
                   2082:   for (key = 0; key < KEYMAP_SIZE; key++)
                   2083:     {
                   2084:       switch (map[key].type)
                   2085:        {
                   2086:        case ISMACR:
                   2087:          /* Macros match, if, and only if, the pointers are identical.
                   2088:             Thus, they are treated exactly like functions in here. */
                   2089:        case ISFUNC:
                   2090:          /* If the function in the keymap is the one we are looking for,
                   2091:             then add the current KEY to the list of invoking keys. */
                   2092:          if (map[key].function == function)
                   2093:            {
                   2094:              char *keyname;
                   2095: 
                   2096:              keyname = _rl_get_keyname (key);
                   2097: 
                   2098:              if (result_index + 2 > result_size)
                   2099:                {
                   2100:                  result_size += 10;
                   2101:                  result = (char **)xrealloc (result, result_size * sizeof (char *));
                   2102:                }
                   2103: 
                   2104:              result[result_index++] = keyname;
                   2105:              result[result_index] = (char *)NULL;
                   2106:            }
                   2107:          break;
                   2108: 
                   2109:        case ISKMAP:
                   2110:          {
                   2111:            char **seqs;
                   2112:            register int i;
                   2113: 
                   2114:            /* Find the list of keyseqs in this map which have FUNCTION as
                   2115:               their target.  Add the key sequences found to RESULT. */
                   2116:            if (map[key].function)
                   2117:              seqs =
                   2118:                rl_invoking_keyseqs_in_map (function, FUNCTION_TO_KEYMAP (map, key));
                   2119:            else
                   2120:              break;
                   2121: 
                   2122:            if (seqs == 0)
                   2123:              break;
                   2124: 
                   2125:            for (i = 0; seqs[i]; i++)
                   2126:              {
                   2127:                char *keyname = (char *)xmalloc (6 + strlen (seqs[i]));
                   2128: 
                   2129:                if (key == ESC)
                   2130:                  {
                   2131:                    /* If ESC is the meta prefix and we're converting chars
                   2132:                       with the eighth bit set to ESC-prefixed sequences, then
                   2133:                       we can use \M-.  Otherwise we need to use the sequence
                   2134:                       for ESC. */
                   2135:                    if (_rl_convert_meta_chars_to_ascii && map[ESC].type == ISKMAP)
                   2136:                      sprintf (keyname, "\\M-");
                   2137:                    else
                   2138:                      sprintf (keyname, "\\e");
                   2139:                  }
                   2140:                else if (CTRL_CHAR (key))
                   2141:                  sprintf (keyname, "\\C-%c", _rl_to_lower (UNCTRL (key)));
                   2142:                else if (key == RUBOUT)
                   2143:                  sprintf (keyname, "\\C-?");
                   2144:                else if (key == '\\' || key == '"')
                   2145:                  {
                   2146:                    keyname[0] = '\\';
                   2147:                    keyname[1] = (char) key;
                   2148:                    keyname[2] = '\0';
                   2149:                  }
                   2150:                else
                   2151:                  {
                   2152:                    keyname[0] = (char) key;
                   2153:                    keyname[1] = '\0';
                   2154:                  }
                   2155:                
                   2156:                strcat (keyname, seqs[i]);
                   2157:                xfree (seqs[i]);
                   2158: 
                   2159:                if (result_index + 2 > result_size)
                   2160:                  {
                   2161:                    result_size += 10;
                   2162:                    result = (char **)xrealloc (result, result_size * sizeof (char *));
                   2163:                  }
                   2164: 
                   2165:                result[result_index++] = keyname;
                   2166:                result[result_index] = (char *)NULL;
                   2167:              }
                   2168: 
                   2169:            xfree (seqs);
                   2170:          }
                   2171:          break;
                   2172:        }
                   2173:     }
                   2174:   return (result);
                   2175: }
                   2176: 
                   2177: /* Return a NULL terminated array of strings which represent the key
                   2178:    sequences that can be used to invoke FUNCTION using the current keymap. */
                   2179: char **
                   2180: rl_invoking_keyseqs (function)
                   2181:      rl_command_func_t *function;
                   2182: {
                   2183:   return (rl_invoking_keyseqs_in_map (function, _rl_keymap));
                   2184: }
                   2185: 
                   2186: /* Print all of the functions and their bindings to rl_outstream.  If
                   2187:    PRINT_READABLY is non-zero, then print the output in such a way
                   2188:    that it can be read back in. */
                   2189: void
                   2190: rl_function_dumper (print_readably)
                   2191:      int print_readably;
                   2192: {
                   2193:   register int i;
                   2194:   const char **names;
                   2195:   const char *name;
                   2196: 
                   2197:   names = rl_funmap_names ();
                   2198: 
                   2199:   fprintf (rl_outstream, "\n");
                   2200: 
                   2201:   for (i = 0; name = names[i]; i++)
                   2202:     {
                   2203:       rl_command_func_t *function;
                   2204:       char **invokers;
                   2205: 
                   2206:       function = rl_named_function (name);
                   2207:       invokers = rl_invoking_keyseqs_in_map (function, _rl_keymap);
                   2208: 
                   2209:       if (print_readably)
                   2210:        {
                   2211:          if (!invokers)
                   2212:            fprintf (rl_outstream, "# %s (not bound)\n", name);
                   2213:          else
                   2214:            {
                   2215:              register int j;
                   2216: 
                   2217:              for (j = 0; invokers[j]; j++)
                   2218:                {
                   2219:                  fprintf (rl_outstream, "\"%s\": %s\n",
                   2220:                           invokers[j], name);
                   2221:                  xfree (invokers[j]);
                   2222:                }
                   2223: 
                   2224:              xfree (invokers);
                   2225:            }
                   2226:        }
                   2227:       else
                   2228:        {
                   2229:          if (!invokers)
                   2230:            fprintf (rl_outstream, "%s is not bound to any keys\n",
                   2231:                     name);
                   2232:          else
                   2233:            {
                   2234:              register int j;
                   2235: 
                   2236:              fprintf (rl_outstream, "%s can be found on ", name);
                   2237: 
                   2238:              for (j = 0; invokers[j] && j < 5; j++)
                   2239:                {
                   2240:                  fprintf (rl_outstream, "\"%s\"%s", invokers[j],
                   2241:                           invokers[j + 1] ? ", " : ".\n");
                   2242:                }
                   2243: 
                   2244:              if (j == 5 && invokers[j])
                   2245:                fprintf (rl_outstream, "...\n");
                   2246: 
                   2247:              for (j = 0; invokers[j]; j++)
                   2248:                xfree (invokers[j]);
                   2249: 
                   2250:              xfree (invokers);
                   2251:            }
                   2252:        }
                   2253:     }
                   2254: 
                   2255:   xfree (names);
                   2256: }
                   2257: 
                   2258: /* Print all of the current functions and their bindings to
                   2259:    rl_outstream.  If an explicit argument is given, then print
                   2260:    the output in such a way that it can be read back in. */
                   2261: int
                   2262: rl_dump_functions (count, key)
                   2263:      int count, key;
                   2264: {
                   2265:   if (rl_dispatching)
                   2266:     fprintf (rl_outstream, "\r\n");
                   2267:   rl_function_dumper (rl_explicit_arg);
                   2268:   rl_on_new_line ();
                   2269:   return (0);
                   2270: }
                   2271: 
                   2272: static void
                   2273: _rl_macro_dumper_internal (print_readably, map, prefix)
                   2274:      int print_readably;
                   2275:      Keymap map;
                   2276:      char *prefix;
                   2277: {
                   2278:   register int key;
                   2279:   char *keyname, *out;
                   2280:   int prefix_len;
                   2281: 
                   2282:   for (key = 0; key < KEYMAP_SIZE; key++)
                   2283:     {
                   2284:       switch (map[key].type)
                   2285:        {
                   2286:        case ISMACR:
                   2287:          keyname = _rl_get_keyname (key);
                   2288:          out = _rl_untranslate_macro_value ((char *)map[key].function, 0);
                   2289: 
                   2290:          if (print_readably)
                   2291:            fprintf (rl_outstream, "\"%s%s\": \"%s\"\n", prefix ? prefix : "",
                   2292:                                                         keyname,
                   2293:                                                         out ? out : "");
                   2294:          else
                   2295:            fprintf (rl_outstream, "%s%s outputs %s\n", prefix ? prefix : "",
                   2296:                                                        keyname,
                   2297:                                                        out ? out : "");
                   2298:          xfree (keyname);
                   2299:          xfree (out);
                   2300:          break;
                   2301:        case ISFUNC:
                   2302:          break;
                   2303:        case ISKMAP:
                   2304:          prefix_len = prefix ? strlen (prefix) : 0;
                   2305:          if (key == ESC)
                   2306:            {
                   2307:              keyname = (char *)xmalloc (3 + prefix_len);
                   2308:              if (prefix)
                   2309:                strcpy (keyname, prefix);
                   2310:              keyname[prefix_len] = '\\';
                   2311:              keyname[prefix_len + 1] = 'e';
                   2312:              keyname[prefix_len + 2] = '\0';
                   2313:            }
                   2314:          else
                   2315:            {
                   2316:              keyname = _rl_get_keyname (key);
                   2317:              if (prefix)
                   2318:                {
                   2319:                  out = (char *)xmalloc (strlen (keyname) + prefix_len + 1);
                   2320:                  strcpy (out, prefix);
                   2321:                  strcpy (out + prefix_len, keyname);
                   2322:                  xfree (keyname);
                   2323:                  keyname = out;
                   2324:                }
                   2325:            }
                   2326: 
                   2327:          _rl_macro_dumper_internal (print_readably, FUNCTION_TO_KEYMAP (map, key), keyname);
                   2328:          xfree (keyname);
                   2329:          break;
                   2330:        }
                   2331:     }
                   2332: }
                   2333: 
                   2334: void
                   2335: rl_macro_dumper (print_readably)
                   2336:      int print_readably;
                   2337: {
                   2338:   _rl_macro_dumper_internal (print_readably, _rl_keymap, (char *)NULL);
                   2339: }
                   2340: 
                   2341: int
                   2342: rl_dump_macros (count, key)
                   2343:      int count, key;
                   2344: {
                   2345:   if (rl_dispatching)
                   2346:     fprintf (rl_outstream, "\r\n");
                   2347:   rl_macro_dumper (rl_explicit_arg);
                   2348:   rl_on_new_line ();
                   2349:   return (0);
                   2350: }
                   2351: 
                   2352: static char *
                   2353: _rl_get_string_variable_value (name)
                   2354:      const char *name;
                   2355: {
                   2356:   static char numbuf[32];
                   2357:   char *ret;
                   2358: 
                   2359:   if (_rl_stricmp (name, "bell-style") == 0)
                   2360:     {
                   2361:       switch (_rl_bell_preference)
                   2362:        {
                   2363:          case NO_BELL:
                   2364:            return "none";
                   2365:          case VISIBLE_BELL:
                   2366:            return "visible";
                   2367:          case AUDIBLE_BELL:
                   2368:          default:
                   2369:            return "audible";
                   2370:        }
                   2371:     }
                   2372:   else if (_rl_stricmp (name, "comment-begin") == 0)
                   2373:     return (_rl_comment_begin ? _rl_comment_begin : RL_COMMENT_BEGIN_DEFAULT);
                   2374:   else if (_rl_stricmp (name, "completion-display-width") == 0)
                   2375:     {
                   2376:       sprintf (numbuf, "%d", _rl_completion_columns);
                   2377:       return (numbuf);
                   2378:     }
                   2379:   else if (_rl_stricmp (name, "completion-prefix-display-length") == 0)
                   2380:     {
                   2381:       sprintf (numbuf, "%d", _rl_completion_prefix_display_length);
                   2382:       return (numbuf);
                   2383:     }
                   2384:   else if (_rl_stricmp (name, "completion-query-items") == 0)
                   2385:     {
                   2386:       sprintf (numbuf, "%d", rl_completion_query_items);
                   2387:       return (numbuf);
                   2388:     }
                   2389:   else if (_rl_stricmp (name, "editing-mode") == 0)
                   2390:     return (rl_get_keymap_name_from_edit_mode ());
                   2391:   else if (_rl_stricmp (name, "history-size") == 0)
                   2392:     {
                   2393:       sprintf (numbuf, "%d", history_is_stifled() ? history_max_entries : 0);
                   2394:       return (numbuf);
                   2395:     }
                   2396:   else if (_rl_stricmp (name, "isearch-terminators") == 0)
                   2397:     {
                   2398:       if (_rl_isearch_terminators == 0)
                   2399:        return 0;
                   2400:       ret = _rl_untranslate_macro_value (_rl_isearch_terminators, 0);
                   2401:       if (ret)
                   2402:        {
                   2403:          strncpy (numbuf, ret, sizeof (numbuf) - 1);
                   2404:          xfree (ret);
                   2405:          numbuf[sizeof(numbuf) - 1] = '\0';
                   2406:        }
                   2407:       else
                   2408:        numbuf[0] = '\0';
                   2409:       return numbuf;
                   2410:     }
                   2411:   else if (_rl_stricmp (name, "keymap") == 0)
                   2412:     {
                   2413:       ret = rl_get_keymap_name (_rl_keymap);
                   2414:       if (ret == 0)
                   2415:        ret = rl_get_keymap_name_from_edit_mode ();
                   2416:       return (ret ? ret : "none");
                   2417:     }
                   2418:   else if (_rl_stricmp (name, "keyseq-timeout") == 0)
                   2419:     {
                   2420:       sprintf (numbuf, "%d", _rl_keyseq_timeout);    
                   2421:       return (numbuf);
                   2422:     }
                   2423:   else
                   2424:     return (0);
                   2425: }
                   2426: 
                   2427: void
                   2428: rl_variable_dumper (print_readably)
                   2429:      int print_readably;
                   2430: {
                   2431:   int i;
                   2432:   char *v;
                   2433: 
                   2434:   for (i = 0; boolean_varlist[i].name; i++)
                   2435:     {
                   2436:       if (print_readably)
                   2437:         fprintf (rl_outstream, "set %s %s\n", boolean_varlist[i].name,
                   2438:                               *boolean_varlist[i].value ? "on" : "off");
                   2439:       else
                   2440:         fprintf (rl_outstream, "%s is set to `%s'\n", boolean_varlist[i].name,
                   2441:                               *boolean_varlist[i].value ? "on" : "off");
                   2442:     }
                   2443: 
                   2444:   for (i = 0; string_varlist[i].name; i++)
                   2445:     {
                   2446:       v = _rl_get_string_variable_value (string_varlist[i].name);
                   2447:       if (v == 0)      /* _rl_isearch_terminators can be NULL */
                   2448:        continue;
                   2449:       if (print_readably)
                   2450:         fprintf (rl_outstream, "set %s %s\n", string_varlist[i].name, v);
                   2451:       else
                   2452:         fprintf (rl_outstream, "%s is set to `%s'\n", string_varlist[i].name, v);
                   2453:     }
                   2454: }
                   2455: 
                   2456: /* Print all of the current variables and their values to
                   2457:    rl_outstream.  If an explicit argument is given, then print
                   2458:    the output in such a way that it can be read back in. */
                   2459: int
                   2460: rl_dump_variables (count, key)
                   2461:      int count, key;
                   2462: {
                   2463:   if (rl_dispatching)
                   2464:     fprintf (rl_outstream, "\r\n");
                   2465:   rl_variable_dumper (rl_explicit_arg);
                   2466:   rl_on_new_line ();
                   2467:   return (0);
                   2468: }
                   2469: 
                   2470: /* Return non-zero if any members of ARRAY are a substring in STRING. */
                   2471: static int
                   2472: substring_member_of_array (string, array)
                   2473:      const char *string;
                   2474:      const char * const *array;
                   2475: {
                   2476:   while (*array)
                   2477:     {
                   2478:       if (_rl_strindex (string, *array))
                   2479:        return (1);
                   2480:       array++;
                   2481:     }
                   2482:   return (0);
                   2483: }

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>