fix(launcher,lock): §310 锁屏/叠加三连 bug——输入穿透·状态栏消失·App死亡残影

用户真机 M6.2 实测三症状,全部位于锁屏/通知中心叠加路径。根因与修法:

S1 锁屏输入穿透(PIN 触摸打到下层 App / 解锁后「启动奇怪界面」)
  根因:run_app_lock_overlay / run_app_notif_overlay 关闭路径先 unlink
  /tmp/meow_notif_active 再 SIGCONT App——App 被 SIGSTOP 冻结期间缓冲的 evdev
  触摸事件在解除瞬间被 SDK 输入线程在无隔离态回放成 App 内点击(穿透触发)。
  修法:反序——标记仍在时先 SIGCONT,让 SDK 输入线程排空冻结期缓冲事件 +
  EVIOCGKEY 对齐,等 OVERLAY_DRAIN_WINDOW_MS(300ms > SDK 200ms 节流) 再 unlink。

S2 解锁后状态栏消失(App 无状态栏全屏残留)
  根因:S1 的回放点击常把 App 导航进全屏页(状态栏随 app.json/fullscreen 隐掉);
  叠加关闭路径也未强制状态栏重同步。
  修法:解锁后 g_sb_mode_last=-1 + 立即 app_overlay_statusbar() 重叠加(不等 1s 慢刷)。

S3 App 异常死亡(OOM sig=9)残影——fb0 停 App 死帧、无状态栏、launcher 不重绘主屏
  根因:锁屏叠加(run_app_lock_overlay→run_lock_screen)阻塞于 lock_screen 内,
  App 叠加期崩溃不被感知(notif 叠加有 run_notif_center 的 proc_is_zombie 探测,
  锁屏独缺),launcher 卡在锁屏会话永不回 menu 重绘。
  修法:run_app_lock_overlay 置位 g_lock_overlay_pid,run_lock_screen 每圈
  proc_is_zombie 探测,App 死即中止锁屏(LCK_OVERLAY_RET_DIED)走统一退出路径
  (reap_wait 回收 + ams_status_valid + break → run_menu 重绘主屏含状态栏)。

新增 overlay_gate.h(纯决策,宿主可单测)+ test_overlay_gate.c(10 断言)+
test_lock_screen.c 扩展(4 断言 overlay-abort)。launcher 全量宿主回归 +
SDK 叠加/状态栏回归(overlay_suppress/sb_collapse/notif_open/notif_gesture/
sdk_fixes/sdk_input_keys)全 PASS;mipsel 交叉 -Wall -Wextra 0 warning。
md5 136dc67c086a9d75c0ad9c83d519ff0d(/usr/bin 只读,待固件打包;fw_content.conf 未动)。
This commit is contained in:
AskaEth committed 2026-09-02 03:41:39 +08:00
1 parent 3611cbbbde
commit bcef8e092e
8 files changed
+203 -11

No files matched your search

@@ -75,6 +75,14 @@ int main(void)
meow_settings_save();
CHECK(lck_wake_should_lock() == 1, "wake_should_lock=1 (wake=1)");
/* ---- §310 残影:锁屏叠加期 App 崩溃中止探针(纯判定)----
* 锁屏在 App 前台叠加会话(overlay_pid>0)且该 App 已成僵尸 → 中止锁屏(返回 1);
* 菜单直接锁屏(overlay_pid=0)恒不中止;叠加期 App 仍活(proc_zombie=0)也不中止。 */
CHECK(lck_overlay_should_abort(0, 0) == 0, "overlay abort=0 (no overlay pid, not zombie)");
CHECK(lck_overlay_should_abort(1234, 0) == 0, "overlay abort=0 (overlay pid, app alive)");
CHECK(lck_overlay_should_abort(0, 1) == 0, "overlay abort=0 (no overlay pid, zombie ignored)");
CHECK(lck_overlay_should_abort(1234, 1) == 1, "overlay abort=1 (overlay pid + zombie -> unified exit)");
/* ---- 面板一次性解锁恢复口(bypass 标志)---- */
CHECK(lck_unlock_once_consume() == 0, "unlock_once_consume=0 when flag absent");
{