xref: /vim-8.2.3635/src/ex_getln.c (revision 2bf24176)
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  * ex_getln.c: Functions for entering and editing an Ex command line.
12  */
13 
14 #include "vim.h"
15 
16 /*
17  * Variables shared between getcmdline(), redrawcmdline() and others.
18  * These need to be saved when using CTRL-R |, that's why they are in a
19  * structure.
20  */
21 struct cmdline_info
22 {
23     char_u	*cmdbuff;	/* pointer to command line buffer */
24     int		cmdbufflen;	/* length of cmdbuff */
25     int		cmdlen;		/* number of chars in command line */
26     int		cmdpos;		/* current cursor position */
27     int		cmdspos;	/* cursor column on screen */
28     int		cmdfirstc;	/* ':', '/', '?', '=', '>' or NUL */
29     int		cmdindent;	/* number of spaces before cmdline */
30     char_u	*cmdprompt;	/* message in front of cmdline */
31     int		cmdattr;	/* attributes for prompt */
32     int		overstrike;	/* Typing mode on the command line.  Shared by
33 				   getcmdline() and put_on_cmdline(). */
34     expand_T	*xpc;		/* struct being used for expansion, xp_pattern
35 				   may point into cmdbuff */
36     int		xp_context;	/* type of expansion */
37 # ifdef FEAT_EVAL
38     char_u	*xp_arg;	/* user-defined expansion arg */
39     int		input_fn;	/* when TRUE Invoked for input() function */
40 # endif
41 };
42 
43 /* The current cmdline_info.  It is initialized in getcmdline() and after that
44  * used by other functions.  When invoking getcmdline() recursively it needs
45  * to be saved with save_cmdline() and restored with restore_cmdline().
46  * TODO: make it local to getcmdline() and pass it around. */
47 static struct cmdline_info ccline;
48 
49 static int	cmd_showtail;		/* Only show path tail in lists ? */
50 
51 #ifdef FEAT_EVAL
52 static int	new_cmdpos;	/* position set by set_cmdline_pos() */
53 #endif
54 
55 #ifdef FEAT_CMDHIST
56 typedef struct hist_entry
57 {
58     int		hisnum;		/* identifying number */
59     int		viminfo;	/* when TRUE hisstr comes from viminfo */
60     char_u	*hisstr;	/* actual entry, separator char after the NUL */
61 } histentry_T;
62 
63 static histentry_T *(history[HIST_COUNT]) = {NULL, NULL, NULL, NULL, NULL};
64 static int	hisidx[HIST_COUNT] = {-1, -1, -1, -1, -1};  /* lastused entry */
65 static int	hisnum[HIST_COUNT] = {0, 0, 0, 0, 0};
66 		    /* identifying (unique) number of newest history entry */
67 static int	hislen = 0;		/* actual length of history tables */
68 
69 static int	hist_char2type __ARGS((int c));
70 
71 static int	in_history __ARGS((int, char_u *, int, int, int));
72 # ifdef FEAT_EVAL
73 static int	calc_hist_idx __ARGS((int histype, int num));
74 # endif
75 #endif
76 
77 #ifdef FEAT_RIGHTLEFT
78 static int	cmd_hkmap = 0;	/* Hebrew mapping during command line */
79 #endif
80 
81 #ifdef FEAT_FKMAP
82 static int	cmd_fkmap = 0;	/* Farsi mapping during command line */
83 #endif
84 
85 static int	cmdline_charsize __ARGS((int idx));
86 static void	set_cmdspos __ARGS((void));
87 static void	set_cmdspos_cursor __ARGS((void));
88 #ifdef FEAT_MBYTE
89 static void	correct_cmdspos __ARGS((int idx, int cells));
90 #endif
91 static void	alloc_cmdbuff __ARGS((int len));
92 static int	realloc_cmdbuff __ARGS((int len));
93 static void	draw_cmdline __ARGS((int start, int len));
94 static void	save_cmdline __ARGS((struct cmdline_info *ccp));
95 static void	restore_cmdline __ARGS((struct cmdline_info *ccp));
96 static int	cmdline_paste __ARGS((int regname, int literally, int remcr));
97 #if defined(FEAT_XIM) && defined(FEAT_GUI_GTK)
98 static void	redrawcmd_preedit __ARGS((void));
99 #endif
100 #ifdef FEAT_WILDMENU
101 static void	cmdline_del __ARGS((int from));
102 #endif
103 static void	redrawcmdprompt __ARGS((void));
104 static void	cursorcmd __ARGS((void));
105 static int	ccheck_abbr __ARGS((int));
106 static int	nextwild __ARGS((expand_T *xp, int type, int options, int escape));
107 static void	escape_fname __ARGS((char_u **pp));
108 static int	showmatches __ARGS((expand_T *xp, int wildmenu));
109 static void	set_expand_context __ARGS((expand_T *xp));
110 static int	ExpandFromContext __ARGS((expand_T *xp, char_u *, int *, char_u ***, int));
111 static int	expand_showtail __ARGS((expand_T *xp));
112 #ifdef FEAT_CMDL_COMPL
113 static int	expand_shellcmd __ARGS((char_u *filepat, int *num_file, char_u ***file, int flagsarg));
114 static int	ExpandRTDir __ARGS((char_u *pat, int *num_file, char_u ***file, char *dirname[]));
115 # ifdef FEAT_CMDHIST
116 static char_u	*get_history_arg __ARGS((expand_T *xp, int idx));
117 # endif
118 # if defined(FEAT_USR_CMDS) && defined(FEAT_EVAL)
119 static int	ExpandUserDefined __ARGS((expand_T *xp, regmatch_T *regmatch, int *num_file, char_u ***file));
120 static int	ExpandUserList __ARGS((expand_T *xp, int *num_file, char_u ***file));
121 # endif
122 #endif
123 #ifdef FEAT_CMDHIST
124 static void	clear_hist_entry __ARGS((histentry_T *hisptr));
125 #endif
126 
127 #ifdef FEAT_CMDWIN
128 static int	ex_window __ARGS((void));
129 #endif
130 
131 #if defined(FEAT_CMDL_COMPL) || defined(PROTO)
132 static int
133 #ifdef __BORLANDC__
134 _RTLENTRYF
135 #endif
136 sort_func_compare __ARGS((const void *s1, const void *s2));
137 #endif
138 
139 /*
140  * getcmdline() - accept a command line starting with firstc.
141  *
142  * firstc == ':'	    get ":" command line.
143  * firstc == '/' or '?'	    get search pattern
144  * firstc == '='	    get expression
145  * firstc == '@'	    get text for input() function
146  * firstc == '>'	    get text for debug mode
147  * firstc == NUL	    get text for :insert command
148  * firstc == -1		    like NUL, and break on CTRL-C
149  *
150  * The line is collected in ccline.cmdbuff, which is reallocated to fit the
151  * command line.
152  *
153  * Careful: getcmdline() can be called recursively!
154  *
155  * Return pointer to allocated string if there is a commandline, NULL
156  * otherwise.
157  */
158     char_u *
159 getcmdline(firstc, count, indent)
160     int		firstc;
161     long	count UNUSED;	/* only used for incremental search */
162     int		indent;		/* indent for inside conditionals */
163 {
164     int		c;
165     int		i;
166     int		j;
167     int		gotesc = FALSE;		/* TRUE when <ESC> just typed */
168     int		do_abbr;		/* when TRUE check for abbr. */
169 #ifdef FEAT_CMDHIST
170     char_u	*lookfor = NULL;	/* string to match */
171     int		hiscnt;			/* current history line in use */
172     int		histype;		/* history type to be used */
173 #endif
174 #ifdef FEAT_SEARCH_EXTRA
175     pos_T	old_cursor;
176     colnr_T	old_curswant;
177     colnr_T	old_leftcol;
178     linenr_T	old_topline;
179 # ifdef FEAT_DIFF
180     int		old_topfill;
181 # endif
182     linenr_T	old_botline;
183     int		did_incsearch = FALSE;
184     int		incsearch_postponed = FALSE;
185 #endif
186     int		did_wild_list = FALSE;	/* did wild_list() recently */
187     int		wim_index = 0;		/* index in wim_flags[] */
188     int		res;
189     int		save_msg_scroll = msg_scroll;
190     int		save_State = State;	/* remember State when called */
191     int		some_key_typed = FALSE;	/* one of the keys was typed */
192 #ifdef FEAT_MOUSE
193     /* mouse drag and release events are ignored, unless they are
194      * preceded with a mouse down event */
195     int		ignore_drag_release = TRUE;
196 #endif
197 #ifdef FEAT_EVAL
198     int		break_ctrl_c = FALSE;
199 #endif
200     expand_T	xpc;
201     long	*b_im_ptr = NULL;
202 #if defined(FEAT_WILDMENU) || defined(FEAT_EVAL) || defined(FEAT_SEARCH_EXTRA)
203     /* Everything that may work recursively should save and restore the
204      * current command line in save_ccline.  That includes update_screen(), a
205      * custom status line may invoke ":normal". */
206     struct cmdline_info save_ccline;
207 #endif
208 
209 #ifdef FEAT_SNIFF
210     want_sniff_request = 0;
211 #endif
212 #ifdef FEAT_EVAL
213     if (firstc == -1)
214     {
215 	firstc = NUL;
216 	break_ctrl_c = TRUE;
217     }
218 #endif
219 #ifdef FEAT_RIGHTLEFT
220     /* start without Hebrew mapping for a command line */
221     if (firstc == ':' || firstc == '=' || firstc == '>')
222 	cmd_hkmap = 0;
223 #endif
224 
225     ccline.overstrike = FALSE;		    /* always start in insert mode */
226 #ifdef FEAT_SEARCH_EXTRA
227     old_cursor = curwin->w_cursor;	    /* needs to be restored later */
228     old_curswant = curwin->w_curswant;
229     old_leftcol = curwin->w_leftcol;
230     old_topline = curwin->w_topline;
231 # ifdef FEAT_DIFF
232     old_topfill = curwin->w_topfill;
233 # endif
234     old_botline = curwin->w_botline;
235 #endif
236 
237     /*
238      * set some variables for redrawcmd()
239      */
240     ccline.cmdfirstc = (firstc == '@' ? 0 : firstc);
241     ccline.cmdindent = (firstc > 0 ? indent : 0);
242 
243     /* alloc initial ccline.cmdbuff */
244     alloc_cmdbuff(exmode_active ? 250 : indent + 1);
245     if (ccline.cmdbuff == NULL)
246 	return NULL;			    /* out of memory */
247     ccline.cmdlen = ccline.cmdpos = 0;
248     ccline.cmdbuff[0] = NUL;
249 
250     /* autoindent for :insert and :append */
251     if (firstc <= 0)
252     {
253 	vim_memset(ccline.cmdbuff, ' ', indent);
254 	ccline.cmdbuff[indent] = NUL;
255 	ccline.cmdpos = indent;
256 	ccline.cmdspos = indent;
257 	ccline.cmdlen = indent;
258     }
259 
260     ExpandInit(&xpc);
261     ccline.xpc = &xpc;
262 
263 #ifdef FEAT_RIGHTLEFT
264     if (curwin->w_p_rl && *curwin->w_p_rlc == 's'
265 					  && (firstc == '/' || firstc == '?'))
266 	cmdmsg_rl = TRUE;
267     else
268 	cmdmsg_rl = FALSE;
269 #endif
270 
271     redir_off = TRUE;		/* don't redirect the typed command */
272     if (!cmd_silent)
273     {
274 	i = msg_scrolled;
275 	msg_scrolled = 0;		/* avoid wait_return message */
276 	gotocmdline(TRUE);
277 	msg_scrolled += i;
278 	redrawcmdprompt();		/* draw prompt or indent */
279 	set_cmdspos();
280     }
281     xpc.xp_context = EXPAND_NOTHING;
282     xpc.xp_backslash = XP_BS_NONE;
283 #ifndef BACKSLASH_IN_FILENAME
284     xpc.xp_shell = FALSE;
285 #endif
286 
287 #if defined(FEAT_EVAL)
288     if (ccline.input_fn)
289     {
290 	xpc.xp_context = ccline.xp_context;
291 	xpc.xp_pattern = ccline.cmdbuff;
292 # if defined(FEAT_USR_CMDS) && defined(FEAT_CMDL_COMPL)
293 	xpc.xp_arg = ccline.xp_arg;
294 # endif
295     }
296 #endif
297 
298     /*
299      * Avoid scrolling when called by a recursive do_cmdline(), e.g. when
300      * doing ":@0" when register 0 doesn't contain a CR.
301      */
302     msg_scroll = FALSE;
303 
304     State = CMDLINE;
305 
306     if (firstc == '/' || firstc == '?' || firstc == '@')
307     {
308 	/* Use ":lmap" mappings for search pattern and input(). */
309 	if (curbuf->b_p_imsearch == B_IMODE_USE_INSERT)
310 	    b_im_ptr = &curbuf->b_p_iminsert;
311 	else
312 	    b_im_ptr = &curbuf->b_p_imsearch;
313 	if (*b_im_ptr == B_IMODE_LMAP)
314 	    State |= LANGMAP;
315 #ifdef USE_IM_CONTROL
316 	im_set_active(*b_im_ptr == B_IMODE_IM);
317 #endif
318     }
319 #ifdef USE_IM_CONTROL
320     else if (p_imcmdline)
321 	im_set_active(TRUE);
322 #endif
323 
324 #ifdef FEAT_MOUSE
325     setmouse();
326 #endif
327 #ifdef CURSOR_SHAPE
328     ui_cursor_shape();		/* may show different cursor shape */
329 #endif
330 
331     /* When inside an autocommand for writing "exiting" may be set and
332      * terminal mode set to cooked.  Need to set raw mode here then. */
333     settmode(TMODE_RAW);
334 
335 #ifdef FEAT_CMDHIST
336     init_history();
337     hiscnt = hislen;		/* set hiscnt to impossible history value */
338     histype = hist_char2type(firstc);
339 #endif
340 
341 #ifdef FEAT_DIGRAPHS
342     do_digraph(-1);		/* init digraph typeahead */
343 #endif
344 
345     /* If something above caused an error, reset the flags, we do want to type
346      * and execute commands. Display may be messed up a bit. */
347     if (did_emsg)
348 	redrawcmd();
349     did_emsg = FALSE;
350     got_int = FALSE;
351 
352     /*
353      * Collect the command string, handling editing keys.
354      */
355     for (;;)
356     {
357 	redir_off = TRUE;	/* Don't redirect the typed command.
358 				   Repeated, because a ":redir" inside
359 				   completion may switch it on. */
360 #ifdef USE_ON_FLY_SCROLL
361 	dont_scroll = FALSE;	/* allow scrolling here */
362 #endif
363 	quit_more = FALSE;	/* reset after CTRL-D which had a more-prompt */
364 
365 	cursorcmd();		/* set the cursor on the right spot */
366 
367 	/* Get a character.  Ignore K_IGNORE, it should not do anything, such
368 	 * as stop completion. */
369 	do
370 	{
371 	    c = safe_vgetc();
372 	} while (c == K_IGNORE);
373 
374 	if (KeyTyped)
375 	{
376 	    some_key_typed = TRUE;
377 #ifdef FEAT_RIGHTLEFT
378 	    if (cmd_hkmap)
379 		c = hkmap(c);
380 # ifdef FEAT_FKMAP
381 	    if (cmd_fkmap)
382 		c = cmdl_fkmap(c);
383 # endif
384 	    if (cmdmsg_rl && !KeyStuffed)
385 	    {
386 		/* Invert horizontal movements and operations.  Only when
387 		 * typed by the user directly, not when the result of a
388 		 * mapping. */
389 		switch (c)
390 		{
391 		    case K_RIGHT:   c = K_LEFT; break;
392 		    case K_S_RIGHT: c = K_S_LEFT; break;
393 		    case K_C_RIGHT: c = K_C_LEFT; break;
394 		    case K_LEFT:    c = K_RIGHT; break;
395 		    case K_S_LEFT:  c = K_S_RIGHT; break;
396 		    case K_C_LEFT:  c = K_C_RIGHT; break;
397 		}
398 	    }
399 #endif
400 	}
401 
402 	/*
403 	 * Ignore got_int when CTRL-C was typed here.
404 	 * Don't ignore it in :global, we really need to break then, e.g., for
405 	 * ":g/pat/normal /pat" (without the <CR>).
406 	 * Don't ignore it for the input() function.
407 	 */
408 	if ((c == Ctrl_C
409 #ifdef UNIX
410 		|| c == intr_char
411 #endif
412 				)
413 #if defined(FEAT_EVAL) || defined(FEAT_CRYPT)
414 		&& firstc != '@'
415 #endif
416 #ifdef FEAT_EVAL
417 		&& !break_ctrl_c
418 #endif
419 		&& !global_busy)
420 	    got_int = FALSE;
421 
422 #ifdef FEAT_CMDHIST
423 	/* free old command line when finished moving around in the history
424 	 * list */
425 	if (lookfor != NULL
426 		&& c != K_S_DOWN && c != K_S_UP
427 		&& c != K_DOWN && c != K_UP
428 		&& c != K_PAGEDOWN && c != K_PAGEUP
429 		&& c != K_KPAGEDOWN && c != K_KPAGEUP
430 		&& c != K_LEFT && c != K_RIGHT
431 		&& (xpc.xp_numfiles > 0 || (c != Ctrl_P && c != Ctrl_N)))
432 	{
433 	    vim_free(lookfor);
434 	    lookfor = NULL;
435 	}
436 #endif
437 
438 	/*
439 	 * When there are matching completions to select <S-Tab> works like
440 	 * CTRL-P (unless 'wc' is <S-Tab>).
441 	 */
442 	if (c != p_wc && c == K_S_TAB && xpc.xp_numfiles > 0)
443 	    c = Ctrl_P;
444 
445 #ifdef FEAT_WILDMENU
446 	/* Special translations for 'wildmenu' */
447 	if (did_wild_list && p_wmnu)
448 	{
449 	    if (c == K_LEFT)
450 		c = Ctrl_P;
451 	    else if (c == K_RIGHT)
452 		c = Ctrl_N;
453 	}
454 	/* Hitting CR after "emenu Name.": complete submenu */
455 	if (xpc.xp_context == EXPAND_MENUNAMES && p_wmnu
456 		&& ccline.cmdpos > 1
457 		&& ccline.cmdbuff[ccline.cmdpos - 1] == '.'
458 		&& ccline.cmdbuff[ccline.cmdpos - 2] != '\\'
459 		&& (c == '\n' || c == '\r' || c == K_KENTER))
460 	    c = K_DOWN;
461 #endif
462 
463 	/* free expanded names when finished walking through matches */
464 	if (xpc.xp_numfiles != -1
465 		&& !(c == p_wc && KeyTyped) && c != p_wcm
466 		&& c != Ctrl_N && c != Ctrl_P && c != Ctrl_A
467 		&& c != Ctrl_L)
468 	{
469 	    (void)ExpandOne(&xpc, NULL, NULL, 0, WILD_FREE);
470 	    did_wild_list = FALSE;
471 #ifdef FEAT_WILDMENU
472 	    if (!p_wmnu || (c != K_UP && c != K_DOWN))
473 #endif
474 		xpc.xp_context = EXPAND_NOTHING;
475 	    wim_index = 0;
476 #ifdef FEAT_WILDMENU
477 	    if (p_wmnu && wild_menu_showing != 0)
478 	    {
479 		int skt = KeyTyped;
480 		int old_RedrawingDisabled = RedrawingDisabled;
481 
482 		if (ccline.input_fn)
483 		    RedrawingDisabled = 0;
484 
485 		if (wild_menu_showing == WM_SCROLLED)
486 		{
487 		    /* Entered command line, move it up */
488 		    cmdline_row--;
489 		    redrawcmd();
490 		}
491 		else if (save_p_ls != -1)
492 		{
493 		    /* restore 'laststatus' and 'winminheight' */
494 		    p_ls = save_p_ls;
495 		    p_wmh = save_p_wmh;
496 		    last_status(FALSE);
497 		    save_cmdline(&save_ccline);
498 		    update_screen(VALID);	/* redraw the screen NOW */
499 		    restore_cmdline(&save_ccline);
500 		    redrawcmd();
501 		    save_p_ls = -1;
502 		}
503 		else
504 		{
505 # ifdef FEAT_VERTSPLIT
506 		    win_redraw_last_status(topframe);
507 # else
508 		    lastwin->w_redr_status = TRUE;
509 # endif
510 		    redraw_statuslines();
511 		}
512 		KeyTyped = skt;
513 		wild_menu_showing = 0;
514 		if (ccline.input_fn)
515 		    RedrawingDisabled = old_RedrawingDisabled;
516 	    }
517 #endif
518 	}
519 
520 #ifdef FEAT_WILDMENU
521 	/* Special translations for 'wildmenu' */
522 	if (xpc.xp_context == EXPAND_MENUNAMES && p_wmnu)
523 	{
524 	    /* Hitting <Down> after "emenu Name.": complete submenu */
525 	    if (c == K_DOWN && ccline.cmdpos > 0
526 				  && ccline.cmdbuff[ccline.cmdpos - 1] == '.')
527 		c = p_wc;
528 	    else if (c == K_UP)
529 	    {
530 		/* Hitting <Up>: Remove one submenu name in front of the
531 		 * cursor */
532 		int found = FALSE;
533 
534 		j = (int)(xpc.xp_pattern - ccline.cmdbuff);
535 		i = 0;
536 		while (--j > 0)
537 		{
538 		    /* check for start of menu name */
539 		    if (ccline.cmdbuff[j] == ' '
540 			    && ccline.cmdbuff[j - 1] != '\\')
541 		    {
542 			i = j + 1;
543 			break;
544 		    }
545 		    /* check for start of submenu name */
546 		    if (ccline.cmdbuff[j] == '.'
547 			    && ccline.cmdbuff[j - 1] != '\\')
548 		    {
549 			if (found)
550 			{
551 			    i = j + 1;
552 			    break;
553 			}
554 			else
555 			    found = TRUE;
556 		    }
557 		}
558 		if (i > 0)
559 		    cmdline_del(i);
560 		c = p_wc;
561 		xpc.xp_context = EXPAND_NOTHING;
562 	    }
563 	}
564 	if ((xpc.xp_context == EXPAND_FILES
565 			      || xpc.xp_context == EXPAND_DIRECTORIES
566 			      || xpc.xp_context == EXPAND_SHELLCMD) && p_wmnu)
567 	{
568 	    char_u upseg[5];
569 
570 	    upseg[0] = PATHSEP;
571 	    upseg[1] = '.';
572 	    upseg[2] = '.';
573 	    upseg[3] = PATHSEP;
574 	    upseg[4] = NUL;
575 
576 	    if (c == K_DOWN
577 		    && ccline.cmdpos > 0
578 		    && ccline.cmdbuff[ccline.cmdpos - 1] == PATHSEP
579 		    && (ccline.cmdpos < 3
580 			|| ccline.cmdbuff[ccline.cmdpos - 2] != '.'
581 			|| ccline.cmdbuff[ccline.cmdpos - 3] != '.'))
582 	    {
583 		/* go down a directory */
584 		c = p_wc;
585 	    }
586 	    else if (STRNCMP(xpc.xp_pattern, upseg + 1, 3) == 0 && c == K_DOWN)
587 	    {
588 		/* If in a direct ancestor, strip off one ../ to go down */
589 		int found = FALSE;
590 
591 		j = ccline.cmdpos;
592 		i = (int)(xpc.xp_pattern - ccline.cmdbuff);
593 		while (--j > i)
594 		{
595 #ifdef FEAT_MBYTE
596 		    if (has_mbyte)
597 			j -= (*mb_head_off)(ccline.cmdbuff, ccline.cmdbuff + j);
598 #endif
599 		    if (vim_ispathsep(ccline.cmdbuff[j]))
600 		    {
601 			found = TRUE;
602 			break;
603 		    }
604 		}
605 		if (found
606 			&& ccline.cmdbuff[j - 1] == '.'
607 			&& ccline.cmdbuff[j - 2] == '.'
608 			&& (vim_ispathsep(ccline.cmdbuff[j - 3]) || j == i + 2))
609 		{
610 		    cmdline_del(j - 2);
611 		    c = p_wc;
612 		}
613 	    }
614 	    else if (c == K_UP)
615 	    {
616 		/* go up a directory */
617 		int found = FALSE;
618 
619 		j = ccline.cmdpos - 1;
620 		i = (int)(xpc.xp_pattern - ccline.cmdbuff);
621 		while (--j > i)
622 		{
623 #ifdef FEAT_MBYTE
624 		    if (has_mbyte)
625 			j -= (*mb_head_off)(ccline.cmdbuff, ccline.cmdbuff + j);
626 #endif
627 		    if (vim_ispathsep(ccline.cmdbuff[j])
628 #ifdef BACKSLASH_IN_FILENAME
629 			    && vim_strchr(" *?[{`$%#", ccline.cmdbuff[j + 1])
630 			       == NULL
631 #endif
632 		       )
633 		    {
634 			if (found)
635 			{
636 			    i = j + 1;
637 			    break;
638 			}
639 			else
640 			    found = TRUE;
641 		    }
642 		}
643 
644 		if (!found)
645 		    j = i;
646 		else if (STRNCMP(ccline.cmdbuff + j, upseg, 4) == 0)
647 		    j += 4;
648 		else if (STRNCMP(ccline.cmdbuff + j, upseg + 1, 3) == 0
649 			     && j == i)
650 		    j += 3;
651 		else
652 		    j = 0;
653 		if (j > 0)
654 		{
655 		    /* TODO this is only for DOS/UNIX systems - need to put in
656 		     * machine-specific stuff here and in upseg init */
657 		    cmdline_del(j);
658 		    put_on_cmdline(upseg + 1, 3, FALSE);
659 		}
660 		else if (ccline.cmdpos > i)
661 		    cmdline_del(i);
662 
663 		/* Now complete in the new directory. Set KeyTyped in case the
664 		 * Up key came from a mapping. */
665 		c = p_wc;
666 		KeyTyped = TRUE;
667 	    }
668 	}
669 
670 #endif	/* FEAT_WILDMENU */
671 
672 	/* CTRL-\ CTRL-N goes to Normal mode, CTRL-\ CTRL-G goes to Insert
673 	 * mode when 'insertmode' is set, CTRL-\ e prompts for an expression. */
674 	if (c == Ctrl_BSL)
675 	{
676 	    ++no_mapping;
677 	    ++allow_keys;
678 	    c = plain_vgetc();
679 	    --no_mapping;
680 	    --allow_keys;
681 	    /* CTRL-\ e doesn't work when obtaining an expression, unless it
682 	     * is in a mapping. */
683 	    if (c != Ctrl_N && c != Ctrl_G && (c != 'e'
684 				    || (ccline.cmdfirstc == '=' && KeyTyped)))
685 	    {
686 		vungetc(c);
687 		c = Ctrl_BSL;
688 	    }
689 #ifdef FEAT_EVAL
690 	    else if (c == 'e')
691 	    {
692 		char_u	*p = NULL;
693 		int	len;
694 
695 		/*
696 		 * Replace the command line with the result of an expression.
697 		 * Need to save and restore the current command line, to be
698 		 * able to enter a new one...
699 		 */
700 		if (ccline.cmdpos == ccline.cmdlen)
701 		    new_cmdpos = 99999;	/* keep it at the end */
702 		else
703 		    new_cmdpos = ccline.cmdpos;
704 
705 		save_cmdline(&save_ccline);
706 		c = get_expr_register();
707 		restore_cmdline(&save_ccline);
708 		if (c == '=')
709 		{
710 		    /* Need to save and restore ccline.  And set "textlock"
711 		     * to avoid nasty things like going to another buffer when
712 		     * evaluating an expression. */
713 		    save_cmdline(&save_ccline);
714 		    ++textlock;
715 		    p = get_expr_line();
716 		    --textlock;
717 		    restore_cmdline(&save_ccline);
718 
719 		    if (p != NULL)
720 		    {
721 			len = (int)STRLEN(p);
722 			if (realloc_cmdbuff(len + 1) == OK)
723 			{
724 			    ccline.cmdlen = len;
725 			    STRCPY(ccline.cmdbuff, p);
726 			    vim_free(p);
727 
728 			    /* Restore the cursor or use the position set with
729 			     * set_cmdline_pos(). */
730 			    if (new_cmdpos > ccline.cmdlen)
731 				ccline.cmdpos = ccline.cmdlen;
732 			    else
733 				ccline.cmdpos = new_cmdpos;
734 
735 			    KeyTyped = FALSE;	/* Don't do p_wc completion. */
736 			    redrawcmd();
737 			    goto cmdline_changed;
738 			}
739 		    }
740 		}
741 		beep_flush();
742 		got_int = FALSE;	/* don't abandon the command line */
743 		did_emsg = FALSE;
744 		emsg_on_display = FALSE;
745 		redrawcmd();
746 		goto cmdline_not_changed;
747 	    }
748 #endif
749 	    else
750 	    {
751 		if (c == Ctrl_G && p_im && restart_edit == 0)
752 		    restart_edit = 'a';
753 		gotesc = TRUE;	/* will free ccline.cmdbuff after putting it
754 				   in history */
755 		goto returncmd;	/* back to Normal mode */
756 	    }
757 	}
758 
759 #ifdef FEAT_CMDWIN
760 	if (c == cedit_key || c == K_CMDWIN)
761 	{
762 	    if (ex_normal_busy == 0 && got_int == FALSE)
763 	    {
764 		/*
765 		 * Open a window to edit the command line (and history).
766 		 */
767 		c = ex_window();
768 		some_key_typed = TRUE;
769 	    }
770 	}
771 # ifdef FEAT_DIGRAPHS
772 	else
773 # endif
774 #endif
775 #ifdef FEAT_DIGRAPHS
776 	    c = do_digraph(c);
777 #endif
778 
779 	if (c == '\n' || c == '\r' || c == K_KENTER || (c == ESC
780 			&& (!KeyTyped || vim_strchr(p_cpo, CPO_ESC) != NULL)))
781 	{
782 	    /* In Ex mode a backslash escapes a newline. */
783 	    if (exmode_active
784 		    && c != ESC
785 		    && ccline.cmdpos == ccline.cmdlen
786 		    && ccline.cmdpos > 0
787 		    && ccline.cmdbuff[ccline.cmdpos - 1] == '\\')
788 	    {
789 		if (c == K_KENTER)
790 		    c = '\n';
791 	    }
792 	    else
793 	    {
794 		gotesc = FALSE;	/* Might have typed ESC previously, don't
795 				       truncate the cmdline now. */
796 		if (ccheck_abbr(c + ABBR_OFF))
797 		    goto cmdline_changed;
798 		if (!cmd_silent)
799 		{
800 		    windgoto(msg_row, 0);
801 		    out_flush();
802 		}
803 		break;
804 	    }
805 	}
806 
807 	/*
808 	 * Completion for 'wildchar' or 'wildcharm' key.
809 	 * - hitting <ESC> twice means: abandon command line.
810 	 * - wildcard expansion is only done when the 'wildchar' key is really
811 	 *   typed, not when it comes from a macro
812 	 */
813 	if ((c == p_wc && !gotesc && KeyTyped) || c == p_wcm)
814 	{
815 	    if (xpc.xp_numfiles > 0)   /* typed p_wc at least twice */
816 	    {
817 		/* if 'wildmode' contains "list" may still need to list */
818 		if (xpc.xp_numfiles > 1
819 			&& !did_wild_list
820 			&& (wim_flags[wim_index] & WIM_LIST))
821 		{
822 		    (void)showmatches(&xpc, FALSE);
823 		    redrawcmd();
824 		    did_wild_list = TRUE;
825 		}
826 		if (wim_flags[wim_index] & WIM_LONGEST)
827 		    res = nextwild(&xpc, WILD_LONGEST, WILD_NO_BEEP,
828 							       firstc != '@');
829 		else if (wim_flags[wim_index] & WIM_FULL)
830 		    res = nextwild(&xpc, WILD_NEXT, WILD_NO_BEEP,
831 							       firstc != '@');
832 		else
833 		    res = OK;	    /* don't insert 'wildchar' now */
834 	    }
835 	    else		    /* typed p_wc first time */
836 	    {
837 		wim_index = 0;
838 		j = ccline.cmdpos;
839 		/* if 'wildmode' first contains "longest", get longest
840 		 * common part */
841 		if (wim_flags[0] & WIM_LONGEST)
842 		    res = nextwild(&xpc, WILD_LONGEST, WILD_NO_BEEP,
843 							       firstc != '@');
844 		else
845 		    res = nextwild(&xpc, WILD_EXPAND_KEEP, WILD_NO_BEEP,
846 							       firstc != '@');
847 
848 		/* if interrupted while completing, behave like it failed */
849 		if (got_int)
850 		{
851 		    (void)vpeekc();	/* remove <C-C> from input stream */
852 		    got_int = FALSE;	/* don't abandon the command line */
853 		    (void)ExpandOne(&xpc, NULL, NULL, 0, WILD_FREE);
854 #ifdef FEAT_WILDMENU
855 		    xpc.xp_context = EXPAND_NOTHING;
856 #endif
857 		    goto cmdline_changed;
858 		}
859 
860 		/* when more than one match, and 'wildmode' first contains
861 		 * "list", or no change and 'wildmode' contains "longest,list",
862 		 * list all matches */
863 		if (res == OK && xpc.xp_numfiles > 1)
864 		{
865 		    /* a "longest" that didn't do anything is skipped (but not
866 		     * "list:longest") */
867 		    if (wim_flags[0] == WIM_LONGEST && ccline.cmdpos == j)
868 			wim_index = 1;
869 		    if ((wim_flags[wim_index] & WIM_LIST)
870 #ifdef FEAT_WILDMENU
871 			    || (p_wmnu && (wim_flags[wim_index] & WIM_FULL) != 0)
872 #endif
873 			    )
874 		    {
875 			if (!(wim_flags[0] & WIM_LONGEST))
876 			{
877 #ifdef FEAT_WILDMENU
878 			    int p_wmnu_save = p_wmnu;
879 			    p_wmnu = 0;
880 #endif
881 			    /* remove match */
882 			    nextwild(&xpc, WILD_PREV, 0, firstc != '@');
883 #ifdef FEAT_WILDMENU
884 			    p_wmnu = p_wmnu_save;
885 #endif
886 			}
887 #ifdef FEAT_WILDMENU
888 			(void)showmatches(&xpc, p_wmnu
889 				&& ((wim_flags[wim_index] & WIM_LIST) == 0));
890 #else
891 			(void)showmatches(&xpc, FALSE);
892 #endif
893 			redrawcmd();
894 			did_wild_list = TRUE;
895 			if (wim_flags[wim_index] & WIM_LONGEST)
896 			    nextwild(&xpc, WILD_LONGEST, WILD_NO_BEEP,
897 							       firstc != '@');
898 			else if (wim_flags[wim_index] & WIM_FULL)
899 			    nextwild(&xpc, WILD_NEXT, WILD_NO_BEEP,
900 							       firstc != '@');
901 		    }
902 		    else
903 			vim_beep(BO_WILD);
904 		}
905 #ifdef FEAT_WILDMENU
906 		else if (xpc.xp_numfiles == -1)
907 		    xpc.xp_context = EXPAND_NOTHING;
908 #endif
909 	    }
910 	    if (wim_index < 3)
911 		++wim_index;
912 	    if (c == ESC)
913 		gotesc = TRUE;
914 	    if (res == OK)
915 		goto cmdline_changed;
916 	}
917 
918 	gotesc = FALSE;
919 
920 	/* <S-Tab> goes to last match, in a clumsy way */
921 	if (c == K_S_TAB && KeyTyped)
922 	{
923 	    if (nextwild(&xpc, WILD_EXPAND_KEEP, 0, firstc != '@') == OK
924 		    && nextwild(&xpc, WILD_PREV, 0, firstc != '@') == OK
925 		    && nextwild(&xpc, WILD_PREV, 0, firstc != '@') == OK)
926 		goto cmdline_changed;
927 	}
928 
929 	if (c == NUL || c == K_ZERO)	    /* NUL is stored as NL */
930 	    c = NL;
931 
932 	do_abbr = TRUE;		/* default: check for abbreviation */
933 
934 	/*
935 	 * Big switch for a typed command line character.
936 	 */
937 	switch (c)
938 	{
939 	case K_BS:
940 	case Ctrl_H:
941 	case K_DEL:
942 	case K_KDEL:
943 	case Ctrl_W:
944 #ifdef FEAT_FKMAP
945 		if (cmd_fkmap && c == K_BS)
946 		    c = K_DEL;
947 #endif
948 		if (c == K_KDEL)
949 		    c = K_DEL;
950 
951 		/*
952 		 * delete current character is the same as backspace on next
953 		 * character, except at end of line
954 		 */
955 		if (c == K_DEL && ccline.cmdpos != ccline.cmdlen)
956 		    ++ccline.cmdpos;
957 #ifdef FEAT_MBYTE
958 		if (has_mbyte && c == K_DEL)
959 		    ccline.cmdpos += mb_off_next(ccline.cmdbuff,
960 					      ccline.cmdbuff + ccline.cmdpos);
961 #endif
962 		if (ccline.cmdpos > 0)
963 		{
964 		    char_u *p;
965 
966 		    j = ccline.cmdpos;
967 		    p = ccline.cmdbuff + j;
968 #ifdef FEAT_MBYTE
969 		    if (has_mbyte)
970 		    {
971 			p = mb_prevptr(ccline.cmdbuff, p);
972 			if (c == Ctrl_W)
973 			{
974 			    while (p > ccline.cmdbuff && vim_isspace(*p))
975 				p = mb_prevptr(ccline.cmdbuff, p);
976 			    i = mb_get_class(p);
977 			    while (p > ccline.cmdbuff && mb_get_class(p) == i)
978 				p = mb_prevptr(ccline.cmdbuff, p);
979 			    if (mb_get_class(p) != i)
980 				p += (*mb_ptr2len)(p);
981 			}
982 		    }
983 		    else
984 #endif
985 			if (c == Ctrl_W)
986 		    {
987 			while (p > ccline.cmdbuff && vim_isspace(p[-1]))
988 			    --p;
989 			i = vim_iswordc(p[-1]);
990 			while (p > ccline.cmdbuff && !vim_isspace(p[-1])
991 				&& vim_iswordc(p[-1]) == i)
992 			    --p;
993 		    }
994 		    else
995 			--p;
996 		    ccline.cmdpos = (int)(p - ccline.cmdbuff);
997 		    ccline.cmdlen -= j - ccline.cmdpos;
998 		    i = ccline.cmdpos;
999 		    while (i < ccline.cmdlen)
1000 			ccline.cmdbuff[i++] = ccline.cmdbuff[j++];
1001 
1002 		    /* Truncate at the end, required for multi-byte chars. */
1003 		    ccline.cmdbuff[ccline.cmdlen] = NUL;
1004 		    redrawcmd();
1005 		}
1006 		else if (ccline.cmdlen == 0 && c != Ctrl_W
1007 				   && ccline.cmdprompt == NULL && indent == 0)
1008 		{
1009 		    /* In ex and debug mode it doesn't make sense to return. */
1010 		    if (exmode_active
1011 #ifdef FEAT_EVAL
1012 			    || ccline.cmdfirstc == '>'
1013 #endif
1014 			    )
1015 			goto cmdline_not_changed;
1016 
1017 		    vim_free(ccline.cmdbuff);	/* no commandline to return */
1018 		    ccline.cmdbuff = NULL;
1019 		    if (!cmd_silent)
1020 		    {
1021 #ifdef FEAT_RIGHTLEFT
1022 			if (cmdmsg_rl)
1023 			    msg_col = Columns;
1024 			else
1025 #endif
1026 			    msg_col = 0;
1027 			msg_putchar(' ');		/* delete ':' */
1028 		    }
1029 		    redraw_cmdline = TRUE;
1030 		    goto returncmd;		/* back to cmd mode */
1031 		}
1032 		goto cmdline_changed;
1033 
1034 	case K_INS:
1035 	case K_KINS:
1036 #ifdef FEAT_FKMAP
1037 		/* if Farsi mode set, we are in reverse insert mode -
1038 		   Do not change the mode */
1039 		if (cmd_fkmap)
1040 		    beep_flush();
1041 		else
1042 #endif
1043 		ccline.overstrike = !ccline.overstrike;
1044 #ifdef CURSOR_SHAPE
1045 		ui_cursor_shape();	/* may show different cursor shape */
1046 #endif
1047 		goto cmdline_not_changed;
1048 
1049 	case Ctrl_HAT:
1050 		if (map_to_exists_mode((char_u *)"", LANGMAP, FALSE))
1051 		{
1052 		    /* ":lmap" mappings exists, toggle use of mappings. */
1053 		    State ^= LANGMAP;
1054 #ifdef USE_IM_CONTROL
1055 		    im_set_active(FALSE);	/* Disable input method */
1056 #endif
1057 		    if (b_im_ptr != NULL)
1058 		    {
1059 			if (State & LANGMAP)
1060 			    *b_im_ptr = B_IMODE_LMAP;
1061 			else
1062 			    *b_im_ptr = B_IMODE_NONE;
1063 		    }
1064 		}
1065 #ifdef USE_IM_CONTROL
1066 		else
1067 		{
1068 		    /* There are no ":lmap" mappings, toggle IM.  When
1069 		     * 'imdisable' is set don't try getting the status, it's
1070 		     * always off. */
1071 		    if ((p_imdisable && b_im_ptr != NULL)
1072 			    ? *b_im_ptr == B_IMODE_IM : im_get_status())
1073 		    {
1074 			im_set_active(FALSE);	/* Disable input method */
1075 			if (b_im_ptr != NULL)
1076 			    *b_im_ptr = B_IMODE_NONE;
1077 		    }
1078 		    else
1079 		    {
1080 			im_set_active(TRUE);	/* Enable input method */
1081 			if (b_im_ptr != NULL)
1082 			    *b_im_ptr = B_IMODE_IM;
1083 		    }
1084 		}
1085 #endif
1086 		if (b_im_ptr != NULL)
1087 		{
1088 		    if (b_im_ptr == &curbuf->b_p_iminsert)
1089 			set_iminsert_global();
1090 		    else
1091 			set_imsearch_global();
1092 		}
1093 #ifdef CURSOR_SHAPE
1094 		ui_cursor_shape();	/* may show different cursor shape */
1095 #endif
1096 #if defined(FEAT_WINDOWS) && defined(FEAT_KEYMAP)
1097 		/* Show/unshow value of 'keymap' in status lines later. */
1098 		status_redraw_curbuf();
1099 #endif
1100 		goto cmdline_not_changed;
1101 
1102 /*	case '@':   only in very old vi */
1103 	case Ctrl_U:
1104 		/* delete all characters left of the cursor */
1105 		j = ccline.cmdpos;
1106 		ccline.cmdlen -= j;
1107 		i = ccline.cmdpos = 0;
1108 		while (i < ccline.cmdlen)
1109 		    ccline.cmdbuff[i++] = ccline.cmdbuff[j++];
1110 		/* Truncate at the end, required for multi-byte chars. */
1111 		ccline.cmdbuff[ccline.cmdlen] = NUL;
1112 		redrawcmd();
1113 		goto cmdline_changed;
1114 
1115 #ifdef FEAT_CLIPBOARD
1116 	case Ctrl_Y:
1117 		/* Copy the modeless selection, if there is one. */
1118 		if (clip_star.state != SELECT_CLEARED)
1119 		{
1120 		    if (clip_star.state == SELECT_DONE)
1121 			clip_copy_modeless_selection(TRUE);
1122 		    goto cmdline_not_changed;
1123 		}
1124 		break;
1125 #endif
1126 
1127 	case ESC:	/* get here if p_wc != ESC or when ESC typed twice */
1128 	case Ctrl_C:
1129 		/* In exmode it doesn't make sense to return.  Except when
1130 		 * ":normal" runs out of characters. */
1131 		if (exmode_active
1132 #ifdef FEAT_EX_EXTRA
1133 			&& (ex_normal_busy == 0 || typebuf.tb_len > 0)
1134 #endif
1135 		   )
1136 		    goto cmdline_not_changed;
1137 
1138 		gotesc = TRUE;		/* will free ccline.cmdbuff after
1139 					   putting it in history */
1140 		goto returncmd;		/* back to cmd mode */
1141 
1142 	case Ctrl_R:			/* insert register */
1143 #ifdef USE_ON_FLY_SCROLL
1144 		dont_scroll = TRUE;	/* disallow scrolling here */
1145 #endif
1146 		putcmdline('"', TRUE);
1147 		++no_mapping;
1148 		i = c = plain_vgetc();	/* CTRL-R <char> */
1149 		if (i == Ctrl_O)
1150 		    i = Ctrl_R;		/* CTRL-R CTRL-O == CTRL-R CTRL-R */
1151 		if (i == Ctrl_R)
1152 		    c = plain_vgetc();	/* CTRL-R CTRL-R <char> */
1153 		--no_mapping;
1154 #ifdef FEAT_EVAL
1155 		/*
1156 		 * Insert the result of an expression.
1157 		 * Need to save the current command line, to be able to enter
1158 		 * a new one...
1159 		 */
1160 		new_cmdpos = -1;
1161 		if (c == '=')
1162 		{
1163 		    if (ccline.cmdfirstc == '=')/* can't do this recursively */
1164 		    {
1165 			beep_flush();
1166 			c = ESC;
1167 		    }
1168 		    else
1169 		    {
1170 			save_cmdline(&save_ccline);
1171 			c = get_expr_register();
1172 			restore_cmdline(&save_ccline);
1173 		    }
1174 		}
1175 #endif
1176 		if (c != ESC)	    /* use ESC to cancel inserting register */
1177 		{
1178 		    cmdline_paste(c, i == Ctrl_R, FALSE);
1179 
1180 #ifdef FEAT_EVAL
1181 		    /* When there was a serious error abort getting the
1182 		     * command line. */
1183 		    if (aborting())
1184 		    {
1185 			gotesc = TRUE;  /* will free ccline.cmdbuff after
1186 					   putting it in history */
1187 			goto returncmd; /* back to cmd mode */
1188 		    }
1189 #endif
1190 		    KeyTyped = FALSE;	/* Don't do p_wc completion. */
1191 #ifdef FEAT_EVAL
1192 		    if (new_cmdpos >= 0)
1193 		    {
1194 			/* set_cmdline_pos() was used */
1195 			if (new_cmdpos > ccline.cmdlen)
1196 			    ccline.cmdpos = ccline.cmdlen;
1197 			else
1198 			    ccline.cmdpos = new_cmdpos;
1199 		    }
1200 #endif
1201 		}
1202 		redrawcmd();
1203 		goto cmdline_changed;
1204 
1205 	case Ctrl_D:
1206 		if (showmatches(&xpc, FALSE) == EXPAND_NOTHING)
1207 		    break;	/* Use ^D as normal char instead */
1208 
1209 		redrawcmd();
1210 		continue;	/* don't do incremental search now */
1211 
1212 	case K_RIGHT:
1213 	case K_S_RIGHT:
1214 	case K_C_RIGHT:
1215 		do
1216 		{
1217 		    if (ccline.cmdpos >= ccline.cmdlen)
1218 			break;
1219 		    i = cmdline_charsize(ccline.cmdpos);
1220 		    if (KeyTyped && ccline.cmdspos + i >= Columns * Rows)
1221 			break;
1222 		    ccline.cmdspos += i;
1223 #ifdef FEAT_MBYTE
1224 		    if (has_mbyte)
1225 			ccline.cmdpos += (*mb_ptr2len)(ccline.cmdbuff
1226 							     + ccline.cmdpos);
1227 		    else
1228 #endif
1229 			++ccline.cmdpos;
1230 		}
1231 		while ((c == K_S_RIGHT || c == K_C_RIGHT
1232 			       || (mod_mask & (MOD_MASK_SHIFT|MOD_MASK_CTRL)))
1233 			&& ccline.cmdbuff[ccline.cmdpos] != ' ');
1234 #ifdef FEAT_MBYTE
1235 		if (has_mbyte)
1236 		    set_cmdspos_cursor();
1237 #endif
1238 		goto cmdline_not_changed;
1239 
1240 	case K_LEFT:
1241 	case K_S_LEFT:
1242 	case K_C_LEFT:
1243 		if (ccline.cmdpos == 0)
1244 		    goto cmdline_not_changed;
1245 		do
1246 		{
1247 		    --ccline.cmdpos;
1248 #ifdef FEAT_MBYTE
1249 		    if (has_mbyte)	/* move to first byte of char */
1250 			ccline.cmdpos -= (*mb_head_off)(ccline.cmdbuff,
1251 					      ccline.cmdbuff + ccline.cmdpos);
1252 #endif
1253 		    ccline.cmdspos -= cmdline_charsize(ccline.cmdpos);
1254 		}
1255 		while (ccline.cmdpos > 0
1256 			&& (c == K_S_LEFT || c == K_C_LEFT
1257 			       || (mod_mask & (MOD_MASK_SHIFT|MOD_MASK_CTRL)))
1258 			&& ccline.cmdbuff[ccline.cmdpos - 1] != ' ');
1259 #ifdef FEAT_MBYTE
1260 		if (has_mbyte)
1261 		    set_cmdspos_cursor();
1262 #endif
1263 		goto cmdline_not_changed;
1264 
1265 	case K_IGNORE:
1266 		/* Ignore mouse event or ex_window() result. */
1267 		goto cmdline_not_changed;
1268 
1269 #ifdef FEAT_GUI_W32
1270 	    /* On Win32 ignore <M-F4>, we get it when closing the window was
1271 	     * cancelled. */
1272 	case K_F4:
1273 	    if (mod_mask == MOD_MASK_ALT)
1274 	    {
1275 		redrawcmd();	    /* somehow the cmdline is cleared */
1276 		goto cmdline_not_changed;
1277 	    }
1278 	    break;
1279 #endif
1280 
1281 #ifdef FEAT_MOUSE
1282 	case K_MIDDLEDRAG:
1283 	case K_MIDDLERELEASE:
1284 		goto cmdline_not_changed;	/* Ignore mouse */
1285 
1286 	case K_MIDDLEMOUSE:
1287 # ifdef FEAT_GUI
1288 		/* When GUI is active, also paste when 'mouse' is empty */
1289 		if (!gui.in_use)
1290 # endif
1291 		    if (!mouse_has(MOUSE_COMMAND))
1292 			goto cmdline_not_changed;   /* Ignore mouse */
1293 # ifdef FEAT_CLIPBOARD
1294 		if (clip_star.available)
1295 		    cmdline_paste('*', TRUE, TRUE);
1296 		else
1297 # endif
1298 		    cmdline_paste(0, TRUE, TRUE);
1299 		redrawcmd();
1300 		goto cmdline_changed;
1301 
1302 # ifdef FEAT_DND
1303 	case K_DROP:
1304 		cmdline_paste('~', TRUE, FALSE);
1305 		redrawcmd();
1306 		goto cmdline_changed;
1307 # endif
1308 
1309 	case K_LEFTDRAG:
1310 	case K_LEFTRELEASE:
1311 	case K_RIGHTDRAG:
1312 	case K_RIGHTRELEASE:
1313 		/* Ignore drag and release events when the button-down wasn't
1314 		 * seen before. */
1315 		if (ignore_drag_release)
1316 		    goto cmdline_not_changed;
1317 		/* FALLTHROUGH */
1318 	case K_LEFTMOUSE:
1319 	case K_RIGHTMOUSE:
1320 		if (c == K_LEFTRELEASE || c == K_RIGHTRELEASE)
1321 		    ignore_drag_release = TRUE;
1322 		else
1323 		    ignore_drag_release = FALSE;
1324 # ifdef FEAT_GUI
1325 		/* When GUI is active, also move when 'mouse' is empty */
1326 		if (!gui.in_use)
1327 # endif
1328 		    if (!mouse_has(MOUSE_COMMAND))
1329 			goto cmdline_not_changed;   /* Ignore mouse */
1330 # ifdef FEAT_CLIPBOARD
1331 		if (mouse_row < cmdline_row && clip_star.available)
1332 		{
1333 		    int	    button, is_click, is_drag;
1334 
1335 		    /*
1336 		     * Handle modeless selection.
1337 		     */
1338 		    button = get_mouse_button(KEY2TERMCAP1(c),
1339 							 &is_click, &is_drag);
1340 		    if (mouse_model_popup() && button == MOUSE_LEFT
1341 					       && (mod_mask & MOD_MASK_SHIFT))
1342 		    {
1343 			/* Translate shift-left to right button. */
1344 			button = MOUSE_RIGHT;
1345 			mod_mask &= ~MOD_MASK_SHIFT;
1346 		    }
1347 		    clip_modeless(button, is_click, is_drag);
1348 		    goto cmdline_not_changed;
1349 		}
1350 # endif
1351 
1352 		set_cmdspos();
1353 		for (ccline.cmdpos = 0; ccline.cmdpos < ccline.cmdlen;
1354 							      ++ccline.cmdpos)
1355 		{
1356 		    i = cmdline_charsize(ccline.cmdpos);
1357 		    if (mouse_row <= cmdline_row + ccline.cmdspos / Columns
1358 				  && mouse_col < ccline.cmdspos % Columns + i)
1359 			break;
1360 # ifdef FEAT_MBYTE
1361 		    if (has_mbyte)
1362 		    {
1363 			/* Count ">" for double-wide char that doesn't fit. */
1364 			correct_cmdspos(ccline.cmdpos, i);
1365 			ccline.cmdpos += (*mb_ptr2len)(ccline.cmdbuff
1366 							 + ccline.cmdpos) - 1;
1367 		    }
1368 # endif
1369 		    ccline.cmdspos += i;
1370 		}
1371 		goto cmdline_not_changed;
1372 
1373 	/* Mouse scroll wheel: ignored here */
1374 	case K_MOUSEDOWN:
1375 	case K_MOUSEUP:
1376 	case K_MOUSELEFT:
1377 	case K_MOUSERIGHT:
1378 	/* Alternate buttons ignored here */
1379 	case K_X1MOUSE:
1380 	case K_X1DRAG:
1381 	case K_X1RELEASE:
1382 	case K_X2MOUSE:
1383 	case K_X2DRAG:
1384 	case K_X2RELEASE:
1385 		goto cmdline_not_changed;
1386 
1387 #endif	/* FEAT_MOUSE */
1388 
1389 #ifdef FEAT_GUI
1390 	case K_LEFTMOUSE_NM:	/* mousefocus click, ignored */
1391 	case K_LEFTRELEASE_NM:
1392 		goto cmdline_not_changed;
1393 
1394 	case K_VER_SCROLLBAR:
1395 		if (msg_scrolled == 0)
1396 		{
1397 		    gui_do_scroll();
1398 		    redrawcmd();
1399 		}
1400 		goto cmdline_not_changed;
1401 
1402 	case K_HOR_SCROLLBAR:
1403 		if (msg_scrolled == 0)
1404 		{
1405 		    gui_do_horiz_scroll(scrollbar_value, FALSE);
1406 		    redrawcmd();
1407 		}
1408 		goto cmdline_not_changed;
1409 #endif
1410 #ifdef FEAT_GUI_TABLINE
1411 	case K_TABLINE:
1412 	case K_TABMENU:
1413 		/* Don't want to change any tabs here.  Make sure the same tab
1414 		 * is still selected. */
1415 		if (gui_use_tabline())
1416 		    gui_mch_set_curtab(tabpage_index(curtab));
1417 		goto cmdline_not_changed;
1418 #endif
1419 
1420 	case K_SELECT:	    /* end of Select mode mapping - ignore */
1421 		goto cmdline_not_changed;
1422 
1423 	case Ctrl_B:	    /* begin of command line */
1424 	case K_HOME:
1425 	case K_KHOME:
1426 	case K_S_HOME:
1427 	case K_C_HOME:
1428 		ccline.cmdpos = 0;
1429 		set_cmdspos();
1430 		goto cmdline_not_changed;
1431 
1432 	case Ctrl_E:	    /* end of command line */
1433 	case K_END:
1434 	case K_KEND:
1435 	case K_S_END:
1436 	case K_C_END:
1437 		ccline.cmdpos = ccline.cmdlen;
1438 		set_cmdspos_cursor();
1439 		goto cmdline_not_changed;
1440 
1441 	case Ctrl_A:	    /* all matches */
1442 		if (nextwild(&xpc, WILD_ALL, 0, firstc != '@') == FAIL)
1443 		    break;
1444 		goto cmdline_changed;
1445 
1446 	case Ctrl_L:
1447 #ifdef FEAT_SEARCH_EXTRA
1448 		if (p_is && !cmd_silent && (firstc == '/' || firstc == '?'))
1449 		{
1450 		    /* Add a character from under the cursor for 'incsearch' */
1451 		    if (did_incsearch
1452 				   && !equalpos(curwin->w_cursor, old_cursor))
1453 		    {
1454 			c = gchar_cursor();
1455 			/* If 'ignorecase' and 'smartcase' are set and the
1456 			* command line has no uppercase characters, convert
1457 			* the character to lowercase */
1458 			if (p_ic && p_scs && !pat_has_uppercase(ccline.cmdbuff))
1459 			    c = MB_TOLOWER(c);
1460 			if (c != NUL)
1461 			{
1462 			    if (c == firstc || vim_strchr((char_u *)(
1463 					    p_magic ? "\\^$.*[" : "\\^$"), c)
1464 								      != NULL)
1465 			    {
1466 				/* put a backslash before special characters */
1467 				stuffcharReadbuff(c);
1468 				c = '\\';
1469 			    }
1470 			    break;
1471 			}
1472 		    }
1473 		    goto cmdline_not_changed;
1474 		}
1475 #endif
1476 
1477 		/* completion: longest common part */
1478 		if (nextwild(&xpc, WILD_LONGEST, 0, firstc != '@') == FAIL)
1479 		    break;
1480 		goto cmdline_changed;
1481 
1482 	case Ctrl_N:	    /* next match */
1483 	case Ctrl_P:	    /* previous match */
1484 		if (xpc.xp_numfiles > 0)
1485 		{
1486 		    if (nextwild(&xpc, (c == Ctrl_P) ? WILD_PREV : WILD_NEXT,
1487 						    0, firstc != '@') == FAIL)
1488 			break;
1489 		    goto cmdline_changed;
1490 		}
1491 
1492 #ifdef FEAT_CMDHIST
1493 	case K_UP:
1494 	case K_DOWN:
1495 	case K_S_UP:
1496 	case K_S_DOWN:
1497 	case K_PAGEUP:
1498 	case K_KPAGEUP:
1499 	case K_PAGEDOWN:
1500 	case K_KPAGEDOWN:
1501 		if (hislen == 0 || firstc == NUL)	/* no history */
1502 		    goto cmdline_not_changed;
1503 
1504 		i = hiscnt;
1505 
1506 		/* save current command string so it can be restored later */
1507 		if (lookfor == NULL)
1508 		{
1509 		    if ((lookfor = vim_strsave(ccline.cmdbuff)) == NULL)
1510 			goto cmdline_not_changed;
1511 		    lookfor[ccline.cmdpos] = NUL;
1512 		}
1513 
1514 		j = (int)STRLEN(lookfor);
1515 		for (;;)
1516 		{
1517 		    /* one step backwards */
1518 		    if (c == K_UP|| c == K_S_UP || c == Ctrl_P
1519 			    || c == K_PAGEUP || c == K_KPAGEUP)
1520 		    {
1521 			if (hiscnt == hislen)	/* first time */
1522 			    hiscnt = hisidx[histype];
1523 			else if (hiscnt == 0 && hisidx[histype] != hislen - 1)
1524 			    hiscnt = hislen - 1;
1525 			else if (hiscnt != hisidx[histype] + 1)
1526 			    --hiscnt;
1527 			else			/* at top of list */
1528 			{
1529 			    hiscnt = i;
1530 			    break;
1531 			}
1532 		    }
1533 		    else    /* one step forwards */
1534 		    {
1535 			/* on last entry, clear the line */
1536 			if (hiscnt == hisidx[histype])
1537 			{
1538 			    hiscnt = hislen;
1539 			    break;
1540 			}
1541 
1542 			/* not on a history line, nothing to do */
1543 			if (hiscnt == hislen)
1544 			    break;
1545 			if (hiscnt == hislen - 1)   /* wrap around */
1546 			    hiscnt = 0;
1547 			else
1548 			    ++hiscnt;
1549 		    }
1550 		    if (hiscnt < 0 || history[histype][hiscnt].hisstr == NULL)
1551 		    {
1552 			hiscnt = i;
1553 			break;
1554 		    }
1555 		    if ((c != K_UP && c != K_DOWN)
1556 			    || hiscnt == i
1557 			    || STRNCMP(history[histype][hiscnt].hisstr,
1558 						    lookfor, (size_t)j) == 0)
1559 			break;
1560 		}
1561 
1562 		if (hiscnt != i)	/* jumped to other entry */
1563 		{
1564 		    char_u	*p;
1565 		    int		len;
1566 		    int		old_firstc;
1567 
1568 		    vim_free(ccline.cmdbuff);
1569 		    xpc.xp_context = EXPAND_NOTHING;
1570 		    if (hiscnt == hislen)
1571 			p = lookfor;	/* back to the old one */
1572 		    else
1573 			p = history[histype][hiscnt].hisstr;
1574 
1575 		    if (histype == HIST_SEARCH
1576 			    && p != lookfor
1577 			    && (old_firstc = p[STRLEN(p) + 1]) != firstc)
1578 		    {
1579 			/* Correct for the separator character used when
1580 			 * adding the history entry vs the one used now.
1581 			 * First loop: count length.
1582 			 * Second loop: copy the characters. */
1583 			for (i = 0; i <= 1; ++i)
1584 			{
1585 			    len = 0;
1586 			    for (j = 0; p[j] != NUL; ++j)
1587 			    {
1588 				/* Replace old sep with new sep, unless it is
1589 				 * escaped. */
1590 				if (p[j] == old_firstc
1591 					      && (j == 0 || p[j - 1] != '\\'))
1592 				{
1593 				    if (i > 0)
1594 					ccline.cmdbuff[len] = firstc;
1595 				}
1596 				else
1597 				{
1598 				    /* Escape new sep, unless it is already
1599 				     * escaped. */
1600 				    if (p[j] == firstc
1601 					      && (j == 0 || p[j - 1] != '\\'))
1602 				    {
1603 					if (i > 0)
1604 					    ccline.cmdbuff[len] = '\\';
1605 					++len;
1606 				    }
1607 				    if (i > 0)
1608 					ccline.cmdbuff[len] = p[j];
1609 				}
1610 				++len;
1611 			    }
1612 			    if (i == 0)
1613 			    {
1614 				alloc_cmdbuff(len);
1615 				if (ccline.cmdbuff == NULL)
1616 				    goto returncmd;
1617 			    }
1618 			}
1619 			ccline.cmdbuff[len] = NUL;
1620 		    }
1621 		    else
1622 		    {
1623 			alloc_cmdbuff((int)STRLEN(p));
1624 			if (ccline.cmdbuff == NULL)
1625 			    goto returncmd;
1626 			STRCPY(ccline.cmdbuff, p);
1627 		    }
1628 
1629 		    ccline.cmdpos = ccline.cmdlen = (int)STRLEN(ccline.cmdbuff);
1630 		    redrawcmd();
1631 		    goto cmdline_changed;
1632 		}
1633 		beep_flush();
1634 		goto cmdline_not_changed;
1635 #endif
1636 
1637 	case Ctrl_V:
1638 	case Ctrl_Q:
1639 #ifdef FEAT_MOUSE
1640 		ignore_drag_release = TRUE;
1641 #endif
1642 		putcmdline('^', TRUE);
1643 		c = get_literal();	    /* get next (two) character(s) */
1644 		do_abbr = FALSE;	    /* don't do abbreviation now */
1645 #ifdef FEAT_MBYTE
1646 		/* may need to remove ^ when composing char was typed */
1647 		if (enc_utf8 && utf_iscomposing(c) && !cmd_silent)
1648 		{
1649 		    draw_cmdline(ccline.cmdpos, ccline.cmdlen - ccline.cmdpos);
1650 		    msg_putchar(' ');
1651 		    cursorcmd();
1652 		}
1653 #endif
1654 		break;
1655 
1656 #ifdef FEAT_DIGRAPHS
1657 	case Ctrl_K:
1658 #ifdef FEAT_MOUSE
1659 		ignore_drag_release = TRUE;
1660 #endif
1661 		putcmdline('?', TRUE);
1662 #ifdef USE_ON_FLY_SCROLL
1663 		dont_scroll = TRUE;	    /* disallow scrolling here */
1664 #endif
1665 		c = get_digraph(TRUE);
1666 		if (c != NUL)
1667 		    break;
1668 
1669 		redrawcmd();
1670 		goto cmdline_not_changed;
1671 #endif /* FEAT_DIGRAPHS */
1672 
1673 #ifdef FEAT_RIGHTLEFT
1674 	case Ctrl__:	    /* CTRL-_: switch language mode */
1675 		if (!p_ari)
1676 		    break;
1677 #ifdef FEAT_FKMAP
1678 		if (p_altkeymap)
1679 		{
1680 		    cmd_fkmap = !cmd_fkmap;
1681 		    if (cmd_fkmap)	/* in Farsi always in Insert mode */
1682 			ccline.overstrike = FALSE;
1683 		}
1684 		else			    /* Hebrew is default */
1685 #endif
1686 		    cmd_hkmap = !cmd_hkmap;
1687 		goto cmdline_not_changed;
1688 #endif
1689 
1690 	default:
1691 #ifdef UNIX
1692 		if (c == intr_char)
1693 		{
1694 		    gotesc = TRUE;	/* will free ccline.cmdbuff after
1695 					   putting it in history */
1696 		    goto returncmd;	/* back to Normal mode */
1697 		}
1698 #endif
1699 		/*
1700 		 * Normal character with no special meaning.  Just set mod_mask
1701 		 * to 0x0 so that typing Shift-Space in the GUI doesn't enter
1702 		 * the string <S-Space>.  This should only happen after ^V.
1703 		 */
1704 		if (!IS_SPECIAL(c))
1705 		    mod_mask = 0x0;
1706 		break;
1707 	}
1708 	/*
1709 	 * End of switch on command line character.
1710 	 * We come here if we have a normal character.
1711 	 */
1712 
1713 	if (do_abbr && (IS_SPECIAL(c) || !vim_iswordc(c)) && (ccheck_abbr(
1714 #ifdef FEAT_MBYTE
1715 			/* Add ABBR_OFF for characters above 0x100, this is
1716 			 * what check_abbr() expects. */
1717 			(has_mbyte && c >= 0x100) ? (c + ABBR_OFF) :
1718 #endif
1719 							 c) || c == Ctrl_RSB))
1720 	    goto cmdline_changed;
1721 
1722 	/*
1723 	 * put the character in the command line
1724 	 */
1725 	if (IS_SPECIAL(c) || mod_mask != 0)
1726 	    put_on_cmdline(get_special_key_name(c, mod_mask), -1, TRUE);
1727 	else
1728 	{
1729 #ifdef FEAT_MBYTE
1730 	    if (has_mbyte)
1731 	    {
1732 		j = (*mb_char2bytes)(c, IObuff);
1733 		IObuff[j] = NUL;	/* exclude composing chars */
1734 		put_on_cmdline(IObuff, j, TRUE);
1735 	    }
1736 	    else
1737 #endif
1738 	    {
1739 		IObuff[0] = c;
1740 		put_on_cmdline(IObuff, 1, TRUE);
1741 	    }
1742 	}
1743 	goto cmdline_changed;
1744 
1745 /*
1746  * This part implements incremental searches for "/" and "?"
1747  * Jump to cmdline_not_changed when a character has been read but the command
1748  * line did not change. Then we only search and redraw if something changed in
1749  * the past.
1750  * Jump to cmdline_changed when the command line did change.
1751  * (Sorry for the goto's, I know it is ugly).
1752  */
1753 cmdline_not_changed:
1754 #ifdef FEAT_SEARCH_EXTRA
1755 	if (!incsearch_postponed)
1756 	    continue;
1757 #endif
1758 
1759 cmdline_changed:
1760 #ifdef FEAT_SEARCH_EXTRA
1761 	/*
1762 	 * 'incsearch' highlighting.
1763 	 */
1764 	if (p_is && !cmd_silent && (firstc == '/' || firstc == '?'))
1765 	{
1766 	    pos_T	end_pos;
1767 #ifdef FEAT_RELTIME
1768 	    proftime_T	tm;
1769 #endif
1770 
1771 	    /* if there is a character waiting, search and redraw later */
1772 	    if (char_avail())
1773 	    {
1774 		incsearch_postponed = TRUE;
1775 		continue;
1776 	    }
1777 	    incsearch_postponed = FALSE;
1778 	    curwin->w_cursor = old_cursor;  /* start at old position */
1779 
1780 	    /* If there is no command line, don't do anything */
1781 	    if (ccline.cmdlen == 0)
1782 		i = 0;
1783 	    else
1784 	    {
1785 		cursor_off();		/* so the user knows we're busy */
1786 		out_flush();
1787 		++emsg_off;    /* So it doesn't beep if bad expr */
1788 #ifdef FEAT_RELTIME
1789 		/* Set the time limit to half a second. */
1790 		profile_setlimit(500L, &tm);
1791 #endif
1792 		i = do_search(NULL, firstc, ccline.cmdbuff, count,
1793 			SEARCH_KEEP + SEARCH_OPT + SEARCH_NOOF + SEARCH_PEEK,
1794 #ifdef FEAT_RELTIME
1795 			&tm
1796 #else
1797 			NULL
1798 #endif
1799 			);
1800 		--emsg_off;
1801 		/* if interrupted while searching, behave like it failed */
1802 		if (got_int)
1803 		{
1804 		    (void)vpeekc();	/* remove <C-C> from input stream */
1805 		    got_int = FALSE;	/* don't abandon the command line */
1806 		    i = 0;
1807 		}
1808 		else if (char_avail())
1809 		    /* cancelled searching because a char was typed */
1810 		    incsearch_postponed = TRUE;
1811 	    }
1812 	    if (i != 0)
1813 		highlight_match = TRUE;		/* highlight position */
1814 	    else
1815 		highlight_match = FALSE;	/* remove highlight */
1816 
1817 	    /* first restore the old curwin values, so the screen is
1818 	     * positioned in the same way as the actual search command */
1819 	    curwin->w_leftcol = old_leftcol;
1820 	    curwin->w_topline = old_topline;
1821 # ifdef FEAT_DIFF
1822 	    curwin->w_topfill = old_topfill;
1823 # endif
1824 	    curwin->w_botline = old_botline;
1825 	    changed_cline_bef_curs();
1826 	    update_topline();
1827 
1828 	    if (i != 0)
1829 	    {
1830 		pos_T	    save_pos = curwin->w_cursor;
1831 
1832 		/*
1833 		 * First move cursor to end of match, then to the start.  This
1834 		 * moves the whole match onto the screen when 'nowrap' is set.
1835 		 */
1836 		curwin->w_cursor.lnum += search_match_lines;
1837 		curwin->w_cursor.col = search_match_endcol;
1838 		if (curwin->w_cursor.lnum > curbuf->b_ml.ml_line_count)
1839 		{
1840 		    curwin->w_cursor.lnum = curbuf->b_ml.ml_line_count;
1841 		    coladvance((colnr_T)MAXCOL);
1842 		}
1843 		validate_cursor();
1844 		end_pos = curwin->w_cursor;
1845 		curwin->w_cursor = save_pos;
1846 	    }
1847 	    else
1848 		end_pos = curwin->w_cursor; /* shutup gcc 4 */
1849 
1850 	    validate_cursor();
1851 # ifdef FEAT_WINDOWS
1852 	    /* May redraw the status line to show the cursor position. */
1853 	    if (p_ru && curwin->w_status_height > 0)
1854 		curwin->w_redr_status = TRUE;
1855 # endif
1856 
1857 	    save_cmdline(&save_ccline);
1858 	    update_screen(SOME_VALID);
1859 	    restore_cmdline(&save_ccline);
1860 
1861 	    /* Leave it at the end to make CTRL-R CTRL-W work. */
1862 	    if (i != 0)
1863 		curwin->w_cursor = end_pos;
1864 
1865 	    msg_starthere();
1866 	    redrawcmdline();
1867 	    did_incsearch = TRUE;
1868 	}
1869 #else /* FEAT_SEARCH_EXTRA */
1870 	;
1871 #endif
1872 
1873 #ifdef FEAT_RIGHTLEFT
1874 	if (cmdmsg_rl
1875 # ifdef FEAT_ARABIC
1876 		|| (p_arshape && !p_tbidi && enc_utf8)
1877 # endif
1878 		)
1879 	    /* Always redraw the whole command line to fix shaping and
1880 	     * right-left typing.  Not efficient, but it works.
1881 	     * Do it only when there are no characters left to read
1882 	     * to avoid useless intermediate redraws. */
1883 	    if (vpeekc() == NUL)
1884 		redrawcmd();
1885 #endif
1886     }
1887 
1888 returncmd:
1889 
1890 #ifdef FEAT_RIGHTLEFT
1891     cmdmsg_rl = FALSE;
1892 #endif
1893 
1894 #ifdef FEAT_FKMAP
1895     cmd_fkmap = 0;
1896 #endif
1897 
1898     ExpandCleanup(&xpc);
1899     ccline.xpc = NULL;
1900 
1901 #ifdef FEAT_SEARCH_EXTRA
1902     if (did_incsearch)
1903     {
1904 	curwin->w_cursor = old_cursor;
1905 	curwin->w_curswant = old_curswant;
1906 	curwin->w_leftcol = old_leftcol;
1907 	curwin->w_topline = old_topline;
1908 # ifdef FEAT_DIFF
1909 	curwin->w_topfill = old_topfill;
1910 # endif
1911 	curwin->w_botline = old_botline;
1912 	highlight_match = FALSE;
1913 	validate_cursor();	/* needed for TAB */
1914 	redraw_later(SOME_VALID);
1915     }
1916 #endif
1917 
1918     if (ccline.cmdbuff != NULL)
1919     {
1920 	/*
1921 	 * Put line in history buffer (":" and "=" only when it was typed).
1922 	 */
1923 #ifdef FEAT_CMDHIST
1924 	if (ccline.cmdlen && firstc != NUL
1925 		&& (some_key_typed || histype == HIST_SEARCH))
1926 	{
1927 	    add_to_history(histype, ccline.cmdbuff, TRUE,
1928 				       histype == HIST_SEARCH ? firstc : NUL);
1929 	    if (firstc == ':')
1930 	    {
1931 		vim_free(new_last_cmdline);
1932 		new_last_cmdline = vim_strsave(ccline.cmdbuff);
1933 	    }
1934 	}
1935 #endif
1936 
1937 	if (gotesc)	    /* abandon command line */
1938 	{
1939 	    vim_free(ccline.cmdbuff);
1940 	    ccline.cmdbuff = NULL;
1941 	    if (msg_scrolled == 0)
1942 		compute_cmdrow();
1943 	    MSG("");
1944 	    redraw_cmdline = TRUE;
1945 	}
1946     }
1947 
1948     /*
1949      * If the screen was shifted up, redraw the whole screen (later).
1950      * If the line is too long, clear it, so ruler and shown command do
1951      * not get printed in the middle of it.
1952      */
1953     msg_check();
1954     msg_scroll = save_msg_scroll;
1955     redir_off = FALSE;
1956 
1957     /* When the command line was typed, no need for a wait-return prompt. */
1958     if (some_key_typed)
1959 	need_wait_return = FALSE;
1960 
1961     State = save_State;
1962 #ifdef USE_IM_CONTROL
1963     if (b_im_ptr != NULL && *b_im_ptr != B_IMODE_LMAP)
1964 	im_save_status(b_im_ptr);
1965     im_set_active(FALSE);
1966 #endif
1967 #ifdef FEAT_MOUSE
1968     setmouse();
1969 #endif
1970 #ifdef CURSOR_SHAPE
1971     ui_cursor_shape();		/* may show different cursor shape */
1972 #endif
1973 
1974     {
1975 	char_u *p = ccline.cmdbuff;
1976 
1977 	/* Make ccline empty, getcmdline() may try to use it. */
1978 	ccline.cmdbuff = NULL;
1979 	return p;
1980     }
1981 }
1982 
1983 #if (defined(FEAT_CRYPT) || defined(FEAT_EVAL)) || defined(PROTO)
1984 /*
1985  * Get a command line with a prompt.
1986  * This is prepared to be called recursively from getcmdline() (e.g. by
1987  * f_input() when evaluating an expression from CTRL-R =).
1988  * Returns the command line in allocated memory, or NULL.
1989  */
1990     char_u *
1991 getcmdline_prompt(firstc, prompt, attr, xp_context, xp_arg)
1992     int		firstc;
1993     char_u	*prompt;	/* command line prompt */
1994     int		attr;		/* attributes for prompt */
1995     int		xp_context;	/* type of expansion */
1996     char_u	*xp_arg;	/* user-defined expansion argument */
1997 {
1998     char_u		*s;
1999     struct cmdline_info	save_ccline;
2000     int			msg_col_save = msg_col;
2001 
2002     save_cmdline(&save_ccline);
2003     ccline.cmdprompt = prompt;
2004     ccline.cmdattr = attr;
2005 # ifdef FEAT_EVAL
2006     ccline.xp_context = xp_context;
2007     ccline.xp_arg = xp_arg;
2008     ccline.input_fn = (firstc == '@');
2009 # endif
2010     s = getcmdline(firstc, 1L, 0);
2011     restore_cmdline(&save_ccline);
2012     /* Restore msg_col, the prompt from input() may have changed it.
2013      * But only if called recursively and the commandline is therefore being
2014      * restored to an old one; if not, the input() prompt stays on the screen,
2015      * so we need its modified msg_col left intact. */
2016     if (ccline.cmdbuff != NULL)
2017 	msg_col = msg_col_save;
2018 
2019     return s;
2020 }
2021 #endif
2022 
2023 /*
2024  * Return TRUE when the text must not be changed and we can't switch to
2025  * another window or buffer.  Used when editing the command line, evaluating
2026  * 'balloonexpr', etc.
2027  */
2028     int
2029 text_locked()
2030 {
2031 #ifdef FEAT_CMDWIN
2032     if (cmdwin_type != 0)
2033 	return TRUE;
2034 #endif
2035     return textlock != 0;
2036 }
2037 
2038 /*
2039  * Give an error message for a command that isn't allowed while the cmdline
2040  * window is open or editing the cmdline in another way.
2041  */
2042     void
2043 text_locked_msg()
2044 {
2045 #ifdef FEAT_CMDWIN
2046     if (cmdwin_type != 0)
2047 	EMSG(_(e_cmdwin));
2048     else
2049 #endif
2050 	EMSG(_(e_secure));
2051 }
2052 
2053 #if defined(FEAT_AUTOCMD) || defined(PROTO)
2054 /*
2055  * Check if "curbuf_lock" or "allbuf_lock" is set and return TRUE when it is
2056  * and give an error message.
2057  */
2058     int
2059 curbuf_locked()
2060 {
2061     if (curbuf_lock > 0)
2062     {
2063 	EMSG(_("E788: Not allowed to edit another buffer now"));
2064 	return TRUE;
2065     }
2066     return allbuf_locked();
2067 }
2068 
2069 /*
2070  * Check if "allbuf_lock" is set and return TRUE when it is and give an error
2071  * message.
2072  */
2073     int
2074 allbuf_locked()
2075 {
2076     if (allbuf_lock > 0)
2077     {
2078 	EMSG(_("E811: Not allowed to change buffer information now"));
2079 	return TRUE;
2080     }
2081     return FALSE;
2082 }
2083 #endif
2084 
2085     static int
2086 cmdline_charsize(idx)
2087     int		idx;
2088 {
2089 #if defined(FEAT_CRYPT) || defined(FEAT_EVAL)
2090     if (cmdline_star > 0)	    /* showing '*', always 1 position */
2091 	return 1;
2092 #endif
2093     return ptr2cells(ccline.cmdbuff + idx);
2094 }
2095 
2096 /*
2097  * Compute the offset of the cursor on the command line for the prompt and
2098  * indent.
2099  */
2100     static void
2101 set_cmdspos()
2102 {
2103     if (ccline.cmdfirstc != NUL)
2104 	ccline.cmdspos = 1 + ccline.cmdindent;
2105     else
2106 	ccline.cmdspos = 0 + ccline.cmdindent;
2107 }
2108 
2109 /*
2110  * Compute the screen position for the cursor on the command line.
2111  */
2112     static void
2113 set_cmdspos_cursor()
2114 {
2115     int		i, m, c;
2116 
2117     set_cmdspos();
2118     if (KeyTyped)
2119     {
2120 	m = Columns * Rows;
2121 	if (m < 0)	/* overflow, Columns or Rows at weird value */
2122 	    m = MAXCOL;
2123     }
2124     else
2125 	m = MAXCOL;
2126     for (i = 0; i < ccline.cmdlen && i < ccline.cmdpos; ++i)
2127     {
2128 	c = cmdline_charsize(i);
2129 #ifdef FEAT_MBYTE
2130 	/* Count ">" for double-wide multi-byte char that doesn't fit. */
2131 	if (has_mbyte)
2132 	    correct_cmdspos(i, c);
2133 #endif
2134 	/* If the cmdline doesn't fit, show cursor on last visible char.
2135 	 * Don't move the cursor itself, so we can still append. */
2136 	if ((ccline.cmdspos += c) >= m)
2137 	{
2138 	    ccline.cmdspos -= c;
2139 	    break;
2140 	}
2141 #ifdef FEAT_MBYTE
2142 	if (has_mbyte)
2143 	    i += (*mb_ptr2len)(ccline.cmdbuff + i) - 1;
2144 #endif
2145     }
2146 }
2147 
2148 #ifdef FEAT_MBYTE
2149 /*
2150  * Check if the character at "idx", which is "cells" wide, is a multi-byte
2151  * character that doesn't fit, so that a ">" must be displayed.
2152  */
2153     static void
2154 correct_cmdspos(idx, cells)
2155     int		idx;
2156     int		cells;
2157 {
2158     if ((*mb_ptr2len)(ccline.cmdbuff + idx) > 1
2159 		&& (*mb_ptr2cells)(ccline.cmdbuff + idx) > 1
2160 		&& ccline.cmdspos % Columns + cells > Columns)
2161 	ccline.cmdspos++;
2162 }
2163 #endif
2164 
2165 /*
2166  * Get an Ex command line for the ":" command.
2167  */
2168     char_u *
2169 getexline(c, cookie, indent)
2170     int		c;		/* normally ':', NUL for ":append" */
2171     void	*cookie UNUSED;
2172     int		indent;		/* indent for inside conditionals */
2173 {
2174     /* When executing a register, remove ':' that's in front of each line. */
2175     if (exec_from_reg && vpeekc() == ':')
2176 	(void)vgetc();
2177     return getcmdline(c, 1L, indent);
2178 }
2179 
2180 /*
2181  * Get an Ex command line for Ex mode.
2182  * In Ex mode we only use the OS supplied line editing features and no
2183  * mappings or abbreviations.
2184  * Returns a string in allocated memory or NULL.
2185  */
2186     char_u *
2187 getexmodeline(promptc, cookie, indent)
2188     int		promptc;	/* normally ':', NUL for ":append" and '?' for
2189 				   :s prompt */
2190     void	*cookie UNUSED;
2191     int		indent;		/* indent for inside conditionals */
2192 {
2193     garray_T	line_ga;
2194     char_u	*pend;
2195     int		startcol = 0;
2196     int		c1 = 0;
2197     int		escaped = FALSE;	/* CTRL-V typed */
2198     int		vcol = 0;
2199     char_u	*p;
2200     int		prev_char;
2201     int		len;
2202 
2203     /* Switch cursor on now.  This avoids that it happens after the "\n", which
2204      * confuses the system function that computes tabstops. */
2205     cursor_on();
2206 
2207     /* always start in column 0; write a newline if necessary */
2208     compute_cmdrow();
2209     if ((msg_col || msg_didout) && promptc != '?')
2210 	msg_putchar('\n');
2211     if (promptc == ':')
2212     {
2213 	/* indent that is only displayed, not in the line itself */
2214 	if (p_prompt)
2215 	    msg_putchar(':');
2216 	while (indent-- > 0)
2217 	    msg_putchar(' ');
2218 	startcol = msg_col;
2219     }
2220 
2221     ga_init2(&line_ga, 1, 30);
2222 
2223     /* autoindent for :insert and :append is in the line itself */
2224     if (promptc <= 0)
2225     {
2226 	vcol = indent;
2227 	while (indent >= 8)
2228 	{
2229 	    ga_append(&line_ga, TAB);
2230 	    msg_puts((char_u *)"        ");
2231 	    indent -= 8;
2232 	}
2233 	while (indent-- > 0)
2234 	{
2235 	    ga_append(&line_ga, ' ');
2236 	    msg_putchar(' ');
2237 	}
2238     }
2239     ++no_mapping;
2240     ++allow_keys;
2241 
2242     /*
2243      * Get the line, one character at a time.
2244      */
2245     got_int = FALSE;
2246     while (!got_int)
2247     {
2248 	long    sw;
2249 	char_u *s;
2250 
2251 	if (ga_grow(&line_ga, 40) == FAIL)
2252 	    break;
2253 
2254 	/* Get one character at a time.  Don't use inchar(), it can't handle
2255 	 * special characters. */
2256 	prev_char = c1;
2257 	c1 = vgetc();
2258 
2259 	/*
2260 	 * Handle line editing.
2261 	 * Previously this was left to the system, putting the terminal in
2262 	 * cooked mode, but then CTRL-D and CTRL-T can't be used properly.
2263 	 */
2264 	if (got_int)
2265 	{
2266 	    msg_putchar('\n');
2267 	    break;
2268 	}
2269 
2270 	if (!escaped)
2271 	{
2272 	    /* CR typed means "enter", which is NL */
2273 	    if (c1 == '\r')
2274 		c1 = '\n';
2275 
2276 	    if (c1 == BS || c1 == K_BS
2277 			  || c1 == DEL || c1 == K_DEL || c1 == K_KDEL)
2278 	    {
2279 		if (line_ga.ga_len > 0)
2280 		{
2281 #ifdef FEAT_MBYTE
2282 		    if (has_mbyte)
2283 		    {
2284 			p = (char_u *)line_ga.ga_data;
2285 			p[line_ga.ga_len] = NUL;
2286 			len = (*mb_head_off)(p, p + line_ga.ga_len - 1) + 1;
2287 			line_ga.ga_len -= len;
2288 		    }
2289 		    else
2290 #endif
2291 			--line_ga.ga_len;
2292 		    goto redraw;
2293 		}
2294 		continue;
2295 	    }
2296 
2297 	    if (c1 == Ctrl_U)
2298 	    {
2299 		msg_col = startcol;
2300 		msg_clr_eos();
2301 		line_ga.ga_len = 0;
2302 		goto redraw;
2303 	    }
2304 
2305 	    if (c1 == Ctrl_T)
2306 	    {
2307 		sw = get_sw_value(curbuf);
2308 		p = (char_u *)line_ga.ga_data;
2309 		p[line_ga.ga_len] = NUL;
2310 		indent = get_indent_str(p, 8, FALSE);
2311 		indent += sw - indent % sw;
2312 add_indent:
2313 		while (get_indent_str(p, 8, FALSE) < indent)
2314 		{
2315 		    (void)ga_grow(&line_ga, 2);  /* one more for the NUL */
2316 		    p = (char_u *)line_ga.ga_data;
2317 		    s = skipwhite(p);
2318 		    mch_memmove(s + 1, s, line_ga.ga_len - (s - p) + 1);
2319 		    *s = ' ';
2320 		    ++line_ga.ga_len;
2321 		}
2322 redraw:
2323 		/* redraw the line */
2324 		msg_col = startcol;
2325 		vcol = 0;
2326 		p = (char_u *)line_ga.ga_data;
2327 		p[line_ga.ga_len] = NUL;
2328 		while (p < (char_u *)line_ga.ga_data + line_ga.ga_len)
2329 		{
2330 		    if (*p == TAB)
2331 		    {
2332 			do
2333 			{
2334 			    msg_putchar(' ');
2335 			} while (++vcol % 8);
2336 			++p;
2337 		    }
2338 		    else
2339 		    {
2340 			len = MB_PTR2LEN(p);
2341 			msg_outtrans_len(p, len);
2342 			vcol += ptr2cells(p);
2343 			p += len;
2344 		    }
2345 		}
2346 		msg_clr_eos();
2347 		windgoto(msg_row, msg_col);
2348 		continue;
2349 	    }
2350 
2351 	    if (c1 == Ctrl_D)
2352 	    {
2353 		/* Delete one shiftwidth. */
2354 		p = (char_u *)line_ga.ga_data;
2355 		if (prev_char == '0' || prev_char == '^')
2356 		{
2357 		    if (prev_char == '^')
2358 			ex_keep_indent = TRUE;
2359 		    indent = 0;
2360 		    p[--line_ga.ga_len] = NUL;
2361 		}
2362 		else
2363 		{
2364 		    p[line_ga.ga_len] = NUL;
2365 		    indent = get_indent_str(p, 8, FALSE);
2366 		    if (indent > 0)
2367 		    {
2368 			--indent;
2369 			indent -= indent % get_sw_value(curbuf);
2370 		    }
2371 		}
2372 		while (get_indent_str(p, 8, FALSE) > indent)
2373 		{
2374 		    s = skipwhite(p);
2375 		    mch_memmove(s - 1, s, line_ga.ga_len - (s - p) + 1);
2376 		    --line_ga.ga_len;
2377 		}
2378 		goto add_indent;
2379 	    }
2380 
2381 	    if (c1 == Ctrl_V || c1 == Ctrl_Q)
2382 	    {
2383 		escaped = TRUE;
2384 		continue;
2385 	    }
2386 
2387 	    /* Ignore special key codes: mouse movement, K_IGNORE, etc. */
2388 	    if (IS_SPECIAL(c1))
2389 		continue;
2390 	}
2391 
2392 	if (IS_SPECIAL(c1))
2393 	    c1 = '?';
2394 #ifdef FEAT_MBYTE
2395 	if (has_mbyte)
2396 	    len = (*mb_char2bytes)(c1,
2397 				  (char_u *)line_ga.ga_data + line_ga.ga_len);
2398 	else
2399 #endif
2400 	{
2401 	    len = 1;
2402 	    ((char_u *)line_ga.ga_data)[line_ga.ga_len] = c1;
2403 	}
2404 	if (c1 == '\n')
2405 	    msg_putchar('\n');
2406 	else if (c1 == TAB)
2407 	{
2408 	    /* Don't use chartabsize(), 'ts' can be different */
2409 	    do
2410 	    {
2411 		msg_putchar(' ');
2412 	    } while (++vcol % 8);
2413 	}
2414 	else
2415 	{
2416 	    msg_outtrans_len(
2417 		     ((char_u *)line_ga.ga_data) + line_ga.ga_len, len);
2418 	    vcol += char2cells(c1);
2419 	}
2420 	line_ga.ga_len += len;
2421 	escaped = FALSE;
2422 
2423 	windgoto(msg_row, msg_col);
2424 	pend = (char_u *)(line_ga.ga_data) + line_ga.ga_len;
2425 
2426 	/* We are done when a NL is entered, but not when it comes after an
2427 	 * odd number of backslashes, that results in a NUL. */
2428 	if (line_ga.ga_len > 0 && pend[-1] == '\n')
2429 	{
2430 	    int bcount = 0;
2431 
2432 	    while (line_ga.ga_len - 2 >= bcount && pend[-2 - bcount] == '\\')
2433 		++bcount;
2434 
2435 	    if (bcount > 0)
2436 	    {
2437 		/* Halve the number of backslashes: "\NL" -> "NUL", "\\NL" ->
2438 		 * "\NL", etc. */
2439 		line_ga.ga_len -= (bcount + 1) / 2;
2440 		pend -= (bcount + 1) / 2;
2441 		pend[-1] = '\n';
2442 	    }
2443 
2444 	    if ((bcount & 1) == 0)
2445 	    {
2446 		--line_ga.ga_len;
2447 		--pend;
2448 		*pend = NUL;
2449 		break;
2450 	    }
2451 	}
2452     }
2453 
2454     --no_mapping;
2455     --allow_keys;
2456 
2457     /* make following messages go to the next line */
2458     msg_didout = FALSE;
2459     msg_col = 0;
2460     if (msg_row < Rows - 1)
2461 	++msg_row;
2462     emsg_on_display = FALSE;		/* don't want ui_delay() */
2463 
2464     if (got_int)
2465 	ga_clear(&line_ga);
2466 
2467     return (char_u *)line_ga.ga_data;
2468 }
2469 
2470 # if defined(MCH_CURSOR_SHAPE) || defined(FEAT_GUI) \
2471 	|| defined(FEAT_MOUSESHAPE) || defined(PROTO)
2472 /*
2473  * Return TRUE if ccline.overstrike is on.
2474  */
2475     int
2476 cmdline_overstrike()
2477 {
2478     return ccline.overstrike;
2479 }
2480 
2481 /*
2482  * Return TRUE if the cursor is at the end of the cmdline.
2483  */
2484     int
2485 cmdline_at_end()
2486 {
2487     return (ccline.cmdpos >= ccline.cmdlen);
2488 }
2489 #endif
2490 
2491 #if (defined(FEAT_XIM) && (defined(FEAT_GUI_GTK))) || defined(PROTO)
2492 /*
2493  * Return the virtual column number at the current cursor position.
2494  * This is used by the IM code to obtain the start of the preedit string.
2495  */
2496     colnr_T
2497 cmdline_getvcol_cursor()
2498 {
2499     if (ccline.cmdbuff == NULL || ccline.cmdpos > ccline.cmdlen)
2500 	return MAXCOL;
2501 
2502 # ifdef FEAT_MBYTE
2503     if (has_mbyte)
2504     {
2505 	colnr_T	col;
2506 	int	i = 0;
2507 
2508 	for (col = 0; i < ccline.cmdpos; ++col)
2509 	    i += (*mb_ptr2len)(ccline.cmdbuff + i);
2510 
2511 	return col;
2512     }
2513     else
2514 # endif
2515 	return ccline.cmdpos;
2516 }
2517 #endif
2518 
2519 #if defined(FEAT_XIM) && defined(FEAT_GUI_GTK)
2520 /*
2521  * If part of the command line is an IM preedit string, redraw it with
2522  * IM feedback attributes.  The cursor position is restored after drawing.
2523  */
2524     static void
2525 redrawcmd_preedit()
2526 {
2527     if ((State & CMDLINE)
2528 	    && xic != NULL
2529 	    /* && im_get_status()  doesn't work when using SCIM */
2530 	    && !p_imdisable
2531 	    && im_is_preediting())
2532     {
2533 	int	cmdpos = 0;
2534 	int	cmdspos;
2535 	int	old_row;
2536 	int	old_col;
2537 	colnr_T	col;
2538 
2539 	old_row = msg_row;
2540 	old_col = msg_col;
2541 	cmdspos = ((ccline.cmdfirstc != NUL) ? 1 : 0) + ccline.cmdindent;
2542 
2543 # ifdef FEAT_MBYTE
2544 	if (has_mbyte)
2545 	{
2546 	    for (col = 0; col < preedit_start_col
2547 			  && cmdpos < ccline.cmdlen; ++col)
2548 	    {
2549 		cmdspos += (*mb_ptr2cells)(ccline.cmdbuff + cmdpos);
2550 		cmdpos  += (*mb_ptr2len)(ccline.cmdbuff + cmdpos);
2551 	    }
2552 	}
2553 	else
2554 # endif
2555 	{
2556 	    cmdspos += preedit_start_col;
2557 	    cmdpos  += preedit_start_col;
2558 	}
2559 
2560 	msg_row = cmdline_row + (cmdspos / (int)Columns);
2561 	msg_col = cmdspos % (int)Columns;
2562 	if (msg_row >= Rows)
2563 	    msg_row = Rows - 1;
2564 
2565 	for (col = 0; cmdpos < ccline.cmdlen; ++col)
2566 	{
2567 	    int char_len;
2568 	    int char_attr;
2569 
2570 	    char_attr = im_get_feedback_attr(col);
2571 	    if (char_attr < 0)
2572 		break; /* end of preedit string */
2573 
2574 # ifdef FEAT_MBYTE
2575 	    if (has_mbyte)
2576 		char_len = (*mb_ptr2len)(ccline.cmdbuff + cmdpos);
2577 	    else
2578 # endif
2579 		char_len = 1;
2580 
2581 	    msg_outtrans_len_attr(ccline.cmdbuff + cmdpos, char_len, char_attr);
2582 	    cmdpos += char_len;
2583 	}
2584 
2585 	msg_row = old_row;
2586 	msg_col = old_col;
2587     }
2588 }
2589 #endif /* FEAT_XIM && FEAT_GUI_GTK */
2590 
2591 /*
2592  * Allocate a new command line buffer.
2593  * Assigns the new buffer to ccline.cmdbuff and ccline.cmdbufflen.
2594  * Returns the new value of ccline.cmdbuff and ccline.cmdbufflen.
2595  */
2596     static void
2597 alloc_cmdbuff(len)
2598     int	    len;
2599 {
2600     /*
2601      * give some extra space to avoid having to allocate all the time
2602      */
2603     if (len < 80)
2604 	len = 100;
2605     else
2606 	len += 20;
2607 
2608     ccline.cmdbuff = alloc(len);    /* caller should check for out-of-memory */
2609     ccline.cmdbufflen = len;
2610 }
2611 
2612 /*
2613  * Re-allocate the command line to length len + something extra.
2614  * return FAIL for failure, OK otherwise
2615  */
2616     static int
2617 realloc_cmdbuff(len)
2618     int	    len;
2619 {
2620     char_u	*p;
2621 
2622     if (len < ccline.cmdbufflen)
2623 	return OK;			/* no need to resize */
2624 
2625     p = ccline.cmdbuff;
2626     alloc_cmdbuff(len);			/* will get some more */
2627     if (ccline.cmdbuff == NULL)		/* out of memory */
2628     {
2629 	ccline.cmdbuff = p;		/* keep the old one */
2630 	return FAIL;
2631     }
2632     /* There isn't always a NUL after the command, but it may need to be
2633      * there, thus copy up to the NUL and add a NUL. */
2634     mch_memmove(ccline.cmdbuff, p, (size_t)ccline.cmdlen);
2635     ccline.cmdbuff[ccline.cmdlen] = NUL;
2636     vim_free(p);
2637 
2638     if (ccline.xpc != NULL
2639 	    && ccline.xpc->xp_pattern != NULL
2640 	    && ccline.xpc->xp_context != EXPAND_NOTHING
2641 	    && ccline.xpc->xp_context != EXPAND_UNSUCCESSFUL)
2642     {
2643 	int i = (int)(ccline.xpc->xp_pattern - p);
2644 
2645 	/* If xp_pattern points inside the old cmdbuff it needs to be adjusted
2646 	 * to point into the newly allocated memory. */
2647 	if (i >= 0 && i <= ccline.cmdlen)
2648 	    ccline.xpc->xp_pattern = ccline.cmdbuff + i;
2649     }
2650 
2651     return OK;
2652 }
2653 
2654 #if defined(FEAT_ARABIC) || defined(PROTO)
2655 static char_u	*arshape_buf = NULL;
2656 
2657 # if defined(EXITFREE) || defined(PROTO)
2658     void
2659 free_cmdline_buf()
2660 {
2661     vim_free(arshape_buf);
2662 }
2663 # endif
2664 #endif
2665 
2666 /*
2667  * Draw part of the cmdline at the current cursor position.  But draw stars
2668  * when cmdline_star is TRUE.
2669  */
2670     static void
2671 draw_cmdline(start, len)
2672     int		start;
2673     int		len;
2674 {
2675 #if defined(FEAT_CRYPT) || defined(FEAT_EVAL)
2676     int		i;
2677 
2678     if (cmdline_star > 0)
2679 	for (i = 0; i < len; ++i)
2680 	{
2681 	    msg_putchar('*');
2682 # ifdef FEAT_MBYTE
2683 	    if (has_mbyte)
2684 		i += (*mb_ptr2len)(ccline.cmdbuff + start + i) - 1;
2685 # endif
2686 	}
2687     else
2688 #endif
2689 #ifdef FEAT_ARABIC
2690 	if (p_arshape && !p_tbidi && enc_utf8 && len > 0)
2691     {
2692 	static int	buflen = 0;
2693 	char_u		*p;
2694 	int		j;
2695 	int		newlen = 0;
2696 	int		mb_l;
2697 	int		pc, pc1 = 0;
2698 	int		prev_c = 0;
2699 	int		prev_c1 = 0;
2700 	int		u8c;
2701 	int		u8cc[MAX_MCO];
2702 	int		nc = 0;
2703 
2704 	/*
2705 	 * Do arabic shaping into a temporary buffer.  This is very
2706 	 * inefficient!
2707 	 */
2708 	if (len * 2 + 2 > buflen)
2709 	{
2710 	    /* Re-allocate the buffer.  We keep it around to avoid a lot of
2711 	     * alloc()/free() calls. */
2712 	    vim_free(arshape_buf);
2713 	    buflen = len * 2 + 2;
2714 	    arshape_buf = alloc(buflen);
2715 	    if (arshape_buf == NULL)
2716 		return;	/* out of memory */
2717 	}
2718 
2719 	if (utf_iscomposing(utf_ptr2char(ccline.cmdbuff + start)))
2720 	{
2721 	    /* Prepend a space to draw the leading composing char on. */
2722 	    arshape_buf[0] = ' ';
2723 	    newlen = 1;
2724 	}
2725 
2726 	for (j = start; j < start + len; j += mb_l)
2727 	{
2728 	    p = ccline.cmdbuff + j;
2729 	    u8c = utfc_ptr2char_len(p, u8cc, start + len - j);
2730 	    mb_l = utfc_ptr2len_len(p, start + len - j);
2731 	    if (ARABIC_CHAR(u8c))
2732 	    {
2733 		/* Do Arabic shaping. */
2734 		if (cmdmsg_rl)
2735 		{
2736 		    /* displaying from right to left */
2737 		    pc = prev_c;
2738 		    pc1 = prev_c1;
2739 		    prev_c1 = u8cc[0];
2740 		    if (j + mb_l >= start + len)
2741 			nc = NUL;
2742 		    else
2743 			nc = utf_ptr2char(p + mb_l);
2744 		}
2745 		else
2746 		{
2747 		    /* displaying from left to right */
2748 		    if (j + mb_l >= start + len)
2749 			pc = NUL;
2750 		    else
2751 		    {
2752 			int	pcc[MAX_MCO];
2753 
2754 			pc = utfc_ptr2char_len(p + mb_l, pcc,
2755 						      start + len - j - mb_l);
2756 			pc1 = pcc[0];
2757 		    }
2758 		    nc = prev_c;
2759 		}
2760 		prev_c = u8c;
2761 
2762 		u8c = arabic_shape(u8c, NULL, &u8cc[0], pc, pc1, nc);
2763 
2764 		newlen += (*mb_char2bytes)(u8c, arshape_buf + newlen);
2765 		if (u8cc[0] != 0)
2766 		{
2767 		    newlen += (*mb_char2bytes)(u8cc[0], arshape_buf + newlen);
2768 		    if (u8cc[1] != 0)
2769 			newlen += (*mb_char2bytes)(u8cc[1],
2770 							arshape_buf + newlen);
2771 		}
2772 	    }
2773 	    else
2774 	    {
2775 		prev_c = u8c;
2776 		mch_memmove(arshape_buf + newlen, p, mb_l);
2777 		newlen += mb_l;
2778 	    }
2779 	}
2780 
2781 	msg_outtrans_len(arshape_buf, newlen);
2782     }
2783     else
2784 #endif
2785 	msg_outtrans_len(ccline.cmdbuff + start, len);
2786 }
2787 
2788 /*
2789  * Put a character on the command line.  Shifts the following text to the
2790  * right when "shift" is TRUE.  Used for CTRL-V, CTRL-K, etc.
2791  * "c" must be printable (fit in one display cell)!
2792  */
2793     void
2794 putcmdline(c, shift)
2795     int		c;
2796     int		shift;
2797 {
2798     if (cmd_silent)
2799 	return;
2800     msg_no_more = TRUE;
2801     msg_putchar(c);
2802     if (shift)
2803 	draw_cmdline(ccline.cmdpos, ccline.cmdlen - ccline.cmdpos);
2804     msg_no_more = FALSE;
2805     cursorcmd();
2806 }
2807 
2808 /*
2809  * Undo a putcmdline(c, FALSE).
2810  */
2811     void
2812 unputcmdline()
2813 {
2814     if (cmd_silent)
2815 	return;
2816     msg_no_more = TRUE;
2817     if (ccline.cmdlen == ccline.cmdpos)
2818 	msg_putchar(' ');
2819 #ifdef FEAT_MBYTE
2820     else if (has_mbyte)
2821 	draw_cmdline(ccline.cmdpos,
2822 			       (*mb_ptr2len)(ccline.cmdbuff + ccline.cmdpos));
2823 #endif
2824     else
2825 	draw_cmdline(ccline.cmdpos, 1);
2826     msg_no_more = FALSE;
2827     cursorcmd();
2828 }
2829 
2830 /*
2831  * Put the given string, of the given length, onto the command line.
2832  * If len is -1, then STRLEN() is used to calculate the length.
2833  * If 'redraw' is TRUE then the new part of the command line, and the remaining
2834  * part will be redrawn, otherwise it will not.  If this function is called
2835  * twice in a row, then 'redraw' should be FALSE and redrawcmd() should be
2836  * called afterwards.
2837  */
2838     int
2839 put_on_cmdline(str, len, redraw)
2840     char_u	*str;
2841     int		len;
2842     int		redraw;
2843 {
2844     int		retval;
2845     int		i;
2846     int		m;
2847     int		c;
2848 
2849     if (len < 0)
2850 	len = (int)STRLEN(str);
2851 
2852     /* Check if ccline.cmdbuff needs to be longer */
2853     if (ccline.cmdlen + len + 1 >= ccline.cmdbufflen)
2854 	retval = realloc_cmdbuff(ccline.cmdlen + len + 1);
2855     else
2856 	retval = OK;
2857     if (retval == OK)
2858     {
2859 	if (!ccline.overstrike)
2860 	{
2861 	    mch_memmove(ccline.cmdbuff + ccline.cmdpos + len,
2862 					       ccline.cmdbuff + ccline.cmdpos,
2863 				     (size_t)(ccline.cmdlen - ccline.cmdpos));
2864 	    ccline.cmdlen += len;
2865 	}
2866 	else
2867 	{
2868 #ifdef FEAT_MBYTE
2869 	    if (has_mbyte)
2870 	    {
2871 		/* Count nr of characters in the new string. */
2872 		m = 0;
2873 		for (i = 0; i < len; i += (*mb_ptr2len)(str + i))
2874 		    ++m;
2875 		/* Count nr of bytes in cmdline that are overwritten by these
2876 		 * characters. */
2877 		for (i = ccline.cmdpos; i < ccline.cmdlen && m > 0;
2878 				 i += (*mb_ptr2len)(ccline.cmdbuff + i))
2879 		    --m;
2880 		if (i < ccline.cmdlen)
2881 		{
2882 		    mch_memmove(ccline.cmdbuff + ccline.cmdpos + len,
2883 			    ccline.cmdbuff + i, (size_t)(ccline.cmdlen - i));
2884 		    ccline.cmdlen += ccline.cmdpos + len - i;
2885 		}
2886 		else
2887 		    ccline.cmdlen = ccline.cmdpos + len;
2888 	    }
2889 	    else
2890 #endif
2891 	    if (ccline.cmdpos + len > ccline.cmdlen)
2892 		ccline.cmdlen = ccline.cmdpos + len;
2893 	}
2894 	mch_memmove(ccline.cmdbuff + ccline.cmdpos, str, (size_t)len);
2895 	ccline.cmdbuff[ccline.cmdlen] = NUL;
2896 
2897 #ifdef FEAT_MBYTE
2898 	if (enc_utf8)
2899 	{
2900 	    /* When the inserted text starts with a composing character,
2901 	     * backup to the character before it.  There could be two of them.
2902 	     */
2903 	    i = 0;
2904 	    c = utf_ptr2char(ccline.cmdbuff + ccline.cmdpos);
2905 	    while (ccline.cmdpos > 0 && utf_iscomposing(c))
2906 	    {
2907 		i = (*mb_head_off)(ccline.cmdbuff,
2908 				      ccline.cmdbuff + ccline.cmdpos - 1) + 1;
2909 		ccline.cmdpos -= i;
2910 		len += i;
2911 		c = utf_ptr2char(ccline.cmdbuff + ccline.cmdpos);
2912 	    }
2913 # ifdef FEAT_ARABIC
2914 	    if (i == 0 && ccline.cmdpos > 0 && arabic_maycombine(c))
2915 	    {
2916 		/* Check the previous character for Arabic combining pair. */
2917 		i = (*mb_head_off)(ccline.cmdbuff,
2918 				      ccline.cmdbuff + ccline.cmdpos - 1) + 1;
2919 		if (arabic_combine(utf_ptr2char(ccline.cmdbuff
2920 						     + ccline.cmdpos - i), c))
2921 		{
2922 		    ccline.cmdpos -= i;
2923 		    len += i;
2924 		}
2925 		else
2926 		    i = 0;
2927 	    }
2928 # endif
2929 	    if (i != 0)
2930 	    {
2931 		/* Also backup the cursor position. */
2932 		i = ptr2cells(ccline.cmdbuff + ccline.cmdpos);
2933 		ccline.cmdspos -= i;
2934 		msg_col -= i;
2935 		if (msg_col < 0)
2936 		{
2937 		    msg_col += Columns;
2938 		    --msg_row;
2939 		}
2940 	    }
2941 	}
2942 #endif
2943 
2944 	if (redraw && !cmd_silent)
2945 	{
2946 	    msg_no_more = TRUE;
2947 	    i = cmdline_row;
2948 	    cursorcmd();
2949 	    draw_cmdline(ccline.cmdpos, ccline.cmdlen - ccline.cmdpos);
2950 	    /* Avoid clearing the rest of the line too often. */
2951 	    if (cmdline_row != i || ccline.overstrike)
2952 		msg_clr_eos();
2953 	    msg_no_more = FALSE;
2954 	}
2955 #ifdef FEAT_FKMAP
2956 	/*
2957 	 * If we are in Farsi command mode, the character input must be in
2958 	 * Insert mode. So do not advance the cmdpos.
2959 	 */
2960 	if (!cmd_fkmap)
2961 #endif
2962 	{
2963 	    if (KeyTyped)
2964 	    {
2965 		m = Columns * Rows;
2966 		if (m < 0)	/* overflow, Columns or Rows at weird value */
2967 		    m = MAXCOL;
2968 	    }
2969 	    else
2970 		m = MAXCOL;
2971 	    for (i = 0; i < len; ++i)
2972 	    {
2973 		c = cmdline_charsize(ccline.cmdpos);
2974 #ifdef FEAT_MBYTE
2975 		/* count ">" for a double-wide char that doesn't fit. */
2976 		if (has_mbyte)
2977 		    correct_cmdspos(ccline.cmdpos, c);
2978 #endif
2979 		/* Stop cursor at the end of the screen, but do increment the
2980 		 * insert position, so that entering a very long command
2981 		 * works, even though you can't see it. */
2982 		if (ccline.cmdspos + c < m)
2983 		    ccline.cmdspos += c;
2984 #ifdef FEAT_MBYTE
2985 		if (has_mbyte)
2986 		{
2987 		    c = (*mb_ptr2len)(ccline.cmdbuff + ccline.cmdpos) - 1;
2988 		    if (c > len - i - 1)
2989 			c = len - i - 1;
2990 		    ccline.cmdpos += c;
2991 		    i += c;
2992 		}
2993 #endif
2994 		++ccline.cmdpos;
2995 	    }
2996 	}
2997     }
2998     if (redraw)
2999 	msg_check();
3000     return retval;
3001 }
3002 
3003 static struct cmdline_info  prev_ccline;
3004 static int		    prev_ccline_used = FALSE;
3005 
3006 /*
3007  * Save ccline, because obtaining the "=" register may execute "normal :cmd"
3008  * and overwrite it.  But get_cmdline_str() may need it, thus make it
3009  * available globally in prev_ccline.
3010  */
3011     static void
3012 save_cmdline(ccp)
3013     struct cmdline_info *ccp;
3014 {
3015     if (!prev_ccline_used)
3016     {
3017 	vim_memset(&prev_ccline, 0, sizeof(struct cmdline_info));
3018 	prev_ccline_used = TRUE;
3019     }
3020     *ccp = prev_ccline;
3021     prev_ccline = ccline;
3022     ccline.cmdbuff = NULL;
3023     ccline.cmdprompt = NULL;
3024     ccline.xpc = NULL;
3025 }
3026 
3027 /*
3028  * Restore ccline after it has been saved with save_cmdline().
3029  */
3030     static void
3031 restore_cmdline(ccp)
3032     struct cmdline_info *ccp;
3033 {
3034     ccline = prev_ccline;
3035     prev_ccline = *ccp;
3036 }
3037 
3038 #if defined(FEAT_EVAL) || defined(PROTO)
3039 /*
3040  * Save the command line into allocated memory.  Returns a pointer to be
3041  * passed to restore_cmdline_alloc() later.
3042  * Returns NULL when failed.
3043  */
3044     char_u *
3045 save_cmdline_alloc()
3046 {
3047     struct cmdline_info *p;
3048 
3049     p = (struct cmdline_info *)alloc((unsigned)sizeof(struct cmdline_info));
3050     if (p != NULL)
3051 	save_cmdline(p);
3052     return (char_u *)p;
3053 }
3054 
3055 /*
3056  * Restore the command line from the return value of save_cmdline_alloc().
3057  */
3058     void
3059 restore_cmdline_alloc(p)
3060     char_u  *p;
3061 {
3062     if (p != NULL)
3063     {
3064 	restore_cmdline((struct cmdline_info *)p);
3065 	vim_free(p);
3066     }
3067 }
3068 #endif
3069 
3070 /*
3071  * Paste a yank register into the command line.
3072  * Used by CTRL-R command in command-line mode.
3073  * insert_reg() can't be used here, because special characters from the
3074  * register contents will be interpreted as commands.
3075  *
3076  * Return FAIL for failure, OK otherwise.
3077  */
3078     static int
3079 cmdline_paste(regname, literally, remcr)
3080     int regname;
3081     int literally;	/* Insert text literally instead of "as typed" */
3082     int remcr;		/* remove trailing CR */
3083 {
3084     long		i;
3085     char_u		*arg;
3086     char_u		*p;
3087     int			allocated;
3088     struct cmdline_info	save_ccline;
3089 
3090     /* check for valid regname; also accept special characters for CTRL-R in
3091      * the command line */
3092     if (regname != Ctrl_F && regname != Ctrl_P && regname != Ctrl_W
3093 	    && regname != Ctrl_A && !valid_yank_reg(regname, FALSE))
3094 	return FAIL;
3095 
3096     /* A register containing CTRL-R can cause an endless loop.  Allow using
3097      * CTRL-C to break the loop. */
3098     line_breakcheck();
3099     if (got_int)
3100 	return FAIL;
3101 
3102 #ifdef FEAT_CLIPBOARD
3103     regname = may_get_selection(regname);
3104 #endif
3105 
3106     /* Need to save and restore ccline.  And set "textlock" to avoid nasty
3107      * things like going to another buffer when evaluating an expression. */
3108     save_cmdline(&save_ccline);
3109     ++textlock;
3110     i = get_spec_reg(regname, &arg, &allocated, TRUE);
3111     --textlock;
3112     restore_cmdline(&save_ccline);
3113 
3114     if (i)
3115     {
3116 	/* Got the value of a special register in "arg". */
3117 	if (arg == NULL)
3118 	    return FAIL;
3119 
3120 	/* When 'incsearch' is set and CTRL-R CTRL-W used: skip the duplicate
3121 	 * part of the word. */
3122 	p = arg;
3123 	if (p_is && regname == Ctrl_W)
3124 	{
3125 	    char_u  *w;
3126 	    int	    len;
3127 
3128 	    /* Locate start of last word in the cmd buffer. */
3129 	    for (w = ccline.cmdbuff + ccline.cmdpos; w > ccline.cmdbuff; )
3130 	    {
3131 #ifdef FEAT_MBYTE
3132 		if (has_mbyte)
3133 		{
3134 		    len = (*mb_head_off)(ccline.cmdbuff, w - 1) + 1;
3135 		    if (!vim_iswordc(mb_ptr2char(w - len)))
3136 			break;
3137 		    w -= len;
3138 		}
3139 		else
3140 #endif
3141 		{
3142 		    if (!vim_iswordc(w[-1]))
3143 			break;
3144 		    --w;
3145 		}
3146 	    }
3147 	    len = (int)((ccline.cmdbuff + ccline.cmdpos) - w);
3148 	    if (p_ic ? STRNICMP(w, arg, len) == 0 : STRNCMP(w, arg, len) == 0)
3149 		p += len;
3150 	}
3151 
3152 	cmdline_paste_str(p, literally);
3153 	if (allocated)
3154 	    vim_free(arg);
3155 	return OK;
3156     }
3157 
3158     return cmdline_paste_reg(regname, literally, remcr);
3159 }
3160 
3161 /*
3162  * Put a string on the command line.
3163  * When "literally" is TRUE, insert literally.
3164  * When "literally" is FALSE, insert as typed, but don't leave the command
3165  * line.
3166  */
3167     void
3168 cmdline_paste_str(s, literally)
3169     char_u	*s;
3170     int		literally;
3171 {
3172     int		c, cv;
3173 
3174     if (literally)
3175 	put_on_cmdline(s, -1, TRUE);
3176     else
3177 	while (*s != NUL)
3178 	{
3179 	    cv = *s;
3180 	    if (cv == Ctrl_V && s[1])
3181 		++s;
3182 #ifdef FEAT_MBYTE
3183 	    if (has_mbyte)
3184 		c = mb_cptr2char_adv(&s);
3185 	    else
3186 #endif
3187 		c = *s++;
3188 	    if (cv == Ctrl_V || c == ESC || c == Ctrl_C
3189 		    || c == CAR || c == NL || c == Ctrl_L
3190 #ifdef UNIX
3191 		    || c == intr_char
3192 #endif
3193 		    || (c == Ctrl_BSL && *s == Ctrl_N))
3194 		stuffcharReadbuff(Ctrl_V);
3195 	    stuffcharReadbuff(c);
3196 	}
3197 }
3198 
3199 #ifdef FEAT_WILDMENU
3200 /*
3201  * Delete characters on the command line, from "from" to the current
3202  * position.
3203  */
3204     static void
3205 cmdline_del(from)
3206     int from;
3207 {
3208     mch_memmove(ccline.cmdbuff + from, ccline.cmdbuff + ccline.cmdpos,
3209 	    (size_t)(ccline.cmdlen - ccline.cmdpos + 1));
3210     ccline.cmdlen -= ccline.cmdpos - from;
3211     ccline.cmdpos = from;
3212 }
3213 #endif
3214 
3215 /*
3216  * this function is called when the screen size changes and with incremental
3217  * search
3218  */
3219     void
3220 redrawcmdline()
3221 {
3222     if (cmd_silent)
3223 	return;
3224     need_wait_return = FALSE;
3225     compute_cmdrow();
3226     redrawcmd();
3227     cursorcmd();
3228 }
3229 
3230     static void
3231 redrawcmdprompt()
3232 {
3233     int		i;
3234 
3235     if (cmd_silent)
3236 	return;
3237     if (ccline.cmdfirstc != NUL)
3238 	msg_putchar(ccline.cmdfirstc);
3239     if (ccline.cmdprompt != NULL)
3240     {
3241 	msg_puts_attr(ccline.cmdprompt, ccline.cmdattr);
3242 	ccline.cmdindent = msg_col + (msg_row - cmdline_row) * Columns;
3243 	/* do the reverse of set_cmdspos() */
3244 	if (ccline.cmdfirstc != NUL)
3245 	    --ccline.cmdindent;
3246     }
3247     else
3248 	for (i = ccline.cmdindent; i > 0; --i)
3249 	    msg_putchar(' ');
3250 }
3251 
3252 /*
3253  * Redraw what is currently on the command line.
3254  */
3255     void
3256 redrawcmd()
3257 {
3258     if (cmd_silent)
3259 	return;
3260 
3261     /* when 'incsearch' is set there may be no command line while redrawing */
3262     if (ccline.cmdbuff == NULL)
3263     {
3264 	windgoto(cmdline_row, 0);
3265 	msg_clr_eos();
3266 	return;
3267     }
3268 
3269     msg_start();
3270     redrawcmdprompt();
3271 
3272     /* Don't use more prompt, truncate the cmdline if it doesn't fit. */
3273     msg_no_more = TRUE;
3274     draw_cmdline(0, ccline.cmdlen);
3275     msg_clr_eos();
3276     msg_no_more = FALSE;
3277 
3278     set_cmdspos_cursor();
3279 
3280     /*
3281      * An emsg() before may have set msg_scroll. This is used in normal mode,
3282      * in cmdline mode we can reset them now.
3283      */
3284     msg_scroll = FALSE;		/* next message overwrites cmdline */
3285 
3286     /* Typing ':' at the more prompt may set skip_redraw.  We don't want this
3287      * in cmdline mode */
3288     skip_redraw = FALSE;
3289 }
3290 
3291     void
3292 compute_cmdrow()
3293 {
3294     if (exmode_active || msg_scrolled != 0)
3295 	cmdline_row = Rows - 1;
3296     else
3297 	cmdline_row = W_WINROW(lastwin) + lastwin->w_height
3298 						   + W_STATUS_HEIGHT(lastwin);
3299 }
3300 
3301     static void
3302 cursorcmd()
3303 {
3304     if (cmd_silent)
3305 	return;
3306 
3307 #ifdef FEAT_RIGHTLEFT
3308     if (cmdmsg_rl)
3309     {
3310 	msg_row = cmdline_row  + (ccline.cmdspos / (int)(Columns - 1));
3311 	msg_col = (int)Columns - (ccline.cmdspos % (int)(Columns - 1)) - 1;
3312 	if (msg_row <= 0)
3313 	    msg_row = Rows - 1;
3314     }
3315     else
3316 #endif
3317     {
3318 	msg_row = cmdline_row + (ccline.cmdspos / (int)Columns);
3319 	msg_col = ccline.cmdspos % (int)Columns;
3320 	if (msg_row >= Rows)
3321 	    msg_row = Rows - 1;
3322     }
3323 
3324     windgoto(msg_row, msg_col);
3325 #if defined(FEAT_XIM) && defined(FEAT_GUI_GTK)
3326     redrawcmd_preedit();
3327 #endif
3328 #ifdef MCH_CURSOR_SHAPE
3329     mch_update_cursor();
3330 #endif
3331 }
3332 
3333     void
3334 gotocmdline(clr)
3335     int		    clr;
3336 {
3337     msg_start();
3338 #ifdef FEAT_RIGHTLEFT
3339     if (cmdmsg_rl)
3340 	msg_col = Columns - 1;
3341     else
3342 #endif
3343 	msg_col = 0;	    /* always start in column 0 */
3344     if (clr)		    /* clear the bottom line(s) */
3345 	msg_clr_eos();	    /* will reset clear_cmdline */
3346     windgoto(cmdline_row, 0);
3347 }
3348 
3349 /*
3350  * Check the word in front of the cursor for an abbreviation.
3351  * Called when the non-id character "c" has been entered.
3352  * When an abbreviation is recognized it is removed from the text with
3353  * backspaces and the replacement string is inserted, followed by "c".
3354  */
3355     static int
3356 ccheck_abbr(c)
3357     int c;
3358 {
3359     if (p_paste || no_abbr)	    /* no abbreviations or in paste mode */
3360 	return FALSE;
3361 
3362     return check_abbr(c, ccline.cmdbuff, ccline.cmdpos, 0);
3363 }
3364 
3365 #if defined(FEAT_CMDL_COMPL) || defined(PROTO)
3366     static int
3367 #ifdef __BORLANDC__
3368 _RTLENTRYF
3369 #endif
3370 sort_func_compare(s1, s2)
3371     const void *s1;
3372     const void *s2;
3373 {
3374     char_u *p1 = *(char_u **)s1;
3375     char_u *p2 = *(char_u **)s2;
3376 
3377     if (*p1 != '<' && *p2 == '<') return -1;
3378     if (*p1 == '<' && *p2 != '<') return 1;
3379     return STRCMP(p1, p2);
3380 }
3381 #endif
3382 
3383 /*
3384  * Return FAIL if this is not an appropriate context in which to do
3385  * completion of anything, return OK if it is (even if there are no matches).
3386  * For the caller, this means that the character is just passed through like a
3387  * normal character (instead of being expanded).  This allows :s/^I^D etc.
3388  */
3389     static int
3390 nextwild(xp, type, options, escape)
3391     expand_T	*xp;
3392     int		type;
3393     int		options;	/* extra options for ExpandOne() */
3394     int		escape;		/* if TRUE, escape the returned matches */
3395 {
3396     int		i, j;
3397     char_u	*p1;
3398     char_u	*p2;
3399     int		difflen;
3400     int		v;
3401 
3402     if (xp->xp_numfiles == -1)
3403     {
3404 	set_expand_context(xp);
3405 	cmd_showtail = expand_showtail(xp);
3406     }
3407 
3408     if (xp->xp_context == EXPAND_UNSUCCESSFUL)
3409     {
3410 	beep_flush();
3411 	return OK;  /* Something illegal on command line */
3412     }
3413     if (xp->xp_context == EXPAND_NOTHING)
3414     {
3415 	/* Caller can use the character as a normal char instead */
3416 	return FAIL;
3417     }
3418 
3419     MSG_PUTS("...");	    /* show that we are busy */
3420     out_flush();
3421 
3422     i = (int)(xp->xp_pattern - ccline.cmdbuff);
3423     xp->xp_pattern_len = ccline.cmdpos - i;
3424 
3425     if (type == WILD_NEXT || type == WILD_PREV)
3426     {
3427 	/*
3428 	 * Get next/previous match for a previous expanded pattern.
3429 	 */
3430 	p2 = ExpandOne(xp, NULL, NULL, 0, type);
3431     }
3432     else
3433     {
3434 	/*
3435 	 * Translate string into pattern and expand it.
3436 	 */
3437 	if ((p1 = addstar(xp->xp_pattern, xp->xp_pattern_len,
3438 						     xp->xp_context)) == NULL)
3439 	    p2 = NULL;
3440 	else
3441 	{
3442 	    int use_options = options |
3443 		    WILD_HOME_REPLACE|WILD_ADD_SLASH|WILD_SILENT;
3444 	    if (escape)
3445 		use_options |= WILD_ESCAPE;
3446 
3447 	    if (p_wic)
3448 		use_options += WILD_ICASE;
3449 	    p2 = ExpandOne(xp, p1,
3450 			 vim_strnsave(&ccline.cmdbuff[i], xp->xp_pattern_len),
3451 							   use_options, type);
3452 	    vim_free(p1);
3453 	    /* longest match: make sure it is not shorter, happens with :help */
3454 	    if (p2 != NULL && type == WILD_LONGEST)
3455 	    {
3456 		for (j = 0; j < xp->xp_pattern_len; ++j)
3457 		     if (ccline.cmdbuff[i + j] == '*'
3458 			     || ccline.cmdbuff[i + j] == '?')
3459 			 break;
3460 		if ((int)STRLEN(p2) < j)
3461 		{
3462 		    vim_free(p2);
3463 		    p2 = NULL;
3464 		}
3465 	    }
3466 	}
3467     }
3468 
3469     if (p2 != NULL && !got_int)
3470     {
3471 	difflen = (int)STRLEN(p2) - xp->xp_pattern_len;
3472 	if (ccline.cmdlen + difflen + 4 > ccline.cmdbufflen)
3473 	{
3474 	    v = realloc_cmdbuff(ccline.cmdlen + difflen + 4);
3475 	    xp->xp_pattern = ccline.cmdbuff + i;
3476 	}
3477 	else
3478 	    v = OK;
3479 	if (v == OK)
3480 	{
3481 	    mch_memmove(&ccline.cmdbuff[ccline.cmdpos + difflen],
3482 		    &ccline.cmdbuff[ccline.cmdpos],
3483 		    (size_t)(ccline.cmdlen - ccline.cmdpos + 1));
3484 	    mch_memmove(&ccline.cmdbuff[i], p2, STRLEN(p2));
3485 	    ccline.cmdlen += difflen;
3486 	    ccline.cmdpos += difflen;
3487 	}
3488     }
3489     vim_free(p2);
3490 
3491     redrawcmd();
3492     cursorcmd();
3493 
3494     /* When expanding a ":map" command and no matches are found, assume that
3495      * the key is supposed to be inserted literally */
3496     if (xp->xp_context == EXPAND_MAPPINGS && p2 == NULL)
3497 	return FAIL;
3498 
3499     if (xp->xp_numfiles <= 0 && p2 == NULL)
3500 	beep_flush();
3501     else if (xp->xp_numfiles == 1)
3502 	/* free expanded pattern */
3503 	(void)ExpandOne(xp, NULL, NULL, 0, WILD_FREE);
3504 
3505     return OK;
3506 }
3507 
3508 /*
3509  * Do wildcard expansion on the string 'str'.
3510  * Chars that should not be expanded must be preceded with a backslash.
3511  * Return a pointer to allocated memory containing the new string.
3512  * Return NULL for failure.
3513  *
3514  * "orig" is the originally expanded string, copied to allocated memory.  It
3515  * should either be kept in orig_save or freed.  When "mode" is WILD_NEXT or
3516  * WILD_PREV "orig" should be NULL.
3517  *
3518  * Results are cached in xp->xp_files and xp->xp_numfiles, except when "mode"
3519  * is WILD_EXPAND_FREE or WILD_ALL.
3520  *
3521  * mode = WILD_FREE:	    just free previously expanded matches
3522  * mode = WILD_EXPAND_FREE: normal expansion, do not keep matches
3523  * mode = WILD_EXPAND_KEEP: normal expansion, keep matches
3524  * mode = WILD_NEXT:	    use next match in multiple match, wrap to first
3525  * mode = WILD_PREV:	    use previous match in multiple match, wrap to first
3526  * mode = WILD_ALL:	    return all matches concatenated
3527  * mode = WILD_LONGEST:	    return longest matched part
3528  * mode = WILD_ALL_KEEP:    get all matches, keep matches
3529  *
3530  * options = WILD_LIST_NOTFOUND:    list entries without a match
3531  * options = WILD_HOME_REPLACE:	    do home_replace() for buffer names
3532  * options = WILD_USE_NL:	    Use '\n' for WILD_ALL
3533  * options = WILD_NO_BEEP:	    Don't beep for multiple matches
3534  * options = WILD_ADD_SLASH:	    add a slash after directory names
3535  * options = WILD_KEEP_ALL:	    don't remove 'wildignore' entries
3536  * options = WILD_SILENT:	    don't print warning messages
3537  * options = WILD_ESCAPE:	    put backslash before special chars
3538  * options = WILD_ICASE:	    ignore case for files
3539  *
3540  * The variables xp->xp_context and xp->xp_backslash must have been set!
3541  */
3542     char_u *
3543 ExpandOne(xp, str, orig, options, mode)
3544     expand_T	*xp;
3545     char_u	*str;
3546     char_u	*orig;	    /* allocated copy of original of expanded string */
3547     int		options;
3548     int		mode;
3549 {
3550     char_u	*ss = NULL;
3551     static int	findex;
3552     static char_u *orig_save = NULL;	/* kept value of orig */
3553     int		orig_saved = FALSE;
3554     int		i;
3555     long_u	len;
3556     int		non_suf_match;		/* number without matching suffix */
3557 
3558     /*
3559      * first handle the case of using an old match
3560      */
3561     if (mode == WILD_NEXT || mode == WILD_PREV)
3562     {
3563 	if (xp->xp_numfiles > 0)
3564 	{
3565 	    if (mode == WILD_PREV)
3566 	    {
3567 		if (findex == -1)
3568 		    findex = xp->xp_numfiles;
3569 		--findex;
3570 	    }
3571 	    else    /* mode == WILD_NEXT */
3572 		++findex;
3573 
3574 	    /*
3575 	     * When wrapping around, return the original string, set findex to
3576 	     * -1.
3577 	     */
3578 	    if (findex < 0)
3579 	    {
3580 		if (orig_save == NULL)
3581 		    findex = xp->xp_numfiles - 1;
3582 		else
3583 		    findex = -1;
3584 	    }
3585 	    if (findex >= xp->xp_numfiles)
3586 	    {
3587 		if (orig_save == NULL)
3588 		    findex = 0;
3589 		else
3590 		    findex = -1;
3591 	    }
3592 #ifdef FEAT_WILDMENU
3593 	    if (p_wmnu)
3594 		win_redr_status_matches(xp, xp->xp_numfiles, xp->xp_files,
3595 							findex, cmd_showtail);
3596 #endif
3597 	    if (findex == -1)
3598 		return vim_strsave(orig_save);
3599 	    return vim_strsave(xp->xp_files[findex]);
3600 	}
3601 	else
3602 	    return NULL;
3603     }
3604 
3605     /* free old names */
3606     if (xp->xp_numfiles != -1 && mode != WILD_ALL && mode != WILD_LONGEST)
3607     {
3608 	FreeWild(xp->xp_numfiles, xp->xp_files);
3609 	xp->xp_numfiles = -1;
3610 	vim_free(orig_save);
3611 	orig_save = NULL;
3612     }
3613     findex = 0;
3614 
3615     if (mode == WILD_FREE)	/* only release file name */
3616 	return NULL;
3617 
3618     if (xp->xp_numfiles == -1)
3619     {
3620 	vim_free(orig_save);
3621 	orig_save = orig;
3622 	orig_saved = TRUE;
3623 
3624 	/*
3625 	 * Do the expansion.
3626 	 */
3627 	if (ExpandFromContext(xp, str, &xp->xp_numfiles, &xp->xp_files,
3628 							     options) == FAIL)
3629 	{
3630 #ifdef FNAME_ILLEGAL
3631 	    /* Illegal file name has been silently skipped.  But when there
3632 	     * are wildcards, the real problem is that there was no match,
3633 	     * causing the pattern to be added, which has illegal characters.
3634 	     */
3635 	    if (!(options & WILD_SILENT) && (options & WILD_LIST_NOTFOUND))
3636 		EMSG2(_(e_nomatch2), str);
3637 #endif
3638 	}
3639 	else if (xp->xp_numfiles == 0)
3640 	{
3641 	    if (!(options & WILD_SILENT))
3642 		EMSG2(_(e_nomatch2), str);
3643 	}
3644 	else
3645 	{
3646 	    /* Escape the matches for use on the command line. */
3647 	    ExpandEscape(xp, str, xp->xp_numfiles, xp->xp_files, options);
3648 
3649 	    /*
3650 	     * Check for matching suffixes in file names.
3651 	     */
3652 	    if (mode != WILD_ALL && mode != WILD_ALL_KEEP
3653 						      && mode != WILD_LONGEST)
3654 	    {
3655 		if (xp->xp_numfiles)
3656 		    non_suf_match = xp->xp_numfiles;
3657 		else
3658 		    non_suf_match = 1;
3659 		if ((xp->xp_context == EXPAND_FILES
3660 			    || xp->xp_context == EXPAND_DIRECTORIES)
3661 			&& xp->xp_numfiles > 1)
3662 		{
3663 		    /*
3664 		     * More than one match; check suffix.
3665 		     * The files will have been sorted on matching suffix in
3666 		     * expand_wildcards, only need to check the first two.
3667 		     */
3668 		    non_suf_match = 0;
3669 		    for (i = 0; i < 2; ++i)
3670 			if (match_suffix(xp->xp_files[i]))
3671 			    ++non_suf_match;
3672 		}
3673 		if (non_suf_match != 1)
3674 		{
3675 		    /* Can we ever get here unless it's while expanding
3676 		     * interactively?  If not, we can get rid of this all
3677 		     * together. Don't really want to wait for this message
3678 		     * (and possibly have to hit return to continue!).
3679 		     */
3680 		    if (!(options & WILD_SILENT))
3681 			EMSG(_(e_toomany));
3682 		    else if (!(options & WILD_NO_BEEP))
3683 			beep_flush();
3684 		}
3685 		if (!(non_suf_match != 1 && mode == WILD_EXPAND_FREE))
3686 		    ss = vim_strsave(xp->xp_files[0]);
3687 	    }
3688 	}
3689     }
3690 
3691     /* Find longest common part */
3692     if (mode == WILD_LONGEST && xp->xp_numfiles > 0)
3693     {
3694 	int mb_len = 1;
3695 	int c0, ci;
3696 
3697 	for (len = 0; xp->xp_files[0][len]; len += mb_len)
3698 	{
3699 #ifdef FEAT_MBYTE
3700 	    if (has_mbyte)
3701 	    {
3702 		mb_len = (*mb_ptr2len)(&xp->xp_files[0][len]);
3703 		c0 =(* mb_ptr2char)(&xp->xp_files[0][len]);
3704 	    }
3705 	    else
3706 #endif
3707 		c0 = xp->xp_files[0][len];
3708 	    for (i = 1; i < xp->xp_numfiles; ++i)
3709 	    {
3710 #ifdef FEAT_MBYTE
3711 		if (has_mbyte)
3712 		    ci =(* mb_ptr2char)(&xp->xp_files[i][len]);
3713 		else
3714 #endif
3715 		    ci = xp->xp_files[i][len];
3716 		if (p_fic && (xp->xp_context == EXPAND_DIRECTORIES
3717 			|| xp->xp_context == EXPAND_FILES
3718 			|| xp->xp_context == EXPAND_SHELLCMD
3719 			|| xp->xp_context == EXPAND_BUFFERS))
3720 		{
3721 		    if (MB_TOLOWER(c0) != MB_TOLOWER(ci))
3722 			break;
3723 		}
3724 		else if (c0 != ci)
3725 		    break;
3726 	    }
3727 	    if (i < xp->xp_numfiles)
3728 	    {
3729 		if (!(options & WILD_NO_BEEP))
3730 		    vim_beep(BO_WILD);
3731 		break;
3732 	    }
3733 	}
3734 
3735 	ss = alloc((unsigned)len + 1);
3736 	if (ss)
3737 	    vim_strncpy(ss, xp->xp_files[0], (size_t)len);
3738 	findex = -1;			    /* next p_wc gets first one */
3739     }
3740 
3741     /* Concatenate all matching names */
3742     if (mode == WILD_ALL && xp->xp_numfiles > 0)
3743     {
3744 	len = 0;
3745 	for (i = 0; i < xp->xp_numfiles; ++i)
3746 	    len += (long_u)STRLEN(xp->xp_files[i]) + 1;
3747 	ss = lalloc(len, TRUE);
3748 	if (ss != NULL)
3749 	{
3750 	    *ss = NUL;
3751 	    for (i = 0; i < xp->xp_numfiles; ++i)
3752 	    {
3753 		STRCAT(ss, xp->xp_files[i]);
3754 		if (i != xp->xp_numfiles - 1)
3755 		    STRCAT(ss, (options & WILD_USE_NL) ? "\n" : " ");
3756 	    }
3757 	}
3758     }
3759 
3760     if (mode == WILD_EXPAND_FREE || mode == WILD_ALL)
3761 	ExpandCleanup(xp);
3762 
3763     /* Free "orig" if it wasn't stored in "orig_save". */
3764     if (!orig_saved)
3765 	vim_free(orig);
3766 
3767     return ss;
3768 }
3769 
3770 /*
3771  * Prepare an expand structure for use.
3772  */
3773     void
3774 ExpandInit(xp)
3775     expand_T	*xp;
3776 {
3777     xp->xp_pattern = NULL;
3778     xp->xp_pattern_len = 0;
3779     xp->xp_backslash = XP_BS_NONE;
3780 #ifndef BACKSLASH_IN_FILENAME
3781     xp->xp_shell = FALSE;
3782 #endif
3783     xp->xp_numfiles = -1;
3784     xp->xp_files = NULL;
3785 #if defined(FEAT_USR_CMDS) && defined(FEAT_EVAL) && defined(FEAT_CMDL_COMPL)
3786     xp->xp_arg = NULL;
3787 #endif
3788     xp->xp_line = NULL;
3789 }
3790 
3791 /*
3792  * Cleanup an expand structure after use.
3793  */
3794     void
3795 ExpandCleanup(xp)
3796     expand_T	*xp;
3797 {
3798     if (xp->xp_numfiles >= 0)
3799     {
3800 	FreeWild(xp->xp_numfiles, xp->xp_files);
3801 	xp->xp_numfiles = -1;
3802     }
3803 }
3804 
3805     void
3806 ExpandEscape(xp, str, numfiles, files, options)
3807     expand_T	*xp;
3808     char_u	*str;
3809     int		numfiles;
3810     char_u	**files;
3811     int		options;
3812 {
3813     int		i;
3814     char_u	*p;
3815 
3816     /*
3817      * May change home directory back to "~"
3818      */
3819     if (options & WILD_HOME_REPLACE)
3820 	tilde_replace(str, numfiles, files);
3821 
3822     if (options & WILD_ESCAPE)
3823     {
3824 	if (xp->xp_context == EXPAND_FILES
3825 		|| xp->xp_context == EXPAND_FILES_IN_PATH
3826 		|| xp->xp_context == EXPAND_SHELLCMD
3827 		|| xp->xp_context == EXPAND_BUFFERS
3828 		|| xp->xp_context == EXPAND_DIRECTORIES)
3829 	{
3830 	    /*
3831 	     * Insert a backslash into a file name before a space, \, %, #
3832 	     * and wildmatch characters, except '~'.
3833 	     */
3834 	    for (i = 0; i < numfiles; ++i)
3835 	    {
3836 		/* for ":set path=" we need to escape spaces twice */
3837 		if (xp->xp_backslash == XP_BS_THREE)
3838 		{
3839 		    p = vim_strsave_escaped(files[i], (char_u *)" ");
3840 		    if (p != NULL)
3841 		    {
3842 			vim_free(files[i]);
3843 			files[i] = p;
3844 #if defined(BACKSLASH_IN_FILENAME)
3845 			p = vim_strsave_escaped(files[i], (char_u *)" ");
3846 			if (p != NULL)
3847 			{
3848 			    vim_free(files[i]);
3849 			    files[i] = p;
3850 			}
3851 #endif
3852 		    }
3853 		}
3854 #ifdef BACKSLASH_IN_FILENAME
3855 		p = vim_strsave_fnameescape(files[i], FALSE);
3856 #else
3857 		p = vim_strsave_fnameescape(files[i], xp->xp_shell);
3858 #endif
3859 		if (p != NULL)
3860 		{
3861 		    vim_free(files[i]);
3862 		    files[i] = p;
3863 		}
3864 
3865 		/* If 'str' starts with "\~", replace "~" at start of
3866 		 * files[i] with "\~". */
3867 		if (str[0] == '\\' && str[1] == '~' && files[i][0] == '~')
3868 		    escape_fname(&files[i]);
3869 	    }
3870 	    xp->xp_backslash = XP_BS_NONE;
3871 
3872 	    /* If the first file starts with a '+' escape it.  Otherwise it
3873 	     * could be seen as "+cmd". */
3874 	    if (*files[0] == '+')
3875 		escape_fname(&files[0]);
3876 	}
3877 	else if (xp->xp_context == EXPAND_TAGS)
3878 	{
3879 	    /*
3880 	     * Insert a backslash before characters in a tag name that
3881 	     * would terminate the ":tag" command.
3882 	     */
3883 	    for (i = 0; i < numfiles; ++i)
3884 	    {
3885 		p = vim_strsave_escaped(files[i], (char_u *)"\\|\"");
3886 		if (p != NULL)
3887 		{
3888 		    vim_free(files[i]);
3889 		    files[i] = p;
3890 		}
3891 	    }
3892 	}
3893     }
3894 }
3895 
3896 /*
3897  * Escape special characters in "fname" for when used as a file name argument
3898  * after a Vim command, or, when "shell" is non-zero, a shell command.
3899  * Returns the result in allocated memory.
3900  */
3901     char_u *
3902 vim_strsave_fnameescape(fname, shell)
3903     char_u *fname;
3904     int    shell;
3905 {
3906     char_u	*p;
3907 #ifdef BACKSLASH_IN_FILENAME
3908     char_u	buf[20];
3909     int		j = 0;
3910 
3911     /* Don't escape '[', '{' and '!' if they are in 'isfname'. */
3912     for (p = PATH_ESC_CHARS; *p != NUL; ++p)
3913 	if ((*p != '[' && *p != '{' && *p != '!') || !vim_isfilec(*p))
3914 	    buf[j++] = *p;
3915     buf[j] = NUL;
3916     p = vim_strsave_escaped(fname, buf);
3917 #else
3918     p = vim_strsave_escaped(fname, shell ? SHELL_ESC_CHARS : PATH_ESC_CHARS);
3919     if (shell && csh_like_shell() && p != NULL)
3920     {
3921 	char_u	    *s;
3922 
3923 	/* For csh and similar shells need to put two backslashes before '!'.
3924 	 * One is taken by Vim, one by the shell. */
3925 	s = vim_strsave_escaped(p, (char_u *)"!");
3926 	vim_free(p);
3927 	p = s;
3928     }
3929 #endif
3930 
3931     /* '>' and '+' are special at the start of some commands, e.g. ":edit" and
3932      * ":write".  "cd -" has a special meaning. */
3933     if (p != NULL && (*p == '>' || *p == '+' || (*p == '-' && p[1] == NUL)))
3934 	escape_fname(&p);
3935 
3936     return p;
3937 }
3938 
3939 /*
3940  * Put a backslash before the file name in "pp", which is in allocated memory.
3941  */
3942     static void
3943 escape_fname(pp)
3944     char_u **pp;
3945 {
3946     char_u	*p;
3947 
3948     p = alloc((unsigned)(STRLEN(*pp) + 2));
3949     if (p != NULL)
3950     {
3951 	p[0] = '\\';
3952 	STRCPY(p + 1, *pp);
3953 	vim_free(*pp);
3954 	*pp = p;
3955     }
3956 }
3957 
3958 /*
3959  * For each file name in files[num_files]:
3960  * If 'orig_pat' starts with "~/", replace the home directory with "~".
3961  */
3962     void
3963 tilde_replace(orig_pat, num_files, files)
3964     char_u  *orig_pat;
3965     int	    num_files;
3966     char_u  **files;
3967 {
3968     int	    i;
3969     char_u  *p;
3970 
3971     if (orig_pat[0] == '~' && vim_ispathsep(orig_pat[1]))
3972     {
3973 	for (i = 0; i < num_files; ++i)
3974 	{
3975 	    p = home_replace_save(NULL, files[i]);
3976 	    if (p != NULL)
3977 	    {
3978 		vim_free(files[i]);
3979 		files[i] = p;
3980 	    }
3981 	}
3982     }
3983 }
3984 
3985 /*
3986  * Show all matches for completion on the command line.
3987  * Returns EXPAND_NOTHING when the character that triggered expansion should
3988  * be inserted like a normal character.
3989  */
3990     static int
3991 showmatches(xp, wildmenu)
3992     expand_T	*xp;
3993     int		wildmenu UNUSED;
3994 {
3995 #define L_SHOWFILE(m) (showtail ? sm_gettail(files_found[m]) : files_found[m])
3996     int		num_files;
3997     char_u	**files_found;
3998     int		i, j, k;
3999     int		maxlen;
4000     int		lines;
4001     int		columns;
4002     char_u	*p;
4003     int		lastlen;
4004     int		attr;
4005     int		showtail;
4006 
4007     if (xp->xp_numfiles == -1)
4008     {
4009 	set_expand_context(xp);
4010 	i = expand_cmdline(xp, ccline.cmdbuff, ccline.cmdpos,
4011 						    &num_files, &files_found);
4012 	showtail = expand_showtail(xp);
4013 	if (i != EXPAND_OK)
4014 	    return i;
4015 
4016     }
4017     else
4018     {
4019 	num_files = xp->xp_numfiles;
4020 	files_found = xp->xp_files;
4021 	showtail = cmd_showtail;
4022     }
4023 
4024 #ifdef FEAT_WILDMENU
4025     if (!wildmenu)
4026     {
4027 #endif
4028 	msg_didany = FALSE;		/* lines_left will be set */
4029 	msg_start();			/* prepare for paging */
4030 	msg_putchar('\n');
4031 	out_flush();
4032 	cmdline_row = msg_row;
4033 	msg_didany = FALSE;		/* lines_left will be set again */
4034 	msg_start();			/* prepare for paging */
4035 #ifdef FEAT_WILDMENU
4036     }
4037 #endif
4038 
4039     if (got_int)
4040 	got_int = FALSE;	/* only int. the completion, not the cmd line */
4041 #ifdef FEAT_WILDMENU
4042     else if (wildmenu)
4043 	win_redr_status_matches(xp, num_files, files_found, 0, showtail);
4044 #endif
4045     else
4046     {
4047 	/* find the length of the longest file name */
4048 	maxlen = 0;
4049 	for (i = 0; i < num_files; ++i)
4050 	{
4051 	    if (!showtail && (xp->xp_context == EXPAND_FILES
4052 			  || xp->xp_context == EXPAND_SHELLCMD
4053 			  || xp->xp_context == EXPAND_BUFFERS))
4054 	    {
4055 		home_replace(NULL, files_found[i], NameBuff, MAXPATHL, TRUE);
4056 		j = vim_strsize(NameBuff);
4057 	    }
4058 	    else
4059 		j = vim_strsize(L_SHOWFILE(i));
4060 	    if (j > maxlen)
4061 		maxlen = j;
4062 	}
4063 
4064 	if (xp->xp_context == EXPAND_TAGS_LISTFILES)
4065 	    lines = num_files;
4066 	else
4067 	{
4068 	    /* compute the number of columns and lines for the listing */
4069 	    maxlen += 2;    /* two spaces between file names */
4070 	    columns = ((int)Columns + 2) / maxlen;
4071 	    if (columns < 1)
4072 		columns = 1;
4073 	    lines = (num_files + columns - 1) / columns;
4074 	}
4075 
4076 	attr = hl_attr(HLF_D);	/* find out highlighting for directories */
4077 
4078 	if (xp->xp_context == EXPAND_TAGS_LISTFILES)
4079 	{
4080 	    MSG_PUTS_ATTR(_("tagname"), hl_attr(HLF_T));
4081 	    msg_clr_eos();
4082 	    msg_advance(maxlen - 3);
4083 	    MSG_PUTS_ATTR(_(" kind file\n"), hl_attr(HLF_T));
4084 	}
4085 
4086 	/* list the files line by line */
4087 	for (i = 0; i < lines; ++i)
4088 	{
4089 	    lastlen = 999;
4090 	    for (k = i; k < num_files; k += lines)
4091 	    {
4092 		if (xp->xp_context == EXPAND_TAGS_LISTFILES)
4093 		{
4094 		    msg_outtrans_attr(files_found[k], hl_attr(HLF_D));
4095 		    p = files_found[k] + STRLEN(files_found[k]) + 1;
4096 		    msg_advance(maxlen + 1);
4097 		    msg_puts(p);
4098 		    msg_advance(maxlen + 3);
4099 		    msg_puts_long_attr(p + 2, hl_attr(HLF_D));
4100 		    break;
4101 		}
4102 		for (j = maxlen - lastlen; --j >= 0; )
4103 		    msg_putchar(' ');
4104 		if (xp->xp_context == EXPAND_FILES
4105 					  || xp->xp_context == EXPAND_SHELLCMD
4106 					  || xp->xp_context == EXPAND_BUFFERS)
4107 		{
4108 		    /* highlight directories */
4109 		    if (xp->xp_numfiles != -1)
4110 		    {
4111 			char_u	*halved_slash;
4112 			char_u	*exp_path;
4113 
4114 			/* Expansion was done before and special characters
4115 			 * were escaped, need to halve backslashes.  Also
4116 			 * $HOME has been replaced with ~/. */
4117 			exp_path = expand_env_save_opt(files_found[k], TRUE);
4118 			halved_slash = backslash_halve_save(
4119 				exp_path != NULL ? exp_path : files_found[k]);
4120 			j = mch_isdir(halved_slash != NULL ? halved_slash
4121 							    : files_found[k]);
4122 			vim_free(exp_path);
4123 			vim_free(halved_slash);
4124 		    }
4125 		    else
4126 			/* Expansion was done here, file names are literal. */
4127 			j = mch_isdir(files_found[k]);
4128 		    if (showtail)
4129 			p = L_SHOWFILE(k);
4130 		    else
4131 		    {
4132 			home_replace(NULL, files_found[k], NameBuff, MAXPATHL,
4133 									TRUE);
4134 			p = NameBuff;
4135 		    }
4136 		}
4137 		else
4138 		{
4139 		    j = FALSE;
4140 		    p = L_SHOWFILE(k);
4141 		}
4142 		lastlen = msg_outtrans_attr(p, j ? attr : 0);
4143 	    }
4144 	    if (msg_col > 0)	/* when not wrapped around */
4145 	    {
4146 		msg_clr_eos();
4147 		msg_putchar('\n');
4148 	    }
4149 	    out_flush();		    /* show one line at a time */
4150 	    if (got_int)
4151 	    {
4152 		got_int = FALSE;
4153 		break;
4154 	    }
4155 	}
4156 
4157 	/*
4158 	 * we redraw the command below the lines that we have just listed
4159 	 * This is a bit tricky, but it saves a lot of screen updating.
4160 	 */
4161 	cmdline_row = msg_row;	/* will put it back later */
4162     }
4163 
4164     if (xp->xp_numfiles == -1)
4165 	FreeWild(num_files, files_found);
4166 
4167     return EXPAND_OK;
4168 }
4169 
4170 /*
4171  * Private gettail for showmatches() (and win_redr_status_matches()):
4172  * Find tail of file name path, but ignore trailing "/".
4173  */
4174     char_u *
4175 sm_gettail(s)
4176     char_u	*s;
4177 {
4178     char_u	*p;
4179     char_u	*t = s;
4180     int		had_sep = FALSE;
4181 
4182     for (p = s; *p != NUL; )
4183     {
4184 	if (vim_ispathsep(*p)
4185 #ifdef BACKSLASH_IN_FILENAME
4186 		&& !rem_backslash(p)
4187 #endif
4188 	   )
4189 	    had_sep = TRUE;
4190 	else if (had_sep)
4191 	{
4192 	    t = p;
4193 	    had_sep = FALSE;
4194 	}
4195 	mb_ptr_adv(p);
4196     }
4197     return t;
4198 }
4199 
4200 /*
4201  * Return TRUE if we only need to show the tail of completion matches.
4202  * When not completing file names or there is a wildcard in the path FALSE is
4203  * returned.
4204  */
4205     static int
4206 expand_showtail(xp)
4207     expand_T	*xp;
4208 {
4209     char_u	*s;
4210     char_u	*end;
4211 
4212     /* When not completing file names a "/" may mean something different. */
4213     if (xp->xp_context != EXPAND_FILES
4214 	    && xp->xp_context != EXPAND_SHELLCMD
4215 	    && xp->xp_context != EXPAND_DIRECTORIES)
4216 	return FALSE;
4217 
4218     end = gettail(xp->xp_pattern);
4219     if (end == xp->xp_pattern)		/* there is no path separator */
4220 	return FALSE;
4221 
4222     for (s = xp->xp_pattern; s < end; s++)
4223     {
4224 	/* Skip escaped wildcards.  Only when the backslash is not a path
4225 	 * separator, on DOS the '*' "path\*\file" must not be skipped. */
4226 	if (rem_backslash(s))
4227 	    ++s;
4228 	else if (vim_strchr((char_u *)"*?[", *s) != NULL)
4229 	    return FALSE;
4230     }
4231     return TRUE;
4232 }
4233 
4234 /*
4235  * Prepare a string for expansion.
4236  * When expanding file names: The string will be used with expand_wildcards().
4237  * Copy "fname[len]" into allocated memory and add a '*' at the end.
4238  * When expanding other names: The string will be used with regcomp().  Copy
4239  * the name into allocated memory and prepend "^".
4240  */
4241     char_u *
4242 addstar(fname, len, context)
4243     char_u	*fname;
4244     int		len;
4245     int		context;	/* EXPAND_FILES etc. */
4246 {
4247     char_u	*retval;
4248     int		i, j;
4249     int		new_len;
4250     char_u	*tail;
4251     int		ends_in_star;
4252 
4253     if (context != EXPAND_FILES
4254 	    && context != EXPAND_FILES_IN_PATH
4255 	    && context != EXPAND_SHELLCMD
4256 	    && context != EXPAND_DIRECTORIES)
4257     {
4258 	/*
4259 	 * Matching will be done internally (on something other than files).
4260 	 * So we convert the file-matching-type wildcards into our kind for
4261 	 * use with vim_regcomp().  First work out how long it will be:
4262 	 */
4263 
4264 	/* For help tags the translation is done in find_help_tags().
4265 	 * For a tag pattern starting with "/" no translation is needed. */
4266 	if (context == EXPAND_HELP
4267 		|| context == EXPAND_COLORS
4268 		|| context == EXPAND_COMPILER
4269 		|| context == EXPAND_OWNSYNTAX
4270 		|| context == EXPAND_FILETYPE
4271 		|| (context == EXPAND_TAGS && fname[0] == '/'))
4272 	    retval = vim_strnsave(fname, len);
4273 	else
4274 	{
4275 	    new_len = len + 2;		/* +2 for '^' at start, NUL at end */
4276 	    for (i = 0; i < len; i++)
4277 	    {
4278 		if (fname[i] == '*' || fname[i] == '~')
4279 		    new_len++;		/* '*' needs to be replaced by ".*"
4280 					   '~' needs to be replaced by "\~" */
4281 
4282 		/* Buffer names are like file names.  "." should be literal */
4283 		if (context == EXPAND_BUFFERS && fname[i] == '.')
4284 		    new_len++;		/* "." becomes "\." */
4285 
4286 		/* Custom expansion takes care of special things, match
4287 		 * backslashes literally (perhaps also for other types?) */
4288 		if ((context == EXPAND_USER_DEFINED
4289 			  || context == EXPAND_USER_LIST) && fname[i] == '\\')
4290 		    new_len++;		/* '\' becomes "\\" */
4291 	    }
4292 	    retval = alloc(new_len);
4293 	    if (retval != NULL)
4294 	    {
4295 		retval[0] = '^';
4296 		j = 1;
4297 		for (i = 0; i < len; i++, j++)
4298 		{
4299 		    /* Skip backslash.  But why?  At least keep it for custom
4300 		     * expansion. */
4301 		    if (context != EXPAND_USER_DEFINED
4302 			    && context != EXPAND_USER_LIST
4303 			    && fname[i] == '\\'
4304 			    && ++i == len)
4305 			break;
4306 
4307 		    switch (fname[i])
4308 		    {
4309 			case '*':   retval[j++] = '.';
4310 				    break;
4311 			case '~':   retval[j++] = '\\';
4312 				    break;
4313 			case '?':   retval[j] = '.';
4314 				    continue;
4315 			case '.':   if (context == EXPAND_BUFFERS)
4316 					retval[j++] = '\\';
4317 				    break;
4318 			case '\\':  if (context == EXPAND_USER_DEFINED
4319 					    || context == EXPAND_USER_LIST)
4320 					retval[j++] = '\\';
4321 				    break;
4322 		    }
4323 		    retval[j] = fname[i];
4324 		}
4325 		retval[j] = NUL;
4326 	    }
4327 	}
4328     }
4329     else
4330     {
4331 	retval = alloc(len + 4);
4332 	if (retval != NULL)
4333 	{
4334 	    vim_strncpy(retval, fname, len);
4335 
4336 	    /*
4337 	     * Don't add a star to *, ~, ~user, $var or `cmd`.
4338 	     * * would become **, which walks the whole tree.
4339 	     * ~ would be at the start of the file name, but not the tail.
4340 	     * $ could be anywhere in the tail.
4341 	     * ` could be anywhere in the file name.
4342 	     * When the name ends in '$' don't add a star, remove the '$'.
4343 	     */
4344 	    tail = gettail(retval);
4345 	    ends_in_star = (len > 0 && retval[len - 1] == '*');
4346 #ifndef BACKSLASH_IN_FILENAME
4347 	    for (i = len - 2; i >= 0; --i)
4348 	    {
4349 		if (retval[i] != '\\')
4350 		    break;
4351 		ends_in_star = !ends_in_star;
4352 	    }
4353 #endif
4354 	    if ((*retval != '~' || tail != retval)
4355 		    && !ends_in_star
4356 		    && vim_strchr(tail, '$') == NULL
4357 		    && vim_strchr(retval, '`') == NULL)
4358 		retval[len++] = '*';
4359 	    else if (len > 0 && retval[len - 1] == '$')
4360 		--len;
4361 	    retval[len] = NUL;
4362 	}
4363     }
4364     return retval;
4365 }
4366 
4367 /*
4368  * Must parse the command line so far to work out what context we are in.
4369  * Completion can then be done based on that context.
4370  * This routine sets the variables:
4371  *  xp->xp_pattern	    The start of the pattern to be expanded within
4372  *				the command line (ends at the cursor).
4373  *  xp->xp_context	    The type of thing to expand.  Will be one of:
4374  *
4375  *  EXPAND_UNSUCCESSFUL	    Used sometimes when there is something illegal on
4376  *			    the command line, like an unknown command.	Caller
4377  *			    should beep.
4378  *  EXPAND_NOTHING	    Unrecognised context for completion, use char like
4379  *			    a normal char, rather than for completion.	eg
4380  *			    :s/^I/
4381  *  EXPAND_COMMANDS	    Cursor is still touching the command, so complete
4382  *			    it.
4383  *  EXPAND_BUFFERS	    Complete file names for :buf and :sbuf commands.
4384  *  EXPAND_FILES	    After command with XFILE set, or after setting
4385  *			    with P_EXPAND set.	eg :e ^I, :w>>^I
4386  *  EXPAND_DIRECTORIES	    In some cases this is used instead of the latter
4387  *			    when we know only directories are of interest.  eg
4388  *			    :set dir=^I
4389  *  EXPAND_SHELLCMD	    After ":!cmd", ":r !cmd"  or ":w !cmd".
4390  *  EXPAND_SETTINGS	    Complete variable names.  eg :set d^I
4391  *  EXPAND_BOOL_SETTINGS    Complete boolean variables only,  eg :set no^I
4392  *  EXPAND_TAGS		    Complete tags from the files in p_tags.  eg :ta a^I
4393  *  EXPAND_TAGS_LISTFILES   As above, but list filenames on ^D, after :tselect
4394  *  EXPAND_HELP		    Complete tags from the file 'helpfile'/tags
4395  *  EXPAND_EVENTS	    Complete event names
4396  *  EXPAND_SYNTAX	    Complete :syntax command arguments
4397  *  EXPAND_HIGHLIGHT	    Complete highlight (syntax) group names
4398  *  EXPAND_AUGROUP	    Complete autocommand group names
4399  *  EXPAND_USER_VARS	    Complete user defined variable names, eg :unlet a^I
4400  *  EXPAND_MAPPINGS	    Complete mapping and abbreviation names,
4401  *			      eg :unmap a^I , :cunab x^I
4402  *  EXPAND_FUNCTIONS	    Complete internal or user defined function names,
4403  *			      eg :call sub^I
4404  *  EXPAND_USER_FUNC	    Complete user defined function names, eg :delf F^I
4405  *  EXPAND_EXPRESSION	    Complete internal or user defined function/variable
4406  *			    names in expressions, eg :while s^I
4407  *  EXPAND_ENV_VARS	    Complete environment variable names
4408  *  EXPAND_USER		    Complete user names
4409  */
4410     static void
4411 set_expand_context(xp)
4412     expand_T	*xp;
4413 {
4414     /* only expansion for ':', '>' and '=' command-lines */
4415     if (ccline.cmdfirstc != ':'
4416 #ifdef FEAT_EVAL
4417 	    && ccline.cmdfirstc != '>' && ccline.cmdfirstc != '='
4418 	    && !ccline.input_fn
4419 #endif
4420 	    )
4421     {
4422 	xp->xp_context = EXPAND_NOTHING;
4423 	return;
4424     }
4425     set_cmd_context(xp, ccline.cmdbuff, ccline.cmdlen, ccline.cmdpos);
4426 }
4427 
4428     void
4429 set_cmd_context(xp, str, len, col)
4430     expand_T	*xp;
4431     char_u	*str;	    /* start of command line */
4432     int		len;	    /* length of command line (excl. NUL) */
4433     int		col;	    /* position of cursor */
4434 {
4435     int		old_char = NUL;
4436     char_u	*nextcomm;
4437 
4438     /*
4439      * Avoid a UMR warning from Purify, only save the character if it has been
4440      * written before.
4441      */
4442     if (col < len)
4443 	old_char = str[col];
4444     str[col] = NUL;
4445     nextcomm = str;
4446 
4447 #ifdef FEAT_EVAL
4448     if (ccline.cmdfirstc == '=')
4449     {
4450 # ifdef FEAT_CMDL_COMPL
4451 	/* pass CMD_SIZE because there is no real command */
4452 	set_context_for_expression(xp, str, CMD_SIZE);
4453 # endif
4454     }
4455     else if (ccline.input_fn)
4456     {
4457 	xp->xp_context = ccline.xp_context;
4458 	xp->xp_pattern = ccline.cmdbuff;
4459 # if defined(FEAT_USR_CMDS) && defined(FEAT_CMDL_COMPL)
4460 	xp->xp_arg = ccline.xp_arg;
4461 # endif
4462     }
4463     else
4464 #endif
4465 	while (nextcomm != NULL)
4466 	    nextcomm = set_one_cmd_context(xp, nextcomm);
4467 
4468     /* Store the string here so that call_user_expand_func() can get to them
4469      * easily. */
4470     xp->xp_line = str;
4471     xp->xp_col = col;
4472 
4473     str[col] = old_char;
4474 }
4475 
4476 /*
4477  * Expand the command line "str" from context "xp".
4478  * "xp" must have been set by set_cmd_context().
4479  * xp->xp_pattern points into "str", to where the text that is to be expanded
4480  * starts.
4481  * Returns EXPAND_UNSUCCESSFUL when there is something illegal before the
4482  * cursor.
4483  * Returns EXPAND_NOTHING when there is nothing to expand, might insert the
4484  * key that triggered expansion literally.
4485  * Returns EXPAND_OK otherwise.
4486  */
4487     int
4488 expand_cmdline(xp, str, col, matchcount, matches)
4489     expand_T	*xp;
4490     char_u	*str;		/* start of command line */
4491     int		col;		/* position of cursor */
4492     int		*matchcount;	/* return: nr of matches */
4493     char_u	***matches;	/* return: array of pointers to matches */
4494 {
4495     char_u	*file_str = NULL;
4496     int		options = WILD_ADD_SLASH|WILD_SILENT;
4497 
4498     if (xp->xp_context == EXPAND_UNSUCCESSFUL)
4499     {
4500 	beep_flush();
4501 	return EXPAND_UNSUCCESSFUL;  /* Something illegal on command line */
4502     }
4503     if (xp->xp_context == EXPAND_NOTHING)
4504     {
4505 	/* Caller can use the character as a normal char instead */
4506 	return EXPAND_NOTHING;
4507     }
4508 
4509     /* add star to file name, or convert to regexp if not exp. files. */
4510     xp->xp_pattern_len = (int)(str + col - xp->xp_pattern);
4511     file_str = addstar(xp->xp_pattern, xp->xp_pattern_len, xp->xp_context);
4512     if (file_str == NULL)
4513 	return EXPAND_UNSUCCESSFUL;
4514 
4515     if (p_wic)
4516 	options += WILD_ICASE;
4517 
4518     /* find all files that match the description */
4519     if (ExpandFromContext(xp, file_str, matchcount, matches, options) == FAIL)
4520     {
4521 	*matchcount = 0;
4522 	*matches = NULL;
4523     }
4524     vim_free(file_str);
4525 
4526     return EXPAND_OK;
4527 }
4528 
4529 #ifdef FEAT_MULTI_LANG
4530 /*
4531  * Cleanup matches for help tags: remove "@en" if "en" is the only language.
4532  */
4533 static void	cleanup_help_tags __ARGS((int num_file, char_u **file));
4534 
4535     static void
4536 cleanup_help_tags(num_file, file)
4537     int		num_file;
4538     char_u	**file;
4539 {
4540     int		i, j;
4541     int		len;
4542 
4543     for (i = 0; i < num_file; ++i)
4544     {
4545 	len = (int)STRLEN(file[i]) - 3;
4546 	if (len > 0 && STRCMP(file[i] + len, "@en") == 0)
4547 	{
4548 	    /* Sorting on priority means the same item in another language may
4549 	     * be anywhere.  Search all items for a match up to the "@en". */
4550 	    for (j = 0; j < num_file; ++j)
4551 		if (j != i
4552 			&& (int)STRLEN(file[j]) == len + 3
4553 			&& STRNCMP(file[i], file[j], len + 1) == 0)
4554 		    break;
4555 	    if (j == num_file)
4556 		file[i][len] = NUL;
4557 	}
4558     }
4559 }
4560 #endif
4561 
4562 /*
4563  * Do the expansion based on xp->xp_context and "pat".
4564  */
4565     static int
4566 ExpandFromContext(xp, pat, num_file, file, options)
4567     expand_T	*xp;
4568     char_u	*pat;
4569     int		*num_file;
4570     char_u	***file;
4571     int		options;  /* EW_ flags */
4572 {
4573 #ifdef FEAT_CMDL_COMPL
4574     regmatch_T	regmatch;
4575 #endif
4576     int		ret;
4577     int		flags;
4578 
4579     flags = EW_DIR;	/* include directories */
4580     if (options & WILD_LIST_NOTFOUND)
4581 	flags |= EW_NOTFOUND;
4582     if (options & WILD_ADD_SLASH)
4583 	flags |= EW_ADDSLASH;
4584     if (options & WILD_KEEP_ALL)
4585 	flags |= EW_KEEPALL;
4586     if (options & WILD_SILENT)
4587 	flags |= EW_SILENT;
4588     if (options & WILD_ALLLINKS)
4589 	flags |= EW_ALLLINKS;
4590 
4591     if (xp->xp_context == EXPAND_FILES
4592 	    || xp->xp_context == EXPAND_DIRECTORIES
4593 	    || xp->xp_context == EXPAND_FILES_IN_PATH)
4594     {
4595 	/*
4596 	 * Expand file or directory names.
4597 	 */
4598 	int	free_pat = FALSE;
4599 	int	i;
4600 
4601 	/* for ":set path=" and ":set tags=" halve backslashes for escaped
4602 	 * space */
4603 	if (xp->xp_backslash != XP_BS_NONE)
4604 	{
4605 	    free_pat = TRUE;
4606 	    pat = vim_strsave(pat);
4607 	    for (i = 0; pat[i]; ++i)
4608 		if (pat[i] == '\\')
4609 		{
4610 		    if (xp->xp_backslash == XP_BS_THREE
4611 			    && pat[i + 1] == '\\'
4612 			    && pat[i + 2] == '\\'
4613 			    && pat[i + 3] == ' ')
4614 			STRMOVE(pat + i, pat + i + 3);
4615 		    if (xp->xp_backslash == XP_BS_ONE
4616 			    && pat[i + 1] == ' ')
4617 			STRMOVE(pat + i, pat + i + 1);
4618 		}
4619 	}
4620 
4621 	if (xp->xp_context == EXPAND_FILES)
4622 	    flags |= EW_FILE;
4623 	else if (xp->xp_context == EXPAND_FILES_IN_PATH)
4624 	    flags |= (EW_FILE | EW_PATH);
4625 	else
4626 	    flags = (flags | EW_DIR) & ~EW_FILE;
4627 	if (options & WILD_ICASE)
4628 	    flags |= EW_ICASE;
4629 
4630 	/* Expand wildcards, supporting %:h and the like. */
4631 	ret = expand_wildcards_eval(&pat, num_file, file, flags);
4632 	if (free_pat)
4633 	    vim_free(pat);
4634 	return ret;
4635     }
4636 
4637     *file = (char_u **)"";
4638     *num_file = 0;
4639     if (xp->xp_context == EXPAND_HELP)
4640     {
4641 	/* With an empty argument we would get all the help tags, which is
4642 	 * very slow.  Get matches for "help" instead. */
4643 	if (find_help_tags(*pat == NUL ? (char_u *)"help" : pat,
4644 						 num_file, file, FALSE) == OK)
4645 	{
4646 #ifdef FEAT_MULTI_LANG
4647 	    cleanup_help_tags(*num_file, *file);
4648 #endif
4649 	    return OK;
4650 	}
4651 	return FAIL;
4652     }
4653 
4654 #ifndef FEAT_CMDL_COMPL
4655     return FAIL;
4656 #else
4657     if (xp->xp_context == EXPAND_SHELLCMD)
4658 	return expand_shellcmd(pat, num_file, file, flags);
4659     if (xp->xp_context == EXPAND_OLD_SETTING)
4660 	return ExpandOldSetting(num_file, file);
4661     if (xp->xp_context == EXPAND_BUFFERS)
4662 	return ExpandBufnames(pat, num_file, file, options);
4663     if (xp->xp_context == EXPAND_TAGS
4664 	    || xp->xp_context == EXPAND_TAGS_LISTFILES)
4665 	return expand_tags(xp->xp_context == EXPAND_TAGS, pat, num_file, file);
4666     if (xp->xp_context == EXPAND_COLORS)
4667     {
4668 	char *directories[] = {"colors", NULL};
4669 	return ExpandRTDir(pat, num_file, file, directories);
4670     }
4671     if (xp->xp_context == EXPAND_COMPILER)
4672     {
4673 	char *directories[] = {"compiler", NULL};
4674 	return ExpandRTDir(pat, num_file, file, directories);
4675     }
4676     if (xp->xp_context == EXPAND_OWNSYNTAX)
4677     {
4678 	char *directories[] = {"syntax", NULL};
4679 	return ExpandRTDir(pat, num_file, file, directories);
4680     }
4681     if (xp->xp_context == EXPAND_FILETYPE)
4682     {
4683 	char *directories[] = {"syntax", "indent", "ftplugin", NULL};
4684 	return ExpandRTDir(pat, num_file, file, directories);
4685     }
4686 # if defined(FEAT_USR_CMDS) && defined(FEAT_EVAL)
4687     if (xp->xp_context == EXPAND_USER_LIST)
4688 	return ExpandUserList(xp, num_file, file);
4689 # endif
4690 
4691     regmatch.regprog = vim_regcomp(pat, p_magic ? RE_MAGIC : 0);
4692     if (regmatch.regprog == NULL)
4693 	return FAIL;
4694 
4695     /* set ignore-case according to p_ic, p_scs and pat */
4696     regmatch.rm_ic = ignorecase(pat);
4697 
4698     if (xp->xp_context == EXPAND_SETTINGS
4699 	    || xp->xp_context == EXPAND_BOOL_SETTINGS)
4700 	ret = ExpandSettings(xp, &regmatch, num_file, file);
4701     else if (xp->xp_context == EXPAND_MAPPINGS)
4702 	ret = ExpandMappings(&regmatch, num_file, file);
4703 # if defined(FEAT_USR_CMDS) && defined(FEAT_EVAL)
4704     else if (xp->xp_context == EXPAND_USER_DEFINED)
4705 	ret = ExpandUserDefined(xp, &regmatch, num_file, file);
4706 # endif
4707     else
4708     {
4709 	static struct expgen
4710 	{
4711 	    int		context;
4712 	    char_u	*((*func)__ARGS((expand_T *, int)));
4713 	    int		ic;
4714 	    int		escaped;
4715 	} tab[] =
4716 	{
4717 	    {EXPAND_COMMANDS, get_command_name, FALSE, TRUE},
4718 	    {EXPAND_BEHAVE, get_behave_arg, TRUE, TRUE},
4719 #ifdef FEAT_CMDHIST
4720 	    {EXPAND_HISTORY, get_history_arg, TRUE, TRUE},
4721 #endif
4722 #ifdef FEAT_USR_CMDS
4723 	    {EXPAND_USER_COMMANDS, get_user_commands, FALSE, TRUE},
4724 	    {EXPAND_USER_ADDR_TYPE, get_user_cmd_addr_type, FALSE, TRUE},
4725 	    {EXPAND_USER_CMD_FLAGS, get_user_cmd_flags, FALSE, TRUE},
4726 	    {EXPAND_USER_NARGS, get_user_cmd_nargs, FALSE, TRUE},
4727 	    {EXPAND_USER_COMPLETE, get_user_cmd_complete, FALSE, TRUE},
4728 #endif
4729 #ifdef FEAT_EVAL
4730 	    {EXPAND_USER_VARS, get_user_var_name, FALSE, TRUE},
4731 	    {EXPAND_FUNCTIONS, get_function_name, FALSE, TRUE},
4732 	    {EXPAND_USER_FUNC, get_user_func_name, FALSE, TRUE},
4733 	    {EXPAND_EXPRESSION, get_expr_name, FALSE, TRUE},
4734 #endif
4735 #ifdef FEAT_MENU
4736 	    {EXPAND_MENUS, get_menu_name, FALSE, TRUE},
4737 	    {EXPAND_MENUNAMES, get_menu_names, FALSE, TRUE},
4738 #endif
4739 #ifdef FEAT_SYN_HL
4740 	    {EXPAND_SYNTAX, get_syntax_name, TRUE, TRUE},
4741 #endif
4742 #ifdef FEAT_PROFILE
4743 	    {EXPAND_SYNTIME, get_syntime_arg, TRUE, TRUE},
4744 #endif
4745 	    {EXPAND_HIGHLIGHT, get_highlight_name, TRUE, TRUE},
4746 #ifdef FEAT_AUTOCMD
4747 	    {EXPAND_EVENTS, get_event_name, TRUE, TRUE},
4748 	    {EXPAND_AUGROUP, get_augroup_name, TRUE, TRUE},
4749 #endif
4750 #ifdef FEAT_CSCOPE
4751 	    {EXPAND_CSCOPE, get_cscope_name, TRUE, TRUE},
4752 #endif
4753 #ifdef FEAT_SIGNS
4754 	    {EXPAND_SIGN, get_sign_name, TRUE, TRUE},
4755 #endif
4756 #ifdef FEAT_PROFILE
4757 	    {EXPAND_PROFILE, get_profile_name, TRUE, TRUE},
4758 #endif
4759 #if (defined(HAVE_LOCALE_H) || defined(X_LOCALE)) \
4760 	&& (defined(FEAT_GETTEXT) || defined(FEAT_MBYTE))
4761 	    {EXPAND_LANGUAGE, get_lang_arg, TRUE, FALSE},
4762 	    {EXPAND_LOCALES, get_locales, TRUE, FALSE},
4763 #endif
4764 	    {EXPAND_ENV_VARS, get_env_name, TRUE, TRUE},
4765 	    {EXPAND_USER, get_users, TRUE, FALSE},
4766 	};
4767 	int	i;
4768 
4769 	/*
4770 	 * Find a context in the table and call the ExpandGeneric() with the
4771 	 * right function to do the expansion.
4772 	 */
4773 	ret = FAIL;
4774 	for (i = 0; i < (int)(sizeof(tab) / sizeof(struct expgen)); ++i)
4775 	    if (xp->xp_context == tab[i].context)
4776 	    {
4777 		if (tab[i].ic)
4778 		    regmatch.rm_ic = TRUE;
4779 		ret = ExpandGeneric(xp, &regmatch, num_file, file,
4780 						tab[i].func, tab[i].escaped);
4781 		break;
4782 	    }
4783     }
4784 
4785     vim_regfree(regmatch.regprog);
4786 
4787     return ret;
4788 #endif /* FEAT_CMDL_COMPL */
4789 }
4790 
4791 #if defined(FEAT_CMDL_COMPL) || defined(PROTO)
4792 /*
4793  * Expand a list of names.
4794  *
4795  * Generic function for command line completion.  It calls a function to
4796  * obtain strings, one by one.	The strings are matched against a regexp
4797  * program.  Matching strings are copied into an array, which is returned.
4798  *
4799  * Returns OK when no problems encountered, FAIL for error (out of memory).
4800  */
4801     int
4802 ExpandGeneric(xp, regmatch, num_file, file, func, escaped)
4803     expand_T	*xp;
4804     regmatch_T	*regmatch;
4805     int		*num_file;
4806     char_u	***file;
4807     char_u	*((*func)__ARGS((expand_T *, int)));
4808 					  /* returns a string from the list */
4809     int		escaped;
4810 {
4811     int		i;
4812     int		count = 0;
4813     int		round;
4814     char_u	*str;
4815 
4816     /* do this loop twice:
4817      * round == 0: count the number of matching names
4818      * round == 1: copy the matching names into allocated memory
4819      */
4820     for (round = 0; round <= 1; ++round)
4821     {
4822 	for (i = 0; ; ++i)
4823 	{
4824 	    str = (*func)(xp, i);
4825 	    if (str == NULL)	    /* end of list */
4826 		break;
4827 	    if (*str == NUL)	    /* skip empty strings */
4828 		continue;
4829 
4830 	    if (vim_regexec(regmatch, str, (colnr_T)0))
4831 	    {
4832 		if (round)
4833 		{
4834 		    if (escaped)
4835 			str = vim_strsave_escaped(str, (char_u *)" \t\\.");
4836 		    else
4837 			str = vim_strsave(str);
4838 		    (*file)[count] = str;
4839 #ifdef FEAT_MENU
4840 		    if (func == get_menu_names && str != NULL)
4841 		    {
4842 			/* test for separator added by get_menu_names() */
4843 			str += STRLEN(str) - 1;
4844 			if (*str == '\001')
4845 			    *str = '.';
4846 		    }
4847 #endif
4848 		}
4849 		++count;
4850 	    }
4851 	}
4852 	if (round == 0)
4853 	{
4854 	    if (count == 0)
4855 		return OK;
4856 	    *num_file = count;
4857 	    *file = (char_u **)alloc((unsigned)(count * sizeof(char_u *)));
4858 	    if (*file == NULL)
4859 	    {
4860 		*file = (char_u **)"";
4861 		return FAIL;
4862 	    }
4863 	    count = 0;
4864 	}
4865     }
4866 
4867     /* Sort the results.  Keep menu's in the specified order. */
4868     if (xp->xp_context != EXPAND_MENUNAMES && xp->xp_context != EXPAND_MENUS)
4869     {
4870 	if (xp->xp_context == EXPAND_EXPRESSION
4871 		|| xp->xp_context == EXPAND_FUNCTIONS
4872 		|| xp->xp_context == EXPAND_USER_FUNC)
4873 	    /* <SNR> functions should be sorted to the end. */
4874 	    qsort((void *)*file, (size_t)*num_file, sizeof(char_u *),
4875 							   sort_func_compare);
4876 	else
4877 	    sort_strings(*file, *num_file);
4878     }
4879 
4880 #ifdef FEAT_CMDL_COMPL
4881     /* Reset the variables used for special highlight names expansion, so that
4882      * they don't show up when getting normal highlight names by ID. */
4883     reset_expand_highlight();
4884 #endif
4885 
4886     return OK;
4887 }
4888 
4889 /*
4890  * Complete a shell command.
4891  * Returns FAIL or OK;
4892  */
4893     static int
4894 expand_shellcmd(filepat, num_file, file, flagsarg)
4895     char_u	*filepat;	/* pattern to match with command names */
4896     int		*num_file;	/* return: number of matches */
4897     char_u	***file;	/* return: array with matches */
4898     int		flagsarg;	/* EW_ flags */
4899 {
4900     char_u	*pat;
4901     int		i;
4902     char_u	*path;
4903     int		mustfree = FALSE;
4904     garray_T    ga;
4905     char_u	*buf = alloc(MAXPATHL);
4906     size_t	l;
4907     char_u	*s, *e;
4908     int		flags = flagsarg;
4909     int		ret;
4910     int		did_curdir = FALSE;
4911 
4912     if (buf == NULL)
4913 	return FAIL;
4914 
4915     /* for ":set path=" and ":set tags=" halve backslashes for escaped
4916      * space */
4917     pat = vim_strsave(filepat);
4918     for (i = 0; pat[i]; ++i)
4919 	if (pat[i] == '\\' && pat[i + 1] == ' ')
4920 	    STRMOVE(pat + i, pat + i + 1);
4921 
4922     flags |= EW_FILE | EW_EXEC | EW_SHELLCMD;
4923 
4924     /* For an absolute name we don't use $PATH. */
4925     if (mch_isFullName(pat))
4926 	path = (char_u *)" ";
4927     else if ((pat[0] == '.' && (vim_ispathsep(pat[1])
4928 			    || (pat[1] == '.' && vim_ispathsep(pat[2])))))
4929 	path = (char_u *)".";
4930     else
4931     {
4932 	path = vim_getenv((char_u *)"PATH", &mustfree);
4933 	if (path == NULL)
4934 	    path = (char_u *)"";
4935     }
4936 
4937     /*
4938      * Go over all directories in $PATH.  Expand matches in that directory and
4939      * collect them in "ga".  When "." is not in $PATH also expand for the
4940      * current directory, to find "subdir/cmd".
4941      */
4942     ga_init2(&ga, (int)sizeof(char *), 10);
4943     for (s = path; ; s = e)
4944     {
4945 	if (*s == NUL)
4946 	{
4947 	    if (did_curdir)
4948 		break;
4949 	    /* Find directories in the current directory, path is empty. */
4950 	    did_curdir = TRUE;
4951 	}
4952 	else if (*s == '.')
4953 	    did_curdir = TRUE;
4954 
4955 	if (*s == ' ')
4956 	    ++s;	/* Skip space used for absolute path name. */
4957 
4958 #if defined(MSDOS) || defined(MSWIN)
4959 	e = vim_strchr(s, ';');
4960 #else
4961 	e = vim_strchr(s, ':');
4962 #endif
4963 	if (e == NULL)
4964 	    e = s + STRLEN(s);
4965 
4966 	l = e - s;
4967 	if (l > MAXPATHL - 5)
4968 	    break;
4969 	vim_strncpy(buf, s, l);
4970 	add_pathsep(buf);
4971 	l = STRLEN(buf);
4972 	vim_strncpy(buf + l, pat, MAXPATHL - 1 - l);
4973 
4974 	/* Expand matches in one directory of $PATH. */
4975 	ret = expand_wildcards(1, &buf, num_file, file, flags);
4976 	if (ret == OK)
4977 	{
4978 	    if (ga_grow(&ga, *num_file) == FAIL)
4979 		FreeWild(*num_file, *file);
4980 	    else
4981 	    {
4982 		for (i = 0; i < *num_file; ++i)
4983 		{
4984 		    s = (*file)[i];
4985 		    if (STRLEN(s) > l)
4986 		    {
4987 			/* Remove the path again. */
4988 			STRMOVE(s, s + l);
4989 			((char_u **)ga.ga_data)[ga.ga_len++] = s;
4990 		    }
4991 		    else
4992 			vim_free(s);
4993 		}
4994 		vim_free(*file);
4995 	    }
4996 	}
4997 	if (*e != NUL)
4998 	    ++e;
4999     }
5000     *file = ga.ga_data;
5001     *num_file = ga.ga_len;
5002 
5003     vim_free(buf);
5004     vim_free(pat);
5005     if (mustfree)
5006 	vim_free(path);
5007     return OK;
5008 }
5009 
5010 
5011 # if defined(FEAT_USR_CMDS) && defined(FEAT_EVAL)
5012 static void * call_user_expand_func __ARGS((void *(*user_expand_func) __ARGS((char_u *, int, char_u **, int)), expand_T	*xp, int *num_file, char_u ***file));
5013 
5014 /*
5015  * Call "user_expand_func()" to invoke a user defined VimL function and return
5016  * the result (either a string or a List).
5017  */
5018     static void *
5019 call_user_expand_func(user_expand_func, xp, num_file, file)
5020     void	*(*user_expand_func) __ARGS((char_u *, int, char_u **, int));
5021     expand_T	*xp;
5022     int		*num_file;
5023     char_u	***file;
5024 {
5025     int		keep = 0;
5026     char_u	num[50];
5027     char_u	*args[3];
5028     int		save_current_SID = current_SID;
5029     void	*ret;
5030     struct cmdline_info	    save_ccline;
5031 
5032     if (xp->xp_arg == NULL || xp->xp_arg[0] == '\0' || xp->xp_line == NULL)
5033 	return NULL;
5034     *num_file = 0;
5035     *file = NULL;
5036 
5037     if (ccline.cmdbuff != NULL)
5038     {
5039 	keep = ccline.cmdbuff[ccline.cmdlen];
5040 	ccline.cmdbuff[ccline.cmdlen] = 0;
5041     }
5042 
5043     args[0] = vim_strnsave(xp->xp_pattern, xp->xp_pattern_len);
5044     args[1] = xp->xp_line;
5045     sprintf((char *)num, "%d", xp->xp_col);
5046     args[2] = num;
5047 
5048     /* Save the cmdline, we don't know what the function may do. */
5049     save_ccline = ccline;
5050     ccline.cmdbuff = NULL;
5051     ccline.cmdprompt = NULL;
5052     current_SID = xp->xp_scriptID;
5053 
5054     ret = user_expand_func(xp->xp_arg, 3, args, FALSE);
5055 
5056     ccline = save_ccline;
5057     current_SID = save_current_SID;
5058     if (ccline.cmdbuff != NULL)
5059 	ccline.cmdbuff[ccline.cmdlen] = keep;
5060 
5061     vim_free(args[0]);
5062     return ret;
5063 }
5064 
5065 /*
5066  * Expand names with a function defined by the user.
5067  */
5068     static int
5069 ExpandUserDefined(xp, regmatch, num_file, file)
5070     expand_T	*xp;
5071     regmatch_T	*regmatch;
5072     int		*num_file;
5073     char_u	***file;
5074 {
5075     char_u	*retstr;
5076     char_u	*s;
5077     char_u	*e;
5078     char_u      keep;
5079     garray_T	ga;
5080 
5081     retstr = call_user_expand_func(call_func_retstr, xp, num_file, file);
5082     if (retstr == NULL)
5083 	return FAIL;
5084 
5085     ga_init2(&ga, (int)sizeof(char *), 3);
5086     for (s = retstr; *s != NUL; s = e)
5087     {
5088 	e = vim_strchr(s, '\n');
5089 	if (e == NULL)
5090 	    e = s + STRLEN(s);
5091 	keep = *e;
5092 	*e = 0;
5093 
5094 	if (xp->xp_pattern[0] && vim_regexec(regmatch, s, (colnr_T)0) == 0)
5095 	{
5096 	    *e = keep;
5097 	    if (*e != NUL)
5098 		++e;
5099 	    continue;
5100 	}
5101 
5102 	if (ga_grow(&ga, 1) == FAIL)
5103 	    break;
5104 
5105 	((char_u **)ga.ga_data)[ga.ga_len] = vim_strnsave(s, (int)(e - s));
5106 	++ga.ga_len;
5107 
5108 	*e = keep;
5109 	if (*e != NUL)
5110 	    ++e;
5111     }
5112     vim_free(retstr);
5113     *file = ga.ga_data;
5114     *num_file = ga.ga_len;
5115     return OK;
5116 }
5117 
5118 /*
5119  * Expand names with a list returned by a function defined by the user.
5120  */
5121     static int
5122 ExpandUserList(xp, num_file, file)
5123     expand_T	*xp;
5124     int		*num_file;
5125     char_u	***file;
5126 {
5127     list_T      *retlist;
5128     listitem_T	*li;
5129     garray_T	ga;
5130 
5131     retlist = call_user_expand_func(call_func_retlist, xp, num_file, file);
5132     if (retlist == NULL)
5133 	return FAIL;
5134 
5135     ga_init2(&ga, (int)sizeof(char *), 3);
5136     /* Loop over the items in the list. */
5137     for (li = retlist->lv_first; li != NULL; li = li->li_next)
5138     {
5139 	if (li->li_tv.v_type != VAR_STRING || li->li_tv.vval.v_string == NULL)
5140 	    continue;  /* Skip non-string items and empty strings */
5141 
5142 	if (ga_grow(&ga, 1) == FAIL)
5143 	    break;
5144 
5145 	((char_u **)ga.ga_data)[ga.ga_len] =
5146 					 vim_strsave(li->li_tv.vval.v_string);
5147 	++ga.ga_len;
5148     }
5149     list_unref(retlist);
5150 
5151     *file = ga.ga_data;
5152     *num_file = ga.ga_len;
5153     return OK;
5154 }
5155 #endif
5156 
5157 /*
5158  * Expand color scheme, compiler or filetype names:
5159  * 'runtimepath'/{dirnames}/{pat}.vim
5160  * "dirnames" is an array with one or more directory names.
5161  */
5162     static int
5163 ExpandRTDir(pat, num_file, file, dirnames)
5164     char_u	*pat;
5165     int		*num_file;
5166     char_u	***file;
5167     char	*dirnames[];
5168 {
5169     char_u	*s;
5170     char_u	*e;
5171     char_u	*match;
5172     garray_T	ga;
5173     int		i;
5174     int		pat_len;
5175 
5176     *num_file = 0;
5177     *file = NULL;
5178     pat_len = (int)STRLEN(pat);
5179     ga_init2(&ga, (int)sizeof(char *), 10);
5180 
5181     for (i = 0; dirnames[i] != NULL; ++i)
5182     {
5183 	s = alloc((unsigned)(STRLEN(dirnames[i]) + pat_len + 7));
5184 	if (s == NULL)
5185 	{
5186 	    ga_clear_strings(&ga);
5187 	    return FAIL;
5188 	}
5189 	sprintf((char *)s, "%s/%s*.vim", dirnames[i], pat);
5190 	globpath(p_rtp, s, &ga, 0);
5191 	vim_free(s);
5192     }
5193 
5194     for (i = 0; i < ga.ga_len; ++i)
5195     {
5196 	match = ((char_u **)ga.ga_data)[i];
5197 	s = match;
5198 	e = s + STRLEN(s);
5199 	if (e - 4 > s && STRNICMP(e - 4, ".vim", 4) == 0)
5200 	{
5201 	    e -= 4;
5202 	    for (s = e; s > match; mb_ptr_back(match, s))
5203 		if (s < match || vim_ispathsep(*s))
5204 		    break;
5205 	    ++s;
5206 	    *e = NUL;
5207 	    mch_memmove(match, s, e - s + 1);
5208 	}
5209     }
5210 
5211     if (ga.ga_len == 0)
5212 	return FAIL;
5213 
5214     /* Sort and remove duplicates which can happen when specifying multiple
5215      * directories in dirnames. */
5216     remove_duplicates(&ga);
5217 
5218     *file = ga.ga_data;
5219     *num_file = ga.ga_len;
5220     return OK;
5221 }
5222 
5223 #endif
5224 
5225 #if defined(FEAT_CMDL_COMPL) || defined(FEAT_EVAL) || defined(PROTO)
5226 /*
5227  * Expand "file" for all comma-separated directories in "path".
5228  * Adds the matches to "ga".  Caller must init "ga".
5229  */
5230     void
5231 globpath(path, file, ga, expand_options)
5232     char_u	*path;
5233     char_u	*file;
5234     garray_T	*ga;
5235     int		expand_options;
5236 {
5237     expand_T	xpc;
5238     char_u	*buf;
5239     int		i;
5240     int		num_p;
5241     char_u	**p;
5242 
5243     buf = alloc(MAXPATHL);
5244     if (buf == NULL)
5245 	return;
5246 
5247     ExpandInit(&xpc);
5248     xpc.xp_context = EXPAND_FILES;
5249 
5250     /* Loop over all entries in {path}. */
5251     while (*path != NUL)
5252     {
5253 	/* Copy one item of the path to buf[] and concatenate the file name. */
5254 	copy_option_part(&path, buf, MAXPATHL, ",");
5255 	if (STRLEN(buf) + STRLEN(file) + 2 < MAXPATHL)
5256 	{
5257 # if defined(MSWIN) || defined(MSDOS)
5258 	    /* Using the platform's path separator (\) makes vim incorrectly
5259 	     * treat it as an escape character, use '/' instead. */
5260 	    if (*buf != NUL && !after_pathsep(buf, buf + STRLEN(buf)))
5261 		STRCAT(buf, "/");
5262 # else
5263 	    add_pathsep(buf);
5264 # endif
5265 	    STRCAT(buf, file);
5266 	    if (ExpandFromContext(&xpc, buf, &num_p, &p,
5267 			     WILD_SILENT|expand_options) != FAIL && num_p > 0)
5268 	    {
5269 		ExpandEscape(&xpc, buf, num_p, p, WILD_SILENT|expand_options);
5270 
5271 		if (ga_grow(ga, num_p) == OK)
5272 		{
5273 		    for (i = 0; i < num_p; ++i)
5274 		    {
5275 			((char_u **)ga->ga_data)[ga->ga_len] =
5276 					vim_strnsave(p[i], (int)STRLEN(p[i]));
5277 			++ga->ga_len;
5278 		    }
5279 		}
5280 
5281 		FreeWild(num_p, p);
5282 	    }
5283 	}
5284     }
5285 
5286     vim_free(buf);
5287 }
5288 
5289 #endif
5290 
5291 #if defined(FEAT_CMDHIST) || defined(PROTO)
5292 
5293 /*********************************
5294  *  Command line history stuff	 *
5295  *********************************/
5296 
5297 /*
5298  * Translate a history character to the associated type number.
5299  */
5300     static int
5301 hist_char2type(c)
5302     int	    c;
5303 {
5304     if (c == ':')
5305 	return HIST_CMD;
5306     if (c == '=')
5307 	return HIST_EXPR;
5308     if (c == '@')
5309 	return HIST_INPUT;
5310     if (c == '>')
5311 	return HIST_DEBUG;
5312     return HIST_SEARCH;	    /* must be '?' or '/' */
5313 }
5314 
5315 /*
5316  * Table of history names.
5317  * These names are used in :history and various hist...() functions.
5318  * It is sufficient to give the significant prefix of a history name.
5319  */
5320 
5321 static char *(history_names[]) =
5322 {
5323     "cmd",
5324     "search",
5325     "expr",
5326     "input",
5327     "debug",
5328     NULL
5329 };
5330 
5331 #if defined(FEAT_CMDL_COMPL) || defined(PROTO)
5332 /*
5333  * Function given to ExpandGeneric() to obtain the possible first
5334  * arguments of the ":history command.
5335  */
5336     static char_u *
5337 get_history_arg(xp, idx)
5338     expand_T	*xp UNUSED;
5339     int		idx;
5340 {
5341     static char_u compl[2] = { NUL, NUL };
5342     char *short_names = ":=@>?/";
5343     int short_names_count = (int)STRLEN(short_names);
5344     int history_name_count = sizeof(history_names) / sizeof(char *) - 1;
5345 
5346     if (idx < short_names_count)
5347     {
5348 	compl[0] = (char_u)short_names[idx];
5349 	return compl;
5350     }
5351     if (idx < short_names_count + history_name_count)
5352 	return (char_u *)history_names[idx - short_names_count];
5353     if (idx == short_names_count + history_name_count)
5354 	return (char_u *)"all";
5355     return NULL;
5356 }
5357 #endif
5358 
5359 /*
5360  * init_history() - Initialize the command line history.
5361  * Also used to re-allocate the history when the size changes.
5362  */
5363     void
5364 init_history()
5365 {
5366     int		newlen;	    /* new length of history table */
5367     histentry_T	*temp;
5368     int		i;
5369     int		j;
5370     int		type;
5371 
5372     /*
5373      * If size of history table changed, reallocate it
5374      */
5375     newlen = (int)p_hi;
5376     if (newlen != hislen)			/* history length changed */
5377     {
5378 	for (type = 0; type < HIST_COUNT; ++type)   /* adjust the tables */
5379 	{
5380 	    if (newlen)
5381 	    {
5382 		temp = (histentry_T *)lalloc(
5383 				(long_u)(newlen * sizeof(histentry_T)), TRUE);
5384 		if (temp == NULL)   /* out of memory! */
5385 		{
5386 		    if (type == 0)  /* first one: just keep the old length */
5387 		    {
5388 			newlen = hislen;
5389 			break;
5390 		    }
5391 		    /* Already changed one table, now we can only have zero
5392 		     * length for all tables. */
5393 		    newlen = 0;
5394 		    type = -1;
5395 		    continue;
5396 		}
5397 	    }
5398 	    else
5399 		temp = NULL;
5400 	    if (newlen == 0 || temp != NULL)
5401 	    {
5402 		if (hisidx[type] < 0)		/* there are no entries yet */
5403 		{
5404 		    for (i = 0; i < newlen; ++i)
5405 			clear_hist_entry(&temp[i]);
5406 		}
5407 		else if (newlen > hislen)	/* array becomes bigger */
5408 		{
5409 		    for (i = 0; i <= hisidx[type]; ++i)
5410 			temp[i] = history[type][i];
5411 		    j = i;
5412 		    for ( ; i <= newlen - (hislen - hisidx[type]); ++i)
5413 			clear_hist_entry(&temp[i]);
5414 		    for ( ; j < hislen; ++i, ++j)
5415 			temp[i] = history[type][j];
5416 		}
5417 		else				/* array becomes smaller or 0 */
5418 		{
5419 		    j = hisidx[type];
5420 		    for (i = newlen - 1; ; --i)
5421 		    {
5422 			if (i >= 0)		/* copy newest entries */
5423 			    temp[i] = history[type][j];
5424 			else			/* remove older entries */
5425 			    vim_free(history[type][j].hisstr);
5426 			if (--j < 0)
5427 			    j = hislen - 1;
5428 			if (j == hisidx[type])
5429 			    break;
5430 		    }
5431 		    hisidx[type] = newlen - 1;
5432 		}
5433 		vim_free(history[type]);
5434 		history[type] = temp;
5435 	    }
5436 	}
5437 	hislen = newlen;
5438     }
5439 }
5440 
5441     static void
5442 clear_hist_entry(hisptr)
5443     histentry_T	*hisptr;
5444 {
5445     hisptr->hisnum = 0;
5446     hisptr->viminfo = FALSE;
5447     hisptr->hisstr = NULL;
5448 }
5449 
5450 /*
5451  * Check if command line 'str' is already in history.
5452  * If 'move_to_front' is TRUE, matching entry is moved to end of history.
5453  */
5454     static int
5455 in_history(type, str, move_to_front, sep, writing)
5456     int	    type;
5457     char_u  *str;
5458     int	    move_to_front;	/* Move the entry to the front if it exists */
5459     int	    sep;
5460     int	    writing;		/* ignore entries read from viminfo */
5461 {
5462     int	    i;
5463     int	    last_i = -1;
5464     char_u  *p;
5465 
5466     if (hisidx[type] < 0)
5467 	return FALSE;
5468     i = hisidx[type];
5469     do
5470     {
5471 	if (history[type][i].hisstr == NULL)
5472 	    return FALSE;
5473 
5474 	/* For search history, check that the separator character matches as
5475 	 * well. */
5476 	p = history[type][i].hisstr;
5477 	if (STRCMP(str, p) == 0
5478 		&& !(writing && history[type][i].viminfo)
5479 		&& (type != HIST_SEARCH || sep == p[STRLEN(p) + 1]))
5480 	{
5481 	    if (!move_to_front)
5482 		return TRUE;
5483 	    last_i = i;
5484 	    break;
5485 	}
5486 	if (--i < 0)
5487 	    i = hislen - 1;
5488     } while (i != hisidx[type]);
5489 
5490     if (last_i >= 0)
5491     {
5492 	str = history[type][i].hisstr;
5493 	while (i != hisidx[type])
5494 	{
5495 	    if (++i >= hislen)
5496 		i = 0;
5497 	    history[type][last_i] = history[type][i];
5498 	    last_i = i;
5499 	}
5500 	history[type][i].hisnum = ++hisnum[type];
5501 	history[type][i].viminfo = FALSE;
5502 	history[type][i].hisstr = str;
5503 	return TRUE;
5504     }
5505     return FALSE;
5506 }
5507 
5508 /*
5509  * Convert history name (from table above) to its HIST_ equivalent.
5510  * When "name" is empty, return "cmd" history.
5511  * Returns -1 for unknown history name.
5512  */
5513     int
5514 get_histtype(name)
5515     char_u	*name;
5516 {
5517     int		i;
5518     int		len = (int)STRLEN(name);
5519 
5520     /* No argument: use current history. */
5521     if (len == 0)
5522 	return hist_char2type(ccline.cmdfirstc);
5523 
5524     for (i = 0; history_names[i] != NULL; ++i)
5525 	if (STRNICMP(name, history_names[i], len) == 0)
5526 	    return i;
5527 
5528     if (vim_strchr((char_u *)":=@>?/", name[0]) != NULL && name[1] == NUL)
5529 	return hist_char2type(name[0]);
5530 
5531     return -1;
5532 }
5533 
5534 static int	last_maptick = -1;	/* last seen maptick */
5535 
5536 /*
5537  * Add the given string to the given history.  If the string is already in the
5538  * history then it is moved to the front.  "histype" may be one of he HIST_
5539  * values.
5540  */
5541     void
5542 add_to_history(histype, new_entry, in_map, sep)
5543     int		histype;
5544     char_u	*new_entry;
5545     int		in_map;		/* consider maptick when inside a mapping */
5546     int		sep;		/* separator character used (search hist) */
5547 {
5548     histentry_T	*hisptr;
5549     int		len;
5550 
5551     if (hislen == 0)		/* no history */
5552 	return;
5553 
5554     if (cmdmod.keeppatterns && histype == HIST_SEARCH)
5555 	return;
5556 
5557     /*
5558      * Searches inside the same mapping overwrite each other, so that only
5559      * the last line is kept.  Be careful not to remove a line that was moved
5560      * down, only lines that were added.
5561      */
5562     if (histype == HIST_SEARCH && in_map)
5563     {
5564 	if (maptick == last_maptick)
5565 	{
5566 	    /* Current line is from the same mapping, remove it */
5567 	    hisptr = &history[HIST_SEARCH][hisidx[HIST_SEARCH]];
5568 	    vim_free(hisptr->hisstr);
5569 	    clear_hist_entry(hisptr);
5570 	    --hisnum[histype];
5571 	    if (--hisidx[HIST_SEARCH] < 0)
5572 		hisidx[HIST_SEARCH] = hislen - 1;
5573 	}
5574 	last_maptick = -1;
5575     }
5576     if (!in_history(histype, new_entry, TRUE, sep, FALSE))
5577     {
5578 	if (++hisidx[histype] == hislen)
5579 	    hisidx[histype] = 0;
5580 	hisptr = &history[histype][hisidx[histype]];
5581 	vim_free(hisptr->hisstr);
5582 
5583 	/* Store the separator after the NUL of the string. */
5584 	len = (int)STRLEN(new_entry);
5585 	hisptr->hisstr = vim_strnsave(new_entry, len + 2);
5586 	if (hisptr->hisstr != NULL)
5587 	    hisptr->hisstr[len + 1] = sep;
5588 
5589 	hisptr->hisnum = ++hisnum[histype];
5590 	hisptr->viminfo = FALSE;
5591 	if (histype == HIST_SEARCH && in_map)
5592 	    last_maptick = maptick;
5593     }
5594 }
5595 
5596 #if defined(FEAT_EVAL) || defined(PROTO)
5597 
5598 /*
5599  * Get identifier of newest history entry.
5600  * "histype" may be one of the HIST_ values.
5601  */
5602     int
5603 get_history_idx(histype)
5604     int	    histype;
5605 {
5606     if (hislen == 0 || histype < 0 || histype >= HIST_COUNT
5607 		    || hisidx[histype] < 0)
5608 	return -1;
5609 
5610     return history[histype][hisidx[histype]].hisnum;
5611 }
5612 
5613 static struct cmdline_info *get_ccline_ptr __ARGS((void));
5614 
5615 /*
5616  * Get pointer to the command line info to use. cmdline_paste() may clear
5617  * ccline and put the previous value in prev_ccline.
5618  */
5619     static struct cmdline_info *
5620 get_ccline_ptr()
5621 {
5622     if ((State & CMDLINE) == 0)
5623 	return NULL;
5624     if (ccline.cmdbuff != NULL)
5625 	return &ccline;
5626     if (prev_ccline_used && prev_ccline.cmdbuff != NULL)
5627 	return &prev_ccline;
5628     return NULL;
5629 }
5630 
5631 /*
5632  * Get the current command line in allocated memory.
5633  * Only works when the command line is being edited.
5634  * Returns NULL when something is wrong.
5635  */
5636     char_u *
5637 get_cmdline_str()
5638 {
5639     struct cmdline_info *p = get_ccline_ptr();
5640 
5641     if (p == NULL)
5642 	return NULL;
5643     return vim_strnsave(p->cmdbuff, p->cmdlen);
5644 }
5645 
5646 /*
5647  * Get the current command line position, counted in bytes.
5648  * Zero is the first position.
5649  * Only works when the command line is being edited.
5650  * Returns -1 when something is wrong.
5651  */
5652     int
5653 get_cmdline_pos()
5654 {
5655     struct cmdline_info *p = get_ccline_ptr();
5656 
5657     if (p == NULL)
5658 	return -1;
5659     return p->cmdpos;
5660 }
5661 
5662 /*
5663  * Set the command line byte position to "pos".  Zero is the first position.
5664  * Only works when the command line is being edited.
5665  * Returns 1 when failed, 0 when OK.
5666  */
5667     int
5668 set_cmdline_pos(pos)
5669     int		pos;
5670 {
5671     struct cmdline_info *p = get_ccline_ptr();
5672 
5673     if (p == NULL)
5674 	return 1;
5675 
5676     /* The position is not set directly but after CTRL-\ e or CTRL-R = has
5677      * changed the command line. */
5678     if (pos < 0)
5679 	new_cmdpos = 0;
5680     else
5681 	new_cmdpos = pos;
5682     return 0;
5683 }
5684 
5685 /*
5686  * Get the current command-line type.
5687  * Returns ':' or '/' or '?' or '@' or '>' or '-'
5688  * Only works when the command line is being edited.
5689  * Returns NUL when something is wrong.
5690  */
5691     int
5692 get_cmdline_type()
5693 {
5694     struct cmdline_info *p = get_ccline_ptr();
5695 
5696     if (p == NULL)
5697 	return NUL;
5698     if (p->cmdfirstc == NUL)
5699 	return (p->input_fn) ? '@' : '-';
5700     return p->cmdfirstc;
5701 }
5702 
5703 /*
5704  * Calculate history index from a number:
5705  *   num > 0: seen as identifying number of a history entry
5706  *   num < 0: relative position in history wrt newest entry
5707  * "histype" may be one of the HIST_ values.
5708  */
5709     static int
5710 calc_hist_idx(histype, num)
5711     int		histype;
5712     int		num;
5713 {
5714     int		i;
5715     histentry_T	*hist;
5716     int		wrapped = FALSE;
5717 
5718     if (hislen == 0 || histype < 0 || histype >= HIST_COUNT
5719 		    || (i = hisidx[histype]) < 0 || num == 0)
5720 	return -1;
5721 
5722     hist = history[histype];
5723     if (num > 0)
5724     {
5725 	while (hist[i].hisnum > num)
5726 	    if (--i < 0)
5727 	    {
5728 		if (wrapped)
5729 		    break;
5730 		i += hislen;
5731 		wrapped = TRUE;
5732 	    }
5733 	if (hist[i].hisnum == num && hist[i].hisstr != NULL)
5734 	    return i;
5735     }
5736     else if (-num <= hislen)
5737     {
5738 	i += num + 1;
5739 	if (i < 0)
5740 	    i += hislen;
5741 	if (hist[i].hisstr != NULL)
5742 	    return i;
5743     }
5744     return -1;
5745 }
5746 
5747 /*
5748  * Get a history entry by its index.
5749  * "histype" may be one of the HIST_ values.
5750  */
5751     char_u *
5752 get_history_entry(histype, idx)
5753     int	    histype;
5754     int	    idx;
5755 {
5756     idx = calc_hist_idx(histype, idx);
5757     if (idx >= 0)
5758 	return history[histype][idx].hisstr;
5759     else
5760 	return (char_u *)"";
5761 }
5762 
5763 /*
5764  * Clear all entries of a history.
5765  * "histype" may be one of the HIST_ values.
5766  */
5767     int
5768 clr_history(histype)
5769     int		histype;
5770 {
5771     int		i;
5772     histentry_T	*hisptr;
5773 
5774     if (hislen != 0 && histype >= 0 && histype < HIST_COUNT)
5775     {
5776 	hisptr = history[histype];
5777 	for (i = hislen; i--;)
5778 	{
5779 	    vim_free(hisptr->hisstr);
5780 	    clear_hist_entry(hisptr);
5781 	}
5782 	hisidx[histype] = -1;	/* mark history as cleared */
5783 	hisnum[histype] = 0;	/* reset identifier counter */
5784 	return OK;
5785     }
5786     return FAIL;
5787 }
5788 
5789 /*
5790  * Remove all entries matching {str} from a history.
5791  * "histype" may be one of the HIST_ values.
5792  */
5793     int
5794 del_history_entry(histype, str)
5795     int		histype;
5796     char_u	*str;
5797 {
5798     regmatch_T	regmatch;
5799     histentry_T	*hisptr;
5800     int		idx;
5801     int		i;
5802     int		last;
5803     int		found = FALSE;
5804 
5805     regmatch.regprog = NULL;
5806     regmatch.rm_ic = FALSE;	/* always match case */
5807     if (hislen != 0
5808 	    && histype >= 0
5809 	    && histype < HIST_COUNT
5810 	    && *str != NUL
5811 	    && (idx = hisidx[histype]) >= 0
5812 	    && (regmatch.regprog = vim_regcomp(str, RE_MAGIC + RE_STRING))
5813 								      != NULL)
5814     {
5815 	i = last = idx;
5816 	do
5817 	{
5818 	    hisptr = &history[histype][i];
5819 	    if (hisptr->hisstr == NULL)
5820 		break;
5821 	    if (vim_regexec(&regmatch, hisptr->hisstr, (colnr_T)0))
5822 	    {
5823 		found = TRUE;
5824 		vim_free(hisptr->hisstr);
5825 		clear_hist_entry(hisptr);
5826 	    }
5827 	    else
5828 	    {
5829 		if (i != last)
5830 		{
5831 		    history[histype][last] = *hisptr;
5832 		    clear_hist_entry(hisptr);
5833 		}
5834 		if (--last < 0)
5835 		    last += hislen;
5836 	    }
5837 	    if (--i < 0)
5838 		i += hislen;
5839 	} while (i != idx);
5840 	if (history[histype][idx].hisstr == NULL)
5841 	    hisidx[histype] = -1;
5842     }
5843     vim_regfree(regmatch.regprog);
5844     return found;
5845 }
5846 
5847 /*
5848  * Remove an indexed entry from a history.
5849  * "histype" may be one of the HIST_ values.
5850  */
5851     int
5852 del_history_idx(histype, idx)
5853     int	    histype;
5854     int	    idx;
5855 {
5856     int	    i, j;
5857 
5858     i = calc_hist_idx(histype, idx);
5859     if (i < 0)
5860 	return FALSE;
5861     idx = hisidx[histype];
5862     vim_free(history[histype][i].hisstr);
5863 
5864     /* When deleting the last added search string in a mapping, reset
5865      * last_maptick, so that the last added search string isn't deleted again.
5866      */
5867     if (histype == HIST_SEARCH && maptick == last_maptick && i == idx)
5868 	last_maptick = -1;
5869 
5870     while (i != idx)
5871     {
5872 	j = (i + 1) % hislen;
5873 	history[histype][i] = history[histype][j];
5874 	i = j;
5875     }
5876     clear_hist_entry(&history[histype][i]);
5877     if (--i < 0)
5878 	i += hislen;
5879     hisidx[histype] = i;
5880     return TRUE;
5881 }
5882 
5883 #endif /* FEAT_EVAL */
5884 
5885 #if defined(FEAT_CRYPT) || defined(PROTO)
5886 /*
5887  * Very specific function to remove the value in ":set key=val" from the
5888  * history.
5889  */
5890     void
5891 remove_key_from_history()
5892 {
5893     char_u	*p;
5894     int		i;
5895 
5896     i = hisidx[HIST_CMD];
5897     if (i < 0)
5898 	return;
5899     p = history[HIST_CMD][i].hisstr;
5900     if (p != NULL)
5901 	for ( ; *p; ++p)
5902 	    if (STRNCMP(p, "key", 3) == 0 && !isalpha(p[3]))
5903 	    {
5904 		p = vim_strchr(p + 3, '=');
5905 		if (p == NULL)
5906 		    break;
5907 		++p;
5908 		for (i = 0; p[i] && !vim_iswhite(p[i]); ++i)
5909 		    if (p[i] == '\\' && p[i + 1])
5910 			++i;
5911 		STRMOVE(p, p + i);
5912 		--p;
5913 	    }
5914 }
5915 #endif
5916 
5917 #endif /* FEAT_CMDHIST */
5918 
5919 #if defined(FEAT_QUICKFIX) || defined(FEAT_CMDHIST) || defined(PROTO)
5920 /*
5921  * Get indices "num1,num2" that specify a range within a list (not a range of
5922  * text lines in a buffer!) from a string.  Used for ":history" and ":clist".
5923  * Returns OK if parsed successfully, otherwise FAIL.
5924  */
5925     int
5926 get_list_range(str, num1, num2)
5927     char_u	**str;
5928     int		*num1;
5929     int		*num2;
5930 {
5931     int		len;
5932     int		first = FALSE;
5933     long	num;
5934 
5935     *str = skipwhite(*str);
5936     if (**str == '-' || vim_isdigit(**str))  /* parse "from" part of range */
5937     {
5938 	vim_str2nr(*str, NULL, &len, FALSE, FALSE, &num, NULL, 0);
5939 	*str += len;
5940 	*num1 = (int)num;
5941 	first = TRUE;
5942     }
5943     *str = skipwhite(*str);
5944     if (**str == ',')			/* parse "to" part of range */
5945     {
5946 	*str = skipwhite(*str + 1);
5947 	vim_str2nr(*str, NULL, &len, FALSE, FALSE, &num, NULL, 0);
5948 	if (len > 0)
5949 	{
5950 	    *num2 = (int)num;
5951 	    *str = skipwhite(*str + len);
5952 	}
5953 	else if (!first)		/* no number given at all */
5954 	    return FAIL;
5955     }
5956     else if (first)			/* only one number given */
5957 	*num2 = *num1;
5958     return OK;
5959 }
5960 #endif
5961 
5962 #if defined(FEAT_CMDHIST) || defined(PROTO)
5963 /*
5964  * :history command - print a history
5965  */
5966     void
5967 ex_history(eap)
5968     exarg_T	*eap;
5969 {
5970     histentry_T	*hist;
5971     int		histype1 = HIST_CMD;
5972     int		histype2 = HIST_CMD;
5973     int		hisidx1 = 1;
5974     int		hisidx2 = -1;
5975     int		idx;
5976     int		i, j, k;
5977     char_u	*end;
5978     char_u	*arg = eap->arg;
5979 
5980     if (hislen == 0)
5981     {
5982 	MSG(_("'history' option is zero"));
5983 	return;
5984     }
5985 
5986     if (!(VIM_ISDIGIT(*arg) || *arg == '-' || *arg == ','))
5987     {
5988 	end = arg;
5989 	while (ASCII_ISALPHA(*end)
5990 		|| vim_strchr((char_u *)":=@>/?", *end) != NULL)
5991 	    end++;
5992 	i = *end;
5993 	*end = NUL;
5994 	histype1 = get_histtype(arg);
5995 	if (histype1 == -1)
5996 	{
5997 	    if (STRNICMP(arg, "all", STRLEN(arg)) == 0)
5998 	    {
5999 		histype1 = 0;
6000 		histype2 = HIST_COUNT-1;
6001 	    }
6002 	    else
6003 	    {
6004 		*end = i;
6005 		EMSG(_(e_trailing));
6006 		return;
6007 	    }
6008 	}
6009 	else
6010 	    histype2 = histype1;
6011 	*end = i;
6012     }
6013     else
6014 	end = arg;
6015     if (!get_list_range(&end, &hisidx1, &hisidx2) || *end != NUL)
6016     {
6017 	EMSG(_(e_trailing));
6018 	return;
6019     }
6020 
6021     for (; !got_int && histype1 <= histype2; ++histype1)
6022     {
6023 	STRCPY(IObuff, "\n      #  ");
6024 	STRCAT(STRCAT(IObuff, history_names[histype1]), " history");
6025 	MSG_PUTS_TITLE(IObuff);
6026 	idx = hisidx[histype1];
6027 	hist = history[histype1];
6028 	j = hisidx1;
6029 	k = hisidx2;
6030 	if (j < 0)
6031 	    j = (-j > hislen) ? 0 : hist[(hislen+j+idx+1) % hislen].hisnum;
6032 	if (k < 0)
6033 	    k = (-k > hislen) ? 0 : hist[(hislen+k+idx+1) % hislen].hisnum;
6034 	if (idx >= 0 && j <= k)
6035 	    for (i = idx + 1; !got_int; ++i)
6036 	    {
6037 		if (i == hislen)
6038 		    i = 0;
6039 		if (hist[i].hisstr != NULL
6040 			&& hist[i].hisnum >= j && hist[i].hisnum <= k)
6041 		{
6042 		    msg_putchar('\n');
6043 		    sprintf((char *)IObuff, "%c%6d  ", i == idx ? '>' : ' ',
6044 							      hist[i].hisnum);
6045 		    if (vim_strsize(hist[i].hisstr) > (int)Columns - 10)
6046 			trunc_string(hist[i].hisstr, IObuff + STRLEN(IObuff),
6047 			     (int)Columns - 10, IOSIZE - (int)STRLEN(IObuff));
6048 		    else
6049 			STRCAT(IObuff, hist[i].hisstr);
6050 		    msg_outtrans(IObuff);
6051 		    out_flush();
6052 		}
6053 		if (i == idx)
6054 		    break;
6055 	    }
6056     }
6057 }
6058 #endif
6059 
6060 #if (defined(FEAT_VIMINFO) && defined(FEAT_CMDHIST)) || defined(PROTO)
6061 /*
6062  * Buffers for history read from a viminfo file.  Only valid while reading.
6063  */
6064 static char_u **viminfo_history[HIST_COUNT] = {NULL, NULL, NULL, NULL};
6065 static int	viminfo_hisidx[HIST_COUNT] = {0, 0, 0, 0};
6066 static int	viminfo_hislen[HIST_COUNT] = {0, 0, 0, 0};
6067 static int	viminfo_add_at_front = FALSE;
6068 
6069 static int	hist_type2char __ARGS((int type, int use_question));
6070 
6071 /*
6072  * Translate a history type number to the associated character.
6073  */
6074     static int
6075 hist_type2char(type, use_question)
6076     int	    type;
6077     int	    use_question;	    /* use '?' instead of '/' */
6078 {
6079     if (type == HIST_CMD)
6080 	return ':';
6081     if (type == HIST_SEARCH)
6082     {
6083 	if (use_question)
6084 	    return '?';
6085 	else
6086 	    return '/';
6087     }
6088     if (type == HIST_EXPR)
6089 	return '=';
6090     return '@';
6091 }
6092 
6093 /*
6094  * Prepare for reading the history from the viminfo file.
6095  * This allocates history arrays to store the read history lines.
6096  */
6097     void
6098 prepare_viminfo_history(asklen, writing)
6099     int	    asklen;
6100     int	    writing;
6101 {
6102     int	    i;
6103     int	    num;
6104     int	    type;
6105     int	    len;
6106 
6107     init_history();
6108     viminfo_add_at_front = (asklen != 0 && !writing);
6109     if (asklen > hislen)
6110 	asklen = hislen;
6111 
6112     for (type = 0; type < HIST_COUNT; ++type)
6113     {
6114 	/* Count the number of empty spaces in the history list.  Entries read
6115 	 * from viminfo previously are also considered empty.  If there are
6116 	 * more spaces available than we request, then fill them up. */
6117 	for (i = 0, num = 0; i < hislen; i++)
6118 	    if (history[type][i].hisstr == NULL || history[type][i].viminfo)
6119 		num++;
6120 	len = asklen;
6121 	if (num > len)
6122 	    len = num;
6123 	if (len <= 0)
6124 	    viminfo_history[type] = NULL;
6125 	else
6126 	    viminfo_history[type] =
6127 		   (char_u **)lalloc((long_u)(len * sizeof(char_u *)), FALSE);
6128 	if (viminfo_history[type] == NULL)
6129 	    len = 0;
6130 	viminfo_hislen[type] = len;
6131 	viminfo_hisidx[type] = 0;
6132     }
6133 }
6134 
6135 /*
6136  * Accept a line from the viminfo, store it in the history array when it's
6137  * new.
6138  */
6139     int
6140 read_viminfo_history(virp, writing)
6141     vir_T	*virp;
6142     int		writing;
6143 {
6144     int		type;
6145     long_u	len;
6146     char_u	*val;
6147     char_u	*p;
6148 
6149     type = hist_char2type(virp->vir_line[0]);
6150     if (viminfo_hisidx[type] < viminfo_hislen[type])
6151     {
6152 	val = viminfo_readstring(virp, 1, TRUE);
6153 	if (val != NULL && *val != NUL)
6154 	{
6155 	    int sep = (*val == ' ' ? NUL : *val);
6156 
6157 	    if (!in_history(type, val + (type == HIST_SEARCH),
6158 					  viminfo_add_at_front, sep, writing))
6159 	    {
6160 		/* Need to re-allocate to append the separator byte. */
6161 		len = STRLEN(val);
6162 		p = lalloc(len + 2, TRUE);
6163 		if (p != NULL)
6164 		{
6165 		    if (type == HIST_SEARCH)
6166 		    {
6167 			/* Search entry: Move the separator from the first
6168 			 * column to after the NUL. */
6169 			mch_memmove(p, val + 1, (size_t)len);
6170 			p[len] = sep;
6171 		    }
6172 		    else
6173 		    {
6174 			/* Not a search entry: No separator in the viminfo
6175 			 * file, add a NUL separator. */
6176 			mch_memmove(p, val, (size_t)len + 1);
6177 			p[len + 1] = NUL;
6178 		    }
6179 		    viminfo_history[type][viminfo_hisidx[type]++] = p;
6180 		}
6181 	    }
6182 	}
6183 	vim_free(val);
6184     }
6185     return viminfo_readline(virp);
6186 }
6187 
6188 /*
6189  * Finish reading history lines from viminfo.  Not used when writing viminfo.
6190  */
6191     void
6192 finish_viminfo_history()
6193 {
6194     int idx;
6195     int i;
6196     int	type;
6197 
6198     for (type = 0; type < HIST_COUNT; ++type)
6199     {
6200 	if (history[type] == NULL)
6201 	    continue;
6202 	idx = hisidx[type] + viminfo_hisidx[type];
6203 	if (idx >= hislen)
6204 	    idx -= hislen;
6205 	else if (idx < 0)
6206 	    idx = hislen - 1;
6207 	if (viminfo_add_at_front)
6208 	    hisidx[type] = idx;
6209 	else
6210 	{
6211 	    if (hisidx[type] == -1)
6212 		hisidx[type] = hislen - 1;
6213 	    do
6214 	    {
6215 		if (history[type][idx].hisstr != NULL
6216 						|| history[type][idx].viminfo)
6217 		    break;
6218 		if (++idx == hislen)
6219 		    idx = 0;
6220 	    } while (idx != hisidx[type]);
6221 	    if (idx != hisidx[type] && --idx < 0)
6222 		idx = hislen - 1;
6223 	}
6224 	for (i = 0; i < viminfo_hisidx[type]; i++)
6225 	{
6226 	    vim_free(history[type][idx].hisstr);
6227 	    history[type][idx].hisstr = viminfo_history[type][i];
6228 	    history[type][idx].viminfo = TRUE;
6229 	    if (--idx < 0)
6230 		idx = hislen - 1;
6231 	}
6232 	idx += 1;
6233 	idx %= hislen;
6234 	for (i = 0; i < viminfo_hisidx[type]; i++)
6235 	{
6236 	    history[type][idx++].hisnum = ++hisnum[type];
6237 	    idx %= hislen;
6238 	}
6239 	vim_free(viminfo_history[type]);
6240 	viminfo_history[type] = NULL;
6241 	viminfo_hisidx[type] = 0;
6242     }
6243 }
6244 
6245 /*
6246  * Write history to viminfo file in "fp".
6247  * When "merge" is TRUE merge history lines with a previously read viminfo
6248  * file, data is in viminfo_history[].
6249  * When "merge" is FALSE just write all history lines.  Used for ":wviminfo!".
6250  */
6251     void
6252 write_viminfo_history(fp, merge)
6253     FILE    *fp;
6254     int	    merge;
6255 {
6256     int	    i;
6257     int	    type;
6258     int	    num_saved;
6259     char_u  *p;
6260     int	    c;
6261     int     round;
6262 
6263     init_history();
6264     if (hislen == 0)
6265 	return;
6266     for (type = 0; type < HIST_COUNT; ++type)
6267     {
6268 	num_saved = get_viminfo_parameter(hist_type2char(type, FALSE));
6269 	if (num_saved == 0)
6270 	    continue;
6271 	if (num_saved < 0)  /* Use default */
6272 	    num_saved = hislen;
6273 	fprintf(fp, _("\n# %s History (newest to oldest):\n"),
6274 			    type == HIST_CMD ? _("Command Line") :
6275 			    type == HIST_SEARCH ? _("Search String") :
6276 			    type == HIST_EXPR ?  _("Expression") :
6277 					_("Input Line"));
6278 	if (num_saved > hislen)
6279 	    num_saved = hislen;
6280 
6281 	/*
6282 	 * Merge typed and viminfo history:
6283 	 * round 1: history of typed commands.
6284 	 * round 2: history from recently read viminfo.
6285 	 */
6286 	for (round = 1; round <= 2; ++round)
6287 	{
6288 	    if (round == 1)
6289 		/* start at newest entry, somewhere in the list */
6290 		i = hisidx[type];
6291 	    else if (viminfo_hisidx[type] > 0)
6292 		/* start at newest entry, first in the list */
6293 		i = 0;
6294 	    else
6295 		/* empty list */
6296 		i = -1;
6297 	    if (i >= 0)
6298 		while (num_saved > 0
6299 			&& !(round == 2 && i >= viminfo_hisidx[type]))
6300 		{
6301 		    p = round == 1 ? history[type][i].hisstr
6302 				   : viminfo_history[type] == NULL ? NULL
6303 						   : viminfo_history[type][i];
6304 		    if (p != NULL && (round == 2
6305 				       || !merge
6306 				       || !history[type][i].viminfo))
6307 		    {
6308 			--num_saved;
6309 			fputc(hist_type2char(type, TRUE), fp);
6310 			/* For the search history: put the separator in the
6311 			 * second column; use a space if there isn't one. */
6312 			if (type == HIST_SEARCH)
6313 			{
6314 			    c = p[STRLEN(p) + 1];
6315 			    putc(c == NUL ? ' ' : c, fp);
6316 			}
6317 			viminfo_writestring(fp, p);
6318 		    }
6319 		    if (round == 1)
6320 		    {
6321 			/* Decrement index, loop around and stop when back at
6322 			 * the start. */
6323 			if (--i < 0)
6324 			    i = hislen - 1;
6325 			if (i == hisidx[type])
6326 			    break;
6327 		    }
6328 		    else
6329 		    {
6330 			/* Increment index. Stop at the end in the while. */
6331 			++i;
6332 		    }
6333 		}
6334 	}
6335 	for (i = 0; i < viminfo_hisidx[type]; ++i)
6336 	    if (viminfo_history[type] != NULL)
6337 		vim_free(viminfo_history[type][i]);
6338 	vim_free(viminfo_history[type]);
6339 	viminfo_history[type] = NULL;
6340 	viminfo_hisidx[type] = 0;
6341     }
6342 }
6343 #endif /* FEAT_VIMINFO */
6344 
6345 #if defined(FEAT_FKMAP) || defined(PROTO)
6346 /*
6347  * Write a character at the current cursor+offset position.
6348  * It is directly written into the command buffer block.
6349  */
6350     void
6351 cmd_pchar(c, offset)
6352     int	    c, offset;
6353 {
6354     if (ccline.cmdpos + offset >= ccline.cmdlen || ccline.cmdpos + offset < 0)
6355     {
6356 	EMSG(_("E198: cmd_pchar beyond the command length"));
6357 	return;
6358     }
6359     ccline.cmdbuff[ccline.cmdpos + offset] = (char_u)c;
6360     ccline.cmdbuff[ccline.cmdlen] = NUL;
6361 }
6362 
6363     int
6364 cmd_gchar(offset)
6365     int	    offset;
6366 {
6367     if (ccline.cmdpos + offset >= ccline.cmdlen || ccline.cmdpos + offset < 0)
6368     {
6369 	/*  EMSG(_("cmd_gchar beyond the command length")); */
6370 	return NUL;
6371     }
6372     return (int)ccline.cmdbuff[ccline.cmdpos + offset];
6373 }
6374 #endif
6375 
6376 #if defined(FEAT_CMDWIN) || defined(PROTO)
6377 /*
6378  * Open a window on the current command line and history.  Allow editing in
6379  * the window.  Returns when the window is closed.
6380  * Returns:
6381  *	CR	 if the command is to be executed
6382  *	Ctrl_C	 if it is to be abandoned
6383  *	K_IGNORE if editing continues
6384  */
6385     static int
6386 ex_window()
6387 {
6388     struct cmdline_info	save_ccline;
6389     buf_T		*old_curbuf = curbuf;
6390     win_T		*old_curwin = curwin;
6391     buf_T		*bp;
6392     win_T		*wp;
6393     int			i;
6394     linenr_T		lnum;
6395     int			histtype;
6396     garray_T		winsizes;
6397 #ifdef FEAT_AUTOCMD
6398     char_u		typestr[2];
6399 #endif
6400     int			save_restart_edit = restart_edit;
6401     int			save_State = State;
6402     int			save_exmode = exmode_active;
6403 #ifdef FEAT_RIGHTLEFT
6404     int			save_cmdmsg_rl = cmdmsg_rl;
6405 #endif
6406 #ifdef FEAT_FOLDING
6407     int			save_KeyTyped;
6408 #endif
6409 
6410     /* Can't do this recursively.  Can't do it when typing a password. */
6411     if (cmdwin_type != 0
6412 # if defined(FEAT_CRYPT) || defined(FEAT_EVAL)
6413 	    || cmdline_star > 0
6414 # endif
6415 	    )
6416     {
6417 	beep_flush();
6418 	return K_IGNORE;
6419     }
6420 
6421     /* Save current window sizes. */
6422     win_size_save(&winsizes);
6423 
6424 # ifdef FEAT_AUTOCMD
6425     /* Don't execute autocommands while creating the window. */
6426     block_autocmds();
6427 # endif
6428     /* don't use a new tab page */
6429     cmdmod.tab = 0;
6430 
6431     /* Create a window for the command-line buffer. */
6432     if (win_split((int)p_cwh, WSP_BOT) == FAIL)
6433     {
6434 	beep_flush();
6435 # ifdef FEAT_AUTOCMD
6436 	unblock_autocmds();
6437 # endif
6438 	return K_IGNORE;
6439     }
6440     cmdwin_type = get_cmdline_type();
6441 
6442     /* Create the command-line buffer empty. */
6443     (void)do_ecmd(0, NULL, NULL, NULL, ECMD_ONE, ECMD_HIDE, NULL);
6444     (void)setfname(curbuf, (char_u *)"[Command Line]", NULL, TRUE);
6445     set_option_value((char_u *)"bt", 0L, (char_u *)"nofile", OPT_LOCAL);
6446     set_option_value((char_u *)"swf", 0L, NULL, OPT_LOCAL);
6447     curbuf->b_p_ma = TRUE;
6448 #ifdef FEAT_FOLDING
6449     curwin->w_p_fen = FALSE;
6450 #endif
6451 # ifdef FEAT_RIGHTLEFT
6452     curwin->w_p_rl = cmdmsg_rl;
6453     cmdmsg_rl = FALSE;
6454 # endif
6455     RESET_BINDING(curwin);
6456 
6457 # ifdef FEAT_AUTOCMD
6458     /* Do execute autocommands for setting the filetype (load syntax). */
6459     unblock_autocmds();
6460 # endif
6461 
6462     /* Showing the prompt may have set need_wait_return, reset it. */
6463     need_wait_return = FALSE;
6464 
6465     histtype = hist_char2type(cmdwin_type);
6466     if (histtype == HIST_CMD || histtype == HIST_DEBUG)
6467     {
6468 	if (p_wc == TAB)
6469 	{
6470 	    add_map((char_u *)"<buffer> <Tab> <C-X><C-V>", INSERT);
6471 	    add_map((char_u *)"<buffer> <Tab> a<C-X><C-V>", NORMAL);
6472 	}
6473 	set_option_value((char_u *)"ft", 0L, (char_u *)"vim", OPT_LOCAL);
6474     }
6475 
6476     /* Reset 'textwidth' after setting 'filetype' (the Vim filetype plugin
6477      * sets 'textwidth' to 78). */
6478     curbuf->b_p_tw = 0;
6479 
6480     /* Fill the buffer with the history. */
6481     init_history();
6482     if (hislen > 0)
6483     {
6484 	i = hisidx[histtype];
6485 	if (i >= 0)
6486 	{
6487 	    lnum = 0;
6488 	    do
6489 	    {
6490 		if (++i == hislen)
6491 		    i = 0;
6492 		if (history[histtype][i].hisstr != NULL)
6493 		    ml_append(lnum++, history[histtype][i].hisstr,
6494 							   (colnr_T)0, FALSE);
6495 	    }
6496 	    while (i != hisidx[histtype]);
6497 	}
6498     }
6499 
6500     /* Replace the empty last line with the current command-line and put the
6501      * cursor there. */
6502     ml_replace(curbuf->b_ml.ml_line_count, ccline.cmdbuff, TRUE);
6503     curwin->w_cursor.lnum = curbuf->b_ml.ml_line_count;
6504     curwin->w_cursor.col = ccline.cmdpos;
6505     changed_line_abv_curs();
6506     invalidate_botline();
6507     redraw_later(SOME_VALID);
6508 
6509     /* Save the command line info, can be used recursively. */
6510     save_ccline = ccline;
6511     ccline.cmdbuff = NULL;
6512     ccline.cmdprompt = NULL;
6513 
6514     /* No Ex mode here! */
6515     exmode_active = 0;
6516 
6517     State = NORMAL;
6518 # ifdef FEAT_MOUSE
6519     setmouse();
6520 # endif
6521 
6522 # ifdef FEAT_AUTOCMD
6523     /* Trigger CmdwinEnter autocommands. */
6524     typestr[0] = cmdwin_type;
6525     typestr[1] = NUL;
6526     apply_autocmds(EVENT_CMDWINENTER, typestr, typestr, FALSE, curbuf);
6527     if (restart_edit != 0)	/* autocmd with ":startinsert" */
6528 	stuffcharReadbuff(K_NOP);
6529 # endif
6530 
6531     i = RedrawingDisabled;
6532     RedrawingDisabled = 0;
6533 
6534     /*
6535      * Call the main loop until <CR> or CTRL-C is typed.
6536      */
6537     cmdwin_result = 0;
6538     main_loop(TRUE, FALSE);
6539 
6540     RedrawingDisabled = i;
6541 
6542 # ifdef FEAT_AUTOCMD
6543 
6544 #  ifdef FEAT_FOLDING
6545     save_KeyTyped = KeyTyped;
6546 #  endif
6547 
6548     /* Trigger CmdwinLeave autocommands. */
6549     apply_autocmds(EVENT_CMDWINLEAVE, typestr, typestr, FALSE, curbuf);
6550 
6551 #  ifdef FEAT_FOLDING
6552     /* Restore KeyTyped in case it is modified by autocommands */
6553     KeyTyped = save_KeyTyped;
6554 #  endif
6555 
6556 # endif
6557 
6558     /* Restore the command line info. */
6559     ccline = save_ccline;
6560     cmdwin_type = 0;
6561 
6562     exmode_active = save_exmode;
6563 
6564     /* Safety check: The old window or buffer was deleted: It's a bug when
6565      * this happens! */
6566     if (!win_valid(old_curwin) || !buf_valid(old_curbuf))
6567     {
6568 	cmdwin_result = Ctrl_C;
6569 	EMSG(_("E199: Active window or buffer deleted"));
6570     }
6571     else
6572     {
6573 # if defined(FEAT_AUTOCMD) && defined(FEAT_EVAL)
6574 	/* autocmds may abort script processing */
6575 	if (aborting() && cmdwin_result != K_IGNORE)
6576 	    cmdwin_result = Ctrl_C;
6577 # endif
6578 	/* Set the new command line from the cmdline buffer. */
6579 	vim_free(ccline.cmdbuff);
6580 	if (cmdwin_result == K_XF1 || cmdwin_result == K_XF2) /* :qa[!] typed */
6581 	{
6582 	    char *p = (cmdwin_result == K_XF2) ? "qa" : "qa!";
6583 
6584 	    if (histtype == HIST_CMD)
6585 	    {
6586 		/* Execute the command directly. */
6587 		ccline.cmdbuff = vim_strsave((char_u *)p);
6588 		cmdwin_result = CAR;
6589 	    }
6590 	    else
6591 	    {
6592 		/* First need to cancel what we were doing. */
6593 		ccline.cmdbuff = NULL;
6594 		stuffcharReadbuff(':');
6595 		stuffReadbuff((char_u *)p);
6596 		stuffcharReadbuff(CAR);
6597 	    }
6598 	}
6599 	else if (cmdwin_result == K_XF2)	/* :qa typed */
6600 	{
6601 	    ccline.cmdbuff = vim_strsave((char_u *)"qa");
6602 	    cmdwin_result = CAR;
6603 	}
6604 	else if (cmdwin_result == Ctrl_C)
6605 	{
6606 	    /* :q or :close, don't execute any command
6607 	     * and don't modify the cmd window. */
6608 	    ccline.cmdbuff = NULL;
6609 	}
6610 	else
6611 	    ccline.cmdbuff = vim_strsave(ml_get_curline());
6612 	if (ccline.cmdbuff == NULL)
6613 	    cmdwin_result = Ctrl_C;
6614 	else
6615 	{
6616 	    ccline.cmdlen = (int)STRLEN(ccline.cmdbuff);
6617 	    ccline.cmdbufflen = ccline.cmdlen + 1;
6618 	    ccline.cmdpos = curwin->w_cursor.col;
6619 	    if (ccline.cmdpos > ccline.cmdlen)
6620 		ccline.cmdpos = ccline.cmdlen;
6621 	    if (cmdwin_result == K_IGNORE)
6622 	    {
6623 		set_cmdspos_cursor();
6624 		redrawcmd();
6625 	    }
6626 	}
6627 
6628 # ifdef FEAT_AUTOCMD
6629 	/* Don't execute autocommands while deleting the window. */
6630 	block_autocmds();
6631 # endif
6632 # ifdef FEAT_CONCEAL
6633 	/* Avoid command-line window first character being concealed. */
6634 	curwin->w_p_cole = 0;
6635 # endif
6636 	wp = curwin;
6637 	bp = curbuf;
6638 	win_goto(old_curwin);
6639 	win_close(wp, TRUE);
6640 
6641 	/* win_close() may have already wiped the buffer when 'bh' is
6642 	 * set to 'wipe' */
6643 	if (buf_valid(bp))
6644 	    close_buffer(NULL, bp, DOBUF_WIPE, FALSE);
6645 
6646 	/* Restore window sizes. */
6647 	win_size_restore(&winsizes);
6648 
6649 # ifdef FEAT_AUTOCMD
6650 	unblock_autocmds();
6651 # endif
6652     }
6653 
6654     ga_clear(&winsizes);
6655     restart_edit = save_restart_edit;
6656 # ifdef FEAT_RIGHTLEFT
6657     cmdmsg_rl = save_cmdmsg_rl;
6658 # endif
6659 
6660     State = save_State;
6661 # ifdef FEAT_MOUSE
6662     setmouse();
6663 # endif
6664 
6665     return cmdwin_result;
6666 }
6667 #endif /* FEAT_CMDWIN */
6668 
6669 /*
6670  * Used for commands that either take a simple command string argument, or:
6671  *	cmd << endmarker
6672  *	  {script}
6673  *	endmarker
6674  * Returns a pointer to allocated memory with {script} or NULL.
6675  */
6676     char_u *
6677 script_get(eap, cmd)
6678     exarg_T	*eap;
6679     char_u	*cmd;
6680 {
6681     char_u	*theline;
6682     char	*end_pattern = NULL;
6683     char	dot[] = ".";
6684     garray_T	ga;
6685 
6686     if (cmd[0] != '<' || cmd[1] != '<' || eap->getline == NULL)
6687 	return NULL;
6688 
6689     ga_init2(&ga, 1, 0x400);
6690 
6691     if (cmd[2] != NUL)
6692 	end_pattern = (char *)skipwhite(cmd + 2);
6693     else
6694 	end_pattern = dot;
6695 
6696     for (;;)
6697     {
6698 	theline = eap->getline(
6699 #ifdef FEAT_EVAL
6700 	    eap->cstack->cs_looplevel > 0 ? -1 :
6701 #endif
6702 	    NUL, eap->cookie, 0);
6703 
6704 	if (theline == NULL || STRCMP(end_pattern, theline) == 0)
6705 	{
6706 	    vim_free(theline);
6707 	    break;
6708 	}
6709 
6710 	ga_concat(&ga, theline);
6711 	ga_append(&ga, '\n');
6712 	vim_free(theline);
6713     }
6714     ga_append(&ga, NUL);
6715 
6716     return (char_u *)ga.ga_data;
6717 }
6718