diff --git a/Cargo.lock b/Cargo.lock index be2d6970..76682e24 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -2787,7 +2787,6 @@ dependencies = [ "crossterm 0.29.0", "git2", "inquire", - "libc", "pretty_assertions", "radicle-signals", "shlex", diff --git a/crates/radicle-remote-helper/src/lib.rs b/crates/radicle-remote-helper/src/lib.rs index b24a4ed0..bdc541b2 100644 --- a/crates/radicle-remote-helper/src/lib.rs +++ b/crates/radicle-remote-helper/src/lib.rs @@ -90,7 +90,7 @@ pub struct Options { pub fn run(profile: radicle::Profile) -> Result<(), Error> { // Since we're going to be writing user output to `stderr`, make sure the paint // module is aware of that. - cli::Paint::set_terminal(io::stderr()); + cli::Paint::set_terminal(cli::TerminalFile::Stderr); let (remote, url): (Option, Url) = { let args = env::args().skip(1).take(2).collect::>(); diff --git a/crates/radicle-term/Cargo.toml b/crates/radicle-term/Cargo.toml index 2de7e2a9..c2653eb9 100644 --- a/crates/radicle-term/Cargo.toml +++ b/crates/radicle-term/Cargo.toml @@ -17,7 +17,6 @@ anyhow = { workspace = true } anstyle-query = "1.0.0" crossterm = "0.29.0" inquire = { version = "0.7.4", default-features = false, features = ["crossterm", "editor"] } -libc = { workspace = true } shlex = { workspace = true } thiserror = { workspace = true } unicode-display-width = "0.3.0" diff --git a/crates/radicle-term/src/ansi.rs b/crates/radicle-term/src/ansi.rs index e3e168ff..00ea7d7d 100644 --- a/crates/radicle-term/src/ansi.rs +++ b/crates/radicle-term/src/ansi.rs @@ -13,4 +13,5 @@ pub use color::Color; pub use paint::paint; pub use paint::Filled; pub use paint::Paint; +pub use paint::TerminalFile; pub use style::Style; diff --git a/crates/radicle-term/src/ansi/paint.rs b/crates/radicle-term/src/ansi/paint.rs index 0926abb3..5ed8a11b 100644 --- a/crates/radicle-term/src/ansi/paint.rs +++ b/crates/radicle-term/src/ansi/paint.rs @@ -1,5 +1,4 @@ use std::io::IsTerminal as _; -use std::os::fd::{AsRawFd, BorrowedFd}; use std::sync::atomic::{AtomicBool, AtomicI32}; use std::sync::LazyLock; use std::{fmt, sync}; @@ -7,8 +6,36 @@ use std::{fmt, sync}; use super::color::Color; use super::style::{Property, Style}; +#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] +#[repr(i32)] +pub enum TerminalFile { + Stdout = 1, + Stderr = 2, +} + +impl TryFrom for TerminalFile { + type Error = (); + + fn try_from(value: i32) -> Result { + match value { + 1 => Ok(TerminalFile::Stdout), + 2 => Ok(TerminalFile::Stderr), + _ => Err(()), + } + } +} + +impl TerminalFile { + fn is_terminal(&self) -> bool { + match self { + TerminalFile::Stdout => std::io::stdout().is_terminal(), + TerminalFile::Stderr => std::io::stderr().is_terminal(), + } + } +} + /// What file is used for text output. -static TERMINAL: AtomicI32 = AtomicI32::new(libc::STDOUT_FILENO); +static TERMINAL: AtomicI32 = AtomicI32::new(TerminalFile::Stdout as i32); /// Whether paint styling is enabled or not. static ENABLED: AtomicBool = AtomicBool::new(true); /// Whether paint styling should be forced. @@ -263,7 +290,7 @@ impl Paint<()> { let clicolor_enabled = clicolor.unwrap_or(false); let clicolor_disabled = !clicolor.unwrap_or(true); let terminal = TERMINAL.load(sync::atomic::Ordering::SeqCst); - let is_terminal = unsafe { BorrowedFd::borrow_raw(terminal).is_terminal() }; + let is_terminal = TerminalFile::try_from(terminal).is_ok_and(|tf| tf.is_terminal()); let is_enabled = ENABLED.load(sync::atomic::Ordering::SeqCst); is_terminal @@ -287,8 +314,8 @@ impl Paint<()> { /// Set the terminal we are writing to. This influences the logic that checks whether or not to /// include colors. - pub fn set_terminal(fd: impl AsRawFd) { - TERMINAL.store(fd.as_raw_fd(), sync::atomic::Ordering::SeqCst); + pub fn set_terminal(tf: TerminalFile) { + TERMINAL.store(tf as i32, sync::atomic::Ordering::SeqCst); } /// Force paint styling. diff --git a/crates/radicle-term/src/lib.rs b/crates/radicle-term/src/lib.rs index 7102da48..80f93f99 100644 --- a/crates/radicle-term/src/lib.rs +++ b/crates/radicle-term/src/lib.rs @@ -17,7 +17,7 @@ use std::fmt; use std::io::IsTerminal; pub use ansi::Color; -pub use ansi::{paint, Filled, Paint, Style}; +pub use ansi::{paint, Filled, Paint, Style, TerminalFile}; pub use editor::Editor; pub use element::{Constraint, Element, Line, Size}; pub use hstack::HStack;