home *** CD-ROM | disk | FTP | other *** search
/ vim.ftp.fu-berlin.de / 2015-02-03.vim.ftp.fu-berlin.de.tar / vim.ftp.fu-berlin.de / unix / vim-6.2.tar.bz2 / vim-6.2.tar / vim62 / src / getchar.c < prev    next >
Encoding:
C/C++ Source or Header  |  2003-05-20  |  106.8 KB  |  4,565 lines

  1. /* vi:set ts=8 sts=4 sw=4:
  2.  *
  3.  * VIM - Vi IMproved    by Bram Moolenaar
  4.  *
  5.  * Do ":help uganda"  in Vim to read copying and usage conditions.
  6.  * Do ":help credits" in Vim to see a list of people who contributed.
  7.  * See README.txt for an overview of the Vim source code.
  8.  */
  9.  
  10. /*
  11.  * getchar.c
  12.  *
  13.  * functions related with getting a character from the user/mapping/redo/...
  14.  *
  15.  * manipulations with redo buffer and stuff buffer
  16.  * mappings and abbreviations
  17.  */
  18.  
  19. #include "vim.h"
  20.  
  21. /*
  22.  * These buffers are used for storing:
  23.  * - stuffed characters: A command that is translated into another command.
  24.  * - redo characters: will redo the last change.
  25.  * - recorded chracters: for the "q" command.
  26.  *
  27.  * The bytes are stored like in the typeahead buffer:
  28.  * - K_SPECIAL introduces a special key (two more bytes follow).  A literal
  29.  *   K_SPECIAL is stored as K_SPECIAL KS_SPECIAL KE_FILLER.
  30.  * - CSI introduces a GUI termcap code (also when gui.in_use is FALSE,
  31.  *   otherwise switching the GUI on would make mappings invalid).
  32.  *   A literal CSI is stored as CSI KS_EXTRA KE_CSI.
  33.  * These translations are also done on multi-byte characters!
  34.  *
  35.  * Escaping CSI bytes is done by the system-specific input functions, called
  36.  * by ui_inchar().
  37.  * Escaping K_SPECIAL is done by inchar().
  38.  * Un-escaping is done by vgetc().
  39.  */
  40.  
  41. #define MINIMAL_SIZE 20            /* minimal size for b_str */
  42.  
  43. static struct buffheader redobuff = {{NULL, {NUL}}, NULL, 0, 0};
  44. static struct buffheader old_redobuff = {{NULL, {NUL}}, NULL, 0, 0};
  45. #if defined(FEAT_AUTOCMD) || defined(FEAT_EVAL) || defined(PROTO)
  46. static struct buffheader save_redobuff = {{NULL, {NUL}}, NULL, 0, 0};
  47. static struct buffheader save_old_redobuff = {{NULL, {NUL}}, NULL, 0, 0};
  48. #endif
  49. static struct buffheader recordbuff = {{NULL, {NUL}}, NULL, 0, 0};
  50.  
  51. static int typeahead_char = 0;        /* typeahead char that's not flushed */
  52.  
  53. /*
  54.  * when block_redo is TRUE redo buffer will not be changed
  55.  * used by edit() to repeat insertions and 'V' command for redoing
  56.  */
  57. static int    block_redo = FALSE;
  58.  
  59. /*
  60.  * Make a hash value for a mapping.
  61.  * "mode" is the lower 4 bits of the State for the mapping.
  62.  * "c1" is the first character of the "lhs".
  63.  * Returns a value between 0 and 255, index in maphash.
  64.  * Put Normal/Visual mode mappings mostly separately from Insert/Cmdline mode.
  65.  */
  66. #define MAP_HASH(mode, c1) (((mode) & (NORMAL + VISUAL + OP_PENDING)) ? (c1) : ((c1) ^ 0x80))
  67.  
  68. /*
  69.  * Each mapping is put in one of the 256 hash lists, to speed up finding it.
  70.  */
  71. static mapblock_T    *(maphash[256]);
  72. static int        maphash_valid = FALSE;
  73.  
  74. /*
  75.  * List used for abbreviations.
  76.  */
  77. static mapblock_T    *first_abbr = NULL; /* first entry in abbrlist */
  78.  
  79. /*
  80.  * variables used by vgetorpeek() and flush_buffers()
  81.  *
  82.  * typebuf.tb_buf[] contains all characters that are not consumed yet.
  83.  * typebuf.tb_buf[typebuf.tb_off] is the first valid character.
  84.  * typebuf.tb_buf[typebuf.tb_off + typebuf.tb_len - 1] is the last valid char.
  85.  * typebuf.tb_buf[typebuf.tb_off + typebuf.tb_len] must be NUL.
  86.  * The head of the buffer may contain the result of mappings, abbreviations
  87.  * and @a commands.  The length of this part is typebuf.tb_maplen.
  88.  * typebuf.tb_silent is the part where <silent> applies.
  89.  * After the head are characters that come from the terminal.
  90.  * typebuf.tb_no_abbr_cnt is the number of characters in typebuf.tb_buf that
  91.  * should not be considered for abbreviations.
  92.  * Some parts of typebuf.tb_buf may not be mapped. These parts are remembered
  93.  * in typebuf.tb_noremap[], which is the same length as typebuf.tb_buf and
  94.  * contains RM_NONE for the characters that are not to be remapped.
  95.  * typebuf.tb_noremap[typebuf.tb_off] is the first valid flag.
  96.  * (typebuf has been put in globals.h, because check_termcode() needs it).
  97.  */
  98. #define RM_YES        0    /* tb_noremap: remap */
  99. #define RM_NONE        1    /* tb_noremap: don't remap */
  100. #define RM_SCRIPT    2    /* tb_noremap: remap local script mappings */
  101.  
  102. /* typebuf.tb_buf has three parts: room in front (for result of mappings), the
  103.  * middle for typeahead and room for new characters (which needs to be 3 *
  104.  * MAXMAPLEN) for the Amiga).
  105.  */
  106. #define TYPELEN_INIT    (5 * (MAXMAPLEN + 3))
  107. static char_u    typebuf_init[TYPELEN_INIT];    /* initial typebuf.tb_buf */
  108. static char_u    noremapbuf_init[TYPELEN_INIT];    /* initial typebuf.tb_noremap */
  109.  
  110. static int    last_recorded_len = 0;    /* number of last recorded chars */
  111.  
  112. static char_u    *get_buffcont __ARGS((struct buffheader *, int));
  113. static void    add_buff __ARGS((struct buffheader *, char_u *, long n));
  114. static void    add_num_buff __ARGS((struct buffheader *, long));
  115. static void    add_char_buff __ARGS((struct buffheader *, int));
  116. static int    read_stuff __ARGS((int advance));
  117. static void    start_stuff __ARGS((void));
  118. static int    read_redo __ARGS((int, int));
  119. static void    copy_redo __ARGS((int));
  120. static void    init_typebuf __ARGS((void));
  121. static void    gotchars __ARGS((char_u *, int));
  122. static void    may_sync_undo __ARGS((void));
  123. static void    closescript __ARGS((void));
  124. static int    vgetorpeek __ARGS((int));
  125. static void    map_free __ARGS((mapblock_T **));
  126. static void    validate_maphash __ARGS((void));
  127. static void    showmap __ARGS((mapblock_T *mp, int local));
  128.  
  129. /*
  130.  * Free and clear a buffer.
  131.  */
  132.     void
  133. free_buff(buf)
  134.     struct buffheader    *buf;
  135. {
  136.     struct buffblock    *p, *np;
  137.  
  138.     for (p = buf->bh_first.b_next; p != NULL; p = np)
  139.     {
  140.     np = p->b_next;
  141.     vim_free(p);
  142.     }
  143.     buf->bh_first.b_next = NULL;
  144. }
  145.  
  146. /*
  147.  * Return the contents of a buffer as a single string.
  148.  * K_SPECIAL and CSI in the returned string are escaped.
  149.  */
  150.     static char_u *
  151. get_buffcont(buffer, dozero)
  152.     struct buffheader    *buffer;
  153.     int            dozero;        /* count == zero is not an error */
  154. {
  155.     long_u        count = 0;
  156.     char_u        *p = NULL;
  157.     char_u        *p2;
  158.     char_u        *str;
  159.     struct buffblock *bp;
  160.  
  161. /* compute the total length of the string */
  162.     for (bp = buffer->bh_first.b_next; bp != NULL; bp = bp->b_next)
  163.     count += (long_u)STRLEN(bp->b_str);
  164.  
  165.     if ((count || dozero) && (p = lalloc(count + 1, TRUE)) != NULL)
  166.     {
  167.     p2 = p;
  168.     for (bp = buffer->bh_first.b_next; bp != NULL; bp = bp->b_next)
  169.         for (str = bp->b_str; *str; )
  170.         *p2++ = *str++;
  171.     *p2 = NUL;
  172.     }
  173.     return (p);
  174. }
  175.  
  176. /*
  177.  * Return the contents of the record buffer as a single string
  178.  * and clear the record buffer.
  179.  * K_SPECIAL and CSI in the returned string are escaped.
  180.  */
  181.     char_u *
  182. get_recorded()
  183. {
  184.     char_u    *p;
  185.     size_t    len;
  186.  
  187.     p = get_buffcont(&recordbuff, TRUE);
  188.     free_buff(&recordbuff);
  189.  
  190.     /*
  191.      * Remove the characters that were added the last time, these must be the
  192.      * (possibly mapped) characters that stopped the recording.
  193.      */
  194.     len = STRLEN(p);
  195.     if ((int)len >= last_recorded_len)
  196.     {
  197.     len -= last_recorded_len;
  198.     p[len] = NUL;
  199.     }
  200.  
  201.     /*
  202.      * When stopping recording from Insert mode with CTRL-O q, also remove the
  203.      * CTRL-O.
  204.      */
  205.     if (len > 0 && restart_edit != 0 && p[len - 1] == Ctrl_O)
  206.     p[len - 1] = NUL;
  207.  
  208.     return (p);
  209. }
  210.  
  211. /*
  212.  * Return the contents of the redo buffer as a single string.
  213.  * K_SPECIAL and CSI in the returned string are escaped.
  214.  */
  215.     char_u *
  216. get_inserted()
  217. {
  218.     return(get_buffcont(&redobuff, FALSE));
  219. }
  220.  
  221. /*
  222.  * add string "s" after the current block of buffer "buf"
  223.  * K_SPECIAL and CSI should have been escaped already.
  224.  */
  225.     static void
  226. add_buff(buf, s, slen)
  227.     struct buffheader    *buf;
  228.     char_u        *s;
  229.     long        slen;    /* length of "s" or -1 */
  230. {
  231.     struct buffblock *p;
  232.     long_u        len;
  233.  
  234.     if (slen < 0)
  235.     slen = (long)STRLEN(s);
  236.     if (slen == 0)                /* don't add empty strings */
  237.     return;
  238.  
  239.     if (buf->bh_first.b_next == NULL)    /* first add to list */
  240.     {
  241.     buf->bh_space = 0;
  242.     buf->bh_curr = &(buf->bh_first);
  243.     }
  244.     else if (buf->bh_curr == NULL)    /* buffer has already been read */
  245.     {
  246.     EMSG(_("E222: Add to read buffer"));
  247.     return;
  248.     }
  249.     else if (buf->bh_index != 0)
  250.     STRCPY(buf->bh_first.b_next->b_str,
  251.                  buf->bh_first.b_next->b_str + buf->bh_index);
  252.     buf->bh_index = 0;
  253.  
  254.     if (buf->bh_space >= (int)slen)
  255.     {
  256.     len = (long_u)STRLEN(buf->bh_curr->b_str);
  257.     STRNCPY(buf->bh_curr->b_str + len, s, slen);
  258.     buf->bh_curr->b_str[len + slen] = NUL;
  259.     buf->bh_space -= slen;
  260.     }
  261.     else
  262.     {
  263.     if (slen < MINIMAL_SIZE)
  264.         len = MINIMAL_SIZE;
  265.     else
  266.         len = slen;
  267.     p = (struct buffblock *)lalloc((long_u)(sizeof(struct buffblock) + len),
  268.                                     TRUE);
  269.     if (p == NULL)
  270.         return; /* no space, just forget it */
  271.     buf->bh_space = len - slen;
  272.     STRNCPY(p->b_str, s, slen);
  273.     p->b_str[slen] = NUL;
  274.  
  275.     p->b_next = buf->bh_curr->b_next;
  276.     buf->bh_curr->b_next = p;
  277.     buf->bh_curr = p;
  278.     }
  279.     return;
  280. }
  281.  
  282. /*
  283.  * Add number "n" to buffer "buf".
  284.  */
  285.     static void
  286. add_num_buff(buf, n)
  287.     struct buffheader *buf;
  288.     long          n;
  289. {
  290.     char_u    number[32];
  291.  
  292.     sprintf((char *)number, "%ld", n);
  293.     add_buff(buf, number, -1L);
  294. }
  295.  
  296. /*
  297.  * Add character 'c' to buffer "buf".
  298.  * Translates special keys, NUL, CSI, K_SPECIAL and multibyte characters.
  299.  */
  300.     static void
  301. add_char_buff(buf, c)
  302.     struct buffheader    *buf;
  303.     int            c;
  304. {
  305. #ifdef FEAT_MBYTE
  306.     char_u    bytes[MB_MAXBYTES + 1];
  307.     int        len;
  308.     int        i;
  309. #endif
  310.     char_u    temp[4];
  311.  
  312. #ifdef FEAT_MBYTE
  313.     if (IS_SPECIAL(c))
  314.     len = 1;
  315.     else
  316.     len = (*mb_char2bytes)(c, bytes);
  317.     for (i = 0; i < len; ++i)
  318.     {
  319.     if (!IS_SPECIAL(c))
  320.         c = bytes[i];
  321. #endif
  322.  
  323.     if (IS_SPECIAL(c) || c == K_SPECIAL || c == NUL)
  324.     {
  325.         /* translate special key code into three byte sequence */
  326.         temp[0] = K_SPECIAL;
  327.         temp[1] = K_SECOND(c);
  328.         temp[2] = K_THIRD(c);
  329.         temp[3] = NUL;
  330.     }
  331. #ifdef FEAT_GUI
  332.     else if (c == CSI)
  333.     {
  334.         /* Translate a CSI to a CSI - KS_EXTRA - KE_CSI sequence */
  335.         temp[0] = CSI;
  336.         temp[1] = KS_EXTRA;
  337.         temp[2] = (int)KE_CSI;
  338.         temp[3] = NUL;
  339.     }
  340. #endif
  341.     else
  342.     {
  343.         temp[0] = c;
  344.         temp[1] = NUL;
  345.     }
  346.     add_buff(buf, temp, -1L);
  347. #ifdef FEAT_MBYTE
  348.     }
  349. #endif
  350. }
  351.  
  352. /*
  353.  * Get one byte from the stuff buffer.
  354.  * If advance == TRUE go to the next char.
  355.  * No translation is done K_SPECIAL and CSI are escaped.
  356.  */
  357.     static int
  358. read_stuff(advance)
  359.     int        advance;
  360. {
  361.     char_u        c;
  362.     struct buffblock    *curr;
  363.  
  364.     if (stuffbuff.bh_first.b_next == NULL)  /* buffer is empty */
  365.     return NUL;
  366.  
  367.     curr = stuffbuff.bh_first.b_next;
  368.     c = curr->b_str[stuffbuff.bh_index];
  369.  
  370.     if (advance)
  371.     {
  372.     if (curr->b_str[++stuffbuff.bh_index] == NUL)
  373.     {
  374.         stuffbuff.bh_first.b_next = curr->b_next;
  375.         vim_free(curr);
  376.         stuffbuff.bh_index = 0;
  377.     }
  378.     }
  379.     return c;
  380. }
  381.  
  382. /*
  383.  * Prepare the stuff buffer for reading (if it contains something).
  384.  */
  385.     static void
  386. start_stuff()
  387. {
  388.     if (stuffbuff.bh_first.b_next != NULL)
  389.     {
  390.     stuffbuff.bh_curr = &(stuffbuff.bh_first);
  391.     stuffbuff.bh_space = 0;
  392.     }
  393. }
  394.  
  395. /*
  396.  * Return TRUE if the stuff buffer is empty.
  397.  */
  398.     int
  399. stuff_empty()
  400. {
  401.     return (stuffbuff.bh_first.b_next == NULL);
  402. }
  403.  
  404. /*
  405.  * Set a typeahead character that won't be flushed.
  406.  */
  407.     void
  408. typeahead_noflush(c)
  409.     int        c;
  410. {
  411.     typeahead_char = c;
  412. }
  413.  
  414. /*
  415.  * Remove the contents of the stuff buffer and the mapped characters in the
  416.  * typeahead buffer (used in case of an error).  If 'typeahead' is true,
  417.  * flush all typeahead characters (used when interrupted by a CTRL-C).
  418.  */
  419.     void
  420. flush_buffers(typeahead)
  421.     int typeahead;
  422. {
  423.     init_typebuf();
  424.  
  425.     start_stuff();
  426.     while (read_stuff(TRUE) != NUL)
  427.     ;
  428.  
  429.     if (typeahead)        /* remove all typeahead */
  430.     {
  431.     /*
  432.      * We have to get all characters, because we may delete the first part
  433.      * of an escape sequence.
  434.      * In an xterm we get one char at a time and we have to get them all.
  435.      */
  436.     while (inchar(typebuf.tb_buf, typebuf.tb_buflen - 1, 10L) != 0)
  437.         ;
  438.     typebuf.tb_off = MAXMAPLEN;
  439.     typebuf.tb_len = 0;
  440.     }
  441.     else            /* remove mapped characters only */
  442.     {
  443.     typebuf.tb_off += typebuf.tb_maplen;
  444.     typebuf.tb_len -= typebuf.tb_maplen;
  445.     }
  446.     typebuf.tb_maplen = 0;
  447.     typebuf.tb_silent = 0;
  448.     cmd_silent = FALSE;
  449.     typebuf.tb_no_abbr_cnt = 0;
  450. }
  451.  
  452. /*
  453.  * The previous contents of the redo buffer is kept in old_redobuffer.
  454.  * This is used for the CTRL-O <.> command in insert mode.
  455.  */
  456.     void
  457. ResetRedobuff()
  458. {
  459.     if (!block_redo)
  460.     {
  461.     free_buff(&old_redobuff);
  462.     old_redobuff = redobuff;
  463.     redobuff.bh_first.b_next = NULL;
  464.     }
  465. }
  466.  
  467. #if defined(FEAT_AUTOCMD) || defined(FEAT_EVAL) || defined(PROTO)
  468. /*
  469.  * Save redobuff and old_redobuff to save_redobuff and save_old_redobuff.
  470.  * Used before executing autocommands and user functions.
  471.  */
  472. static int save_level = 0;
  473.  
  474.     void
  475. saveRedobuff()
  476. {
  477.     if (save_level++ == 0)
  478.     {
  479.     save_redobuff = redobuff;
  480.     redobuff.bh_first.b_next = NULL;
  481.     save_old_redobuff = old_redobuff;
  482.     old_redobuff.bh_first.b_next = NULL;
  483.     }
  484. }
  485.  
  486. /*
  487.  * Restore redobuff and old_redobuff from save_redobuff and save_old_redobuff.
  488.  * Used after executing autocommands and user functions.
  489.  */
  490.     void
  491. restoreRedobuff()
  492. {
  493.     if (--save_level == 0)
  494.     {
  495.     free_buff(&redobuff);
  496.     redobuff = save_redobuff;
  497.     free_buff(&old_redobuff);
  498.     old_redobuff = save_old_redobuff;
  499.     }
  500. }
  501. #endif
  502.  
  503. /*
  504.  * Append "s" to the redo buffer.
  505.  * K_SPECIAL and CSI should already have been escaped.
  506.  */
  507.     void
  508. AppendToRedobuff(s)
  509.     char_u       *s;
  510. {
  511.     if (!block_redo)
  512.     add_buff(&redobuff, s, -1L);
  513. }
  514.  
  515. /*
  516.  * Append to Redo buffer literally, escaping special characters with CTRL-V.
  517.  * K_SPECIAL and CSI are escaped as well.
  518.  */
  519.     void
  520. AppendToRedobuffLit(s)
  521.     char_u    *s;
  522. {
  523.     int        c;
  524.     char_u    *start;
  525.  
  526.     if (block_redo)
  527.     return;
  528.  
  529.     while (*s != NUL)
  530.     {
  531.     /* Put a string of normal characters in the redo buffer (that's
  532.      * faster). */
  533.     start = s;
  534.     while (*s >= ' '
  535. #ifndef EBCDIC
  536.         && *s < DEL    /* EBCDIC: all chars above space are normal */
  537. #endif
  538.         )
  539.         ++s;
  540.  
  541.     /* Don't put '0' or '^' as last character, just in case a CTRL-D is
  542.      * typed next. */
  543.     if (*s == NUL && (s[-1] == '0' || s[-1] == '^'))
  544.         --s;
  545.     if (s > start)
  546.         add_buff(&redobuff, start, (long)(s - start));
  547.  
  548.     if (*s != NUL)
  549.     {
  550.         /* Handle a special or multibyte character. */
  551. #ifdef FEAT_MBYTE
  552.         if (has_mbyte)
  553.         c = mb_ptr2char_adv(&s);
  554.         else
  555. #endif
  556.         c = *s++;
  557.         if (c < ' ' || c == DEL || (*s == NUL && (c == '0' || c == '^')))
  558.         add_char_buff(&redobuff, Ctrl_V);
  559.  
  560.         /* CTRL-V '0' must be inserted as CTRL-V 048 (EBCDIC: xf0) */
  561.         if (*s == NUL && c == '0')
  562. #ifdef EBCDIC
  563.         add_buff(&redobuff, (char_u *)"xf0", 3L);
  564. #else
  565.         add_buff(&redobuff, (char_u *)"048", 3L);
  566. #endif
  567.         else
  568.         add_char_buff(&redobuff, c);
  569.     }
  570.     }
  571. }
  572.  
  573. /*
  574.  * Append a character to the redo buffer.
  575.  * Translates special keys, NUL, CSI, K_SPECIAL and multibyte characters.
  576.  */
  577.     void
  578. AppendCharToRedobuff(c)
  579.     int           c;
  580. {
  581.     if (!block_redo)
  582.     add_char_buff(&redobuff, c);
  583. }
  584.  
  585. /*
  586.  * Append a number to the redo buffer.
  587.  */
  588.     void
  589. AppendNumberToRedobuff(n)
  590.     long        n;
  591. {
  592.     if (!block_redo)
  593.     add_num_buff(&redobuff, n);
  594. }
  595.  
  596. /*
  597.  * Append string "s" to the stuff buffer.
  598.  * CSI and K_SPECIAL must already have been escaped.
  599.  */
  600.     void
  601. stuffReadbuff(s)
  602.     char_u    *s;
  603. {
  604.     add_buff(&stuffbuff, s, -1L);
  605. }
  606.  
  607.     void
  608. stuffReadbuffLen(s, len)
  609.     char_u    *s;
  610.     long    len;
  611. {
  612.     add_buff(&stuffbuff, s, len);
  613. }
  614.  
  615. #if defined(FEAT_EVAL) || defined(PROTO)
  616. /*
  617.  * Stuff "s" into the stuff buffer, leaving special key codes unmodified and
  618.  * escaping other K_SPECIAL and CSI bytes.
  619.  */
  620.     void
  621. stuffReadbuffSpec(s)
  622.     char_u    *s;
  623. {
  624.     while (*s != NUL)
  625.     {
  626.     if (*s == K_SPECIAL && s[1] != NUL && s[2] != NUL)
  627.     {
  628.         /* Insert special key literally. */
  629.         stuffReadbuffLen(s, 3L);
  630.         s += 3;
  631.     }
  632.     else
  633. #ifdef FEAT_MBYTE
  634.         stuffcharReadbuff(mb_ptr2char_adv(&s));
  635. #else
  636.         stuffcharReadbuff(*s++);
  637. #endif
  638.     }
  639. }
  640. #endif
  641.  
  642. /*
  643.  * Append a character to the stuff buffer.
  644.  * Translates special keys, NUL, CSI, K_SPECIAL and multibyte characters.
  645.  */
  646.     void
  647. stuffcharReadbuff(c)
  648.     int           c;
  649. {
  650.     add_char_buff(&stuffbuff, c);
  651. }
  652.  
  653. /*
  654.  * Append a number to the stuff buffer.
  655.  */
  656.     void
  657. stuffnumReadbuff(n)
  658.     long    n;
  659. {
  660.     add_num_buff(&stuffbuff, n);
  661. }
  662.  
  663. /*
  664.  * Read a character from the redo buffer.  Translates K_SPECIAL, CSI and
  665.  * multibyte characters.
  666.  * The redo buffer is left as it is.
  667.  * if init is TRUE, prepare for redo, return FAIL if nothing to redo, OK
  668.  * otherwise
  669.  * if old is TRUE, use old_redobuff instead of redobuff
  670.  */
  671.     static int
  672. read_redo(init, old_redo)
  673.     int        init;
  674.     int        old_redo;
  675. {
  676.     static struct buffblock    *bp;
  677.     static char_u        *p;
  678.     int                c;
  679. #ifdef FEAT_MBYTE
  680.     int                n;
  681.     char_u            buf[MB_MAXBYTES];
  682.     int                i;
  683. #endif
  684.  
  685.     if (init)
  686.     {
  687.     if (old_redo)
  688.         bp = old_redobuff.bh_first.b_next;
  689.     else
  690.         bp = redobuff.bh_first.b_next;
  691.     if (bp == NULL)
  692.         return FAIL;
  693.     p = bp->b_str;
  694.     return OK;
  695.     }
  696.     if ((c = *p) != NUL)
  697.     {
  698.     /* Reverse the conversion done by add_char_buff() */
  699. #ifdef FEAT_MBYTE
  700.     /* For a multi-byte character get all the bytes and return the
  701.      * converted character. */
  702.     if (has_mbyte && (c != K_SPECIAL || p[1] == KS_SPECIAL))
  703.         n = MB_BYTE2LEN_CHECK(c);
  704.     else
  705.         n = 1;
  706.     for (i = 0; ; ++i)
  707. #endif
  708.     {
  709.         if (c == K_SPECIAL) /* special key or escaped K_SPECIAL */
  710.         {
  711.         c = TO_SPECIAL(p[1], p[2]);
  712.         p += 2;
  713.         }
  714. #ifdef FEAT_GUI
  715.         if (c == CSI)    /* escaped CSI */
  716.         p += 2;
  717. #endif
  718.         if (*++p == NUL && bp->b_next != NULL)
  719.         {
  720.         bp = bp->b_next;
  721.         p = bp->b_str;
  722.         }
  723. #ifdef FEAT_MBYTE
  724.         buf[i] = c;
  725.         if (i == n - 1)    /* last byte of a character */
  726.         {
  727.         if (n != 1)
  728.             c = (*mb_ptr2char)(buf);
  729.         break;
  730.         }
  731.         c = *p;
  732.         if (c == NUL)    /* cannot happen? */
  733.         break;
  734. #endif
  735.     }
  736.     }
  737.  
  738.     return c;
  739. }
  740.  
  741. /*
  742.  * Copy the rest of the redo buffer into the stuff buffer (in a slow way).
  743.  * If old_redo is TRUE, use old_redobuff instead of redobuff.
  744.  * The escaped K_SPECIAL and CSI are copied without translation.
  745.  */
  746.     static void
  747. copy_redo(old_redo)
  748.     int        old_redo;
  749. {
  750.     int        c;
  751.  
  752.     while ((c = read_redo(FALSE, old_redo)) != NUL)
  753.     stuffcharReadbuff(c);
  754. }
  755.  
  756. /*
  757.  * Stuff the redo buffer into the stuffbuff.
  758.  * Insert the redo count into the command.
  759.  * If 'old_redo' is TRUE, the last but one command is repeated
  760.  * instead of the last command (inserting text). This is used for
  761.  * CTRL-O <.> in insert mode
  762.  *
  763.  * return FAIL for failure, OK otherwise
  764.  */
  765.     int
  766. start_redo(count, old_redo)
  767.     long    count;
  768.     int        old_redo;
  769. {
  770.     int        c;
  771.  
  772.     /* init the pointers; return if nothing to redo */
  773.     if (read_redo(TRUE, old_redo) == FAIL)
  774.     return FAIL;
  775.  
  776.     c = read_redo(FALSE, old_redo);
  777.  
  778.     /* copy the buffer name, if present */
  779.     if (c == '"')
  780.     {
  781.     add_buff(&stuffbuff, (char_u *)"\"", 1L);
  782.     c = read_redo(FALSE, old_redo);
  783.  
  784.     /* if a numbered buffer is used, increment the number */
  785.     if (c >= '1' && c < '9')
  786.         ++c;
  787.     add_char_buff(&stuffbuff, c);
  788.     c = read_redo(FALSE, old_redo);
  789.     }
  790.  
  791. #ifdef FEAT_VISUAL
  792.     if (c == 'v')   /* redo Visual */
  793.     {
  794.     VIsual = curwin->w_cursor;
  795.     VIsual_active = TRUE;
  796.     VIsual_select = FALSE;
  797.     VIsual_reselect = TRUE;
  798.     redo_VIsual_busy = TRUE;
  799.     c = read_redo(FALSE, old_redo);
  800.     }
  801. #endif
  802.  
  803.     /* try to enter the count (in place of a previous count) */
  804.     if (count)
  805.     {
  806.     while (isdigit(c))    /* skip "old" count */
  807.         c = read_redo(FALSE, old_redo);
  808.     add_num_buff(&stuffbuff, count);
  809.     }
  810.  
  811.     /* copy from the redo buffer into the stuff buffer */
  812.     add_char_buff(&stuffbuff, c);
  813.     copy_redo(old_redo);
  814.     return OK;
  815. }
  816.  
  817. /*
  818.  * Repeat the last insert (R, o, O, a, A, i or I command) by stuffing
  819.  * the redo buffer into the stuffbuff.
  820.  * return FAIL for failure, OK otherwise
  821.  */
  822.     int
  823. start_redo_ins()
  824. {
  825.     int        c;
  826.  
  827.     if (read_redo(TRUE, FALSE) == FAIL)
  828.     return FAIL;
  829.     start_stuff();
  830.  
  831.     /* skip the count and the command character */
  832.     while ((c = read_redo(FALSE, FALSE)) != NUL)
  833.     {
  834.     if (vim_strchr((char_u *)"AaIiRrOo", c) != NULL)
  835.     {
  836.         if (c == 'O' || c == 'o')
  837.         stuffReadbuff(NL_STR);
  838.         break;
  839.     }
  840.     }
  841.  
  842.     /* copy the typed text from the redo buffer into the stuff buffer */
  843.     copy_redo(FALSE);
  844.     block_redo = TRUE;
  845.     return OK;
  846. }
  847.  
  848.     void
  849. stop_redo_ins()
  850. {
  851.     block_redo = FALSE;
  852. }
  853.  
  854. /*
  855.  * Initialize typebuf.tb_buf to point to typebuf_init.
  856.  * Alloc() cannot be used here: In out-of-memory situations it would
  857.  * be impossible to type anything.
  858.  */
  859.     static void
  860. init_typebuf()
  861. {
  862.     if (typebuf.tb_buf == NULL)
  863.     {
  864.     typebuf.tb_buf = typebuf_init;
  865.     typebuf.tb_noremap = noremapbuf_init;
  866.     typebuf.tb_buflen = TYPELEN_INIT;
  867.     typebuf.tb_len = 0;
  868.     typebuf.tb_off = 0;
  869.     }
  870. }
  871.  
  872. /*
  873.  * insert a string in position 'offset' in the typeahead buffer (for "@r"
  874.  * and ":normal" command, vgetorpeek() and check_termcode())
  875.  *
  876.  * If noremap is REMAP_YES, new string can be mapped again.
  877.  * If noremap is REMAP_NONE, new string cannot be mapped again.
  878.  * If noremap is REMAP_SCRIPT, new string cannot be mapped again, except for
  879.  *            script-local mappings.
  880.  * If noremap is > 0, that many characters of the new string cannot be mapped.
  881.  *
  882.  * If nottyped is TRUE, the string does not return KeyTyped (don't use when
  883.  * offset is non-zero!).
  884.  *
  885.  * If silent is TRUE, cmd_silent is set when the characters are obtained.
  886.  *
  887.  * return FAIL for failure, OK otherwise
  888.  */
  889.     int
  890. ins_typebuf(str, noremap, offset, nottyped, silent)
  891.     char_u    *str;
  892.     int        noremap;
  893.     int        offset;
  894.     int        nottyped;
  895.     int        silent;
  896. {
  897.     char_u    *s1, *s2;
  898.     int        newlen;
  899.     int        addlen;
  900.     int        i;
  901.     int        newoff;
  902.     int        val;
  903.     int        nrm;
  904.  
  905.     init_typebuf();
  906.  
  907.     addlen = (int)STRLEN(str);
  908.     /*
  909.      * Easy case: there is room in front of typebuf.tb_buf[typebuf.tb_off]
  910.      */
  911.     if (offset == 0 && addlen <= typebuf.tb_off)
  912.     {
  913.     typebuf.tb_off -= addlen;
  914.     mch_memmove(typebuf.tb_buf + typebuf.tb_off, str, (size_t)addlen);
  915.     }
  916.     /*
  917.      * Need to allocate new buffer.
  918.      * In typebuf.tb_buf there must always be room for 3 * MAXMAPLEN + 4
  919.      * characters.  We add some extra room to avoid having to allocate too
  920.      * often.
  921.      */
  922.     else
  923.     {
  924.     newoff = MAXMAPLEN + 4;
  925.     newlen = typebuf.tb_len + addlen + newoff + 4 * (MAXMAPLEN + 4);
  926.     if (newlen < 0)            /* string is getting too long */
  927.     {
  928.         EMSG(_(e_toocompl));    /* also calls flush_buffers */
  929.         setcursor();
  930.         return FAIL;
  931.     }
  932.     s1 = alloc(newlen);
  933.     if (s1 == NULL)            /* out of memory */
  934.         return FAIL;
  935.     s2 = alloc(newlen);
  936.     if (s2 == NULL)            /* out of memory */
  937.     {
  938.         vim_free(s1);
  939.         return FAIL;
  940.     }
  941.     typebuf.tb_buflen = newlen;
  942.  
  943.     /* copy the old chars, before the insertion point */
  944.     mch_memmove(s1 + newoff, typebuf.tb_buf + typebuf.tb_off,
  945.                                   (size_t)offset);
  946.     /* copy the new chars */
  947.     mch_memmove(s1 + newoff + offset, str, (size_t)addlen);
  948.     /* copy the old chars, after the insertion point, including the    NUL at
  949.      * the end */
  950.     mch_memmove(s1 + newoff + offset + addlen,
  951.                      typebuf.tb_buf + typebuf.tb_off + offset,
  952.                        (size_t)(typebuf.tb_len - offset + 1));
  953.     if (typebuf.tb_buf != typebuf_init)
  954.         vim_free(typebuf.tb_buf);
  955.     typebuf.tb_buf = s1;
  956.  
  957.     mch_memmove(s2 + newoff, typebuf.tb_noremap + typebuf.tb_off,
  958.                                   (size_t)offset);
  959.     mch_memmove(s2 + newoff + offset + addlen,
  960.            typebuf.tb_noremap + typebuf.tb_off + offset,
  961.                        (size_t)(typebuf.tb_len - offset));
  962.     if (typebuf.tb_noremap != noremapbuf_init)
  963.         vim_free(typebuf.tb_noremap);
  964.     typebuf.tb_noremap = s2;
  965.  
  966.     typebuf.tb_off = newoff;
  967.     }
  968.     typebuf.tb_len += addlen;
  969.  
  970.     /* If noremap == REMAP_SCRIPT: do remap script-local mappings. */
  971.     if (noremap == REMAP_SCRIPT)
  972.     val = RM_SCRIPT;
  973.     else
  974.     val = RM_NONE;
  975.  
  976.     /*
  977.      * Adjust typebuf.tb_noremap[] for the new characters:
  978.      * If noremap == REMAP_NONE or REMAP_SCRIPT: new characters are
  979.      *            (sometimes) not remappable
  980.      * If noremap == REMAP_YES: all the new characters are mappable
  981.      * If noremap  > 0: "noremap" characters are not remappable, the rest
  982.      *            mappable
  983.      */
  984.     if (noremap < 0)
  985.     nrm = addlen;
  986.     else
  987.     nrm = noremap;
  988.     for (i = 0; i < addlen; ++i)
  989.     typebuf.tb_noremap[typebuf.tb_off + i + offset] =
  990.                           (--nrm >= 0) ? val : RM_YES;
  991.  
  992.     /* tb_maplen and tb_silent only remember the length of mapped and/or
  993.      * silent mappings at the start of the buffer, assuming that a mapped
  994.      * sequence doesn't result in typed characters. */
  995.     if (nottyped || typebuf.tb_maplen > offset)
  996.     typebuf.tb_maplen += addlen;
  997.     if (silent || typebuf.tb_silent > offset)
  998.     {
  999.     typebuf.tb_silent += addlen;
  1000.     cmd_silent = TRUE;
  1001.     }
  1002.     if (typebuf.tb_no_abbr_cnt && offset == 0)    /* and not used for abbrev.s */
  1003.     typebuf.tb_no_abbr_cnt += addlen;
  1004.  
  1005.     return OK;
  1006. }
  1007.  
  1008. /*
  1009.  * Return TRUE if there are no characters in the typeahead buffer that have
  1010.  * not been typed (result from a mapping or come from ":normal").
  1011.  */
  1012.     int
  1013. typebuf_typed()
  1014. {
  1015.     return typebuf.tb_maplen == 0;
  1016. }
  1017.  
  1018. /*
  1019.  * Return the number of characters that are mapped (or not typed).
  1020.  */
  1021.     int
  1022. typebuf_maplen()
  1023. {
  1024.     return typebuf.tb_maplen;
  1025. }
  1026.  
  1027. /*
  1028.  * remove "len" characters from typebuf.tb_buf[typebuf.tb_off + offset]
  1029.  */
  1030.     void
  1031. del_typebuf(len, offset)
  1032.     int    len;
  1033.     int    offset;
  1034. {
  1035.     int        i;
  1036.  
  1037.     if (len == 0)
  1038.     return;        /* nothing to do */
  1039.  
  1040.     typebuf.tb_len -= len;
  1041.  
  1042.     /*
  1043.      * Easy case: Just increase typebuf.tb_off.
  1044.      */
  1045.     if (offset == 0 && typebuf.tb_buflen - (typebuf.tb_off + len)
  1046.                              >= 3 * MAXMAPLEN + 3)
  1047.     typebuf.tb_off += len;
  1048.     /*
  1049.      * Have to move the characters in typebuf.tb_buf[] and typebuf.tb_noremap[]
  1050.      */
  1051.     else
  1052.     {
  1053.     i = typebuf.tb_off + offset;
  1054.     /*
  1055.      * Leave some extra room at the end to avoid reallocation.
  1056.      */
  1057.     if (typebuf.tb_off > MAXMAPLEN)
  1058.     {
  1059.         mch_memmove(typebuf.tb_buf + MAXMAPLEN,
  1060.                  typebuf.tb_buf + typebuf.tb_off, (size_t)offset);
  1061.         mch_memmove(typebuf.tb_noremap + MAXMAPLEN,
  1062.              typebuf.tb_noremap + typebuf.tb_off, (size_t)offset);
  1063.         typebuf.tb_off = MAXMAPLEN;
  1064.     }
  1065.     /* adjust typebuf.tb_buf (include the NUL at the end) */
  1066.     mch_memmove(typebuf.tb_buf + typebuf.tb_off + offset,
  1067.                              typebuf.tb_buf + i + len,
  1068.                        (size_t)(typebuf.tb_len - offset + 1));
  1069.     /* adjust typebuf.tb_noremap[] */
  1070.     mch_memmove(typebuf.tb_noremap + typebuf.tb_off + offset,
  1071.                          typebuf.tb_noremap + i + len,
  1072.                        (size_t)(typebuf.tb_len - offset));
  1073.     }
  1074.  
  1075.     if (typebuf.tb_maplen > offset)        /* adjust tb_maplen */
  1076.     {
  1077.     if (typebuf.tb_maplen < offset + len)
  1078.         typebuf.tb_maplen = offset;
  1079.     else
  1080.         typebuf.tb_maplen -= len;
  1081.     }
  1082.     if (typebuf.tb_silent > offset)        /* adjust tb_silent */
  1083.     {
  1084.     if (typebuf.tb_silent < offset + len)
  1085.         typebuf.tb_silent = offset;
  1086.     else
  1087.         typebuf.tb_silent -= len;
  1088.     }
  1089.     if (typebuf.tb_no_abbr_cnt > offset)    /* adjust tb_no_abbr_cnt */
  1090.     {
  1091.     if (typebuf.tb_no_abbr_cnt < offset + len)
  1092.         typebuf.tb_no_abbr_cnt = offset;
  1093.     else
  1094.         typebuf.tb_no_abbr_cnt -= len;
  1095.     }
  1096.  
  1097. #ifdef FEAT_CLIENTSERVER
  1098.     /* Reset the flag that text received from a client was inserted in the
  1099.      * typeahead buffer. */
  1100.     received_from_client = FALSE;
  1101. #endif
  1102. }
  1103.  
  1104. /*
  1105.  * Write typed characters to script file.
  1106.  * If recording is on put the character in the recordbuffer.
  1107.  */
  1108.     static void
  1109. gotchars(s, len)
  1110.     char_u    *s;
  1111.     int        len;
  1112. {
  1113.     int        c;
  1114.     char_u    buf[2];
  1115.  
  1116.     /* remember how many chars were last recorded */
  1117.     if (Recording)
  1118.     last_recorded_len += len;
  1119.  
  1120.     buf[1] = NUL;
  1121.     while (len--)
  1122.     {
  1123.     /* Handle one byte at a time; no translation to be done. */
  1124.     c = *s++;
  1125.     updatescript(c);
  1126.  
  1127.     if (Recording)
  1128.     {
  1129.         buf[0] = c;
  1130.         add_buff(&recordbuff, buf, 1L);
  1131.     }
  1132.     }
  1133.     may_sync_undo();
  1134.  
  1135. #ifdef FEAT_EVAL
  1136.     /* output "debug mode" message next time in debug mode */
  1137.     debug_did_msg = FALSE;
  1138. #endif
  1139.  
  1140.     /* Since characters have been typed, consider the following to be in
  1141.      * another mapping.  Search string will be kept in history. */
  1142.     ++maptick;
  1143. }
  1144.  
  1145. /*
  1146.  * Sync undo.  Called when typed characters are obtained from the typeahead
  1147.  * buffer, or when a menu is used.
  1148.  * Do not sync:
  1149.  * - In Insert mode, unless cursor key has been used.
  1150.  * - While reading a script file.
  1151.  * - When no_u_sync is non-zero.
  1152.  */
  1153.     static void
  1154. may_sync_undo()
  1155. {
  1156.     if ((!(State & (INSERT + CMDLINE)) || arrow_used)
  1157.         && scriptin[curscript] == NULL && no_u_sync == 0)
  1158.     u_sync();
  1159. }
  1160.  
  1161. /*
  1162.  * Make "typebuf" empty and allocate new buffers.
  1163.  * Returns FAIL when out of memory.
  1164.  */
  1165.     int
  1166. alloc_typebuf()
  1167. {
  1168.     typebuf.tb_buf = alloc(TYPELEN_INIT);
  1169.     typebuf.tb_noremap = alloc(TYPELEN_INIT);
  1170.     if (typebuf.tb_buf == NULL || typebuf.tb_noremap == NULL)
  1171.     {
  1172.     free_typebuf();
  1173.     return FAIL;
  1174.     }
  1175.     typebuf.tb_buflen = TYPELEN_INIT;
  1176.     typebuf.tb_off = 0;
  1177.     typebuf.tb_len = 0;
  1178.     typebuf.tb_maplen = 0;
  1179.     typebuf.tb_silent = 0;
  1180.     typebuf.tb_no_abbr_cnt = 0;
  1181.     return OK;
  1182. }
  1183.  
  1184. /*
  1185.  * Free the buffers of "typebuf".
  1186.  */
  1187.     void
  1188. free_typebuf()
  1189. {
  1190.     vim_free(typebuf.tb_buf);
  1191.     vim_free(typebuf.tb_noremap);
  1192. }
  1193.  
  1194. /*
  1195.  * When doing ":so! file", the current typeahead needs to be saved, and
  1196.  * restored when "file" has been read completely.
  1197.  */
  1198. static typebuf_T saved_typebuf[NSCRIPT];
  1199.  
  1200.     int
  1201. save_typebuf()
  1202. {
  1203.     init_typebuf();
  1204.     saved_typebuf[curscript] = typebuf;
  1205.     /* If out of memory: restore typebuf and close file. */
  1206.     if (alloc_typebuf() == FAIL)
  1207.     {
  1208.     closescript();
  1209.     return FAIL;
  1210.     }
  1211.     return OK;
  1212. }
  1213.  
  1214. #if defined(FEAT_EVAL) || defined(FEAT_EX_EXTRA) || defined(PROTO)
  1215.  
  1216. /*
  1217.  * Save all three kinds of typeahead, so that the user must type at a prompt.
  1218.  */
  1219.     void
  1220. save_typeahead(tp)
  1221.     tasave_T    *tp;
  1222. {
  1223.     tp->save_typebuf = typebuf;
  1224.     tp->typebuf_valid = (alloc_typebuf() == OK);
  1225.     if (!tp->typebuf_valid)
  1226.     typebuf = tp->save_typebuf;
  1227.  
  1228.     tp->save_stuffbuff = stuffbuff;
  1229.     stuffbuff.bh_first.b_next = NULL;
  1230. # ifdef USE_INPUT_BUF
  1231.     tp->save_inputbuf = get_input_buf();
  1232. # endif
  1233. }
  1234.  
  1235. /*
  1236.  * Restore the typeahead to what it was before calling save_typeahead().
  1237.  */
  1238.     void
  1239. restore_typeahead(tp)
  1240.     tasave_T    *tp;
  1241. {
  1242.     if (tp->typebuf_valid)
  1243.     {
  1244.     free_typebuf();
  1245.     typebuf = tp->save_typebuf;
  1246.     }
  1247.  
  1248.     free_buff(&stuffbuff);
  1249.     stuffbuff = tp->save_stuffbuff;
  1250. # ifdef USE_INPUT_BUF
  1251.     set_input_buf(tp->save_inputbuf);
  1252. # endif
  1253. }
  1254. #endif
  1255.  
  1256. /*
  1257.  * Open a new script file for the ":source!" command.
  1258.  */
  1259.     void
  1260. openscript(name, directly)
  1261.     char_u    *name;
  1262.     int        directly;    /* when TRUE execute directly */
  1263. {
  1264.     if (curscript + 1 == NSCRIPT)
  1265.     {
  1266.     EMSG(_(e_nesting));
  1267.     return;
  1268.     }
  1269.  
  1270.     if (scriptin[curscript] != NULL)    /* already reading script */
  1271.     ++curscript;
  1272.                 /* use NameBuff for expanded name */
  1273.     expand_env(name, NameBuff, MAXPATHL);
  1274.     if ((scriptin[curscript] = mch_fopen((char *)NameBuff, READBIN)) == NULL)
  1275.     {
  1276.     EMSG2(_(e_notopen), name);
  1277.     if (curscript)
  1278.         --curscript;
  1279.     return;
  1280.     }
  1281.     if (save_typebuf() == FAIL)
  1282.     return;
  1283.  
  1284.     /*
  1285.      * Execute the commands from the file right now when using ":source!"
  1286.      * after ":global" or ":argdo" or in a loop.  Also when another command
  1287.      * follows.  This means the display won't be updated.  Don't do this
  1288.      * always, "make test" would fail.
  1289.      */
  1290.     if (directly)
  1291.     {
  1292.     oparg_T    oa;
  1293.     int    oldcurscript;
  1294.     int    save_State = State;
  1295.     int    save_restart_edit = restart_edit;
  1296.     int    save_insertmode = p_im;
  1297.     int    save_finish_op = finish_op;
  1298.     int    save_msg_scroll = msg_scroll;
  1299.  
  1300.     State = NORMAL;
  1301.     msg_scroll = FALSE;    /* no msg scrolling in Normal mode */
  1302.     restart_edit = 0;    /* don't go to Insert mode */
  1303.     p_im = FALSE;        /* don't use 'insertmode' */
  1304.     clear_oparg(&oa);
  1305.     finish_op = FALSE;
  1306.  
  1307.     oldcurscript = curscript;
  1308.     do
  1309.     {
  1310.         update_topline_cursor();    /* update cursor position and topline */
  1311.         normal_cmd(&oa, FALSE);    /* execute one command */
  1312.         vpeekc();            /* check for end of file */
  1313.     }
  1314.     while (scriptin[oldcurscript] != NULL);
  1315.  
  1316.     State = save_State;
  1317.     msg_scroll = save_msg_scroll;
  1318.     restart_edit = save_restart_edit;
  1319.     p_im = save_insertmode;
  1320.     finish_op = save_finish_op;
  1321.     }
  1322. }
  1323.  
  1324. /*
  1325.  * Close the currently active input script.
  1326.  */
  1327.     static void
  1328. closescript()
  1329. {
  1330.     free_typebuf();
  1331.     typebuf = saved_typebuf[curscript];
  1332.  
  1333.     fclose(scriptin[curscript]);
  1334.     scriptin[curscript] = NULL;
  1335.     if (curscript > 0)
  1336.     --curscript;
  1337. }
  1338.  
  1339. #if defined(FEAT_INS_EXPAND) || defined(PROTO)
  1340. /*
  1341.  * Return TRUE when reading keys from a script file.
  1342.  */
  1343.     int
  1344. using_script()
  1345. {
  1346.     return scriptin[curscript] != NULL;
  1347. }
  1348. #endif
  1349.  
  1350. /*
  1351.  * updatescipt() is called when a character can be written into the script file
  1352.  * or when we have waited some time for a character (c == 0)
  1353.  *
  1354.  * All the changed memfiles are synced if c == 0 or when the number of typed
  1355.  * characters reaches 'updatecount' and 'updatecount' is non-zero.
  1356.  */
  1357.     void
  1358. updatescript(c)
  1359.     int c;
  1360. {
  1361.     static int        count = 0;
  1362.  
  1363.     if (c && scriptout)
  1364.     putc(c, scriptout);
  1365.     if (c == 0 || (p_uc > 0 && ++count >= p_uc))
  1366.     {
  1367.     ml_sync_all(c == 0, TRUE);
  1368.     count = 0;
  1369.     }
  1370. }
  1371.  
  1372. #define KL_PART_KEY -1        /* keylen value for incomplete key-code */
  1373. #define KL_PART_MAP -2        /* keylen value for incomplete mapping */
  1374.  
  1375. static int old_char = -1;    /* character put back by vungetc() */
  1376. static int old_mod_mask;    /* mod_mask for ungotten character */
  1377.  
  1378. /*
  1379.  * Get the next input character.
  1380.  * Can return a special key or a multi-byte character.
  1381.  * Can return NUL when called recursively, use safe_vgetc() if that's not
  1382.  * wanted.
  1383.  * This translates escaped K_SPECIAL and CSI bytes to a K_SPECIAL or CSI byte.
  1384.  * Collects the bytes of a multibyte character into the whole character.
  1385.  * Returns the modifers in the global "mod_mask".
  1386.  */
  1387.     int
  1388. vgetc()
  1389. {
  1390.     int        c, c2;
  1391. #ifdef FEAT_MBYTE
  1392.     int        n;
  1393.     char_u    buf[MB_MAXBYTES];
  1394.     int        i;
  1395. #endif
  1396.  
  1397.     /*
  1398.      * If a character was put back with vungetc, it was already processed.
  1399.      * Return it directly.
  1400.      */
  1401.     if (old_char != -1)
  1402.     {
  1403.     c = old_char;
  1404.     old_char = -1;
  1405.     mod_mask = old_mod_mask;
  1406.     return c;
  1407.     }
  1408.  
  1409.     mod_mask = 0x0;
  1410.     last_recorded_len = 0;
  1411.     for (;;)            /* this is done twice if there are modifiers */
  1412.     {
  1413.     if (mod_mask)        /* no mapping after modifier has been read */
  1414.     {
  1415.         ++no_mapping;
  1416.         ++allow_keys;
  1417.     }
  1418.     c = vgetorpeek(TRUE);
  1419.     if (mod_mask)
  1420.     {
  1421.         --no_mapping;
  1422.         --allow_keys;
  1423.     }
  1424.  
  1425.     /* Get two extra bytes for special keys */
  1426.     if (c == K_SPECIAL
  1427. #ifdef FEAT_GUI
  1428.         || c == CSI
  1429. #endif
  1430.        )
  1431.     {
  1432.         ++no_mapping;
  1433.         c2 = vgetorpeek(TRUE);    /* no mapping for these chars */
  1434.         c = vgetorpeek(TRUE);
  1435.         --no_mapping;
  1436.         if (c2 == KS_MODIFIER)
  1437.         {
  1438.         mod_mask = c;
  1439.         continue;
  1440.         }
  1441.         c = TO_SPECIAL(c2, c);
  1442.  
  1443. #if defined(FEAT_GUI_W32) && defined(FEAT_MENU) && defined(FEAT_TEAROFF)
  1444.         /* Handle K_TEAROFF here, the caller of vgetc() doesn't need to
  1445.          * know that a menu was torn off */
  1446.         if (c == K_TEAROFF)
  1447.         {
  1448.         char_u    name[200];
  1449.         int    i;
  1450.  
  1451.         /* get menu path, it ends with a <CR> */
  1452.         for (i = 0; (c = vgetorpeek(TRUE)) != '\r'; )
  1453.         {
  1454.             name[i] = c;
  1455.             if (i < 199)
  1456.             ++i;
  1457.         }
  1458.         name[i] = NUL;
  1459.         gui_make_tearoff(name);
  1460.         continue;
  1461.         }
  1462. #endif
  1463. #ifdef FEAT_GUI
  1464.         /* Translate K_CSI to CSI.  The special key is only used to avoid
  1465.          * it being recognized as the start of a special key. */
  1466.         if (c == K_CSI)
  1467.         c = CSI;
  1468. #endif
  1469.     }
  1470. #ifdef MSDOS
  1471.     /*
  1472.      * If K_NUL was typed, it is replaced by K_NUL, 3 in mch_inchar().
  1473.      * Delete the 3 here.
  1474.      */
  1475.     else if (c == K_NUL && vpeekc() == 3)
  1476.         (void)vgetorpeek(TRUE);
  1477. #endif
  1478.  
  1479.     if (c >= FIRST_KEYPAD && c <= LAST_KEYPAD)
  1480.     {
  1481.         /* a keypad key was not mapped, use it like its ASCII equivalent */
  1482.         switch (c)
  1483.         {
  1484.         case K_KPLUS:        c = '+'; break;
  1485.         case K_KMINUS:        c = '-'; break;
  1486.         case K_KDIVIDE:        c = '/'; break;
  1487.         case K_KMULTIPLY:    c = '*'; break;
  1488.         case K_KENTER:        c = CR; break;
  1489.         case K_KPOINT:        c = '.'; break;
  1490.         case K_K0:        c = '0'; break;
  1491.         case K_K1:        c = '1'; break;
  1492.         case K_K2:        c = '2'; break;
  1493.         case K_K3:        c = '3'; break;
  1494.         case K_K4:        c = '4'; break;
  1495.         case K_K5:        c = '5'; break;
  1496.         case K_K6:        c = '6'; break;
  1497.         case K_K7:        c = '7'; break;
  1498.         case K_K8:        c = '8'; break;
  1499.         case K_K9:        c = '9'; break;
  1500.         }
  1501.     }
  1502.  
  1503. #ifdef FEAT_MBYTE
  1504.     /* For a multi-byte character get all the bytes and return the
  1505.      * converted character.
  1506.      * Note: This will loop until enough bytes are received!
  1507.      */
  1508.     if (has_mbyte && (n = MB_BYTE2LEN_CHECK(c)) > 1)
  1509.     {
  1510.         ++no_mapping;
  1511.         buf[0] = c;
  1512.         for (i = 1; i < n; ++i)
  1513.         {
  1514.         buf[i] = vgetorpeek(TRUE);
  1515.         if (buf[i] == K_SPECIAL
  1516. #ifdef FEAT_GUI
  1517.             || buf[i] == CSI
  1518. #endif
  1519.             )
  1520.         {
  1521.             /* Must be a K_SPECIAL - KS_SPECIAL - KE_FILLER sequence,
  1522.              * which represents a K_SPECIAL (0x80),
  1523.              * or a CSI - KS_EXTRA - KE_CSI sequence, which represents
  1524.              * a CSI (0x9B),
  1525.              * of a K_SPECIAL - KS_EXTRA - KE_CSI, which is CSI too. */
  1526.             c = vgetorpeek(TRUE);
  1527.             if (vgetorpeek(TRUE) == (int)KE_CSI && c == KS_EXTRA)
  1528.             buf[i] = CSI;
  1529.         }
  1530.         }
  1531.         --no_mapping;
  1532.         c = (*mb_ptr2char)(buf);
  1533.     }
  1534. #endif
  1535.  
  1536.     return c;
  1537.     }
  1538. }
  1539.  
  1540. /*
  1541.  * Like vgetc(), but never return a NUL when called recursively, get a key
  1542.  * directly from the user (ignoring typeahead).
  1543.  */
  1544.     int
  1545. safe_vgetc()
  1546. {
  1547.     int    c;
  1548.  
  1549.     c = vgetc();
  1550.     if (c == NUL)
  1551.     c = get_keystroke();
  1552.     return c;
  1553. }
  1554.  
  1555. /*
  1556.  * Check if a character is available, such that vgetc() will not block.
  1557.  * If the next character is a special character or multi-byte, the returned
  1558.  * character is not valid!.
  1559.  */
  1560.     int
  1561. vpeekc()
  1562. {
  1563.     if (old_char != -1)
  1564.     return old_char;
  1565.     return vgetorpeek(FALSE);
  1566. }
  1567.  
  1568. #if defined(FEAT_TERMRESPONSE) || defined(PROTO)
  1569. /*
  1570.  * Like vpeekc(), but don't allow mapping.  Do allow checking for terminal
  1571.  * codes.
  1572.  */
  1573.     int
  1574. vpeekc_nomap()
  1575. {
  1576.     int        c;
  1577.  
  1578.     ++no_mapping;
  1579.     ++allow_keys;
  1580.     c = vpeekc();
  1581.     --no_mapping;
  1582.     --allow_keys;
  1583.     return c;
  1584. }
  1585. #endif
  1586.  
  1587. #if defined(FEAT_INS_EXPAND) || defined(PROTO)
  1588. /*
  1589.  * Check if any character is available, also half an escape sequence.
  1590.  * Trick: when no typeahead found, but there is something in the typeahead
  1591.  * buffer, it must be an ESC that is recognized as the start of a key code.
  1592.  */
  1593.     int
  1594. vpeekc_any()
  1595. {
  1596.     int        c;
  1597.  
  1598.     c = vpeekc();
  1599.     if (c == NUL && typebuf.tb_len > 0)
  1600.     c = ESC;
  1601.     return c;
  1602. }
  1603. #endif
  1604.  
  1605. /*
  1606.  * Call vpeekc() without causing anything to be mapped.
  1607.  * Return TRUE if a character is available, FALSE otherwise.
  1608.  */
  1609.     int
  1610. char_avail()
  1611. {
  1612.     int        retval;
  1613.  
  1614.     ++no_mapping;
  1615.     retval = vpeekc();
  1616.     --no_mapping;
  1617.     return (retval != NUL);
  1618. }
  1619.  
  1620.     void
  1621. vungetc(c)    /* unget one character (can only be done once!) */
  1622.     int        c;
  1623. {
  1624.     old_char = c;
  1625.     old_mod_mask = mod_mask;
  1626. }
  1627.  
  1628. /*
  1629.  * get a character:
  1630.  * 1. from the stuffbuffer
  1631.  *    This is used for abbreviated commands like "D" -> "d$".
  1632.  *    Also used to redo a command for ".".
  1633.  * 2. from the typeahead buffer
  1634.  *    Stores text obtained previously but not used yet.
  1635.  *    Also stores the result of mappings.
  1636.  *    Also used for the ":normal" command.
  1637.  * 3. from the user
  1638.  *    This may do a blocking wait if "advance" is TRUE.
  1639.  *
  1640.  * if "advance" is TRUE (vgetc()):
  1641.  *    really get the character.
  1642.  *    KeyTyped is set to TRUE in the case the user typed the key.
  1643.  *    KeyStuffed is TRUE if the character comes from the stuff buffer.
  1644.  * if "advance" is FALSE (vpeekc()):
  1645.  *    just look whether there is a character available.
  1646.  *
  1647.  * When "no_mapping" is zero, checks for mappings in the current mode.
  1648.  * Only returns one byte (of a multi-byte character).
  1649.  * K_SPECIAL and CSI may be escaped, need to get two more bytes then.
  1650.  */
  1651.     static int
  1652. vgetorpeek(advance)
  1653.     int        advance;
  1654. {
  1655.     int        c, c1;
  1656.     int        keylen;
  1657.     char_u    *s;
  1658.     mapblock_T    *mp;
  1659. #ifdef FEAT_LOCALMAP
  1660.     mapblock_T    *mp2;
  1661. #endif
  1662.     mapblock_T    *mp_match;
  1663.     int        mp_match_len = 0;
  1664.     int        timedout = FALSE;        /* waited for more than 1 second
  1665.                         for mapping to complete */
  1666.     int        mapdepth = 0;        /* check for recursive mapping */
  1667.     int        mode_deleted = FALSE;   /* set when mode has been deleted */
  1668.     int        local_State;
  1669.     int        mlen;
  1670.     int        max_mlen;
  1671. #ifdef FEAT_CMDL_INFO
  1672.     int        i;
  1673.     int        new_wcol, new_wrow;
  1674. #endif
  1675. #ifdef FEAT_GUI
  1676. # ifdef FEAT_MENU
  1677.     int        idx;
  1678. # endif
  1679.     int        shape_changed = FALSE;  /* adjusted cursor shape */
  1680. #endif
  1681.     int        n;
  1682. #ifdef FEAT_LANGMAP
  1683.     int        nolmaplen;
  1684. #endif
  1685.     int        old_wcol, old_wrow;
  1686.  
  1687.     /*
  1688.      * This function doesn't work very well when called recursively.  This may
  1689.      * happen though, because of:
  1690.      * 1. The call to add_to_showcmd().    char_avail() is then used to check if
  1691.      * there is a character available, which calls this function.  In that
  1692.      * case we must return NUL, to indicate no character is available.
  1693.      * 2. A GUI callback function writes to the screen, causing a
  1694.      * wait_return().
  1695.      * Using ":normal" can also do this, but it saves the typeahead buffer,
  1696.      * thus it should be OK.  But don't get a key from the user then.
  1697.      */
  1698.     if (vgetc_busy
  1699. #ifdef FEAT_EX_EXTRA
  1700.         && ex_normal_busy == 0
  1701. #endif
  1702.         )
  1703.     return NUL;
  1704.  
  1705.     local_State = get_real_state();
  1706.  
  1707.     vgetc_busy = TRUE;
  1708.  
  1709.     if (advance)
  1710.     KeyStuffed = FALSE;
  1711.  
  1712.     init_typebuf();
  1713.     start_stuff();
  1714.     if (advance && typebuf.tb_maplen == 0)
  1715.     Exec_reg = FALSE;
  1716.     do
  1717.     {
  1718. /*
  1719.  * get a character: 1. from the stuffbuffer
  1720.  */
  1721.     if (typeahead_char != 0)
  1722.     {
  1723.         c = typeahead_char;
  1724.         if (advance)
  1725.         typeahead_char = 0;
  1726.     }
  1727.     else
  1728.         c = read_stuff(advance);
  1729.     if (c != NUL && !got_int)
  1730.     {
  1731.         if (advance)
  1732.         {
  1733.         /* KeyTyped = FALSE;  When the command that stuffed something
  1734.          * was typed, behave like the stuffed command was typed.
  1735.          * needed for CTRL-W CTRl-] to open a fold, for example. */
  1736.         KeyStuffed = TRUE;
  1737.         }
  1738.         if (typebuf.tb_no_abbr_cnt == 0)
  1739.         typebuf.tb_no_abbr_cnt = 1;    /* no abbreviations now */
  1740.     }
  1741.     else
  1742.     {
  1743.         /*
  1744.          * Loop until we either find a matching mapped key, or we
  1745.          * are sure that it is not a mapped key.
  1746.          * If a mapped key sequence is found we go back to the start to
  1747.          * try re-mapping.
  1748.          */
  1749.         for (;;)
  1750.         {
  1751.         /*
  1752.          * ui_breakcheck() is slow, don't use it too often when
  1753.          * inside a mapping.  But call it each time for typed
  1754.          * characters.
  1755.          */
  1756.         if (typebuf.tb_maplen)
  1757.             line_breakcheck();
  1758.         else
  1759.             ui_breakcheck();        /* check for CTRL-C */
  1760.         keylen = 0;
  1761.         if (got_int)
  1762.         {
  1763.             /* flush all input */
  1764.             c = inchar(typebuf.tb_buf, typebuf.tb_buflen - 1, 0L);
  1765.             /*
  1766.              * If inchar returns TRUE (script file was active) or we
  1767.              * are inside a mapping, get out of insert mode.
  1768.              * Otherwise we behave like having gotten a CTRL-C.
  1769.              * As a result typing CTRL-C in insert mode will
  1770.              * really insert a CTRL-C.
  1771.              */
  1772.             if ((c || typebuf.tb_maplen)
  1773.                           && (State & (INSERT + CMDLINE)))
  1774.             c = ESC;
  1775.             else
  1776.             c = Ctrl_C;
  1777.             flush_buffers(TRUE);    /* flush all typeahead */
  1778.  
  1779.             /* Also record this character, it might be needed to
  1780.              * get out of Insert mode. */
  1781.             *typebuf.tb_buf = c;
  1782.             gotchars(typebuf.tb_buf, 1);
  1783.             cmd_silent = FALSE;
  1784.  
  1785.             break;
  1786.         }
  1787.         else if (typebuf.tb_len > 0)
  1788.         {
  1789.             /*
  1790.              * Check for a mappable key sequence.
  1791.              * Walk through one maphash[] list until we find an
  1792.              * entry that matches.
  1793.              *
  1794.              * Don't look for mappings if:
  1795.              * - no_mapping set: mapping disabled (e.g. for CTRL-V)
  1796.              * - maphash_valid not set: no mappings present.
  1797.              * - typebuf.tb_buf[typebuf.tb_off] should not be remapped
  1798.              * - in insert or cmdline mode and 'paste' option set
  1799.              * - waiting for "hit return to continue" and CR or SPACE
  1800.              *     typed
  1801.              * - waiting for a char with --more--
  1802.              * - in Ctrl-X mode, and we get a valid char for that mode
  1803.              */
  1804.             mp = NULL;
  1805.             max_mlen = 0;
  1806.             c1 = typebuf.tb_buf[typebuf.tb_off];
  1807.             if (no_mapping == 0 && maphash_valid
  1808.                 && (typebuf.tb_maplen == 0
  1809.                 || (p_remap
  1810.                     && typebuf.tb_noremap[typebuf.tb_off]
  1811.                                   != RM_NONE))
  1812.                 && !(p_paste && (State & (INSERT + CMDLINE)))
  1813.                 && !(State == HITRETURN && (c1 == CR || c1 == ' '))
  1814.                 && State != ASKMORE
  1815.                 && State != CONFIRM
  1816. #ifdef FEAT_INS_EXPAND
  1817.                 && !((ctrl_x_mode != 0 && vim_is_ctrl_x_key(c1))
  1818.                     || ((continue_status & CONT_LOCAL)
  1819.                     && (c1 == Ctrl_N || c1 == Ctrl_P)))
  1820. #endif
  1821.                 )
  1822.             {
  1823. #ifdef FEAT_LANGMAP
  1824.             if (c1 == K_SPECIAL)
  1825.                 nolmaplen = 2;
  1826.             else
  1827.             {
  1828.                 LANGMAP_ADJUST(c1, TRUE);
  1829.                 nolmaplen = 0;
  1830.             }
  1831. #endif
  1832. #ifdef FEAT_LOCALMAP
  1833.             /* First try buffer-local mappings. */
  1834.             mp = curbuf->b_maphash[MAP_HASH(local_State, c1)];
  1835.             mp2 = maphash[MAP_HASH(local_State, c1)];
  1836.             if (mp == NULL)
  1837.             {
  1838.                 mp = mp2;
  1839.                 mp2 = NULL;
  1840.             }
  1841. #else
  1842.             mp = maphash[MAP_HASH(local_State, c1)];
  1843. #endif
  1844.             /*
  1845.              * Loop until a partly matching mapping is found or
  1846.              * all (local) mappings have been checked.
  1847.              * The longest full match is remembered in "mp_match".
  1848.              * A full match is only accepted if there is no partly
  1849.              * match, so "aa" and "aaa" can both be mapped.
  1850.              */
  1851.             mp_match = NULL;
  1852.             mp_match_len = 0;
  1853.             for ( ; mp != NULL;
  1854. #ifdef FEAT_LOCALMAP
  1855.                 mp->m_next == NULL ? (mp = mp2, mp2 = NULL) :
  1856. #endif
  1857.                 (mp = mp->m_next))
  1858.             {
  1859.                 /*
  1860.                  * Only consider an entry if the first character
  1861.                  * matches and it is for the current state.
  1862.                  * Skip ":lmap" mappings if keys were mapped.
  1863.                  */
  1864.                 if (mp->m_keys[0] == c1
  1865.                     && (mp->m_mode & local_State)
  1866.                     && ((mp->m_mode & LANGMAP) == 0
  1867.                     || typebuf.tb_maplen == 0))
  1868.                 {
  1869. #ifdef FEAT_LANGMAP
  1870.                 int    nomap = nolmaplen;
  1871.                 int    c2;
  1872. #endif
  1873.                 /* find the match length of this mapping */
  1874.                 for (mlen = 1; mlen < typebuf.tb_len; ++mlen)
  1875.                 {
  1876. #ifdef FEAT_LANGMAP
  1877.                     c2 = typebuf.tb_buf[typebuf.tb_off + mlen];
  1878.                     if (nomap > 0)
  1879.                     --nomap;
  1880.                     else if (c2 == K_SPECIAL)
  1881.                     nomap = 2;
  1882.                     else
  1883.                     LANGMAP_ADJUST(c2, TRUE);
  1884.                     if (mp->m_keys[mlen] != c2)
  1885. #else
  1886.                     if (mp->m_keys[mlen] !=
  1887.                     typebuf.tb_buf[typebuf.tb_off + mlen])
  1888. #endif
  1889.                     break;
  1890.                 }
  1891.  
  1892. #ifdef FEAT_MBYTE
  1893.                 /* Don't allow mapping the first byte(s) of a
  1894.                  * multi-byte char.  Happens when mapping
  1895.                  * <M-a> and then changing 'encoding'. */
  1896.                 if (has_mbyte && MB_BYTE2LEN(c1)
  1897.                         > (*mb_ptr2len_check)(mp->m_keys))
  1898.                     mlen = 0;
  1899. #endif
  1900.                 /*
  1901.                  * Check an entry whether it matches.
  1902.                  * - Full match: mlen == keylen
  1903.                  * - Partly match: mlen == typebuf.tb_len
  1904.                  */
  1905.                 keylen = mp->m_keylen;
  1906.                 if (mlen == keylen
  1907.                      || (mlen == typebuf.tb_len
  1908.                           && typebuf.tb_len < keylen))
  1909.                 {
  1910.                     /*
  1911.                      * If only script-local mappings are
  1912.                      * allowed, check if the mapping starts
  1913.                      * with K_SNR.
  1914.                      */
  1915.                     s = typebuf.tb_noremap + typebuf.tb_off;
  1916.                     if (*s == RM_SCRIPT
  1917.                         && (mp->m_keys[0] != K_SPECIAL
  1918.                         || mp->m_keys[1] != KS_EXTRA
  1919.                         || mp->m_keys[2]
  1920.                                   != (int)KE_SNR))
  1921.                     continue;
  1922.                     /*
  1923.                      * If one of the typed keys cannot be
  1924.                      * remapped, skip the entry.
  1925.                      */
  1926.                     for (n = mlen; --n >= 0; )
  1927.                     if (*s++ == RM_NONE)
  1928.                         break;
  1929.                     if (n >= 0)
  1930.                     continue;
  1931.  
  1932.                     if (keylen > typebuf.tb_len)
  1933.                     {
  1934.                     if (!timedout)
  1935.                     {
  1936.                         /* break at a partly match */
  1937.                         keylen = KL_PART_MAP;
  1938.                         break;
  1939.                     }
  1940.                     }
  1941.                     else if (keylen > mp_match_len)
  1942.                     {
  1943.                     /* found a longer match */
  1944.                     mp_match = mp;
  1945.                     mp_match_len = keylen;
  1946.                     }
  1947.                 }
  1948.                 else
  1949.                     /* No match; may have to check for
  1950.                      * termcode at next character. */
  1951.                     if (max_mlen < mlen)
  1952.                     max_mlen = mlen;
  1953.                 }
  1954.             }
  1955.  
  1956.             /* If no partly match found, use the longest full
  1957.              * match. */
  1958.             if (keylen != KL_PART_MAP)
  1959.             {
  1960.                 mp = mp_match;
  1961.                 keylen = mp_match_len;
  1962.             }
  1963.             }
  1964.  
  1965.             /* Check for match with 'pastetoggle' */
  1966.             if (*p_pt != NUL && mp == NULL && (State & (INSERT|NORMAL)))
  1967.             {
  1968.             for (mlen = 0; mlen < typebuf.tb_len && p_pt[mlen];
  1969.                                        ++mlen)
  1970.                 if (p_pt[mlen] != typebuf.tb_buf[typebuf.tb_off
  1971.                                       + mlen])
  1972.                     break;
  1973.             if (p_pt[mlen] == NUL)    /* match */
  1974.             {
  1975.                 /* write chars to script file(s) */
  1976.                 if (mlen > typebuf.tb_maplen)
  1977.                 gotchars(typebuf.tb_buf + typebuf.tb_off
  1978.                               + typebuf.tb_maplen,
  1979.                             mlen - typebuf.tb_maplen);
  1980.  
  1981.                 del_typebuf(mlen, 0); /* remove the chars */
  1982.                 set_option_value((char_u *)"paste",
  1983.                              (long)!p_paste, NULL, 0);
  1984.                 if (!(State & INSERT))
  1985.                 {
  1986.                 msg_col = 0;
  1987.                 msg_row = Rows - 1;
  1988.                 msg_clr_eos();        /* clear ruler */
  1989.                 }
  1990.                 showmode();
  1991.                 setcursor();
  1992.                 continue;
  1993.             }
  1994.             /* Need more chars for partly match. */
  1995.             if (mlen == typebuf.tb_len)
  1996.                 keylen = KL_PART_MAP;
  1997.             else if (max_mlen < mlen)
  1998.                 /* no match, may have to check for termcode at
  1999.                  * next character */
  2000.                 max_mlen = mlen + 1;
  2001.             }
  2002.  
  2003.             if ((mp == NULL || max_mlen >= mp_match_len)
  2004.                              && keylen != KL_PART_MAP)
  2005.             {
  2006.             /*
  2007.              * When no matching mapping found or found a
  2008.              * non-matching mapping that matches at least what the
  2009.              * matching mapping matched:
  2010.              * Check if we have a terminal code, when:
  2011.              *  mapping is allowed,
  2012.              *  keys have not been mapped,
  2013.              *  and not an ESC sequence, not in insert mode or
  2014.              *    p_ek is on,
  2015.              *  and when not timed out,
  2016.              */
  2017.             if ((no_mapping == 0 || allow_keys != 0)
  2018.                 && (typebuf.tb_maplen == 0
  2019.                     || (p_remap && typebuf.tb_noremap[
  2020.                            typebuf.tb_off] == RM_YES))
  2021.                 && !timedout)
  2022.             {
  2023.                 keylen = check_termcode(max_mlen + 1, NULL, 0);
  2024.  
  2025.                 /*
  2026.                  * When getting a partial match, but the last
  2027.                  * characters were not typed, don't wait for a
  2028.                  * typed character to complete the termcode.
  2029.                  * This helps a lot when a ":normal" command ends
  2030.                  * in an ESC.
  2031.                  */
  2032.                 if (keylen < 0
  2033.                        && typebuf.tb_len == typebuf.tb_maplen)
  2034.                 keylen = 0;
  2035.             }
  2036.             else
  2037.                 keylen = 0;
  2038.             if (keylen == 0)    /* no matching terminal code */
  2039.             {
  2040. #ifdef AMIGA            /* check for window bounds report */
  2041.                 if (typebuf.tb_maplen == 0 && (typebuf.tb_buf[
  2042.                            typebuf.tb_off] & 0xff) == CSI)
  2043.                 {
  2044.                 for (s = typebuf.tb_buf + typebuf.tb_off + 1;
  2045.                     s < typebuf.tb_buf + typebuf.tb_off
  2046.                                   + typebuf.tb_len
  2047.                    && (isdigit(*s) || *s == ';' || *s == ' ');
  2048.                     ++s)
  2049.                     ;
  2050.                 if (*s == 'r' || *s == '|') /* found one */
  2051.                 {
  2052.                     del_typebuf((int)(s + 1 -
  2053.                        (typebuf.tb_buf + typebuf.tb_off)), 0);
  2054.                     /* get size and redraw screen */
  2055.                     shell_resized();
  2056.                     continue;
  2057.                 }
  2058.                 if (*s == NUL)        /* need more characters */
  2059.                     keylen = KL_PART_KEY;
  2060.                 }
  2061.                 if (keylen >= 0)
  2062. #endif
  2063.                   /* When there was a matching mapping and no
  2064.                    * termcode could be replaced after another one,
  2065.                    * use that mapping. */
  2066.                   if (mp == NULL)
  2067.                   {
  2068. /*
  2069.  * get a character: 2. from the typeahead buffer
  2070.  */
  2071.                 c = typebuf.tb_buf[typebuf.tb_off] & 255;
  2072.                 if (advance)    /* remove chars from tb_buf */
  2073.                 {
  2074.                     cmd_silent = (typebuf.tb_silent > 0);
  2075.                     if (typebuf.tb_maplen > 0)
  2076.                     KeyTyped = FALSE;
  2077.                     else
  2078.                     {
  2079.                     KeyTyped = TRUE;
  2080.                     /* write char to script file(s) */
  2081.                     gotchars(typebuf.tb_buf
  2082.                              + typebuf.tb_off, 1);
  2083.                     }
  2084.                     del_typebuf(1, 0);
  2085.                 }
  2086.                 break;        /* got character, break for loop */
  2087.                   }
  2088.             }
  2089.             if (keylen > 0)        /* full matching terminal code */
  2090.             {
  2091. #if defined(FEAT_GUI) && defined(FEAT_MENU)
  2092.                 if (typebuf.tb_buf[typebuf.tb_off] == K_SPECIAL
  2093.                      && typebuf.tb_buf[typebuf.tb_off + 1]
  2094.                                    == KS_MENU)
  2095.                 {
  2096.                 /*
  2097.                  * Using a menu may cause a break in undo!
  2098.                  * It's like using gotchars(), but without
  2099.                  * recording or writing to a script file.
  2100.                  */
  2101.                 may_sync_undo();
  2102.                 del_typebuf(3, 0);
  2103.                 idx = get_menu_index(current_menu, local_State);
  2104.                 if (idx != MENU_INDEX_INVALID)
  2105.                 {
  2106. # ifdef FEAT_VISUAL
  2107.                     /*
  2108.                      * In Select mode, a Visual mode menu is
  2109.                      * used.  Switch to Visual mode
  2110.                      * temporarily.  Append K_SELECT to switch
  2111.                      * back to Select mode.
  2112.                      */
  2113.                     if (VIsual_active && VIsual_select)
  2114.                     {
  2115.                     VIsual_select = FALSE;
  2116.                     (void)ins_typebuf(K_SELECT_STRING,
  2117.                           REMAP_NONE, 0, TRUE, FALSE);
  2118.                     }
  2119. # endif
  2120.                     ins_typebuf(current_menu->strings[idx],
  2121.                         current_menu->noremap[idx],
  2122.                         0, TRUE,
  2123.                            current_menu->silent[idx]);
  2124.                 }
  2125.                 }
  2126. #endif /* FEAT_GUI */
  2127.                 continue;    /* try mapping again */
  2128.             }
  2129.  
  2130.             /* Partial match: get some more characters.  When a
  2131.              * matching mapping was found use that one. */
  2132.             if (mp == NULL || keylen < 0)
  2133.                 keylen = KL_PART_KEY;
  2134.             else
  2135.                 keylen = mp_match_len;
  2136.             }
  2137.  
  2138.             /* complete match */
  2139.             if (keylen >= 0 && keylen <= typebuf.tb_len)
  2140.             {
  2141.             /* write chars to script file(s) */
  2142.             if (keylen > typebuf.tb_maplen)
  2143.                 gotchars(typebuf.tb_buf + typebuf.tb_off
  2144.                               + typebuf.tb_maplen,
  2145.                           keylen - typebuf.tb_maplen);
  2146.  
  2147.             cmd_silent = (typebuf.tb_silent > 0);
  2148.             del_typebuf(keylen, 0);    /* remove the mapped keys */
  2149.  
  2150.             /*
  2151.              * Put the replacement string in front of mapstr.
  2152.              * The depth check catches ":map x y" and ":map y x".
  2153.              */
  2154.             if (++mapdepth >= p_mmd)
  2155.             {
  2156.                 EMSG(_("E223: recursive mapping"));
  2157.                 if (State & CMDLINE)
  2158.                 redrawcmdline();
  2159.                 else
  2160.                 setcursor();
  2161.                 flush_buffers(FALSE);
  2162.                 mapdepth = 0;    /* for next one */
  2163.                 c = -1;
  2164.                 break;
  2165.             }
  2166.  
  2167. #ifdef FEAT_VISUAL
  2168.             /*
  2169.              * In Select mode, a Visual mode mapping is used.
  2170.              * Switch to Visual mode temporarily.  Append K_SELECT
  2171.              * to switch back to Select mode.
  2172.              */
  2173.             if (VIsual_active && VIsual_select)
  2174.             {
  2175.                 VIsual_select = FALSE;
  2176.                 (void)ins_typebuf(K_SELECT_STRING, REMAP_NONE,
  2177.                                   0, TRUE, FALSE);
  2178.             }
  2179. #endif
  2180.  
  2181.             /*
  2182.              * Insert the 'to' part in the typebuf.tb_buf.
  2183.              * If 'from' field is the same as the start of the
  2184.              * 'to' field, don't remap the first character.
  2185.              * If m_noremap is set, don't remap the whole 'to'
  2186.              * part.
  2187.              */
  2188.             if (ins_typebuf(mp->m_str,
  2189.                 mp->m_noremap != REMAP_YES
  2190.                         ? mp->m_noremap
  2191.                         : STRNCMP(mp->m_str, mp->m_keys,
  2192.                                    (size_t)keylen)
  2193.                                   ? REMAP_YES : 1,
  2194.                 0, TRUE, cmd_silent || mp->m_silent) == FAIL)
  2195.             {
  2196.                 c = -1;
  2197.                 break;
  2198.             }
  2199.             continue;
  2200.             }
  2201.         }
  2202.  
  2203. /*
  2204.  * get a character: 3. from the user - handle <Esc> in Insert mode
  2205.  */
  2206.         /*
  2207.          * special case: if we get an <ESC> in insert mode and there
  2208.          * are no more characters at once, we pretend to go out of
  2209.          * insert mode.  This prevents the one second delay after
  2210.          * typing an <ESC>.  If we get something after all, we may
  2211.          * have to redisplay the mode. That the cursor is in the wrong
  2212.          * place does not matter.
  2213.          */
  2214.         c = 0;
  2215. #ifdef FEAT_CMDL_INFO
  2216.         new_wcol = curwin->w_wcol;
  2217.         new_wrow = curwin->w_wrow;
  2218. #endif
  2219.         if (       advance
  2220.             && typebuf.tb_len == 1
  2221.             && typebuf.tb_buf[typebuf.tb_off] == ESC
  2222.             && !no_mapping
  2223. #ifdef FEAT_EX_EXTRA
  2224.             && ex_normal_busy == 0
  2225. #endif
  2226.             && typebuf.tb_maplen == 0
  2227.             && (State & INSERT)
  2228.             && (p_timeout || (keylen == KL_PART_KEY && p_ttimeout))
  2229.             && (c = inchar(typebuf.tb_buf + typebuf.tb_off
  2230.                             + typebuf.tb_len, 3, 25L))
  2231.                                      == 0)
  2232.         {
  2233.             colnr_T    col = 0, vcol;
  2234.             char_u    *ptr;
  2235.  
  2236.             if (p_smd)
  2237.             {
  2238.             unshowmode(TRUE);
  2239.             mode_deleted = TRUE;
  2240.             }
  2241. #ifdef FEAT_GUI
  2242.             /* may show different cursor shape */
  2243.             if (gui.in_use)
  2244.             {
  2245.             int        save_State;
  2246.  
  2247.             save_State = State;
  2248.             State = NORMAL;
  2249.             gui_update_cursor(TRUE, FALSE);
  2250.             State = save_State;
  2251.             shape_changed = TRUE;
  2252.             }
  2253. #endif
  2254.             validate_cursor();
  2255.             old_wcol = curwin->w_wcol;
  2256.             old_wrow = curwin->w_wrow;
  2257.  
  2258.             /* move cursor left, if possible */
  2259.             if (curwin->w_cursor.col != 0)
  2260.             {
  2261.             if (curwin->w_wcol > 0)
  2262.             {
  2263.                 if (did_ai)
  2264.                 {
  2265.                 /*
  2266.                  * We are expecting to truncate the trailing
  2267.                  * white-space, so find the last non-white
  2268.                  * character -- webb
  2269.                  */
  2270.                 col = vcol = curwin->w_wcol = 0;
  2271.                 ptr = ml_get_curline();
  2272.                 while (col < curwin->w_cursor.col)
  2273.                 {
  2274.                     if (!vim_iswhite(ptr[col]))
  2275.                     curwin->w_wcol = vcol;
  2276.                     vcol += lbr_chartabsize(ptr + col,
  2277.                                    (colnr_T)vcol);
  2278. #ifdef FEAT_MBYTE
  2279.                     if (has_mbyte)
  2280.                     col += (*mb_ptr2len_check)(ptr + col);
  2281.                     else
  2282. #endif
  2283.                     ++col;
  2284.                 }
  2285.                 curwin->w_wrow = curwin->w_cline_row
  2286.                        + curwin->w_wcol / W_WIDTH(curwin);
  2287.                 curwin->w_wcol %= W_WIDTH(curwin);
  2288.                 curwin->w_wcol += curwin_col_off();
  2289. #ifdef FEAT_MBYTE
  2290.                 col = 0;    /* no correction needed */
  2291. #endif
  2292.                 }
  2293.                 else
  2294.                 {
  2295.                 --curwin->w_wcol;
  2296. #ifdef FEAT_MBYTE
  2297.                 col = curwin->w_cursor.col - 1;
  2298. #endif
  2299.                 }
  2300.             }
  2301.             else if (curwin->w_p_wrap && curwin->w_wrow)
  2302.             {
  2303.                 --curwin->w_wrow;
  2304.                 curwin->w_wcol = W_WIDTH(curwin) - 1;
  2305. #ifdef FEAT_MBYTE
  2306.                 col = curwin->w_cursor.col - 1;
  2307. #endif
  2308.             }
  2309. #ifdef FEAT_MBYTE
  2310.             if (has_mbyte && col > 0 && curwin->w_wcol > 0)
  2311.             {
  2312.                 /* Correct when the cursor is on the right halve
  2313.                  * of a double-wide character. */
  2314.                 ptr = ml_get_curline();
  2315.                 col -= (*mb_head_off)(ptr, ptr + col);
  2316.                 if ((*mb_ptr2cells)(ptr + col) > 1)
  2317.                 --curwin->w_wcol;
  2318.             }
  2319. #endif
  2320.             }
  2321.             setcursor();
  2322.             out_flush();
  2323. #ifdef FEAT_CMDL_INFO
  2324.             new_wcol = curwin->w_wcol;
  2325.             new_wrow = curwin->w_wrow;
  2326. #endif
  2327.             curwin->w_wcol = old_wcol;
  2328.             curwin->w_wrow = old_wrow;
  2329.         }
  2330.         if (c < 0)
  2331.             continue;    /* end of input script reached */
  2332.         typebuf.tb_len += c;
  2333.  
  2334.         /* buffer full, don't map */
  2335.         if (typebuf.tb_len >= typebuf.tb_maplen + MAXMAPLEN)
  2336.         {
  2337.             timedout = TRUE;
  2338.             continue;
  2339.         }
  2340.  
  2341. #ifdef FEAT_EX_EXTRA
  2342.         if (ex_normal_busy > 0)
  2343.         {
  2344. # ifdef FEAT_CMDWIN
  2345.             static int tc = 0;
  2346. # endif
  2347.  
  2348.             /* No typeahead left and inside ":normal".  Must return
  2349.              * something to avoid getting stuck.  When an incomplete
  2350.              * mapping is present, behave like it timed out. */
  2351.             if (typebuf.tb_len > 0)
  2352.             {
  2353.             timedout = TRUE;
  2354.             continue;
  2355.             }
  2356.             /* When 'insertmode' is set, ESC just beeps in Insert
  2357.              * mode.  Use CTRL-L to make edit() return.
  2358.              * For the command line only CTRL-C always breaks it.
  2359.              * For the cmdline window: Alternate between ESC and
  2360.              * CTRL-C: ESC for most situations and CTRL-C to close the
  2361.              * cmdline window. */
  2362.             if (p_im && (State & INSERT))
  2363.             c = Ctrl_L;
  2364.             else if ((State & CMDLINE)
  2365. # ifdef FEAT_CMDWIN
  2366.                 || (cmdwin_type > 0 && tc == ESC)
  2367. # endif
  2368.                 )
  2369.             c = Ctrl_C;
  2370.             else
  2371.             c = ESC;
  2372. # ifdef FEAT_CMDWIN
  2373.             tc = c;
  2374. # endif
  2375.             break;
  2376.         }
  2377. #endif
  2378.  
  2379. /*
  2380.  * get a character: 3. from the user - update display
  2381.  */
  2382.         /* In insert mode a screen update is skipped when characters
  2383.          * are still available.  But when those available characters
  2384.          * are part of a mapping, and we are going to do a blocking
  2385.          * wait here.  Need to update the screen to display the
  2386.          * changed text so far. */
  2387.         if ((State & INSERT) && advance && must_redraw != 0)
  2388.         {
  2389.             update_screen(0);
  2390.             setcursor(); /* put cursor back where it belongs */
  2391.         }
  2392.  
  2393.         /*
  2394.          * If we have a partial match (and are going to wait for more
  2395.          * input from the user), show the partially matched characters
  2396.          * to the user with showcmd.
  2397.          */
  2398. #ifdef FEAT_CMDL_INFO
  2399.         i = 0;
  2400. #endif
  2401.         c1 = 0;
  2402.         if (typebuf.tb_len > 0 && advance && !exmode_active)
  2403.         {
  2404.             if (((State & (NORMAL | INSERT)) || State == LANGMAP)
  2405.                 && State != HITRETURN)
  2406.             {
  2407.             /* this looks nice when typing a dead character map */
  2408.             if (State & INSERT
  2409.                 && ptr2cells(typebuf.tb_buf + typebuf.tb_off
  2410.                            + typebuf.tb_len - 1) == 1)
  2411.             {
  2412.                 edit_putchar(typebuf.tb_buf[typebuf.tb_off
  2413.                         + typebuf.tb_len - 1], FALSE);
  2414.                 setcursor(); /* put cursor back where it belongs */
  2415.                 c1 = 1;
  2416.             }
  2417. #ifdef FEAT_CMDL_INFO
  2418.             /* need to use the col and row from above here */
  2419.             old_wcol = curwin->w_wcol;
  2420.             old_wrow = curwin->w_wrow;
  2421.             curwin->w_wcol = new_wcol;
  2422.             curwin->w_wrow = new_wrow;
  2423.             push_showcmd();
  2424.             if (typebuf.tb_len > SHOWCMD_COLS)
  2425.                 i = typebuf.tb_len - SHOWCMD_COLS;
  2426.             while (i < typebuf.tb_len)
  2427.                 (void)add_to_showcmd(typebuf.tb_buf[typebuf.tb_off
  2428.                                       + i++]);
  2429.             curwin->w_wcol = old_wcol;
  2430.             curwin->w_wrow = old_wrow;
  2431. #endif
  2432.             }
  2433.  
  2434.             /* this looks nice when typing a dead character map */
  2435.             if ((State & CMDLINE)
  2436. #if defined(FEAT_CRYPT) || defined(FEAT_EVAL)
  2437.                 && cmdline_star == 0
  2438. #endif
  2439.                 && ptr2cells(typebuf.tb_buf + typebuf.tb_off
  2440.                            + typebuf.tb_len - 1) == 1)
  2441.             {
  2442.             putcmdline(typebuf.tb_buf[typebuf.tb_off
  2443.                         + typebuf.tb_len - 1], FALSE);
  2444.             c1 = 1;
  2445.             }
  2446.         }
  2447.  
  2448. /*
  2449.  * get a character: 3. from the user - get it
  2450.  */
  2451.         c = inchar(typebuf.tb_buf + typebuf.tb_off + typebuf.tb_len,
  2452.             typebuf.tb_buflen - typebuf.tb_off - typebuf.tb_len - 1,
  2453.             !advance
  2454.                 ? 0
  2455.                 : ((typebuf.tb_len == 0
  2456.                     || !(p_timeout || (p_ttimeout
  2457.                            && keylen == KL_PART_KEY)))
  2458.                     ? -1L
  2459.                     : ((keylen == KL_PART_KEY && p_ttm >= 0)
  2460.                         ? p_ttm
  2461.                         : p_tm)));
  2462.  
  2463. #ifdef FEAT_CMDL_INFO
  2464.         if (i != 0)
  2465.             pop_showcmd();
  2466. #endif
  2467.         if (c1 == 1)
  2468.         {
  2469.             if (State & INSERT)
  2470.             edit_unputchar();
  2471.             if (State & CMDLINE)
  2472.             unputcmdline();
  2473.             setcursor();    /* put cursor back where it belongs */
  2474.         }
  2475.  
  2476.         if (c < 0)
  2477.             continue;        /* end of input script reached */
  2478.         if (c == NUL)        /* no character available */
  2479.         {
  2480.             if (!advance)
  2481.             break;
  2482.             if (typebuf.tb_len > 0)    /* timed out */
  2483.             {
  2484.             timedout = TRUE;
  2485.             continue;
  2486.             }
  2487.         }
  2488.         else
  2489.         {        /* allow mapping for just typed characters */
  2490.             while (typebuf.tb_buf[typebuf.tb_off
  2491.                              + typebuf.tb_len] != NUL)
  2492.             typebuf.tb_noremap[typebuf.tb_off
  2493.                          + typebuf.tb_len++] = RM_YES;
  2494. #ifdef USE_IM_CONTROL
  2495.             /* Get IM status right after getting keys, not after the
  2496.              * timeout for a mapping (focus may be lost by then). */
  2497.             vgetc_im_active = im_get_status();
  2498. #endif
  2499.         }
  2500.         }        /* for (;;) */
  2501.     }    /* if (!character from stuffbuf) */
  2502.  
  2503.             /* if advance is FALSE don't loop on NULs */
  2504.     } while (c < 0 || (advance && c == NUL));
  2505.  
  2506.     /*
  2507.      * The "INSERT" message is taken care of here:
  2508.      *     if we return an ESC to exit insert mode, the message is deleted
  2509.      *     if we don't return an ESC but deleted the message before, redisplay it
  2510.      */
  2511.     if (advance && p_smd && (State & INSERT))
  2512.     {
  2513.     if (c == ESC && !mode_deleted && !no_mapping)
  2514.     {
  2515.         if (typebuf.tb_len && !KeyTyped)
  2516.         redraw_cmdline = TRUE;        /* delete mode later */
  2517.         else
  2518.         unshowmode(FALSE);
  2519.     }
  2520.     else if (c != ESC && mode_deleted)
  2521.     {
  2522.         if (typebuf.tb_len && !KeyTyped)
  2523.         redraw_cmdline = TRUE;        /* show mode later */
  2524.         else
  2525.         showmode();
  2526.     }
  2527.     }
  2528. #ifdef FEAT_GUI
  2529.     /* may unshow different cursor shape */
  2530.     if (gui.in_use && shape_changed)
  2531.     gui_update_cursor(TRUE, FALSE);
  2532. #endif
  2533.  
  2534.     vgetc_busy = FALSE;
  2535.  
  2536.     return c;
  2537. }
  2538.  
  2539. /*
  2540.  * inchar() - get one character from
  2541.  *    1. a scriptfile
  2542.  *    2. the keyboard
  2543.  *
  2544.  *  As much characters as we can get (upto 'maxlen') are put in buf and
  2545.  *  NUL terminated (buffer length must be 'maxlen' + 1).
  2546.  *  Minimum for 'maxlen' is 3!!!!
  2547.  *
  2548.  *  If we got an interrupt all input is read until none is available.
  2549.  *
  2550.  *  If wait_time == 0  there is no waiting for the char.
  2551.  *  If wait_time == n  we wait for n msec for a character to arrive.
  2552.  *  If wait_time == -1 we wait forever for a character to arrive.
  2553.  *
  2554.  *  Return the number of obtained characters.
  2555.  *  Return -1 when end of input script reached.
  2556.  */
  2557.  
  2558.     int
  2559. inchar(buf, maxlen, wait_time)
  2560.     char_u    *buf;
  2561.     int        maxlen;
  2562.     long    wait_time;        /* milli seconds */
  2563. {
  2564.     int        len = 0;        /* init for GCC */
  2565.     int        retesc = FALSE;        /* return ESC with gotint */
  2566.     int        script_char;
  2567.  
  2568.     if (wait_time == -1L || wait_time > 100L)  /* flush output before waiting */
  2569.     {
  2570.     cursor_on();
  2571.     out_flush();
  2572. #ifdef FEAT_GUI
  2573.     if (gui.in_use)
  2574.     {
  2575.         gui_update_cursor(FALSE, FALSE);
  2576. # ifdef FEAT_MOUSESHAPE
  2577.         if (postponed_mouseshape)
  2578.         update_mouseshape(-1);
  2579. # endif
  2580.     }
  2581. #endif
  2582.     }
  2583.  
  2584.     /*
  2585.      * Don't reset these when at the hit-return prompt, otherwise a endless
  2586.      * recursive loop may result (write error in swapfile, hit-return, timeout
  2587.      * on char wait, flush swapfile, write error....).
  2588.      */
  2589.     if (State != HITRETURN)
  2590.     {
  2591.     did_outofmem_msg = FALSE;   /* display out of memory message (again) */
  2592.     did_swapwrite_msg = FALSE;  /* display swap file write error again */
  2593.     }
  2594.     undo_off = FALSE;            /* restart undo now */
  2595.  
  2596.     /*
  2597.      * first try script file
  2598.      *    If interrupted: Stop reading script files.
  2599.      */
  2600.     script_char = -1;
  2601.     while (scriptin[curscript] != NULL && script_char < 0)
  2602.     {
  2603.     if (got_int || (script_char = getc(scriptin[curscript])) < 0)
  2604.     {
  2605.         /* Reached EOF.
  2606.          * Careful: closescript() frees typebuf.tb_buf[] and buf[] may
  2607.          * point inside typebuf.tb_buf[].  Don't use buf[] after this! */
  2608.         closescript();
  2609.         /*
  2610.          * When reading script file is interrupted, return an ESC to get
  2611.          * back to normal mode.
  2612.          * Otherwise return -1, because typebuf.tb_buf[] has changed.
  2613.          */
  2614.         if (got_int)
  2615.         retesc = TRUE;
  2616.         else
  2617.         return -1;
  2618.     }
  2619.     else
  2620.     {
  2621.         buf[0] = script_char;
  2622.         len = 1;
  2623.     }
  2624.     }
  2625.  
  2626.     if (script_char < 0)    /* did not get a character from script */
  2627.     {
  2628.     /*
  2629.      * If we got an interrupt, skip all previously typed characters and
  2630.      * return TRUE if quit reading script file.
  2631.      * Stop reading typeahead when a single CTRL-C was read,
  2632.      * fill_input_buf() returns this when not able to read from stdin.
  2633.      * Don't use buf[] here, closescript() may have freed typebuf.tb_buf[]
  2634.      * and buf may be pointing inside typebuf.tb_buf[].
  2635.      */
  2636.     if (got_int)
  2637.     {
  2638. #define DUM_LEN MAXMAPLEN * 3 + 3
  2639.         char_u    dum[DUM_LEN + 1];
  2640.  
  2641.         for (;;)
  2642.         {
  2643.         len = ui_inchar(dum, DUM_LEN, 0L);
  2644.         if (len == 0 || (len == 1 && dum[0] == 3))
  2645.             break;
  2646.         }
  2647.         return retesc;
  2648.     }
  2649.  
  2650.     /*
  2651.      * Always flush the output characters when getting input characters
  2652.      * from the user.
  2653.      */
  2654.     out_flush();
  2655.  
  2656.     /*
  2657.      * Fill up to a third of the buffer, because each character may be
  2658.      * tripled below.
  2659.      */
  2660.     len = ui_inchar(buf, maxlen / 3, wait_time);
  2661.     }
  2662.  
  2663.     return fix_input_buffer(buf, len, script_char >= 0);
  2664. }
  2665.  
  2666. /*
  2667.  * Fix typed characters for use by vgetc() and check_termcode().
  2668.  * buf[] must have room to triple the number of bytes!
  2669.  * Returns the new length.
  2670.  */
  2671.     int
  2672. fix_input_buffer(buf, len, script)
  2673.     char_u    *buf;
  2674.     int        len;
  2675.     int        script;        /* TRUE when reading from a script */
  2676. {
  2677.     int        i;
  2678.     char_u    *p = buf;
  2679.  
  2680.     /*
  2681.      * Two characters are special: NUL and K_SPECIAL.
  2682.      * When compiled With the GUI CSI is also special.
  2683.      * Replace         NUL by K_SPECIAL KS_ZERO     KE_FILLER
  2684.      * Replace K_SPECIAL by K_SPECIAL KS_SPECIAL KE_FILLER
  2685.      * Replace       CSI by K_SPECIAL KS_EXTRA   KE_CSI
  2686.      * Don't replace K_SPECIAL when reading a script file.
  2687.      */
  2688.     for (i = len; --i >= 0; ++p)
  2689.     {
  2690. #ifdef FEAT_GUI
  2691.     /* When the GUI is used any character can come after a CSI, don't
  2692.      * escape it. */
  2693.     if (gui.in_use && p[0] == CSI && i >= 2)
  2694.     {
  2695.         p += 2;
  2696.         i -= 2;
  2697.     }
  2698.     /* When the GUI is not used CSI needs to be escaped. */
  2699.     else if (!gui.in_use && p[0] == CSI)
  2700.     {
  2701.         mch_memmove(p + 3, p + 1, (size_t)i);
  2702.         *p++ = K_SPECIAL;
  2703.         *p++ = KS_EXTRA;
  2704.         *p = (int)KE_CSI;
  2705.         len += 2;
  2706.     }
  2707.     else
  2708. #endif
  2709.     if (p[0] == NUL || (p[0] == K_SPECIAL && !script))
  2710.     {
  2711.         mch_memmove(p + 3, p + 1, (size_t)i);
  2712.         p[2] = K_THIRD(p[0]);
  2713.         p[1] = K_SECOND(p[0]);
  2714.         p[0] = K_SPECIAL;
  2715.         p += 2;
  2716.         len += 2;
  2717.     }
  2718.     }
  2719.     *p = NUL;        /* add trailing NUL */
  2720.     return len;
  2721. }
  2722.  
  2723. #if defined(USE_INPUT_BUF) || defined(PROTO)
  2724. /*
  2725.  * Return TRUE when bytes are in the input buffer or in the typeahead buffer.
  2726.  * Normally the input buffer would be sufficient, but the server_to_input_buf()
  2727.  * may insert characters in the typeahead buffer while we are waiting for
  2728.  * input to arrive.
  2729.  */
  2730.     int
  2731. input_available()
  2732. {
  2733.     return (!vim_is_input_buf_empty()
  2734. # ifdef FEAT_CLIENTSERVER
  2735.         || received_from_client
  2736. # endif
  2737.         );
  2738. }
  2739. #endif
  2740.  
  2741. /*
  2742.  * map[!]            : show all key mappings
  2743.  * map[!] {lhs}            : show key mapping for {lhs}
  2744.  * map[!] {lhs} {rhs}        : set key mapping for {lhs} to {rhs}
  2745.  * noremap[!] {lhs} {rhs}   : same, but no remapping for {rhs}
  2746.  * unmap[!] {lhs}        : remove key mapping for {lhs}
  2747.  * abbr                : show all abbreviations
  2748.  * abbr {lhs}            : show abbreviations for {lhs}
  2749.  * abbr {lhs} {rhs}        : set abbreviation for {lhs} to {rhs}
  2750.  * noreabbr {lhs} {rhs}        : same, but no remapping for {rhs}
  2751.  * unabbr {lhs}            : remove abbreviation for {lhs}
  2752.  *
  2753.  * maptype: 0 for :map, 1 for :unmap, 2 for noremap.
  2754.  *
  2755.  * arg is pointer to any arguments. Note: arg cannot be a read-only string,
  2756.  * it will be modified.
  2757.  *
  2758.  * for :map   mode is NORMAL + VISUAL + OP_PENDING
  2759.  * for :map!  mode is INSERT + CMDLINE
  2760.  * for :cmap  mode is CMDLINE
  2761.  * for :imap  mode is INSERT
  2762.  * for :lmap  mode is LANGMAP
  2763.  * for :nmap  mode is NORMAL
  2764.  * for :vmap  mode is VISUAL
  2765.  * for :omap  mode is OP_PENDING
  2766.  *
  2767.  * for :abbr  mode is INSERT + CMDLINE
  2768.  * for :iabbr mode is INSERT
  2769.  * for :cabbr mode is CMDLINE
  2770.  *
  2771.  * Return 0 for success
  2772.  *      1 for invalid arguments
  2773.  *      2 for no match
  2774.  *      4 for out of mem
  2775.  *      5 for entry not unique
  2776.  */
  2777.     int
  2778. do_map(maptype, arg, mode, abbrev)
  2779.     int        maptype;
  2780.     char_u    *arg;
  2781.     int        mode;
  2782.     int        abbrev;        /* not a mapping but an abbreviation */
  2783. {
  2784.     char_u    *keys;
  2785.     mapblock_T    *mp, **mpp;
  2786.     char_u    *rhs;
  2787.     char_u    *p;
  2788.     int        n;
  2789.     int        len = 0;    /* init for GCC */
  2790.     char_u    *newstr;
  2791.     int        hasarg;
  2792.     int        haskey;
  2793.     int        did_it = FALSE;
  2794. #ifdef FEAT_LOCALMAP
  2795.     int        did_local = FALSE;
  2796. #endif
  2797.     int        round;
  2798.     char_u    *keys_buf = NULL;
  2799.     char_u    *arg_buf = NULL;
  2800.     int        retval = 0;
  2801.     int        do_backslash;
  2802.     int        hash;
  2803.     int        new_hash;
  2804.     mapblock_T    **abbr_table;
  2805.     mapblock_T    **map_table;
  2806.     int        unique = FALSE;
  2807.     int        silent = FALSE;
  2808.     int        noremap;
  2809.  
  2810.     keys = arg;
  2811.     map_table = maphash;
  2812.     abbr_table = &first_abbr;
  2813.  
  2814.     /* For ":noremap" don't remap, otherwise do remap. */
  2815.     if (maptype == 2)
  2816.     noremap = REMAP_NONE;
  2817.     else
  2818.     noremap = REMAP_YES;
  2819.  
  2820.     /* Accept <buffer>, <silent>, <script> and <unique> in any order. */
  2821.     for (;;)
  2822.     {
  2823. #ifdef FEAT_LOCALMAP
  2824.     /*
  2825.      * Check for "<buffer>": mapping local to buffer.
  2826.      */
  2827.     if (STRNCMP(keys, "<buffer>", 8) == 0)
  2828.     {
  2829.         keys = skipwhite(keys + 8);
  2830.         map_table = curbuf->b_maphash;
  2831.         abbr_table = &curbuf->b_first_abbr;
  2832.         continue;
  2833.     }
  2834. #endif
  2835.  
  2836.     /*
  2837.      * Check for "<silent>": don't echo commands.
  2838.      */
  2839.     if (STRNCMP(keys, "<silent>", 8) == 0)
  2840.     {
  2841.         keys = skipwhite(keys + 8);
  2842.         silent = TRUE;
  2843.         continue;
  2844.     }
  2845.  
  2846. #ifdef FEAT_EVAL
  2847.     /*
  2848.      * Check for "<script>": remap script-local mappings only
  2849.      */
  2850.     if (STRNCMP(keys, "<script>", 8) == 0)
  2851.     {
  2852.         keys = skipwhite(keys + 8);
  2853.         noremap = REMAP_SCRIPT;
  2854.         continue;
  2855.     }
  2856. #endif
  2857.     /*
  2858.      * Check for "<unique>": don't overwrite an existing mapping.
  2859.      */
  2860.     if (STRNCMP(keys, "<unique>", 8) == 0)
  2861.     {
  2862.         keys = skipwhite(keys + 8);
  2863.         unique = TRUE;
  2864.         continue;
  2865.     }
  2866.     break;
  2867.     }
  2868.  
  2869.     validate_maphash();
  2870.  
  2871.     /*
  2872.      * find end of keys and skip CTRL-Vs (and backslashes) in it
  2873.      * Accept backslash like CTRL-V when 'cpoptions' does not contain 'B'.
  2874.      * with :unmap white space is included in the keys, no argument possible
  2875.      */
  2876.     p = keys;
  2877.     do_backslash = (vim_strchr(p_cpo, CPO_BSLASH) == NULL);
  2878.     while (*p && (maptype == 1 || !vim_iswhite(*p)))
  2879.     {
  2880.     if ((p[0] == Ctrl_V || (do_backslash && p[0] == '\\')) &&
  2881.                                   p[1] != NUL)
  2882.         ++p;        /* skip CTRL-V or backslash */
  2883.     ++p;
  2884.     }
  2885.     if (*p != NUL)
  2886.     *p++ = NUL;
  2887.     p = skipwhite(p);
  2888.     rhs = p;
  2889.     hasarg = (*rhs != NUL);
  2890.     haskey = (*keys != NUL);
  2891.  
  2892.     /* check for :unmap without argument */
  2893.     if (maptype == 1 && !haskey)
  2894.     {
  2895.     retval = 1;
  2896.     goto theend;
  2897.     }
  2898.  
  2899.     /*
  2900.      * If mapping has been given as ^V<C_UP> say, then replace the term codes
  2901.      * with the appropriate two bytes. If it is a shifted special key, unshift
  2902.      * it too, giving another two bytes.
  2903.      * replace_termcodes() may move the result to allocated memory, which
  2904.      * needs to be freed later (*keys_buf and *arg_buf).
  2905.      * replace_termcodes() also removes CTRL-Vs and sometimes backslashes.
  2906.      */
  2907.     if (haskey)
  2908.     keys = replace_termcodes(keys, &keys_buf, TRUE, TRUE);
  2909.     if (hasarg)
  2910.     {
  2911.     if (STRICMP(rhs, "<nop>") == 0)        /* "<Nop>" means nothing */
  2912.         rhs = (char_u *)"";
  2913.     else
  2914.         rhs = replace_termcodes(rhs, &arg_buf, FALSE, TRUE);
  2915.     }
  2916.  
  2917. #ifdef FEAT_FKMAP
  2918.     /*
  2919.      * when in right-to-left mode and alternate keymap option set,
  2920.      * reverse the character flow in the rhs in Farsi.
  2921.      */
  2922.     if (p_altkeymap && curwin->w_p_rl)
  2923.     lrswap(rhs);
  2924. #endif
  2925.  
  2926.     /*
  2927.      * check arguments and translate function keys
  2928.      */
  2929.     if (haskey)
  2930.     {
  2931.     len = (int)STRLEN(keys);
  2932.     if (len > MAXMAPLEN)        /* maximum length of MAXMAPLEN chars */
  2933.     {
  2934.         retval = 1;
  2935.         goto theend;
  2936.     }
  2937.  
  2938.     if (abbrev && maptype != 1)
  2939.     {
  2940.         /*
  2941.          * If an abbreviation ends in a keyword character, the
  2942.          * rest must be all keyword-char or all non-keyword-char.
  2943.          * Otherwise we won't be able to find the start of it in a
  2944.          * vi-compatible way.
  2945.          */
  2946. #ifdef FEAT_MBYTE
  2947.         if (has_mbyte)
  2948.         {
  2949.         int    first, last;
  2950.         int    same = -1;
  2951.  
  2952.         first = vim_iswordp(keys);
  2953.         last = first;
  2954.         p = keys + mb_ptr2len_check(keys);
  2955.         n = 1;
  2956.         while (p < keys + len)
  2957.         {
  2958.             ++n;            /* nr of (multi-byte) chars */
  2959.             last = vim_iswordp(p);    /* type of last char */
  2960.             if (same == -1 && last != first)
  2961.             same = n - 1;        /* count of same char type */
  2962.             p += mb_ptr2len_check(p);
  2963.         }
  2964.         if (last && n > 2 && same >= 0 && same < n - 1)
  2965.         {
  2966.             retval = 1;
  2967.             goto theend;
  2968.         }
  2969.         }
  2970.         else
  2971. #endif
  2972.         if (vim_iswordc(keys[len - 1]))    /* ends in keyword char */
  2973.             for (n = 0; n < len - 2; ++n)
  2974.             if (vim_iswordc(keys[n]) != vim_iswordc(keys[len - 2]))
  2975.             {
  2976.                 retval = 1;
  2977.                 goto theend;
  2978.             }
  2979.         /* An abbrevation cannot contain white space. */
  2980.         for (n = 0; n < len; ++n)
  2981.         if (vim_iswhite(keys[n]))
  2982.         {
  2983.             retval = 1;
  2984.             goto theend;
  2985.         }
  2986.     }
  2987.     }
  2988.  
  2989.     if (haskey && hasarg && abbrev)    /* if we will add an abbreviation */
  2990.     no_abbr = FALSE;        /* reset flag that indicates there are
  2991.                                 no abbreviations */
  2992.  
  2993.     if (!haskey || (maptype != 1 && !hasarg))
  2994.     msg_start();
  2995.  
  2996. #ifdef FEAT_LOCALMAP
  2997.     /*
  2998.      * Check if a new local mapping wasn't already defined globally.
  2999.      */
  3000.     if (map_table == curbuf->b_maphash && haskey && hasarg && maptype != 1)
  3001.     {
  3002.     /* need to loop over all global hash lists */
  3003.     for (hash = 0; hash < 256 && !got_int; ++hash)
  3004.     {
  3005.         if (abbrev)
  3006.         {
  3007.         if (hash != 0)    /* there is only one abbreviation list */
  3008.             break;
  3009.         mp = first_abbr;
  3010.         }
  3011.         else
  3012.         mp = maphash[hash];
  3013.         for ( ; mp != NULL && !got_int; mp = mp->m_next)
  3014.         {
  3015.         /* check entries with the same mode */
  3016.         if ((mp->m_mode & mode) != 0
  3017.             && mp->m_keylen == len
  3018.             && unique
  3019.             && STRNCMP(mp->m_keys, keys, (size_t)len) == 0)
  3020.         {
  3021.             if (abbrev)
  3022.             EMSG2(_("E224: global abbreviation already exists for %s"),
  3023.                 mp->m_keys);
  3024.             else
  3025.             EMSG2(_("E225: global mapping already exists for %s"),
  3026.                 mp->m_keys);
  3027.             retval = 5;
  3028.             goto theend;
  3029.         }
  3030.         }
  3031.     }
  3032.     }
  3033.  
  3034.     /*
  3035.      * When listing global mappings, also list buffer-local ones here.
  3036.      */
  3037.     if (map_table != curbuf->b_maphash && !hasarg && maptype != 1)
  3038.     {
  3039.     /* need to loop over all global hash lists */
  3040.     for (hash = 0; hash < 256 && !got_int; ++hash)
  3041.     {
  3042.         if (abbrev)
  3043.         {
  3044.         if (hash != 0)    /* there is only one abbreviation list */
  3045.             break;
  3046.         mp = curbuf->b_first_abbr;
  3047.         }
  3048.         else
  3049.         mp = curbuf->b_maphash[hash];
  3050.         for ( ; mp != NULL && !got_int; mp = mp->m_next)
  3051.         {
  3052.         /* check entries with the same mode */
  3053.         if ((mp->m_mode & mode) != 0)
  3054.         {
  3055.             if (!haskey)            /* show all entries */
  3056.             {
  3057.             showmap(mp, TRUE);
  3058.             did_local = TRUE;
  3059.             }
  3060.             else
  3061.             {
  3062.             n = mp->m_keylen;
  3063.             if (STRNCMP(mp->m_keys, keys,
  3064.                         (size_t)(n < len ? n : len)) == 0)
  3065.             {
  3066.                 showmap(mp, TRUE);
  3067.                 did_local = TRUE;
  3068.             }
  3069.             }
  3070.         }
  3071.         }
  3072.     }
  3073.     }
  3074. #endif
  3075.  
  3076.     /*
  3077.      * Find an entry in the maphash[] list that matches.
  3078.      * For :unmap we may loop two times: once to try to unmap an entry with a
  3079.      * matching 'from' part, a second time, if the first fails, to unmap an
  3080.      * entry with a matching 'to' part. This was done to allow ":ab foo bar"
  3081.      * to be unmapped by typing ":unab foo", where "foo" will be replaced by
  3082.      * "bar" because of the abbreviation.
  3083.      */
  3084.     for (round = 0; (round == 0 || maptype == 1) && round <= 1
  3085.                           && !did_it && !got_int; ++round)
  3086.     {
  3087.     /* need to loop over all hash lists */
  3088.     for (hash = 0; hash < 256 && !got_int; ++hash)
  3089.     {
  3090.         if (abbrev)
  3091.         {
  3092.         if (hash != 0)    /* there is only one abbreviation list */
  3093.             break;
  3094.         mpp = abbr_table;
  3095.         }
  3096.         else
  3097.         mpp = &(map_table[hash]);
  3098.         for (mp = *mpp; mp != NULL && !got_int; mp = *mpp)
  3099.         {
  3100.  
  3101.         if (!(mp->m_mode & mode))   /* skip entries with wrong mode */
  3102.         {
  3103.             mpp = &(mp->m_next);
  3104.             continue;
  3105.         }
  3106.         if (!haskey)            /* show all entries */
  3107.         {
  3108.             showmap(mp, map_table != maphash);
  3109.             did_it = TRUE;
  3110.         }
  3111.         else                /* do we have a match? */
  3112.         {
  3113.             if (round)        /* second round: Try unmap "rhs" string */
  3114.             {
  3115.             n = (int)STRLEN(mp->m_str);
  3116.             p = mp->m_str;
  3117.             }
  3118.             else
  3119.             {
  3120.             n = mp->m_keylen;
  3121.             p = mp->m_keys;
  3122.             }
  3123.             if (STRNCMP(p, keys, (size_t)(n < len ? n : len)) == 0)
  3124.             {
  3125.             if (maptype == 1)    /* delete entry */
  3126.             {
  3127.                 if (n != len)    /* not a full match */
  3128.                 {
  3129.                 mpp = &(mp->m_next);
  3130.                 continue;
  3131.                 }
  3132.                 /*
  3133.                  * We reset the indicated mode bits. If nothing is
  3134.                  * left the entry is deleted below.
  3135.                  */
  3136.                 mp->m_mode &= ~mode;
  3137.                 did_it = TRUE;    /* remember we did something */
  3138.             }
  3139.             else if (!hasarg)    /* show matching entry */
  3140.             {
  3141.                 showmap(mp, map_table != maphash);
  3142.                 did_it = TRUE;
  3143.             }
  3144.             else if (n != len)    /* new entry is ambigious */
  3145.             {
  3146.                 mpp = &(mp->m_next);
  3147.                 continue;
  3148.             }
  3149.             else if (unique)
  3150.             {
  3151.                 if (abbrev)
  3152.                 EMSG2(_("E226: abbreviation already exists for %s"),
  3153.                                        p);
  3154.                 else
  3155.                 EMSG2(_("E227: mapping already exists for %s"), p);
  3156.                 retval = 5;
  3157.                 goto theend;
  3158.             }
  3159.             else            /* new rhs for existing entry */
  3160.             {
  3161.                 mp->m_mode &= ~mode;    /* remove mode bits */
  3162.                 if (mp->m_mode == 0 && !did_it) /* reuse entry */
  3163.                 {
  3164.                 newstr = vim_strsave(rhs);
  3165.                 if (newstr == NULL)
  3166.                 {
  3167.                     retval = 4;        /* no mem */
  3168.                     goto theend;
  3169.                 }
  3170.                 vim_free(mp->m_str);
  3171.                 mp->m_str = newstr;
  3172.                 mp->m_noremap = noremap;
  3173.                 mp->m_silent = silent;
  3174.                 mp->m_mode = mode;
  3175.                 did_it = TRUE;
  3176.                 }
  3177.             }
  3178.             if (mp->m_mode == 0)    /* entry can be deleted */
  3179.             {
  3180.                 map_free(mpp);
  3181.                 continue;        /* continue with *mpp */
  3182.             }
  3183.  
  3184.             /*
  3185.              * May need to put this entry into another hash list.
  3186.              */
  3187.             new_hash = MAP_HASH(mp->m_mode, mp->m_keys[0]);
  3188.             if (!abbrev && new_hash != hash)
  3189.             {
  3190.                 *mpp = mp->m_next;
  3191.                 mp->m_next = map_table[new_hash];
  3192.                 map_table[new_hash] = mp;
  3193.  
  3194.                 continue;        /* continue with *mpp */
  3195.             }
  3196.             }
  3197.         }
  3198.         mpp = &(mp->m_next);
  3199.         }
  3200.     }
  3201.     }
  3202.  
  3203.     if (maptype == 1)                /* delete entry */
  3204.     {
  3205.     if (!did_it)
  3206.         retval = 2;                /* no match */
  3207.     goto theend;
  3208.     }
  3209.  
  3210.     if (!haskey || !hasarg)            /* print entries */
  3211.     {
  3212.     if (!did_it
  3213. #ifdef FEAT_LOCALMAP
  3214.         && !did_local
  3215. #endif
  3216.         )
  3217.     {
  3218.         if (abbrev)
  3219.         MSG(_("No abbreviation found"));
  3220.         else
  3221.         MSG(_("No mapping found"));
  3222.     }
  3223.     goto theend;                /* listing finished */
  3224.     }
  3225.  
  3226.     if (did_it)            /* have added the new entry already */
  3227.     goto theend;
  3228.  
  3229.     /*
  3230.      * Get here when adding a new entry to the maphash[] list or abbrlist.
  3231.      */
  3232.     mp = (mapblock_T *)alloc((unsigned)sizeof(mapblock_T));
  3233.     if (mp == NULL)
  3234.     {
  3235.     retval = 4;        /* no mem */
  3236.     goto theend;
  3237.     }
  3238.  
  3239.     /* If CTRL-C has been mapped, don't always use it for Interrupting */
  3240.     if (*keys == Ctrl_C)
  3241.     mapped_ctrl_c = TRUE;
  3242.  
  3243.     mp->m_keys = vim_strsave(keys);
  3244.     mp->m_str = vim_strsave(rhs);
  3245.     if (mp->m_keys == NULL || mp->m_str == NULL)
  3246.     {
  3247.     vim_free(mp->m_keys);
  3248.     vim_free(mp->m_str);
  3249.     vim_free(mp);
  3250.     retval = 4;    /* no mem */
  3251.     goto theend;
  3252.     }
  3253.     mp->m_keylen = (int)STRLEN(mp->m_keys);
  3254.     mp->m_noremap = noremap;
  3255.     mp->m_silent = silent;
  3256.     mp->m_mode = mode;
  3257.  
  3258.     /* add the new entry in front of the abbrlist or maphash[] list */
  3259.     if (abbrev)
  3260.     {
  3261.     mp->m_next = *abbr_table;
  3262.     *abbr_table = mp;
  3263.     }
  3264.     else
  3265.     {
  3266.     n = MAP_HASH(mp->m_mode, mp->m_keys[0]);
  3267.     mp->m_next = map_table[n];
  3268.     map_table[n] = mp;
  3269.     }
  3270.  
  3271. theend:
  3272.     vim_free(keys_buf);
  3273.     vim_free(arg_buf);
  3274.     return retval;
  3275. }
  3276.  
  3277. /*
  3278.  * Delete one entry from the abbrlist or maphash[].
  3279.  * "mpp" is a pointer to the m_next field of the PREVIOUS entry!
  3280.  */
  3281.     static void
  3282. map_free(mpp)
  3283.     mapblock_T    **mpp;
  3284. {
  3285.     mapblock_T    *mp;
  3286.  
  3287.     mp = *mpp;
  3288.     vim_free(mp->m_keys);
  3289.     vim_free(mp->m_str);
  3290.     *mpp = mp->m_next;
  3291.     vim_free(mp);
  3292. }
  3293.  
  3294. /*
  3295.  * Initialize maphash[] for first use.
  3296.  */
  3297.     static void
  3298. validate_maphash()
  3299. {
  3300.     if (!maphash_valid)
  3301.     {
  3302.     vim_memset(maphash, 0, sizeof(maphash));
  3303.     maphash_valid = TRUE;
  3304.     }
  3305. }
  3306.  
  3307. /*
  3308.  * Get the mapping mode from the command name.
  3309.  */
  3310.     int
  3311. get_map_mode(cmdp, forceit)
  3312.     char_u    **cmdp;
  3313.     int        forceit;
  3314. {
  3315.     char_u    *p;
  3316.     int        modec;
  3317.     int        mode;
  3318.  
  3319.     p = *cmdp;
  3320.     modec = *p++;
  3321.     if (modec == 'i')
  3322.     mode = INSERT;                /* :imap */
  3323.     else if (modec == 'l')
  3324.     mode = LANGMAP;                /* :lmap */
  3325.     else if (modec == 'c')
  3326.     mode = CMDLINE;                /* :cmap */
  3327.     else if (modec == 'n' && *p != 'o')            /* avoid :noremap */
  3328.     mode = NORMAL;                /* :nmap */
  3329.     else if (modec == 'v')
  3330.     mode = VISUAL;                /* :vmap */
  3331.     else if (modec == 'o')
  3332.     mode = OP_PENDING;            /* :omap */
  3333.     else
  3334.     {
  3335.     --p;
  3336.     if (forceit)
  3337.         mode = INSERT + CMDLINE;        /* :map ! */
  3338.     else
  3339.         mode = VISUAL + NORMAL + OP_PENDING;/* :map */
  3340.     }
  3341.  
  3342.     *cmdp = p;
  3343.     return mode;
  3344. }
  3345.  
  3346. /*
  3347.  * Clear all mappings or abbreviations.
  3348.  * 'abbr' should be FALSE for mappings, TRUE for abbreviations.
  3349.  */
  3350. /*ARGSUSED*/
  3351.     void
  3352. map_clear(cmdp, arg, forceit, abbr)
  3353.     char_u    *cmdp;
  3354.     char_u    *arg;
  3355.     int        forceit;
  3356.     int        abbr;
  3357. {
  3358.     int        mode;
  3359. #ifdef FEAT_LOCALMAP
  3360.     int        local;
  3361.  
  3362.     local = (STRCMP(arg, "<buffer>") == 0);
  3363.     if (!local && *arg != NUL)
  3364.     {
  3365.     EMSG(_(e_invarg));
  3366.     return;
  3367.     }
  3368. #endif
  3369.  
  3370.     mode = get_map_mode(&cmdp, forceit);
  3371.     map_clear_int(curbuf, mode,
  3372. #ifdef FEAT_LOCALMAP
  3373.         local,
  3374. #else
  3375.         FALSE,
  3376. #endif
  3377.         abbr);
  3378. }
  3379.  
  3380. /*
  3381.  * Clear all mappings in "mode".
  3382.  */
  3383. /*ARGSUSED*/
  3384.     void
  3385. map_clear_int(buf, mode, local, abbr)
  3386.     buf_T    *buf;        /* buffer for local mappings */
  3387.     int        mode;        /* mode in which to delete */
  3388.     int        local;        /* TRUE for buffer-local mappings */
  3389.     int        abbr;        /* TRUE for abbreviations */
  3390. {
  3391.     mapblock_T    *mp, **mpp;
  3392.     int        hash;
  3393.     int        new_hash;
  3394.  
  3395.     validate_maphash();
  3396.  
  3397.     for (hash = 0; hash < 256; ++hash)
  3398.     {
  3399.     if (abbr)
  3400.     {
  3401.         if (hash)        /* there is only one abbrlist */
  3402.         break;
  3403. #ifdef FEAT_LOCALMAP
  3404.         if (local)
  3405.         mpp = &buf->b_first_abbr;
  3406.         else
  3407. #endif
  3408.         mpp = &first_abbr;
  3409.     }
  3410.     else
  3411.     {
  3412. #ifdef FEAT_LOCALMAP
  3413.         if (local)
  3414.         mpp = &buf->b_maphash[hash];
  3415.         else
  3416. #endif
  3417.         mpp = &maphash[hash];
  3418.     }
  3419.     while (*mpp != NULL)
  3420.     {
  3421.         mp = *mpp;
  3422.         if (mp->m_mode & mode)
  3423.         {
  3424.         mp->m_mode &= ~mode;
  3425.         if (mp->m_mode == 0) /* entry can be deleted */
  3426.         {
  3427.             map_free(mpp);
  3428.             continue;
  3429.         }
  3430.         /*
  3431.          * May need to put this entry into another hash list.
  3432.          */
  3433.         new_hash = MAP_HASH(mp->m_mode, mp->m_keys[0]);
  3434.         if (!abbr && new_hash != hash)
  3435.         {
  3436.             *mpp = mp->m_next;
  3437. #ifdef FEAT_LOCALMAP
  3438.             if (local)
  3439.             {
  3440.             mp->m_next = buf->b_maphash[new_hash];
  3441.             buf->b_maphash[new_hash] = mp;
  3442.             }
  3443.             else
  3444. #endif
  3445.             {
  3446.             mp->m_next = maphash[new_hash];
  3447.             maphash[new_hash] = mp;
  3448.             }
  3449.             continue;        /* continue with *mpp */
  3450.         }
  3451.         }
  3452.         mpp = &(mp->m_next);
  3453.     }
  3454.     }
  3455. }
  3456.  
  3457.     static void
  3458. showmap(mp, local)
  3459.     mapblock_T    *mp;
  3460.     int        local;        /* TRUE for buffer-local map */
  3461. {
  3462.     int len = 1;
  3463.  
  3464.     if (msg_didout)
  3465.     msg_putchar('\n');
  3466.     if ((mp->m_mode & (INSERT + CMDLINE)) == INSERT + CMDLINE)
  3467.     msg_putchar('!');            /* :map! */
  3468.     else if (mp->m_mode & INSERT)
  3469.     msg_putchar('i');            /* :imap */
  3470.     else if (mp->m_mode & LANGMAP)
  3471.     msg_putchar('l');            /* :lmap */
  3472.     else if (mp->m_mode & CMDLINE)
  3473.     msg_putchar('c');            /* :cmap */
  3474.     else if ((mp->m_mode & (NORMAL + VISUAL + OP_PENDING))
  3475.                           == NORMAL + VISUAL + OP_PENDING)
  3476.     msg_putchar(' ');            /* :map */
  3477.     else
  3478.     {
  3479.     len = 0;
  3480.     if (mp->m_mode & NORMAL)
  3481.     {
  3482.         msg_putchar('n');        /* :nmap */
  3483.         ++len;
  3484.     }
  3485.     if (mp->m_mode & OP_PENDING)
  3486.     {
  3487.         msg_putchar('o');        /* :omap */
  3488.         ++len;
  3489.     }
  3490.     if (mp->m_mode & VISUAL)
  3491.     {
  3492.         msg_putchar('v');        /* :vmap */
  3493.         ++len;
  3494.     }
  3495.     }
  3496.     while (++len <= 3)
  3497.     msg_putchar(' ');
  3498.  
  3499.     /* Get length of what we write */
  3500.     len = msg_outtrans_special(mp->m_keys, TRUE);
  3501.     do
  3502.     {
  3503.     msg_putchar(' ');        /* padd with blanks */
  3504.     ++len;
  3505.     } while (len < 12);
  3506.  
  3507.     if (mp->m_noremap == REMAP_NONE)
  3508.     msg_puts_attr((char_u *)"*", hl_attr(HLF_8));
  3509.     else if (mp->m_noremap == REMAP_SCRIPT)
  3510.     msg_puts_attr((char_u *)"&", hl_attr(HLF_8));
  3511.     else
  3512.     msg_putchar(' ');
  3513.  
  3514.     if (local)
  3515.     msg_putchar('@');
  3516.     else
  3517.     msg_putchar(' ');
  3518.  
  3519.     /* Use FALSE below if we only want things like <Up> to show up as such on
  3520.      * the rhs, and not M-x etc, TRUE gets both -- webb
  3521.      */
  3522.     if (*mp->m_str == NUL)
  3523.     msg_puts_attr((char_u *)"<Nop>", hl_attr(HLF_8));
  3524.     else
  3525.     msg_outtrans_special(mp->m_str, FALSE);
  3526.     out_flush();            /* show one line at a time */
  3527. }
  3528.  
  3529. #if defined(FEAT_EVAL) || defined(PROTO)
  3530. /*
  3531.  * Return TRUE if a map exists that has "str" in the rhs for mode "modechars".
  3532.  * Recognize termcap codes in "str".
  3533.  * Also checks mappings local to the current buffer.
  3534.  */
  3535.     int
  3536. map_to_exists(str, modechars)
  3537.     char_u    *str;
  3538.     char_u    *modechars;
  3539. {
  3540.     int        mode = 0;
  3541.     char_u    *rhs;
  3542.     char_u    *buf;
  3543.     int        retval;
  3544.  
  3545.     rhs = replace_termcodes(str, &buf, FALSE, TRUE);
  3546.  
  3547.     if (vim_strchr(modechars, 'n') != NULL)
  3548.     mode |= NORMAL;
  3549.     if (vim_strchr(modechars, 'v') != NULL)
  3550.     mode |= VISUAL;
  3551.     if (vim_strchr(modechars, 'o') != NULL)
  3552.     mode |= OP_PENDING;
  3553.     if (vim_strchr(modechars, 'i') != NULL)
  3554.     mode |= INSERT;
  3555.     if (vim_strchr(modechars, 'l') != NULL)
  3556.     mode |= LANGMAP;
  3557.     if (vim_strchr(modechars, 'c') != NULL)
  3558.     mode |= CMDLINE;
  3559.  
  3560.     retval = map_to_exists_mode(rhs, mode);
  3561.     vim_free(buf);
  3562.  
  3563.     return retval;
  3564. }
  3565. #endif
  3566.  
  3567. /*
  3568.  * Return TRUE if a map exists that has "str" in the rhs for mode "mode".
  3569.  * Also checks mappings local to the current buffer.
  3570.  */
  3571.     int
  3572. map_to_exists_mode(rhs, mode)
  3573.     char_u    *rhs;
  3574.     int        mode;
  3575. {
  3576.     mapblock_T    *mp;
  3577.     int        hash;
  3578. # ifdef FEAT_LOCALMAP
  3579.     int        expand_buffer = FALSE;
  3580.  
  3581.     validate_maphash();
  3582.  
  3583.     /* Do it twice: once for global maps and once for local maps. */
  3584.     for (;;)
  3585.     {
  3586. # endif
  3587.     for (hash = 0; hash < 256; ++hash)
  3588.     {
  3589. # ifdef FEAT_LOCALMAP
  3590.         if (expand_buffer)
  3591.         mp = curbuf->b_maphash[hash];
  3592.         else
  3593. # endif
  3594.         mp = maphash[hash];
  3595.         for (; mp; mp = mp->m_next)
  3596.         {
  3597.         if ((mp->m_mode & mode)
  3598.             && strstr((char *)mp->m_str, (char *)rhs) != NULL)
  3599.             return TRUE;
  3600.         }
  3601.     }
  3602. # ifdef FEAT_LOCALMAP
  3603.     if (expand_buffer)
  3604.         break;
  3605.     expand_buffer = TRUE;
  3606.     }
  3607. # endif
  3608.  
  3609.     return FALSE;
  3610. }
  3611.  
  3612. #if defined(FEAT_CMDL_COMPL) || defined(PROTO)
  3613. /*
  3614.  * Used below when expanding mapping/abbreviation names.
  3615.  */
  3616. static int    expand_mapmodes = 0;
  3617. static int    expand_isabbrev = 0;
  3618. #ifdef FEAT_LOCALMAP
  3619. static int    expand_buffer = FALSE;
  3620. #endif
  3621.  
  3622. /*
  3623.  * Work out what to complete when doing command line completion of mapping
  3624.  * or abbreviation names.
  3625.  */
  3626.     char_u *
  3627. set_context_in_map_cmd(xp, cmd, arg, forceit, isabbrev, isunmap, cmdidx)
  3628.     expand_T    *xp;
  3629.     char_u    *cmd;
  3630.     char_u    *arg;
  3631.     int        forceit;    /* TRUE if '!' given */
  3632.     int        isabbrev;    /* TRUE if abbreviation */
  3633.     int        isunmap;    /* TRUE if unmap/unabbrev command */
  3634.     cmdidx_T    cmdidx;
  3635. {
  3636.     if (forceit && cmdidx != CMD_map && cmdidx != CMD_unmap)
  3637.     xp->xp_context = EXPAND_NOTHING;
  3638.     else
  3639.     {
  3640.     if (isunmap)
  3641.         expand_mapmodes = get_map_mode(&cmd, forceit || isabbrev);
  3642.     else
  3643.     {
  3644.         expand_mapmodes = INSERT + CMDLINE;
  3645.         if (!isabbrev)
  3646.         expand_mapmodes += VISUAL + NORMAL + OP_PENDING;
  3647.     }
  3648.     expand_isabbrev = isabbrev;
  3649.     xp->xp_context = EXPAND_MAPPINGS;
  3650. #ifdef FEAT_LOCALMAP
  3651.     expand_buffer = FALSE;
  3652. #endif
  3653.     for (;;)
  3654.     {
  3655. #ifdef FEAT_LOCALMAP
  3656.         if (STRNCMP(arg, "<buffer>", 8) == 0)
  3657.         {
  3658.         expand_buffer = TRUE;
  3659.         arg = skipwhite(arg + 8);
  3660.         continue;
  3661.         }
  3662. #endif
  3663.         if (STRNCMP(arg, "<unique>", 8) == 0)
  3664.         {
  3665.         arg = skipwhite(arg + 8);
  3666.         continue;
  3667.         }
  3668.         if (STRNCMP(arg, "<silent>", 8) == 0)
  3669.         {
  3670.         arg = skipwhite(arg + 8);
  3671.         continue;
  3672.         }
  3673.         if (STRNCMP(arg, "<script>", 8) == 0)
  3674.         {
  3675.         arg = skipwhite(arg + 8);
  3676.         continue;
  3677.         }
  3678.         break;
  3679.     }
  3680.     xp->xp_pattern = arg;
  3681.     }
  3682.  
  3683.     return NULL;
  3684. }
  3685.  
  3686. /*
  3687.  * Find all mapping/abbreviation names that match regexp 'prog'.
  3688.  * For command line expansion of ":[un]map" and ":[un]abbrev" in all modes.
  3689.  * Return OK if matches found, FAIL otherwise.
  3690.  */
  3691.     int
  3692. ExpandMappings(regmatch, num_file, file)
  3693.     regmatch_T    *regmatch;
  3694.     int        *num_file;
  3695.     char_u    ***file;
  3696. {
  3697.     mapblock_T    *mp;
  3698.     int        hash;
  3699.     int        count;
  3700.     int        round;
  3701.     char_u    *p;
  3702.     int        i;
  3703.  
  3704.     validate_maphash();
  3705.  
  3706.     *num_file = 0;            /* return values in case of FAIL */
  3707.     *file = NULL;
  3708.  
  3709.     /*
  3710.      * round == 1: Count the matches.
  3711.      * round == 2: Build the array to keep the matches.
  3712.      */
  3713.     for (round = 1; round <= 2; ++round)
  3714.     {
  3715.     count = 0;
  3716.  
  3717.     for (i = 0; i < 4; ++i)
  3718.     {
  3719.         if (i == 0)
  3720.         p = (char_u *)"<silent>";
  3721.         else if (i == 1)
  3722.         p = (char_u *)"<unique>";
  3723. #ifdef FEAT_EVAL
  3724.         else if (i == 2)
  3725.         p = (char_u *)"<script>";
  3726. #endif
  3727. #ifdef FEAT_LOCALMAP
  3728.         else if (i == 3 && !expand_buffer)
  3729.         p = (char_u *)"<buffer>";
  3730. #endif
  3731.         else
  3732.         continue;
  3733.  
  3734.         if (vim_regexec(regmatch, p, (colnr_T)0))
  3735.         {
  3736.         if (round == 1)
  3737.             ++count;
  3738.         else
  3739.             (*file)[count++] = vim_strsave(p);
  3740.         }
  3741.     }
  3742.  
  3743.     for (hash = 0; hash < 256; ++hash)
  3744.     {
  3745.         if (expand_isabbrev)
  3746.         {
  3747.         if (hash)    /* only one abbrev list */
  3748.             break; /* for (hash) */
  3749.         mp = first_abbr;
  3750.         }
  3751. #ifdef FEAT_LOCALMAP
  3752.         else if (expand_buffer)
  3753.         mp = curbuf->b_maphash[hash];
  3754. #endif
  3755.         else
  3756.         mp = maphash[hash];
  3757.         for (; mp; mp = mp->m_next)
  3758.         {
  3759.         if (mp->m_mode & expand_mapmodes)
  3760.         {
  3761.             p = translate_mapping(mp->m_keys, TRUE);
  3762.             if (p != NULL && vim_regexec(regmatch, p, (colnr_T)0))
  3763.             {
  3764.             if (round == 1)
  3765.                 ++count;
  3766.             else
  3767.             {
  3768.                 (*file)[count++] = p;
  3769.                 p = NULL;
  3770.             }
  3771.             }
  3772.             vim_free(p);
  3773.         }
  3774.         } /* for (mp) */
  3775.     } /* for (hash) */
  3776.  
  3777.     if (count == 0)            /* no match found */
  3778.         break; /* for (round) */
  3779.  
  3780.     if (round == 1)
  3781.     {
  3782.         *file = (char_u **)alloc((unsigned)(count * sizeof(char_u *)));
  3783.         if (*file == NULL)
  3784.         return FAIL;
  3785.     }
  3786.     } /* for (round) */
  3787.  
  3788.     /* Sort the matches */
  3789.     sort_strings(*file, count);
  3790.  
  3791.     /* Remove multiple entries */
  3792.     {
  3793.     char_u    **ptr1 = *file;
  3794.     char_u    **ptr2 = ptr1 + 1;
  3795.     char_u    **ptr3 = ptr1 + count;
  3796.  
  3797.     while (ptr2 < ptr3)
  3798.     {
  3799.         if (STRCMP(*ptr1, *ptr2))
  3800.         *++ptr1 = *ptr2++;
  3801.         else
  3802.         {
  3803.         vim_free(*ptr2++);
  3804.         count--;
  3805.         }
  3806.     }
  3807.     }
  3808.  
  3809.     *num_file = count;
  3810.     return (count == 0 ? FAIL : OK);
  3811. }
  3812. #endif /* FEAT_CMDL_COMPL */
  3813.  
  3814. /*
  3815.  * Check for an abbreviation.
  3816.  * Cursor is at ptr[col]. When inserting, mincol is where insert started.
  3817.  * "c" is the character typed before check_abbr was called.  It may have
  3818.  * ABBR_OFF added to avoid prepending a CTRL-V to it.
  3819.  *
  3820.  * Historic vi practice: The last character of an abbreviation must be an id
  3821.  * character ([a-zA-Z0-9_]). The characters in front of it must be all id
  3822.  * characters or all non-id characters. This allows for abbr. "#i" to
  3823.  * "#include".
  3824.  *
  3825.  * Vim addition: Allow for abbreviations that end in a non-keyword character.
  3826.  * Then there must be white space before the abbr.
  3827.  *
  3828.  * return TRUE if there is an abbreviation, FALSE if not
  3829.  */
  3830.     int
  3831. check_abbr(c, ptr, col, mincol)
  3832.     int        c;
  3833.     char_u    *ptr;
  3834.     int        col;
  3835.     int        mincol;
  3836. {
  3837.     int        len;
  3838.     int        scol;        /* starting column of the abbr. */
  3839.     int        j;
  3840. #ifdef FEAT_MBYTE
  3841.     char_u    tb[MB_MAXBYTES + 4];
  3842. #else
  3843.     char_u    tb[4];
  3844. #endif
  3845.     mapblock_T    *mp;
  3846. #ifdef FEAT_LOCALMAP
  3847.     mapblock_T    *mp2;
  3848. #endif
  3849. #ifdef FEAT_MBYTE
  3850.     int        clen = 0;    /* length in characters */
  3851. #endif
  3852.     int        is_id = TRUE;
  3853.     int        vim_abbr;
  3854.  
  3855.     if (typebuf.tb_no_abbr_cnt)    /* abbrev. are not recursive */
  3856.     return FALSE;
  3857.  
  3858.     /*
  3859.      * Check for word before the cursor: If it ends in a keyword char all
  3860.      * chars before it must be al keyword chars or non-keyword chars, but not
  3861.      * white space. If it ends in a non-keyword char we accept any characters
  3862.      * before it except white space.
  3863.      */
  3864.     if (col == 0)                /* cannot be an abbr. */
  3865.     return FALSE;
  3866.  
  3867. #ifdef FEAT_MBYTE
  3868.     if (has_mbyte)
  3869.     {
  3870.     char_u *p;
  3871.  
  3872.     p = mb_prevptr(ptr, ptr + col);
  3873.     if (!vim_iswordp(p))
  3874.         vim_abbr = TRUE;            /* Vim added abbr. */
  3875.     else
  3876.     {
  3877.         vim_abbr = FALSE;            /* vi compatible abbr. */
  3878.         if (p > ptr)
  3879.         is_id = vim_iswordp(mb_prevptr(ptr, p));
  3880.     }
  3881.     clen = 1;
  3882.     while (p > ptr)
  3883.     {
  3884.         p = mb_prevptr(ptr, p);
  3885.         if (vim_isspace(*p) || (!vim_abbr && is_id != vim_iswordp(p)))
  3886.         {
  3887.         p += (*mb_ptr2len_check)(p);
  3888.         break;
  3889.         }
  3890.         ++clen;
  3891.     }
  3892.     scol = (int)(p - ptr);
  3893.     }
  3894.     else
  3895. #endif
  3896.     {
  3897.     if (!vim_iswordc(ptr[col - 1]))
  3898.         vim_abbr = TRUE;            /* Vim added abbr. */
  3899.     else
  3900.     {
  3901.         vim_abbr = FALSE;            /* vi compatible abbr. */
  3902.         if (col > 1)
  3903.         is_id = vim_iswordc(ptr[col - 2]);
  3904.     }
  3905.     for (scol = col - 1; scol > 0 && !vim_isspace(ptr[scol - 1])
  3906.         && (vim_abbr || is_id == vim_iswordc(ptr[scol - 1])); --scol)
  3907.         ;
  3908.     }
  3909.  
  3910.     if (scol < mincol)
  3911.     scol = mincol;
  3912.     if (scol < col)        /* there is a word in front of the cursor */
  3913.     {
  3914.     ptr += scol;
  3915.     len = col - scol;
  3916. #ifdef FEAT_LOCALMAP
  3917.     mp = curbuf->b_first_abbr;
  3918.     mp2 = first_abbr;
  3919.     if (mp == NULL)
  3920.     {
  3921.         mp = mp2;
  3922.         mp2 = NULL;
  3923.     }
  3924. #else
  3925.     mp = first_abbr;
  3926. #endif
  3927.     for ( ; mp;
  3928. #ifdef FEAT_LOCALMAP
  3929.         mp->m_next == NULL ? (mp = mp2, mp2 = NULL) :
  3930. #endif
  3931.         (mp = mp->m_next))
  3932.     {
  3933.         /* find entries with right mode and keys */
  3934.         if (       (mp->m_mode & State)
  3935.             && mp->m_keylen == len
  3936.             && !STRNCMP(mp->m_keys, ptr, (size_t)len))
  3937.         break;
  3938.     }
  3939.     if (mp != NULL)
  3940.     {
  3941.         /*
  3942.          * Found a match:
  3943.          * Insert the rest of the abbreviation in typebuf.tb_buf[].
  3944.          * This goes from end to start.
  3945.          *
  3946.          * Characters 0x000 - 0x100: normal chars, may need CTRL-V,
  3947.          * except K_SPECIAL: Becomes K_SPECIAL KS_SPECIAL KE_FILLER
  3948.          * Characters where IS_SPECIAL() == TRUE: key codes, need
  3949.          * K_SPECIAL. Other characters (with ABBR_OFF): don't use CTRL-V.
  3950.          *
  3951.          * Character CTRL-] is treated specially - it completes the
  3952.          * abbreviation, but is not inserted into the input stream.
  3953.          */
  3954.         j = 0;
  3955.                     /* special key code, split up */
  3956.         if (c != Ctrl_RSB)
  3957.         {
  3958.         if (IS_SPECIAL(c) || c == K_SPECIAL)
  3959.         {
  3960.             tb[j++] = K_SPECIAL;
  3961.             tb[j++] = K_SECOND(c);
  3962.             tb[j++] = K_THIRD(c);
  3963.         }
  3964.         else
  3965.         {
  3966.             if (c < ABBR_OFF && (c < ' ' || c > '~'))
  3967.             tb[j++] = Ctrl_V;    /* special char needs CTRL-V */
  3968. #ifdef FEAT_MBYTE
  3969.             if (has_mbyte)
  3970.             {
  3971.             /* if ABBR_OFF has been added, remove it here */
  3972.             if (c >= ABBR_OFF)
  3973.                 c -= ABBR_OFF;
  3974.             j += (*mb_char2bytes)(c, tb + j);
  3975.             }
  3976.             else
  3977. #endif
  3978.             tb[j++] = c;
  3979.         }
  3980.         tb[j] = NUL;
  3981.                     /* insert the last typed char */
  3982.         (void)ins_typebuf(tb, 1, 0, TRUE, mp->m_silent);
  3983.         }
  3984.                     /* insert the to string */
  3985.         (void)ins_typebuf(mp->m_str, mp->m_noremap, 0, TRUE, mp->m_silent);
  3986.                     /* no abbrev. for these chars */
  3987.         typebuf.tb_no_abbr_cnt += (int)STRLEN(mp->m_str) + j + 1;
  3988.  
  3989.         tb[0] = Ctrl_H;
  3990.         tb[1] = NUL;
  3991. #ifdef FEAT_MBYTE
  3992.         if (has_mbyte)
  3993.         len = clen;    /* Delete characters instead of bytes */
  3994. #endif
  3995.         while (len-- > 0)        /* delete the from string */
  3996.         (void)ins_typebuf(tb, 1, 0, TRUE, mp->m_silent);
  3997.         return TRUE;
  3998.     }
  3999.     }
  4000.     return FALSE;
  4001. }
  4002.  
  4003. /*
  4004.  * Write map commands for the current mappings to an .exrc file.
  4005.  * Return FAIL on error, OK otherwise.
  4006.  */
  4007.     int
  4008. makemap(fd, buf)
  4009.     FILE    *fd;
  4010.     buf_T    *buf;        /* buffer for local mappings or NULL */
  4011. {
  4012.     mapblock_T    *mp;
  4013.     char_u    c1, c2;
  4014.     char_u    *p;
  4015.     char    *cmd;
  4016.     int        abbr;
  4017.     int        hash;
  4018.     int        did_cpo = FALSE;
  4019.     int        i;
  4020.  
  4021.     validate_maphash();
  4022.  
  4023.     /*
  4024.      * Do the loop twice: Once for mappings, once for abbreviations.
  4025.      * Then loop over all map hash lists.
  4026.      */
  4027.     for (abbr = 0; abbr < 2; ++abbr)
  4028.     for (hash = 0; hash < 256; ++hash)
  4029.     {
  4030.         if (abbr)
  4031.         {
  4032.         if (hash)        /* there is only one abbr list */
  4033.             break;
  4034. #ifdef FEAT_LOCALMAP
  4035.         if (buf != NULL)
  4036.             mp = buf->b_first_abbr;
  4037.         else
  4038. #endif
  4039.             mp = first_abbr;
  4040.         }
  4041.         else
  4042.         {
  4043. #ifdef FEAT_LOCALMAP
  4044.         if (buf != NULL)
  4045.             mp = buf->b_maphash[hash];
  4046.         else
  4047. #endif
  4048.             mp = maphash[hash];
  4049.         }
  4050.  
  4051.         for ( ; mp; mp = mp->m_next)
  4052.         {
  4053.         /* skip script-local mappings */
  4054.         if (mp->m_noremap == REMAP_SCRIPT)
  4055.             continue;
  4056.  
  4057.         /* skip mappings that contain a <SNR> (script-local thing),
  4058.          * they probably don't work when loaded again */
  4059.         for (p = mp->m_str; *p != NUL; ++p)
  4060.             if (p[0] == K_SPECIAL && p[1] == KS_EXTRA
  4061.                                && p[2] == (int)KE_SNR)
  4062.             break;
  4063.         if (*p != NUL)
  4064.             continue;
  4065.  
  4066.         c1 = NUL;
  4067.         c2 = NUL;
  4068.         if (abbr)
  4069.             cmd = "abbr";
  4070.         else
  4071.             cmd = "map";
  4072.         switch (mp->m_mode)
  4073.         {
  4074.             case NORMAL + VISUAL + OP_PENDING:
  4075.             break;
  4076.             case NORMAL:
  4077.             c1 = 'n';
  4078.             break;
  4079.             case VISUAL:
  4080.             c1 = 'v';
  4081.             break;
  4082.             case OP_PENDING:
  4083.             c1 = 'o';
  4084.             break;
  4085.             case NORMAL + VISUAL:
  4086.             c1 = 'n';
  4087.             c2 = 'v';
  4088.             break;
  4089.             case VISUAL + OP_PENDING:
  4090.             c1 = 'v';
  4091.             c2 = 'o';
  4092.             break;
  4093.             case NORMAL + OP_PENDING:
  4094.             c1 = 'n';
  4095.             c2 = 'o';
  4096.             break;
  4097.             case CMDLINE + INSERT:
  4098.             if (!abbr)
  4099.                 cmd = "map!";
  4100.             break;
  4101.             case CMDLINE:
  4102.             c1 = 'c';
  4103.             break;
  4104.             case INSERT:
  4105.             c1 = 'i';
  4106.             break;
  4107.             case LANGMAP:
  4108.             c1 = 'l';
  4109.             break;
  4110.             default:
  4111.             EMSG(_("E228: makemap: Illegal mode"));
  4112.             return FAIL;
  4113.         }
  4114.         do    /* may do this twice if c2 is set */
  4115.         {
  4116.             /* When outputting <> form, need to make sure that 'cpo'
  4117.              * is set to the Vim default. */
  4118.             if (!did_cpo)
  4119.             {
  4120.             if (*mp->m_str == NUL)        /* will use <Nop> */
  4121.                 did_cpo = TRUE;
  4122.             else
  4123.                 for (i = 0; i < 2; ++i)
  4124.                 for (p = (i ? mp->m_str : mp->m_keys); *p; ++p)
  4125.                     if (*p == K_SPECIAL || *p == NL)
  4126.                     did_cpo = TRUE;
  4127.             if (did_cpo)
  4128.             {
  4129.                 if (fprintf(fd, "let s:cpo_save=&cpo") < 0
  4130.                     || put_eol(fd) < 0
  4131.                     || fprintf(fd, "set cpo&vim") < 0
  4132.                     || put_eol(fd) < 0)
  4133.                 return FAIL;
  4134.             }
  4135.             }
  4136.             if (c1 && putc(c1, fd) < 0)
  4137.             return FAIL;
  4138.             if (mp->m_noremap != REMAP_YES && fprintf(fd, "nore") < 0)
  4139.             return FAIL;
  4140.             if (fprintf(fd, cmd) < 0)
  4141.             return FAIL;
  4142.             if (buf != NULL && fputs(" <buffer>", fd) < 0)
  4143.             return FAIL;
  4144.             if (mp->m_silent && fputs(" <silent>", fd) < 0)
  4145.             return FAIL;
  4146.  
  4147.             if (       putc(' ', fd) < 0
  4148.                 || put_escstr(fd, mp->m_keys, 0) == FAIL
  4149.                 || putc(' ', fd) < 0
  4150.                 || put_escstr(fd, mp->m_str, 1) == FAIL
  4151.                 || put_eol(fd) < 0)
  4152.             return FAIL;
  4153.             c1 = c2;
  4154.             c2 = NUL;
  4155.         }
  4156.         while (c1);
  4157.         }
  4158.     }
  4159.  
  4160.     if (did_cpo)
  4161.     if (fprintf(fd, "let &cpo=s:cpo_save") < 0
  4162.         || put_eol(fd) < 0
  4163.         || fprintf(fd, "unlet s:cpo_save") < 0
  4164.         || put_eol(fd) < 0)
  4165.         return FAIL;
  4166.     return OK;
  4167. }
  4168.  
  4169. /*
  4170.  * write escape string to file
  4171.  * "what": 0 for :map lhs, 1 for :map rhs, 2 for :set
  4172.  *
  4173.  * return FAIL for failure, OK otherwise
  4174.  */
  4175.     int
  4176. put_escstr(fd, strstart, what)
  4177.     FILE    *fd;
  4178.     char_u    *strstart;
  4179.     int        what;
  4180. {
  4181.     char_u    *str = strstart;
  4182.     int        c;
  4183.     int        modifiers;
  4184.  
  4185.     /* :map xx <Nop> */
  4186.     if (*str == NUL && what == 1)
  4187.     {
  4188.     if (fprintf(fd, "<Nop>") < 0)
  4189.         return FAIL;
  4190.     return OK;
  4191.     }
  4192.  
  4193.     for ( ; *str != NUL; ++str)
  4194.     {
  4195. #ifdef FEAT_MBYTE
  4196.     char_u    *p;
  4197.  
  4198.     /* Check for a multi-byte character, which may contain escaped
  4199.      * K_SPECIAL and CSI bytes */
  4200.     p = mb_unescape(&str);
  4201.     if (p != NULL)
  4202.     {
  4203.         while (*p != NUL)
  4204.         if (putc(*p++, fd) < 0)
  4205.             return FAIL;
  4206.         --str;
  4207.         continue;
  4208.     }
  4209. #endif
  4210.  
  4211.     c = *str;
  4212.     /*
  4213.      * Special key codes have to be translated to be able to make sense
  4214.      * when they are read back.
  4215.      */
  4216.     if (c == K_SPECIAL && what != 2)
  4217.     {
  4218.         modifiers = 0x0;
  4219.         if (str[1] == KS_MODIFIER)
  4220.         {
  4221.         modifiers = str[2];
  4222.         str += 3;
  4223.         c = *str;
  4224.         }
  4225.         if (c == K_SPECIAL)
  4226.         {
  4227.         c = TO_SPECIAL(str[1], str[2]);
  4228.         str += 2;
  4229.         }
  4230.         if (IS_SPECIAL(c) || modifiers)    /* special key */
  4231.         {
  4232.         if (fprintf(fd, (char *)get_special_key_name(c, modifiers)) < 0)
  4233.             return FAIL;
  4234.         continue;
  4235.         }
  4236.     }
  4237.  
  4238.     /*
  4239.      * A '\n' in a map command should be written as <NL>.
  4240.      * A '\n' in a set command should be written as \^V^J.
  4241.      */
  4242.     if (c == NL)
  4243.     {
  4244.         if (what == 2)
  4245.         {
  4246.         if (fprintf(fd, IF_EB("\\\026\n", "\\" CTRL_V_STR "\n")) < 0)
  4247.             return FAIL;
  4248.         }
  4249.         else
  4250.         {
  4251.         if (fprintf(fd, "<NL>") < 0)
  4252.             return FAIL;
  4253.         }
  4254.         continue;
  4255.     }
  4256.  
  4257.     /*
  4258.      * Some characters have to be escaped with CTRL-V to
  4259.      * prevent them from misinterpreted in DoOneCmd().
  4260.      * A space, Tab and '"' has to be escaped with a backslash to
  4261.      * prevent it to be misinterpreted in do_set().
  4262.      * A space has to be escaped with a CTRL-V when it's at the start of a
  4263.      * ":map" rhs.
  4264.      * A '<' has to be escaped with a CTRL-V to prevent it being
  4265.      * interpreted as the start of a special key name.
  4266.      * A space in the lhs of a :map needs a CTRL-V.
  4267.      */
  4268.     if (what == 2 && (vim_iswhite(c) || c == '"' || c == '\\'))
  4269.     {
  4270.         if (putc('\\', fd) < 0)
  4271.         return FAIL;
  4272.     }
  4273.     else if (c < ' ' || c > '~' || c == '|'
  4274.         || (what == 0 && c == ' ')
  4275.         || (what == 1 && str == strstart && c == ' ')
  4276.         || (what != 2 && c == '<'))
  4277.     {
  4278.         if (putc(Ctrl_V, fd) < 0)
  4279.         return FAIL;
  4280.     }
  4281.     if (putc(c, fd) < 0)
  4282.         return FAIL;
  4283.     }
  4284.     return OK;
  4285. }
  4286.  
  4287. /*
  4288.  * Check all mappings for the presence of special key codes.
  4289.  * Used after ":set term=xxx".
  4290.  */
  4291.     void
  4292. check_map_keycodes()
  4293. {
  4294.     mapblock_T    *mp;
  4295.     char_u    *p;
  4296.     int        i;
  4297.     char_u    buf[3];
  4298.     char_u    *save_name;
  4299.     int        abbr;
  4300.     int        hash;
  4301. #ifdef FEAT_LOCALMAP
  4302.     buf_T    *bp;
  4303. #endif
  4304.  
  4305.     validate_maphash();
  4306.     save_name = sourcing_name;
  4307.     sourcing_name = (char_u *)"mappings"; /* avoids giving error messages */
  4308.  
  4309. #ifdef FEAT_LOCALMAP
  4310.     /* This this once for each buffer, and then once for global
  4311.      * mappings/abbreviations with bp == NULL */
  4312.     for (bp = firstbuf; ; bp = bp->b_next)
  4313.     {
  4314. #endif
  4315.     /*
  4316.      * Do the loop twice: Once for mappings, once for abbreviations.
  4317.      * Then loop over all map hash lists.
  4318.      */
  4319.     for (abbr = 0; abbr <= 1; ++abbr)
  4320.         for (hash = 0; hash < 256; ++hash)
  4321.         {
  4322.         if (abbr)
  4323.         {
  4324.             if (hash)        /* there is only one abbr list */
  4325.             break;
  4326. #ifdef FEAT_LOCALMAP
  4327.             if (bp != NULL)
  4328.             mp = bp->b_first_abbr;
  4329.             else
  4330. #endif
  4331.             mp = first_abbr;
  4332.         }
  4333.         else
  4334.         {
  4335. #ifdef FEAT_LOCALMAP
  4336.             if (bp != NULL)
  4337.             mp = bp->b_maphash[hash];
  4338.             else
  4339. #endif
  4340.             mp = maphash[hash];
  4341.         }
  4342.         for ( ; mp != NULL; mp = mp->m_next)
  4343.         {
  4344.             for (i = 0; i <= 1; ++i)    /* do this twice */
  4345.             {
  4346.             if (i == 0)
  4347.                 p = mp->m_keys;    /* once for the "from" part */
  4348.             else
  4349.                 p = mp->m_str;    /* and once for the "to" part */
  4350.             while (*p)
  4351.             {
  4352.                 if (*p == K_SPECIAL)
  4353.                 {
  4354.                 ++p;
  4355.                 if (*p < 128)   /* for "normal" tcap entries */
  4356.                 {
  4357.                     buf[0] = p[0];
  4358.                     buf[1] = p[1];
  4359.                     buf[2] = NUL;
  4360.                     (void)add_termcap_entry(buf, FALSE);
  4361.                 }
  4362.                 ++p;
  4363.                 }
  4364.                 ++p;
  4365.             }
  4366.             }
  4367.         }
  4368.         }
  4369. #ifdef FEAT_LOCALMAP
  4370.     if (bp == NULL)
  4371.         break;
  4372.     }
  4373. #endif
  4374.     sourcing_name = save_name;
  4375. }
  4376.  
  4377. #ifdef FEAT_EVAL
  4378. /*
  4379.  * Check the string "keys" against the lhs of all mappings
  4380.  * Return pointer to rhs of mapping (mapblock->m_str)
  4381.  * NULL otherwise
  4382.  */
  4383.     char_u *
  4384. check_map(keys, mode, exact)
  4385.     char_u    *keys;
  4386.     int        mode;
  4387.     int        exact;        /* require exact match */
  4388. {
  4389.     int        hash;
  4390.     int        len, minlen;
  4391.     mapblock_T    *mp;
  4392. #ifdef FEAT_LOCALMAP
  4393.     int        local;
  4394. #endif
  4395.  
  4396.     validate_maphash();
  4397.  
  4398.     len = (int)STRLEN(keys);
  4399. #ifdef FEAT_LOCALMAP
  4400.     for (local = 1; local >= 0; --local)
  4401. #endif
  4402.     /* loop over all hash lists */
  4403.     for (hash = 0; hash < 256; ++hash)
  4404.     {
  4405. #ifdef FEAT_LOCALMAP
  4406.         if (local)
  4407.         mp = curbuf->b_maphash[hash];
  4408.         else
  4409. #endif
  4410.         mp = maphash[hash];
  4411.         for ( ; mp != NULL; mp = mp->m_next)
  4412.         {
  4413.         /* skip entries with wrong mode, wrong length and not matching
  4414.          * ones */
  4415.         if (mp->m_keylen < len)
  4416.             minlen = mp->m_keylen;
  4417.         else
  4418.             minlen = len;
  4419.         if ((mp->m_mode & mode)
  4420.             && (!exact || mp->m_keylen == len)
  4421.             && STRNCMP(mp->m_keys, keys, minlen) == 0)
  4422.             return mp->m_str;
  4423.         }
  4424.     }
  4425.  
  4426.     return NULL;
  4427. }
  4428. #endif
  4429.  
  4430. /*
  4431.  * Default mappings for some often used keys.
  4432.  */
  4433. static struct initmap
  4434. {
  4435.     char_u    *arg;
  4436.     int        mode;
  4437. } initmappings[] =
  4438. {
  4439. #if defined(MSDOS) || defined(MSWIN) || defined(OS2)
  4440.     /* Use the Windows (CUA) keybindings. */
  4441. # ifdef FEAT_GUI
  4442.     {(char_u *)"<C-PageUp> H", NORMAL+VISUAL},
  4443.     {(char_u *)"<C-PageUp> <C-O>H",INSERT},
  4444.     {(char_u *)"<C-PageDown> L$", NORMAL+VISUAL},
  4445.     {(char_u *)"<C-PageDown> <C-O>L<C-O>$", INSERT},
  4446.  
  4447.     /* paste, copy and cut */
  4448.     {(char_u *)"<S-Insert> \"*P", NORMAL},
  4449.     {(char_u *)"<S-Insert> \"-d\"*P", VISUAL},
  4450.     {(char_u *)"<S-Insert> <C-R><C-O>*", INSERT+CMDLINE},
  4451.     {(char_u *)"<C-Insert> \"*y", VISUAL},
  4452.     {(char_u *)"<S-Del> \"*d", VISUAL},
  4453.     {(char_u *)"<C-Del> \"*d", VISUAL},
  4454.     {(char_u *)"<C-X> \"*d", VISUAL},
  4455.     /* Missing: CTRL-C (cancel) and CTRL-V (block selection) */
  4456. # else
  4457.     {(char_u *)"\316\204 H", NORMAL+VISUAL},    /* CTRL-PageUp is "H" */
  4458.     {(char_u *)"\316\204 \017H",INSERT},        /* CTRL-PageUp is "^OH"*/
  4459.     {(char_u *)"\316v L$", NORMAL+VISUAL},        /* CTRL-PageDown is "L$" */
  4460.     {(char_u *)"\316v \017L\017$", INSERT},        /* CTRL-PageDown ="^OL^O$"*/
  4461.     {(char_u *)"\316w <C-Home>", NORMAL+VISUAL},
  4462.     {(char_u *)"\316w <C-Home>", INSERT+CMDLINE},
  4463.     {(char_u *)"\316u <C-End>", NORMAL+VISUAL},
  4464.     {(char_u *)"\316u <C-End>", INSERT+CMDLINE},
  4465.  
  4466.     /* paste, copy and cut */
  4467. #  ifdef FEAT_CLIPBOARD
  4468. #   ifdef DJGPP
  4469.     {(char_u *)"\316\122 \"*P", NORMAL},        /* SHIFT-Insert is "*P */
  4470.     {(char_u *)"\316\122 \"-d\"*P", VISUAL},    /* SHIFT-Insert is "-d"*P */
  4471.     {(char_u *)"\316\122 \022\017*", INSERT},  /* SHIFT-Insert is ^R^O* */
  4472.     {(char_u *)"\316\222 \"*y", VISUAL},        /* CTRL-Insert is "*y */
  4473. #    if 0 /* Shift-Del produces the same code as Del */
  4474.     {(char_u *)"\316\123 \"*d", VISUAL},        /* SHIFT-Del is "*d */
  4475. #    endif
  4476.     {(char_u *)"\316\223 \"*d", VISUAL},        /* CTRL-Del is "*d */
  4477.     {(char_u *)"\030 \"-d", VISUAL},        /* CTRL-X is "-d */
  4478. #   else
  4479.     {(char_u *)"\316\324 \"*P", NORMAL},        /* SHIFT-Insert is "*P */
  4480.     {(char_u *)"\316\324 \"-d\"*P", VISUAL},    /* SHIFT-Insert is "-d"*P */
  4481.     {(char_u *)"\316\324 \022\017*", INSERT},  /* SHIFT-Insert is ^R^O* */
  4482.     {(char_u *)"\316\325 \"*y", VISUAL},        /* CTRL-Insert is "*y */
  4483.     {(char_u *)"\316\327 \"*d", VISUAL},        /* SHIFT-Del is "*d */
  4484.     {(char_u *)"\316\330 \"*d", VISUAL},        /* CTRL-Del is "*d */
  4485.     {(char_u *)"\030 \"-d", VISUAL},        /* CTRL-X is "-d */
  4486. #   endif
  4487. #  else
  4488.     {(char_u *)"\316\324 P", NORMAL},        /* SHIFT-Insert is P */
  4489.     {(char_u *)"\316\324 \"-dP", VISUAL},        /* SHIFT-Insert is "-dP */
  4490.     {(char_u *)"\316\324 \022\017\"", INSERT}, /* SHIFT-Insert is ^R^O" */
  4491.     {(char_u *)"\316\325 y", VISUAL},        /* CTRL-Insert is y */
  4492.     {(char_u *)"\316\327 d", VISUAL},        /* SHIFT-Del is d */
  4493.     {(char_u *)"\316\330 d", VISUAL},        /* CTRL-Del is d */
  4494. #  endif
  4495. # endif
  4496. #endif
  4497.  
  4498. #if defined(MACOS)
  4499.     /* Use the Standard MacOS binding. */
  4500.     /* paste, copy and cut */
  4501.     {(char_u *)"<D-v> \"*P", NORMAL},
  4502.     {(char_u *)"<D-v> \"-d\"*P", VISUAL},
  4503.     {(char_u *)"<D-v> <C-R>*", INSERT+CMDLINE},
  4504.     {(char_u *)"<D-c> \"*y", VISUAL},
  4505.     {(char_u *)"<D-x> \"*d", VISUAL},
  4506.     {(char_u *)"<Backspace> \"-d", VISUAL},
  4507. #endif
  4508.  
  4509.     /* Map extra keys to their normal equivalents. */
  4510.     {(char_u *)"<xF1> <F1>", NORMAL+VISUAL+OP_PENDING},
  4511.     {(char_u *)"<xF1> <F1>", INSERT+CMDLINE},
  4512.     {(char_u *)"<xF2> <F2>", NORMAL+VISUAL+OP_PENDING},
  4513.     {(char_u *)"<xF2> <F2>", INSERT+CMDLINE},
  4514.     {(char_u *)"<xF3> <F3>", NORMAL+VISUAL+OP_PENDING},
  4515.     {(char_u *)"<xF3> <F3>", INSERT+CMDLINE},
  4516.     {(char_u *)"<xF4> <F4>", NORMAL+VISUAL+OP_PENDING},
  4517.     {(char_u *)"<xF4> <F4>", INSERT+CMDLINE},
  4518.     {(char_u *)"<S-xF1> <S-F1>", NORMAL+VISUAL+OP_PENDING},
  4519.     {(char_u *)"<S-xF1> <S-F1>", INSERT+CMDLINE},
  4520.     {(char_u *)"<S-xF2> <S-F2>", NORMAL+VISUAL+OP_PENDING},
  4521.     {(char_u *)"<S-xF2> <S-F2>", INSERT+CMDLINE},
  4522.     {(char_u *)"<S-xF3> <S-F3>", NORMAL+VISUAL+OP_PENDING},
  4523.     {(char_u *)"<S-xF3> <S-F3>", INSERT+CMDLINE},
  4524.     {(char_u *)"<S-xF4> <S-F4>", NORMAL+VISUAL+OP_PENDING},
  4525.     {(char_u *)"<S-xF4> <S-F4>", INSERT+CMDLINE},
  4526.     {(char_u *)"<xEND> <END>", NORMAL+VISUAL+OP_PENDING},
  4527.     {(char_u *)"<xEND> <END>", INSERT+CMDLINE},
  4528.     {(char_u *)"<xHOME> <HOME>", NORMAL+VISUAL+OP_PENDING},
  4529.     {(char_u *)"<xHOME> <HOME>", INSERT+CMDLINE},
  4530. };
  4531.  
  4532. /*
  4533.  * Set up default mappings.
  4534.  */
  4535.     void
  4536. init_mappings()
  4537. {
  4538.     int        i;
  4539.  
  4540.     for (i = 0; i < sizeof(initmappings) / sizeof(struct initmap); ++i)
  4541.     add_map(initmappings[i].arg, initmappings[i].mode);
  4542. }
  4543.  
  4544. /*
  4545.  * Add a mapping "map" for mode "mode".
  4546.  * Need to put string in allocated memory, because do_map() will modify it.
  4547.  */
  4548.     void
  4549. add_map(map, mode)
  4550.     char_u    *map;
  4551.     int        mode;
  4552. {
  4553.     char_u    *s;
  4554.     char_u    *cpo_save = p_cpo;
  4555.  
  4556.     p_cpo = (char_u *)"";    /* Allow <> notation */
  4557.     s = vim_strsave(map);
  4558.     if (s != NULL)
  4559.     {
  4560.     (void)do_map(0, s, mode, FALSE);
  4561.     vim_free(s);
  4562.     }
  4563.     p_cpo = cpo_save;
  4564. }
  4565.