/*
** DroidPlugin Project
**
** Copyright(c) 2015 Andy Zhang <zhangyong232@gmail.com>
**
** This file is part of DroidPlugin.
**
** DroidPlugin is free software: you can redistribute it and/or
** modify it under the terms of the GNU Lesser General Public
** License as published by the Free Software Foundation, either
** version 3 of the License, or (at your option) any later version.
**
** DroidPlugin is distributed in the hope that it will be useful,
** but WITHOUT ANY WARRANTY; without even the implied warranty of
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
** Lesser General Public License for more details.
**
** You should have received a copy of the GNU Lesser General Public
** License along with DroidPlugin. If not, see <http://www.gnu.org/licenses/lgpl.txt>
**
**/
package com.morgoo.droidplugin.hook.handle;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.pm.ActivityInfo;
import android.content.pm.ApplicationInfo;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager;
import android.content.pm.PermissionGroupInfo;
import android.content.pm.PermissionInfo;
import android.content.pm.ProviderInfo;
import android.content.pm.ResolveInfo;
import android.content.pm.ServiceInfo;
import android.os.Build;
import android.os.Build.VERSION;
import android.os.Build.VERSION_CODES;
import android.os.Parcelable;
import android.os.RemoteException;
import android.text.TextUtils;
import com.morgoo.droidplugin.hook.BaseHookHandle;
import com.morgoo.droidplugin.hook.HookedMethodHandler;
import com.morgoo.droidplugin.pm.PluginManager;
import com.morgoo.droidplugin.reflect.MethodUtils;
import com.morgoo.helper.Log;
import com.morgoo.helper.compat.IPackageDataObserverCompat;
import com.morgoo.helper.compat.ParceledListSliceCompat;
import java.lang.reflect.Method;
import java.util.ArrayList;
import java.util.List;
/**
* Created by Andy Zhang(zhangyong232@gmail.com) on 2015/2/28.
*/
public class IPackageManagerHookHandle extends BaseHookHandle {
private static final String TAG = IPackageManagerHookHandle.class.getSimpleName();
public IPackageManagerHookHandle(Context hostContext) {
super(hostContext);
}
@Override
protected void init() {
sHookedMethodHandlers.put("getPackageInfo", new getPackageInfo(mHostContext));
sHookedMethodHandlers.put("getPackageUid", new getPackageUid(mHostContext));
sHookedMethodHandlers.put("getPackageGids", new getPackageGids(mHostContext));
sHookedMethodHandlers.put("currentToCanonicalPackageNames", new currentToCanonicalPackageNames(mHostContext));
sHookedMethodHandlers.put("canonicalToCurrentPackageNames", new canonicalToCurrentPackageNames(mHostContext));
sHookedMethodHandlers.put("getPermissionInfo", new getPermissionInfo(mHostContext));
sHookedMethodHandlers.put("queryPermissionsByGroup", new queryPermissionsByGroup(mHostContext));
sHookedMethodHandlers.put("getPermissionGroupInfo", new getPermissionGroupInfo(mHostContext));
sHookedMethodHandlers.put("getAllPermissionGroups", new getAllPermissionGroups(mHostContext));
sHookedMethodHandlers.put("getApplicationInfo", new getApplicationInfo(mHostContext));
sHookedMethodHandlers.put("getActivityInfo", new getActivityInfo(mHostContext));
sHookedMethodHandlers.put("getReceiverInfo", new getReceiverInfo(mHostContext));
sHookedMethodHandlers.put("getServiceInfo", new getServiceInfo(mHostContext));
sHookedMethodHandlers.put("getProviderInfo", new getProviderInfo(mHostContext));
sHookedMethodHandlers.put("checkPermission", new checkPermission(mHostContext));
sHookedMethodHandlers.put("checkUidPermission", new checkUidPermission(mHostContext));
sHookedMethodHandlers.put("addPermission", new addPermission(mHostContext));
sHookedMethodHandlers.put("removePermission", new removePermission(mHostContext));
sHookedMethodHandlers.put("grantPermission", new grantPermission(mHostContext));
sHookedMethodHandlers.put("revokePermission", new revokePermission(mHostContext));
sHookedMethodHandlers.put("checkSignatures", new checkSignatures(mHostContext));
sHookedMethodHandlers.put("getPackagesForUid", new getPackagesForUid(mHostContext));
sHookedMethodHandlers.put("getNameForUid", new getNameForUid(mHostContext));
sHookedMethodHandlers.put("getUidForSharedUser", new getUidForSharedUser(mHostContext));
sHookedMethodHandlers.put("getFlagsForUid", new getFlagsForUid(mHostContext));
sHookedMethodHandlers.put("resolveIntent", new resolveIntent(mHostContext));
sHookedMethodHandlers.put("queryIntentActivities", new queryIntentActivities(mHostContext));
sHookedMethodHandlers.put("queryIntentActivityOptions", new queryIntentActivityOptions(mHostContext));
sHookedMethodHandlers.put("queryIntentReceivers", new queryIntentReceivers(mHostContext));
sHookedMethodHandlers.put("resolveService", new resolveService(mHostContext));
sHookedMethodHandlers.put("queryIntentServices", new queryIntentServices(mHostContext));
sHookedMethodHandlers.put("queryIntentContentProviders", new queryIntentContentProviders(mHostContext));
sHookedMethodHandlers.put("getInstalledPackages", new getInstalledPackages(mHostContext));
sHookedMethodHandlers.put("getPackagesHoldingPermissions", new getPackagesHoldingPermissions(mHostContext));
sHookedMethodHandlers.put("getInstalledApplications", new getInstalledApplications(mHostContext));
sHookedMethodHandlers.put("getPersistentApplications", new getPersistentApplications(mHostContext));
sHookedMethodHandlers.put("resolveContentProvider", new resolveContentProvider(mHostContext));
sHookedMethodHandlers.put("querySyncProviders", new querySyncProviders(mHostContext));
sHookedMethodHandlers.put("queryContentProviders", new queryContentProviders(mHostContext));
sHookedMethodHandlers.put("getInstrumentationInfo", new getInstrumentationInfo(mHostContext));
sHookedMethodHandlers.put("queryInstrumentation", new queryInstrumentation(mHostContext));
sHookedMethodHandlers.put("getInstallerPackageName", new getInstallerPackageName(mHostContext));
sHookedMethodHandlers.put("addPackageToPreferred", new addPackageToPreferred(mHostContext));
sHookedMethodHandlers.put("removePackageFromPreferred", new removePackageFromPreferred(mHostContext));
sHookedMethodHandlers.put("getPreferredPackages", new getPreferredPackages(mHostContext));
sHookedMethodHandlers.put("resetPreferredActivities", new resetPreferredActivities(mHostContext));
sHookedMethodHandlers.put("getLastChosenActivity", new getLastChosenActivity(mHostContext));
sHookedMethodHandlers.put("setLastChosenActivity", new setLastChosenActivity(mHostContext));
sHookedMethodHandlers.put("addPreferredActivity", new addPreferredActivity(mHostContext));
sHookedMethodHandlers.put("replacePreferredActivity", new replacePreferredActivity(mHostContext));
sHookedMethodHandlers.put("clearPackagePreferredActivities", new clearPackagePreferredActivities(mHostContext));
sHookedMethodHandlers.put("getPreferredActivities", new getPreferredActivities(mHostContext));
sHookedMethodHandlers.put("getHomeActivities", new getHomeActivities(mHostContext));
sHookedMethodHandlers.put("setComponentEnabledSetting", new setComponentEnabledSetting(mHostContext));
sHookedMethodHandlers.put("getComponentEnabledSetting", new getComponentEnabledSetting(mHostContext));
sHookedMethodHandlers.put("setApplicationEnabledSetting", new setApplicationEnabledSetting(mHostContext));
sHookedMethodHandlers.put("getApplicationEnabledSetting", new getApplicationEnabledSetting(mHostContext));
sHookedMethodHandlers.put("setPackageStoppedState", new setPackageStoppedState(mHostContext));
sHookedMethodHandlers.put("deleteApplicationCacheFiles", new deleteApplicationCacheFiles(mHostContext));
sHookedMethodHandlers.put("clearApplicationUserData", new clearApplicationUserData(mHostContext));
sHookedMethodHandlers.put("getPackageSizeInfo", new getPackageSizeInfo(mHostContext));
sHookedMethodHandlers.put("performDexOpt", new performDexOpt(mHostContext));
sHookedMethodHandlers.put("movePackage", new movePackage(mHostContext));
}
private class getPackageInfo extends HookedMethodHandler {
public getPackageInfo(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1
/*public PackageInfo getPackageInfo(String packageName, int flags) throws RemoteException;*/
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public PackageInfo getPackageInfo(String packageName, int flags, int userId) throws RemoteException;*/
if (args != null) {
final int index0 = 0, index1 = 1;
String packageName = null;
if (args.length > index0) {
if (args[index0] != null && args[index0] instanceof String) {
packageName = (String) args[index0];
}
}
int flags = 0;
if (args.length > index1) {
if (args[index1] != null && args[index1] instanceof Integer) {
flags = (Integer) args[index1];
}
}
if (packageName != null) {
PackageInfo packageInfo = null;
try {
packageInfo = PluginManager.getInstance().getPackageInfo(packageName, flags);
} catch (Exception e) {
e.printStackTrace();
}
if (packageInfo != null) {
setFakedResult(packageInfo);
return true;
} else {
Log.i(TAG, "getPackageInfo(%s) fail,pkginfo is null", packageName);
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class getPackageUid extends HookedMethodHandler {
public getPackageUid(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01_r1, 4.0.3_r1
/*public int getPackageUid(String packageName) throws RemoteException;*/
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public int getPackageUid(String packageName, int userId) throws RemoteException;*/
if (args != null) {
final int index0 = 0;
String packageName = null;
if (args.length > index0) {
if (args[index0] != null && args[index0] instanceof String) {
packageName = (String) args[index0];
}
if (packageName != null && PluginManager.getInstance().isPluginPackage(packageName)) {
args[index0] = mHostContext.getPackageName();
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class getPackageGids extends HookedMethodHandler {
public getPackageGids(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01_r1, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public int[] getPackageGids(String packageName) throws RemoteException;*/
if (args != null) {
final int index0 = 0;
String packageName = null;
if (args.length > index0) {
if (args[index0] != null && args[index0] instanceof String) {
packageName = (String) args[index0];
}
if (packageName != null && PluginManager.getInstance().isPluginPackage(packageName)) {
args[index0] = mHostContext.getPackageName();
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class currentToCanonicalPackageNames extends HookedMethodHandler {
public currentToCanonicalPackageNames(Context context) {
super(context);
}
//API 2.3, 4.01_r1, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public String[] currentToCanonicalPackageNames(String[] names) throws RemoteException;*/
}
private class canonicalToCurrentPackageNames extends HookedMethodHandler {
public canonicalToCurrentPackageNames(Context context) {
super(context);
}
//API 2.3, 4.01_r1, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public String[] canonicalToCurrentPackageNames(String[] names) throws RemoteException;*/
}
private class getPermissionInfo extends HookedMethodHandler {
public getPermissionInfo(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01_r1, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public PermissionInfo getPermissionInfo(String name, int flags) throws RemoteException;*/
if (args != null) {
final int index0 = 0, index1 = 1;
if (args.length > 1 && args[index0] instanceof String && args[index1] instanceof Integer) {
String packageName = (String) args[index0];
int flags = (Integer) args[index1];
PermissionInfo permissionInfo = PluginManager.getInstance().getPermissionInfo(packageName, flags);
if (permissionInfo != null) {
setFakedResult(permissionInfo);
return true;
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class queryPermissionsByGroup extends HookedMethodHandler {
public queryPermissionsByGroup(Context context) {
super(context);
}
@Override
protected void afterInvoke(Object receiver, Method method, Object[] args, Object invokeResult) throws Throwable {
//API 2.3, 4.01_r1, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public List<PermissionInfo> queryPermissionsByGroup(String group, int flags) throws RemoteException;*/
if (args != null && invokeResult instanceof List) {
final int index0 = 0, index1 = 1;
if (args.length > 1 && args[index0] instanceof String && args[index1] instanceof Integer) {
String group = (String) args[index0];
int flags = (Integer) args[index1];
List<PermissionInfo> infos = PluginManager.getInstance().queryPermissionsByGroup(group, flags);
if (infos != null && infos.size() > 0) {
List old = (List) invokeResult;
old.addAll(infos);
}
}
}
super.afterInvoke(receiver, method, args, invokeResult);
}
}
private class getPermissionGroupInfo extends HookedMethodHandler {
public getPermissionGroupInfo(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01_r1, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public PermissionGroupInfo getPermissionGroupInfo(String name, int flags) throws RemoteException;*/
if (args != null) {
final int index0 = 0, index1 = 1;
if (args.length > 1 && args[index0] instanceof String && args[index1] instanceof Integer) {
String name = (String) args[index0];
int flags = (Integer) args[index1];
PermissionGroupInfo permissionInfo = PluginManager.getInstance().getPermissionGroupInfo(name, flags);
if (permissionInfo != null) {
setFakedResult(permissionInfo);
return true;
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class getAllPermissionGroups extends HookedMethodHandler {
public getAllPermissionGroups(Context context) {
super(context);
}
@Override
protected void afterInvoke(Object receiver, Method method, Object[] args, Object invokeResult) throws Throwable {
//API 2.3, 4.01_r1, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public List<PermissionGroupInfo> getAllPermissionGroups(int flags) throws RemoteException;*/
if (args != null && invokeResult instanceof List) {
final int index = 0;
if (args.length > index && args[index] instanceof Integer) {
int flags = (Integer) args[index];
List<PermissionGroupInfo> infos = PluginManager.getInstance().getAllPermissionGroups(flags);
if (infos != null && infos.size() > 0) {
List old = (List) invokeResult;
old.addAll(infos);
}
}
}
super.afterInvoke(receiver, method, args, invokeResult);
}
}
private class getApplicationInfo extends HookedMethodHandler {
public getApplicationInfo(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1
/* public ApplicationInfo getApplicationInfo(String packageName, int flags) throws RemoteException;*/
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public ApplicationInfo getApplicationInfo(String packageName, int flags, int userId) throws RemoteException;*/
if (args != null) {
final int index0 = 0, index1 = 1;
if (args.length >= 2 && args[index0] instanceof String && args[index1] instanceof Integer) {
String packageName = (String) args[index0];
int flags = (Integer) args[index1];
ApplicationInfo info = PluginManager.getInstance().getApplicationInfo(packageName, flags);
if (info != null) {
setFakedResult(info);
return true;
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class getActivityInfo extends HookedMethodHandler {
public getActivityInfo(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1
/* public ActivityInfo getActivityInfo(ComponentName className, int flags) throws RemoteException;*/
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public ActivityInfo getActivityInfo(ComponentName className, int flags, int userId) throws RemoteException;*/
if (args != null) {
final int index0 = 0, index1 = 1;
if (args.length >= 2 && args[index0] instanceof ComponentName && args[index1] instanceof Integer) {
ComponentName className = (ComponentName) args[index0];
int flags = (Integer) args[index1];
ActivityInfo info = PluginManager.getInstance().getActivityInfo(className, flags);
if (info != null) {
setFakedResult(info);
return true;
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class getReceiverInfo extends HookedMethodHandler {
public getReceiverInfo(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1
/*public ActivityInfo getReceiverInfo(ComponentName className, int flags) throws RemoteException;*/
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public ActivityInfo getReceiverInfo(ComponentName className, int flags, int userId) throws RemoteException;*/
if (args != null) {
final int index0 = 0, index1 = 1;
if (args.length >= 2 && args[index0] instanceof ComponentName && args[index1] instanceof Integer) {
ComponentName className = (ComponentName) args[index0];
int flags = (Integer) args[index1];
ActivityInfo info = PluginManager.getInstance().getReceiverInfo(className, flags);
if (info != null) {
setFakedResult(info);
return true;
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class getServiceInfo extends HookedMethodHandler {
public getServiceInfo(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1
/* public ServiceInfo getServiceInfo(ComponentName className, int flags) throws RemoteException;*/
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public ServiceInfo getServiceInfo(ComponentName className, int flags, int userId) throws RemoteException;*/
if (args != null) {
final int index0 = 0, index1 = 1;
if (args.length >= 2 && args[index0] instanceof ComponentName && args[index1] instanceof Integer) {
ComponentName className = (ComponentName) args[index0];
int flags = (Integer) args[index1];
ServiceInfo info = PluginManager.getInstance().getServiceInfo(className, flags);
if (info != null) {
setFakedResult(info);
return true;
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class getProviderInfo extends HookedMethodHandler {
public getProviderInfo(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3
/*public ProviderInfo getProviderInfo(ComponentName className, int flags) throws RemoteException;*/
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public ProviderInfo getProviderInfo(ComponentName className, int flags, int userId) throws RemoteException;*/
if (args != null) {
final int index0 = 0, index1 = 1;
if (args.length >= 2 && args[index0] instanceof ComponentName && args[index1] instanceof Integer) {
ComponentName className = (ComponentName) args[index0];
int flags = (Integer) args[index1];
ProviderInfo info = PluginManager.getInstance().getProviderInfo(className, flags);
if (info != null) {
setFakedResult(info);
return true;
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class checkPermission extends HookedMethodHandler {
public checkPermission(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01_r1, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public int checkPermission(String permName, String pkgName) throws RemoteException;*/
if (args != null) {
final int index = 1;
if (args.length > index && args[index] instanceof String) {
String packageName = (String) args[index];
if (PluginManager.getInstance().isPluginPackage(packageName)) {
args[index] = mHostContext.getPackageName();
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class checkUidPermission extends HookedMethodHandler {
public checkUidPermission(Context context) {
super(context);
}
//API 2.3, 4.01_r1, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public int checkUidPermission(String permName, int uid) throws RemoteException;*/
}
private class addPermission extends HookedMethodHandler {
public addPermission(Context context) {
super(context);
}
//API 2.3, 4.01_r1, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public boolean addPermission(PermissionInfo info) throws RemoteException;*/
}
private class removePermission extends HookedMethodHandler {
public removePermission(Context context) {
super(context);
}
//API 2.3, 4.01_r1, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public void removePermission(String name) throws RemoteException;*/
}
private class grantPermission extends HookedMethodHandler {
public grantPermission(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1
//NO
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public void grantPermission(String packageName, String permissionName) throws RemoteException;*/
if (args != null) {
final int index = 0;
if (args.length > index && args[index] instanceof String) {
String packageName = (String) args[index];
if (PluginManager.getInstance().isPluginPackage(packageName)) {
args[index] = mHostContext.getPackageName();
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class revokePermission extends HookedMethodHandler {
public revokePermission(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1
//NO
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public void revokePermission(String packageName, String permissionName) throws RemoteException;*/
if (args != null) {
final int index = 0;
if (args.length > index && args[index] instanceof String) {
String packageName = (String) args[index];
if (PluginManager.getInstance().isPluginPackage(packageName)) {
args[index] = mHostContext.getPackageName();
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class checkSignatures extends HookedMethodHandler {
public checkSignatures(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01_r1, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public int checkSignatures(String pkg1, String pkg2) throws android.os.RemoteException;*/
final int index0 = 0, index1 = 1;
String pkg0 = null, pkg1 = null;
if (args != null && args[index0] != null && args[index0] instanceof String) {
pkg0 = (String) args[index0];
}
if (args != null && args[index1] != null && args[index1] instanceof String) {
pkg1 = (String) args[index1];
}
if (!TextUtils.isEmpty(pkg0) && !TextUtils.isEmpty(pkg1)) {
PluginManager instance = PluginManager.getInstance();
if (instance.isPluginPackage(pkg0) && instance.isPluginPackage(pkg1)) {
int result = instance.checkSignatures(pkg0, pkg1);
setFakedResult(result);
return true;
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class getPackagesForUid extends HookedMethodHandler {
public getPackagesForUid(Context context) {
super(context);
}
//API 2.3, 4.01_r1, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public String[] getPackagesForUid(int uid) throws RemoteException*/
}
private class getNameForUid extends HookedMethodHandler {
public getNameForUid(Context context) {
super(context);
}
//API 2.3, 4.01_r1, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public String getNameForUid(int uid) throws RemoteException;*/
}
private class getUidForSharedUser extends HookedMethodHandler {
public getUidForSharedUser(Context context) {
super(context);
}
//API 2.3, 4.01_r1, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public int getUidForSharedUser(String sharedUserName) throws RemoteException;*/
}
private class getFlagsForUid extends HookedMethodHandler {
public getFlagsForUid(Context context) {
super(context);
}
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1
// NO
//API 4.4_r1, 5.0.2_r1
/*public int getFlagsForUid(int uid) throws android.os.RemoteException;*/
}
private class resolveIntent extends HookedMethodHandler {
public resolveIntent(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1
/* public ResolveInfo resolveIntent(Intent intent, String resolvedType, int flags) throws RemoteException;*/
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public ResolveInfo resolveIntent(Intent intent, String resolvedType, int flags, int userId) throws RemoteException;*/
if (args != null) {
final int index0 = 0, index1 = 1, index2 = 2;
Intent intent = null;
if (args.length > index0) {
if (args[index0] instanceof Intent) {
intent = (Intent) args[index0];
}
}
String resolvedType = null;
if (args.length > index1) {
if (args[index1] instanceof String) {
resolvedType = (String) args[index1];
}
}
Integer flags = 0;
if (args.length > index2) {
if (args[index2] instanceof Integer) {
flags = (Integer) args[index2];
}
}
if (intent != null) {
ResolveInfo info = PluginManager.getInstance().resolveIntent(intent, resolvedType, flags);
if (info != null) {
setFakedResult(info);
return true;
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class queryIntentActivities extends HookedMethodHandler {
public queryIntentActivities(Context context) {
super(context);
}
@Override
protected void afterInvoke(Object receiver, Method method, Object[] args, Object invokeResult) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1
/* public List<ResolveInfo> queryIntentActivities(Intent intent, String resolvedType, int flags) throws RemoteException;*/
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public List<ResolveInfo> queryIntentActivities(Intent intent, String resolvedType, int flags, int userId) throws RemoteException;*/
if (args != null && (invokeResult instanceof List || ParceledListSliceCompat.isParceledListSlice(invokeResult))) {
final int index0 = 0, index1 = 1, index2 = 2;
Intent intent = null;
if (args.length > index0) {
if (args[index0] instanceof Intent) {
intent = (Intent) args[index0];
}
}
String resolvedType = null;
if (args.length > index1) {
if (args[index1] instanceof String) {
resolvedType = (String) args[index1];
}
}
Integer flags = 0;
if (args.length > index2) {
if (args[index2] instanceof Integer) {
flags = (Integer) args[index2];
}
}
if (intent != null) {
List<ResolveInfo> infos = PluginManager.getInstance().queryIntentActivities(intent, resolvedType, flags);
if (infos != null && infos.size() > 0) {
if (invokeResult instanceof List) {
List old = (List) invokeResult;
old.addAll(infos);
} else if (ParceledListSliceCompat.isParceledListSlice(invokeResult)) {
if (VERSION.SDK_INT >= VERSION_CODES.JELLY_BEAN_MR2) { //Only for api 24
Method getListMethod = MethodUtils.getAccessibleMethod(invokeResult.getClass(), "getList");
List data = (List) getListMethod.invoke(invokeResult);
data.addAll(infos);
}
}
}
}
}
super.afterInvoke(receiver, method, args, invokeResult);
}
}
private class queryIntentActivityOptions extends HookedMethodHandler {
public queryIntentActivityOptions(Context context) {
super(context);
}
//API 2.3, 4.01, 4.0.3_r1
/*public List<ResolveInfo> queryIntentActivityOptions(ComponentName caller, Intent[] specifics, String[] specificTypes, Intent intent, String resolvedType, int flags) throws RemoteException;*/
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public List<ResolveInfo> queryIntentActivityOptions(ComponentName caller, Intent[] specifics, String[] specificTypes, Intent intent, String resolvedType, int flags, int userId) throws RemoteException;*/
//TODO 这里需要实现。查询插件的结果,并入到返回值中。
}
private class queryIntentReceivers extends HookedMethodHandler {
public queryIntentReceivers(Context context) {
super(context);
}
@Override
protected void afterInvoke(Object receiver, Method method, Object[] args, Object invokeResult) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1
/* public List<ResolveInfo> queryIntentReceivers(Intent intent, String resolvedType, int flags) throws RemoteException;*/
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public List<ResolveInfo> queryIntentReceivers(Intent intent, String resolvedType, int flags, int userId) throws RemoteException;*/
if (args != null && invokeResult instanceof List) {
final int index0 = 0, index1 = 1, index2 = 2;
Intent intent = null;
if (args.length > index0) {
if (args[index0] instanceof Intent) {
intent = (Intent) args[index0];
}
}
String resolvedType = null;
if (args.length > index1) {
if (args[index1] instanceof String) {
resolvedType = (String) args[index1];
}
}
Integer flags = 0;
if (args.length > index2) {
if (args[index2] instanceof Integer) {
flags = (Integer) args[index2];
}
}
if (intent != null) {
List<ResolveInfo> infos = PluginManager.getInstance().queryIntentReceivers(intent, resolvedType, flags);
if (infos != null && infos.size() > 0) {
List old = (List) invokeResult;
old.addAll(infos);
setFakedResult(invokeResult);
}
}
}
super.afterInvoke(receiver, method, args, invokeResult);
}
}
private class resolveService extends HookedMethodHandler {
public resolveService(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1
/* public ResolveInfo resolveService(Intent intent, String resolvedType, int flags) throws RemoteException;*/
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public ResolveInfo resolveService(Intent intent, String resolvedType, int flags, int userId) throws RemoteException;*/
if (args != null) {
final int index0 = 0, index1 = 1, index2 = 2;
Intent intent = null;
if (args.length > index0) {
if (args[index0] instanceof Intent) {
intent = (Intent) args[index0];
}
}
String resolvedType = null;
if (args.length > index1) {
if (args[index1] instanceof String) {
resolvedType = (String) args[index1];
}
}
Integer flags = 0;
if (args.length > index2) {
if (args[index2] instanceof Integer) {
flags = (Integer) args[index2];
}
}
if (intent != null) {
ResolveInfo info = PluginManager.getInstance().resolveService(intent, resolvedType, flags);
if (info != null) {
setFakedResult(info);
return true;
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class queryIntentServices extends HookedMethodHandler {
public queryIntentServices(Context context) {
super(context);
}
@Override
protected void afterInvoke(Object receiver, Method method, Object[] args, Object invokeResult) throws Throwable {
//API 2.3
/*public List<ResolveInfo> queryIntentServices(Intent intent, String resolvedType, int flags) throws RemoteException;*/
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public List<ResolveInfo> queryIntentServices(Intent intent, String resolvedType, int flags, int userId) throwsRemoteException;*/
if (args != null && invokeResult instanceof List) {
final int index0 = 0, index1 = 1, index2 = 2;
Intent intent = null;
if (args.length > index0) {
if (args[index0] instanceof Intent) {
intent = (Intent) args[index0];
}
}
String resolvedType = null;
if (args.length > index1) {
if (args[index1] instanceof String) {
resolvedType = (String) args[index1];
}
}
Integer flags = 0;
if (args.length > index2) {
if (args[index2] instanceof Integer) {
flags = (Integer) args[index2];
}
}
if (intent != null) {
List<ResolveInfo> infos = PluginManager.getInstance().queryIntentServices(intent, resolvedType, flags);
if (infos != null && infos.size() > 0) {
List old = (List) invokeResult;
old.addAll(infos);
}
}
}
super.afterInvoke(receiver, method, args, invokeResult);
}
}
private class queryIntentContentProviders extends HookedMethodHandler {
public queryIntentContentProviders(Context context) {
super(context);
}
@Override
protected void afterInvoke(Object receiver, Method method, Object[] args, Object invokeResult) throws Throwable {
//ONLY FOR API 4.4_r1, 5.0.2_r1
/*public List<ResolveInfo> queryIntentContentProviders(Intent intent, String resolvedType, int flags, int userId) throws RemoteException;*/
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
if (args != null && invokeResult instanceof List) {
final int index0 = 0, index1 = 1, index2 = 2;
Intent intent = null;
if (args.length > index0) {
if (args[index0] instanceof Intent) {
intent = (Intent) args[index0];
}
}
String resolvedType = null;
if (args.length > index1) {
if (args[index1] instanceof String) {
resolvedType = (String) args[index1];
}
}
Integer flags = 0;
if (args.length > index2) {
if (args[index2] instanceof Integer) {
flags = (Integer) args[index2];
}
}
if (intent != null) {
List<ResolveInfo> infos = PluginManager.getInstance().queryIntentContentProviders(intent, resolvedType, flags);
if (infos != null && infos.size() > 0) {
List old = (List) invokeResult;
old.addAll(infos);
}
}
}
}
super.afterInvoke(receiver, method, args, invokeResult);
}
}
private class getInstalledPackages extends HookedMethodHandler {
public getInstalledPackages(Context context) {
super(context);
}
@Override
protected void afterInvoke(Object receiver, Method method, Object[] args, Object invokeResult) throws Throwable {
//API 2.3
/* public List<PackageInfo> getInstalledPackages(int flags) throws RemoteException;*/
//API 4.01, 4.0.3_r1, 4.1.1_r1
/*public ParceledListSlice getInstalledPackages(int flags, String lastRead) */
//API 4.2_r1
/* public ParceledListSlice getInstalledPackages(int flags, String lastRead, int userId) throws RemoteException*/
//API 4.3_r1, 4.4_r1,5.0.2_r1
/*public ParceledListSlice getInstalledPackages(int flags, int userId) throws RemoteException;*/
try {
if (invokeResult != null && ParceledListSliceCompat.isParceledListSlice(invokeResult)) {
if (VERSION.SDK_INT >= VERSION_CODES.JELLY_BEAN_MR2) {
Method getListMethod = MethodUtils.getAccessibleMethod(invokeResult.getClass(), "getList");
List data = (List) getListMethod.invoke(invokeResult);
final int index0 = 0;
if (args.length > index0 && args[index0] instanceof Integer) {
int flags = (Integer) args[index0];
List<PackageInfo> infos = PluginManager.getInstance().getInstalledPackages(flags);
if (infos != null && infos.size() > 0) {
data.addAll(infos);
}
}
} else {
Method isLastSliceMethod = invokeResult.getClass().getMethod("isLastSlice");
Method setLastSlice = invokeResult.getClass().getMethod("setLastSlice", boolean.class);
Method appendMethod = invokeResult.getClass().getMethod("append", Parcelable.class);
Method populateList = invokeResult.getClass().getMethod("populateList", List.class, Parcelable.Creator.class);
if (!setLastSlice.isAccessible()) {
setLastSlice.setAccessible(true);
}
if (!populateList.isAccessible()) {
populateList.setAccessible(true);
}
if (!isLastSliceMethod.isAccessible()) {
isLastSliceMethod.setAccessible(true);
}
if (!appendMethod.isAccessible()) {
appendMethod.setAccessible(true);
}
boolean isLastSlice = (Boolean) isLastSliceMethod.invoke(invokeResult);
if (isLastSlice) {
final int index0 = 0;
if (args.length > index0 && args[index0] instanceof Integer) {
int flags = (Integer) args[index0];
List<PackageInfo> infos = PluginManager.getInstance().getInstalledPackages(flags);
if (infos != null && infos.size() > 0) {
final List<PackageInfo> packageInfos = new ArrayList<PackageInfo>();
populateList.invoke(invokeResult, packageInfos, PackageInfo.CREATOR);
packageInfos.addAll(infos);
Object parceledListSlice = invokeResult.getClass().newInstance();
for (PackageInfo packageInfo : packageInfos) {
appendMethod.invoke(parceledListSlice, packageInfo);
}
setLastSlice.invoke(parceledListSlice, true);
setFakedResult(parceledListSlice);
}
}
}
}
} else if (invokeResult instanceof List) {
final int index0 = 0;
if (args.length > index0 && args[index0] instanceof Integer) {
int flags = (Integer) args[index0];
List<PackageInfo> infos = PluginManager.getInstance().getInstalledPackages(flags);
if (infos != null && infos.size() > 0) {
List old = (List) invokeResult;
old.addAll(infos);
}
}
}
}catch (Exception e) {
e.printStackTrace();
}
super.afterInvoke(receiver, method, args, invokeResult);
}
}
private class getPackagesHoldingPermissions extends HookedMethodHandler {
public getPackagesHoldingPermissions(Context context) {
super(context);
}
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1, 4.2_r1 NO
//API 4.3_r1, 4.4_r1, 5.0.2_r1
/* public ParceledListSlice getPackagesHoldingPermissions(String[] permissions, int flags, int userId) throws RemoteException;*/
}
private class getInstalledApplications extends HookedMethodHandler {
public getInstalledApplications(Context context) {
super(context);
}
@Override
protected void afterInvoke(Object receiver, Method method, Object[] args, Object invokeResult) throws Throwable {
//API 2.3
/* public List<ApplicationInfo> getInstalledApplications(int flags) throws RemoteException;*/
//API 4.01, 4.0.3_r1
/*public ParceledListSlice getInstalledApplications(int flags, java.lang.String lastRead) throws RemoteException;*/
//API 4.1.1_r1 , 4.2_r1
/* public ParceledListSlice getInstalledApplications(int flags, java.lang.String lastRead, int userId) throws RemoteException*/
//API 4.3_r1,4.4_r1, 5.0.2_r1
/* public ParceledListSlice getInstalledApplications(int flags, int userId) throws RemoteException */
try {
if (ParceledListSliceCompat.isParceledListSlice(invokeResult)) {
if (VERSION.SDK_INT >= VERSION_CODES.JELLY_BEAN_MR2) {
Method getListMethod = MethodUtils.getAccessibleMethod(invokeResult.getClass(), "getList");
List data = (List) getListMethod.invoke(invokeResult);
final int index0 = 0;
if (args.length > index0 && args[index0] instanceof Integer) {
int flags = (Integer) args[index0];
List<ApplicationInfo> infos = PluginManager.getInstance().getInstalledApplications(flags);
if (infos != null && infos.size() > 0) {
data.addAll(infos);
}
}
} else {
Method isLastSliceMethod = invokeResult.getClass().getMethod("isLastSlice");
Method setLastSlice = invokeResult.getClass().getMethod("setLastSlice", boolean.class);
Method appendMethod = invokeResult.getClass().getMethod("append", Parcelable.class);
Method populateList = invokeResult.getClass().getMethod("populateList", List.class, Parcelable.Creator.class);
if (!setLastSlice.isAccessible()) {
setLastSlice.setAccessible(true);
}
if (!populateList.isAccessible()) {
populateList.setAccessible(true);
}
if (!isLastSliceMethod.isAccessible()) {
isLastSliceMethod.setAccessible(true);
}
if (!appendMethod.isAccessible()) {
appendMethod.setAccessible(true);
}
boolean isLastSlice = (Boolean) isLastSliceMethod.invoke(invokeResult);
if (isLastSlice) {
final int index0 = 0;
if (args.length > index0 && args[index0] instanceof Integer) {
int flags = (Integer) args[index0];
List<ApplicationInfo> infos = PluginManager.getInstance().getInstalledApplications(flags);
if (infos != null && infos.size() > 0) {
final List<ApplicationInfo> packageInfos = new ArrayList<ApplicationInfo>();
populateList.invoke(invokeResult, packageInfos, ApplicationInfo.CREATOR);
packageInfos.addAll(infos);
Object parceledListSlice = invokeResult.getClass().newInstance();
for (ApplicationInfo info : packageInfos) {
appendMethod.invoke(parceledListSlice, info);
}
setLastSlice.invoke(parceledListSlice, true);
setFakedResult(parceledListSlice);
}
}
}
}
} else if (invokeResult instanceof List) {
final int index0 = 0;
if (args.length > index0 && args[index0] instanceof Integer) {
int flags = (Integer) args[index0];
List<ApplicationInfo> infos = PluginManager.getInstance().getInstalledApplications(flags);
if (infos != null && infos.size() > 0) {
List old = (List) invokeResult;
old.addAll(infos);
}
}
}
} catch (Exception e) {
Log.e(TAG, "fake getInstalledApplications", e);
}
super.afterInvoke(receiver, method, args, invokeResult);
}
}
private class getPersistentApplications extends HookedMethodHandler {
public getPersistentApplications(Context context) {
super(context);
}
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public List<ApplicationInfo> getPersistentApplications(int flags) throws RemoteException;*/
}
private class resolveContentProvider extends HookedMethodHandler {
public resolveContentProvider(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1
/*public ProviderInfo resolveContentProvider(String name, int flags) throws RemoteException;*/
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public ProviderInfo resolveContentProvider(String name, int flags, int userId) throws RemoteException*/
return super.beforeInvoke(receiver, method, args);
}
@Override
protected void afterInvoke(Object receiver, Method method, Object[] args, Object invokeResult) throws Throwable {
if (args != null) {
if (invokeResult == null) {
final int index0 = 0, index1 = 1;
if (args.length >= 2 && args[index0] instanceof String && args[index1] instanceof Integer) {
String name = (String) args[index0];
Integer flags = (Integer) args[index1];
ProviderInfo info = PluginManager.getInstance().resolveContentProvider(name, flags);
if (info != null) {
setFakedResult(info);
}
}
}
}
super.afterInvoke(receiver, method, args, invokeResult);
}
}
private class querySyncProviders extends HookedMethodHandler {
public querySyncProviders(Context context) {
super(context);
}
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public void querySyncProviders(List<String> outNames, List<ProviderInfo> outInfo) throws RemoteException;*/
//TODO 查询插件的结果并入到返回值中。
}
private class queryContentProviders extends HookedMethodHandler {
public queryContentProviders(Context context) {
super(context);
}
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public List<ProviderInfo> queryContentProviders(String processName, int uid, int flags) throws RemoteException;*/
//TODO 查询插件的结果并入到返回值中。
}
private class getInstrumentationInfo extends HookedMethodHandler {
public getInstrumentationInfo(Context context) {
super(context);
}
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public InstrumentationInfo getInstrumentationInfo(ComponentName className, int flags) throws RemoteException;*/
//FIXME 自动化测试相关的东西,先不处理。
}
private class queryInstrumentation extends HookedMethodHandler {
public queryInstrumentation(Context context) {
super(context);
}
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public List<InstrumentationInfo> queryInstrumentation(String targetPackage, int flags) throws RemoteException;*/
//FIXME 自动化测试相关的东西,先不处理。
}
private class getInstallerPackageName extends HookedMethodHandler {
public getInstallerPackageName(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public String getInstallerPackageName(String packageName) throws RemoteException;*/
if (args != null) {
final int index = 0;
if (args.length > index && args[index] instanceof String) {
String packageName = (String) args[index];
if (PluginManager.getInstance().isPluginPackage(packageName)) {
setFakedResult(mHostContext.getPackageName());
return true;
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class addPackageToPreferred extends HookedMethodHandler {
public addPackageToPreferred(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public void addPackageToPreferred(String packageName) throws RemoteException;*/
if (args != null) {
final int index = 0;
if (args.length > index && args[index] instanceof String) {
String packageName = (String) args[index];
if (PluginManager.getInstance().isPluginPackage(packageName)) {
args[index] = mHostContext.getPackageName();
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class removePackageFromPreferred extends HookedMethodHandler {
public removePackageFromPreferred(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public void removePackageFromPreferred(String packageName) throws RemoteException;*/
if (args != null) {
final int index = 0;
if (args.length > index && args[index] instanceof String) {
String packageName = (String) args[index];
if (PluginManager.getInstance().isPluginPackage(packageName)) {
args[index] = mHostContext.getPackageName();
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class getPreferredPackages extends HookedMethodHandler {
public getPreferredPackages(Context context) {
super(context);
}
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public List<PackageInfo> getPreferredPackages(int flags) throws RemoteException;*/
//这里插件没有结果的,所以就不处理了。
}
private class resetPreferredActivities extends HookedMethodHandler {
public resetPreferredActivities(Context context) {
super(context);
}
//API 4.3_r1, 4.4_r1, 5.0.2_r1
/* public void resetPreferredActivities(int userId) throws android.os.RemoteException;*/
//这里插件没有结果的,所以就不处理了。
}
private class getLastChosenActivity extends HookedMethodHandler {
public getLastChosenActivity(Context context) {
super(context);
}
//API 4.4_r1, 5.0.2_r1
/*public ResolveInfo getLastChosenActivity(Intent intent, String resolvedType, int flags) throws RemoteException;*/
//这里插件没有结果的,所以就不处理了。
}
private class setLastChosenActivity extends HookedMethodHandler {
public setLastChosenActivity(Context context) {
super(context);
}
//API 4.4_r1, 5.0.2_r1
/*public void setLastChosenActivity(Intent intent, String resolvedType, int flags, IntentFilter filter, int match, ComponentName activity) throws RemoteException;*/
//这里插件没有结果的,所以就不处理了。
}
private class addPreferredActivity extends HookedMethodHandler {
public addPreferredActivity(Context context) {
super(context);
}
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1
/* public void addPreferredActivity(IntentFilter filter, int match, ComponentName[] set, ComponentName activity) throws RemoteException;*/
//API 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public void addPreferredActivity(IntentFilter filter, int match, ComponentName[] set, ComponentName activity, int userId) throws RemoteException;*/
//这里插件没有结果的,所以就不处理了。
}
private class replacePreferredActivity extends HookedMethodHandler {
public replacePreferredActivity(Context context) {
super(context);
}
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1
/*public void replacePreferredActivity(IntentFilter filter, int match, ComponentName[] set, ComponentName activity) throws RemoteException;*/
//API 5.0.2_r1
/*public void replacePreferredActivity(IntentFilter filter, int match, ComponentName[] set, ComponentName activity, int userId) throws RemoteException;*/
//这里插件没有结果的,所以就不处理了。
}
private class clearPackagePreferredActivities extends HookedMethodHandler {
public clearPackagePreferredActivities(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public void clearPackagePreferredActivities(String packageName) throws RemoteException;*/
if (args != null) {
final int index = 0;
if (args.length > index && args[index] instanceof String) {
String packageName = (String) args[index];
if (PluginManager.getInstance().isPluginPackage(packageName)) {
args[index] = mHostContext.getPackageName();
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class getPreferredActivities extends HookedMethodHandler {
public getPreferredActivities(Context context) {
super(context);
}
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public int getPreferredActivities(List<IntentFilter> outFilters, List<ComponentName> outActivities, String packageName) throws RemoteException;*/
//这里插件没有结果的,所以就不处理了。
}
//ONLY for 4.4_r1 or later
private class getHomeActivities extends HookedMethodHandler {
public getHomeActivities(Context context) {
super(context);
}
//API 4.4_r1, 5.0.2_r1
/* public ComponentName getHomeActivities(List<ResolveInfo> outHomeCandidates) throws RemoteException;*/
//这里插件没有结果的,所以就不处理了。
}
private class setComponentEnabledSetting extends HookedMethodHandler {
public setComponentEnabledSetting(Context context) {
super(context);
}
//API 2.3
/* public void setComponentEnabledSetting(ComponentName componentName, int newState, int flags) throws RemoteException;*/
//API 4.01
//API 4.0.3_r1
//API 4.1.1_r1
//API 4.2_r1
//API 4.3_r1
//API 4.4_r1
//API 5.0.2_r1
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
final int index = 0;
if (args != null && args.length > index && args[index] instanceof ComponentName) {
ComponentName componentName = (ComponentName) args[index];
if (PluginManager.getInstance().isPluginPackage(componentName)) {
setFakedResult(PackageManager.COMPONENT_ENABLED_STATE_DEFAULT);
return true;
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class getComponentEnabledSetting extends HookedMethodHandler {
public getComponentEnabledSetting(Context context) {
super(context);
}
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1
/*public int getComponentEnabledSetting(ComponentName componentName) throws RemoteException;*/
//API 4.2_r1, 4.3_r1,4.4_r1, 5.0.2_r1
/*public void setComponentEnabledSetting(ComponentName componentName, int newState, int flags, int userId) throws RemoteException*/
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
final int index = 0;
if (args != null && args.length > index && args[index] instanceof ComponentName) {
ComponentName componentName = (ComponentName) args[index];
if (PluginManager.getInstance().isPluginPackage(componentName)) {
setFakedResult(PackageManager.COMPONENT_ENABLED_STATE_DEFAULT);
return true;
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class setApplicationEnabledSetting extends HookedMethodHandler {
public setApplicationEnabledSetting(Context context) {
super(context);
}
//API 2.3
/*public void setApplicationEnabledSetting(String packageName, int newState, int flags) throws RemoteException;*/
//API 4.01, 4.0.3_r1, 4.1.1_r1, 4.2_r1
/*public void setApplicationEnabledSetting(String packageName, int newState, int flags, int userId) throws RemoteException*/
//API 4.3_r1, 4.4_r1, 5.0.2_r1
/*public void setApplicationEnabledSetting(String packageName, int newState, int flags, int userId, String callingPackage) throws RemoteException;*/
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
final int index = 0;
if (args != null && args.length > index && args[index] instanceof String) {
String packageName = (String) args[index];
if (PluginManager.getInstance().isPluginPackage(packageName)) {
return true;
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class getApplicationEnabledSetting extends HookedMethodHandler {
public getApplicationEnabledSetting(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1,
/* public int getApplicationEnabledSetting(String packageName) throws RemoteException;*/
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public int getApplicationEnabledSetting(String packageName, int userId) throws RemoteException;*/
if (args != null) {
final int index = 0;
if (args.length > index && args[index] instanceof String) {
String packageName = (String) args[index];
if (PluginManager.getInstance().isPluginPackage(packageName)) {
//DO NOTHING
setFakedResult(PackageManager.COMPONENT_ENABLED_STATE_DEFAULT);
return true;
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class setPackageStoppedState extends HookedMethodHandler {
public setPackageStoppedState(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 4.01, 4.0.3_r1
/* public void setPackageStoppedState(String packageName, boolean stopped) throws RemoteException;*/
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public void setPackageStoppedState(java.lang.String packageName, boolean stopped, int userId) throws android.os.RemoteException;*/
if (args != null) {
final int index = 0;
if (args.length > index && args[index] instanceof String) {
String packageName = (String) args[index];
if (PluginManager.getInstance().isPluginPackage(packageName)) {
//DO NOTHING
PluginManager.getInstance().forceStopPackage(packageName);
return true;
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class deleteApplicationCacheFiles extends HookedMethodHandler {
public deleteApplicationCacheFiles(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public void deleteApplicationCacheFiles(String packageName, IPackageDataObserver observer) throws RemoteException;*/
if (args != null) {
final int index0 = 0, index1 = 1;
if (args.length >= 2 && args[index0] instanceof String && IPackageDataObserverCompat.isIPackageDataObserver(args[index1])) {
String packageName = (String) args[index0];
if (PluginManager.getInstance().isPluginPackage(packageName)) {
final Object observer = args[index1];
PluginManager.getInstance().deleteApplicationCacheFiles(packageName, observer);
return true;
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class clearApplicationUserData extends HookedMethodHandler {
public clearApplicationUserData(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1
/* public void clearApplicationUserData(String packageName, IPackageDataObserver observer) throws RemoteException;*/
//API 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/*public void clearApplicationUserData(String packageName, IPackageDataObserver observer, int userId) throws RemoteException;*/
if (args != null) {
final int index0 = 0, index1 = 1;
if (args.length >= 2 && args[index0] instanceof String && IPackageDataObserverCompat.isIPackageDataObserver(args[index1])) {
String packageName = (String) args[index0];
if (PluginManager.getInstance().isPluginPackage(packageName)) {
final Object observer = args[index1];
PluginManager.getInstance().clearApplicationUserData(packageName, observer);
return true;
}
}
}
return super.beforeInvoke(receiver, method, args);
}
}
private class getPackageSizeInfo extends HookedMethodHandler {
public getPackageSizeInfo(Context context) {
super(context);
}
@Override
protected boolean beforeInvoke(Object receiver, Method method, Object[] args) throws Throwable {
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1
/*public void getPackageSizeInfo(String packageName, IPackageStatsObserver observer) throws RemoteException;*/
//API 4.2_r1 4.3_r1, 4.4_r1, 5.0.2_r1
/*public void getPackageSizeInfo(String packageName, int userHandle, IPackageStatsObserver observer) throws RemoteException;*/
//TODO 获取包大小。
return super.beforeInvoke(receiver, method, args);
}
}
private class performDexOpt extends HookedMethodHandler {
public performDexOpt(Context context) {
super(context);
}
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1
/* public boolean performDexOpt(String packageName) throws RemoteException;*/
//API 5.0.2_r1 NO
}
private class movePackage extends HookedMethodHandler {
public movePackage(Context context) {
super(context);
}
//API 2.3, 4.01, 4.0.3_r1, 4.1.1_r1, 4.2_r1, 4.3_r1, 4.4_r1, 5.0.2_r1
/* public void movePackage(String packageName, IPackageMoveObserver observer, int flags) throws RemoteException;*/
}
}