├── demoApp ├── .gitignore ├── src │ └── main │ │ ├── jni │ │ ├── Application.mk │ │ ├── Android.mk │ │ └── hello.c │ │ ├── res │ │ ├── values │ │ │ ├── strings.xml │ │ │ ├── styles.xml │ │ │ └── colors.xml │ │ ├── mipmap-hdpi │ │ │ ├── ic_launcher.png │ │ │ └── ic_launcher_round.png │ │ ├── mipmap-mdpi │ │ │ ├── ic_launcher.png │ │ │ └── ic_launcher_round.png │ │ ├── mipmap-xhdpi │ │ │ ├── ic_launcher.png │ │ │ └── ic_launcher_round.png │ │ ├── mipmap-xxhdpi │ │ │ ├── ic_launcher.png │ │ │ └── ic_launcher_round.png │ │ ├── mipmap-xxxhdpi │ │ │ ├── ic_launcher.png │ │ │ └── ic_launcher_round.png │ │ └── layout │ │ │ └── activity_main.xml │ │ ├── java │ │ └── lab │ │ │ └── galaxy │ │ │ └── yahfa │ │ │ └── demoApp │ │ │ ├── ClassWithJNIMethod.java │ │ │ ├── ClassWithCtor.java │ │ │ ├── ClassWithStaticMethod.java │ │ │ ├── ClassWithVirtualMethod.java │ │ │ ├── Hook_Log_e.java │ │ │ ├── MainApp.java │ │ │ └── MainActivity.java │ │ └── AndroidManifest.xml ├── build.gradle └── README.md ├── demoPlugin ├── .gitignore ├── src │ └── main │ │ ├── res │ │ └── values │ │ │ └── strings.xml │ │ ├── AndroidManifest.xml │ │ └── java │ │ └── lab │ │ └── galaxy │ │ └── yahfa │ │ ├── demoPlugin │ │ ├── Hook_Log_e.java │ │ ├── Hook_ClassWithCtor.java │ │ ├── Hook_ClassWithJNIMethod_fromJNI.java │ │ ├── Hook_String_startsWith.java │ │ ├── Hook_ClassWithStaticMethod_tac.java │ │ └── Hook_ClassWithVirtualMethod_tac.java │ │ └── HookInfo.java ├── build.gradle └── README.md ├── library ├── .gitignore ├── src │ ├── main │ │ ├── res │ │ │ └── values │ │ │ │ └── strings.xml │ │ ├── AndroidManifest.xml │ │ ├── jni │ │ │ ├── trampoline.h │ │ │ ├── common.h │ │ │ ├── trampoline.c │ │ │ ├── utils.c │ │ │ └── HookMain.c │ │ └── java │ │ │ └── lab │ │ │ └── galaxy │ │ │ └── yahfa │ │ │ ├── HookAnnotation.java │ │ │ └── HookMain.java │ └── androidTest │ │ └── java │ │ └── lab │ │ └── galaxy │ │ └── yahfa │ │ └── HookingTest.java ├── build.gradle └── CMakeLists.txt ├── settings.gradle ├── gradle └── wrapper │ ├── gradle-wrapper.jar │ └── gradle-wrapper.properties ├── .gitignore ├── .github └── workflows │ └── ci.yml ├── gradle.properties ├── gradlew.bat ├── README.md ├── gradlew └── LICENSE /demoApp/.gitignore: -------------------------------------------------------------------------------- 1 | /build 2 | -------------------------------------------------------------------------------- /demoPlugin/.gitignore: -------------------------------------------------------------------------------- 1 | /build 2 | -------------------------------------------------------------------------------- /library/.gitignore: -------------------------------------------------------------------------------- 1 | /build 2 | -------------------------------------------------------------------------------- /settings.gradle: -------------------------------------------------------------------------------- 1 | include ':demoApp', ':library', ':demoPlugin' 2 | -------------------------------------------------------------------------------- /demoApp/src/main/jni/Application.mk: -------------------------------------------------------------------------------- 1 | APP_ABI := arm64-v8a armeabi-v7a x86 2 | -------------------------------------------------------------------------------- /gradle/wrapper/gradle-wrapper.jar: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/PAGalaxyLab/YAHFA/HEAD/gradle/wrapper/gradle-wrapper.jar -------------------------------------------------------------------------------- /library/src/main/res/values/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | YAHFA 3 | 4 | -------------------------------------------------------------------------------- /demoApp/src/main/res/values/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | YAHFA Demo 3 | 4 | -------------------------------------------------------------------------------- /demoPlugin/src/main/res/values/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | YAHFA demoPlugin 3 | 4 | -------------------------------------------------------------------------------- /demoApp/src/main/res/mipmap-hdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/PAGalaxyLab/YAHFA/HEAD/demoApp/src/main/res/mipmap-hdpi/ic_launcher.png -------------------------------------------------------------------------------- /demoApp/src/main/res/mipmap-mdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/PAGalaxyLab/YAHFA/HEAD/demoApp/src/main/res/mipmap-mdpi/ic_launcher.png -------------------------------------------------------------------------------- /demoApp/src/main/res/mipmap-xhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/PAGalaxyLab/YAHFA/HEAD/demoApp/src/main/res/mipmap-xhdpi/ic_launcher.png -------------------------------------------------------------------------------- /demoApp/src/main/res/mipmap-xxhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/PAGalaxyLab/YAHFA/HEAD/demoApp/src/main/res/mipmap-xxhdpi/ic_launcher.png -------------------------------------------------------------------------------- /demoApp/src/main/res/mipmap-xxxhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/PAGalaxyLab/YAHFA/HEAD/demoApp/src/main/res/mipmap-xxxhdpi/ic_launcher.png -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | *.iml 2 | .gradle 3 | /local.properties 4 | /.idea 5 | .DS_Store 6 | /build 7 | /captures 8 | .externalNativeBuild 9 | *.swp 10 | *.aar 11 | -------------------------------------------------------------------------------- /demoApp/src/main/res/mipmap-hdpi/ic_launcher_round.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/PAGalaxyLab/YAHFA/HEAD/demoApp/src/main/res/mipmap-hdpi/ic_launcher_round.png -------------------------------------------------------------------------------- /demoApp/src/main/res/mipmap-mdpi/ic_launcher_round.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/PAGalaxyLab/YAHFA/HEAD/demoApp/src/main/res/mipmap-mdpi/ic_launcher_round.png -------------------------------------------------------------------------------- /demoApp/src/main/res/mipmap-xhdpi/ic_launcher_round.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/PAGalaxyLab/YAHFA/HEAD/demoApp/src/main/res/mipmap-xhdpi/ic_launcher_round.png -------------------------------------------------------------------------------- /demoApp/src/main/res/mipmap-xxhdpi/ic_launcher_round.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/PAGalaxyLab/YAHFA/HEAD/demoApp/src/main/res/mipmap-xxhdpi/ic_launcher_round.png -------------------------------------------------------------------------------- /demoApp/src/main/res/mipmap-xxxhdpi/ic_launcher_round.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/PAGalaxyLab/YAHFA/HEAD/demoApp/src/main/res/mipmap-xxxhdpi/ic_launcher_round.png -------------------------------------------------------------------------------- /demoApp/src/main/jni/Android.mk: -------------------------------------------------------------------------------- 1 | LOCAL_PATH:= $(call my-dir) 2 | include $(CLEAR_VARS) 3 | 4 | LOCAL_SRC_FILES:= hello.c 5 | 6 | LOCAL_LDLIBS := -llog 7 | 8 | LOCAL_MODULE:= hello 9 | 10 | include $(BUILD_SHARED_LIBRARY) 11 | -------------------------------------------------------------------------------- /demoApp/src/main/jni/hello.c: -------------------------------------------------------------------------------- 1 | // 2 | // Created by lrk on 5/4/17. 3 | // 4 | #include 5 | 6 | jstring Java_lab_galaxy_yahfa_demoApp_ClassWithJNIMethod_fromJNI(JNIEnv *env, jclass clazz) { 7 | return (*env)->NewStringUTF(env, "hello from JNI"); 8 | } -------------------------------------------------------------------------------- /gradle/wrapper/gradle-wrapper.properties: -------------------------------------------------------------------------------- 1 | distributionBase=GRADLE_USER_HOME 2 | distributionPath=wrapper/dists 3 | zipStoreBase=GRADLE_USER_HOME 4 | zipStorePath=wrapper/dists 5 | distributionUrl=https\://services.gradle.org/distributions/gradle-6.5-bin.zip 6 | -------------------------------------------------------------------------------- /demoApp/src/main/res/values/styles.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /demoApp/src/main/res/values/colors.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | #3F51B5 4 | #303F9F 5 | #FF4081 6 | 7 | -------------------------------------------------------------------------------- /demoPlugin/build.gradle: -------------------------------------------------------------------------------- 1 | apply plugin: 'com.android.application' 2 | 3 | android { 4 | compileSdkVersion 28 5 | defaultConfig { 6 | applicationId "lab.galaxy.yahfa.demoPlugin" 7 | minSdkVersion 21 8 | targetSdkVersion 28 9 | versionCode 1 10 | versionName "1.0" 11 | } 12 | } -------------------------------------------------------------------------------- /demoApp/src/main/java/lab/galaxy/yahfa/demoApp/ClassWithJNIMethod.java: -------------------------------------------------------------------------------- 1 | package lab.galaxy.yahfa.demoApp; 2 | 3 | /** 4 | * Created by lrk on 5/4/17. 5 | */ 6 | 7 | public class ClassWithJNIMethod { 8 | static { 9 | System.loadLibrary("hello"); 10 | } 11 | 12 | public native static String fromJNI(); 13 | } 14 | -------------------------------------------------------------------------------- /demoApp/src/main/java/lab/galaxy/yahfa/demoApp/ClassWithCtor.java: -------------------------------------------------------------------------------- 1 | package lab.galaxy.yahfa.demoApp; 2 | 3 | public class ClassWithCtor { 4 | private String field; 5 | 6 | public ClassWithCtor(String param) { 7 | field = param; 8 | } 9 | 10 | public String getField() { 11 | return field; 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /library/src/main/AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 4 | 5 | 9 | 10 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /.github/workflows/ci.yml: -------------------------------------------------------------------------------- 1 | name: Android CI 2 | 3 | on: [push, pull_request] 4 | 5 | jobs: 6 | build: 7 | runs-on: ubuntu-latest 8 | steps: 9 | - uses: actions/checkout@v1 10 | - uses: actions/setup-java@v1 11 | with: 12 | java-version: 1.8 13 | - name: build 14 | run: ./gradlew :library:build --stacktrace 15 | 16 | 17 | -------------------------------------------------------------------------------- /library/src/main/jni/trampoline.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by liuruikai756 on 05/07/2017. 3 | // 4 | 5 | #ifndef YAHFA_TAMPOLINE_H 6 | #define YAHFA_TAMPOLINE_H 7 | 8 | void setupTrampoline(unsigned char offset); 9 | 10 | void *genTrampoline(void *toMethod, void *entrypoint); 11 | 12 | #define TRAMPOLINE_SPACE_SIZE 4096 // 4k mem page size 13 | 14 | #endif //YAHFA_TAMPOLINE_H 15 | -------------------------------------------------------------------------------- /demoPlugin/src/main/AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 4 | 5 | 8 | 11 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /demoApp/src/main/java/lab/galaxy/yahfa/demoApp/ClassWithStaticMethod.java: -------------------------------------------------------------------------------- 1 | package lab.galaxy.yahfa.demoApp; 2 | 3 | /** 4 | * Created by liuruikai756 on 30/03/2017. 5 | */ 6 | 7 | public class ClassWithStaticMethod { 8 | public static String tac(String a, String b, String c, String d) { 9 | try { 10 | return d + c + b + a; 11 | } catch (Exception e) { 12 | e.printStackTrace(); 13 | return ""; 14 | } 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /demoApp/src/main/java/lab/galaxy/yahfa/demoApp/ClassWithVirtualMethod.java: -------------------------------------------------------------------------------- 1 | package lab.galaxy.yahfa.demoApp; 2 | 3 | /** 4 | * Created by liuruikai756 on 30/03/2017. 5 | */ 6 | 7 | public class ClassWithVirtualMethod { 8 | final public String tac(String a, String b, String c, String d) { 9 | try { 10 | return d + c + b + a; 11 | } catch (Exception e) { 12 | e.printStackTrace(); 13 | return ""; 14 | } 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /demoApp/build.gradle: -------------------------------------------------------------------------------- 1 | apply plugin: 'com.android.application' 2 | 3 | android { 4 | compileSdkVersion 28 5 | defaultConfig { 6 | applicationId "lab.galaxy.yahfa.demoApp" 7 | minSdkVersion 21 8 | targetSdkVersion 28 9 | versionCode 1 10 | versionName "1.0" 11 | } 12 | externalNativeBuild { 13 | ndkBuild { 14 | path 'src/main/jni/Android.mk' 15 | } 16 | } 17 | } 18 | 19 | dependencies { 20 | implementation project(':library') 21 | } 22 | -------------------------------------------------------------------------------- /demoApp/README.md: -------------------------------------------------------------------------------- 1 | YAHFA demoApp 2 | ------------- 3 | 4 | Here is a demo app which shows the basic usage of YAHFA. 5 | 6 | ## Prerequisite 7 | 8 | Please build and push the [demoPlugin](https://github.com/rk700/YAHFA/tree/master/demoPlugin) APK to sdcard before running the demo app. 9 | 10 | ## Usage 11 | 12 | Click the button and take a look at the app log. 13 | 14 | ## What happened 15 | 16 | The demo app loads and applies the plugin APK, which hooks the following methods: 17 | 18 | - Log.e() 19 | - String.startsWith() 20 | - ClassWithVirtualMethod.tac() 21 | - ClassWithStaticMethod.tac() 22 | 23 | After hooking, the arguments would be displayed and then the original method be called. 24 | -------------------------------------------------------------------------------- /demoApp/src/main/java/lab/galaxy/yahfa/demoApp/Hook_Log_e.java: -------------------------------------------------------------------------------- 1 | package lab.galaxy.yahfa.demoApp; 2 | 3 | import android.util.Log; 4 | 5 | public class Hook_Log_e { 6 | public static String className = "android.util.Log"; 7 | public static String methodName = "e"; 8 | public static String methodSig = "(Ljava/lang/String;Ljava/lang/String;)I"; 9 | 10 | public static int hook(String tag, String msg) { 11 | Log.w("HookTest", "in Log.e(): " + tag + ", " + msg); 12 | return backup(tag, msg); 13 | } 14 | 15 | public static int backup(String tag, String msg) { 16 | Log.w("HookTest", "Log.e() should not be here"); 17 | return 1; 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /demoPlugin/src/main/java/lab/galaxy/yahfa/demoPlugin/Hook_Log_e.java: -------------------------------------------------------------------------------- 1 | package lab.galaxy.yahfa.demoPlugin; 2 | 3 | import android.util.Log; 4 | 5 | import static lab.galaxy.yahfa.HookInfo.TAG; 6 | 7 | /** 8 | * Created by liuruikai756 on 30/03/2017. 9 | */ 10 | 11 | public class Hook_Log_e { 12 | public static String className = "android.util.Log"; 13 | public static String methodName = "e"; 14 | public static String methodSig = "(Ljava/lang/String;Ljava/lang/String;)I"; 15 | 16 | public static int hook(String tag, String msg) { 17 | Log.w(TAG, "in Log.e(): " + tag + ", " + msg); 18 | return backup(tag, msg); 19 | } 20 | 21 | public static int backup(String tag, String msg) { 22 | Log.w(TAG, "Log.e() should not be here"); 23 | return 1; 24 | } 25 | } 26 | -------------------------------------------------------------------------------- /demoPlugin/src/main/java/lab/galaxy/yahfa/demoPlugin/Hook_ClassWithCtor.java: -------------------------------------------------------------------------------- 1 | package lab.galaxy.yahfa.demoPlugin; 2 | 3 | import android.util.Log; 4 | 5 | import static lab.galaxy.yahfa.HookInfo.TAG; 6 | 7 | public class Hook_ClassWithCtor { 8 | public static String className = "lab.galaxy.yahfa.demoApp.ClassWithCtor"; 9 | public static String methodName = ""; 10 | public static String methodSig = 11 | "(Ljava/lang/String;)V"; 12 | 13 | public static void hook(Object thiz, String param) { 14 | Log.w(TAG, "in ClassWithCtor.: " + param); 15 | backup(thiz, "hooked " + param); 16 | return; 17 | } 18 | 19 | public static void backup(Object thiz, String param) { 20 | Log.w(TAG, "ClassWithVirtualMethod.tac() should not be here"); 21 | return; 22 | } 23 | } 24 | -------------------------------------------------------------------------------- /demoPlugin/src/main/java/lab/galaxy/yahfa/demoPlugin/Hook_ClassWithJNIMethod_fromJNI.java: -------------------------------------------------------------------------------- 1 | package lab.galaxy.yahfa.demoPlugin; 2 | 3 | import android.util.Log; 4 | 5 | import static lab.galaxy.yahfa.HookInfo.TAG; 6 | 7 | /** 8 | * Created by lrk on 5/4/17. 9 | */ 10 | 11 | public class Hook_ClassWithJNIMethod_fromJNI { 12 | public static String className = "lab.galaxy.yahfa.demoApp.ClassWithJNIMethod"; 13 | public static String methodName = "fromJNI"; 14 | public static String methodSig = "()Ljava/lang/String;"; 15 | 16 | // calling origin method is no longer available for JNI methods 17 | public static String hook() { 18 | Log.w(TAG, "calling fromJNI"); 19 | return backup(); 20 | } 21 | 22 | public static String backup() { 23 | Log.w(TAG, "calling fromJNI"); 24 | return "1234"; 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /demoPlugin/src/main/java/lab/galaxy/yahfa/demoPlugin/Hook_String_startsWith.java: -------------------------------------------------------------------------------- 1 | package lab.galaxy.yahfa.demoPlugin; 2 | 3 | import android.util.Log; 4 | 5 | import static lab.galaxy.yahfa.HookInfo.TAG; 6 | 7 | /** 8 | * Created by liuruikai756 on 30/03/2017. 9 | */ 10 | 11 | public class Hook_String_startsWith { 12 | public static String className = "java.lang.String"; 13 | public static String methodName = "startsWith"; 14 | public static String methodSig = "(Ljava/lang/String;)Z"; 15 | 16 | public static boolean hook(String thiz, String prefix) { 17 | Log.w(TAG, "in String.startsWith(): " + thiz + ", " + prefix); 18 | return backup(thiz, prefix); 19 | } 20 | 21 | public static boolean backup(String thiz, String prefix) { 22 | Log.w(TAG, "String.startsWith() should not be here"); 23 | return false; 24 | } 25 | } 26 | -------------------------------------------------------------------------------- /gradle.properties: -------------------------------------------------------------------------------- 1 | ## Project-wide Gradle settings. 2 | # 3 | # For more details on how to configure your build environment visit 4 | # http://www.gradle.org/docs/current/userguide/build_environment.html 5 | # 6 | # Specifies the JVM arguments used for the daemon process. 7 | # The setting is particularly useful for tweaking memory settings. 8 | # Default value: -Xmx1024m -XX:MaxPermSize=256m 9 | # org.gradle.jvmargs=-Xmx2048m -XX:MaxPermSize=512m -XX:+HeapDumpOnOutOfMemoryError -Dfile.encoding=UTF-8 10 | # 11 | # When configured, Gradle will run in incubating parallel mode. 12 | # This option should only be used with decoupled projects. More details, visit 13 | # http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects 14 | # org.gradle.parallel=true 15 | #Wed Dec 06 09:59:46 CST 2017 16 | android.enableJetifier=true 17 | android.useAndroidX=true 18 | org.gradle.jvmargs=-Xmx1536m 19 | -------------------------------------------------------------------------------- /demoApp/src/main/res/layout/activity_main.xml: -------------------------------------------------------------------------------- 1 | 2 | 7 | 8 |