fix(core): fix missing TOUCH_END in touch driver
What changed, and why it matters
This commit fixes a touch-screen driver bug in Trezor hardware wallets where a finger lift (TOUCH_END event) could be lost. The symptom was 'stuck hold-to-confirm buttons' on some models. In practice, a missing release event could make the device think a finger was still held on the screen, potentially causing an unintended confirmation action or leaving the UI in a confused state. The patch is small and defensive, adding a state-machine correction rather than changing large amounts of code.
Treat as a low-to-moderate reliability fix. Include in the next firmware release for affected models. If hold-to-confirm is used for high-value actions, consider adding a redundant timeout or release check in the UI layer so a stuck driver state cannot alone cause confirmation. No emergency response is indicated because exploitation requires physical touch interaction and the bug appears to cause UI confusion rather than a deterministic bypass.
Security signals we found
Missing input event in a safety-critical confirmation path (hold-to-confirm)
Finite-state-machine transition bug that could cause a stuck or spurious confirmation state
User-interface state desynchronization between physical touch and firmware state
No explicit security framing by the vendor; classified as a functional/touch bug
Evidence from the diff
In core/embed/io/touch/touch_poll.c, the touch finite-state machine (touch_fsm_get_event) can miss a TOUCH_END when it sees a new TOUCH_START while still in the TOUCH_END state. The fix sets touch_state to the newly generated TOUCH_START | xy event so the next driver iteration will detect the transition and emit the matching TOUCH_END. A debug print was also switched from printf to dbg_printf with different format specifiers. The changelog notes the user-visible effect as ‘stuck hold-to-confirm buttons’ on T2T1, T3T1, and T3W1 models.
Changed components
core/embed/io/touch/touch_poll.cTrezor Model T (T2T1), Safe 3 (T3T1), Safe 3 Plus (T3W1) touch input stackHold-to-confirm UI gesture handlingInspect captured patch +7 / −2
diff --git a/core/.changelog.d/6075.fixed b/core/.changelog.d/6075.fixed
new file mode 100644
index 000000000..e2d101bb9
--- /dev/null
+++ b/core/.changelog.d/6075.fixed
@@ -0,0 +1 @@
+[T2T1,T3T1,T3W1] Fixed touch issue causing stuck hold-to-confirm buttons.
diff --git a/core/embed/io/touch/touch_poll.c b/core/embed/io/touch/touch_poll.c
index cfd89f97a..0ebcc7a9a 100644
--- a/core/embed/io/touch/touch_poll.c
+++ b/core/embed/io/touch/touch_poll.c
@@ -79,8 +79,8 @@ void trace_event(uint32_t event) {
systask_id_t task_id = systask_id(systask_active());
- printf("%04ld [task=%d, event=%c, x=%3d, y=%3d]\r\n", time, task_id,
- event_type, x, y);
+ dbg_printf("%d [task=%d, event=%c, x=%d, y=%d]\r\n", time, task_id,
+ event_type, x, y);
}
#endif
@@ -136,6 +136,10 @@ uint32_t touch_fsm_get_event(touch_fsm_t* fsm, uint32_t touch_state) {
// This suggests that the previous touch was very short,
// or/and the driver is not called very frequently.
event = TOUCH_START | xy;
+
+ // We have to remember "false" touch state to convince
+ // the state machine to signal the TOUCH_END event next.
+ touch_state = event;
} else {
// Either the driver is starving or the coordinates
// have not changed, which would suggest that the TOUCH_END
Why this scored 42/100
Community notes
Notes can correct, qualify, or add evidence to the AI analysis. Every note shown here has been validated by a human moderator.
The AI analysis stands alone for now. Submit a note if you can add evidence or important context.