Revert "Restore terminal state on SIGTERM again"

This reverts commit 1d6fa258f6.

This reintroduces commit 941701da3d, which was then reverted in
941701da3d8; this commit reverts the revert to reintroduce 941701da3d.

The reason is that the existing logic in terminal_protocols_disable_ifn does a
bunch of stuff for which nobody has thought about its signal safety, such as
accessing the reader stack (clearly not async signal safe).
Even functions which happen to be safe now may become unsafe in the future.

This is just the nature of signal handling code. We must ensure that only
async-signal safe syscalls are run, and only functions which are themselves
async-signal safe, which we (try) to designate with the "safe_" prefix.
This commit is contained in:
Peter Ammon
2025-07-19 15:35:27 -07:00
parent c7262d6c05
commit 65a4cb5245
3 changed files with 4 additions and 7 deletions

View File

@@ -734,7 +734,7 @@ pub(crate) fn terminal_protocols_disable_ifn() {
}
})
});
let mut out = Outputter::new_from_fd(libc::STDOUT_FILENO);
let mut out = Outputter::stdoutput().borrow_mut();
if BRACKETED_PASTE.load(Ordering::Acquire) {
out.write_command(DecrstBracketedPaste);
if IS_TMUX.load() {

View File

@@ -4,8 +4,7 @@
use crate::common::exit_without_destructors;
use crate::event::{enqueue_signal, is_signal_observed};
use crate::nix::getpid;
use crate::panic::AT_EXIT;
use crate::reader::{reader_handle_sigint, reader_sighup};
use crate::reader::{reader_handle_sigint, reader_sighup, safe_restore_term_mode};
use crate::termsize::TermsizeContainer;
use crate::topic_monitor::{topic_monitor_principal, Generation, GenerationsList, Topic};
use crate::wchar::prelude::*;
@@ -90,9 +89,7 @@ extern "C" fn fish_signal_handler(
libc::SIGTERM => {
// Handle sigterm. The only thing we do is restore the front process ID, then die.
if !observed {
if let Some(at_exit) = AT_EXIT.get() {
(at_exit)();
}
safe_restore_term_mode();
// Safety: signal() and raise() are async-signal-safe.
unsafe {
libc::signal(libc::SIGTERM, libc::SIG_DFL);

View File

@@ -441,7 +441,7 @@ pub struct Outputter {
impl Outputter {
/// Construct an outputter which outputs to a given fd.
/// If the fd is negative, the outputter will buffer its output.
pub const fn new_from_fd(fd: RawFd) -> Self {
const fn new_from_fd(fd: RawFd) -> Self {
Self {
contents: Vec::new(),
buffer_count: 0,