1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170
| using namespace std; string packname; string origpath; string fakepath;
int (*orig_open)(const char *pathname, int flags, ...); int (*orig_openat)(int,const char *pathname, int flags, ...); FILE *(*orig_fopen)(const char *filename, const char *mode); static long (*orig_syscall)(long number, ...); int (*orig__NR_openat)(int,const char *pathname, int flags, ...);
void* (*orig_dlopen_CI)(const char *filename, int flag); void* (*orig_dlopen_CIV)(const char *filename, int flag, const void *extinfo); void* (*orig_dlopen_CIVV)(const char *name, int flags, const void *extinfo, void *caller_addr);
static inline bool needs_mode(int flags) { return ((flags & O_CREAT) == O_CREAT) || ((flags & O_TMPFILE) == O_TMPFILE); } bool startsWith(string str, string sub){ return str.find(sub)==0; }
bool endsWith(string s,string sub){ return s.rfind(sub)==(s.length()-sub.length()); } bool isOrigAPK(string path){
if(path==origpath){ return true; } return false; }
int fake_open(const char *pathname, int flags, ...) { mode_t mode = 0; if (needs_mode(flags)) { va_list args; va_start(args, flags); mode = static_cast<mode_t>(va_arg(args, int)); va_end(args); } string cpp_path= pathname; if(isOrigAPK(cpp_path)){ LOGI("libc_open, redirect: %s, --->: %s",pathname, fakepath.data()); return orig_open("/data/user/0/com.zj.wuaipojie/files/base.apk", flags, mode); } return orig_open(pathname, flags, mode);
}
int fake_openat(int fd, const char *pathname, int flags, ...) { mode_t mode = 0; if (needs_mode(flags)) { va_list args; va_start(args, flags); mode = static_cast<mode_t>(va_arg(args, int)); va_end(args); } LOGI("openat, fd: %d, path: %s, flags: %d, mode: %d",fd ,pathname, flags ,mode); string cpp_path= pathname; if(isOrigAPK(cpp_path)){ LOGI("libc_openat, redirect: %s, --->: %s",pathname, fakepath.data()); return orig_openat(fd,fakepath.data(), flags, mode); } return orig_openat(fd,pathname, flags, mode);
} FILE *fake_fopen(const char *filename, const char *mode) {
string cpp_path= filename; if(isOrigAPK(cpp_path)){ return orig_fopen(fakepath.data(), mode); } return orig_fopen(filename, mode); }
static long fake_syscall(long number, ...) { void *arg[7]; va_list list;
va_start(list, number); for (int i = 0; i < 7; ++i) { arg[i] = va_arg(list, void *); } va_end(list); if (number == __NR_openat){ const char *cpp_path = static_cast<const char *>(arg[1]); LOGI("syscall __NR_openat, fd: %d, path: %s, flags: %d, mode: %d",arg[0] ,arg[1], arg[2], arg[3]); if (isOrigAPK(cpp_path)){ LOGI("syscall __NR_openat, redirect: %s, --->: %s",arg[1], fakepath.data()); return orig_syscall(number,arg[0], fakepath.data() ,arg[2],arg[3]); } } return orig_syscall(number, arg[0], arg[1], arg[2], arg[3], arg[4], arg[5], arg[6]);
}
extern "C" JNIEXPORT void JNICALL Java_com_zj_wuaipojie_util_SecurityUtil_hook(JNIEnv *env, jclass clazz, jobject context) { jclass conext_class = env->GetObjectClass(context); jmethodID methodId_pack = env->GetMethodID(conext_class, "getPackageName", "()Ljava/lang/String;"); auto packname_js = reinterpret_cast<jstring>(env->CallObjectMethod(context, methodId_pack)); const char *pn = env->GetStringUTFChars(packname_js, 0); packname = string(pn);
env->ReleaseStringUTFChars(packname_js, pn); fakepath= "/data/user/0/"+ packname +"/files/base.apk";
jclass conext_class2 = env->GetObjectClass(context); jmethodID methodId_pack2 = env->GetMethodID(conext_class2,"getApplicationInfo","()Landroid/content/pm/ApplicationInfo;"); jobject application_info = env->CallObjectMethod(context,methodId_pack2); jclass pm_clazz = env->GetObjectClass(application_info);
jfieldID package_info_id = env->GetFieldID(pm_clazz,"sourceDir","Ljava/lang/String;"); auto sourceDir_js = reinterpret_cast<jstring>(env->GetObjectField(application_info,package_info_id)); const char *sourceDir = env->GetStringUTFChars(sourceDir_js, 0); origpath = string(sourceDir); LOGI("sourceDir: %s", sourceDir);
jfieldID package_info_id2 = env->GetFieldID(pm_clazz,"nativeLibraryDir","Ljava/lang/String;"); auto nativeLibraryDir_js = reinterpret_cast<jstring>(env->GetObjectField(application_info,package_info_id2)); const char *nativeLibraryDir = env->GetStringUTFChars(nativeLibraryDir_js, 0); LOGI("nativeLibraryDir: %s", nativeLibraryDir);
void *handle = dlopen("libc.so",RTLD_NOW); auto pagesize = sysconf(_SC_PAGE_SIZE); auto addr = ((uintptr_t)dlsym(handle,"open") & (-pagesize)); auto addr2 = ((uintptr_t)dlsym(handle,"openat") & (-pagesize)); auto addr3 = ((uintptr_t)fopen) & (-pagesize); auto addr4 = ((uintptr_t)syscall) & (-pagesize);
mprotect((void*)addr, pagesize, PROT_READ | PROT_WRITE | PROT_EXEC); mprotect((void*)addr2, pagesize, PROT_READ | PROT_WRITE | PROT_EXEC); mprotect((void*)addr3, pagesize, PROT_READ | PROT_WRITE | PROT_EXEC); mprotect((void*)addr4, pagesize, PROT_READ | PROT_WRITE | PROT_EXEC);
DobbyHook((void *)dlsym(handle,"open"), (void *)fake_open, (void **)&orig_open); DobbyHook((void *)dlsym(handle,"openat"), (void *)fake_openat, (void **)&orig_openat); DobbyHook((void *)fopen, (void *)fake_fopen, (void**)&orig_fopen); DobbyHook((void *)syscall, (void *)fake_syscall, (void **)&orig_syscall); }
|