1 /* vi:set ts=8 sts=4 sw=4 noet:
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 * ui.c: functions that handle the user interface.
12 * 1. Keyboard input stuff, and a bit of windowing stuff. These are called
13 * before the machine specific stuff (mch_*) so that we can call the GUI
14 * stuff instead if the GUI is running.
15 * 2. Input buffer stuff.
16 */
17
18 #include "vim.h"
19
20 void
ui_write(char_u * s,int len,int console UNUSED)21 ui_write(char_u *s, int len, int console UNUSED)
22 {
23 #ifdef FEAT_GUI
24 if (gui.in_use && !gui.dying && !gui.starting
25 # ifndef NO_CONSOLE
26 && !console
27 # endif
28 )
29 {
30 gui_write(s, len);
31 if (p_wd)
32 gui_wait_for_chars(p_wd, typebuf.tb_change_cnt);
33 return;
34 }
35 #endif
36 #ifndef NO_CONSOLE
37 // Don't output anything in silent mode ("ex -s") unless 'verbose' set
38 if (!(silent_mode && p_verbose == 0))
39 {
40 # if !defined(MSWIN)
41 char_u *tofree = NULL;
42
43 if (output_conv.vc_type != CONV_NONE)
44 {
45 // Convert characters from 'encoding' to 'termencoding'.
46 tofree = string_convert(&output_conv, s, &len);
47 if (tofree != NULL)
48 s = tofree;
49 }
50 # endif
51
52 mch_write(s, len);
53 # if defined(HAVE_FSYNC)
54 if (console && s[len - 1] == '\n')
55 vim_fsync(1);
56 # endif
57
58 # if !defined(MSWIN)
59 if (output_conv.vc_type != CONV_NONE)
60 vim_free(tofree);
61 # endif
62 }
63 #endif
64 }
65
66 #if defined(UNIX) || defined(VMS) || defined(PROTO) || defined(MSWIN)
67 /*
68 * When executing an external program, there may be some typed characters that
69 * are not consumed by it. Give them back to ui_inchar() and they are stored
70 * here for the next call.
71 */
72 static char_u *ta_str = NULL;
73 static int ta_off; // offset for next char to use when ta_str != NULL
74 static int ta_len; // length of ta_str when it's not NULL
75
76 void
ui_inchar_undo(char_u * s,int len)77 ui_inchar_undo(char_u *s, int len)
78 {
79 char_u *new;
80 int newlen;
81
82 newlen = len;
83 if (ta_str != NULL)
84 newlen += ta_len - ta_off;
85 new = alloc(newlen);
86 if (new != NULL)
87 {
88 if (ta_str != NULL)
89 {
90 mch_memmove(new, ta_str + ta_off, (size_t)(ta_len - ta_off));
91 mch_memmove(new + ta_len - ta_off, s, (size_t)len);
92 vim_free(ta_str);
93 }
94 else
95 mch_memmove(new, s, (size_t)len);
96 ta_str = new;
97 ta_len = newlen;
98 ta_off = 0;
99 }
100 }
101 #endif
102
103 /*
104 * ui_inchar(): low level input function.
105 * Get characters from the keyboard.
106 * Return the number of characters that are available.
107 * If "wtime" == 0 do not wait for characters.
108 * If "wtime" == -1 wait forever for characters.
109 * If "wtime" > 0 wait "wtime" milliseconds for a character.
110 *
111 * "tb_change_cnt" is the value of typebuf.tb_change_cnt if "buf" points into
112 * it. When typebuf.tb_change_cnt changes (e.g., when a message is received
113 * from a remote client) "buf" can no longer be used. "tb_change_cnt" is NULL
114 * otherwise.
115 */
116 int
ui_inchar(char_u * buf,int maxlen,long wtime,int tb_change_cnt)117 ui_inchar(
118 char_u *buf,
119 int maxlen,
120 long wtime, // don't use "time", MIPS cannot handle it
121 int tb_change_cnt)
122 {
123 int retval = 0;
124
125 #if defined(FEAT_GUI) && (defined(UNIX) || defined(VMS))
126 /*
127 * Use the typeahead if there is any.
128 */
129 if (ta_str != NULL)
130 {
131 if (maxlen >= ta_len - ta_off)
132 {
133 mch_memmove(buf, ta_str + ta_off, (size_t)ta_len);
134 VIM_CLEAR(ta_str);
135 return ta_len;
136 }
137 mch_memmove(buf, ta_str + ta_off, (size_t)maxlen);
138 ta_off += maxlen;
139 return maxlen;
140 }
141 #endif
142
143 #ifdef FEAT_PROFILE
144 if (do_profiling == PROF_YES && wtime != 0)
145 prof_inchar_enter();
146 #endif
147
148 #ifdef NO_CONSOLE_INPUT
149 // Don't wait for character input when the window hasn't been opened yet.
150 // Do try reading, this works when redirecting stdin from a file.
151 // Must return something, otherwise we'll loop forever. If we run into
152 // this very often we probably got stuck, exit Vim.
153 if (no_console_input())
154 {
155 static int count = 0;
156
157 # ifndef NO_CONSOLE
158 retval = mch_inchar(buf, maxlen, wtime, tb_change_cnt);
159 if (retval > 0 || typebuf_changed(tb_change_cnt) || wtime >= 0)
160 goto theend;
161 # endif
162 if (wtime == -1 && ++count == 1000)
163 read_error_exit();
164 buf[0] = CAR;
165 retval = 1;
166 goto theend;
167 }
168 #endif
169
170 // If we are going to wait for some time or block...
171 if (wtime == -1 || wtime > 100L)
172 {
173 // ... allow signals to kill us.
174 (void)vim_handle_signal(SIGNAL_UNBLOCK);
175
176 // ... there is no need for CTRL-C to interrupt something, don't let
177 // it set got_int when it was mapped.
178 if ((mapped_ctrl_c | curbuf->b_mapped_ctrl_c) & get_real_state())
179 ctrl_c_interrupts = FALSE;
180 }
181
182 /*
183 * Here we call gui_inchar() or mch_inchar(), the GUI or machine-dependent
184 * input function. The functionality they implement is like this:
185 *
186 * while (not timed out)
187 * {
188 * handle-resize;
189 * parse-queued-messages;
190 * if (waited for 'updatetime')
191 * trigger-cursorhold;
192 * ui_wait_for_chars_or_timer()
193 * if (character available)
194 * break;
195 * }
196 *
197 * ui_wait_for_chars_or_timer() does:
198 *
199 * while (not timed out)
200 * {
201 * if (any-timer-triggered)
202 * invoke-timer-callback;
203 * wait-for-character();
204 * if (character available)
205 * break;
206 * }
207 *
208 * wait-for-character() does:
209 * while (not timed out)
210 * {
211 * Wait for event;
212 * if (something on channel)
213 * read/write channel;
214 * else if (resized)
215 * handle_resize();
216 * else if (system event)
217 * deal-with-system-event;
218 * else if (character available)
219 * break;
220 * }
221 *
222 */
223
224 #ifdef FEAT_GUI
225 if (gui.in_use)
226 retval = gui_inchar(buf, maxlen, wtime, tb_change_cnt);
227 #endif
228 #ifndef NO_CONSOLE
229 # ifdef FEAT_GUI
230 else
231 # endif
232 retval = mch_inchar(buf, maxlen, wtime, tb_change_cnt);
233 #endif
234
235 if (wtime == -1 || wtime > 100L)
236 // block SIGHUP et al.
237 (void)vim_handle_signal(SIGNAL_BLOCK);
238
239 ctrl_c_interrupts = TRUE;
240
241 #ifdef NO_CONSOLE_INPUT
242 theend:
243 #endif
244 #ifdef FEAT_PROFILE
245 if (do_profiling == PROF_YES && wtime != 0)
246 prof_inchar_exit();
247 #endif
248 return retval;
249 }
250
251 #if defined(UNIX) || defined(VMS) || defined(FEAT_GUI) || defined(PROTO)
252 /*
253 * Common code for mch_inchar() and gui_inchar(): Wait for a while or
254 * indefinitely until characters are available, dealing with timers and
255 * messages on channels.
256 *
257 * "buf" may be NULL if the available characters are not to be returned, only
258 * check if they are available.
259 *
260 * Return the number of characters that are available.
261 * If "wtime" == 0 do not wait for characters.
262 * If "wtime" == n wait a short time for characters.
263 * If "wtime" == -1 wait forever for characters.
264 */
265 int
inchar_loop(char_u * buf,int maxlen,long wtime,int tb_change_cnt,int (* wait_func)(long wtime,int * interrupted,int ignore_input),int (* resize_func)(int check_only))266 inchar_loop(
267 char_u *buf,
268 int maxlen,
269 long wtime, // don't use "time", MIPS cannot handle it
270 int tb_change_cnt,
271 int (*wait_func)(long wtime, int *interrupted, int ignore_input),
272 int (*resize_func)(int check_only))
273 {
274 int len;
275 int interrupted = FALSE;
276 int did_call_wait_func = FALSE;
277 int did_start_blocking = FALSE;
278 long wait_time;
279 long elapsed_time = 0;
280 #ifdef ELAPSED_FUNC
281 elapsed_T start_tv;
282
283 ELAPSED_INIT(start_tv);
284 #endif
285
286 // repeat until we got a character or waited long enough
287 for (;;)
288 {
289 // Check if window changed size while we were busy, perhaps the ":set
290 // columns=99" command was used.
291 if (resize_func != NULL)
292 resize_func(FALSE);
293
294 #ifdef MESSAGE_QUEUE
295 // Only process messages when waiting.
296 if (wtime != 0)
297 {
298 parse_queued_messages();
299 // If input was put directly in typeahead buffer bail out here.
300 if (typebuf_changed(tb_change_cnt))
301 return 0;
302 }
303 #endif
304 if (wtime < 0 && did_start_blocking)
305 // blocking and already waited for p_ut
306 wait_time = -1;
307 else
308 {
309 if (wtime >= 0)
310 wait_time = wtime;
311 else
312 // going to block after p_ut
313 wait_time = p_ut;
314 #ifdef ELAPSED_FUNC
315 elapsed_time = ELAPSED_FUNC(start_tv);
316 #endif
317 wait_time -= elapsed_time;
318
319 // If the waiting time is now zero or less, we timed out. However,
320 // loop at least once to check for characters and events. Matters
321 // when "wtime" is zero.
322 if (wait_time <= 0 && did_call_wait_func)
323 {
324 if (wtime >= 0)
325 // no character available within "wtime"
326 return 0;
327
328 // No character available within 'updatetime'.
329 did_start_blocking = TRUE;
330 if (trigger_cursorhold() && maxlen >= 3
331 && !typebuf_changed(tb_change_cnt))
332 {
333 // Put K_CURSORHOLD in the input buffer or return it.
334 if (buf == NULL)
335 {
336 char_u ibuf[3];
337
338 ibuf[0] = CSI;
339 ibuf[1] = KS_EXTRA;
340 ibuf[2] = (int)KE_CURSORHOLD;
341 add_to_input_buf(ibuf, 3);
342 }
343 else
344 {
345 buf[0] = K_SPECIAL;
346 buf[1] = KS_EXTRA;
347 buf[2] = (int)KE_CURSORHOLD;
348 }
349 return 3;
350 }
351
352 // There is no character available within 'updatetime' seconds:
353 // flush all the swap files to disk. Also done when
354 // interrupted by SIGWINCH.
355 before_blocking();
356 continue;
357 }
358 }
359
360 #ifdef FEAT_JOB_CHANNEL
361 if (wait_time < 0 || wait_time > 100L)
362 {
363 // Checking if a job ended requires polling. Do this at least
364 // every 100 msec.
365 if (has_pending_job())
366 wait_time = 100L;
367
368 // If there is readahead then parse_queued_messages() timed out and
369 // we should call it again soon.
370 if (channel_any_readahead())
371 wait_time = 10L;
372 }
373 #endif
374 #ifdef FEAT_BEVAL_GUI
375 if (p_beval && wait_time > 100L)
376 // The 'balloonexpr' may indirectly invoke a callback while waiting
377 // for a character, need to check often.
378 wait_time = 100L;
379 #endif
380
381 // Wait for a character to be typed or another event, such as the winch
382 // signal or an event on the monitored file descriptors.
383 did_call_wait_func = TRUE;
384 if (wait_func(wait_time, &interrupted, FALSE))
385 {
386 // If input was put directly in typeahead buffer bail out here.
387 if (typebuf_changed(tb_change_cnt))
388 return 0;
389
390 // We might have something to return now.
391 if (buf == NULL)
392 // "buf" is NULL, we were just waiting, not actually getting
393 // input.
394 return input_available();
395
396 len = read_from_input_buf(buf, (long)maxlen);
397 if (len > 0)
398 return len;
399 continue;
400 }
401 // Timed out or interrupted with no character available.
402
403 #ifndef ELAPSED_FUNC
404 // estimate the elapsed time
405 elapsed_time += wait_time;
406 #endif
407
408 if ((resize_func != NULL && resize_func(TRUE))
409 #if defined(FEAT_CLIENTSERVER) && defined(UNIX)
410 || server_waiting()
411 #endif
412 #ifdef MESSAGE_QUEUE
413 || interrupted
414 #endif
415 || wait_time > 0
416 || (wtime < 0 && !did_start_blocking))
417 // no character available, but something to be done, keep going
418 continue;
419
420 // no character available or interrupted, return zero
421 break;
422 }
423 return 0;
424 }
425 #endif
426
427 #if defined(FEAT_TIMERS) || defined(PROTO)
428 /*
429 * Wait for a timer to fire or "wait_func" to return non-zero.
430 * Returns OK when something was read.
431 * Returns FAIL when it timed out or was interrupted.
432 */
433 int
ui_wait_for_chars_or_timer(long wtime,int (* wait_func)(long wtime,int * interrupted,int ignore_input),int * interrupted,int ignore_input)434 ui_wait_for_chars_or_timer(
435 long wtime,
436 int (*wait_func)(long wtime, int *interrupted, int ignore_input),
437 int *interrupted,
438 int ignore_input)
439 {
440 int due_time;
441 long remaining = wtime;
442 int tb_change_cnt = typebuf.tb_change_cnt;
443 # ifdef FEAT_JOB_CHANNEL
444 int brief_wait = FALSE;
445 # endif
446
447 // When waiting very briefly don't trigger timers.
448 if (wtime >= 0 && wtime < 10L)
449 return wait_func(wtime, NULL, ignore_input);
450
451 while (wtime < 0 || remaining > 0)
452 {
453 // Trigger timers and then get the time in wtime until the next one is
454 // due. Wait up to that time.
455 due_time = check_due_timer();
456 if (typebuf.tb_change_cnt != tb_change_cnt)
457 {
458 // timer may have used feedkeys()
459 return FAIL;
460 }
461 if (due_time <= 0 || (wtime > 0 && due_time > remaining))
462 due_time = remaining;
463 # if defined(FEAT_JOB_CHANNEL) || defined(FEAT_SOUND_CANBERRA)
464 if ((due_time < 0 || due_time > 10L) && (
465 # if defined(FEAT_JOB_CHANNEL)
466 (
467 # if defined(FEAT_GUI)
468 !gui.in_use &&
469 # endif
470 (has_pending_job() || channel_any_readahead()))
471 # ifdef FEAT_SOUND_CANBERRA
472 ||
473 # endif
474 # endif
475 # ifdef FEAT_SOUND_CANBERRA
476 has_any_sound_callback()
477 # endif
478 ))
479 {
480 // There is a pending job or channel, should return soon in order
481 // to handle them ASAP. Do check for input briefly.
482 due_time = 10L;
483 # ifdef FEAT_JOB_CHANNEL
484 brief_wait = TRUE;
485 # endif
486 }
487 # endif
488 if (wait_func(due_time, interrupted, ignore_input))
489 return OK;
490 if ((interrupted != NULL && *interrupted)
491 # ifdef FEAT_JOB_CHANNEL
492 || brief_wait
493 # endif
494 )
495 // Nothing available, but need to return so that side effects get
496 // handled, such as handling a message on a channel.
497 return FAIL;
498 if (wtime > 0)
499 remaining -= due_time;
500 }
501 return FAIL;
502 }
503 #endif
504
505 /*
506 * Return non-zero if a character is available.
507 */
508 int
ui_char_avail(void)509 ui_char_avail(void)
510 {
511 #ifdef FEAT_GUI
512 if (gui.in_use)
513 {
514 gui_mch_update();
515 return input_available();
516 }
517 #endif
518 #ifndef NO_CONSOLE
519 # ifdef NO_CONSOLE_INPUT
520 if (no_console_input())
521 return 0;
522 # endif
523 return mch_char_avail();
524 #else
525 return 0;
526 #endif
527 }
528
529 /*
530 * Delay for the given number of milliseconds. If ignoreinput is FALSE then we
531 * cancel the delay if a key is hit.
532 */
533 void
ui_delay(long msec_arg,int ignoreinput)534 ui_delay(long msec_arg, int ignoreinput)
535 {
536 long msec = msec_arg;
537
538 #ifdef FEAT_EVAL
539 if (ui_delay_for_testing > 0)
540 msec = ui_delay_for_testing;
541 #endif
542 #ifdef FEAT_JOB_CHANNEL
543 ch_log(NULL, "ui_delay(%ld)", msec);
544 #endif
545 #ifdef FEAT_GUI
546 if (gui.in_use && !ignoreinput)
547 gui_wait_for_chars(msec, typebuf.tb_change_cnt);
548 else
549 #endif
550 mch_delay(msec, ignoreinput ? MCH_DELAY_IGNOREINPUT : 0);
551 }
552
553 /*
554 * If the machine has job control, use it to suspend the program,
555 * otherwise fake it by starting a new shell.
556 * When running the GUI iconify the window.
557 */
558 void
ui_suspend(void)559 ui_suspend(void)
560 {
561 #ifdef FEAT_GUI
562 if (gui.in_use)
563 {
564 gui_mch_iconify();
565 return;
566 }
567 #endif
568 mch_suspend();
569 }
570
571 #if !defined(UNIX) || !defined(SIGTSTP) || defined(PROTO)
572 /*
573 * When the OS can't really suspend, call this function to start a shell.
574 * This is never called in the GUI.
575 */
576 void
suspend_shell(void)577 suspend_shell(void)
578 {
579 if (*p_sh == NUL)
580 emsg(_(e_shellempty));
581 else
582 {
583 msg_puts(_("new shell started\n"));
584 do_shell(NULL, 0);
585 }
586 }
587 #endif
588
589 /*
590 * Try to get the current Vim shell size. Put the result in Rows and Columns.
591 * Use the new sizes as defaults for 'columns' and 'lines'.
592 * Return OK when size could be determined, FAIL otherwise.
593 */
594 int
ui_get_shellsize(void)595 ui_get_shellsize(void)
596 {
597 int retval;
598
599 #ifdef FEAT_GUI
600 if (gui.in_use)
601 retval = gui_get_shellsize();
602 else
603 #endif
604 retval = mch_get_shellsize();
605
606 check_shellsize();
607
608 // adjust the default for 'lines' and 'columns'
609 if (retval == OK)
610 {
611 set_number_default("lines", Rows);
612 set_number_default("columns", Columns);
613 }
614 return retval;
615 }
616
617 /*
618 * Set the size of the Vim shell according to Rows and Columns, if possible.
619 * The gui_set_shellsize() or mch_set_shellsize() function will try to set the
620 * new size. If this is not possible, it will adjust Rows and Columns.
621 */
622 void
ui_set_shellsize(int mustset UNUSED)623 ui_set_shellsize(
624 int mustset UNUSED) // set by the user
625 {
626 #ifdef FEAT_GUI
627 if (gui.in_use)
628 gui_set_shellsize(mustset, TRUE, RESIZE_BOTH);
629 else
630 #endif
631 mch_set_shellsize();
632 }
633
634 /*
635 * Called when Rows and/or Columns changed. Adjust scroll region and mouse
636 * region.
637 */
638 void
ui_new_shellsize(void)639 ui_new_shellsize(void)
640 {
641 if (full_screen && !exiting)
642 {
643 #ifdef FEAT_GUI
644 if (gui.in_use)
645 gui_new_shellsize();
646 else
647 #endif
648 mch_new_shellsize();
649 }
650 }
651
652 #if ((defined(FEAT_EVAL) || defined(FEAT_TERMINAL)) \
653 && (defined(FEAT_GUI) \
654 || defined(MSWIN) \
655 || (defined(HAVE_TGETENT) && defined(FEAT_TERMRESPONSE)))) \
656 || defined(PROTO)
657 /*
658 * Get the window position in pixels, if possible.
659 * Return FAIL when not possible.
660 */
661 int
ui_get_winpos(int * x,int * y,varnumber_T timeout UNUSED)662 ui_get_winpos(int *x, int *y, varnumber_T timeout UNUSED)
663 {
664 # ifdef FEAT_GUI
665 if (gui.in_use)
666 return gui_mch_get_winpos(x, y);
667 # endif
668 # if defined(MSWIN) && (!defined(FEAT_GUI) || defined(VIMDLL))
669 return mch_get_winpos(x, y);
670 # else
671 # if defined(HAVE_TGETENT) && defined(FEAT_TERMRESPONSE)
672 return term_get_winpos(x, y, timeout);
673 # else
674 return FAIL;
675 # endif
676 # endif
677 }
678 #endif
679
680 void
ui_breakcheck(void)681 ui_breakcheck(void)
682 {
683 ui_breakcheck_force(FALSE);
684 }
685
686 /*
687 * When "force" is true also check when the terminal is not in raw mode.
688 * This is useful to read input on channels.
689 */
690 void
ui_breakcheck_force(int force)691 ui_breakcheck_force(int force)
692 {
693 static int recursive = FALSE;
694 int save_updating_screen = updating_screen;
695
696 // We could be called recursively if stderr is redirected, calling
697 // fill_input_buf() calls settmode() when stdin isn't a tty. settmode()
698 // calls vgetorpeek() which calls ui_breakcheck() again.
699 if (recursive)
700 return;
701 recursive = TRUE;
702
703 // We do not want gui_resize_shell() to redraw the screen here.
704 ++updating_screen;
705
706 #ifdef FEAT_GUI
707 if (gui.in_use)
708 gui_mch_update();
709 else
710 #endif
711 mch_breakcheck(force);
712
713 if (save_updating_screen)
714 updating_screen = TRUE;
715 else
716 after_updating_screen(FALSE);
717
718 recursive = FALSE;
719 }
720
721 //////////////////////////////////////////////////////////////////////////////
722 // Functions that handle the input buffer.
723 // This is used for any GUI version, and the unix terminal version.
724 //
725 // For Unix, the input characters are buffered to be able to check for a
726 // CTRL-C. This should be done with signals, but I don't know how to do that
727 // in a portable way for a tty in RAW mode.
728 //
729 // For the client-server code in the console the received keys are put in the
730 // input buffer.
731
732 #if defined(USE_INPUT_BUF) || defined(PROTO)
733
734 /*
735 * Internal typeahead buffer. Includes extra space for long key code
736 * descriptions which would otherwise overflow. The buffer is considered full
737 * when only this extra space (or part of it) remains.
738 */
739 #if defined(FEAT_JOB_CHANNEL) || defined(FEAT_CLIENTSERVER)
740 /*
741 * NetBeans stuffs debugger commands into the input buffer.
742 * This requires a larger buffer...
743 * (Madsen) Go with this for remote input as well ...
744 */
745 # define INBUFLEN 4096
746 #else
747 # define INBUFLEN 250
748 #endif
749
750 static char_u inbuf[INBUFLEN + MAX_KEY_CODE_LEN];
751 static int inbufcount = 0; // number of chars in inbuf[]
752
753 /*
754 * vim_is_input_buf_full(), vim_is_input_buf_empty(), add_to_input_buf(), and
755 * trash_input_buf() are functions for manipulating the input buffer. These
756 * are used by the gui_* calls when a GUI is used to handle keyboard input.
757 */
758
759 int
vim_is_input_buf_full(void)760 vim_is_input_buf_full(void)
761 {
762 return (inbufcount >= INBUFLEN);
763 }
764
765 int
vim_is_input_buf_empty(void)766 vim_is_input_buf_empty(void)
767 {
768 return (inbufcount == 0);
769 }
770
771 #if defined(FEAT_OLE) || defined(PROTO)
772 int
vim_free_in_input_buf(void)773 vim_free_in_input_buf(void)
774 {
775 return (INBUFLEN - inbufcount);
776 }
777 #endif
778
779 #if defined(FEAT_GUI_GTK) || defined(PROTO)
780 int
vim_used_in_input_buf(void)781 vim_used_in_input_buf(void)
782 {
783 return inbufcount;
784 }
785 #endif
786
787 /*
788 * Return the current contents of the input buffer and make it empty.
789 * The returned pointer must be passed to set_input_buf() later.
790 */
791 char_u *
get_input_buf(void)792 get_input_buf(void)
793 {
794 garray_T *gap;
795
796 // We use a growarray to store the data pointer and the length.
797 gap = ALLOC_ONE(garray_T);
798 if (gap != NULL)
799 {
800 // Add one to avoid a zero size.
801 gap->ga_data = alloc(inbufcount + 1);
802 if (gap->ga_data != NULL)
803 mch_memmove(gap->ga_data, inbuf, (size_t)inbufcount);
804 gap->ga_len = inbufcount;
805 }
806 trash_input_buf();
807 return (char_u *)gap;
808 }
809
810 /*
811 * Restore the input buffer with a pointer returned from get_input_buf().
812 * The allocated memory is freed, this only works once!
813 * When "overwrite" is FALSE input typed later is kept.
814 */
815 void
set_input_buf(char_u * p,int overwrite)816 set_input_buf(char_u *p, int overwrite)
817 {
818 garray_T *gap = (garray_T *)p;
819
820 if (gap != NULL)
821 {
822 if (gap->ga_data != NULL)
823 {
824 if (overwrite || inbufcount + gap->ga_len >= INBUFLEN)
825 {
826 mch_memmove(inbuf, gap->ga_data, gap->ga_len);
827 inbufcount = gap->ga_len;
828 }
829 else
830 {
831 mch_memmove(inbuf + gap->ga_len, inbuf, inbufcount);
832 mch_memmove(inbuf, gap->ga_data, gap->ga_len);
833 inbufcount += gap->ga_len;
834 }
835 vim_free(gap->ga_data);
836 }
837 vim_free(gap);
838 }
839 }
840
841 /*
842 * Add the given bytes to the input buffer
843 * Special keys start with CSI. A real CSI must have been translated to
844 * CSI KS_EXTRA KE_CSI. K_SPECIAL doesn't require translation.
845 */
846 void
add_to_input_buf(char_u * s,int len)847 add_to_input_buf(char_u *s, int len)
848 {
849 if (inbufcount + len > INBUFLEN + MAX_KEY_CODE_LEN)
850 return; // Shouldn't ever happen!
851
852 while (len--)
853 inbuf[inbufcount++] = *s++;
854 }
855
856 /*
857 * Add "str[len]" to the input buffer while escaping CSI bytes.
858 */
859 void
add_to_input_buf_csi(char_u * str,int len)860 add_to_input_buf_csi(char_u *str, int len)
861 {
862 int i;
863 char_u buf[2];
864
865 for (i = 0; i < len; ++i)
866 {
867 add_to_input_buf(str + i, 1);
868 if (str[i] == CSI)
869 {
870 // Turn CSI into K_CSI.
871 buf[0] = KS_EXTRA;
872 buf[1] = (int)KE_CSI;
873 add_to_input_buf(buf, 2);
874 }
875 }
876 }
877
878 /*
879 * Remove everything from the input buffer. Called when ^C is found.
880 */
881 void
trash_input_buf(void)882 trash_input_buf(void)
883 {
884 inbufcount = 0;
885 }
886
887 /*
888 * Read as much data from the input buffer as possible up to maxlen, and store
889 * it in buf.
890 */
891 int
read_from_input_buf(char_u * buf,long maxlen)892 read_from_input_buf(char_u *buf, long maxlen)
893 {
894 if (inbufcount == 0) // if the buffer is empty, fill it
895 fill_input_buf(TRUE);
896 if (maxlen > inbufcount)
897 maxlen = inbufcount;
898 mch_memmove(buf, inbuf, (size_t)maxlen);
899 inbufcount -= maxlen;
900 if (inbufcount)
901 mch_memmove(inbuf, inbuf + maxlen, (size_t)inbufcount);
902 return (int)maxlen;
903 }
904
905 void
fill_input_buf(int exit_on_error UNUSED)906 fill_input_buf(int exit_on_error UNUSED)
907 {
908 #if defined(UNIX) || defined(VMS) || defined(MACOS_X)
909 int len;
910 int try;
911 static int did_read_something = FALSE;
912 static char_u *rest = NULL; // unconverted rest of previous read
913 static int restlen = 0;
914 int unconverted;
915 #endif
916
917 #ifdef FEAT_GUI
918 if (gui.in_use
919 # ifdef NO_CONSOLE_INPUT
920 // Don't use the GUI input when the window hasn't been opened yet.
921 // We get here from ui_inchar() when we should try reading from stdin.
922 && !no_console_input()
923 # endif
924 )
925 {
926 gui_mch_update();
927 return;
928 }
929 #endif
930 #if defined(UNIX) || defined(VMS) || defined(MACOS_X)
931 if (vim_is_input_buf_full())
932 return;
933 /*
934 * Fill_input_buf() is only called when we really need a character.
935 * If we can't get any, but there is some in the buffer, just return.
936 * If we can't get any, and there isn't any in the buffer, we give up and
937 * exit Vim.
938 */
939 if (rest != NULL)
940 {
941 // Use remainder of previous call, starts with an invalid character
942 // that may become valid when reading more.
943 if (restlen > INBUFLEN - inbufcount)
944 unconverted = INBUFLEN - inbufcount;
945 else
946 unconverted = restlen;
947 mch_memmove(inbuf + inbufcount, rest, unconverted);
948 if (unconverted == restlen)
949 VIM_CLEAR(rest);
950 else
951 {
952 restlen -= unconverted;
953 mch_memmove(rest, rest + unconverted, restlen);
954 }
955 inbufcount += unconverted;
956 }
957 else
958 unconverted = 0;
959
960 len = 0; // to avoid gcc warning
961 for (try = 0; try < 100; ++try)
962 {
963 size_t readlen = (size_t)((INBUFLEN - inbufcount)
964 / input_conv.vc_factor);
965 # ifdef VMS
966 len = vms_read((char *)inbuf + inbufcount, readlen);
967 # else
968 len = read(read_cmd_fd, (char *)inbuf + inbufcount, readlen);
969 # endif
970 # ifdef FEAT_JOB_CHANNEL
971 if (len > 0)
972 {
973 inbuf[inbufcount + len] = NUL;
974 ch_log(NULL, "raw key input: \"%s\"", inbuf + inbufcount);
975 }
976 # endif
977
978 if (len > 0 || got_int)
979 break;
980 /*
981 * If reading stdin results in an error, continue reading stderr.
982 * This helps when using "foo | xargs vim".
983 */
984 if (!did_read_something && !isatty(read_cmd_fd) && read_cmd_fd == 0)
985 {
986 int m = cur_tmode;
987
988 // We probably set the wrong file descriptor to raw mode. Switch
989 // back to cooked mode, use another descriptor and set the mode to
990 // what it was.
991 settmode(TMODE_COOK);
992 #ifdef HAVE_DUP
993 // Use stderr for stdin, also works for shell commands.
994 close(0);
995 vim_ignored = dup(2);
996 #else
997 read_cmd_fd = 2; // read from stderr instead of stdin
998 #endif
999 settmode(m);
1000 }
1001 if (!exit_on_error)
1002 return;
1003 }
1004 if (len <= 0 && !got_int)
1005 read_error_exit();
1006 if (len > 0)
1007 did_read_something = TRUE;
1008 if (got_int)
1009 {
1010 // Interrupted, pretend a CTRL-C was typed.
1011 inbuf[0] = 3;
1012 inbufcount = 1;
1013 }
1014 else
1015 {
1016 /*
1017 * May perform conversion on the input characters.
1018 * Include the unconverted rest of the previous call.
1019 * If there is an incomplete char at the end it is kept for the next
1020 * time, reading more bytes should make conversion possible.
1021 * Don't do this in the unlikely event that the input buffer is too
1022 * small ("rest" still contains more bytes).
1023 */
1024 if (input_conv.vc_type != CONV_NONE)
1025 {
1026 inbufcount -= unconverted;
1027 len = convert_input_safe(inbuf + inbufcount,
1028 len + unconverted, INBUFLEN - inbufcount,
1029 rest == NULL ? &rest : NULL, &restlen);
1030 }
1031 while (len-- > 0)
1032 {
1033 // If a CTRL-C was typed, remove it from the buffer and set
1034 // got_int. Also recognize CTRL-C with modifyOtherKeys set, in two
1035 // forms.
1036 if (ctrl_c_interrupts && (inbuf[inbufcount] == 3
1037 || (len >= 10 && STRNCMP(inbuf + inbufcount,
1038 "\033[27;5;99~", 10) == 0)
1039 || (len >= 7 && STRNCMP(inbuf + inbufcount,
1040 "\033[99;5u", 7) == 0)))
1041 {
1042 // remove everything typed before the CTRL-C
1043 mch_memmove(inbuf, inbuf + inbufcount, (size_t)(len + 1));
1044 inbufcount = 0;
1045 got_int = TRUE;
1046 }
1047 ++inbufcount;
1048 }
1049 }
1050 #endif // UNIX || VMS || MACOS_X
1051 }
1052 #endif // USE_INPUT_BUF
1053
1054 /*
1055 * Exit because of an input read error.
1056 */
1057 void
read_error_exit(void)1058 read_error_exit(void)
1059 {
1060 if (silent_mode) // Normal way to exit for "ex -s"
1061 getout(0);
1062 STRCPY(IObuff, _("Vim: Error reading input, exiting...\n"));
1063 preserve_exit();
1064 }
1065
1066 #if defined(CURSOR_SHAPE) || defined(PROTO)
1067 /*
1068 * May update the shape of the cursor.
1069 */
1070 void
ui_cursor_shape_forced(int forced)1071 ui_cursor_shape_forced(int forced)
1072 {
1073 # ifdef FEAT_GUI
1074 if (gui.in_use)
1075 gui_update_cursor_later();
1076 else
1077 # endif
1078 term_cursor_mode(forced);
1079
1080 # ifdef MCH_CURSOR_SHAPE
1081 mch_update_cursor();
1082 # endif
1083
1084 # ifdef FEAT_CONCEAL
1085 conceal_check_cursor_line(FALSE);
1086 # endif
1087 }
1088
1089 void
ui_cursor_shape(void)1090 ui_cursor_shape(void)
1091 {
1092 ui_cursor_shape_forced(FALSE);
1093 }
1094 #endif
1095
1096 /*
1097 * Check bounds for column number
1098 */
1099 int
check_col(int col)1100 check_col(int col)
1101 {
1102 if (col < 0)
1103 return 0;
1104 if (col >= (int)screen_Columns)
1105 return (int)screen_Columns - 1;
1106 return col;
1107 }
1108
1109 /*
1110 * Check bounds for row number
1111 */
1112 int
check_row(int row)1113 check_row(int row)
1114 {
1115 if (row < 0)
1116 return 0;
1117 if (row >= (int)screen_Rows)
1118 return (int)screen_Rows - 1;
1119 return row;
1120 }
1121
1122 /*
1123 * Called when focus changed. Used for the GUI or for systems where this can
1124 * be done in the console (Win32).
1125 */
1126 void
ui_focus_change(int in_focus)1127 ui_focus_change(
1128 int in_focus) // TRUE if focus gained.
1129 {
1130 static time_t last_time = (time_t)0;
1131 int need_redraw = FALSE;
1132
1133 // When activated: Check if any file was modified outside of Vim.
1134 // Only do this when not done within the last two seconds (could get
1135 // several events in a row).
1136 if (in_focus && last_time + 2 < time(NULL))
1137 {
1138 need_redraw = check_timestamps(
1139 # ifdef FEAT_GUI
1140 gui.in_use
1141 # else
1142 FALSE
1143 # endif
1144 );
1145 last_time = time(NULL);
1146 }
1147
1148 /*
1149 * Fire the focus gained/lost autocommand.
1150 */
1151 need_redraw |= apply_autocmds(in_focus ? EVENT_FOCUSGAINED
1152 : EVENT_FOCUSLOST, NULL, NULL, FALSE, curbuf);
1153
1154 if (need_redraw)
1155 {
1156 // Something was executed, make sure the cursor is put back where it
1157 // belongs.
1158 need_wait_return = FALSE;
1159
1160 if (State & CMDLINE)
1161 redrawcmdline();
1162 else if (State == HITRETURN || State == SETWSIZE || State == ASKMORE
1163 || State == EXTERNCMD || State == CONFIRM || exmode_active)
1164 repeat_message();
1165 else if ((State & NORMAL) || (State & INSERT))
1166 {
1167 if (must_redraw != 0)
1168 update_screen(0);
1169 setcursor();
1170 }
1171 cursor_on(); // redrawing may have switched it off
1172 out_flush_cursor(FALSE, TRUE);
1173 # ifdef FEAT_GUI
1174 if (gui.in_use)
1175 gui_update_scrollbars(FALSE);
1176 # endif
1177 }
1178
1179 // File may have been changed from 'readonly' to 'noreadonly'
1180 if (need_maketitle)
1181 maketitle();
1182 }
1183
1184 #if defined(HAVE_INPUT_METHOD) || defined(PROTO)
1185 /*
1186 * Save current Input Method status to specified place.
1187 */
1188 void
im_save_status(long * psave)1189 im_save_status(long *psave)
1190 {
1191 // Don't save when 'imdisable' is set or "xic" is NULL, IM is always
1192 // disabled then (but might start later).
1193 // Also don't save when inside a mapping, vgetc_im_active has not been set
1194 // then.
1195 // And don't save when the keys were stuffed (e.g., for a "." command).
1196 // And don't save when the GUI is running but our window doesn't have
1197 // input focus (e.g., when a find dialog is open).
1198 if (!p_imdisable && KeyTyped && !KeyStuffed
1199 # ifdef FEAT_XIM
1200 && xic != NULL
1201 # endif
1202 # ifdef FEAT_GUI
1203 && (!gui.in_use || gui.in_focus)
1204 # endif
1205 )
1206 {
1207 // Do save when IM is on, or IM is off and saved status is on.
1208 if (vgetc_im_active)
1209 *psave = B_IMODE_IM;
1210 else if (*psave == B_IMODE_IM)
1211 *psave = B_IMODE_NONE;
1212 }
1213 }
1214 #endif
1215