Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 22e15c68 authored by Antony Sargent's avatar Antony Sargent Committed by Automerger Merge Worker
Browse files

Merge "Prevent deadlocks during VirtualDisplay creation" into tm-dev am:...

Merge "Prevent deadlocks during VirtualDisplay creation" into tm-dev am: fc6eb70e am: de2d849a am: 4c50bc79

Original change: https://googleplex-android-review.googlesource.com/c/platform/frameworks/base/+/18246032



Change-Id: I7f4e099784e1c5ae8b96d60567c24d43102bac6b
Signed-off-by: default avatarAutomerger Merge Worker <android-build-automerger-merge-worker@system.gserviceaccount.com>
parents 751086c7 4c50bc79
Loading
Loading
Loading
Loading
+14 −0
Original line number Diff line number Diff line
@@ -19,6 +19,8 @@ package android.companion.virtual;
import android.companion.virtual.IVirtualDevice;
import android.companion.virtual.IVirtualDeviceActivityListener;
import android.companion.virtual.VirtualDeviceParams;
import android.hardware.display.IVirtualDisplayCallback;
import android.hardware.display.VirtualDisplayConfig;

/**
 * Interface for communication between VirtualDeviceManager and VirtualDeviceManagerService.
@@ -42,4 +44,16 @@ interface IVirtualDeviceManager {
    IVirtualDevice createVirtualDevice(
            in IBinder token, String packageName, int associationId,
            in VirtualDeviceParams params, in IVirtualDeviceActivityListener activityListener);

    /**
     * Creates a virtual display owned by a particular virtual device.
     *
     * @param virtualDisplayConfig The configuration used in creating the display
     * @param callback A callback that receives display lifecycle events
     * @param virtualDevice The device that will own this display
     * @param packageName The package name of the calling app
     */
    int createVirtualDisplay(in VirtualDisplayConfig virtualDisplayConfig,
            in IVirtualDisplayCallback callback, in IVirtualDevice virtualDevice,
            String packageName);
}
+22 −13
Original line number Diff line number Diff line
@@ -33,6 +33,8 @@ import android.content.Context;
import android.graphics.Point;
import android.hardware.display.DisplayManager;
import android.hardware.display.DisplayManager.VirtualDisplayFlag;
import android.hardware.display.DisplayManagerGlobal;
import android.hardware.display.IVirtualDisplayCallback;
import android.hardware.display.VirtualDisplay;
import android.hardware.display.VirtualDisplayConfig;
import android.hardware.input.VirtualKeyboard;
@@ -65,7 +67,7 @@ import java.util.function.IntConsumer;
public final class VirtualDeviceManager {

    private static final boolean DEBUG = false;
    private static final String LOG_TAG = "VirtualDeviceManager";
    private static final String TAG = "VirtualDeviceManager";

