feat(termio): port pty, child command spawning, shell integration
Ports the parts of Ghostty's IO layer that don't depend on the terminal: - pty.zig: pty pair, window size, mode, child-side setsid/TIOCSCTTY; master is CLOEXEC with IUTF8 set - Command.zig: fork/execvpe with Ghostty's exact child setup (stdio dup2, best-effort chdir, rlimit restore, os/runtime pre-exec hooks, cgroup handling) and exit status decoding - shell_integration.zig for bash/zsh/fish/elvish/nushell plus feature flags; scripts copied verbatim to resources/shell-integration/ - terminfo generator for xterm-ghostty, byte-identical to Zig's encode output (golden file produced with the real Zig code) This crate opts into unsafe_code = "deny" (fork/exec need it) with allow + SAFETY comments on minimal items. Integration left: config-derived option types are local stand-ins; cgroup D-Bus scope creation is a closure hook; Exec/Termio/Thread/ stream_handler wait for ghostty-terminal. Pty now closes both fds on drop (Zig never auto-closed the slave) - to re-check when wiring Exec. Test Plan: - cargo test -p ghostty-termio (52 tests, incl. real pty spawn test expecting "hi\r\n31 97\r\n" from `echo hi; stty size`)
This commit is contained in:
1 parent
6792799fbe
commit
59bc84fde0
21 files changed
+7120
-28
No files matched your search
@@ -4,10 +4,52 @@ version.workspace = true
|
||||
edition.workspace = true
|
||||
license.workspace = true
|
||||
|
||||
# NOTE: the `ghostty-config` and `ghostty-terminal` dependencies were removed
|
||||
# for now (config is being written concurrently, terminal is in progress).
|
||||
# TODO(integration): re-add them when Exec/Termio/stream_handler are ported and
|
||||
# replace the local stand-ins (shell_integration::{Command, ShellIntegrationFeatures},
|
||||
# command::{LinuxCgroup, GtkSingleInstance}).
|
||||
[dependencies]
|
||||
ghostty-config.workspace = true
|
||||
ghostty-terminal.workspace = true
|
||||
ghostty-os.workspace = true
|
||||
libc = "0.2.190"
|
||||
log = "0.4.34"
|
||||
nix = { version = "0.31.3", features = ["signal"] }
|
||||
rustix = { version = "1.1.5", features = ["fs", "process", "pty", "termios", "stdio"] }
|
||||
thiserror = "2.0.21"
|
||||
|
||||
[lints]
|
||||
workspace = true
|
||||
# Termio forks/execs children and sets up ptys; unsafe is denied by default
|
||||
# and only allowed on minimal, SAFETY-commented items.
|
||||
[lints.rust]
|
||||
unsafe_code = "deny"
|
||||
|
||||
[lints.clippy]
|
||||
pedantic = { level = "warn", priority = -1 }
|
||||
todo = "warn"
|
||||
unwrap_used = "warn"
|
||||
# Porting a low-level terminal emulator involves a lot of intentional
|
||||
# numeric casts and long state-machine functions; these pedantic lints are
|
||||
# noise for this codebase.
|
||||
cast_possible_truncation = "allow"
|
||||
cast_possible_wrap = "allow"
|
||||
cast_sign_loss = "allow"
|
||||
cast_precision_loss = "allow"
|
||||
cast_lossless = "allow"
|
||||
module_name_repetitions = "allow"
|
||||
too_many_lines = "allow"
|
||||
missing_errors_doc = "allow"
|
||||
missing_panics_doc = "allow"
|
||||
similar_names = "allow"
|
||||
struct_excessive_bools = "allow"
|
||||
fn_params_excessive_bools = "allow"
|
||||
match_same_arms = "allow"
|
||||
unreadable_literal = "allow"
|
||||
many_single_char_names = "allow"
|
||||
doc_markdown = "allow"
|
||||
must_use_candidate = "allow"
|
||||
return_self_not_must_use = "allow"
|
||||
used_underscore_binding = "allow"
|
||||
large_stack_arrays = "allow"
|
||||
inline_always = "allow"
|
||||
|
||||
[dev-dependencies]
|
||||
temp-env = "0.3.6"
|
||||
Reference in new issue
Block a user