github aeroxy/tunnix 0.3.0
tunnix v0.3.0

7 hours ago

1. High-Level Summary (TL;DR)

  • Impact: High - Introduces a major new feature: the ability to execute remote commands or launch an interactive shell over the existing tunnel.
  • Key Changes:
    • New CLI Subcommand: Added tunnix remote-exec to the client for opening interactive remote sessions.
    • Opt-in Server Security: Added a strict, opt-in --allow-exec configuration on the server to authorize Remote Code Execution (RCE).
    • Protocol Extension: Introduced Exec, Resize, and ExitStatus messages to negotiate PTY sessions and sync terminal dimensions.
    • Unix-only PTY Integration: Integrated portable-pty and nix to handle raw terminal states, PTY allocation, and asynchronous file descriptors.
    • Tunnel Synchronization: Fixed an SSE initialization race condition in tunnel.rs to guarantee the session is fully established before sending connection data.

2. Visual Overview (Code & Logic Map)

flow

3. Detailed Change Analysis

🚀 CLI & Configuration (main.rs, config.rs, reload.rs)

  • What Changed: Added the remote-exec client command to pass arguments, server URL, and authentication. On the server, an explicit --allow-exec flag (or allow_exec = true in config) was added. Without this flag, the server actively rejects execution requests.

Configuration Changes

Key / Flag Old Value New Value Description
allow_exec / --allow-exec N/A false Security gate. Explicitly authorizes the server to spawn a shell for authenticated clients.

🔌 Tunnel Protocol (protocol.rs)

  • What Changed: Extended the base communication protocol to support terminal sessions.

New API Messages

Variant Fields Description
Exec conn_id, cmd, cols, rows, term Requests the server to open a PTY and spawn a process/shell.
Resize conn_id, cols, rows Notifies the server of a client terminal resize event (SIGWINCH).
ExitStatus conn_id, code Relays the child process's final exit code back to the client.

💻 Client-Side Execution (exec.rs)

  • What Changed: A completely new module that orchestrates the local terminal. It forces the terminal into raw mode (RawGuard) to capture direct keystrokes (like Ctrl+C and Ctrl+D) and streams them to the server. It handles SIGWINCH to capture window resize events.
  • Edge Case Handling: When stdin hits EOF, the client synthetically injects a newline (\n) if one is missing before sending the EOF signal (0x04). This is required for the canonical PTY to flush the buffer (Source: exec.rs and documented in wiki/enriched-context.md).

🖥️ Server-Side PTY Relay (server.rs)

  • What Changed: handle_send now provisions a pseudo-terminal using portable_pty. To prevent blocking the async runtime, it converts the blocking file descriptors into non-blocking AsyncFd streams.
  • Watchdog Logic: A dedicated loop monitors the SSE stream connection. If a connection drops continuously for > 6 seconds, the orphaned child process is killed to prevent resource leaks.

⚙️ Tunnel Synchronization (tunnel.rs)

  • What Changed: Hardened the SSE start-up sequence. The tunnel now explicitly blocks until the first valid SSE data frame is received. This mitigates a race condition where the client could fire a POST /send request before the server had completed registering the session via GET /stream.

Dependencies Added (Unix Only)

Package Version Description
libc 0.2 Low-level POSIX bindings.
portable-pty 0.9 Cross-platform (Unix utilized here) PTY allocation.
nix 0.29 Rust-friendly Unix APIs (used for termios and raw mode).
shlex 1.3 Safely shell-quotes arguments when parsing remote-exec inputs.

4. Impact & Risk Assessment

  • ⚠️ Security (God Mode): The --allow-exec flag intentionally grants Remote Code Execution (RCE) to anyone with the server password. Ensure operators fully understand the implications. The server logs a prominent warning at startup when this is active.
  • ⚠️ Data Fidelity: remote-exec operates over a Canonical PTY. It is not safe for binary data transfers. Piping binary data will result in dropped or altered bytes (e.g., EOF newline injection, handling of ^C). Recommend standard TCP tunneling for raw binary streams.
  • Platform Compatibility: This feature is gated strictly behind #[cfg(unix)]. If a client connects to a non-Unix server (or a Unix server without --allow-exec), the server gracefully responds with an explicit error message.

Don't miss a new tunnix release

NewReleases is sending notifications on new releases.