Fix predefined deoptmization (#1759)

This commit is contained in:
LoveSy 2022-03-15 15:59:57 +08:00 committed by GitHub
parent 8c4c25fc40
commit 159c65d6b2
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 44 additions and 28 deletions

View File

@ -20,6 +20,14 @@
package org.lsposed.lspd.deopt; package org.lsposed.lspd.deopt;
import android.content.Context;
import android.content.pm.ApplicationInfo;
import android.content.res.AssetManager;
import android.content.res.Configuration;
import android.content.res.Resources;
import android.util.DisplayMetrics;
import android.util.TypedValue;
import java.util.HashMap; import java.util.HashMap;
/** /**
@ -40,38 +48,38 @@ public class InlinedMethodCallers {
* Key should be {@link #KEY_BOOT_IMAGE}, {@link #KEY_SYSTEM_SERVER}, or a package name * Key should be {@link #KEY_BOOT_IMAGE}, {@link #KEY_SYSTEM_SERVER}, or a package name
* of system apps or priv-apps i.e. com.android.systemui * of system apps or priv-apps i.e. com.android.systemui
*/ */
private static final HashMap<String, String[][]> CALLERS = new HashMap<>(); private static final HashMap<String, Object[][]> CALLERS = new HashMap<>();
/** /**
* format for each row: {className, methodName, methodSig} * format for each row: {className, methodName, methodSig}
*/ */
private static final String[][] BOOT_IMAGE = { private static final Object[][] BOOT_IMAGE = {
// callers of Application#attach(Context) // callers of Application#attach(Context)
{"android.app.Instrumentation", "newApplication", "(Ljava/lang/ClassLoader;Ljava/lang/String;Landroid/content/Context;)Landroid/app/Application;"}, {"android.app.Instrumentation", "newApplication", ClassLoader.class, String.class, Context.class},
{"android.app.Instrumentation", "newApplication", "(Ljava/lang/ClassLoader;Landroid/content/Context;)Landroid/app/Application;"}, {"android.app.Instrumentation", "newApplication", ClassLoader.class, Context.class},
}; };
// TODO deprecate this // TODO deprecate this
private static final String[][] BOOT_IMAGE_FOR_MIUI_RES = { private static final Object[][] BOOT_IMAGE_FOR_MIUI_RES = {
// for MIUI resources hooking // for MIUI resources hooking
{"android.content.res.MiuiResources", "init", "(Ljava/lang/String;)V"}, {"android.content.res.MiuiResources", "init", String.class},
{"android.content.res.MiuiResources", "updateMiuiImpl", "()V"}, {"android.content.res.MiuiResources", "updateMiuiImpl"},
{"android.content.res.MiuiResources", "setImpl", "(Landroid/content/res/ResourcesImpl;)V"}, {"android.content.res.MiuiResources", "setImpl", "android.content.res.ResourcesImpl"},
{"android.content.res.MiuiResources", "loadOverlayValue", "(Landroid/util/TypedValue;I)V"}, {"android.content.res.MiuiResources", "loadOverlayValue", TypedValue.class, int.class},
{"android.content.res.MiuiResources", "getThemeString", "(I)Ljava/lang/CharSequence;"}, {"android.content.res.MiuiResources", "getThemeString", CharSequence.class},
{"android.content.res.MiuiResources", "<init>", "(Ljava/lang/ClassLoader;)V"}, {"android.content.res.MiuiResources", "<init>", ClassLoader.class},
{"android.content.res.MiuiResources", "<init>", "()V"}, {"android.content.res.MiuiResources", "<init>"},
{"android.content.res.MiuiResources", "<init>", "(Landroid/content/res/AssetManager;Landroid/util/DisplayMetrics;Landroid/content/res/Configuration;)V"}, {"android.content.res.MiuiResources", "<init>", AssetManager.class, DisplayMetrics.class, Configuration.class},
{"android.miui.ResourcesManager", "initMiuiResource", "(Landroid/content/res/Resources;Ljava/lang/String;)V"}, {"android.miui.ResourcesManager", "initMiuiResource", Resources.class, String.class},
{"android.app.LoadedApk", "getResources", "()Landroid/content/res/Resources;"}, {"android.app.LoadedApk", "getResources", Resources.class},
{"android.content.res.Resources", "getSystem", "()Landroid/content/res/Resources;"}, {"android.content.res.Resources", "getSystem", Resources.class},
{"android.app.ApplicationPackageManager", "getResourcesForApplication", "(Landroid/content/pm/ApplicationInfo;)Landroid/content/res/Resources;"}, {"android.app.ApplicationPackageManager", "getResourcesForApplication", ApplicationInfo.class},
{"android.app.ContextImpl", "setResources", "(Landroid/content/res/Resources;)V"}, {"android.app.ContextImpl", "setResources", Resources.class},
}; };
private static final String[][] SYSTEM_SERVER = {}; private static final Object[][] SYSTEM_SERVER = {};
private static final String[][] SYSTEM_UI = {}; private static final Object[][] SYSTEM_UI = {};
static { static {
CALLERS.put(KEY_BOOT_IMAGE, BOOT_IMAGE); CALLERS.put(KEY_BOOT_IMAGE, BOOT_IMAGE);
@ -80,11 +88,11 @@ public class InlinedMethodCallers {
CALLERS.put("com.android.systemui", SYSTEM_UI); CALLERS.put("com.android.systemui", SYSTEM_UI);
} }
public static HashMap<String, String[][]> getAll() { public static HashMap<String, Object[][]> getAll() {
return CALLERS; return CALLERS;
} }
public static String[][] get(String where) { public static Object[][] get(String where) {
return CALLERS.get(where); return CALLERS.get(where);
} }
} }

