Add Zygisk API getFlags()

This commit is contained in:
topjohnwu
2022-01-17 19:54:33 -08:00
parent 76ddfeb93a
commit bb7a74e4b4
11 changed files with 173 additions and 82 deletions
+30 -24
View File
@@ -26,7 +26,7 @@ static bool unhook_functions();
namespace {
enum {
UNMOUNT_FLAG,
DO_UNMOUNT,
FORK_AND_SPECIALIZE,
APP_SPECIALIZE,
SERVER_SPECIALIZE,
@@ -46,12 +46,13 @@ struct HookContext {
void *raw_args;
};
const char *process;
int pid;
bitset<FLAG_MAX> flags;
AppInfo info;
vector<ZygiskModule> modules;
bitset<FLAG_MAX> state;
HookContext() : pid(-1), info{} {}
int pid;
uint32_t flags;
HookContext() : pid(-1), flags(0) {}
static void close_fds();
void unload_zygisk();
@@ -154,7 +155,7 @@ DCL_HOOK_FUNC(int, fork) {
DCL_HOOK_FUNC(int, unshare, int flags) {
int res = old_unshare(flags);
if (g_ctx && (flags & CLONE_NEWNS) != 0 && res == 0) {
if (g_ctx->flags[UNMOUNT_FLAG]) {
if (g_ctx->state[DO_UNMOUNT]) {
revert_unmount();
} else {
umount2("/system/bin/app_process64", MNT_DETACH);
@@ -174,7 +175,7 @@ DCL_HOOK_FUNC(void, android_log_close) {
DCL_HOOK_FUNC(int, selinux_android_setcontext,
uid_t uid, int isSystemServer, const char *seinfo, const char *pkgname) {
if (g_ctx) {
g_ctx->flags[CAN_DLCLOSE] = unhook_functions();
g_ctx->state[CAN_DLCLOSE] = unhook_functions();
}
return old_selinux_android_setcontext(uid, isSystemServer, seinfo, pkgname);
}
@@ -297,6 +298,7 @@ bool ZygiskModule::RegisterModule(ApiTable *table, long *module) {
switch (ver) {
case 2:
table->v2.getModuleDir = [](ZygiskModule *m) { return m->getModuleDir(); };
table->v2.getFlags = [](auto) { return ZygiskModule::getFlags(); };
[[fallthrough]];
case 1:
table->v1.hookJniNativeMethods = &hookJniNativeMethods;
@@ -345,7 +347,7 @@ void ZygiskModule::setOption(zygisk::Option opt) {
return;
switch (opt) {
case zygisk::FORCE_DENYLIST_UNMOUNT:
g_ctx->flags[UNMOUNT_FLAG] = true;
g_ctx->state[DO_UNMOUNT] = true;
break;
case zygisk::DLCLOSE_MODULE_LIBRARY:
unload = true;
@@ -353,6 +355,10 @@ void ZygiskModule::setOption(zygisk::Option opt) {
}
}
uint32_t ZygiskModule::getFlags() {
return g_ctx ? (g_ctx->flags & ~PRIVATE_MASK) : 0;
}
void HookContext::run_modules_pre(const vector<int> &fds) {
char buf[256];
@@ -384,9 +390,9 @@ void HookContext::run_modules_pre(const vector<int> &fds) {
for (auto &m : modules) {
m.entry(&m.api, env);
if (flags[APP_SPECIALIZE]) {
if (state[APP_SPECIALIZE]) {
m.preAppSpecialize(args);
} else if (flags[SERVER_SPECIALIZE]) {
} else if (state[SERVER_SPECIALIZE]) {
m.preServerSpecialize(server_args);
}
}
@@ -403,9 +409,9 @@ void HookContext::run_modules_pre(const vector<int> &fds) {
void HookContext::run_modules_post() {
for (const auto &m : modules) {
if (flags[APP_SPECIALIZE]) {
if (state[APP_SPECIALIZE]) {
m.postAppSpecialize(args);
} else if (flags[SERVER_SPECIALIZE]) {
} else if (state[SERVER_SPECIALIZE]) {
m.postServerSpecialize(server_args);
}
m.doUnload();
@@ -417,7 +423,7 @@ void HookContext::close_fds() {
}
void HookContext::unload_zygisk() {
if (flags[CAN_DLCLOSE]) {
if (state[CAN_DLCLOSE]) {
// Do NOT call the destructor
operator delete(jni_method_map);
// Directly unmap the whole memory block
@@ -436,19 +442,19 @@ void HookContext::unload_zygisk() {
void HookContext::nativeSpecializeAppProcess_pre() {
g_ctx = this;
flags[APP_SPECIALIZE] = true;
state[APP_SPECIALIZE] = true;
process = env->GetStringUTFChars(args->nice_name, nullptr);
if (flags[FORK_AND_SPECIALIZE]) {
if (state[FORK_AND_SPECIALIZE]) {
ZLOGV("pre forkAndSpecialize [%s]\n", process);
} else {
ZLOGV("pre specialize [%s]\n", process);
}
auto module_fds = remote_get_info(args->uid, process, &info);
if (info.on_denylist) {
auto module_fds = remote_get_info(args->uid, process, &flags);
if ((flags & UNMOUNT_MASK) == UNMOUNT_MASK) {
// TODO: Handle MOUNT_EXTERNAL_NONE on older platforms
ZLOGI("[%s] is on the denylist\n", process);
flags[UNMOUNT_FLAG] = true;
state[DO_UNMOUNT] = true;
} else {
run_modules_pre(module_fds);
}
@@ -458,7 +464,7 @@ void HookContext::nativeSpecializeAppProcess_pre() {
}
void HookContext::nativeSpecializeAppProcess_post() {
if (flags[FORK_AND_SPECIALIZE]) {
if (state[FORK_AND_SPECIALIZE]) {
ZLOGV("post forkAndSpecialize [%s]\n", process);
} else {
ZLOGV("post specialize [%s]\n", process);
@@ -466,21 +472,21 @@ void HookContext::nativeSpecializeAppProcess_post() {
env->ReleaseStringUTFChars(args->nice_name, process);
run_modules_post();
if (info.is_magisk_app) {
if (flags & PROCESS_IS_MAGISK_APP) {
setenv("ZYGISK_ENABLED", "1", 1);
}
g_ctx = nullptr;
if (!flags[FORK_AND_SPECIALIZE]) {
if (!state[FORK_AND_SPECIALIZE]) {
unload_zygisk();
}
}
void HookContext::nativeForkSystemServer_pre() {
fork_pre();
flags[SERVER_SPECIALIZE] = true;
state[SERVER_SPECIALIZE] = true;
if (pid == 0) {
ZLOGV("pre forkSystemServer\n");
run_modules_pre(remote_get_info(1000, "system_server", &info));
run_modules_pre(remote_get_info(1000, "system_server", &flags));
close_fds();
android_logging();
}
@@ -496,7 +502,7 @@ void HookContext::nativeForkSystemServer_post() {
void HookContext::nativeForkAndSpecialize_pre() {
fork_pre();
flags[FORK_AND_SPECIALIZE] = true;
state[FORK_AND_SPECIALIZE] = true;
if (pid == 0) {
nativeSpecializeAppProcess_pre();
}