From 4ae471a7b9924ad5f5df3a666b74382d9fb3bf66 Mon Sep 17 00:00:00 2001 From: OTKUSteyler <90369564+OTKUSteyler@users.noreply.github.com> Date: Fri, 21 Nov 2025 23:47:28 +0100 Subject: [PATCH] Update Main.kt --- .../kotlin/io/github/revenge/xposed/Main.kt | 107 ++++++++++++------ 1 file changed, 72 insertions(+), 35 deletions(-) diff --git a/app/src/main/kotlin/io/github/revenge/xposed/Main.kt b/app/src/main/kotlin/io/github/revenge/xposed/Main.kt index 7818082..0031ce2 100644 --- a/app/src/main/kotlin/io/github/revenge/xposed/Main.kt +++ b/app/src/main/kotlin/io/github/revenge/xposed/Main.kt @@ -1,11 +1,5 @@ -package GoonXposed.xposed +package ShiggyXposed.xposed -import GoonXposed.xposed.modules.* -import GoonXposed.xposed.module.appearance.ThemesModule -import GoonXposed.xposed.modules.appearance.FontsModule -import GoonXposed.xposed.modules.appearance.SysColorsModule -import GoonXposed.xposed.modules.bridge.AdditionalBridgeMethodsModule -import GoonXposed.xposed.modules.bridge.BridgeModule import android.app.Activity import android.content.Context import android.content.ContextWrapper @@ -13,48 +7,91 @@ import android.os.Bundle import de.robv.android.xposed.IXposedHookLoadPackage import de.robv.android.xposed.IXposedHookZygoteInit import de.robv.android.xposed.callbacks.XC_LoadPackage +import GoonXposed.xposed.Utils.Log +import GoonXposed.xposed.modules.* +import GoonXposed.xposed.modules.appearance.FontsModule +import GoonXposed.xposed.modules.appearance.SysColorsModule +import GoonXposed.xposed.modules.appearance.ThemesModule +import GoonXposed.xposed.modules.bridge.AdditionalBridgeMethodsModule +import GoonXposed.xposed.modules.bridge.BridgeModule +import GoonXposed.xposed.modules.no_track.BlockCrashReportingModule +import GoonXposed.xposed.modules.no_track.BlockDeepLinksTrackingModule +import kotlinx.coroutines.CompletableDeferred + +object HookStateHolder { + /** + * Whether all hooks are completed, and we are ready to load the JS bundle. + */ + val readyDeferred = CompletableDeferred() + + /** + * Whether we have successfully received a [Context] yet. + * Sometimes the app process is recreated and Xposed hooks way too late for us to get [Context] from [ContextWrapper.attachBaseContext]. + * But since Xposed hooks before [Activity.onCreate], we can still get it from there and still initialize properly. + */ + @Volatile + var gotContext = false +} class Main : Module(), IXposedHookLoadPackage, IXposedHookZygoteInit { private var hooked = false - private val modules = - mutableListOf( - HookScriptLoaderModule(), - BridgeModule(), - AdditionalBridgeMethodsModule(), - UpdaterModule(), - FixResourcesModule(), - LogBoxModule(), - FontsModule(), - SysColorsModule(), - ThemesModule(), - ) + private val modules = mutableListOf( + HookScriptLoaderModule, + BridgeModule, + AdditionalBridgeMethodsModule, + PluginsModule(), + UpdaterModule, + FixResourcesModule, + BlockDeepLinksTrackingModule, + BlockCrashReportingModule, + LogBoxModule, + CacheModule, + FontsModule, + ThemesModule, + SysColorsModule + ) init { - modules.add(PayloadGlobalModule(modules)) + modules += PayloadGlobalModule(modules) } override fun initZygote(startupParam: IXposedHookZygoteInit.StartupParam) { for (module in modules) module.onInit(startupParam) } - override fun handleLoadPackage(param: XC_LoadPackage.LoadPackageParam) = - with(param) { - if (hooked) return + override fun handleLoadPackage(param: XC_LoadPackage.LoadPackageParam) = with(param) { + if (hooked) return - val reactActivity = classLoader.loadClass(Constants.TARGET_ACTIVITY) + val reactActivity = classLoader.loadClass(Constants.TARGET_ACTIVITY) - ContextWrapper::class.java.hookMethod("attachBaseContext", Context::class.java) { - after { this@Main.onContext(args[0] as Context) } - } - - reactActivity.hookMethod("onCreate", Bundle::class.java) { - after { this@Main.onActivity(thisObject as Activity) } - } - - this@Main.onLoad(param) - - hooked = true + ContextWrapper::class.java.hookMethod("attachBaseContext", Context::class.java) { + after { + val ctx = args[0] as Context + HookStateHolder.gotContext = true + Log.i("Received Context") + this@Main.onContext(ctx) } + } + + reactActivity.hookMethod("onCreate", Bundle::class.java) { + after { + val act = thisObject as Activity + Log.i("Received Activity") + + if (!HookStateHolder.gotContext) { + Log.w("Activity created before we got Context, process may have been recreated!") + this@Main.onContext(act.applicationContext) + } + + this@Main.onActivity(act) + HookStateHolder.readyDeferred.complete(Unit) + } + } + + this@Main.onLoad(param) + + hooked = true + } override fun onLoad(packageParam: XC_LoadPackage.LoadPackageParam) { for (module in modules) module.onLoad(packageParam)