From 02fd5be2fc1323dca4d928ba6e792d71d059e591 Mon Sep 17 00:00:00 2001 From: LoveSy Date: Fri, 21 May 2021 14:28:17 +0800 Subject: [PATCH] [core] Switch to user if needed --- .../lsposed/manager/adapters/AppHelper.java | 3 +++ .../lspd/service/ActivityManagerService.java | 19 ++++++++++++++++--- .../lspd/service/LSPManagerService.java | 8 ++++++++ .../lsposed/lspd/service/PackageService.java | 3 +-- .../org/lsposed/lspd/service/UserService.java | 6 ++++++ .../java/android/app/IActivityManager.java | 7 +++++++ .../android/content/pm/IPackageManager.java | 8 +++++--- .../java/android/content/pm/ResolveInfo.java | 4 ++++ .../main/java/android/os/IUserManager.java | 2 ++ .../org/lsposed/lspd/ILSPManagerService.aidl | 2 +- 10 files changed, 53 insertions(+), 9 deletions(-) create mode 100644 hiddenapi-stubs/src/main/java/android/content/pm/ResolveInfo.java diff --git a/app/src/main/java/org/lsposed/manager/adapters/AppHelper.java b/app/src/main/java/org/lsposed/manager/adapters/AppHelper.java index bcbd83e7..84ab794f 100644 --- a/app/src/main/java/org/lsposed/manager/adapters/AppHelper.java +++ b/app/src/main/java/org/lsposed/manager/adapters/AppHelper.java @@ -38,6 +38,7 @@ import java.util.List; public class AppHelper { public static final String SETTINGS_CATEGORY = "de.robv.android.xposed.category.MODULE_SETTINGS"; + public static final int FLAG_SHOW_FOR_ALL_USERS = 0x0400; private static List appList; public static Intent getSettingsIntent(String packageName, int userId) { @@ -55,6 +56,7 @@ public class AppHelper { intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); intent.setClassName(ris.get(0).activityInfo.packageName, ris.get(0).activityInfo.name); + intent.putExtra("lsp_no_switch_to_user", (ris.get(0).activityInfo.flags & FLAG_SHOW_FOR_ALL_USERS) != 0); return intent; } @@ -79,6 +81,7 @@ public class AppHelper { intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); intent.setClassName(ris.get(0).activityInfo.packageName, ris.get(0).activityInfo.name); + intent.putExtra("lsp_no_switch_to_user", (ris.get(0).activityInfo.flags & FLAG_SHOW_FOR_ALL_USERS) != 0); return intent; } diff --git a/core/src/main/java/org/lsposed/lspd/service/ActivityManagerService.java b/core/src/main/java/org/lsposed/lspd/service/ActivityManagerService.java index dff1cce2..77caee94 100644 --- a/core/src/main/java/org/lsposed/lspd/service/ActivityManagerService.java +++ b/core/src/main/java/org/lsposed/lspd/service/ActivityManagerService.java @@ -26,6 +26,7 @@ import android.app.ProfilerInfo; import android.content.IIntentReceiver; import android.content.Intent; import android.content.IntentFilter; +import android.content.pm.UserInfo; import android.os.Build; import android.os.Bundle; import android.os.IBinder; @@ -120,9 +121,9 @@ public class ActivityManagerService { } public static int startActivityAsUserWithFeature(String callingPackage, - String callingFeatureId, Intent intent, String resolvedType, - IBinder resultTo, String resultWho, int requestCode, int flags, - ProfilerInfo profilerInfo, Bundle options, int userId) throws RemoteException { + String callingFeatureId, Intent intent, String resolvedType, + IBinder resultTo, String resultWho, int requestCode, int flags, + ProfilerInfo profilerInfo, Bundle options, int userId) throws RemoteException { IActivityManager am = getActivityManager(); if (am == null || thread == null) return -1; if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) { @@ -136,4 +137,16 @@ public class ActivityManagerService { ActivityManagerService.thread = thread; ActivityManagerService.token = token; } + + public static boolean switchUser(int userid) throws RemoteException { + IActivityManager am = getActivityManager(); + if (am == null) return false; + return am.switchUser(userid); + } + + public static UserInfo getCurrentUser() throws RemoteException { + IActivityManager am = getActivityManager(); + if (am == null) return null; + return am.getCurrentUser(); + } } diff --git a/core/src/main/java/org/lsposed/lspd/service/LSPManagerService.java b/core/src/main/java/org/lsposed/lspd/service/LSPManagerService.java index c4b1e3b2..26793024 100644 --- a/core/src/main/java/org/lsposed/lspd/service/LSPManagerService.java +++ b/core/src/main/java/org/lsposed/lspd/service/LSPManagerService.java @@ -230,6 +230,14 @@ public class LSPManagerService extends ILSPManagerService.Stub { @Override public int startActivityAsUserWithFeature(Intent intent, int userId) throws RemoteException { + if (!intent.getBooleanExtra("lsp_no_switch_to_user", false)) { + intent.removeExtra("lsp_no_switch_to_user"); + var currentUser = ActivityManagerService.getCurrentUser(); + if (currentUser == null) return -1; + var parent = UserService.getProfileParent(userId); + if (parent < 0) return -1; + if (currentUser.id != parent && !ActivityManagerService.switchUser(parent)) return -1; + } return ActivityManagerService.startActivityAsUserWithFeature("android", null, intent, intent.getType(), null, null, 0, 0, null, null, userId); } diff --git a/core/src/main/java/org/lsposed/lspd/service/PackageService.java b/core/src/main/java/org/lsposed/lspd/service/PackageService.java index 013948fe..6d62deb6 100644 --- a/core/src/main/java/org/lsposed/lspd/service/PackageService.java +++ b/core/src/main/java/org/lsposed/lspd/service/PackageService.java @@ -274,8 +274,7 @@ public class PackageService { public static ParceledListSlice queryIntentActivities(android.content.Intent intent, java.lang.String resolvedType, int flags, int userId) throws RemoteException { IPackageManager pm = getPackageManager(); if (pm == null) return null; - //noinspection unchecked - return new ParceledListSlice(pm.queryIntentActivities(intent, resolvedType, flags, userId).getList()); + return new ParceledListSlice<>(pm.queryIntentActivities(intent, resolvedType, flags, userId).getList()); } @SuppressWarnings("JavaReflectionMemberAccess") diff --git a/core/src/main/java/org/lsposed/lspd/service/UserService.java b/core/src/main/java/org/lsposed/lspd/service/UserService.java index 0ef46eed..eefec929 100644 --- a/core/src/main/java/org/lsposed/lspd/service/UserService.java +++ b/core/src/main/java/org/lsposed/lspd/service/UserService.java @@ -78,4 +78,10 @@ public class UserService { } return userArray; } + + public static int getProfileParent(int userId) throws RemoteException { + IUserManager um = getUserManager(); + if (um == null) return -1; + return um.getProfileParentId(userId); + } } diff --git a/hiddenapi-stubs/src/main/java/android/app/IActivityManager.java b/hiddenapi-stubs/src/main/java/android/app/IActivityManager.java index 334df924..15bbf95f 100644 --- a/hiddenapi-stubs/src/main/java/android/app/IActivityManager.java +++ b/hiddenapi-stubs/src/main/java/android/app/IActivityManager.java @@ -22,6 +22,7 @@ package android.app; import android.content.IIntentReceiver; import android.content.Intent; import android.content.IntentFilter; +import android.content.pm.UserInfo; import android.os.Binder; import android.os.Bundle; import android.os.IBinder; @@ -70,6 +71,8 @@ public interface IActivityManager extends IInterface { Intent registerReceiver(IApplicationThread caller, String callerPackage, IIntentReceiver receiver, IntentFilter filter, String requiredPermission, int userId, int flags); + + @RequiresApi(30) Intent registerReceiverWithFeature(IApplicationThread caller, String callerPackage, String callingFeatureId, IIntentReceiver receiver, IntentFilter filter, String requiredPermission, int userId, int flags) throws RemoteException; @@ -80,6 +83,10 @@ public interface IActivityManager extends IInterface { boolean unbindService(IServiceConnection connection) throws RemoteException; + boolean switchUser(int userid) throws RemoteException; + + UserInfo getCurrentUser() throws RemoteException; + abstract class Stub extends Binder implements IActivityManager { public static IActivityManager asInterface(IBinder obj) { diff --git a/hiddenapi-stubs/src/main/java/android/content/pm/IPackageManager.java b/hiddenapi-stubs/src/main/java/android/content/pm/IPackageManager.java index 56fa9ed1..c45c463e 100644 --- a/hiddenapi-stubs/src/main/java/android/content/pm/IPackageManager.java +++ b/hiddenapi-stubs/src/main/java/android/content/pm/IPackageManager.java @@ -1,5 +1,6 @@ package android.content.pm; +import android.content.Intent; import android.os.Binder; import android.os.IBinder; import android.os.IInterface; @@ -52,13 +53,14 @@ public interface IPackageManager extends IInterface { IPackageInstaller getPackageInstaller() throws RemoteException; int installExistingPackageAsUser(String packageName, int userId, int installFlags, - int installReason) throws RemoteException;; + int installReason) throws RemoteException; @RequiresApi(29) int installExistingPackageAsUser(String packageName, int userId, int installFlags, - int installReason, List whiteListedPermissions) throws RemoteException;; + int installReason, List whiteListedPermissions) throws RemoteException; - android.content.pm.ParceledListSlice queryIntentActivities(android.content.Intent intent, java.lang.String resolvedType, int flags, int userId) throws RemoteException; + ParceledListSlice queryIntentActivities(Intent intent, + String resolvedType, int flags, int userId) throws RemoteException; abstract class Stub extends Binder implements IPackageManager { diff --git a/hiddenapi-stubs/src/main/java/android/content/pm/ResolveInfo.java b/hiddenapi-stubs/src/main/java/android/content/pm/ResolveInfo.java new file mode 100644 index 00000000..e00de135 --- /dev/null +++ b/hiddenapi-stubs/src/main/java/android/content/pm/ResolveInfo.java @@ -0,0 +1,4 @@ +package android.content.pm; + +public class ResolveInfo { +} diff --git a/hiddenapi-stubs/src/main/java/android/os/IUserManager.java b/hiddenapi-stubs/src/main/java/android/os/IUserManager.java index 1986e009..7e35a62f 100644 --- a/hiddenapi-stubs/src/main/java/android/os/IUserManager.java +++ b/hiddenapi-stubs/src/main/java/android/os/IUserManager.java @@ -8,6 +8,8 @@ import java.util.List; public interface IUserManager extends IInterface { + int getProfileParentId(int userId) throws RemoteException; + @RequiresApi(26) boolean isUserUnlocked(int userId) throws RemoteException; diff --git a/manager-service/src/main/aidl/org/lsposed/lspd/ILSPManagerService.aidl b/manager-service/src/main/aidl/org/lsposed/lspd/ILSPManagerService.aidl index 87b4f987..29d00bbf 100644 --- a/manager-service/src/main/aidl/org/lsposed/lspd/ILSPManagerService.aidl +++ b/manager-service/src/main/aidl/org/lsposed/lspd/ILSPManagerService.aidl @@ -55,5 +55,5 @@ interface ILSPManagerService { int startActivityAsUserWithFeature(in Intent intent, int userId) = 30; - ParceledListSlice queryIntentActivitiesAsUser(in Intent intent, int flags, int userId) = 31; + ParceledListSlice queryIntentActivitiesAsUser(in Intent intent, int flags, int userId) = 31; }