Maintain global daemon status

This commit is contained in:
topjohnwu 2020-05-18 05:18:49 -07:00
parent b27b9c1d18
commit 501d3e6c32
2 changed files with 83 additions and 55 deletions

View File

@ -20,66 +20,25 @@ using namespace std;
int SDK_INT = -1; int SDK_INT = -1;
bool RECOVERY_MODE = false; bool RECOVERY_MODE = false;
string MAGISKTMP; string MAGISKTMP;
int daemon_state = STATE_UNKNOWN;
static struct stat self_st; static struct stat self_st;
static void verify_client(int client, pid_t pid) { static bool verify_client(int client, pid_t pid) {
// Verify caller is the same as server // Verify caller is the same as server
char path[32]; char path[32];
sprintf(path, "/proc/%d/exe", pid); sprintf(path, "/proc/%d/exe", pid);
struct stat st; struct stat st;
if (stat(path, &st) || st.st_dev != self_st.st_dev || st.st_ino != self_st.st_ino) { return !(stat(path, &st) || st.st_dev != self_st.st_dev || st.st_ino != self_st.st_ino);
close(client);
pthread_exit(nullptr);
}
} }
static void *request_handler(void *args) { static void request_handler(int client, int req_code, ucred cred) {
int client = reinterpret_cast<intptr_t>(args); switch (req_code) {
struct ucred credential;
get_client_cred(client, &credential);
if (credential.uid != 0)
verify_client(client, credential.pid);
int req = read_int(client);
switch (req) {
case MAGISKHIDE:
case POST_FS_DATA:
case LATE_START:
case BOOT_COMPLETE:
case SQLITE_CMD:
case GET_PATH:
if (credential.uid != 0) {
write_int(client, ROOT_REQUIRED);
close(client);
return nullptr;
}
break;
case REMOVE_MODULES:
if (credential.uid != UID_SHELL && credential.uid != UID_ROOT) {
write_int(client, 1);
close(client);
return nullptr;
}
break;
default:
break;
}
switch (req) {
case MAGISKHIDE: case MAGISKHIDE:
magiskhide_handler(client); magiskhide_handler(client);
break; break;
case SUPERUSER: case SUPERUSER:
su_daemon_handler(client, &credential); su_daemon_handler(client, &cred);
break;
case CHECK_VERSION:
write_string(client, MAGISK_VERSION ":MAGISK");
close(client);
break;
case CHECK_VERSION_CODE:
write_int(client, MAGISK_VER_CODE);
close(client);
break; break;
case POST_FS_DATA: case POST_FS_DATA:
post_fs_data(client); post_fs_data(client);
@ -99,15 +58,75 @@ static void *request_handler(void *args) {
close(client); close(client);
reboot(); reboot();
break; break;
case GET_PATH:
write_string(client, MAGISKTMP.data());
close(client);
break;
default: default:
close(client); close(client);
break; break;
} }
return nullptr; }
static void handle_request(int client) {
int req_code;
// Verify client credentials
ucred cred;
get_client_cred(client, &cred);
if (cred.uid != 0 && !verify_client(client, cred.pid))
goto shortcut;
// Check client permissions
req_code = read_int(client);
switch (req_code) {
case MAGISKHIDE:
case POST_FS_DATA:
case LATE_START:
case BOOT_COMPLETE:
case SQLITE_CMD:
case GET_PATH:
if (cred.uid != 0) {
write_int(client, ROOT_REQUIRED);
goto shortcut;
}
break;
case REMOVE_MODULES:
if (cred.uid != UID_SHELL && cred.uid != UID_ROOT) {
write_int(client, 1);
goto shortcut;
}
break;
}
switch (req_code) {
// In case of init trigger launches, set the corresponding states
case POST_FS_DATA:
daemon_state = STATE_POST_FS_DATA;
break;
case LATE_START:
daemon_state = STATE_LATE_START;
break;
case BOOT_COMPLETE:
daemon_state = STATE_BOOT_COMPLETE;
break;
// Simple requests to query daemon info
case CHECK_VERSION:
write_string(client, MAGISK_VERSION ":MAGISK");
goto shortcut;
case CHECK_VERSION_CODE:
write_int(client, MAGISK_VER_CODE);
goto shortcut;
case GET_PATH:
write_string(client, MAGISKTMP.data());
goto shortcut;
case DO_NOTHING:
goto shortcut;
}
// Create new thread to handle complex requests
new_daemon_thread(std::bind(&request_handler, client, req_code, cred));
return;
shortcut:
close(client);
} }
static void android_logging() { static void android_logging() {
@ -207,7 +226,7 @@ static void daemon_entry(int ppid) {
// Loop forever to listen for requests // Loop forever to listen for requests
for (;;) { for (;;) {
int client = xaccept4(fd, nullptr, nullptr, SOCK_CLOEXEC); int client = xaccept4(fd, nullptr, nullptr, SOCK_CLOEXEC);
new_daemon_thread(request_handler, reinterpret_cast<void*>(client)); handle_request(client);
} }
} }

View File

@ -6,7 +6,7 @@
#include <socket.hpp> #include <socket.hpp>
// Commands require connecting to daemon // Daemon command codes
enum { enum {
DO_NOTHING = 0, DO_NOTHING = 0,
SUPERUSER, SUPERUSER,
@ -29,8 +29,17 @@ enum {
DAEMON_LAST DAEMON_LAST
}; };
// Daemon state
enum {
STATE_POST_FS_DATA,
STATE_LATE_START,
STATE_BOOT_COMPLETE,
STATE_UNKNOWN
};
extern int SDK_INT; extern int SDK_INT;
extern bool RECOVERY_MODE; extern bool RECOVERY_MODE;
extern int daemon_state;
extern bool pfs_done; extern bool pfs_done;
extern std::vector<std::string> module_list; extern std::vector<std::string> module_list;
#define APP_DATA_DIR (SDK_INT >= 24 ? "/data/user_de" : "/data/user") #define APP_DATA_DIR (SDK_INT >= 24 ? "/data/user_de" : "/data/user")