fix: C action buffer lengths, byte-faithful callbacks, runtime finalize
Resolves the 8 gaps in docs/rewrite/notes/review-rv10-codex.md (final-Z13.md): - P1 memory safety: the C key-table action (and hovered-link/open-URL payloads) could advertise a length larger than the NUL-truncated allocation. A counted_bytes helper now passes the full bytes plus a trailing NUL with len == byte count, like Zig's backing slices; all C pointer+len structs were audited and tested to read exactly len. - ghostty-bench args follow cli/args.zig (ordered duplicates, empty value resets, first bad value errors, parseBool spellings); the C benchmark tokenizer uses the ArgIteratorGeneral port. - OSC 7 derived titles, desktop notifications and OSC 8 hover links forward raw bytes to the runtime; GTK converts only for display. - C diagnostic getter exports original bytes; escaped surrogates report Utf8CannotEncodeSurrogateHalf; config float formatters print `nan`. - Config::finalize_for(AppRuntime): GTK-only finalization (gtk-single- instance=detect) and termio's cgroup hooks apply only to the GTK runtime, so libghostty keeps `detect` like Zig. Test Plan: - cargo test --workspace --no-fail-fast (exit 0) - cargo test -p ghostty-lib --features test-platform - just check-wasm (macOS/Windows clippy re-run after the concurrent terminal changes land)
This commit is contained in:
1 parent
95fe02b55a
commit
f2ccb04aa4
21 files changed
+479
-133
No files matched your search
@@ -1286,8 +1286,9 @@ impl Application {
|
||||
})
|
||||
}
|
||||
Action::MouseOverLink(v) => {
|
||||
let url = v.url.to_text_lossy();
|
||||
tgt.with_surface_void("mouse over link", |s| {
|
||||
s.set_mouse_hover_url(if v.url.is_empty() { None } else { Some(&v.url) });
|
||||
s.set_mouse_hover_url(if url.is_empty() { None } else { Some(&url) });
|
||||
});
|
||||
true
|
||||
}
|
||||
@@ -1585,26 +1586,28 @@ impl Application {
|
||||
|
||||
fn desktop_notification(&self, tgt: &Tgt, n: &action::DesktopNotification) {
|
||||
if let Some(s) = &tgt.surface {
|
||||
s.send_desktop_notification(&n.title, &n.body);
|
||||
s.send_desktop_notification(&n.title.to_text_lossy(), &n.body.to_text_lossy());
|
||||
return;
|
||||
}
|
||||
|
||||
// Set a default title if we don't already have one
|
||||
let title = if n.title.is_empty() {
|
||||
let n_title = n.title.to_text_lossy();
|
||||
let n_body = n.body.to_text_lossy();
|
||||
let title = if n_title.is_empty() {
|
||||
"Ghostty"
|
||||
} else {
|
||||
n.title.as_str()
|
||||
n_title.as_str()
|
||||
};
|
||||
|
||||
let notification = gio::Notification::new(title);
|
||||
notification.set_body(Some(&n.body));
|
||||
notification.set_body(Some(&n_body));
|
||||
notification.set_icon(&gio::ThemedIcon::new("com.mitchellh.ghostty"));
|
||||
notification
|
||||
.set_default_action_and_target_value("app.present-surface", Some(&0u64.to_variant()));
|
||||
|
||||
// We set the notification ID to the body content. If the content is
|
||||
// the same, this notification may replace a previous notification.
|
||||
self.send_notification(Some(&n.body), ¬ification);
|
||||
self.send_notification(Some(&n_body), ¬ification);
|
||||
}
|
||||
|
||||
fn goto_split(surface: &Surface, to: action::GotoSplit) -> bool {
|
||||
|
||||
Reference in new issue
Block a user