[Bug] Crash on SSH connect (use-after-free in idle callback) #13

Closed
opened 2026-09-07 15:50:33 +00:00 by x3 · 0 comments
Owner

Bug: Application crashes when connecting to an SSH server.

Root cause: The IO thread uses g_idle_add() to notify the UI of status changes. If the SshTerminal object is destroyed before the idle callback fires, the callback accesses freed memory (use-after-free).

Timeline:

  1. IO thread calls g_idle_add(callback, self) to queue status notification
  2. disconnect() joins the thread (thread finishes)
  3. Pending idle callback still references self
  4. SshTerminal destructor destroys vte_box_ and frees the object
  5. Idle callback fires - accesses freed self pointer

Fix: In ssh_terminal.cpp, added idle callback flush after thread join in disconnect():

void SshTerminal::disconnect() {
    running_ = false;
    if (thread_) {
        g_thread_join(thread_);
        thread_ = nullptr;
    }
    // Flush pending idle callbacks before cleanup
    while (g_main_context_pending(NULL))
        g_main_context_iteration(NULL, FALSE);
    // ... cleanup ...
}

Also added g_message/g_warning logging to SSH connect, auth, and IO thread operations for better diagnostics.

Status: Fixed in commit fe7050c

**Bug:** Application crashes when connecting to an SSH server. **Root cause:** The IO thread uses `g_idle_add()` to notify the UI of status changes. If the SshTerminal object is destroyed before the idle callback fires, the callback accesses freed memory (use-after-free). Timeline: 1. IO thread calls `g_idle_add(callback, self)` to queue status notification 2. `disconnect()` joins the thread (thread finishes) 3. Pending idle callback still references `self` 4. `SshTerminal` destructor destroys `vte_box_` and frees the object 5. Idle callback fires - accesses freed `self` pointer **Fix:** In `ssh_terminal.cpp`, added idle callback flush after thread join in `disconnect()`: ```cpp void SshTerminal::disconnect() { running_ = false; if (thread_) { g_thread_join(thread_); thread_ = nullptr; } // Flush pending idle callbacks before cleanup while (g_main_context_pending(NULL)) g_main_context_iteration(NULL, FALSE); // ... cleanup ... } ``` Also added `g_message`/`g_warning` logging to SSH connect, auth, and IO thread operations for better diagnostics. **Status:** Fixed in commit fe7050c
x3 closed this issue 2026-09-07 16:58:14 +00:00
Sign in to join this conversation.
No labels
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: x3/x3-ssh#13