    private static final int DEFAULT_VIRTUAL_DISPLAY_FLAGS =
            DisplayManager.VIRTUAL_DISPLAY_FLAG_PUBLIC
@@ -150,6 +152,7 @@ public final class VirtualDeviceManager {
    public static class VirtualDevice implements AutoCloseable {

        private final Context mContext;
        private final IVirtualDeviceManager mService;
        private final IVirtualDevice mVirtualDevice;
        private final ArrayMap<ActivityListener, ActivityListenerDelegate> mActivityListeners =
                new ArrayMap<>();
@@ -189,6 +192,7 @@ public final class VirtualDeviceManager {
                Context context,
                int associationId,
                VirtualDeviceParams params) throws RemoteException {
            mService = service;
            mContext = context.getApplicationContext();
            mVirtualDevice = service.createVirtualDevice(
                    new Binder(),
@@ -274,18 +278,23 @@ public final class VirtualDeviceManager {
            // TODO(b/205343547): Handle display groups properly instead of creating a new display
            //  group for every new virtual display created using this API.
            // belongs to the same display group.
            DisplayManager displayManager = mContext.getSystemService(DisplayManager.class);
            // DisplayManager will call into VirtualDeviceManagerInternal to register the
            // created displays.
            return displayManager.createVirtualDisplay(
                    mVirtualDevice,
                    new VirtualDisplayConfig.Builder(
            VirtualDisplayConfig config = new VirtualDisplayConfig.Builder(
                    getVirtualDisplayName(), width, height, densityDpi)
                    .setSurface(surface)
                    .setFlags(getVirtualDisplayFlags(flags))
                            .build(),
                    callback,
                    executor);
                    .build();
            IVirtualDisplayCallback callbackWrapper =
                    new DisplayManagerGlobal.VirtualDisplayCallback(callback, executor);
            final int displayId;
            try {
                displayId = mService.createVirtualDisplay(config, callbackWrapper, mVirtualDevice,
                        mContext.getPackageName());
            } catch (RemoteException ex) {
                throw ex.rethrowFromSystemServer();
            }
            DisplayManagerGlobal displayManager = DisplayManagerGlobal.getInstance();
            return displayManager.createVirtualDisplayWrapper(config, mContext, callbackWrapper,
                    displayId);
        }

        /**
+2 −12
Original line number Diff line number Diff line
@@ -31,7 +31,6 @@ import android.annotation.SystemApi;
import android.annotation.SystemService;
import android.annotation.TestApi;
import android.app.KeyguardManager;
import android.companion.virtual.IVirtualDevice;
import android.compat.annotation.UnsupportedAppUsage;
import android.content.Context;
import android.content.res.Resources;
@@ -971,17 +970,8 @@ public final class DisplayManager {
            executor = new HandlerExecutor(
                    Handler.createAsync(handler != null ? handler.getLooper() : Looper.myLooper()));
        }
        return mGlobal.createVirtualDisplay(mContext, projection, null /* virtualDevice */,
                virtualDisplayConfig, callback, executor, windowContext);
    }

    /** @hide */
    public VirtualDisplay createVirtualDisplay(@Nullable IVirtualDevice virtualDevice,
            @NonNull VirtualDisplayConfig virtualDisplayConfig,
            @Nullable VirtualDisplay.Callback callback,
            @Nullable Executor executor) {
        return mGlobal.createVirtualDisplay(mContext, null /* projection */, virtualDevice,
                virtualDisplayConfig, callback, executor, null);
        return mGlobal.createVirtualDisplay(mContext, projection, virtualDisplayConfig, callback,
                executor, windowContext);
    }

    /**
+19 −7
Original line number Diff line number Diff line
@@ -24,7 +24,6 @@ import android.annotation.IntDef;
import android.annotation.NonNull;
import android.annotation.Nullable;
import android.app.PropertyInvalidatedCache;
import android.companion.virtual.IVirtualDevice;
import android.compat.annotation.UnsupportedAppUsage;
import android.content.Context;
import android.content.pm.ParceledListSlice;
@@ -586,18 +585,28 @@ public final class DisplayManagerGlobal {
    }

    public VirtualDisplay createVirtualDisplay(@NonNull Context context, MediaProjection projection,
            IVirtualDevice virtualDevice, @NonNull VirtualDisplayConfig virtualDisplayConfig,
            VirtualDisplay.Callback callback, @Nullable Executor executor,
            @Nullable Context windowContext) {
            @NonNull VirtualDisplayConfig virtualDisplayConfig, VirtualDisplay.Callback callback,
            @Nullable Executor executor, @Nullable Context windowContext) {
        VirtualDisplayCallback callbackWrapper = new VirtualDisplayCallback(callback, executor);
        IMediaProjection projectionToken = projection != null ? projection.getProjection() : null;
        int displayId;
        try {
            displayId = mDm.createVirtualDisplay(virtualDisplayConfig, callbackWrapper,
                    projectionToken, virtualDevice, context.getPackageName());
                    projectionToken, context.getPackageName());
        } catch (RemoteException ex) {
            throw ex.rethrowFromSystemServer();
        }
        return createVirtualDisplayWrapper(virtualDisplayConfig, windowContext, callbackWrapper,
                displayId);
    }

    /**
     * Create a VirtualDisplay wrapper object for a newly created virtual display ; to be called
     * once the display has been created in system_server.
     */
    @Nullable
    public VirtualDisplay createVirtualDisplayWrapper(VirtualDisplayConfig virtualDisplayConfig,
            Context windowContext, IVirtualDisplayCallback callbackWrapper, int displayId) {
        if (displayId < 0) {
            Log.e(TAG, "Could not create virtual display: " + virtualDisplayConfig.getName());
            return null;
@@ -1050,7 +1059,10 @@ public final class DisplayManagerGlobal {
        }
    }

    private final static class VirtualDisplayCallback extends IVirtualDisplayCallback.Stub {
    /**
     * Assists in dispatching VirtualDisplay lifecycle event callbacks on a given Executor.
     */
    public static final class VirtualDisplayCallback extends IVirtualDisplayCallback.Stub {
        @Nullable private final VirtualDisplay.Callback mCallback;
        @Nullable private final Executor mExecutor;

@@ -1062,7 +1074,7 @@ public final class DisplayManagerGlobal {
         * @param executor The executor to call the {@code callback} on. Must not be {@code null} if
         * the callback is not {@code null}.
         */
        VirtualDisplayCallback(VirtualDisplay.Callback callback, Executor executor) {
        public VirtualDisplayCallback(VirtualDisplay.Callback callback, Executor executor) {
            mCallback = callback;
            mExecutor = mCallback != null ? Objects.requireNonNull(executor) : null;
        }
+9 −0
Original line number Diff line number Diff line
@@ -18,6 +18,7 @@ package android.hardware.display;

import android.annotation.IntDef;
import android.annotation.Nullable;
import android.companion.virtual.IVirtualDevice;
import android.graphics.Point;
import android.hardware.SensorManager;
import android.os.Handler;
@@ -59,6 +60,14 @@ public abstract class DisplayManagerInternal {
    public abstract void initPowerManagement(DisplayPowerCallbacks callbacks,
            Handler handler, SensorManager sensorManager);

    /**
     * Called by the VirtualDeviceManagerService to create a VirtualDisplay owned by a
     * VirtualDevice.
     */
    public abstract int createVirtualDisplay(VirtualDisplayConfig config,
            IVirtualDisplayCallback callback, IVirtualDevice virtualDevice,
            DisplayWindowPolicyController dwpc, String packageName);

    /**
     * Called by the power manager to request a new power state.
     * <p>
Loading