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

Commit 76a8a6cc authored by Charles Chen's avatar Charles Chen
Browse files

Fix the condition to enable registerCleaner

It should only be enabled when both track_system_ui_context_before_wms
and clean_up_window_context_with_cleaner are enabled.

Also add @DisabledOnRavenwood tag to #testSystemUiContextCleanUp to prevent it from running in Ravenwood.

Test: atest WindowContextTest ContextTest
Flag: com.android.window.flags.clean_up_window_context_with_cleaner
Bug: 339727951
Bug: 410675385
Change-Id: I9730affbc9ebaf41d326e91a219fd3ba31fc4b95
parent d478048f
Loading
Loading
Loading
Loading
+11 −5
Original line number Original line Diff line number Diff line
@@ -3431,9 +3431,7 @@ class ContextImpl extends Context {
        // if this Context is not a WindowContext. WindowContext finalization is handled in
        // if this Context is not a WindowContext. WindowContext finalization is handled in
        // WindowContext class.
        // WindowContext class.
        try {
        try {
            if (!(com.android.window.flags.Flags.cleanUpWindowContextWithCleaner()
            if (!isCleanerEnabled() && mToken instanceof WindowTokenClient && mOwnsToken) {
                    || com.android.window.flags.Flags.trackSystemUiContextBeforeWms())
                    && mToken instanceof WindowTokenClient && mOwnsToken) {
                WindowTokenClientController.getInstance()
                WindowTokenClientController.getInstance()
                        .detachIfNeeded((WindowTokenClient) mToken);
                        .detachIfNeeded((WindowTokenClient) mToken);
            }
            }
@@ -3442,6 +3440,15 @@ class ContextImpl extends Context {
        }
        }
    }
    }


    /**
     * Returns {@code true} if {@link WindowContext#registerCleaner} is enabled.
     */
    private static boolean isCleanerEnabled() {
        return com.android.window.flags.Flags.cleanUpWindowContextWithCleaner()
                // Cleaner only works on SystemUiContext or WindowContext.
                && com.android.window.flags.Flags.trackSystemUiContextBeforeWms();
    }

    @UnsupportedAppUsage
    @UnsupportedAppUsage
    static ContextImpl createSystemContext(ActivityThread mainThread) {
    static ContextImpl createSystemContext(ActivityThread mainThread) {
        LoadedApk packageInfo = new LoadedApk(mainThread);
        LoadedApk packageInfo = new LoadedApk(mainThread);
@@ -3482,8 +3489,7 @@ class ContextImpl extends Context {
        WindowTokenClientController.getInstance().attachToDisplayContent(token, displayId);
        WindowTokenClientController.getInstance().attachToDisplayContent(token, displayId);
        context.mContextType = CONTEXT_TYPE_SYSTEM_OR_SYSTEM_UI;
        context.mContextType = CONTEXT_TYPE_SYSTEM_OR_SYSTEM_UI;
        context.mOwnsToken = true;
        context.mOwnsToken = true;
        if (!com.android.window.flags.Flags.trackSystemUiContextBeforeWms()) {
        if (isCleanerEnabled()) {
            // #registerCleaner only support SystemUiContext or WindowContext.
            registerCleaner(systemUiContext);
            registerCleaner(systemUiContext);
        }
        }
        return systemUiContext;
        return systemUiContext;
+34 −0
Original line number Original line Diff line number Diff line
@@ -29,6 +29,13 @@ import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertTrue;
import static org.junit.Assert.assertTrue;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.anyInt;
import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.Mockito.doNothing;
import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.verify;


import android.app.ActivityThread;
import android.app.ActivityThread;
import android.content.res.Configuration;
import android.content.res.Configuration;
@@ -46,18 +53,22 @@ import android.platform.test.flag.junit.SetFlagsRule;
import android.platform.test.ravenwood.RavenwoodRule;
import android.platform.test.ravenwood.RavenwoodRule;
import android.view.Display;
import android.view.Display;
import android.window.WindowTokenClient;
import android.window.WindowTokenClient;
import android.window.WindowTokenClientController;


import androidx.test.core.app.ApplicationProvider;
import androidx.test.core.app.ApplicationProvider;
import androidx.test.ext.junit.runners.AndroidJUnit4;
import androidx.test.ext.junit.runners.AndroidJUnit4;
import androidx.test.filters.SmallTest;
import androidx.test.filters.SmallTest;
import androidx.test.platform.app.InstrumentationRegistry;
import androidx.test.platform.app.InstrumentationRegistry;


import com.android.internal.util.GcUtils;
import com.android.window.flags.Flags;
import com.android.window.flags.Flags;


import org.junit.Rule;
import org.junit.Rule;
import org.junit.Test;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runner.RunWith;


import java.lang.ref.WeakReference;

/**
/**
 *  Build/Install/Run:
 *  Build/Install/Run:
 *   atest FrameworksCoreTests:ContextTest
 *   atest FrameworksCoreTests:ContextTest
@@ -331,4 +342,27 @@ public class ContextTest {
        assertWithMessage("ComponentCallbacks should delegate to SystemUiContext "
        assertWithMessage("ComponentCallbacks should delegate to SystemUiContext "
                + "if the flag is enabled.").that(callbacks.mConfiguration).isEqualTo(config);
                + "if the flag is enabled.").that(callbacks.mConfiguration).isEqualTo(config);
    }
    }

    @Test
    @DisabledOnRavenwood(blockedBy = Context.class)
    public void testSystemUiContextCleanUp() {
        final WindowTokenClientController origController =
                WindowTokenClientController.getInstance();
        final WindowTokenClientController mockController = mock(WindowTokenClientController.class);
        doReturn(true).when(mockController).attachToDisplayContent(any(), anyInt());
        doNothing().when(mockController).detachIfNeeded(any());
        WindowTokenClientController.overrideForTesting(mockController);

        WeakReference<Context> windowContextRef = new WeakReference<>(
                ActivityThread.currentActivityThread()
                        .createSystemUiContextForTesting(DEFAULT_DISPLAY));
        final WindowTokenClient token =
                (WindowTokenClient) windowContextRef.get().getWindowContextToken();

        GcUtils.runGcAndFinalizersSync();

        verify(mockController).detachIfNeeded(eq(token));

        WindowTokenClientController.overrideForTesting(origController);
    }
}
}
+12 −10
Original line number Original line Diff line number Diff line
@@ -35,6 +35,8 @@ import static org.junit.Assert.fail;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.anyInt;
import static org.mockito.ArgumentMatchers.anyInt;
import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.Mockito.doNothing;
import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.verify;
@@ -82,6 +84,7 @@ import org.junit.Rule;
import org.junit.Test;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runner.RunWith;


import java.lang.ref.WeakReference;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.TimeUnit;


@@ -527,20 +530,19 @@ public class WindowContextTest {


    @Test
    @Test
    public void testWindowContextCleanup() {
    public void testWindowContextCleanup() {
        final WindowContext windowContext = createWindowContext();
        final WindowTokenClientController mockController = mock(WindowTokenClientController.class);
        doReturn(true).when(mockController).attachToDisplayArea(
                any(), anyInt(), anyInt(), any());
        doNothing().when(mockController).detachIfNeeded(any());
        WindowTokenClientController.overrideForTesting(mockController);


        windowContext.getSystemService(WindowManager.class).getCurrentWindowMetrics();
        WeakReference<WindowContext> windowContextRef = new WeakReference<>(createWindowContext());
        final WindowTokenClient token =
                (WindowTokenClient) windowContextRef.get().getWindowContextToken();


        GcUtils.runGcAndFinalizersSync();
        GcUtils.runGcAndFinalizersSync();


        PollingCheck.waitFor(() -> {
        verify(mockController).detachIfNeeded(eq(token));
            try {
                return !mWms.isWindowToken(windowContext.getWindowContextToken());
            } catch (RemoteException e) {
                fail("Fail due to " + e);
            }
            return false;
        });
    }
    }


    private static class ConfigurationListener implements ComponentCallbacks {
    private static class ConfigurationListener implements ComponentCallbacks {