Mercurial > emacs
changeset 83012:4aa172a45af1
Fix C-g handling with multiple ttys.
src/sysdep.c (init_sys_modes): Disable interrupt and quit keys on
secondary terminals. Added a big fat comment about this.
lib-src/emacsclient.c (init_signals): Don't pass SIGINT and SIGQUIT to Emacs.
src/keyboard.c (interrupt_signal): Exit Emacs if there are no frames
on the controlling tty. Otherwise set internal_last_event_frame to
the controlling tty's top frame.
src/term.c (ring_bell, tty_ring_bell): Don't look at updating_frame.
git-archimport-id: lorentey@elte.hu--2004/emacs--multi-tty--0--patch-52
author | Karoly Lorentey <lorentey@elte.hu> |
---|---|
date | Sun, 11 Jan 2004 02:45:44 +0000 |
parents | c4d4cbf86260 |
children | e77d1a63471b |
files | README.multi-tty lib-src/emacsclient.c src/keyboard.c src/sysdep.c src/term.c |
diffstat | 5 files changed, 87 insertions(+), 40 deletions(-) [+] |
line wrap: on
line diff
--- a/README.multi-tty Sun Jan 11 01:18:45 2004 +0000 +++ b/README.multi-tty Sun Jan 11 02:45:44 2004 +0000 @@ -133,14 +133,12 @@ the fly in write_glyphs, which might be problematic, as color approximation is currently done in lisp (term/tty-colors.el).) -** frame-creation-function should always create a frame that is on the - same display as the selected frame. Maybe frame-creation-function - should simply be removed and make-frame changed to do the right - thing. - ** Fix interactive use of temacs. There are face-related SEGVs, most likely because of changes in realize_default_face, realize_face. +** Very strange bug: visible-bell does not work on secondary + terminals. This might be something xterm (konsole) specific. + ** Allow opening an X session after -nw. ** Find out the best way to support suspending Emacs with multiple @@ -149,7 +147,7 @@ extend emacsclient to handle suspend/resume. A `kill -STOP' almost works right now.) -** Exiting Emacs while there are emacsclient frames don't restore the +** Exiting Emacs while there are emacsclient frames doesn't restore the ttys to their default states. ** Move baud_rate to struct display. @@ -182,9 +180,6 @@ why raw terminal support is broken again. I really do need to understand input.) -** Make sure C-g goes to the right frame with ttys. This is hard, as - SIGINT doesn't have a tty parameter. :-( - ** I have seen a case when Emacs with multiple ttys fell into a loop eating 100% of CPU time. Strace showed this loop: @@ -212,7 +207,8 @@ about face problems. This can even lock up Emacs (if the recursive frame sets single_kboard). Update: the face problems are caused by bugs in term.el, not in multi-tty. The lockup is caused by - single_kboard mode. + single_kboard mode, and is not easily solvable. The best thing to + do is to simply refuse to create a tty frame of type `eterm'. DIARY OF CHANGES ---------------- @@ -520,4 +516,26 @@ (Fixed.) +-- frame-creation-function should always create a frame that is on the + same display as the selected frame. Maybe frame-creation-function + should simply be removed and make-frame changed to do the right + thing. + + (Done, with a nice hack. frame-creation-function is now frame-local.) + +-- Fix C-g on raw ttys. + + (Done. I disabled the interrupt/quit keys on all secondary + terminals, so Emacs sees C-g as normal input. This looks like an + overkill, because emacsclient has extra code to pass SIGINT to + Emacs, so C-g should remain the interrupt/quit key on emacsclient + frames. See the next entry why implementing this distinction would + be a bad idea.) + +-- Make sure C-g goes to the right frame with ttys. This is hard, as + SIGINT doesn't have a tty parameter. :-( + + (Done, the previous change fixes this as a pleasant side effect.) + + ;;; arch-tag: 8da1619e-2e79-41a8-9ac9-a0485daad17d
--- a/lib-src/emacsclient.c Sun Jan 11 01:18:45 2004 +0000 +++ b/lib-src/emacsclient.c Sun Jan 11 02:45:44 2004 +0000 @@ -299,8 +299,14 @@ { /* Set up signal handlers. */ signal (SIGWINCH, pass_signal_to_emacs); + + /* Don't pass SIGINT and SIGQUIT to Emacs, because it has no way of + deciding which terminal the signal came from. C-g is now a + normal input event on secondary terminals. */ +#if 0 signal (SIGINT, pass_signal_to_emacs); signal (SIGQUIT, pass_signal_to_emacs); +#endif }
--- a/src/keyboard.c Sun Jan 11 01:18:45 2004 +0000 +++ b/src/keyboard.c Sun Jan 11 02:45:44 2004 +0000 @@ -10279,6 +10279,7 @@ { /* Must preserve main program's value of errno. */ int old_errno = errno; + struct display *display; #if defined (USG) && !defined (POSIX_SIGNALS) /* USG systems forget handlers when they are used; @@ -10287,24 +10288,27 @@ signal (SIGQUIT, interrupt_signal); #endif /* USG */ - if (! tty_list) - { - /* If there are no tty frames, exit Emacs. - - Emacs should exit on SIGINT if and only if there are no - frames on its controlling tty and the signal came from there. - We can check for the first condition, but (alas) not for the - second. The best we can do is that we only exit if we are - sure that the SIGINT was from the controlling tty, i.e., if - there are no termcap frames. - */ + /* See if we have a display on our controlling terminal. */ + display = get_named_tty_display (NULL); + if (!display) + { + /* If there are no frames there, let's pretend that we are a + well-behaving UN*X program and quit. */ Fkill_emacs (Qnil); + } + else + { + /* Otherwise, the SIGINT was probably generated by C-g. */ - errno = old_errno; - return; - } - - handle_interrupt (); + /* Set internal_last_event_frame to the top frame of the + controlling tty, if we have a frame there. We disable the + interrupt key on secondary ttys, so the SIGINT must have come + from the controlling tty. */ + internal_last_event_frame = display->display_info.tty->top_frame; + + handle_interrupt (); + + } errno = old_errno; } @@ -10437,7 +10441,7 @@ } if (waiting_for_input && !echoing) - quit_throw_to_read_char (); + quit_throw_to_read_char (); } /* Handle a C-g by making read_char return C-g. */ @@ -10700,7 +10704,8 @@ only if the current session was a tty session. Now an Emacs session may have multiple display types, so we always handle SIGINT. There is special code in interrupt_signal to exit - Emacs on SIGINT when there are no termcap frames. */ + Emacs on SIGINT when there are no termcap frames on the + controlling terminal. */ signal (SIGINT, interrupt_signal); #if defined (HAVE_TERMIO) || defined (HAVE_TERMIOS) /* For systems with SysV TERMIO, C-g is set up for both SIGINT and
--- a/src/sysdep.c Sun Jan 11 01:18:45 2004 +0000 +++ b/src/sysdep.c Sun Jan 11 02:45:44 2004 +0000 @@ -1453,11 +1453,34 @@ tty.main.c_cflag &= ~PARENB;/* Don't check parity */ } #endif - tty.main.c_cc[VINTR] = quit_char; /* C-g (usually) gives SIGINT */ - /* Set up C-g for both SIGQUIT and SIGINT. - We don't know which we will get, but we handle both alike - so which one it really gives us does not matter. */ - tty.main.c_cc[VQUIT] = quit_char; + if (tty_out->input == stdin) + { + tty.main.c_cc[VINTR] = quit_char; /* C-g (usually) gives SIGINT */ + /* Set up C-g for both SIGQUIT and SIGINT. + We don't know which we will get, but we handle both alike + so which one it really gives us does not matter. */ + tty.main.c_cc[VQUIT] = quit_char; + } + else + { + /* We normally don't get interrupt or quit signals from tty + devices other than our controlling terminal; therefore, + we must handle C-g as normal input. Unfortunately, this + means that the interrupt and quit feature must be + disabled on secondary ttys, or we would not even see the + keypress. + + Note that even though emacsclient could have special code + to pass SIGINT to Emacs, we should _not_ enable + interrupt/quit keys for emacsclient frames. This means + that we can't break out of loops in C code from a + secondary tty frame, but we can always decide what + display the C-g came from, which is more important from a + usability point of view. (Consider the case when two + people work together using the same Emacs instance.) */ + tty.main.c_cc[VINTR] = CDISABLE; + tty.main.c_cc[VQUIT] = CDISABLE; + } tty.main.c_cc[VMIN] = 1; /* Input should wait for at least 1 char */ tty.main.c_cc[VTIME] = 0; /* no matter how long that takes. */ #ifdef VSWTCH
--- a/src/term.c Sun Jan 11 01:18:45 2004 +0000 +++ b/src/term.c Sun Jan 11 02:45:44 2004 +0000 @@ -176,9 +176,7 @@ void ring_bell () { - struct frame *f = (updating_frame - ? updating_frame - : XFRAME (selected_frame)); + struct frame *f = XFRAME (selected_frame); if (!NILP (Vring_bell_function)) { @@ -206,10 +204,7 @@ void tty_ring_bell () { - struct frame *f = (updating_frame - ? updating_frame - : XFRAME (selected_frame)); - + struct frame *f = XFRAME (selected_frame); struct tty_display_info *tty = FRAME_TTY (f); OUTPUT (tty, (tty->TS_visible_bell && visible_bell