From 01ac06c3fd43725ee5e95842eb6cea6477ba9f8e Mon Sep 17 00:00:00 2001 From: Wang Han <416810799@qq.com> Date: Wed, 12 Nov 2025 21:43:02 +0800 Subject: [PATCH] kernel: Prune allowlist only after boot completed For unknown reason, packages.list is not reliable during boot for oplus devices, so we have to disable pruning and re-run pruning after boot. --- kernel/allowlist.c | 6 ++++++ kernel/ksud.c | 2 ++ kernel/pkg_observer.c | 2 +- kernel/throne_tracker.c | 6 +++++- kernel/throne_tracker.h | 2 +- 5 files changed, 15 insertions(+), 3 deletions(-) diff --git a/kernel/allowlist.c b/kernel/allowlist.c index 0cf994eb..914fefe6 100644 --- a/kernel/allowlist.c +++ b/kernel/allowlist.c @@ -15,6 +15,7 @@ #endif #include "klog.h" // IWYU pragma: keep +#include "ksud.h" #include "selinux/selinux.h" #include "allowlist.h" #include "manager.h" @@ -489,6 +490,11 @@ void ksu_prune_allowlist(bool (*is_uid_valid)(uid_t, char *, void *), struct perm_data *np = NULL; struct perm_data *n = NULL; + if (!ksu_boot_completed) { + pr_info("boot not completed, skip prune\n"); + return; + } + bool modified = false; // TODO: use RCU! mutex_lock(&allowlist_mutex); diff --git a/kernel/ksud.c b/kernel/ksud.c index 08b2d5b3..8f093016 100644 --- a/kernel/ksud.c +++ b/kernel/ksud.c @@ -24,6 +24,7 @@ #include "ksud.h" #include "selinux/selinux.h" #include "syscall_hook_manager.h" +#include "throne_tracker.h" bool ksu_module_mounted __read_mostly = false; bool ksu_boot_completed __read_mostly = false; @@ -126,6 +127,7 @@ void on_module_mounted(void){ void on_boot_completed(void){ ksu_boot_completed = true; pr_info("on_boot_completed!\n"); + track_throne(true); // remark process, we don't want to mark other init // forked process excepte zygote and adbd ksu_mark_running_process(); diff --git a/kernel/pkg_observer.c b/kernel/pkg_observer.c index e0641332..b632cd15 100644 --- a/kernel/pkg_observer.c +++ b/kernel/pkg_observer.c @@ -37,7 +37,7 @@ static int ksu_handle_inode_event(struct fsnotify_mark *mark, u32 mask, if (ksu_uid_scanner_enabled) { ksu_request_userspace_scan(); } - track_throne(); + track_throne(false); } return 0; } diff --git a/kernel/throne_tracker.c b/kernel/throne_tracker.c index 0a4fd21a..dc32b795 100644 --- a/kernel/throne_tracker.c +++ b/kernel/throne_tracker.c @@ -427,7 +427,7 @@ static bool is_uid_exist(uid_t uid, char *package, void *data) return exist; } -void track_throne(void) +void track_throne(bool prune_only) { struct list_head uid_list; struct uid_data *np, *n; @@ -504,6 +504,9 @@ void track_throne(void) } uid_ready: + if (prune_only) + goto prune; + // first, check if manager_uid exist! list_for_each_entry(np, &uid_list, list) { if (np->uid == current_manager_uid) { @@ -547,6 +550,7 @@ uid_ready: pr_info("Manager search finished\n"); } +prune: // then prune the allowlist ksu_prune_allowlist(is_uid_exist, &uid_list); out: diff --git a/kernel/throne_tracker.h b/kernel/throne_tracker.h index 5d7f4770..6be7d5f0 100644 --- a/kernel/throne_tracker.h +++ b/kernel/throne_tracker.h @@ -5,6 +5,6 @@ void ksu_throne_tracker_init(); void ksu_throne_tracker_exit(); -void track_throne(); +void track_throne(bool prune_only); #endif