diff --git a/jni/core/bootstages.c b/jni/core/bootstages.c index df512a24f..ba4c8bf33 100644 --- a/jni/core/bootstages.c +++ b/jni/core/bootstages.c @@ -24,7 +24,6 @@ static char *buf, *buf2; static struct vector module_list; -static int seperate_vendor = 0; extern char **environ; @@ -395,102 +394,6 @@ static void simple_mount(const char *path) { * Miscellaneous * *****************/ -// A one time setup -static void daemon_init() { - LOGI("* Creating /sbin overlay"); - DIR *dir; - struct dirent *entry; - int root, sbin; - // Setup links under /sbin - xmount(NULL, "/", NULL, MS_REMOUNT, NULL); - xmkdir("/root", 0755); - chmod("/root", 0755); - root = xopen("/root", O_RDONLY | O_CLOEXEC); - sbin = xopen("/sbin", O_RDONLY | O_CLOEXEC); - dir = xfdopendir(sbin); - while((entry = xreaddir(dir))) { - if (strcmp(entry->d_name, ".") == 0 || strcmp(entry->d_name, "..") == 0) continue; - linkat(sbin, entry->d_name, root, entry->d_name, 0); - if (strcmp(entry->d_name, "magisk") == 0) - unlinkat(sbin, entry->d_name, 0); - } - close(sbin); - xmount("tmpfs", "/sbin", "tmpfs", 0, NULL); - sbin = xopen("/sbin", O_RDONLY | O_CLOEXEC); - fchmod(sbin, 0755); - fsetfilecon(sbin, "u:object_r:rootfs:s0"); - dir = xfdopendir(root); - while((entry = xreaddir(dir))) { - if (strcmp(entry->d_name, ".") == 0 || strcmp(entry->d_name, "..") == 0) continue; - snprintf(buf, PATH_MAX, "/root/%s", entry->d_name); - snprintf(buf2, PATH_MAX, "/sbin/%s", entry->d_name); - xsymlink(buf, buf2); - } - for (int i = 0; applet[i]; ++i) { - snprintf(buf2, PATH_MAX, "/sbin/%s", applet[i]); - xsymlink("/root/magisk", buf2); - } - xsymlink(MOUNTPOINT, FAKEPOINT); - close(root); - close(sbin); - xmount(NULL, "/", NULL, MS_REMOUNT | MS_RDONLY, NULL); - - LOGI("* Mounting mirrors"); - struct vector mounts; - vec_init(&mounts); - file_to_vector("/proc/mounts", &mounts); - char *line; - int skip_initramfs = 0; - // Check whether skip_initramfs device - vec_for_each(&mounts, line) { - if (strstr(line, " /system_root ")) { - xmkdir_p(MIRRDIR "/system", 0755); - bind_mount("/system_root/system", MIRRDIR "/system"); - skip_initramfs = 1; - break; - } - } - vec_for_each(&mounts, line) { - if (!skip_initramfs && strstr(line, " /system ")) { - sscanf(line, "%s", buf); - xmkdir_p(MIRRDIR "/system", 0755); - xmount(buf, MIRRDIR "/system", "ext4", MS_RDONLY, NULL); - #ifdef MAGISK_DEBUG - LOGI("mount: %s -> %s\n", buf, MIRRDIR "/system"); - #else - LOGI("mount: %s\n", MIRRDIR "/system"); - #endif - } else if (strstr(line, " /vendor ")) { - seperate_vendor = 1; - sscanf(line, "%s", buf); - xmkdir_p(MIRRDIR "/vendor", 0755); - xmount(buf, MIRRDIR "/vendor", "ext4", MS_RDONLY, NULL); - #ifdef MAGISK_DEBUG - LOGI("mount: %s -> %s\n", buf, MIRRDIR "/vendor"); - #else - LOGI("mount: %s\n", MIRRDIR "/vendor"); - #endif - } - free(line); - } - vec_destroy(&mounts); - if (!seperate_vendor) { - xsymlink(MIRRDIR "/system/vendor", MIRRDIR "/vendor"); - #ifdef MAGISK_DEBUG - LOGI("link: %s -> %s\n", MIRRDIR "/system/vendor", MIRRDIR "/vendor"); - #else - LOGI("link: %s\n", MIRRDIR "/vendor"); - #endif - } - xmkdir_p(MIRRDIR "/bin", 0755); - bind_mount(DATABIN, MIRRDIR "/bin"); - - LOGI("* Setting up internal busybox"); - xmkdir_p(BBPATH, 0755); - exec_command_sync(MIRRDIR "/bin/busybox", "--install", "-s", BBPATH, NULL); - xsymlink(MIRRDIR "/bin/busybox", BBPATH "/busybox"); -} - static int prepare_img() { // First merge images if (merge_img("/data/magisk_merge.img", MAINIMG)) { @@ -624,7 +527,8 @@ void post_fs_data(int client) { exec_command_sync("sh", "-c", "mv -f /data/magisk/stock_*.img.gz /data", NULL); // Initialize - daemon_init(); + if (!is_daemon_init) + daemon_init(); // uninstaller if (access(UNINSTALLER, F_OK) == 0) { diff --git a/jni/core/daemon.c b/jni/core/daemon.c index ebdac594e..89b7a92e5 100644 --- a/jni/core/daemon.c +++ b/jni/core/daemon.c @@ -13,6 +13,7 @@ #include #include #include +#include #include #include "magisk.h" @@ -22,7 +23,7 @@ #include "resetprop.h" pthread_t sepol_patch; -int is_restart = 0; +int is_daemon_init = 0, seperate_vendor = 0; static void *request_handler(void *args) { int client = *((int *) args); @@ -108,6 +109,107 @@ void auto_start_magiskhide() { free(hide_prop); } + void daemon_init() { + is_daemon_init = 1; + LOGI("* Creating /sbin overlay"); + DIR *dir; + struct dirent *entry; + int root, sbin; + char buf[PATH_MAX], buf2[PATH_MAX]; + + // Setup links under /sbin + xmount(NULL, "/", NULL, MS_REMOUNT, NULL); + xmkdir("/root", 0755); + chmod("/root", 0755); + root = xopen("/root", O_RDONLY | O_CLOEXEC); + sbin = xopen("/sbin", O_RDONLY | O_CLOEXEC); + dir = xfdopendir(sbin); + while((entry = xreaddir(dir))) { + if (strcmp(entry->d_name, ".") == 0 || strcmp(entry->d_name, "..") == 0) continue; + linkat(sbin, entry->d_name, root, entry->d_name, 0); + if (strcmp(entry->d_name, "magisk") == 0) + unlinkat(sbin, entry->d_name, 0); + } + close(sbin); + xsymlink(MOUNTPOINT, FAKEPOINT); + xmount(NULL, "/", NULL, MS_REMOUNT | MS_RDONLY, NULL); + + xmount("tmpfs", "/sbin", "tmpfs", 0, NULL); + chmod("/sbin", 0755); + setfilecon("/sbin", "u:object_r:rootfs:s0"); + dir = xfdopendir(root); + while((entry = xreaddir(dir))) { + if (strcmp(entry->d_name, ".") == 0 || strcmp(entry->d_name, "..") == 0) continue; + snprintf(buf, PATH_MAX, "/root/%s", entry->d_name); + snprintf(buf2, PATH_MAX, "/sbin/%s", entry->d_name); + xsymlink(buf, buf2); + } + for (int i = 0; applet[i]; ++i) { + snprintf(buf2, PATH_MAX, "/sbin/%s", applet[i]); + xsymlink("/root/magisk", buf2); + } + for (int i = 0; init_applet[i]; ++i) { + snprintf(buf2, PATH_MAX, "/sbin/%s", init_applet[i]); + xsymlink("/root/magiskinit", buf2); + } + close(root); + + LOGI("* Mounting mirrors"); + struct vector mounts; + vec_init(&mounts); + file_to_vector("/proc/mounts", &mounts); + char *line; + int skip_initramfs = 0; + // Check whether skip_initramfs device + vec_for_each(&mounts, line) { + if (strstr(line, " /system_root ")) { + xmkdir_p(MIRRDIR "/system", 0755); + bind_mount("/system_root/system", MIRRDIR "/system"); + skip_initramfs = 1; + break; + } + } + vec_for_each(&mounts, line) { + if (!skip_initramfs && strstr(line, " /system ")) { + sscanf(line, "%s", buf); + xmkdir_p(MIRRDIR "/system", 0755); + xmount(buf, MIRRDIR "/system", "ext4", MS_RDONLY, NULL); + #ifdef MAGISK_DEBUG + LOGI("mount: %s -> %s\n", buf, MIRRDIR "/system"); + #else + LOGI("mount: %s\n", MIRRDIR "/system"); + #endif + } else if (strstr(line, " /vendor ")) { + seperate_vendor = 1; + sscanf(line, "%s", buf); + xmkdir_p(MIRRDIR "/vendor", 0755); + xmount(buf, MIRRDIR "/vendor", "ext4", MS_RDONLY, NULL); + #ifdef MAGISK_DEBUG + LOGI("mount: %s -> %s\n", buf, MIRRDIR "/vendor"); + #else + LOGI("mount: %s\n", MIRRDIR "/vendor"); + #endif + } + free(line); + } + vec_destroy(&mounts); + if (!seperate_vendor) { + xsymlink(MIRRDIR "/system/vendor", MIRRDIR "/vendor"); + #ifdef MAGISK_DEBUG + LOGI("link: %s -> %s\n", MIRRDIR "/system/vendor", MIRRDIR "/vendor"); + #else + LOGI("link: %s\n", MIRRDIR "/vendor"); + #endif + } + xmkdir_p(MIRRDIR "/bin", 0755); + bind_mount(DATABIN, MIRRDIR "/bin"); + + LOGI("* Setting up internal busybox"); + xmkdir_p(BBPATH, 0755); + exec_command_sync(MIRRDIR "/bin/busybox", "--install", "-s", BBPATH, NULL); + xsymlink(MIRRDIR "/bin/busybox", BBPATH "/busybox"); +} + void start_daemon() { setsid(); setcon("u:r:su:s0"); @@ -132,11 +234,13 @@ void start_daemon() { exit(1); xlisten(fd, 10); - if ((is_restart = access(MAGISKTMP, F_OK) == 0)) { + if ((is_daemon_init = access(MAGISKTMP, F_OK) == 0)) { // Restart stuffs if the daemon is restarted exec_command_sync("logcat", "-b", "all", "-c", NULL); auto_start_magiskhide(); start_debug_log(); + } else if (check_data()) { + daemon_init(); } // Start the log monitor diff --git a/jni/core/log_monitor.c b/jni/core/log_monitor.c index 40aa4c16c..300f3d0c5 100644 --- a/jni/core/log_monitor.c +++ b/jni/core/log_monitor.c @@ -15,7 +15,7 @@ #include "utils.h" int logcat_events[] = { -1, -1, -1 }; -extern int is_restart; +extern int is_daemon_init; #ifdef MAGISK_DEBUG static int debug_log_pid, debug_log_fd; @@ -71,7 +71,7 @@ static void *magisk_log_thread(void *args) { if (!have_data) { if ((have_data = check_data())) { // Dump buffered logs to file - if (!is_restart) + if (!is_daemon_init) rename(LOGFILE, LASTLOG); log = xfopen(LOGFILE, "a"); setbuf(log, NULL); diff --git a/jni/core/magisk.c b/jni/core/magisk.c index 2e921b6f6..584fd5a85 100644 --- a/jni/core/magisk.c +++ b/jni/core/magisk.c @@ -12,11 +12,7 @@ char *argv0; -char *applet[] = - { "su", "resetprop", "magiskhide", NULL }; - -int (*applet_main[]) (int, char *[]) = - { su_client_main, resetprop_main, magiskhide_main, NULL }; +int (*applet_main[]) (int, char *[]) = { su_client_main, resetprop_main, magiskhide_main, NULL }; int create_links(const char *bin, const char *path) { char self[PATH_MAX], linkpath[PATH_MAX]; diff --git a/jni/core/magiskinit.c b/jni/core/magiskinit.c index f8237d41f..a045193bd 100644 --- a/jni/core/magiskinit.c +++ b/jni/core/magiskinit.c @@ -38,7 +38,6 @@ #include #include - #include "dump.h" #include "magiskrc.h" #include "utils.h" @@ -49,6 +48,8 @@ // #define VLOG(fmt, ...) printf(fmt, __VA_ARGS__) /* Enable to debug */ #define VLOG(fmt, ...) +int (*init_applet_main[]) (int, char *[]) = { magiskpolicy_main, magiskpolicy_main, NULL }; + struct cmdline { int skip_initramfs; char slot[3]; @@ -383,10 +384,10 @@ static void magisk_init_daemon() { int main(int argc, char *argv[]) { umask(0); - if (strcmp(basename(argv[0]), "magiskpolicy") == 0 || strcmp(basename(argv[0]), "supolicy") == 0) - return magiskpolicy_main(argc, argv); - if (argc > 1 && (strcmp(argv[1], "magiskpolicy") == 0 || strcmp(argv[1], "supolicy") == 0)) - return magiskpolicy_main(argc - 1, argv + 1); + for (int i = 0; init_applet[i]; ++i) { + if (strcmp(basename(argv[0]), init_applet[i]) == 0) + return (*init_applet_main[i])(argc, argv); + } if (argc > 1 && strcmp(argv[1], "-x") == 0) { if (strcmp(argv[2], "magisk") == 0) @@ -402,8 +403,6 @@ int main(int argc, char *argv[]) { dump_magisk("/overlay/sbin/magisk", 0755); mkdir("/overlay/root", 0755); link("/init", "/overlay/root/magiskinit"); - symlink("/root/magiskinit", "/overlay/root/magiskpolicy"); - symlink("/root/magiskinit", "/overlay/root/supolicy"); struct cmdline cmd; parse_cmdline(&cmd); diff --git a/jni/include/daemon.h b/jni/include/daemon.h index c34b80526..255b02f40 100644 --- a/jni/include/daemon.h +++ b/jni/include/daemon.h @@ -8,7 +8,7 @@ #include extern pthread_t sepol_patch; -extern int is_restart; +extern int is_daemon_init, seperate_vendor; // Commands require connecting to daemon typedef enum { @@ -43,6 +43,7 @@ typedef enum { void start_daemon(); int connect_daemon(); void auto_start_magiskhide(); +void daemon_init(); // socket.c diff --git a/jni/include/magisk.h b/jni/include/magisk.h index b5b86c571..59ef772b1 100644 --- a/jni/include/magisk.h +++ b/jni/include/magisk.h @@ -44,8 +44,10 @@ extern char *argv0; /* For changing process name */ -extern char *applet[]; -extern int (*applet_main[]) (int, char *[]); +#define applet ((char *[]) { "su", "resetprop", "magiskhide", NULL }) +#define init_applet ((char *[]) { "magiskpolicy", "supolicy", NULL }) + +extern int (*applet_main[]) (int, char *[]), (*init_applet_main[]) (int, char *[]); int create_links(const char *bin, const char *path);