mirror of
https://github.com/topjohnwu/Magisk.git
synced 2024-11-24 02:25:28 +00:00
Generalize logging interface
This commit is contained in:
parent
12ced52012
commit
df8b047bca
@ -17,6 +17,7 @@ COMMON_UTILS := \
|
||||
utils/misc.c \
|
||||
utils/vector.c \
|
||||
utils/selinux.c \
|
||||
utils/logging.c \
|
||||
utils/xwrap.c
|
||||
|
||||
########################
|
||||
@ -32,7 +33,6 @@ LOCAL_SHARED_LIBRARIES := libsqlite
|
||||
LOCAL_STATIC_LIBRARIES := libnanopb libsystemproperties
|
||||
LOCAL_C_INCLUDES := \
|
||||
jni/include \
|
||||
jni/magiskpolicy \
|
||||
$(EXT_PATH)/include \
|
||||
$(LIBNANOPB) \
|
||||
$(LIBSYSTEMPROPERTIES)
|
||||
@ -144,7 +144,7 @@ include jni/external/busybox/Android.mk
|
||||
endif
|
||||
|
||||
########################
|
||||
# Externals
|
||||
# Libraries
|
||||
########################
|
||||
include jni/external/Android.mk
|
||||
include jni/resetprop/libsystemproperties/Android.mk
|
||||
|
@ -1,14 +1,14 @@
|
||||
APP_ABI := armeabi-v7a x86
|
||||
APP_CFLAGS := -std=gnu99 ${MAGISK_DEBUG} \
|
||||
APP_CFLAGS := -std=gnu11 ${MAGISK_DEBUG} \
|
||||
-DMAGISK_VERSION="${MAGISK_VERSION}" -DMAGISK_VER_CODE=${MAGISK_VER_CODE}
|
||||
APP_CPPFLAGS := -std=c++14
|
||||
APP_STL := system
|
||||
APP_PLATFORM := android-16
|
||||
APP_CFLAGS += -Wno-implicit-function-declaration
|
||||
|
||||
# Busybox require some additional settings
|
||||
ifdef B_BB
|
||||
APP_SHORT_COMMANDS := true
|
||||
NDK_TOOLCHAIN_VERSION := 4.9
|
||||
APP_PLATFORM := android-21
|
||||
APP_CFLAGS += -Wno-implicit-function-declaration
|
||||
endif
|
||||
|
@ -96,6 +96,10 @@ static void *request_handler(void *args) {
|
||||
}
|
||||
|
||||
void main_daemon() {
|
||||
android_logging();
|
||||
#ifndef MAGISK_DEBUG
|
||||
log_cb.d = nop_log;
|
||||
#endif
|
||||
setsid();
|
||||
setcon("u:r:"SEPOL_PROC_DOMAIN":s0");
|
||||
int fd = xopen("/dev/null", O_RDWR | O_CLOEXEC);
|
||||
|
@ -8,6 +8,8 @@
|
||||
#include <stdio.h>
|
||||
#include <pthread.h>
|
||||
#include <unistd.h>
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
#include <sys/wait.h>
|
||||
#include <fcntl.h>
|
||||
|
||||
|
@ -5,6 +5,7 @@
|
||||
#include <stdio.h>
|
||||
#include <unistd.h>
|
||||
#include <libgen.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "utils.h"
|
||||
#include "magisk.h"
|
||||
|
@ -46,12 +46,6 @@
|
||||
#include "daemon.h"
|
||||
#include "magisk.h"
|
||||
|
||||
#ifdef MAGISK_DEBUG
|
||||
#define VLOG(fmt, ...) fprintf(stderr, fmt, __VA_ARGS__)
|
||||
#else
|
||||
#define VLOG(fmt, ...)
|
||||
#endif
|
||||
|
||||
#define DEFAULT_DT_DIR "/proc/device-tree/firmware/android"
|
||||
|
||||
int (*init_applet_main[]) (int, char *[]) = { magiskpolicy_main, magiskpolicy_main, NULL };
|
||||
@ -94,7 +88,7 @@ static void parse_cmdline(struct cmdline *cmd) {
|
||||
if (cmd->dt_dir[0] == '\0')
|
||||
strcpy(cmd->dt_dir, DEFAULT_DT_DIR);
|
||||
|
||||
VLOG("cmdline: skip_initramfs[%d] slot[%s] dt_dir[%s]\n", cmd->skip_initramfs, cmd->slot, cmd->dt_dir);
|
||||
LOGD("cmdline: skip_initramfs[%d] slot[%s] dt_dir[%s]\n", cmd->skip_initramfs, cmd->slot, cmd->dt_dir);
|
||||
}
|
||||
|
||||
static void parse_device(struct device *dev, const char *uevent) {
|
||||
@ -113,7 +107,7 @@ static void parse_device(struct device *dev, const char *uevent) {
|
||||
}
|
||||
}
|
||||
fclose(fp);
|
||||
VLOG("%s [%s] (%u, %u)\n", dev->devname, dev->partname, (unsigned) dev->major, (unsigned) dev->minor);
|
||||
LOGD("%s [%s] (%u, %u)\n", dev->devname, dev->partname, (unsigned) dev->major, (unsigned) dev->minor);
|
||||
}
|
||||
|
||||
static int setup_block(struct device *dev, const char *partname) {
|
||||
@ -199,7 +193,7 @@ static int verify_precompiled() {
|
||||
}
|
||||
}
|
||||
closedir(dir);
|
||||
VLOG("sys_sha[%.*s]\nven_sha[%.*s]\n", sizeof(sys_sha), sys_sha, sizeof(ven_sha), ven_sha);
|
||||
LOGD("sys_sha[%.*s]\nven_sha[%.*s]\n", sizeof(sys_sha), sys_sha, sizeof(ven_sha), ven_sha);
|
||||
return memcmp(sys_sha, ven_sha, sizeof(sys_sha)) == 0;
|
||||
}
|
||||
|
||||
@ -339,6 +333,10 @@ int main(int argc, char *argv[]) {
|
||||
return dump_magiskrc(argv[3], 0755);
|
||||
}
|
||||
|
||||
#ifdef MAGISK_DEBUG
|
||||
log_cb.d = vprintf;
|
||||
#endif
|
||||
|
||||
// Prevent file descriptor confusion
|
||||
mknod("/null", S_IFCHR | 0666, makedev(1, 3));
|
||||
int null = open("/null", O_RDWR | O_CLOEXEC);
|
||||
|
@ -1,6 +1,8 @@
|
||||
/* socket.c - All socket related operations
|
||||
*/
|
||||
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
#include <fcntl.h>
|
||||
#include <endian.h>
|
||||
|
||||
|
@ -1,68 +1,44 @@
|
||||
/* logging.h - Error handling and logging
|
||||
*/
|
||||
|
||||
#ifndef _LOGGING_H_
|
||||
#define _LOGGING_H_
|
||||
#pragma once
|
||||
|
||||
#include <string.h>
|
||||
#include <errno.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdarg.h>
|
||||
#include <string.h>
|
||||
|
||||
#define str(a) #a
|
||||
#define xstr(a) str(a)
|
||||
|
||||
/**************
|
||||
* No logging *
|
||||
**************/
|
||||
typedef enum {
|
||||
L_DEBUG,
|
||||
L_INFO,
|
||||
L_WARN,
|
||||
L_ERR
|
||||
} log_type;
|
||||
|
||||
#define LOGD(...)
|
||||
#define LOGI(...)
|
||||
#define LOGW(...)
|
||||
#define LOGE(...)
|
||||
#define PLOGE(...)
|
||||
struct log_callback {
|
||||
int (*d)(const char* fmt, va_list ap);
|
||||
int (*i)(const char* fmt, va_list ap);
|
||||
int (*w)(const char* fmt, va_list ap);
|
||||
int (*e)(const char* fmt, va_list ap);
|
||||
void (*ex)(int code);
|
||||
};
|
||||
|
||||
/******************
|
||||
* Daemon logging *
|
||||
******************/
|
||||
extern struct log_callback log_cb;
|
||||
|
||||
#ifdef IS_DAEMON
|
||||
|
||||
#undef LOGI
|
||||
#undef LOGW
|
||||
#undef LOGE
|
||||
#undef PLOGE
|
||||
|
||||
#include <pthread.h>
|
||||
#include <android/log.h>
|
||||
|
||||
#define LOG_TAG "Magisk"
|
||||
|
||||
#ifdef MAGISK_DEBUG
|
||||
#undef LOGD
|
||||
#define LOGD(...) __android_log_print(ANDROID_LOG_DEBUG, LOG_TAG, __VA_ARGS__)
|
||||
#endif
|
||||
#define LOGI(...) __android_log_print(ANDROID_LOG_INFO, LOG_TAG, __VA_ARGS__)
|
||||
#define LOGW(...) __android_log_print(ANDROID_LOG_WARN, LOG_TAG, __VA_ARGS__)
|
||||
#define LOGE(...) __android_log_print(ANDROID_LOG_ERROR, LOG_TAG, __VA_ARGS__)
|
||||
#define LOGD(...) log_handler(L_DEBUG, __VA_ARGS__)
|
||||
#define LOGI(...) log_handler(L_INFO, __VA_ARGS__)
|
||||
#define LOGW(...) log_handler(L_WARN, __VA_ARGS__)
|
||||
#define LOGE(...) log_handler(L_ERR, __VA_ARGS__)
|
||||
#define PLOGE(fmt, args...) LOGE(fmt " failed with %d: %s", ##args, errno, strerror(errno))
|
||||
|
||||
#endif
|
||||
int nop_log(const char *fmt, va_list ap);
|
||||
void nop_ex(int i);
|
||||
|
||||
/********************
|
||||
* Tools Log & Exit *
|
||||
********************/
|
||||
void no_logging();
|
||||
void android_logging();
|
||||
void cmdline_logging();
|
||||
|
||||
#ifdef XWRAP_EXIT
|
||||
int log_handler(log_type t, const char *fmt, ...);
|
||||
|
||||
#undef LOGE
|
||||
#undef PLOGE
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
#define LOGE(...) { fprintf(stderr, __VA_ARGS__); exit(1); }
|
||||
#define PLOGE(fmt, args...) { fprintf(stderr, fmt " failed with %d: %s\n\n", ##args, errno, strerror(errno)); exit(1); }
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
#endif // _LOGGING_H_
|
||||
|
@ -250,6 +250,7 @@ int parse_img(const char *image, boot_img *boot) {
|
||||
}
|
||||
}
|
||||
LOGE("No boot image magic found!\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
int unpack(const char *image) {
|
||||
|
@ -1,5 +1,7 @@
|
||||
#include <unistd.h>
|
||||
#include <fcntl.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <sys/mman.h>
|
||||
|
||||
#include <zlib.h>
|
||||
|
@ -1,6 +1,8 @@
|
||||
#include <stdio.h>
|
||||
#include <unistd.h>
|
||||
#include <fcntl.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "cpio.h"
|
||||
#include "logging.h"
|
||||
|
@ -1,12 +1,14 @@
|
||||
#include <stdio.h>
|
||||
#include <unistd.h>
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
#include <sys/stat.h>
|
||||
#include <utils.h>
|
||||
#include <sys/mman.h>
|
||||
#include <fcntl.h>
|
||||
|
||||
#include "magiskboot.h"
|
||||
#include "cpio.h"
|
||||
#include "utils.h"
|
||||
|
||||
static void cpio_patch(struct vector *v, int keepverity, int keepforceencrypt) {
|
||||
fprintf(stderr, "Patch with flag KEEPVERITY=[%s] KEEPFORCEENCRYPT=[%s]\n",
|
||||
|
@ -114,6 +114,7 @@ void stop_magiskhide(int client) {
|
||||
}
|
||||
|
||||
int magiskhide_main(int argc, char *argv[]) {
|
||||
cmdline_logging();
|
||||
if (argc < 2) {
|
||||
usage(argv[0]);
|
||||
}
|
||||
|
@ -391,6 +391,7 @@ static void syntax_error_msg() {
|
||||
}
|
||||
|
||||
int magiskpolicy_main(int argc, char *argv[]) {
|
||||
cmdline_logging();
|
||||
char *outfile = NULL, *tok, *saveptr;
|
||||
int magisk = 0;
|
||||
struct vector rules;
|
||||
|
@ -10,9 +10,6 @@
|
||||
|
||||
extern int prop_verbose;
|
||||
|
||||
#define PRINT_D(...) { LOGD(__VA_ARGS__); if (prop_verbose) fprintf(stderr, __VA_ARGS__); }
|
||||
#define PRINT_E(...) { LOGE(__VA_ARGS__); fprintf(stderr, __VA_ARGS__); }
|
||||
|
||||
struct prop_t {
|
||||
char *name;
|
||||
char value[PROP_VALUE_MAX];
|
||||
|
@ -153,7 +153,7 @@ static void pb_getprop_cb(const char *name, const char *value, void *v) {
|
||||
|
||||
void persist_getprop_all(struct read_cb_t *read_cb) {
|
||||
if (access(PERSISTENT_PROPERTY_DIR "/persistent_properties", R_OK) == 0) {
|
||||
PRINT_D("resetprop: decode with protobuf from [" PERSISTENT_PROPERTY_DIR "/persistent_properties]\n");
|
||||
LOGD("resetprop: decode with protobuf from [" PERSISTENT_PROPERTY_DIR "/persistent_properties]\n");
|
||||
PersistentProperties props = PersistentProperties_init_zero;
|
||||
props.properties.funcs.decode = prop_decode;
|
||||
props.properties.arg = read_cb;
|
||||
@ -196,7 +196,7 @@ char *persist_getprop(const char *name) {
|
||||
int fd = open(path, O_RDONLY | O_CLOEXEC);
|
||||
if (fd < 0)
|
||||
return NULL;
|
||||
PRINT_D("resetprop: read prop from [%s]\n", path);
|
||||
LOGD("resetprop: read prop from [%s]\n", path);
|
||||
prop.value[read(fd, prop.value, sizeof(PROP_VALUE_MAX))] = '\0'; // Null terminate the read value
|
||||
close(fd);
|
||||
}
|
||||
@ -231,7 +231,7 @@ bool persist_deleteprop(const char *name) {
|
||||
pb_ostream_t ostream = create_ostream(PERSISTENT_PROPERTY_DIR "/persistent_properties.tmp");
|
||||
props.properties.funcs.encode = prop_encode;
|
||||
props.properties.arg = &v;
|
||||
PRINT_D("resetprop: encode with protobuf to [" PERSISTENT_PROPERTY_DIR "/persistent_properties.tmp]\n");
|
||||
LOGD("resetprop: encode with protobuf to [" PERSISTENT_PROPERTY_DIR "/persistent_properties.tmp]\n");
|
||||
if (!pb_encode(&ostream, PersistentProperties_fields, &props))
|
||||
return false;
|
||||
clone_attr(PERSISTENT_PROPERTY_DIR "/persistent_properties", PERSISTENT_PROPERTY_DIR "/persistent_properties.tmp");
|
||||
@ -244,7 +244,7 @@ bool persist_deleteprop(const char *name) {
|
||||
char path[PATH_MAX];
|
||||
snprintf(path, sizeof(path), PERSISTENT_PROPERTY_DIR "/%s", name);
|
||||
if (unlink(path) == 0) {
|
||||
PRINT_D("resetprop: unlink [%s]\n", path);
|
||||
LOGD("resetprop: unlink [%s]\n", path);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
@ -50,7 +50,7 @@ static int check_legal_property_name(const char *name) {
|
||||
return 0;
|
||||
|
||||
illegal:
|
||||
PRINT_E("Illegal property name: [%s]\n", name);
|
||||
LOGE("Illegal property name: [%s]\n", name);
|
||||
return 1;
|
||||
}
|
||||
|
||||
@ -124,7 +124,7 @@ static int prop_cmp(const void *p1, const void *p2) {
|
||||
|
||||
static int init_resetprop() {
|
||||
if (__system_properties_init()) {
|
||||
PRINT_E("resetprop: Initialize error\n");
|
||||
LOGE("resetprop: Initialize error\n");
|
||||
return -1;
|
||||
}
|
||||
return 0;
|
||||
@ -176,7 +176,7 @@ char *getprop2(const char *name, int persist) {
|
||||
if (value)
|
||||
return value;
|
||||
}
|
||||
PRINT_D("resetprop: prop [%s] does not exist\n", name);
|
||||
LOGD("resetprop: prop [%s] does not exist\n", name);
|
||||
return NULL;
|
||||
} else {
|
||||
char value[PROP_VALUE_MAX];
|
||||
@ -185,7 +185,7 @@ char *getprop2(const char *name, int persist) {
|
||||
.cookie = value
|
||||
};
|
||||
__system_property_read_callback(pi, callback_wrapper, &read_cb);
|
||||
PRINT_D("resetprop: getprop [%s]: [%s]\n", name, value);
|
||||
LOGD("resetprop: getprop [%s]: [%s]\n", name, value);
|
||||
return strdup(value);
|
||||
}
|
||||
}
|
||||
@ -218,7 +218,7 @@ int setprop2(const char *name, const char *value, const int trigger) {
|
||||
ret = __system_property_update(pi, value, strlen(value));
|
||||
}
|
||||
} else {
|
||||
PRINT_D("resetprop: New prop [%s]\n", name);
|
||||
LOGD("resetprop: New prop [%s]\n", name);
|
||||
if (trigger) {
|
||||
ret = __system_property_set(name, value);
|
||||
} else {
|
||||
@ -226,11 +226,11 @@ int setprop2(const char *name, const char *value, const int trigger) {
|
||||
}
|
||||
}
|
||||
|
||||
PRINT_D("resetprop: setprop [%s]: [%s] by %s\n", name, value,
|
||||
LOGD("resetprop: setprop [%s]: [%s] by %s\n", name, value,
|
||||
trigger ? "property_service" : "modifing prop data structure");
|
||||
|
||||
if (ret)
|
||||
PRINT_E("resetprop: setprop error\n");
|
||||
LOGE("resetprop: setprop error\n");
|
||||
|
||||
return ret;
|
||||
}
|
||||
@ -245,7 +245,7 @@ int deleteprop2(const char *name, int persist) {
|
||||
if (init_resetprop()) return -1;
|
||||
char path[PATH_MAX];
|
||||
path[0] = '\0';
|
||||
PRINT_D("resetprop: deleteprop [%s]\n", name);
|
||||
LOGD("resetprop: deleteprop [%s]\n", name);
|
||||
if (persist && strncmp(name, "persist.", 8) == 0)
|
||||
persist = persist_deleteprop(name);
|
||||
return __system_property_del(name) && !(persist && strncmp(name, "persist.", 8) == 0);
|
||||
@ -253,10 +253,10 @@ int deleteprop2(const char *name, int persist) {
|
||||
|
||||
int read_prop_file(const char* filename, const int trigger) {
|
||||
if (init_resetprop()) return -1;
|
||||
PRINT_D("resetprop: Load prop file [%s]\n", filename);
|
||||
LOGD("resetprop: Load prop file [%s]\n", filename);
|
||||
FILE *fp = fopen(filename, "r");
|
||||
if (fp == NULL) {
|
||||
PRINT_E("Cannot open [%s]\n", filename);
|
||||
LOGE("Cannot open [%s]\n", filename);
|
||||
return 1;
|
||||
}
|
||||
char *line = NULL, *pch;
|
||||
@ -292,7 +292,14 @@ int read_prop_file(const char* filename, const int trigger) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int verbose_logging(const char *fmt, va_list ap) {
|
||||
return prop_verbose ? vfprintf(stderr, fmt, ap) : 0;
|
||||
}
|
||||
|
||||
int resetprop_main(int argc, char *argv[]) {
|
||||
cmdline_logging();
|
||||
log_cb.d = verbose_logging;
|
||||
|
||||
int trigger = 1, persist = 0;
|
||||
char *argv0 = argv[0], *prop;
|
||||
|
||||
|
@ -4,6 +4,8 @@
|
||||
#include <unistd.h>
|
||||
#include <libgen.h>
|
||||
#include <fcntl.h>
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/wait.h>
|
||||
#include <sys/mount.h>
|
||||
@ -97,6 +99,7 @@ static void usage() {
|
||||
}
|
||||
|
||||
int imgtool_main(int argc, char *argv[]) {
|
||||
cmdline_logging();
|
||||
if (argc < 2)
|
||||
usage();
|
||||
if (strcmp(argv[1], "create") == 0) {
|
||||
|
88
native/jni/utils/logging.c
Normal file
88
native/jni/utils/logging.c
Normal file
@ -0,0 +1,88 @@
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <android/log.h>
|
||||
|
||||
#include "logging.h"
|
||||
|
||||
int nop_log(const char *fmt, va_list ap) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
void nop_ex(int i) {}
|
||||
|
||||
struct log_callback log_cb = {
|
||||
.d = nop_log,
|
||||
.i = nop_log,
|
||||
.w = nop_log,
|
||||
.e = nop_log,
|
||||
.ex = nop_ex
|
||||
};
|
||||
|
||||
void no_logging() {
|
||||
log_cb.d = nop_log;
|
||||
log_cb.i = nop_log;
|
||||
log_cb.w = nop_log;
|
||||
log_cb.e = nop_log;
|
||||
log_cb.ex = nop_ex;
|
||||
}
|
||||
|
||||
#define LOG_TAG "Magisk"
|
||||
|
||||
static int log_d(const char *fmt, va_list ap) {
|
||||
return __android_log_vprint(ANDROID_LOG_DEBUG, LOG_TAG, fmt, ap);
|
||||
}
|
||||
|
||||
static int log_i(const char *fmt, va_list ap) {
|
||||
return __android_log_vprint(ANDROID_LOG_INFO, LOG_TAG, fmt, ap);
|
||||
}
|
||||
|
||||
static int log_w(const char *fmt, va_list ap) {
|
||||
return __android_log_vprint(ANDROID_LOG_WARN, LOG_TAG, fmt, ap);
|
||||
}
|
||||
|
||||
static int log_e(const char *fmt, va_list ap) {
|
||||
return __android_log_vprint(ANDROID_LOG_ERROR, LOG_TAG, fmt, ap);
|
||||
}
|
||||
|
||||
void android_logging() {
|
||||
log_cb.d = log_d;
|
||||
log_cb.i = log_i;
|
||||
log_cb.w = log_w;
|
||||
log_cb.e = log_e;
|
||||
log_cb.ex = nop_ex;
|
||||
}
|
||||
|
||||
static int vprinte(const char *fmt, va_list ap) {
|
||||
return vfprintf(stderr, fmt, ap);
|
||||
}
|
||||
|
||||
void cmdline_logging() {
|
||||
log_cb.d = vprinte;
|
||||
log_cb.i = vprintf;
|
||||
log_cb.w = vprinte;
|
||||
log_cb.e = vprinte;
|
||||
log_cb.ex = exit;
|
||||
}
|
||||
|
||||
int log_handler(log_type t, const char *fmt, ...) {
|
||||
va_list argv;
|
||||
int ret = 0;
|
||||
va_start(argv, fmt);
|
||||
switch (t) {
|
||||
case L_DEBUG:
|
||||
ret = log_cb.d(fmt, argv);
|
||||
break;
|
||||
case L_INFO:
|
||||
ret = log_cb.i(fmt, argv);
|
||||
break;
|
||||
case L_WARN:
|
||||
ret = log_cb.w(fmt, argv);
|
||||
break;
|
||||
case L_ERR:
|
||||
ret = log_cb.e(fmt, argv);
|
||||
log_cb.ex(1);
|
||||
break;
|
||||
}
|
||||
va_end(argv);
|
||||
return ret;
|
||||
}
|
@ -1,9 +1,9 @@
|
||||
#include <dlfcn.h>
|
||||
#include <unistd.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "magisk.h"
|
||||
#include "utils.h"
|
||||
#include "logging.h"
|
||||
#include "selinux.h"
|
||||
|
||||
#define UNLABEL_CON "u:object_r:unlabeled:s0"
|
||||
|
Loading…
Reference in New Issue
Block a user