1
0
mirror of https://github.com/trezor/trezor-firmware.git synced 2025-05-28 19:58:45 +00:00

fix(eckhart): fix last pending char for max len passphrase

This commit is contained in:
Lukas Bielesch 2025-03-19 10:18:20 +01:00 committed by obrusvit
parent 0d7605f3e4
commit 438632c785
3 changed files with 60 additions and 11 deletions

View File

@ -34,12 +34,20 @@ pub enum ButtonState {
const KEYPAD_MAX_KEYS: usize = 10; const KEYPAD_MAX_KEYS: usize = 10;
type KeypadKeys = [Maybe<Button>; KEYPAD_MAX_KEYS]; type KeypadKeys = [Maybe<Button>; KEYPAD_MAX_KEYS];
/// Represents the state of a keypad, including individual button states.
pub struct KeypadState { pub struct KeypadState {
/// State of the "Back" button.
pub back: ButtonState, pub back: ButtonState,
/// State of the "Erase" button.
pub erase: ButtonState, pub erase: ButtonState,
/// State of the "Cancel" button.
pub cancel: ButtonState, pub cancel: ButtonState,
/// State of the "Confirm" button.
pub confirm: ButtonState, pub confirm: ButtonState,
/// Common state of the keypad generic keys.
pub keys: ButtonState, pub keys: ButtonState,
/// Optional override for one key, containing the index and state.
pub override_key: Option<(usize, ButtonState)>,
} }
pub struct Keypad { pub struct Keypad {
@ -167,7 +175,7 @@ impl Keypad {
Self::apply_button_state(&mut self.erase, &state.erase, ctx); Self::apply_button_state(&mut self.erase, &state.erase, ctx);
Self::apply_button_state(&mut self.cancel, &state.cancel, ctx); Self::apply_button_state(&mut self.cancel, &state.cancel, ctx);
Self::apply_button_state(&mut self.confirm, &state.confirm, ctx); Self::apply_button_state(&mut self.confirm, &state.confirm, ctx);
self.set_keys_state(ctx, &state.keys); self.set_keys_state(ctx, &state.keys, state.override_key);
} }
/// Set the content of a key at the specified index. /// Set the content of a key at the specified index.
@ -221,11 +229,31 @@ impl Keypad {
} }
} }
/// Set the state of all key buttons /// Sets the state of all key buttons, except for an optional override key.
pub fn set_keys_state(&mut self, ctx: &mut EventCtx, state: &ButtonState) { pub fn set_keys_state(
for btn in self.keys.iter_mut() { &mut self,
ctx: &mut EventCtx,
state: &ButtonState,
override_key: Option<(usize, ButtonState)>,
) {
// Apply the state to all keys except the override key.
for (idx, btn) in self.keys.iter_mut().enumerate() {
if let Some((override_idx, _)) = override_key {
if override_idx == idx {
continue; // Skip setting the state for the override key
}
}
Self::apply_button_state(btn, state, ctx); Self::apply_button_state(btn, state, ctx);
} }
// Apply the override state if any.
if let Some((override_idx, override_state)) = override_key {
Self::apply_button_state(
self.get_button_mut(&KeypadButton::Key(override_idx)),
&override_state,
ctx,
);
}
} }
/// Set the state of one keypad button. /// Set the state of one keypad button.

View File

@ -210,17 +210,31 @@ impl PassphraseKeyboard {
cancel: ButtonState::Hidden, cancel: ButtonState::Hidden,
confirm: ButtonState::Disabled, confirm: ButtonState::Disabled,
keys: ButtonState::Disabled, keys: ButtonState::Disabled,
override_key: None,
} }
} }
_ => { _ => {
if self.passphrase().len() == MAX_LENGTH { if self.passphrase().len() == MAX_LENGTH {
// Disable all except of confirm and erase buttons if let Some(pending_key) = self.multi_tap.pending_key() {
KeypadState { // Disable all except of confirm, erase and the pending key
back: ButtonState::Hidden, KeypadState {
erase: ButtonState::Enabled, back: ButtonState::Hidden,
cancel: ButtonState::Hidden, erase: ButtonState::Enabled,
confirm: ButtonState::Enabled, cancel: ButtonState::Hidden,
keys: ButtonState::Disabled, confirm: ButtonState::Enabled,
keys: ButtonState::Disabled,
override_key: Some((pending_key, ButtonState::Enabled)),
}
} else {
// Disable all except of confirm and erase buttons
KeypadState {
back: ButtonState::Hidden,
erase: ButtonState::Enabled,
cancel: ButtonState::Hidden,
confirm: ButtonState::Enabled,
keys: ButtonState::Disabled,
override_key: None,
}
} }
} else if self.input.textbox.is_empty() { } else if self.input.textbox.is_empty() {
// Disable all except of confirm and erase buttons // Disable all except of confirm and erase buttons
@ -230,6 +244,7 @@ impl PassphraseKeyboard {
cancel: ButtonState::Hidden, cancel: ButtonState::Hidden,
confirm: ButtonState::Enabled, confirm: ButtonState::Enabled,
keys: ButtonState::Enabled, keys: ButtonState::Enabled,
override_key: None,
} }
} else { } else {
KeypadState { KeypadState {
@ -238,6 +253,7 @@ impl PassphraseKeyboard {
cancel: ButtonState::Hidden, cancel: ButtonState::Hidden,
confirm: ButtonState::Enabled, confirm: ButtonState::Enabled,
keys: ButtonState::Enabled, keys: ButtonState::Enabled,
override_key: None,
} }
} }
} }
@ -292,6 +308,7 @@ impl Component for PassphraseKeyboard {
.last_char_timer .last_char_timer
.start(ctx, Duration::from_secs(LAST_DIGIT_TIMEOUT_S)); .start(ctx, Duration::from_secs(LAST_DIGIT_TIMEOUT_S));
self.input.marker = false; self.input.marker = false;
self.update_keypad_state(ctx);
return None; return None;
} }

View File

@ -73,6 +73,7 @@ impl<'a> PinKeyboard<'a> {
cancel: ButtonState::Hidden, cancel: ButtonState::Hidden,
confirm: ButtonState::Disabled, confirm: ButtonState::Disabled,
keys: ButtonState::Disabled, keys: ButtonState::Disabled,
override_key: None,
} }
} }
_ => { _ => {
@ -84,6 +85,7 @@ impl<'a> PinKeyboard<'a> {
cancel: ButtonState::Hidden, cancel: ButtonState::Hidden,
confirm: ButtonState::Enabled, confirm: ButtonState::Enabled,
keys: ButtonState::Disabled, keys: ButtonState::Disabled,
override_key: None,
} }
} else if self.input.is_empty() { } else if self.input.is_empty() {
KeypadState { KeypadState {
@ -96,6 +98,7 @@ impl<'a> PinKeyboard<'a> {
}, },
confirm: ButtonState::Hidden, confirm: ButtonState::Hidden,
keys: ButtonState::Enabled, keys: ButtonState::Enabled,
override_key: None,
} }
} else { } else {
KeypadState { KeypadState {
@ -104,6 +107,7 @@ impl<'a> PinKeyboard<'a> {
cancel: ButtonState::Hidden, cancel: ButtonState::Hidden,
confirm: ButtonState::Enabled, confirm: ButtonState::Enabled,
keys: ButtonState::Enabled, keys: ButtonState::Enabled,
override_key: None,
} }
} }
} }