diff --git a/src/builtins/bind.rs b/src/builtins/bind.rs index 69c1d2f86..0912476b5 100644 --- a/src/builtins/bind.rs +++ b/src/builtins/bind.rs @@ -7,10 +7,9 @@ use crate::highlight::{colorize, highlight_shell}; use crate::input::{ input_function_get_names, input_mappings, input_terminfo_get_name, input_terminfo_get_names, - input_terminfo_get_sequence, InputMappingSet, + input_terminfo_get_sequence, GetSequenceError, InputMappingSet, }; use crate::nix::isatty; -use nix::errno::Errno; use std::sync::MutexGuard; const DEFAULT_BIND_MODE: &wstr = L!("default"); @@ -195,35 +194,27 @@ fn function_names(&self, streams: &mut IoStreams) { /// Wraps input_terminfo_get_sequence(), appending the correct error messages as needed. fn get_terminfo_sequence(&self, seq: &wstr, streams: &mut IoStreams) -> Option { - let mut tseq = WString::new(); - if input_terminfo_get_sequence(seq, &mut tseq) { - return Some(tseq); - } - let err = Errno::last(); - - if !self.opts.silent { - let eseq = escape_string(seq, EscapeStringStyle::Script(EscapeFlags::NO_PRINTABLES)); - if err == Errno::ENOENT { - streams.err.append(wgettext_fmt!( - "%ls: No key with name '%ls' found\n", - "bind", - eseq - )); - } else if err == Errno::EILSEQ { - streams.err.append(wgettext_fmt!( - "%ls: Key with name '%ls' does not have any mapping\n", - "bind", - eseq - )); - } else { - streams.err.append(wgettext_fmt!( - "%ls: Unknown error trying to bind to key named '%ls'\n", - "bind", - eseq - )); + match input_terminfo_get_sequence(seq) { + Ok(tseq) => Some(tseq), + Err(err) if !self.opts.silent => { + let eseq = + escape_string(seq, EscapeStringStyle::Script(EscapeFlags::NO_PRINTABLES)); + match err { + GetSequenceError::NotFound => streams.err.append(wgettext_fmt!( + "%ls: No key with name '%ls' found\n", + "bind", + eseq + )), + GetSequenceError::NoSeq => streams.err.append(wgettext_fmt!( + "%ls: Key with name '%ls' does not have any mapping\n", + "bind", + eseq + )), + }; + None } + Err(_) => None, } - None } /// Add specified key binding. diff --git a/src/input.rs b/src/input.rs index 072e5d46e..b4e110902 100644 --- a/src/input.rs +++ b/src/input.rs @@ -14,7 +14,6 @@ use crate::signal::signal_clear_cancel; use crate::threads::assert_is_main_thread; use crate::wchar::prelude::*; -use errno::{set_errno, Errno}; use once_cell::sync::{Lazy, OnceCell}; use std::cell::RefCell; use std::collections::VecDeque; @@ -1120,29 +1119,33 @@ macro_rules! terminfo_add { ]); } +/// Possible errors from from input_terminfo_get_sequence. +pub enum GetSequenceError { + /// The mapping was not found. + NotFound, + /// The terminfo variable does not have a value. + NoSeq, +} + /// Return the sequence for the terminfo variable of the specified name. /// /// If no terminfo variable of the specified name could be found, return false and set errno to /// ENOENT. If the terminfo variable does not have a value, return false and set errno to EILSEQ. -pub fn input_terminfo_get_sequence(name: &wstr, out_seq: &mut WString) -> bool { - // TODO: stop using errno for this. +pub fn input_terminfo_get_sequence(name: &wstr) -> Result { let mappings = TERMINFO_MAPPINGS .get() .expect("TERMINFO_MAPPINGS not initialized"); for m in mappings.iter() { if name == m.name { // Found the mapping. - if m.seq.is_none() { - set_errno(Errno(libc::EILSEQ)); - return false; + return if let Some(seq) = &m.seq { + Ok(str2wcstring(seq)) } else { - *out_seq = str2wcstring(m.seq.as_ref().unwrap()); - return true; - } + Err(GetSequenceError::NoSeq) + }; } } - set_errno(Errno(libc::ENOENT)); - false + Err(GetSequenceError::NotFound) } /// Return the name of the terminfo variable with the specified sequence.