From cb6e930e3f0b1e19bb50284c52b48d2465403238 Mon Sep 17 00:00:00 2001
From: Nullptr <52071314+Dr-TSNG@users.noreply.github.com>
Date: Fri, 18 Feb 2022 11:01:39 +0800
Subject: [PATCH] Unit test
---
gradle/wrapper/gradle-wrapper.properties | 2 +-
library/build.gradle.kts | 7 +++
settings.gradle.kts | 1 +
test/.gitignore | 1 +
test/build.gradle.kts | 57 +++++++++++++++++++
test/proguard-rules.pro | 21 +++++++
.../java/org/lsposed/lsplant/UnitTest.java | 17 ++++++
test/src/main/AndroidManifest.xml | 8 +++
.../java/org/lsposed/lsplant/LSPTest.java | 10 ++++
test/src/main/jni/CMakeLists.txt | 10 ++++
test/src/main/jni/test.cpp | 55 ++++++++++++++++++
11 files changed, 188 insertions(+), 1 deletion(-)
create mode 100644 test/.gitignore
create mode 100644 test/build.gradle.kts
create mode 100644 test/proguard-rules.pro
create mode 100644 test/src/androidTest/java/org/lsposed/lsplant/UnitTest.java
create mode 100644 test/src/main/AndroidManifest.xml
create mode 100644 test/src/main/java/org/lsposed/lsplant/LSPTest.java
create mode 100644 test/src/main/jni/CMakeLists.txt
create mode 100644 test/src/main/jni/test.cpp
diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties
index 2e6e589..41dfb87 100644
--- a/gradle/wrapper/gradle-wrapper.properties
+++ b/gradle/wrapper/gradle-wrapper.properties
@@ -1,5 +1,5 @@
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
-distributionUrl=https\://services.gradle.org/distributions/gradle-7.3.3-bin.zip
+distributionUrl=https\://services.gradle.org/distributions/gradle-7.4-bin.zip
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists
diff --git a/library/build.gradle.kts b/library/build.gradle.kts
index 2a6ce83..fa33063 100644
--- a/library/build.gradle.kts
+++ b/library/build.gradle.kts
@@ -34,6 +34,13 @@ android {
buildFeatures {
prefab = true
+ prefabPublishing = true
+ }
+
+ prefab {
+ create("lsplant") {
+ headers = "jni/include"
+ }
}
defaultConfig {
diff --git a/settings.gradle.kts b/settings.gradle.kts
index 3839100..82f2921 100644
--- a/settings.gradle.kts
+++ b/settings.gradle.kts
@@ -9,4 +9,5 @@ dependencyResolutionManagement {
rootProject.name = "LSPlant"
include(
":library",
+ ":test"
)
diff --git a/test/.gitignore b/test/.gitignore
new file mode 100644
index 0000000..42afabf
--- /dev/null
+++ b/test/.gitignore
@@ -0,0 +1 @@
+/build
\ No newline at end of file
diff --git a/test/build.gradle.kts b/test/build.gradle.kts
new file mode 100644
index 0000000..382f4f0
--- /dev/null
+++ b/test/build.gradle.kts
@@ -0,0 +1,57 @@
+plugins {
+ id("com.android.application")
+}
+
+val androidTargetSdkVersion: Int by rootProject.extra
+val androidMinSdkVersion: Int by rootProject.extra
+val androidBuildToolsVersion: String by rootProject.extra
+val androidCompileSdkVersion: Int by rootProject.extra
+val androidCompileNdkVersion: String by rootProject.extra
+
+android {
+ namespace = "org.lsposed.lsplant.test"
+ compileSdk = androidCompileSdkVersion
+ ndkVersion = androidCompileNdkVersion
+ buildToolsVersion = androidBuildToolsVersion
+
+ buildFeatures {
+ prefab = true
+ }
+
+ defaultConfig {
+ applicationId = "org.lsposed.lsplant.test"
+ minSdk = androidMinSdkVersion
+ targetSdk = androidTargetSdkVersion
+ versionCode = 1
+ versionName = "1.0"
+
+ testInstrumentationRunner = "android.support.test.runner.AndroidJUnitRunner"
+ }
+
+ externalNativeBuild {
+ cmake {
+ path("src/main/jni/CMakeLists.txt")
+ }
+ }
+
+ buildTypes {
+ release {
+ isMinifyEnabled = true
+ proguardFiles(getDefaultProguardFile("proguard-android-optimize.txt"), "proguard-rules.pro")
+ }
+ }
+
+ compileOptions {
+ sourceCompatibility = JavaVersion.VERSION_11
+ targetCompatibility = JavaVersion.VERSION_11
+ }
+}
+
+dependencies {
+ implementation(project(":library"))
+ implementation("io.github.vvb2060.ndk:dobby:1.2")
+
+ testImplementation("junit:junit:4.13.2")
+ androidTestImplementation("com.android.support.test:runner:1.0.2")
+ androidTestImplementation("com.android.support.test.espresso:espresso-core:3.0.2")
+}
diff --git a/test/proguard-rules.pro b/test/proguard-rules.pro
new file mode 100644
index 0000000..481bb43
--- /dev/null
+++ b/test/proguard-rules.pro
@@ -0,0 +1,21 @@
+# Add project specific ProGuard rules here.
+# You can control the set of applied configuration files using the
+# proguardFiles setting in build.gradle.
+#
+# For more details, see
+# http://developer.android.com/guide/developing/tools/proguard.html
+
+# If your project uses WebView with JS, uncomment the following
+# and specify the fully qualified class name to the JavaScript interface
+# class:
+#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
+# public *;
+#}
+
+# Uncomment this to preserve the line number information for
+# debugging stack traces.
+#-keepattributes SourceFile,LineNumberTable
+
+# If you keep the line number information, uncomment this to
+# hide the original source file name.
+#-renamesourcefileattribute SourceFile
\ No newline at end of file
diff --git a/test/src/androidTest/java/org/lsposed/lsplant/UnitTest.java b/test/src/androidTest/java/org/lsposed/lsplant/UnitTest.java
new file mode 100644
index 0000000..72d7063
--- /dev/null
+++ b/test/src/androidTest/java/org/lsposed/lsplant/UnitTest.java
@@ -0,0 +1,17 @@
+package org.lsposed.lsplant;
+
+import android.support.test.runner.AndroidJUnit4;
+
+import org.junit.Assert;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+
+@RunWith(AndroidJUnit4.class)
+public class UnitTest {
+
+ @Test
+ public void initTest() {
+ boolean result = LSPTest.initHooker();
+ Assert.assertTrue(result);
+ }
+}
diff --git a/test/src/main/AndroidManifest.xml b/test/src/main/AndroidManifest.xml
new file mode 100644
index 0000000..b51b00f
--- /dev/null
+++ b/test/src/main/AndroidManifest.xml
@@ -0,0 +1,8 @@
+
+
+
+
+
diff --git a/test/src/main/java/org/lsposed/lsplant/LSPTest.java b/test/src/main/java/org/lsposed/lsplant/LSPTest.java
new file mode 100644
index 0000000..84dc323
--- /dev/null
+++ b/test/src/main/java/org/lsposed/lsplant/LSPTest.java
@@ -0,0 +1,10 @@
+package org.lsposed.lsplant;
+
+public class LSPTest {
+
+ static {
+ System.loadLibrary("test");
+ }
+
+ native static boolean initHooker();
+}
diff --git a/test/src/main/jni/CMakeLists.txt b/test/src/main/jni/CMakeLists.txt
new file mode 100644
index 0000000..cc4d2d6
--- /dev/null
+++ b/test/src/main/jni/CMakeLists.txt
@@ -0,0 +1,10 @@
+cmake_minimum_required(VERSION 3.18.1)
+project("lsplant_test")
+
+set(CMAKE_CXX_STANDARD 20)
+set(CMAKE_CXX_STANDARD_REQUIRED ON)
+
+add_library(test SHARED test.cpp)
+find_package(dobby REQUIRED CONFIG)
+find_package(library REQUIRED CONFIG)
+target_link_libraries(test log dobby::dobby library::lsplant)
diff --git a/test/src/main/jni/test.cpp b/test/src/main/jni/test.cpp
new file mode 100644
index 0000000..9cb4493
--- /dev/null
+++ b/test/src/main/jni/test.cpp
@@ -0,0 +1,55 @@
+#include
+#include
+#include
+
+#define _uintval(p) reinterpret_cast(p)
+#define _ptr(p) reinterpret_cast(p)
+#define _align_up(x, n) (((x) + ((n) - 1)) & ~((n) - 1))
+#define _align_down(x, n) ((x) & -(n))
+#define _page_size 4096
+#define _page_align(n) _align_up(static_cast(n), _page_size)
+#define _ptr_align(x) _ptr(_align_down(reinterpret_cast(x), _page_size))
+#define _make_rwx(p, n) ::mprotect(_ptr_align(p), \
+ _page_align(_uintval(p) + n) != _page_align(_uintval(p)) ? _page_align(n) + _page_size : _page_align(n), \
+ PROT_READ | PROT_WRITE | PROT_EXEC)
+
+bool init_result;
+
+void* InlineHooker(void* target, void* hooker) {
+ _make_rwx(target, _page_size);
+ void* origin_call;
+ if (DobbyHook(target, hooker, &origin_call) == RS_SUCCESS) {
+ return origin_call;
+ } else {
+ return nullptr;
+ }
+}
+
+bool InlineUnhooker(void* func) {
+ return DobbyDestroy(func) == RT_SUCCESS;
+}
+
+void* ArtSymbolResolver(std::string_view symbol_name) {
+ return DobbySymbolResolver("libart.so", symbol_name.data());
+}
+
+extern "C"
+JNIEXPORT jboolean JNICALL
+Java_org_lsposed_lsplant_LSPTest_initHooker(JNIEnv*, jclass) {
+ return init_result;
+}
+
+JNIEXPORT jint JNICALL
+JNI_OnLoad(JavaVM* vm, void* reserved) {
+ JNIEnv* env;
+ if (vm->GetEnv((void**) &env, JNI_VERSION_1_6) != JNI_OK) {
+ return JNI_ERR;
+ }
+ lsplant::InitInfo initInfo{
+ .inline_hooker = InlineHooker,
+ .inline_unhooker = InlineUnhooker,
+ .art_symbol_resolver = ArtSymbolResolver
+ };
+ init_result = lsplant::Init(env, initInfo);
+ return JNI_VERSION_1_6;
+}