Loading services/core/java/com/android/server/am/flags.aconfig +0 −8 Original line number Diff line number Diff line Loading @@ -98,14 +98,6 @@ flag { is_fixed_read_only: true } flag { name: "defer_display_events_when_frozen" namespace: "system_performance" is_fixed_read_only: true description: "Defer submitting display events to frozen processes." bug: "326315985" } flag { name: "push_global_state_to_oomadjuster" namespace: "backstage_power" Loading services/core/java/com/android/server/display/DisplayManagerService.java +48 −208 Original line number Diff line number Diff line Loading @@ -29,7 +29,6 @@ import static android.Manifest.permission.MODIFY_HDR_CONVERSION_MODE; import static android.Manifest.permission.RESTRICT_DISPLAY_MODES; import static android.Manifest.permission.WRITE_SETTINGS; import static android.app.ActivityManager.RunningAppProcessInfo.IMPORTANCE_CACHED; import static android.app.ActivityManager.RunningAppProcessInfo.IMPORTANCE_GONE; import static android.app.ActivityManager.RunningAppProcessInfo.IMPORTANCE_VISIBLE; import static android.hardware.display.DisplayManager.BRIGHTNESS_UNIT_PERCENTAGE; import static android.hardware.display.DisplayManager.VIRTUAL_DISPLAY_FLAG_ALWAYS_UNLOCKED; Loading Loading @@ -347,7 +346,6 @@ public final class DisplayManagerService extends SystemService { private final SparseArray<CallbackRecord> mCallbacks = new SparseArray<>(); // All callback records indexed by [uid][pid], for fast lookup by uid. // This is only used if {@link deferDisplayEventsWhenFrozen()} is true. @GuardedBy("mSyncRoot") private final SparseArray<SparseArray<CallbackRecord>> mCallbackRecordByPidByUid = new SparseArray<>(); Loading Loading @@ -503,13 +501,6 @@ public final class DisplayManagerService extends SystemService { // May be used outside of the lock but only on the handler thread. private final ArrayList<CallbackRecord> mTempCallbacks = new ArrayList<>(); // Pending callback records indexed by calling process uid and pid. // Must be used outside of the lock mSyncRoot and should be self-locked. // This is only used when {@link deferDisplayEventsWhenFrozen()} is false. @GuardedBy("mPendingCallbackSelfLocked") private final SparseArray<SparseArray<PendingCallback>> mPendingCallbackSelfLocked = new SparseArray<>(); // Temporary viewports, used when sending new viewport information to the // input system. May be used outside of the lock but only on the handler thread. private final ArrayList<DisplayViewport> mTempViewports = new ArrayList<>(); Loading Loading @@ -1139,46 +1130,6 @@ public final class DisplayManagerService extends SystemService { private class UidImportanceListener implements ActivityManager.OnUidImportanceListener { @Override public void onUidImportance(int uid, int importance) { if (deferDisplayEventsWhenFrozen()) { onUidImportanceFlagged(uid, importance); } else { onUidImportanceUnflagged(uid, importance); } } private void onUidImportanceUnflagged(int uid, int importance) { synchronized (mPendingCallbackSelfLocked) { if (importance >= IMPORTANCE_GONE) { // Clean up as the app is already gone Slog.d(TAG, "Drop pending events for gone uid " + uid); mPendingCallbackSelfLocked.delete(uid); return; } else if (importance >= IMPORTANCE_CACHED) { // Nothing to do as the app is still in cached mode return; } // Do we care about this uid? SparseArray<PendingCallback> pendingCallbacks = mPendingCallbackSelfLocked.get(uid); if (pendingCallbacks == null) { return; } // Send the pending events out when a certain uid becomes non-cached if (DEBUG) { Slog.d(TAG, "Uid " + uid + " becomes " + importance); } for (int i = 0; i < pendingCallbacks.size(); i++) { PendingCallback pendingCallback = pendingCallbacks.valueAt(i); if (pendingCallback != null) { pendingCallback.sendPendingDisplayEvent(); } } mPendingCallbackSelfLocked.delete(uid); } } private void onUidImportanceFlagged(int uid, int importance) { final boolean cached = (importance >= IMPORTANCE_CACHED); List<CallbackRecord> readyCallbackRecords = null; synchronized (mSyncRoot) { Loading Loading @@ -1573,7 +1524,6 @@ public final class DisplayManagerService extends SystemService { } mCallbacks.put(callingPid, record); if (deferDisplayEventsWhenFrozen()) { SparseArray<CallbackRecord> uidPeers = mCallbackRecordByPidByUid.get(record.mUid); if (uidPeers == null) { uidPeers = new SparseArray<CallbackRecord>(); Loading @@ -1582,12 +1532,10 @@ public final class DisplayManagerService extends SystemService { uidPeers.put(record.mPid, record); } } } private void onCallbackDied(CallbackRecord record) { synchronized (mSyncRoot) { mCallbacks.remove(record.mPid); if (deferDisplayEventsWhenFrozen()) { SparseArray<CallbackRecord> uidPeers = mCallbackRecordByPidByUid.get(record.mUid); if (uidPeers != null) { uidPeers.remove(record.mPid); Loading @@ -1595,7 +1543,6 @@ public final class DisplayManagerService extends SystemService { mCallbackRecordByPidByUid.remove(record.mUid); } } } stopWifiDisplayScanLocked(record); } } Loading Loading @@ -3743,46 +3690,9 @@ public final class DisplayManagerService extends SystemService { // After releasing the lock, send the notifications out. for (int i = 0; i < mTempCallbacks.size(); i++) { CallbackRecord callbackRecord = mTempCallbacks.get(i); if (deferDisplayEventsWhenFrozen()) { deliverEventFlagged(callbackRecord, displayId, event); } else { deliverEventUnflagged(callbackRecord, displayId, event); } } mTempCallbacks.clear(); } private void deliverEventUnflagged(CallbackRecord callbackRecord, int displayId, int event) { final int uid = callbackRecord.mUid; final int pid = callbackRecord.mPid; if (isUidCached(uid)) { // For cached apps, save the pending event until it becomes non-cached synchronized (mPendingCallbackSelfLocked) { SparseArray<PendingCallback> pendingCallbacks = mPendingCallbackSelfLocked.get( uid); if (extraLogging(callbackRecord.mPackageName)) { Slog.i(TAG, "Uid is cached: " + uid + ", pendingCallbacks: " + pendingCallbacks); } if (pendingCallbacks == null) { pendingCallbacks = new SparseArray<>(); mPendingCallbackSelfLocked.put(uid, pendingCallbacks); } PendingCallback pendingCallback = pendingCallbacks.get(pid); if (pendingCallback == null) { pendingCallbacks.put(pid, new PendingCallback(callbackRecord, displayId, event)); } else { pendingCallback.addDisplayEvent(displayId, event); } } } else { callbackRecord.notifyDisplayEventAsync(displayId, event); } } private void deliverEventFlagged(CallbackRecord callbackRecord, int displayId, int event) { callbackRecord.notifyDisplayEventAsync(displayId, event); mTempCallbacks.clear(); } private void deliverTopologyUpdate(DisplayTopology topology) { Loading Loading @@ -4403,7 +4313,7 @@ public final class DisplayManagerService extends SystemService { private record Event(int displayId, @DisplayEvent int event) { }; // The list of pending display events. This is null until there is a pending event to be // saved. This is only used if {@link deferDisplayEventsWhenFrozen()} is true. // saved. @GuardedBy("mCallback") @Nullable private ArrayList<Event> mPendingDisplayEvents; Loading Loading @@ -4431,7 +4341,6 @@ public final class DisplayManagerService extends SystemService { mFrozen = false; mAlive = true; if (deferDisplayEventsWhenFrozen()) { try { callback.asBinder().addFrozenStateChangeCallback(this); } catch (UnsupportedOperationException e) { Loading @@ -4444,7 +4353,6 @@ public final class DisplayManagerService extends SystemService { // This is unexpected. Just give up. throw new RuntimeException(e); } } String[] packageNames = mContext.getPackageManager().getPackagesForUid(uid); mPackageName = packageNames == null ? null : packageNames[0]; Loading Loading @@ -4489,7 +4397,6 @@ public final class DisplayManagerService extends SystemService { /** * Set the frozen flag for this process. Return true if the process is now ready to * receive events and there are pending events to be delivered. * This is only used if {@link deferDisplayEventsWhenFrozen()} is true. */ private boolean setFrozen(boolean frozen) { synchronized (mCallback) { Loading @@ -4501,7 +4408,6 @@ public final class DisplayManagerService extends SystemService { /** * Set the cached flag for this process. Return true if the process is now ready to * receive events and there are pending events to be delivered. * This is only used if {@link deferDisplayEventsWhenFrozen()} is true. */ public boolean setCached(boolean cached) { synchronized (mCallback) { Loading Loading @@ -4558,7 +4464,6 @@ public final class DisplayManagerService extends SystemService { return true; } if (deferDisplayEventsWhenFrozen()) { synchronized (mCallback) { // Add the new event to the pending list if the client frozen or cached (not // ready) or if there are existing pending events. The latter condition Loading @@ -4573,7 +4478,6 @@ public final class DisplayManagerService extends SystemService { return true; } } } if (!shouldReceiveRefreshRateWithChangeUpdate(event)) { // The client is not visible to the user and is not a system service, so do nothing. Loading Loading @@ -4650,7 +4554,6 @@ public final class DisplayManagerService extends SystemService { // Add a single event to the pending list, possibly combining or collapsing events in the // list. // This is only used if {@link deferDisplayEventsWhenFrozen()} is true. @GuardedBy("mCallback") private void addDisplayEvent(int displayId, int event) { if (mPendingDisplayEvents == null) { Loading Loading @@ -4692,7 +4595,6 @@ public final class DisplayManagerService extends SystemService { return true; } if (deferDisplayEventsWhenFrozen()) { synchronized (mCallback) { // Save the new update if the client frozen or cached (not ready). if (!isReadyLocked()) { Loading @@ -4701,7 +4603,6 @@ public final class DisplayManagerService extends SystemService { return true; } } } return transmitTopologyUpdate(topology); } Loading @@ -4725,7 +4626,6 @@ public final class DisplayManagerService extends SystemService { // Send all pending events. This can safely be called if the process is not ready, but it // would be unusual to do so. The method returns true on success. // This is only used if {@link deferDisplayEventsWhenFrozen()} is true. public boolean dispatchPending() { Event[] pendingDisplayEvents = null; DisplayTopology pendingTopology; Loading Loading @@ -4783,7 +4683,6 @@ public final class DisplayManagerService extends SystemService { // Return a string suitable for dumpsys. private String dump() { if (deferDisplayEventsWhenFrozen()) { final String fmt = "mPid=%d mUid=%d mWifiDisplayScanRequested=%s" + " cached=%s frozen=%s pendingDisplayEvents=%d pendingTopology=%b"; Loading @@ -4793,57 +4692,6 @@ public final class DisplayManagerService extends SystemService { (mPendingDisplayEvents == null) ? 0 : mPendingDisplayEvents.size(), mPendingTopology != null); } } else { final String fmt = "mPid=%d mUid=%d mWifiDisplayScanRequested=%s"; return formatSimple(fmt, mPid, mUid, mWifiDisplayScanRequested); } } } /** * This is only used if {@link deferDisplayEventsWhenFrozen()} is false. */ private static final class PendingCallback { private final CallbackRecord mCallbackRecord; private final ArrayList<Pair<Integer, Integer>> mDisplayEvents; PendingCallback(CallbackRecord cr, int displayId, int event) { mCallbackRecord = cr; mDisplayEvents = new ArrayList<>(); mDisplayEvents.add(new Pair<>(displayId, event)); } public void addDisplayEvent(int displayId, int event) { // Ignore redundant events. Further optimization is possible by merging adjacent events. Pair<Integer, Integer> last = mDisplayEvents.get(mDisplayEvents.size() - 1); if (last.first == displayId && last.second == event) { if (DEBUG) { Slog.d(TAG, "Ignore redundant display event " + displayId + "/" + event + " to " + mCallbackRecord.mUid + "/" + mCallbackRecord.mPid); } return; } mDisplayEvents.add(new Pair<>(displayId, event)); } public void sendPendingDisplayEvent() { for (int i = 0; i < mDisplayEvents.size(); i++) { Pair<Integer, Integer> displayEvent = mDisplayEvents.get(i); if (DEBUG) { Slog.d(TAG, "Send pending display event #" + i + " " + displayEvent.first + "/" + displayEvent.second + " to " + mCallbackRecord.mUid + "/" + mCallbackRecord.mPid); } if (!mCallbackRecord.notifyDisplayEventAsync(displayEvent.first, displayEvent.second)) { Slog.d(TAG, "Drop pending events for dead process " + mCallbackRecord.mPid); break; } } mDisplayEvents.clear(); } } Loading Loading @@ -6524,14 +6372,6 @@ public final class DisplayManagerService extends SystemService { } } /** * Return the value of the pause */ private static boolean deferDisplayEventsWhenFrozen() { return android.os.Flags.binderFrozenStateChangeCallback() && com.android.server.am.Flags.deferDisplayEventsWhenFrozen(); } interface DisplayInfoProvider { @Nullable DisplayInfo get(int displayId); Loading services/tests/displayservicetests/src/com/android/server/display/DisplayEventDeliveryTest.java +5 −17 Original line number Diff line number Diff line Loading @@ -31,20 +31,14 @@ import android.hardware.display.VirtualDisplay; import android.os.Handler; import android.os.Looper; import android.os.Message; import android.platform.test.annotations.RequiresFlagsEnabled; import android.platform.test.flag.junit.CheckFlagsRule; import android.platform.test.flag.junit.DeviceFlagsValueProvider; import android.util.Log; import android.util.SparseArray; import androidx.annotation.GuardedBy; import androidx.annotation.NonNull; import com.android.server.am.Flags; import org.junit.After; import org.junit.Before; import org.junit.Rule; import org.junit.Test; import org.junit.runner.RunWith; import org.junit.runners.Parameterized; Loading @@ -62,10 +56,6 @@ import java.util.concurrent.TimeUnit; public class DisplayEventDeliveryTest extends EventDeliveryTestBase { private static final String TAG = "DisplayEventDeliveryTest"; @Rule public final CheckFlagsRule mCheckFlagsRule = DeviceFlagsValueProvider.createCheckFlagsRule(); private static final String NAME = TAG; private static final int WIDTH = 720; private static final int HEIGHT = 480; Loading Loading @@ -123,7 +113,7 @@ public class DisplayEventDeliveryTest extends EventDeliveryTestBase { * @param event The corresponding display event */ public void addDisplayEvent(int event) { Log.d(TAG, "Received " + mDisplayId + " " + event); Log.i(TAG, "Received " + mDisplayId + " " + event); mExpectations.offer(event); } Loading @@ -150,7 +140,7 @@ public class DisplayEventDeliveryTest extends EventDeliveryTestBase { event = mExpectations.poll(TEST_FAILURE_TIMEOUT_MSEC, TimeUnit.MILLISECONDS); assertNotNull(event); if (expect == event) { Log.d(TAG, "Found " + mDisplayId + " " + event); Log.i(TAG, "Found " + mDisplayId + " " + event); return; } } catch (InterruptedException e) { Loading Loading @@ -182,11 +172,11 @@ public class DisplayEventDeliveryTest extends EventDeliveryTestBase { case MESSAGE_LAUNCHED: mPid = msg.arg1; mUid = msg.arg2; Log.d(TAG, "Launched " + mPid + " " + mUid); Log.i(TAG, "Launched " + mPid + " " + mUid); mLatchActivityLaunch.countDown(); break; case MESSAGE_CALLBACK: Log.d(TAG, "Callback " + msg.arg1 + " " + msg.arg2); Log.i(TAG, "Callback " + msg.arg1 + " " + msg.arg2); synchronized (mLock) { // arg1: displayId DisplayBundle bundle = mDisplayBundles.get(msg.arg1); Loading Loading @@ -264,7 +254,7 @@ public class DisplayEventDeliveryTest extends EventDeliveryTestBase { * displays is set by the {@link #data()} parameter. */ private void testDisplayEventsInternal(boolean cached, boolean frozen) { Log.d(TAG, "Start test testDisplayEvents " + mDisplayCount + " " + cached + " " + frozen); Log.i(TAG, "Start test testDisplayEvents " + mDisplayCount + " " + cached + " " + frozen); // Launch DisplayEventActivity and start listening to display events int pid = launchTestActivity(); Loading Loading @@ -361,7 +351,6 @@ public class DisplayEventDeliveryTest extends EventDeliveryTestBase { * Create virtual displays, change their configurations and release them. The display app is * frozen and the test verifies that no events are delivered to the frozen app. */ @RequiresFlagsEnabled(Flags.FLAG_DEFER_DISPLAY_EVENTS_WHEN_FROZEN) @Test public void testDisplayEventsFrozen() { assumeTrue(isAppFreezerEnabled()); Loading @@ -372,7 +361,6 @@ public class DisplayEventDeliveryTest extends EventDeliveryTestBase { * Create virtual displays, change their configurations and release them. The display app is * cached and frozen and the test verifies that no events are delivered to the app. */ @RequiresFlagsEnabled(Flags.FLAG_DEFER_DISPLAY_EVENTS_WHEN_FROZEN) @Test public void testDisplayEventsCachedFrozen() { assumeTrue(isAppFreezerEnabled()); Loading services/tests/displayservicetests/src/com/android/server/display/TopologyUpdateDeliveryTest.java +2 −4 Original line number Diff line number Diff line Loading @@ -222,8 +222,7 @@ public class TopologyUpdateDeliveryTest extends EventDeliveryTestBase { /** * The app is frozen and the test verifies that no updates are delivered to the frozen app. */ @RequiresFlagsEnabled({com.android.server.am.Flags.FLAG_DEFER_DISPLAY_EVENTS_WHEN_FROZEN, com.android.server.display.feature.flags.Flags.FLAG_DISPLAY_TOPOLOGY}) @RequiresFlagsEnabled(com.android.server.display.feature.flags.Flags.FLAG_DISPLAY_TOPOLOGY) @Test public void testTopologyUpdateFrozen() { assumeTrue(isAppFreezerEnabled()); Loading @@ -233,8 +232,7 @@ public class TopologyUpdateDeliveryTest extends EventDeliveryTestBase { /** * The app is cached and frozen and the test verifies that no updates are delivered to the app. */ @RequiresFlagsEnabled({com.android.server.am.Flags.FLAG_DEFER_DISPLAY_EVENTS_WHEN_FROZEN, com.android.server.display.feature.flags.Flags.FLAG_DISPLAY_TOPOLOGY}) @RequiresFlagsEnabled(com.android.server.display.feature.flags.Flags.FLAG_DISPLAY_TOPOLOGY) @Test public void testTopologyUpdateCachedFrozen() { assumeTrue(isAppFreezerEnabled()); Loading Loading
services/core/java/com/android/server/am/flags.aconfig +0 −8 Original line number Diff line number Diff line Loading @@ -98,14 +98,6 @@ flag { is_fixed_read_only: true } flag { name: "defer_display_events_when_frozen" namespace: "system_performance" is_fixed_read_only: true description: "Defer submitting display events to frozen processes." bug: "326315985" } flag { name: "push_global_state_to_oomadjuster" namespace: "backstage_power" Loading
services/core/java/com/android/server/display/DisplayManagerService.java +48 −208 Original line number Diff line number Diff line Loading @@ -29,7 +29,6 @@ import static android.Manifest.permission.MODIFY_HDR_CONVERSION_MODE; import static android.Manifest.permission.RESTRICT_DISPLAY_MODES; import static android.Manifest.permission.WRITE_SETTINGS; import static android.app.ActivityManager.RunningAppProcessInfo.IMPORTANCE_CACHED; import static android.app.ActivityManager.RunningAppProcessInfo.IMPORTANCE_GONE; import static android.app.ActivityManager.RunningAppProcessInfo.IMPORTANCE_VISIBLE; import static android.hardware.display.DisplayManager.BRIGHTNESS_UNIT_PERCENTAGE; import static android.hardware.display.DisplayManager.VIRTUAL_DISPLAY_FLAG_ALWAYS_UNLOCKED; Loading Loading @@ -347,7 +346,6 @@ public final class DisplayManagerService extends SystemService { private final SparseArray<CallbackRecord> mCallbacks = new SparseArray<>(); // All callback records indexed by [uid][pid], for fast lookup by uid. // This is only used if {@link deferDisplayEventsWhenFrozen()} is true. @GuardedBy("mSyncRoot") private final SparseArray<SparseArray<CallbackRecord>> mCallbackRecordByPidByUid = new SparseArray<>(); Loading Loading @@ -503,13 +501,6 @@ public final class DisplayManagerService extends SystemService { // May be used outside of the lock but only on the handler thread. private final ArrayList<CallbackRecord> mTempCallbacks = new ArrayList<>(); // Pending callback records indexed by calling process uid and pid. // Must be used outside of the lock mSyncRoot and should be self-locked. // This is only used when {@link deferDisplayEventsWhenFrozen()} is false. @GuardedBy("mPendingCallbackSelfLocked") private final SparseArray<SparseArray<PendingCallback>> mPendingCallbackSelfLocked = new SparseArray<>(); // Temporary viewports, used when sending new viewport information to the // input system. May be used outside of the lock but only on the handler thread. private final ArrayList<DisplayViewport> mTempViewports = new ArrayList<>(); Loading Loading @@ -1139,46 +1130,6 @@ public final class DisplayManagerService extends SystemService { private class UidImportanceListener implements ActivityManager.OnUidImportanceListener { @Override public void onUidImportance(int uid, int importance) { if (deferDisplayEventsWhenFrozen()) { onUidImportanceFlagged(uid, importance); } else { onUidImportanceUnflagged(uid, importance); } } private void onUidImportanceUnflagged(int uid, int importance) { synchronized (mPendingCallbackSelfLocked) { if (importance >= IMPORTANCE_GONE) { // Clean up as the app is already gone Slog.d(TAG, "Drop pending events for gone uid " + uid); mPendingCallbackSelfLocked.delete(uid); return; } else if (importance >= IMPORTANCE_CACHED) { // Nothing to do as the app is still in cached mode return; } // Do we care about this uid? SparseArray<PendingCallback> pendingCallbacks = mPendingCallbackSelfLocked.get(uid); if (pendingCallbacks == null) { return; } // Send the pending events out when a certain uid becomes non-cached if (DEBUG) { Slog.d(TAG, "Uid " + uid + " becomes " + importance); } for (int i = 0; i < pendingCallbacks.size(); i++) { PendingCallback pendingCallback = pendingCallbacks.valueAt(i); if (pendingCallback != null) { pendingCallback.sendPendingDisplayEvent(); } } mPendingCallbackSelfLocked.delete(uid); } } private void onUidImportanceFlagged(int uid, int importance) { final boolean cached = (importance >= IMPORTANCE_CACHED); List<CallbackRecord> readyCallbackRecords = null; synchronized (mSyncRoot) { Loading Loading @@ -1573,7 +1524,6 @@ public final class DisplayManagerService extends SystemService { } mCallbacks.put(callingPid, record); if (deferDisplayEventsWhenFrozen()) { SparseArray<CallbackRecord> uidPeers = mCallbackRecordByPidByUid.get(record.mUid); if (uidPeers == null) { uidPeers = new SparseArray<CallbackRecord>(); Loading @@ -1582,12 +1532,10 @@ public final class DisplayManagerService extends SystemService { uidPeers.put(record.mPid, record); } } } private void onCallbackDied(CallbackRecord record) { synchronized (mSyncRoot) { mCallbacks.remove(record.mPid); if (deferDisplayEventsWhenFrozen()) { SparseArray<CallbackRecord> uidPeers = mCallbackRecordByPidByUid.get(record.mUid); if (uidPeers != null) { uidPeers.remove(record.mPid); Loading @@ -1595,7 +1543,6 @@ public final class DisplayManagerService extends SystemService { mCallbackRecordByPidByUid.remove(record.mUid); } } } stopWifiDisplayScanLocked(record); } } Loading Loading @@ -3743,46 +3690,9 @@ public final class DisplayManagerService extends SystemService { // After releasing the lock, send the notifications out. for (int i = 0; i < mTempCallbacks.size(); i++) { CallbackRecord callbackRecord = mTempCallbacks.get(i); if (deferDisplayEventsWhenFrozen()) { deliverEventFlagged(callbackRecord, displayId, event); } else { deliverEventUnflagged(callbackRecord, displayId, event); } } mTempCallbacks.clear(); } private void deliverEventUnflagged(CallbackRecord callbackRecord, int displayId, int event) { final int uid = callbackRecord.mUid; final int pid = callbackRecord.mPid; if (isUidCached(uid)) { // For cached apps, save the pending event until it becomes non-cached synchronized (mPendingCallbackSelfLocked) { SparseArray<PendingCallback> pendingCallbacks = mPendingCallbackSelfLocked.get( uid); if (extraLogging(callbackRecord.mPackageName)) { Slog.i(TAG, "Uid is cached: " + uid + ", pendingCallbacks: " + pendingCallbacks); } if (pendingCallbacks == null) { pendingCallbacks = new SparseArray<>(); mPendingCallbackSelfLocked.put(uid, pendingCallbacks); } PendingCallback pendingCallback = pendingCallbacks.get(pid); if (pendingCallback == null) { pendingCallbacks.put(pid, new PendingCallback(callbackRecord, displayId, event)); } else { pendingCallback.addDisplayEvent(displayId, event); } } } else { callbackRecord.notifyDisplayEventAsync(displayId, event); } } private void deliverEventFlagged(CallbackRecord callbackRecord, int displayId, int event) { callbackRecord.notifyDisplayEventAsync(displayId, event); mTempCallbacks.clear(); } private void deliverTopologyUpdate(DisplayTopology topology) { Loading Loading @@ -4403,7 +4313,7 @@ public final class DisplayManagerService extends SystemService { private record Event(int displayId, @DisplayEvent int event) { }; // The list of pending display events. This is null until there is a pending event to be // saved. This is only used if {@link deferDisplayEventsWhenFrozen()} is true. // saved. @GuardedBy("mCallback") @Nullable private ArrayList<Event> mPendingDisplayEvents; Loading Loading @@ -4431,7 +4341,6 @@ public final class DisplayManagerService extends SystemService { mFrozen = false; mAlive = true; if (deferDisplayEventsWhenFrozen()) { try { callback.asBinder().addFrozenStateChangeCallback(this); } catch (UnsupportedOperationException e) { Loading @@ -4444,7 +4353,6 @@ public final class DisplayManagerService extends SystemService { // This is unexpected. Just give up. throw new RuntimeException(e); } } String[] packageNames = mContext.getPackageManager().getPackagesForUid(uid); mPackageName = packageNames == null ? null : packageNames[0]; Loading Loading @@ -4489,7 +4397,6 @@ public final class DisplayManagerService extends SystemService { /** * Set the frozen flag for this process. Return true if the process is now ready to * receive events and there are pending events to be delivered. * This is only used if {@link deferDisplayEventsWhenFrozen()} is true. */ private boolean setFrozen(boolean frozen) { synchronized (mCallback) { Loading @@ -4501,7 +4408,6 @@ public final class DisplayManagerService extends SystemService { /** * Set the cached flag for this process. Return true if the process is now ready to * receive events and there are pending events to be delivered. * This is only used if {@link deferDisplayEventsWhenFrozen()} is true. */ public boolean setCached(boolean cached) { synchronized (mCallback) { Loading Loading @@ -4558,7 +4464,6 @@ public final class DisplayManagerService extends SystemService { return true; } if (deferDisplayEventsWhenFrozen()) { synchronized (mCallback) { // Add the new event to the pending list if the client frozen or cached (not // ready) or if there are existing pending events. The latter condition Loading @@ -4573,7 +4478,6 @@ public final class DisplayManagerService extends SystemService { return true; } } } if (!shouldReceiveRefreshRateWithChangeUpdate(event)) { // The client is not visible to the user and is not a system service, so do nothing. Loading Loading @@ -4650,7 +4554,6 @@ public final class DisplayManagerService extends SystemService { // Add a single event to the pending list, possibly combining or collapsing events in the // list. // This is only used if {@link deferDisplayEventsWhenFrozen()} is true. @GuardedBy("mCallback") private void addDisplayEvent(int displayId, int event) { if (mPendingDisplayEvents == null) { Loading Loading @@ -4692,7 +4595,6 @@ public final class DisplayManagerService extends SystemService { return true; } if (deferDisplayEventsWhenFrozen()) { synchronized (mCallback) { // Save the new update if the client frozen or cached (not ready). if (!isReadyLocked()) { Loading @@ -4701,7 +4603,6 @@ public final class DisplayManagerService extends SystemService { return true; } } } return transmitTopologyUpdate(topology); } Loading @@ -4725,7 +4626,6 @@ public final class DisplayManagerService extends SystemService { // Send all pending events. This can safely be called if the process is not ready, but it // would be unusual to do so. The method returns true on success. // This is only used if {@link deferDisplayEventsWhenFrozen()} is true. public boolean dispatchPending() { Event[] pendingDisplayEvents = null; DisplayTopology pendingTopology; Loading Loading @@ -4783,7 +4683,6 @@ public final class DisplayManagerService extends SystemService { // Return a string suitable for dumpsys. private String dump() { if (deferDisplayEventsWhenFrozen()) { final String fmt = "mPid=%d mUid=%d mWifiDisplayScanRequested=%s" + " cached=%s frozen=%s pendingDisplayEvents=%d pendingTopology=%b"; Loading @@ -4793,57 +4692,6 @@ public final class DisplayManagerService extends SystemService { (mPendingDisplayEvents == null) ? 0 : mPendingDisplayEvents.size(), mPendingTopology != null); } } else { final String fmt = "mPid=%d mUid=%d mWifiDisplayScanRequested=%s"; return formatSimple(fmt, mPid, mUid, mWifiDisplayScanRequested); } } } /** * This is only used if {@link deferDisplayEventsWhenFrozen()} is false. */ private static final class PendingCallback { private final CallbackRecord mCallbackRecord; private final ArrayList<Pair<Integer, Integer>> mDisplayEvents; PendingCallback(CallbackRecord cr, int displayId, int event) { mCallbackRecord = cr; mDisplayEvents = new ArrayList<>(); mDisplayEvents.add(new Pair<>(displayId, event)); } public void addDisplayEvent(int displayId, int event) { // Ignore redundant events. Further optimization is possible by merging adjacent events. Pair<Integer, Integer> last = mDisplayEvents.get(mDisplayEvents.size() - 1); if (last.first == displayId && last.second == event) { if (DEBUG) { Slog.d(TAG, "Ignore redundant display event " + displayId + "/" + event + " to " + mCallbackRecord.mUid + "/" + mCallbackRecord.mPid); } return; } mDisplayEvents.add(new Pair<>(displayId, event)); } public void sendPendingDisplayEvent() { for (int i = 0; i < mDisplayEvents.size(); i++) { Pair<Integer, Integer> displayEvent = mDisplayEvents.get(i); if (DEBUG) { Slog.d(TAG, "Send pending display event #" + i + " " + displayEvent.first + "/" + displayEvent.second + " to " + mCallbackRecord.mUid + "/" + mCallbackRecord.mPid); } if (!mCallbackRecord.notifyDisplayEventAsync(displayEvent.first, displayEvent.second)) { Slog.d(TAG, "Drop pending events for dead process " + mCallbackRecord.mPid); break; } } mDisplayEvents.clear(); } } Loading Loading @@ -6524,14 +6372,6 @@ public final class DisplayManagerService extends SystemService { } } /** * Return the value of the pause */ private static boolean deferDisplayEventsWhenFrozen() { return android.os.Flags.binderFrozenStateChangeCallback() && com.android.server.am.Flags.deferDisplayEventsWhenFrozen(); } interface DisplayInfoProvider { @Nullable DisplayInfo get(int displayId); Loading
services/tests/displayservicetests/src/com/android/server/display/DisplayEventDeliveryTest.java +5 −17 Original line number Diff line number Diff line Loading @@ -31,20 +31,14 @@ import android.hardware.display.VirtualDisplay; import android.os.Handler; import android.os.Looper; import android.os.Message; import android.platform.test.annotations.RequiresFlagsEnabled; import android.platform.test.flag.junit.CheckFlagsRule; import android.platform.test.flag.junit.DeviceFlagsValueProvider; import android.util.Log; import android.util.SparseArray; import androidx.annotation.GuardedBy; import androidx.annotation.NonNull; import com.android.server.am.Flags; import org.junit.After; import org.junit.Before; import org.junit.Rule; import org.junit.Test; import org.junit.runner.RunWith; import org.junit.runners.Parameterized; Loading @@ -62,10 +56,6 @@ import java.util.concurrent.TimeUnit; public class DisplayEventDeliveryTest extends EventDeliveryTestBase { private static final String TAG = "DisplayEventDeliveryTest"; @Rule public final CheckFlagsRule mCheckFlagsRule = DeviceFlagsValueProvider.createCheckFlagsRule(); private static final String NAME = TAG; private static final int WIDTH = 720; private static final int HEIGHT = 480; Loading Loading @@ -123,7 +113,7 @@ public class DisplayEventDeliveryTest extends EventDeliveryTestBase { * @param event The corresponding display event */ public void addDisplayEvent(int event) { Log.d(TAG, "Received " + mDisplayId + " " + event); Log.i(TAG, "Received " + mDisplayId + " " + event); mExpectations.offer(event); } Loading @@ -150,7 +140,7 @@ public class DisplayEventDeliveryTest extends EventDeliveryTestBase { event = mExpectations.poll(TEST_FAILURE_TIMEOUT_MSEC, TimeUnit.MILLISECONDS); assertNotNull(event); if (expect == event) { Log.d(TAG, "Found " + mDisplayId + " " + event); Log.i(TAG, "Found " + mDisplayId + " " + event); return; } } catch (InterruptedException e) { Loading Loading @@ -182,11 +172,11 @@ public class DisplayEventDeliveryTest extends EventDeliveryTestBase { case MESSAGE_LAUNCHED: mPid = msg.arg1; mUid = msg.arg2; Log.d(TAG, "Launched " + mPid + " " + mUid); Log.i(TAG, "Launched " + mPid + " " + mUid); mLatchActivityLaunch.countDown(); break; case MESSAGE_CALLBACK: Log.d(TAG, "Callback " + msg.arg1 + " " + msg.arg2); Log.i(TAG, "Callback " + msg.arg1 + " " + msg.arg2); synchronized (mLock) { // arg1: displayId DisplayBundle bundle = mDisplayBundles.get(msg.arg1); Loading Loading @@ -264,7 +254,7 @@ public class DisplayEventDeliveryTest extends EventDeliveryTestBase { * displays is set by the {@link #data()} parameter. */ private void testDisplayEventsInternal(boolean cached, boolean frozen) { Log.d(TAG, "Start test testDisplayEvents " + mDisplayCount + " " + cached + " " + frozen); Log.i(TAG, "Start test testDisplayEvents " + mDisplayCount + " " + cached + " " + frozen); // Launch DisplayEventActivity and start listening to display events int pid = launchTestActivity(); Loading Loading @@ -361,7 +351,6 @@ public class DisplayEventDeliveryTest extends EventDeliveryTestBase { * Create virtual displays, change their configurations and release them. The display app is * frozen and the test verifies that no events are delivered to the frozen app. */ @RequiresFlagsEnabled(Flags.FLAG_DEFER_DISPLAY_EVENTS_WHEN_FROZEN) @Test public void testDisplayEventsFrozen() { assumeTrue(isAppFreezerEnabled()); Loading @@ -372,7 +361,6 @@ public class DisplayEventDeliveryTest extends EventDeliveryTestBase { * Create virtual displays, change their configurations and release them. The display app is * cached and frozen and the test verifies that no events are delivered to the app. */ @RequiresFlagsEnabled(Flags.FLAG_DEFER_DISPLAY_EVENTS_WHEN_FROZEN) @Test public void testDisplayEventsCachedFrozen() { assumeTrue(isAppFreezerEnabled()); Loading
services/tests/displayservicetests/src/com/android/server/display/TopologyUpdateDeliveryTest.java +2 −4 Original line number Diff line number Diff line Loading @@ -222,8 +222,7 @@ public class TopologyUpdateDeliveryTest extends EventDeliveryTestBase { /** * The app is frozen and the test verifies that no updates are delivered to the frozen app. */ @RequiresFlagsEnabled({com.android.server.am.Flags.FLAG_DEFER_DISPLAY_EVENTS_WHEN_FROZEN, com.android.server.display.feature.flags.Flags.FLAG_DISPLAY_TOPOLOGY}) @RequiresFlagsEnabled(com.android.server.display.feature.flags.Flags.FLAG_DISPLAY_TOPOLOGY) @Test public void testTopologyUpdateFrozen() { assumeTrue(isAppFreezerEnabled()); Loading @@ -233,8 +232,7 @@ public class TopologyUpdateDeliveryTest extends EventDeliveryTestBase { /** * The app is cached and frozen and the test verifies that no updates are delivered to the app. */ @RequiresFlagsEnabled({com.android.server.am.Flags.FLAG_DEFER_DISPLAY_EVENTS_WHEN_FROZEN, com.android.server.display.feature.flags.Flags.FLAG_DISPLAY_TOPOLOGY}) @RequiresFlagsEnabled(com.android.server.display.feature.flags.Flags.FLAG_DISPLAY_TOPOLOGY) @Test public void testTopologyUpdateCachedFrozen() { assumeTrue(isAppFreezerEnabled()); Loading