terminal: Kill the terminal child process, not the terminal process on exit (#41631)

When rerunning a task, our process id fetching seems to sometimes return
the previous terminal's process id when respawning the task, causing us
to kill the new terminal once the previous one drops as we spawn a new
one, then drop the old one. This results in rerun sometimes spawning a
blank task as the terminal immediately exits. The fix here is simple, we
actually want to kill the process running inside the terminal process,
not the terminal process itself when we exit in the terminal.

No relnotes as this was introduced yesterday in
https://github.com/zed-industries/zed/pull/41562

Release Notes:

- N/A *or* Added/Fixed/Improved ...
This commit is contained in:
Lukas Wirth
2025-10-31 15:01:50 +00:00
committed by GitHub
parent c6d61870e2
commit f73d6fe4ce
3 changed files with 18 additions and 10 deletions
+15 -8
View File
@@ -15,6 +15,12 @@ pub struct ProcessIdGetter {
fallback_pid: u32,
}
impl ProcessIdGetter {
pub fn fallback_pid(&self) -> Pid {
Pid::from_u32(self.fallback_pid)
}
}
#[cfg(unix)]
impl ProcessIdGetter {
fn new(pty: &Pty) -> ProcessIdGetter {
@@ -31,10 +37,6 @@ impl ProcessIdGetter {
}
Some(Pid::from_u32(pid as u32))
}
pub fn fallback_pid(&self) -> u32 {
self.fallback_pid
}
}
#[cfg(windows)]
@@ -66,10 +68,6 @@ impl ProcessIdGetter {
}
Some(Pid::from_u32(pid))
}
pub fn fallback_pid(&self) -> u32 {
self.fallback_pid
}
}
#[derive(Clone, Debug)]
@@ -122,10 +120,19 @@ impl PtyProcessInfo {
}
}
fn get_child(&self) -> Option<&Process> {
let pid = self.pid_getter.fallback_pid();
self.system.process(pid)
}
pub(crate) fn kill_current_process(&mut self) -> bool {
self.refresh().is_some_and(|process| process.kill())
}
pub(crate) fn kill_child_process(&mut self) -> bool {
self.get_child().is_some_and(|process| process.kill())
}
fn load(&mut self) -> Option<ProcessInfo> {
let process = self.refresh()?;
let cwd = process.cwd().map_or(PathBuf::new(), |p| p.to_owned());
+1 -1
View File
@@ -2237,7 +2237,7 @@ unsafe fn append_text_to_term(term: &mut Term<ZedListener>, text_lines: &[&str])
impl Drop for Terminal {
fn drop(&mut self) {
if let TerminalType::Pty { pty_tx, info } = &mut self.terminal_type {
info.kill_current_process();
info.kill_child_process();
pty_tx.0.send(Msg::Shutdown).ok();
}
}
+2 -1
View File
@@ -1141,7 +1141,8 @@ impl Item for TerminalView {
let pid = terminal.pid_getter()?.fallback_pid();
Some(TabTooltipContent::Custom(Box::new(move |_window, cx| {
cx.new(|_| TerminalTooltip::new(title.clone(), pid)).into()
cx.new(|_| TerminalTooltip::new(title.clone(), pid.as_u32()))
.into()
})))
}