Add setAllowedActivities/setBlockActivities implementation
These APIs allow Virtual Device owners to configure allow and deny lists of components which are allowed to be streamed. Bug: 201559291 Test: To be added in ag/15781910 Change-Id: I5e9297b9fdbe987690e164b7215352e741806fd5
This commit is contained in:
@@ -20,7 +20,9 @@ import static android.Manifest.permission.ADD_ALWAYS_UNLOCKED_DISPLAY;
|
||||
|
||||
import android.annotation.IntDef;
|
||||
import android.annotation.NonNull;
|
||||
import android.annotation.Nullable;
|
||||
import android.annotation.RequiresPermission;
|
||||
import android.content.ComponentName;
|
||||
import android.os.Parcel;
|
||||
import android.os.Parcelable;
|
||||
import android.os.UserHandle;
|
||||
@@ -65,18 +67,26 @@ public final class VirtualDeviceParams implements Parcelable {
|
||||
|
||||
private final int mLockState;
|
||||
private final ArraySet<UserHandle> mUsersWithMatchingAccounts;
|
||||
@Nullable private final ArraySet<ComponentName> mAllowedActivities;
|
||||
@Nullable private final ArraySet<ComponentName> mBlockedActivities;
|
||||
|
||||
private VirtualDeviceParams(
|
||||
@LockState int lockState,
|
||||
@NonNull Set<UserHandle> usersWithMatchingAccounts) {
|
||||
@NonNull Set<UserHandle> usersWithMatchingAccounts,
|
||||
@Nullable Set<ComponentName> allowedActivities,
|
||||
@Nullable Set<ComponentName> blockedActivities) {
|
||||
mLockState = lockState;
|
||||
mUsersWithMatchingAccounts = new ArraySet<>(usersWithMatchingAccounts);
|
||||
mAllowedActivities = allowedActivities == null ? null : new ArraySet<>(allowedActivities);
|
||||
mBlockedActivities = blockedActivities == null ? null : new ArraySet<>(blockedActivities);
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
private VirtualDeviceParams(Parcel parcel) {
|
||||
mLockState = parcel.readInt();
|
||||
mUsersWithMatchingAccounts = (ArraySet<UserHandle>) parcel.readArraySet(null);
|
||||
mAllowedActivities = (ArraySet<ComponentName>) parcel.readArraySet(null);
|
||||
mBlockedActivities = (ArraySet<ComponentName>) parcel.readArraySet(null);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -98,6 +108,33 @@ public final class VirtualDeviceParams implements Parcelable {
|
||||
return Collections.unmodifiableSet(mUsersWithMatchingAccounts);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the set of activities allowed to be streamed, or {@code null} if this is not set.
|
||||
*
|
||||
* @see Builder#setAllowedActivities(Set)
|
||||
*/
|
||||
@Nullable
|
||||
public Set<ComponentName> getAllowedActivities() {
|
||||
if (mAllowedActivities == null) {
|
||||
return null;
|
||||
}
|
||||
return Collections.unmodifiableSet(mAllowedActivities);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the set of activities that are blocked from streaming, or {@code null} if this is not
|
||||
* set.
|
||||
*
|
||||
* @see Builder#setBlockedActivities(Set)
|
||||
*/
|
||||
@Nullable
|
||||
public Set<ComponentName> getBlockedActivities() {
|
||||
if (mBlockedActivities == null) {
|
||||
return null;
|
||||
}
|
||||
return Collections.unmodifiableSet(mBlockedActivities);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int describeContents() {
|
||||
return 0;
|
||||
@@ -107,6 +144,8 @@ public final class VirtualDeviceParams implements Parcelable {
|
||||
public void writeToParcel(@NonNull Parcel dest, int flags) {
|
||||
dest.writeInt(mLockState);
|
||||
dest.writeArraySet(mUsersWithMatchingAccounts);
|
||||
dest.writeArraySet(mAllowedActivities);
|
||||
dest.writeArraySet(mBlockedActivities);
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -118,8 +157,10 @@ public final class VirtualDeviceParams implements Parcelable {
|
||||
return false;
|
||||
}
|
||||
VirtualDeviceParams that = (VirtualDeviceParams) o;
|
||||
return mLockState == that.mLockState && mUsersWithMatchingAccounts.equals(
|
||||
that.mUsersWithMatchingAccounts);
|
||||
return mLockState == that.mLockState
|
||||
&& mUsersWithMatchingAccounts.equals(that.mUsersWithMatchingAccounts)
|
||||
&& Objects.equals(mAllowedActivities, that.mAllowedActivities)
|
||||
&& Objects.equals(mBlockedActivities, that.mBlockedActivities);
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -132,6 +173,8 @@ public final class VirtualDeviceParams implements Parcelable {
|
||||
return "VirtualDeviceParams("
|
||||
+ " mLockState=" + mLockState
|
||||
+ " mUsersWithMatchingAccounts=" + mUsersWithMatchingAccounts
|
||||
+ " mAllowedActivities=" + mAllowedActivities
|
||||
+ " mBlockedActivities=" + mBlockedActivities
|
||||
+ ")";
|
||||
}
|
||||
|
||||
@@ -153,6 +196,8 @@ public final class VirtualDeviceParams implements Parcelable {
|
||||
|
||||
private @LockState int mLockState = LOCK_STATE_ALWAYS_LOCKED;
|
||||
private Set<UserHandle> mUsersWithMatchingAccounts;
|
||||
@Nullable private Set<ComponentName> mBlockedActivities;
|
||||
@Nullable private Set<ComponentName> mAllowedActivities;
|
||||
|
||||
/**
|
||||
* Sets the lock state of the device. The permission {@code ADD_ALWAYS_UNLOCKED_DISPLAY}
|
||||
@@ -175,6 +220,7 @@ public final class VirtualDeviceParams implements Parcelable {
|
||||
*
|
||||
* @param usersWithMatchingAccounts A set of user handles with matching managed
|
||||
* accounts on the remote device this is streaming to.
|
||||
*
|
||||
* @see android.app.admin.DevicePolicyManager#NEARBY_STREAMING_SAME_MANAGED_ACCOUNT_ONLY
|
||||
*/
|
||||
public Builder setUsersWithMatchingAccounts(
|
||||
@@ -183,6 +229,52 @@ public final class VirtualDeviceParams implements Parcelable {
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the activities allowed to be launched in the virtual device. If
|
||||
* {@code allowedActivities} is non-null, all activities other than the ones in the set will
|
||||
* be blocked from launching.
|
||||
*
|
||||
* <p>{@code allowedActivities} and the set in {@link #setBlockedActivities(Set)} cannot
|
||||
* both be non-null at the same time.
|
||||
*
|
||||
* @throws IllegalArgumentException if {@link #setBlockedActivities(Set)} has been set to a
|
||||
* non-null value.
|
||||
*
|
||||
* @param allowedActivities A set of activity {@link ComponentName} allowed to be launched
|
||||
* in the virtual device.
|
||||
*/
|
||||
public Builder setAllowedActivities(@Nullable Set<ComponentName> allowedActivities) {
|
||||
if (mBlockedActivities != null && allowedActivities != null) {
|
||||
throw new IllegalArgumentException(
|
||||
"Allowed activities and Blocked activities cannot both be set.");
|
||||
}
|
||||
mAllowedActivities = allowedActivities;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the activities blocked from launching in the virtual device. If the {@code
|
||||
* blockedActivities} is non-null, activities in the set are blocked from launching in the
|
||||
* virtual device.
|
||||
*
|
||||
* {@code blockedActivities} and the set in {@link #setAllowedActivities(Set)} cannot both
|
||||
* be non-null at the same time.
|
||||
*
|
||||
* @throws IllegalArgumentException if {@link #setAllowedActivities(Set)} has been set to a
|
||||
* non-null value.
|
||||
*
|
||||
* @param blockedActivities A set of {@link ComponentName} to be blocked launching from
|
||||
* virtual device.
|
||||
*/
|
||||
public Builder setBlockedActivities(@Nullable Set<ComponentName> blockedActivities) {
|
||||
if (mAllowedActivities != null && blockedActivities != null) {
|
||||
throw new IllegalArgumentException(
|
||||
"Allowed activities and Blocked activities cannot both be set.");
|
||||
}
|
||||
mBlockedActivities = blockedActivities;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Builds the {@link VirtualDeviceParams} instance.
|
||||
*/
|
||||
@@ -191,7 +283,13 @@ public final class VirtualDeviceParams implements Parcelable {
|
||||
if (mUsersWithMatchingAccounts == null) {
|
||||
mUsersWithMatchingAccounts = Collections.emptySet();
|
||||
}
|
||||
return new VirtualDeviceParams(mLockState, mUsersWithMatchingAccounts);
|
||||
if (mAllowedActivities != null && mBlockedActivities != null) {
|
||||
// Should never reach here because the setters block this as well.
|
||||
throw new IllegalStateException(
|
||||
"Allowed activities and Blocked activities cannot both be set.");
|
||||
}
|
||||
return new VirtualDeviceParams(mLockState, mUsersWithMatchingAccounts,
|
||||
mAllowedActivities, mBlockedActivities);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -21,6 +21,7 @@ import static android.view.WindowManager.LayoutParams.FLAG_SECURE;
|
||||
import static android.view.WindowManager.LayoutParams.SYSTEM_FLAG_HIDE_NON_SYSTEM_OVERLAY_WINDOWS;
|
||||
|
||||
import android.annotation.NonNull;
|
||||
import android.annotation.Nullable;
|
||||
import android.app.compat.CompatChanges;
|
||||
import android.compat.annotation.ChangeId;
|
||||
import android.compat.annotation.EnabledSince;
|
||||
@@ -33,6 +34,7 @@ import android.util.Slog;
|
||||
import android.window.DisplayWindowPolicyController;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
|
||||
/**
|
||||
@@ -49,13 +51,23 @@ class GenericWindowPolicyController extends DisplayWindowPolicyController {
|
||||
@ChangeId
|
||||
@EnabledSince(targetSdkVersion = Build.VERSION_CODES.TIRAMISU)
|
||||
public static final long ALLOW_SECURE_ACTIVITY_DISPLAY_ON_REMOTE_DEVICE = 201712607L;
|
||||
@NonNull private final ArraySet<UserHandle> mAllowedUsers;
|
||||
@NonNull
|
||||
private final ArraySet<UserHandle> mAllowedUsers;
|
||||
@Nullable
|
||||
private final ArraySet<ComponentName> mAllowedActivities;
|
||||
@Nullable
|
||||
private final ArraySet<ComponentName> mBlockedActivities;
|
||||
|
||||
@NonNull final ArraySet<Integer> mRunningUids = new ArraySet<>();
|
||||
@NonNull
|
||||
final ArraySet<Integer> mRunningUids = new ArraySet<>();
|
||||
|
||||
GenericWindowPolicyController(int windowFlags, int systemWindowFlags,
|
||||
@NonNull ArraySet<UserHandle> allowedUsers) {
|
||||
@NonNull ArraySet<UserHandle> allowedUsers,
|
||||
@Nullable Set<ComponentName> allowedActivities,
|
||||
@Nullable Set<ComponentName> blockedActivities) {
|
||||
mAllowedUsers = allowedUsers;
|
||||
mAllowedActivities = allowedActivities == null ? null : new ArraySet<>(allowedActivities);
|
||||
mBlockedActivities = blockedActivities == null ? null : new ArraySet<>(blockedActivities);
|
||||
setInterestedWindowFlags(windowFlags, systemWindowFlags);
|
||||
}
|
||||
|
||||
@@ -108,6 +120,18 @@ class GenericWindowPolicyController extends DisplayWindowPolicyController {
|
||||
Slog.d(TAG, "Virtual device activity not allowed from user " + activityUser);
|
||||
return false;
|
||||
}
|
||||
if (mBlockedActivities != null
|
||||
&& mBlockedActivities.contains(activityInfo.getComponentName())) {
|
||||
Slog.d(TAG,
|
||||
"Virtual device blocking launch of " + activityInfo.getComponentName());
|
||||
return false;
|
||||
}
|
||||
if (mAllowedActivities != null
|
||||
&& !mAllowedActivities.contains(activityInfo.getComponentName())) {
|
||||
Slog.d(TAG,
|
||||
activityInfo.getComponentName() + " is not in the allowed list.");
|
||||
return false;
|
||||
}
|
||||
if (!CompatChanges.isChangeEnabled(ALLOW_SECURE_ACTIVITY_DISPLAY_ON_REMOTE_DEVICE,
|
||||
activityInfo.packageName, activityUser)) {
|
||||
// TODO(b/201712607): Add checks for the apps that use SurfaceView#setSecure.
|
||||
|
||||
@@ -328,6 +328,7 @@ final class VirtualDeviceImpl extends IVirtualDevice.Stub
|
||||
protected void dump(FileDescriptor fd, PrintWriter fout, String[] args) {
|
||||
fout.println(" VirtualDevice: ");
|
||||
fout.println(" mAssociationId: " + mAssociationInfo.getId());
|
||||
fout.println(" mParams: " + mParams);
|
||||
fout.println(" mVirtualDisplayIds: ");
|
||||
synchronized (mVirtualDeviceLock) {
|
||||
for (int id : mVirtualDisplayIds) {
|
||||
@@ -345,7 +346,9 @@ final class VirtualDeviceImpl extends IVirtualDevice.Stub
|
||||
mVirtualDisplayIds.add(displayId);
|
||||
final GenericWindowPolicyController dwpc =
|
||||
new GenericWindowPolicyController(FLAG_SECURE,
|
||||
SYSTEM_FLAG_HIDE_NON_SYSTEM_OVERLAY_WINDOWS, getAllowedUserHandles());
|
||||
SYSTEM_FLAG_HIDE_NON_SYSTEM_OVERLAY_WINDOWS, getAllowedUserHandles(),
|
||||
mParams.getAllowedActivities(),
|
||||
mParams.getBlockedActivities());
|
||||
mWindowPolicyControllers.put(displayId, dwpc);
|
||||
return dwpc;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user