diff options
| author | Karl Heuer | 1996-02-21 21:06:51 +0000 |
|---|---|---|
| committer | Karl Heuer | 1996-02-21 21:06:51 +0000 |
| commit | d9d4c147ce55dab6b824df03632ce439b48c9105 (patch) | |
| tree | 51ef75281497b2888f3602d2f62c53360e4c343b /src | |
| parent | 53e28d2aee3322a7ded788adbc5c916f0fb2e57a (diff) | |
| download | emacs-d9d4c147ce55dab6b824df03632ce439b48c9105.tar.gz emacs-d9d4c147ce55dab6b824df03632ce439b48c9105.zip | |
(swallow_events): New arg DO_DISPLAY.
(swallow_events): Process timer_event events here.
(detect_input_pending_run_timers): New function.
(Vtimer_idle_list): New variable.
(syms_of_keyboard): Set up Lisp var.
(timer_check): Check for idle-time timers too.
Expect timers to have 8 slots. Initialize triggertime.
(timer_start_idle, timer_stop_idle): New functions.
(get_input_pending): New arg do_timers_now.
(readable_events): Likewise.
(Finput_pending_p): Use get_input_pending, so we can specify
1 for do_timers_now.
(timer_check): Check for difference being zero.
Diffstat (limited to 'src')
| -rw-r--r-- | src/keyboard.c | 327 |
1 files changed, 206 insertions, 121 deletions
diff --git a/src/keyboard.c b/src/keyboard.c index 768036d803d..50d39831497 100644 --- a/src/keyboard.c +++ b/src/keyboard.c | |||
| @@ -474,9 +474,12 @@ extern char *x_get_keysym_name (); | |||
| 474 | 474 | ||
| 475 | Lisp_Object Qpolling_period; | 475 | Lisp_Object Qpolling_period; |
| 476 | 476 | ||
| 477 | /* List of active timers. Appears in order of next scheduled event. */ | 477 | /* List of absolute timers. Appears in order of next scheduled event. */ |
| 478 | Lisp_Object Vtimer_list; | 478 | Lisp_Object Vtimer_list; |
| 479 | 479 | ||
| 480 | /* List of idle time timers. Appears in order of next scheduled event. */ | ||
| 481 | Lisp_Object Vtimer_idle_list; | ||
| 482 | |||
| 480 | extern Lisp_Object Vprint_level, Vprint_length; | 483 | extern Lisp_Object Vprint_level, Vprint_length; |
| 481 | 484 | ||
| 482 | /* Address (if not 0) of EMACS_TIME to zero out if a SIGIO interrupt | 485 | /* Address (if not 0) of EMACS_TIME to zero out if a SIGIO interrupt |
| @@ -1809,6 +1812,8 @@ read_char (commandflag, nmaps, maps, prev_event, used_mouse_menu) | |||
| 1809 | goto non_reread; | 1812 | goto non_reread; |
| 1810 | } | 1813 | } |
| 1811 | 1814 | ||
| 1815 | timer_start_idle (); | ||
| 1816 | |||
| 1812 | /* If in middle of key sequence and minibuffer not active, | 1817 | /* If in middle of key sequence and minibuffer not active, |
| 1813 | start echoing if enough time elapses. */ | 1818 | start echoing if enough time elapses. */ |
| 1814 | 1819 | ||
| @@ -1888,25 +1893,11 @@ read_char (commandflag, nmaps, maps, prev_event, used_mouse_menu) | |||
| 1888 | && XINT (Vauto_save_timeout) > 0) | 1893 | && XINT (Vauto_save_timeout) > 0) |
| 1889 | { | 1894 | { |
| 1890 | Lisp_Object tem0; | 1895 | Lisp_Object tem0; |
| 1891 | EMACS_TIME timer_delay; | ||
| 1892 | EMACS_TIME delay, difference; | ||
| 1893 | |||
| 1894 | EMACS_SET_SECS (delay, | ||
| 1895 | delay_level * XFASTINT (Vauto_save_timeout) / 4); | ||
| 1896 | EMACS_SET_USECS (delay, 0); | ||
| 1897 | |||
| 1898 | /* Don't wait longer than until the next timer will fire. */ | ||
| 1899 | timer_delay = timer_check (0); | ||
| 1900 | if (! EMACS_TIME_NEG_P (timer_delay)) | ||
| 1901 | { | ||
| 1902 | EMACS_SUB_TIME (difference, timer_delay, delay); | ||
| 1903 | if (EMACS_TIME_NEG_P (difference)) | ||
| 1904 | delay = timer_delay; | ||
| 1905 | } | ||
| 1906 | 1896 | ||
| 1907 | save_getcjmp (save_jump); | 1897 | save_getcjmp (save_jump); |
| 1908 | restore_getcjmp (local_getcjmp); | 1898 | restore_getcjmp (local_getcjmp); |
| 1909 | tem0 = sit_for (EMACS_SECS (delay), EMACS_USECS (delay), 1, 1); | 1899 | tem0 = sit_for (delay_level * XFASTINT (Vauto_save_timeout) / 4, |
| 1900 | 0, 1, 1); | ||
| 1910 | restore_getcjmp (save_jump); | 1901 | restore_getcjmp (save_jump); |
| 1911 | 1902 | ||
| 1912 | if (EQ (tem0, Qt)) | 1903 | if (EQ (tem0, Qt)) |
| @@ -1938,7 +1929,7 @@ read_char (commandflag, nmaps, maps, prev_event, used_mouse_menu) | |||
| 1938 | = XCONS (current_kboard->kbd_queue)->cdr; | 1929 | = XCONS (current_kboard->kbd_queue)->cdr; |
| 1939 | if (NILP (current_kboard->kbd_queue)) | 1930 | if (NILP (current_kboard->kbd_queue)) |
| 1940 | current_kboard->kbd_queue_has_data = 0; | 1931 | current_kboard->kbd_queue_has_data = 0; |
| 1941 | input_pending = readable_events (); | 1932 | input_pending = readable_events (0); |
| 1942 | #ifdef MULTI_FRAME | 1933 | #ifdef MULTI_FRAME |
| 1943 | if (EVENT_HAS_PARAMETERS (c) | 1934 | if (EVENT_HAS_PARAMETERS (c) |
| 1944 | && EQ (EVENT_HEAD_KIND (EVENT_HEAD (c)), Qswitch_frame)) | 1935 | && EQ (EVENT_HEAD_KIND (EVENT_HEAD (c)), Qswitch_frame)) |
| @@ -2026,6 +2017,11 @@ read_char (commandflag, nmaps, maps, prev_event, used_mouse_menu) | |||
| 2026 | 2017 | ||
| 2027 | non_reread: | 2018 | non_reread: |
| 2028 | 2019 | ||
| 2020 | /* Now that we have read an event, Emacs is not idle-- | ||
| 2021 | unless the event was a timer event. */ | ||
| 2022 | if (! (CONSP (c) && EQ (XCONS (c)->car, Qtimer_event))) | ||
| 2023 | timer_stop_idle (); | ||
| 2024 | |||
| 2029 | start_polling (); | 2025 | start_polling (); |
| 2030 | 2026 | ||
| 2031 | if (NILP (c)) | 2027 | if (NILP (c)) |
| @@ -2293,10 +2289,10 @@ tracking_off (old_value) | |||
| 2293 | input has been processed. If the only input available was | 2289 | input has been processed. If the only input available was |
| 2294 | the sort that we have just disabled, then we need to call | 2290 | the sort that we have just disabled, then we need to call |
| 2295 | redisplay. */ | 2291 | redisplay. */ |
| 2296 | if (!readable_events ()) | 2292 | if (!readable_events (1)) |
| 2297 | { | 2293 | { |
| 2298 | redisplay_preserve_echo_area (); | 2294 | redisplay_preserve_echo_area (); |
| 2299 | get_input_pending (&input_pending); | 2295 | get_input_pending (&input_pending, 1); |
| 2300 | } | 2296 | } |
| 2301 | } | 2297 | } |
| 2302 | } | 2298 | } |
| @@ -2346,9 +2342,10 @@ some_mouse_moved () | |||
| 2346 | /* Return true iff there are any events in the queue that read-char | 2342 | /* Return true iff there are any events in the queue that read-char |
| 2347 | would return. If this returns false, a read-char would block. */ | 2343 | would return. If this returns false, a read-char would block. */ |
| 2348 | static int | 2344 | static int |
| 2349 | readable_events () | 2345 | readable_events (do_timers_now) |
| 2346 | int do_timers_now; | ||
| 2350 | { | 2347 | { |
| 2351 | timer_check (1); | 2348 | timer_check (do_timers_now); |
| 2352 | if (kbd_fetch_ptr != kbd_store_ptr) | 2349 | if (kbd_fetch_ptr != kbd_store_ptr) |
| 2353 | return 1; | 2350 | return 1; |
| 2354 | #ifdef HAVE_MOUSE | 2351 | #ifdef HAVE_MOUSE |
| @@ -2548,17 +2545,6 @@ kbd_buffer_get_event (kbp, used_mouse_menu) | |||
| 2548 | break; | 2545 | break; |
| 2549 | #endif | 2546 | #endif |
| 2550 | 2547 | ||
| 2551 | /* Check when the next timer fires. */ | ||
| 2552 | next_timer_delay = timer_check (0); | ||
| 2553 | if (EMACS_SECS (next_timer_delay) == 0 | ||
| 2554 | && EMACS_USECS (next_timer_delay) == 0) | ||
| 2555 | break; | ||
| 2556 | if (EMACS_TIME_NEG_P (next_timer_delay)) | ||
| 2557 | { | ||
| 2558 | EMACS_SET_SECS (next_timer_delay, 0); | ||
| 2559 | EMACS_SET_USECS (next_timer_delay, 0); | ||
| 2560 | } | ||
| 2561 | |||
| 2562 | /* If the quit flag is set, then read_char will return | 2548 | /* If the quit flag is set, then read_char will return |
| 2563 | quit_char, so that counts as "available input." */ | 2549 | quit_char, so that counts as "available input." */ |
| 2564 | if (!NILP (Vquit_flag)) | 2550 | if (!NILP (Vquit_flag)) |
| @@ -2584,9 +2570,7 @@ kbd_buffer_get_event (kbp, used_mouse_menu) | |||
| 2584 | Lisp_Object minus_one; | 2570 | Lisp_Object minus_one; |
| 2585 | 2571 | ||
| 2586 | XSETINT (minus_one, -1); | 2572 | XSETINT (minus_one, -1); |
| 2587 | wait_reading_process_input (EMACS_SECS (next_timer_delay), | 2573 | wait_reading_process_input (0, 0, minus_one, 1); |
| 2588 | EMACS_USECS (next_timer_delay), | ||
| 2589 | minus_one, 1); | ||
| 2590 | 2574 | ||
| 2591 | if (!interrupt_input && kbd_fetch_ptr == kbd_store_ptr) | 2575 | if (!interrupt_input && kbd_fetch_ptr == kbd_store_ptr) |
| 2592 | /* Pass 1 for EXPECT since we just waited to have input. */ | 2576 | /* Pass 1 for EXPECT since we just waited to have input. */ |
| @@ -2631,7 +2615,7 @@ kbd_buffer_get_event (kbp, used_mouse_menu) | |||
| 2631 | and process it again. */ | 2615 | and process it again. */ |
| 2632 | copy = *event; | 2616 | copy = *event; |
| 2633 | kbd_fetch_ptr = event + 1; | 2617 | kbd_fetch_ptr = event + 1; |
| 2634 | input_pending = readable_events (); | 2618 | input_pending = readable_events (0); |
| 2635 | x_handle_selection_request (©); | 2619 | x_handle_selection_request (©); |
| 2636 | #else | 2620 | #else |
| 2637 | /* We're getting selection request events, but we don't have | 2621 | /* We're getting selection request events, but we don't have |
| @@ -2648,7 +2632,7 @@ kbd_buffer_get_event (kbp, used_mouse_menu) | |||
| 2648 | /* Remove it from the buffer before processing it. */ | 2632 | /* Remove it from the buffer before processing it. */ |
| 2649 | copy = *event; | 2633 | copy = *event; |
| 2650 | kbd_fetch_ptr = event + 1; | 2634 | kbd_fetch_ptr = event + 1; |
| 2651 | input_pending = readable_events (); | 2635 | input_pending = readable_events (0); |
| 2652 | x_handle_selection_clear (©); | 2636 | x_handle_selection_clear (©); |
| 2653 | #else | 2637 | #else |
| 2654 | /* We're getting selection request events, but we don't have | 2638 | /* We're getting selection request events, but we don't have |
| @@ -2689,7 +2673,7 @@ kbd_buffer_get_event (kbp, used_mouse_menu) | |||
| 2689 | else if (event->kind == menu_bar_activate_event) | 2673 | else if (event->kind == menu_bar_activate_event) |
| 2690 | { | 2674 | { |
| 2691 | kbd_fetch_ptr = event + 1; | 2675 | kbd_fetch_ptr = event + 1; |
| 2692 | input_pending = readable_events (); | 2676 | input_pending = readable_events (0); |
| 2693 | x_activate_menubar (XFRAME (event->frame_or_window)); | 2677 | x_activate_menubar (XFRAME (event->frame_or_window)); |
| 2694 | } | 2678 | } |
| 2695 | #endif | 2679 | #endif |
| @@ -2801,7 +2785,7 @@ kbd_buffer_get_event (kbp, used_mouse_menu) | |||
| 2801 | something for us to read! */ | 2785 | something for us to read! */ |
| 2802 | abort (); | 2786 | abort (); |
| 2803 | 2787 | ||
| 2804 | input_pending = readable_events (); | 2788 | input_pending = readable_events (0); |
| 2805 | 2789 | ||
| 2806 | #ifdef MULTI_FRAME | 2790 | #ifdef MULTI_FRAME |
| 2807 | Vlast_event_frame = internal_last_event_frame; | 2791 | Vlast_event_frame = internal_last_event_frame; |
| @@ -2814,7 +2798,8 @@ kbd_buffer_get_event (kbp, used_mouse_menu) | |||
| 2814 | then return, without reading any user-visible events. */ | 2798 | then return, without reading any user-visible events. */ |
| 2815 | 2799 | ||
| 2816 | void | 2800 | void |
| 2817 | swallow_events () | 2801 | swallow_events (do_display) |
| 2802 | int do_display; | ||
| 2818 | { | 2803 | { |
| 2819 | while (kbd_fetch_ptr != kbd_store_ptr) | 2804 | while (kbd_fetch_ptr != kbd_store_ptr) |
| 2820 | { | 2805 | { |
| @@ -2838,7 +2823,7 @@ swallow_events () | |||
| 2838 | and process it again. */ | 2823 | and process it again. */ |
| 2839 | copy = *event; | 2824 | copy = *event; |
| 2840 | kbd_fetch_ptr = event + 1; | 2825 | kbd_fetch_ptr = event + 1; |
| 2841 | input_pending = readable_events (); | 2826 | input_pending = readable_events (0); |
| 2842 | x_handle_selection_request (©); | 2827 | x_handle_selection_request (©); |
| 2843 | #else | 2828 | #else |
| 2844 | /* We're getting selection request events, but we don't have | 2829 | /* We're getting selection request events, but we don't have |
| @@ -2856,7 +2841,7 @@ swallow_events () | |||
| 2856 | copy = *event; | 2841 | copy = *event; |
| 2857 | 2842 | ||
| 2858 | kbd_fetch_ptr = event + 1; | 2843 | kbd_fetch_ptr = event + 1; |
| 2859 | input_pending = readable_events (); | 2844 | input_pending = readable_events (0); |
| 2860 | x_handle_selection_clear (©); | 2845 | x_handle_selection_clear (©); |
| 2861 | #else | 2846 | #else |
| 2862 | /* We're getting selection request events, but we don't have | 2847 | /* We're getting selection request events, but we don't have |
| @@ -2864,13 +2849,69 @@ swallow_events () | |||
| 2864 | abort (); | 2849 | abort (); |
| 2865 | #endif | 2850 | #endif |
| 2866 | } | 2851 | } |
| 2852 | else if (event->kind == timer_event) | ||
| 2853 | { | ||
| 2854 | Lisp_Object tem, lisp_event; | ||
| 2855 | int was_locked = single_kboard; | ||
| 2856 | |||
| 2857 | tem = get_keymap_1 (Vspecial_event_map, 0, 0); | ||
| 2858 | tem = get_keyelt (access_keymap (tem, Qtimer_event, 0, 0), | ||
| 2859 | 1); | ||
| 2860 | lisp_event = Fcons (Qtimer_event, | ||
| 2861 | Fcons (Fcdr (event->frame_or_window), Qnil)); | ||
| 2862 | kbd_fetch_ptr = event + 1; | ||
| 2863 | if (kbd_fetch_ptr == kbd_store_ptr) | ||
| 2864 | input_pending = 0; | ||
| 2865 | Fcommand_execute (tem, Qnil, Fvector (1, &lisp_event)); | ||
| 2866 | if (do_display) | ||
| 2867 | redisplay_preserve_echo_area (); | ||
| 2868 | |||
| 2869 | /* Resume allowing input from any kboard, if that was true before. */ | ||
| 2870 | if (!was_locked) | ||
| 2871 | any_kboard_state (); | ||
| 2872 | } | ||
| 2867 | else | 2873 | else |
| 2868 | break; | 2874 | break; |
| 2869 | } | 2875 | } |
| 2870 | 2876 | ||
| 2871 | get_input_pending (&input_pending); | 2877 | get_input_pending (&input_pending, 1); |
| 2872 | } | 2878 | } |
| 2873 | 2879 | ||
| 2880 | static EMACS_TIME timer_idleness_start_time; | ||
| 2881 | |||
| 2882 | /* Record the start of when Emacs is idle, | ||
| 2883 | for the sake of running idle-time timers. */ | ||
| 2884 | |||
| 2885 | timer_start_idle () | ||
| 2886 | { | ||
| 2887 | Lisp_Object timers; | ||
| 2888 | |||
| 2889 | /* If we are already in the idle state, do nothing. */ | ||
| 2890 | if (! EMACS_TIME_NEG_P (timer_idleness_start_time)) | ||
| 2891 | return; | ||
| 2892 | |||
| 2893 | EMACS_GET_TIME (timer_idleness_start_time); | ||
| 2894 | |||
| 2895 | /* Mark all idle-time timers as once again candidates for running. */ | ||
| 2896 | for (timers = Vtimer_idle_list; CONSP (timers); timers = XCONS (timers)->cdr) | ||
| 2897 | { | ||
| 2898 | Lisp_Object timer; | ||
| 2899 | |||
| 2900 | timer = XCONS (timers)->car; | ||
| 2901 | |||
| 2902 | if (!VECTORP (timer) || XVECTOR (timer)->size != 8) | ||
| 2903 | continue; | ||
| 2904 | XVECTOR (timer)->contents[0] = Qnil; | ||
| 2905 | } | ||
| 2906 | } | ||
| 2907 | |||
| 2908 | /* Record that Emacs is no longer idle, so stop running idle-time timers. */ | ||
| 2909 | |||
| 2910 | timer_stop_idle () | ||
| 2911 | { | ||
| 2912 | EMACS_SET_SECS_USECS (timer_idleness_start_time, -1, -1); | ||
| 2913 | } | ||
| 2914 | |||
| 2874 | /* Check whether a timer has fired. To prevent larger problems we simply | 2915 | /* Check whether a timer has fired. To prevent larger problems we simply |
| 2875 | disregard elements that are not proper timers. Do not make a circular | 2916 | disregard elements that are not proper timers. Do not make a circular |
| 2876 | timer list for the time being. | 2917 | timer list for the time being. |
| @@ -2892,6 +2933,7 @@ timer_check (do_it_now) | |||
| 2892 | /* Nonzero if we generate some events. */ | 2933 | /* Nonzero if we generate some events. */ |
| 2893 | int events_generated = 0; | 2934 | int events_generated = 0; |
| 2894 | struct gcpro gcpro1, gcpro2; | 2935 | struct gcpro gcpro1, gcpro2; |
| 2936 | int listnum; | ||
| 2895 | 2937 | ||
| 2896 | EMACS_SET_SECS (nexttime, -1); | 2938 | EMACS_SET_SECS (nexttime, -1); |
| 2897 | EMACS_SET_USECS (nexttime, -1); | 2939 | EMACS_SET_USECS (nexttime, -1); |
| @@ -2900,89 +2942,112 @@ timer_check (do_it_now) | |||
| 2900 | timer = Qnil; | 2942 | timer = Qnil; |
| 2901 | GCPRO2 (timers, timer); | 2943 | GCPRO2 (timers, timer); |
| 2902 | 2944 | ||
| 2903 | if (CONSP (timers)) | 2945 | if (CONSP (Vtimer_list) || CONSP (Vtimer_idle_list)) |
| 2904 | EMACS_GET_TIME (now); | 2946 | EMACS_GET_TIME (now); |
| 2905 | 2947 | ||
| 2906 | while (CONSP (timers)) | 2948 | for (listnum = 0; listnum < 2; listnum++) |
| 2907 | { | 2949 | { |
| 2908 | int triggertime; | 2950 | EMACS_TIME compare_time; |
| 2909 | Lisp_Object *vector; | ||
| 2910 | EMACS_TIME timer_time; | ||
| 2911 | EMACS_TIME difference; | ||
| 2912 | |||
| 2913 | timer = XCONS (timers)->car; | ||
| 2914 | timers = XCONS (timers)->cdr; | ||
| 2915 | 2951 | ||
| 2916 | if (!VECTORP (timer) || XVECTOR (timer)->size != 7) | 2952 | /* Always first scan the absolute timer list. */ |
| 2917 | continue; | 2953 | if (listnum == 0) |
| 2918 | vector = XVECTOR (timer)->contents; | 2954 | { |
| 2919 | 2955 | timers = Vtimer_list; | |
| 2920 | if (!INTEGERP (vector[1]) || !INTEGERP (vector[2]) | 2956 | compare_time = now; |
| 2921 | || !INTEGERP (vector[3])) | 2957 | } |
| 2922 | continue; | 2958 | /* If Emacs is idle, scan the idle timer list |
| 2959 | using the length of idleness as the time value. */ | ||
| 2960 | else if (! EMACS_TIME_NEG_P (timer_idleness_start_time)) | ||
| 2961 | { | ||
| 2962 | timers = Vtimer_idle_list; | ||
| 2963 | EMACS_SUB_TIME (compare_time, now, timer_idleness_start_time); | ||
| 2964 | } | ||
| 2965 | else | ||
| 2966 | break; | ||
| 2923 | 2967 | ||
| 2924 | EMACS_SET_SECS (timer_time, | 2968 | while (CONSP (timers)) |
| 2925 | (XINT (vector[1]) << 16) | (XINT (vector[2]))); | ||
| 2926 | EMACS_SET_USECS (timer_time, XINT (vector[3])); | ||
| 2927 | EMACS_SUB_TIME (difference, timer_time, now); | ||
| 2928 | /* If event is past, run it if it hasn't been run. */ | ||
| 2929 | if (EMACS_TIME_NEG_P (difference)) | ||
| 2930 | { | 2969 | { |
| 2931 | if (NILP (vector[0])) | 2970 | int triggertime = EMACS_SECS (now); |
| 2971 | Lisp_Object *vector; | ||
| 2972 | EMACS_TIME timer_time; | ||
| 2973 | EMACS_TIME difference; | ||
| 2974 | |||
| 2975 | timer = XCONS (timers)->car; | ||
| 2976 | timers = XCONS (timers)->cdr; | ||
| 2977 | |||
| 2978 | if (!VECTORP (timer) || XVECTOR (timer)->size != 8) | ||
| 2979 | continue; | ||
| 2980 | vector = XVECTOR (timer)->contents; | ||
| 2981 | |||
| 2982 | if (!INTEGERP (vector[1]) || !INTEGERP (vector[2]) | ||
| 2983 | || !INTEGERP (vector[3])) | ||
| 2984 | continue; | ||
| 2985 | |||
| 2986 | EMACS_SET_SECS (timer_time, | ||
| 2987 | (XINT (vector[1]) << 16) | (XINT (vector[2]))); | ||
| 2988 | EMACS_SET_USECS (timer_time, XINT (vector[3])); | ||
| 2989 | EMACS_SUB_TIME (difference, timer_time, compare_time); | ||
| 2990 | /* If event is past, run it if it hasn't been run. */ | ||
| 2991 | if (EMACS_TIME_NEG_P (difference) | ||
| 2992 | || (EMACS_SECS (difference) == 0 | ||
| 2993 | && EMACS_USECS (difference) == 0)) | ||
| 2932 | { | 2994 | { |
| 2933 | /* Mark the timer as triggered to prevent problems if the lisp | 2995 | if (NILP (vector[0])) |
| 2934 | code fails to reschedule it right. */ | ||
| 2935 | vector[0] = Qt; | ||
| 2936 | |||
| 2937 | /* Run the timer or queue a timer event. */ | ||
| 2938 | if (do_it_now) | ||
| 2939 | { | 2996 | { |
| 2940 | Lisp_Object tem, event; | 2997 | /* Mark the timer as triggered to prevent problems if the lisp |
| 2941 | int was_locked = single_kboard; | 2998 | code fails to reschedule it right. */ |
| 2999 | vector[0] = Qt; | ||
| 2942 | 3000 | ||
| 2943 | tem = get_keymap_1 (Vspecial_event_map, 0, 0); | 3001 | /* Run the timer or queue a timer event. */ |
| 2944 | tem = get_keyelt (access_keymap (tem, Qtimer_event, 0, 0), | 3002 | if (do_it_now) |
| 2945 | 1); | 3003 | { |
| 2946 | event = Fcons (Qtimer_event, Fcons (timer, Qnil)); | 3004 | Lisp_Object tem, event; |
| 2947 | Fcommand_execute (tem, Qnil, Fvector (1, &event)); | 3005 | int was_locked = single_kboard; |
| 2948 | 3006 | ||
| 2949 | /* Resume allowing input from any kboard, if that was true before. */ | 3007 | tem = get_keymap_1 (Vspecial_event_map, 0, 0); |
| 2950 | if (!was_locked) | 3008 | tem = get_keyelt (access_keymap (tem, Qtimer_event, 0, 0), |
| 2951 | any_kboard_state (); | 3009 | 1); |
| 3010 | event = Fcons (Qtimer_event, Fcons (timer, Qnil)); | ||
| 3011 | Fcommand_execute (tem, Qnil, Fvector (1, &event)); | ||
| 2952 | 3012 | ||
| 2953 | /* Since we have handled the event, | 3013 | /* Resume allowing input from any kboard, if that was true before. */ |
| 2954 | we don't need to tell the caller to wake up and do it. */ | 3014 | if (!was_locked) |
| 2955 | } | 3015 | any_kboard_state (); |
| 2956 | else | 3016 | |
| 2957 | { | 3017 | /* Since we have handled the event, |
| 2958 | /* Generate a timer event so the caller will handle it. */ | 3018 | we don't need to tell the caller to wake up and do it. */ |
| 2959 | struct input_event event; | 3019 | } |
| 2960 | 3020 | else | |
| 2961 | event.kind = timer_event; | 3021 | { |
| 2962 | event.modifiers = 0; | 3022 | /* Generate a timer event so the caller will handle it. */ |
| 2963 | event.x = event.y = Qnil; | 3023 | struct input_event event; |
| 2964 | event.timestamp = triggertime; | 3024 | |
| 2965 | /* Store the timer in the frame slot. */ | 3025 | event.kind = timer_event; |
| 2966 | event.frame_or_window = Fcons (Fselected_frame (), timer); | 3026 | event.modifiers = 0; |
| 2967 | kbd_buffer_store_event (&event); | 3027 | event.x = event.y = Qnil; |
| 2968 | 3028 | event.timestamp = triggertime; | |
| 2969 | /* Tell caller to handle this event right away. */ | 3029 | /* Store the timer in the frame slot. */ |
| 2970 | events_generated = 1; | 3030 | event.frame_or_window = Fcons (Fselected_frame (), timer); |
| 2971 | EMACS_SET_SECS (nexttime, 0); | 3031 | kbd_buffer_store_event (&event); |
| 2972 | EMACS_SET_USECS (nexttime, 0); | 3032 | |
| 3033 | /* Tell caller to handle this event right away. */ | ||
| 3034 | events_generated = 1; | ||
| 3035 | EMACS_SET_SECS (nexttime, 0); | ||
| 3036 | EMACS_SET_USECS (nexttime, 0); | ||
| 3037 | } | ||
| 2973 | } | 3038 | } |
| 2974 | } | 3039 | } |
| 2975 | } | 3040 | else |
| 2976 | else | 3041 | /* When we encounter a timer that is still waiting, |
| 2977 | /* When we encounter a timer that is still waiting, | 3042 | return the amount of time to wait before it is ripe. */ |
| 2978 | return the amount of time to wait before it is ripe. */ | 3043 | { |
| 2979 | { | 3044 | UNGCPRO; |
| 2980 | UNGCPRO; | 3045 | /* But if we generated an event, |
| 2981 | /* But if we generated an event, | 3046 | tell the caller to handle it now. */ |
| 2982 | tell the caller to handle it now. */ | 3047 | if (events_generated) |
| 2983 | if (events_generated) | 3048 | return nexttime; |
| 2984 | return nexttime; | 3049 | return difference; |
| 2985 | return difference; | 3050 | } |
| 2986 | } | 3051 | } |
| 2987 | } | 3052 | } |
| 2988 | /* No timers are pending in the future. */ | 3053 | /* No timers are pending in the future. */ |
| @@ -4428,14 +4493,17 @@ lucid_event_type_list_p (object) | |||
| 4428 | /* Store into *addr a value nonzero if terminal input chars are available. | 4493 | /* Store into *addr a value nonzero if terminal input chars are available. |
| 4429 | Serves the purpose of ioctl (0, FIONREAD, addr) | 4494 | Serves the purpose of ioctl (0, FIONREAD, addr) |
| 4430 | but works even if FIONREAD does not exist. | 4495 | but works even if FIONREAD does not exist. |
| 4431 | (In fact, this may actually read some input.) */ | 4496 | (In fact, this may actually read some input.) |
| 4497 | |||
| 4498 | If DO_TIMERS_NOW is nonzero, actually run timer events that are ripe. */ | ||
| 4432 | 4499 | ||
| 4433 | static void | 4500 | static void |
| 4434 | get_input_pending (addr) | 4501 | get_input_pending (addr, do_timers_now) |
| 4435 | int *addr; | 4502 | int *addr; |
| 4503 | int do_timers_now; | ||
| 4436 | { | 4504 | { |
| 4437 | /* First of all, have we already counted some input? */ | 4505 | /* First of all, have we already counted some input? */ |
| 4438 | *addr = !NILP (Vquit_flag) || readable_events (); | 4506 | *addr = !NILP (Vquit_flag) || readable_events (do_timers_now); |
| 4439 | 4507 | ||
| 4440 | /* If input is being read as it arrives, and we have none, there is none. */ | 4508 | /* If input is being read as it arrives, and we have none, there is none. */ |
| 4441 | if (*addr > 0 || (interrupt_input && ! interrupts_deferred)) | 4509 | if (*addr > 0 || (interrupt_input && ! interrupts_deferred)) |
| @@ -4443,7 +4511,7 @@ get_input_pending (addr) | |||
| 4443 | 4511 | ||
| 4444 | /* Try to read some input and see how much we get. */ | 4512 | /* Try to read some input and see how much we get. */ |
| 4445 | gobble_input (0); | 4513 | gobble_input (0); |
| 4446 | *addr = !NILP (Vquit_flag) || readable_events (); | 4514 | *addr = !NILP (Vquit_flag) || readable_events (do_timers_now); |
| 4447 | } | 4515 | } |
| 4448 | 4516 | ||
| 4449 | /* Interface to read_avail_input, blocking SIGIO or SIGALRM if necessary. */ | 4517 | /* Interface to read_avail_input, blocking SIGIO or SIGALRM if necessary. */ |
| @@ -6786,11 +6854,23 @@ current_active_maps (maps_p) | |||
| 6786 | return nmaps; | 6854 | return nmaps; |
| 6787 | } | 6855 | } |
| 6788 | 6856 | ||
| 6857 | /* Return nonzero if input events are pending. */ | ||
| 6789 | 6858 | ||
| 6790 | detect_input_pending () | 6859 | detect_input_pending () |
| 6791 | { | 6860 | { |
| 6792 | if (!input_pending) | 6861 | if (!input_pending) |
| 6793 | get_input_pending (&input_pending); | 6862 | get_input_pending (&input_pending, 0); |
| 6863 | |||
| 6864 | return input_pending; | ||
| 6865 | } | ||
| 6866 | |||
| 6867 | /* Return nonzero if input events are pending. | ||
| 6868 | Execute timers immediately; don't make events for them. */ | ||
| 6869 | |||
| 6870 | detect_input_pending_run_timers () | ||
| 6871 | { | ||
| 6872 | if (!input_pending) | ||
| 6873 | get_input_pending (&input_pending, 1); | ||
| 6794 | 6874 | ||
| 6795 | return input_pending; | 6875 | return input_pending; |
| 6796 | } | 6876 | } |
| @@ -6811,7 +6891,8 @@ Actually, the value is nil only if we can be sure that no input is available.") | |||
| 6811 | if (!NILP (Vunread_command_events) || unread_command_char != -1) | 6891 | if (!NILP (Vunread_command_events) || unread_command_char != -1) |
| 6812 | return (Qt); | 6892 | return (Qt); |
| 6813 | 6893 | ||
| 6814 | return detect_input_pending () ? Qt : Qnil; | 6894 | get_input_pending (&input_pending, 1); |
| 6895 | return input_pending > 0 ? Qt : Qnil; | ||
| 6815 | } | 6896 | } |
| 6816 | 6897 | ||
| 6817 | DEFUN ("recent-keys", Frecent_keys, Srecent_keys, 0, 0, 0, | 6898 | DEFUN ("recent-keys", Frecent_keys, Srecent_keys, 0, 0, 0, |
| @@ -7862,8 +7943,12 @@ If the value is non-nil and not a number, we wait 2 seconds."); | |||
| 7862 | Vcolumn_number_mode = Qnil; | 7943 | Vcolumn_number_mode = Qnil; |
| 7863 | 7944 | ||
| 7864 | DEFVAR_LISP ("timer-list", &Vtimer_list, | 7945 | DEFVAR_LISP ("timer-list", &Vtimer_list, |
| 7865 | "List of active timers in order of increasing time"); | 7946 | "List of active absolute time timers in order of increasing time"); |
| 7866 | Vtimer_list = Qnil; | 7947 | Vtimer_list = Qnil; |
| 7948 | |||
| 7949 | DEFVAR_LISP ("timer-idle-list", &Vtimer_idle_list, | ||
| 7950 | "List of active idle-time timers in order of increasing time"); | ||
| 7951 | Vtimer_idle_list = Qnil; | ||
| 7867 | } | 7952 | } |
| 7868 | 7953 | ||
| 7869 | keys_of_keyboard () | 7954 | keys_of_keyboard () |