From 7e393f47e4d1438c96a56470e9ec0ad022d1cd58 Mon Sep 17 00:00:00 2001 From: Johannes Altmanninger Date: Sat, 26 Apr 2025 18:49:33 +0200 Subject: [PATCH] Prevent code execution from focus events while blocked on query response While we are waiting for a query response from the terminal, we defer any input processing until we receive our query response Then that response is promoted to the front of the input queue, and remaining inputs are processed in order. We accidentally process focus events, which may run arbitrary code. We can't do this; it breaks a lot of invariants (for example the it can invalidate the cursor positions for CursorPositionQuery, or it can cause fish to exit before fully consumeing a query response). Make sure we only process known-safe events. We definitely need to process CheckExit (in case we received SIGHUP). I guess we should also process Eof, in case the terminal is buggy. --- src/input_common.rs | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/src/input_common.rs b/src/input_common.rs index 6e1601130..acfafe401 100644 --- a/src/input_common.rs +++ b/src/input_common.rs @@ -778,11 +778,15 @@ pub trait InputEventQueuer { /// Return the next event in the queue, or none if the queue is empty. fn try_pop(&mut self) -> Option { if self.is_blocked_querying() { + use ImplicitEvent::*; match self.get_input_data().queue.front()? { - CharEvent::Key(_) | CharEvent::Readline(_) | CharEvent::Command(_) => { + CharEvent::QueryResponse(_) | CharEvent::Implicit(CheckExit | Eof) => {} + CharEvent::Key(_) + | CharEvent::Readline(_) + | CharEvent::Command(_) + | CharEvent::Implicit(_) => { return None; // No code execution while blocked. } - CharEvent::Implicit(_) | CharEvent::QueryResponse(_) => (), } } self.get_input_data_mut().queue.pop_front()