View File

@ -25,6 +25,7 @@ import static org.lsposed.lspd.deopt.InlinedMethodCallers.KEY_BOOT_IMAGE_MIUI_RE
import static org.lsposed.lspd.deopt.InlinedMethodCallers.KEY_SYSTEM_SERVER; import static org.lsposed.lspd.deopt.InlinedMethodCallers.KEY_SYSTEM_SERVER;
import org.lsposed.lspd.nativebridge.HookBridge; import org.lsposed.lspd.nativebridge.HookBridge;
import org.lsposed.lspd.util.Hookers;
import org.lsposed.lspd.util.Utils; import org.lsposed.lspd.util.Utils;
import java.lang.reflect.Executable; import java.lang.reflect.Executable;
@ -35,18 +36,25 @@ import de.robv.android.xposed.XposedHelpers;
public class PrebuiltMethodsDeopter { public class PrebuiltMethodsDeopter {
public static void deoptMethods(String where, ClassLoader cl) { public static void deoptMethods(String where, ClassLoader cl) {
String[][] callers = InlinedMethodCallers.get(where); Object[][] callers = InlinedMethodCallers.get(where);
if (callers == null) { if (callers == null) {
return; return;
} }
for (String[] caller : callers) { for (Object[] caller : callers) {
try { try {
Class clazz = XposedHelpers.findClassIfExists(caller[0], cl); if (caller.length < 2) continue;
if (clazz == null) { if (!(caller[0] instanceof String)) continue;
continue; if (!(caller[1] instanceof String)) continue;
Executable method;
Object[] params = new Object[caller.length - 2];
System.arraycopy(caller, 2, params, 0, params.length);
if ("<init>".equals(caller[1])) {
method = XposedHelpers.findConstructorExactIfExists((String) caller[0], cl, params);
} else {
method = XposedHelpers.findMethodExactIfExists((String) caller[0], cl, (String) caller[1], params);
} }
Executable method = null;
if (method != null) { if (method != null) {
Hookers.logD("deoptimizing " + method);
HookBridge.deoptimizeMethod(method); HookBridge.deoptimizeMethod(method);
} }
} catch (Throwable throwable) { } catch (Throwable throwable) {