Files
ddidderr f4c020101c fix: close remaining gaps found by the completeness audit
Addresses the partial ports listed in
docs/rewrite/notes/review-completeness-codex.md (details in
docs/rewrite/notes/gaps-X2.md):
- Flatpak: the exit watcher no longer consumes the host command; a
  shared FlatpakSignalHandle lets closing a surface still SIGHUP the
  host process group.
- Child environment is byte-preserving end to end (ghostty_os::EnvMap
  of OsStrings) and Snap paths are filtered like filterSnapPaths.
- argv handling no longer panics on non-UTF-8 arguments.
- URI percent-decoding keeps raw bytes; OSC 7 pwd is passed through
  without lossy conversion.
- Keybinding comparison/hashing uses full Unicode case folding from a
  table generated from CaseFolding.txt (Unicode 17.0.0).
- Link regexes set Oniguruma's whole-search retry limit through the new
  minimal ghostty-onig crate (one SAFETY-commented FFI call).
- OSC 9 NUL-capacity check ordering matches Zig.
- Wayland registry binds/clears globals advertised after startup.
- Custom shaders may pass sampler2D to helper functions (naga adapter).
- +list-themes preview renders OSC 8 links, styled underlines and
  follows color-scheme reports.

Also includes the inspector's integration edits in shared files
(renderer state hook, termio VT recording, core/apprt-gtk wiring), X1's
config/input/cli additions for completion generation, and a fix for a
race in the termio backpressure test (it wrote before `stty raw`
applied, so the cooked line discipline dropped bytes past MAX_CANON).

Test Plan:
- cargo test --workspace
- cargo clippy --workspace --all-targets -- -D warnings
2026-10-12 04:39:24 +02:00

4.6 KiB

Gap fixes X2 (partial ports)

# Item Status
1 Flatpak exit watcher consumed the command Fixed. ghostty_os::flatpak::FlatpakSignalHandle (FlatpakHostCommand::signal_handle(), shares the Arc<Shared> state); termio/exec.rs keeps it so stop() still SIGHUPs the host process group after wait_callback takes the command. Test: signal_handle_survives_wait_callback (real DBus path not testable here).
2 Child env byte-preserving + filterSnapPaths Fixed. New ghostty_os::EnvMap (OsString keys/values); get_env_map(), RtSurface::default_termio_env, core rt_surface_env, shell_integration::EnvMap, Command.env/Subprocess.env, append_env_os/prepend_env_os are all byte-preserving; GTK default_termio_env no longer uses std::env::vars(). ghostty_os::filter_snap_paths ported; applied when SNAP is set (Zig gates on the compile-time snap option). Flatpak HostCommand (a{ss}) can only carry UTF-8, so env is lossily converted at that DBus boundary only. config.env (RepeatableStringMap) remains String (config values).
3 Root main.rs argv Fixed. ghostty_os::args::collect_lossy() (args_os based) used by src/main.rs, ghostty_config::cli_args::args_iterator, ghostty_cli::action::detect_args. Downstream CLI/config parsing is String based, so a non-UTF-8 arg becomes U+FFFD instead of panicking (not byte-exact end-to-end).
4 os/uri.rs percent-decoding Fixed. Component::to_raw_bytes() (lossless), to_raw() is a lossy text view, new uri::parse_bytes (handles non-UTF-8 input incl. raw_path). OSC 7 (termio/stream_handler.rs) uses bytes for set_pwd and the pwd surface message; only the window-title fallback is lossy.
5 Keybinding Unicode case folding Fixed. ucd/CaseFolding.txt (17.0.0, from uucode-0.2.0) vendored; build.rs generates CASE_FOLDING_FULL (status C+F); API ghostty_unicode::case_folding::{lookup, fold_full}; input/binding::folded_codepoint uses it (hash and folded_equal).
6 StringMap whole-search retry limit Fixed. onig 6.5.3 only wraps retry-limit-in-match; onig_sys exposes onig_set_retry_limit_in_search_of_match_param. New crate crates/ghostty-onig (unsafe_code = "deny", one SAFETY-commented call) provides set_retry_limit_in_search; string_map.rs now sets only that limit, like Zig. Tests in both crates (catastrophic regex aborts).
7 osc9 NUL reservation order Fixed. Parser::reserve_nul(); osc9 uses buffered() and reserves only in branches where Zig calls writeByte(0) (11, 2, 3, 6, 7, 8, 9 and the notification fallback). Tests for full-buffer behaviour.
8 Wayland registry add/remove Fixed in winproto/wayland.rs only: the registry Dispatch now binds newly advertised supported globals (blur, decoration manager, slide, xdg-activation; xdg_wm_dialog_v1 flag) and clears/destroys removed ones, tracked by registry name (bound_names; Zig compares object id to name, which looks like an upstream quirk). Binds version 1 as the existing init does. No unit test (needs a compositor).
9 shadertoy sampler2D helpers Fixed. renderer/src/shadertoy_sampler.rs token-level rewrite: sampler2D params -> texture2D x_tex, sampler x_smp, uses in bodies -> sampler2D(x_tex, x_smp), call args x/iChannel0 -> pairs, forwarding and prototypes work, texture2D( -> texture( (the prefix macro would clash with the type). Prefix-only rewrites no longer touch user text. Tests incl. textureSize/texelFetch/textureLod. Remaining limits: sampler args must be plain identifiers (no ternary/struct member), no sampler locals/arrays/struct fields, only sampler2D (iChannel1-3 are unused upstream).
10 +list-themes preview Fixed. OSC 8 file:// hyperlinks (list entries, header name/path, error path) and double/dashed/dotted/curly underlines are recorded during draw and re-emitted as raw escapes after each ratatui flush (Overlay, render_overlays); popups drop covered overlays. Input moved from crossterm to termina (drawing still ratatui+crossterm backend) so `CSI ? 997 ; 1

Gate: build/test/clippy/fmt pass for ghostty-{os,termio,input,unicode,vt,terminal,onig,renderer,cli,config,core,apprt}. ghostty-inspector (another agent) currently fails clippy and blocks workspace-wide clippy -D warnings; it also makes clippy of crates depending on it unreliable (checked with warnings visible: none in X2 files).