Add zygote server notifier

This commit is contained in:
topjohnwu 2019-03-04 16:45:18 -05:00
parent e73fa57d54
commit 6c3896079d
8 changed files with 68 additions and 13 deletions

View File

@ -11,13 +11,15 @@
static int (*applet_main[]) (int, char *[]) =
{ magisk_main, su_client_main, resetprop_main, magiskhide_main, nullptr };
__attribute__((noreturn)) static void call_applets(int argc, char *argv[]) {
[[noreturn]] static void call_applets(int argc, char *argv[]) {
// Applets
for (int i = 0; applet_names[i]; ++i) {
if (strcmp(basename(argv[0]), applet_names[i]) == 0) {
exit((*applet_main[i])(argc, argv));
}
}
if (strncmp(basename(argv[0]), "app_process", 11) == 0)
exit(app_process_main(argc, argv));
fprintf(stderr, "%s: applet not found\n", argv[0]);
exit(1);
}

View File

@ -575,11 +575,30 @@ static void dump_logs() {
pthread_exit(nullptr);
}
[[noreturn]] static inline void core_only() {
[[noreturn]] static void core_only() {
auto_start_magiskhide();
cp_afc("/sbin/magisk", MAGISKTMP "/app_process");
struct stat st;
for (const char *app : { "app_process", "app_process32", "app_process64" }) {
sprintf(buf, "/system/bin/%s", app);
if (lstat(buf, &st) == 0 && S_ISREG(st.st_mode)) {
clone_attr(buf, MAGISKTMP "/app_process");
bind_mount(MAGISKTMP "/app_process", buf);
}
}
unblock_boot_process();
}
void zygote_notify(int client, struct ucred *cred) {
/* TODO: notify services that need zygote PIDs */
char *path = read_string(client);
LOGD("%s PID=[%d]\n", path, cred->pid);
close(client);
usleep(100000);
bind_mount(MAGISKTMP "/app_process", path);
free(path);
}
void post_fs_data(int client) {
// ack
write_int(client, 0);

View File

@ -88,7 +88,9 @@ static void *request_handler(void *args) {
break;
case SQLITE_CMD:
exec_sql(client);
close(client);
break;
case ZYGOTE_NOTIFY:
zygote_notify(client, &credential);
break;
default:
close(client);
@ -161,13 +163,13 @@ int switch_mnt_ns(int pid) {
return ret;
}
int connect_daemon() {
int connect_daemon(bool create) {
struct sockaddr_un sun;
socklen_t len = setup_sockaddr(&sun, MAIN_SOCKET);
int fd = xsocket(AF_LOCAL, SOCK_STREAM | SOCK_CLOEXEC, 0);
if (connect(fd, (struct sockaddr*) &sun, len)) {
if (getuid() != UID_ROOT || getgid() != UID_ROOT) {
fprintf(stderr, "No daemon is currently running!\n");
if (!create || getuid() != UID_ROOT || getgid() != UID_ROOT) {
LOGE("No daemon is currently running!\n");
exit(1);
}

View File

@ -320,4 +320,5 @@ void exec_sql(int client) {
return;
);
write_int(client, 0);
close(client);
}

View File

@ -1,3 +1,4 @@
#include <sys/mount.h>
#include <stdlib.h>
#include <stdio.h>
#include <unistd.h>
@ -81,19 +82,19 @@ int magisk_main(int argc, char *argv[]) {
cp_afc(argv[2], argv[3]);
return 0;
} else if (strcmp(argv[1], "--daemon") == 0) {
int fd = connect_daemon();
int fd = connect_daemon(true);
write_int(fd, DO_NOTHING);
return 0;
} else if (strcmp(argv[1], "--post-fs-data") == 0) {
int fd = connect_daemon();
int fd = connect_daemon(true);
write_int(fd, POST_FS_DATA);
return read_int(fd);
} else if (strcmp(argv[1], "--service") == 0) {
int fd = connect_daemon();
int fd = connect_daemon(true);
write_int(fd, LATE_START);
return read_int(fd);
} else if (strcmp(argv[1], "--boot-complete") == 0) {
int fd = connect_daemon();
int fd = connect_daemon(true);
write_int(fd, BOOT_COMPLETE);
return read_int(fd);
} else if (strcmp(argv[1], "--sqlite") == 0) {
@ -111,3 +112,29 @@ int magisk_main(int argc, char *argv[]) {
#endif
usage();
}
int app_process_main(int argc, char *argv[]) {
char path[512];
bool zygote = false;
for (int i = 0; i < argc; ++i) {
if (strcmp(argv[i], "--zygote") == 0) {
zygote = true;
break;
}
}
if (zygote) {
// Notify main daemon
sprintf(path, "/system/bin/%s", basename(argv[0]));
umount2(path, MNT_DETACH);
int fd = connect_daemon();
write_int(fd, ZYGOTE_NOTIFY);
write_string(fd, path);
close(fd);
} else {
// Redirect to system mirror
sprintf(path, MIRRDIR "/system/bin/%s", basename(argv[0]));
}
argv[0] = path;
execve(path, argv, environ);
return -1;
}

View File

@ -21,6 +21,7 @@ enum {
BOOT_COMPLETE,
MAGISKHIDE,
SQLITE_CMD,
ZYGOTE_NOTIFY,
};
// Return codes for daemon
@ -33,7 +34,7 @@ enum {
// daemon.c
int connect_daemon();
int connect_daemon(bool create = false);
int switch_mnt_ns(int pid);
// socket.c
@ -60,6 +61,7 @@ void write_key_token(int fd, const char *key, int tok);
***************/
void unlock_blocks();
void zygote_notify(int client, struct ucred *cred);
void post_fs_data(int client);
void late_start(int client);
void boot_complete(int client);

View File

@ -41,8 +41,8 @@
extern int SDK_INT;
#define applet_names ((const char *[]) { "magisk", "su", "resetprop", "magiskhide", nullptr })
#define init_applet ((const char *[]) { "magiskpolicy", "supolicy", nullptr })
constexpr const char *applet_names[] = { "magisk", "su", "resetprop", "magiskhide", nullptr };
constexpr const char *init_applet[] = { "magiskpolicy", "supolicy", nullptr };
// Multi-call entrypoints
int magisk_main(int argc, char *argv[]);
@ -50,5 +50,6 @@ int magiskhide_main(int argc, char *argv[]);
int magiskpolicy_main(int argc, char *argv[]);
int su_client_main(int argc, char *argv[]);
int resetprop_main(int argc, char *argv[]);
int app_process_main(int argc, char *argv[]);
#endif

View File

@ -78,6 +78,7 @@ void sepol_magisk_rules() {
allowSuClient("untrusted_app_25");
allowSuClient("untrusted_app_27");
allowSuClient("update_engine");
allowSuClient("zygote");
// suRights
sepol_allow("servicemanager", SEPOL_PROC_DOMAIN, "dir", "search");