Mercurial > emacs
changeset 74611:4d547fe4a938
(make_lispy_event): Use find_user_signal_name.
(read_avail_input): Store pending user signal events.
(struct user_signal_info): New struct.
(user_signals): New variable.
(add_user_signal, store_user_signal_events find_user_signal_name):
New functions.
(handle_user_signal): Move function from emacs.c. Don't store
USER_SIGNAL_EVENT here, but increment number of pending signals.
author | YAMAMOTO Mitsuharu <mituharu@math.s.chiba-u.ac.jp> |
---|---|
date | Thu, 14 Dec 2006 08:41:46 +0000 |
parents | 0da2b2f82afc |
children | e0cd1d7ea60c |
files | src/keyboard.c |
diffstat | 1 files changed, 144 insertions(+), 14 deletions(-) [+] |
line wrap: on
line diff
--- a/src/keyboard.c Thu Dec 14 08:41:23 2006 +0000 +++ b/src/keyboard.c Thu Dec 14 08:41:46 2006 +0000 @@ -699,6 +699,9 @@ static void timer_start_idle P_ ((void)); static void timer_stop_idle P_ ((void)); static void timer_resume_idle P_ ((void)); +static SIGTYPE handle_user_signal P_ ((int)); +static char *find_user_signal_name P_ ((int)); +static int store_user_signal_events P_ ((void)); /* Nonzero means don't try to suspend even if the operating system seems to support it. */ @@ -5948,20 +5951,16 @@ case USER_SIGNAL_EVENT: /* A user signal. */ - switch (event->code) - { - case 0: - return Qsignal; -#ifdef SIGUSR1 - case SIGUSR1: - return intern ("usr1"); -#endif -#ifdef SIGUSR2 - case SIGUSR2: - return intern ("usr2"); -#endif - default: - return make_number (event->code); + if (event->code == 0) + return Qsignal; + else + { + char *name = find_user_signal_name (event->code); + + if (name) + return intern (name); + else + return make_number (event->code); } case SAVE_SESSION_EVENT: @@ -6799,6 +6798,10 @@ register int i; int nread = 0; + /* Store pending user signal events, if any. */ + if (store_user_signal_events ()) + expected = 0; + if (read_socket_hook) { int nr; @@ -7022,6 +7025,133 @@ +/* User signal events. */ + +struct user_signal_info +{ + /* Signal number. */ + int sig; + + /* Name of the signal. */ + char *name; + + /* Number of pending signals. */ + int npending; + + struct user_signal_info *next; +}; + +/* List of user signals. */ +static struct user_signal_info *user_signals = NULL; + +void +add_user_signal (sig, name) + int sig; + const char *name; +{ + struct user_signal_info *p; + + for (p = user_signals; p; p = p->next) + if (p->sig == sig) + /* Already added. */ + return; + + p = xmalloc (sizeof (struct user_signal_info)); + p->sig = sig; + p->name = xstrdup (name); + p->npending = 0; + p->next = user_signals; + user_signals = p; + + signal (sig, handle_user_signal); +} + +static SIGTYPE +handle_user_signal (sig) + int sig; +{ + int old_errno = errno; + struct user_signal_info *p; + +#if defined (USG) && !defined (POSIX_SIGNALS) + /* USG systems forget handlers when they are used; + must reestablish each time */ + signal (sig, handle_user_signal); +#endif + + SIGNAL_THREAD_CHECK (sig); + + for (p = user_signals; p; p = p->next) + if (p->sig == sig) + { + p->npending++; +#ifdef SIGIO + if (interrupt_input) + kill (getpid (), SIGIO); + else +#endif + { + /* Tell wait_reading_process_output that it needs to wake + up and look around. */ + if (input_available_clear_time) + EMACS_SET_SECS_USECS (*input_available_clear_time, 0, 0); + } + break; + } + + errno = old_errno; +} + +static char * +find_user_signal_name (sig) + int sig; +{ + struct user_signal_info *p; + + for (p = user_signals; p; p = p->next) + if (p->sig == sig) + return p->name; + + return NULL; +} + +static int +store_user_signal_events () +{ + struct user_signal_info *p; + struct input_event buf; + int nstored = 0; + + for (p = user_signals; p; p = p->next) + if (p->npending > 0) + { + SIGMASKTYPE mask; + + if (nstored == 0) + { + bzero (&buf, sizeof buf); + buf.kind = USER_SIGNAL_EVENT; + buf.frame_or_window = selected_frame; + } + nstored += p->npending; + + mask = sigblock (sigmask (p->sig)); + do + { + buf.code = 0; + kbd_buffer_store_event (&buf); + buf.code = p->sig; + kbd_buffer_store_event (&buf); + p->npending--; + } + while (p->npending > 0); + sigsetmask (mask); + } + + return nstored; +} + + static void menu_bar_item P_ ((Lisp_Object, Lisp_Object, Lisp_Object, void*)); static Lisp_Object menu_bar_one_keymap_changed_items;