#include <jni.h>
#include <sys/types.h>
#include <riru.h>
#include <malloc.h>
#include <cstring>
#include <config.h>
#include <unistd.h>
#include <pthread.h>
#include <android/log.h>
#include <sys/stat.h>
#include <sys/wait.h>
#include <dlfcn.h>
#define LOGTAG "test_fridahook"
#define LOGV(...) __android_log_print(ANDROID_LOG_VERBOSE, LOGTAG , __VA_ARGS__)
#define LOGD(...) __android_log_print(ANDROID_LOG_DEBUG , LOGTAG, __VA_ARGS__)
#define LOGI(...) __android_log_print(ANDROID_LOG_INFO , LOGTAG, __VA_ARGS__)
#define LOGW(...) __android_log_print(ANDROID_LOG_WARN , LOGTAG, __VA_ARGS__)
#define LOGE(...) __android_log_print(ANDROID_LOG_ERROR , LOGTAG, __VA_ARGS__)
#if defined(__arm__)
#elif defined(__aarch64__)
#endif
int
mysystem(
char
*cmdstring,
char
*buf,
int
len);
static
int
enable_hack;
static
jstring *_appDataDir;
static
char
package_name[256];
const
char
*sopath =
"/data/local/tmp/libfg1502.so"
;
int
rirutest(JNIEnv *env, jstring appDataDir) {
if
(!appDataDir) {
LOGD(
"forkAndSpecializePre appDataDir null"
);
return
0;
}
const
char
*app_data_dir = env->GetStringUTFChars(appDataDir, NULL);
int
user = 0;
if
(
sscanf
(app_data_dir,
"/data/%*[^/]/%d/%s"
, &user, package_name) != 2) {
if
(
sscanf
(app_data_dir,
"/data/%*[^/]/%s"
, package_name) != 1) {
package_name[0] =
'\0'
;
LOGW(
"can't parse %s"
, app_data_dir);
env->ReleaseStringUTFChars(appDataDir, app_data_dir);
return
0;
}
}
env->ReleaseStringUTFChars(appDataDir, app_data_dir);
char
cmd_string[1024];
const
char
*filepath =
"/data/local/tmp/pkg.conf"
;
sprintf
(cmd_string,
"cat %s"
, filepath);
int
bufsize = 1024 * 10;
char
buf[bufsize];
mysystem(cmd_string, buf, bufsize);
int
ret = 0;
char
*item = NULL;
char
*delims =
"\r\n"
;
item =
strtok
(buf, delims);
while
(item != NULL) {
if
(
strcmp
(item, package_name) == 0) {
ret = 1;
LOGD(
"package item: %s"
, item);
break
;
}
else
{
ret = 0;
}
item =
strtok
(NULL, delims);
}
return
ret;
}
int
mysystem(
char
*cmdstring,
char
*buf,
int
len) {
int
fd[2];
pid_t pid;
int
n, count;
memset
(buf, 0, len);
if
(pipe(fd) < 0)
return
-1;
if
((pid = fork()) < 0){
LOGE(
"fork faild"
);
return
-1;
}
else
if
(pid > 0) {
close(fd[1]);
count = 0;
while
((n = read(fd[0], buf + count, len)) > 0 && count > len)
count += n;
close(fd[0]);
if
(waitpid(pid, NULL, 0) > 0)
return
-1;
}
else
{
close(fd[0]);
if
(fd[1] != STDOUT_FILENO) {
if
(dup2(fd[1], STDOUT_FILENO) != STDOUT_FILENO) {
return
-1;
}
close(fd[1]);
}
if
(execl(
"/system/bin/sh"
,
"sh"
,
"-c"
, cmdstring, (
char
*) 0) == -1){
LOGE(
"execl (%s) faild"
, cmdstring);
return
-1;
}
}
return
0;
}
static
void
forkAndSpecializePre(
JNIEnv *env, jclass clazz, jint *uid, jint *gid, jintArray *gids, jint *runtimeFlags,
jobjectArray *rlimits, jint *mountExternal, jstring *seInfo, jstring *niceName,
jintArray *fdsToClose, jintArray *fdsToIgnore, jboolean *is_child_zygote,
jstring *instructionSet, jstring *appDataDir, jboolean *isTopApp, jobjectArray *pkgDataInfoList,
jobjectArray *whitelistedDataInfoList, jboolean *bindMountAppDataDirs, jboolean *bindMountAppStorageDirs) {
_appDataDir = appDataDir;
}
static
void
forkAndSpecializePost(JNIEnv *env, jclass clazz, jint res) {
if
(res == 0) {
enable_hack = rirutest(env, *_appDataDir);
if
(enable_hack) {
char
cmd_string[1024];
const
char
*filepath =
"/data/local/tmp/"
;
sprintf
(cmd_string,
"%s%s/libtest.so"
, filepath, package_name);
LOGE(
"Start Load Library"
);
void
* handle = dlopen( cmd_string, RTLD_LAZY );
if
( handle != 0) {
LOGE(
"Load %s success!"
, cmd_string);
}
else
{
LOGE(
"Load %s failed! dlopen failed: %s\n"
, cmd_string, dlerror());
}
}
riru_set_unload_allowed(
true
);
}
else
{
}
}
static
void
specializeAppProcessPre(
JNIEnv *env, jclass clazz, jint *uid, jint *gid, jintArray *gids, jint *runtimeFlags,
jobjectArray *rlimits, jint *mountExternal, jstring *seInfo, jstring *niceName,
jboolean *startChildZygote, jstring *instructionSet, jstring *appDataDir,
jboolean *isTopApp, jobjectArray *pkgDataInfoList, jobjectArray *whitelistedDataInfoList,
jboolean *bindMountAppDataDirs, jboolean *bindMountAppStorageDirs) {
}
static
void
specializeAppProcessPost(
JNIEnv *env, jclass clazz) {
riru_set_unload_allowed(
true
);
}
static
void
forkSystemServerPre(
JNIEnv *env, jclass clazz, uid_t *uid, gid_t *gid, jintArray *gids, jint *runtimeFlags,
jobjectArray *rlimits, jlong *permittedCapabilities, jlong *effectiveCapabilities) {
}
static
void
forkSystemServerPost(JNIEnv *env, jclass clazz, jint res) {
if
(res == 0) {
}
else
{
}
}
static
void
onModuleLoaded() {
}
extern
"C"
{
int
riru_api_version;
const
char
*riru_magisk_module_path = nullptr;
int
*riru_allow_unload = nullptr;
static
auto
module = RiruVersionedModuleInfo{
.moduleApiVersion = riru::moduleApiVersion,
.moduleInfo= RiruModuleInfo{
.supportHide =
true
,
.version = riru::moduleVersionCode,
.versionName = riru::moduleVersionName,
.onModuleLoaded = onModuleLoaded,
.forkAndSpecializePre = forkAndSpecializePre,
.forkAndSpecializePost = forkAndSpecializePost,
.forkSystemServerPre = forkSystemServerPre,
.forkSystemServerPost = forkSystemServerPost,
.specializeAppProcessPre = specializeAppProcessPre,
.specializeAppProcessPost = specializeAppProcessPost
}
};
RiruVersionedModuleInfo *init(Riru *riru) {
auto
core_max_api_version = riru->riruApiVersion;
riru_api_version = core_max_api_version <= riru::moduleApiVersion ? core_max_api_version : riru::moduleApiVersion;
module.moduleApiVersion = riru_api_version;
riru_magisk_module_path = strdup(riru->magiskModulePath);
if
(riru_api_version >= 25) {
riru_allow_unload = riru->allowUnload;
}
return
&module;
}
}