diff --git a/Android.mk b/Android.mk
index fcd4a94efc..7805b32e8e 100644
--- a/Android.mk
+++ b/Android.mk
@@ -67,7 +67,10 @@ LOCAL_STATIC_ANDROID_LIBRARIES := Launcher3CommonDepsLib
LOCAL_SRC_FILES := \
$(call all-java-files-under, src) \
$(call all-java-files-under, src_shortcuts_overrides) \
- $(call all-java-files-under, src_ui_overrides)
+ $(call all-java-files-under, src_ui_overrides) \
+ $(call all-java-files-under, ext_tests/src)
+
+LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/ext_tests/res
LOCAL_PROGUARD_FLAG_FILES := proguard.flags
# Proguard is disable for testing. Derivarive prjects to keep proguard enabled
diff --git a/ext_tests/res/values/overrides.xml b/ext_tests/res/values/overrides.xml
new file mode 100644
index 0000000000..3f071d4219
--- /dev/null
+++ b/ext_tests/res/values/overrides.xml
@@ -0,0 +1,5 @@
+
+
+ com.android.launcher3.testing.DebugTestInformationHandler
+
+
diff --git a/ext_tests/src/com/android/launcher3/testing/DebugTestInformationHandler.java b/ext_tests/src/com/android/launcher3/testing/DebugTestInformationHandler.java
new file mode 100644
index 0000000000..b84c7aa8e8
--- /dev/null
+++ b/ext_tests/src/com/android/launcher3/testing/DebugTestInformationHandler.java
@@ -0,0 +1,141 @@
+/*
+ * Copyright (C) 2020 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.launcher3.testing;
+
+import static android.graphics.Bitmap.Config.ARGB_8888;
+
+import android.content.Context;
+import android.graphics.Bitmap;
+import android.graphics.Color;
+import android.os.Bundle;
+import android.os.Debug;
+import android.system.Os;
+import android.view.View;
+
+import androidx.annotation.Keep;
+
+import java.util.LinkedList;
+import java.util.concurrent.CountDownLatch;
+import java.util.concurrent.TimeUnit;
+
+/**
+ * Class to handle requests from tests, including debug ones.
+ */
+public class DebugTestInformationHandler extends TestInformationHandler {
+ private static LinkedList sLeaks;
+
+ public DebugTestInformationHandler(Context context) {
+ init(context);
+ }
+
+ private static void runGcAndFinalizersSync() {
+ Runtime.getRuntime().gc();
+ Runtime.getRuntime().runFinalization();
+
+ final CountDownLatch fence = new CountDownLatch(1);
+ createFinalizationObserver(fence);
+ try {
+ do {
+ Runtime.getRuntime().gc();
+ Runtime.getRuntime().runFinalization();
+ } while (!fence.await(100, TimeUnit.MILLISECONDS));
+ } catch (InterruptedException ex) {
+ throw new RuntimeException(ex);
+ }
+ }
+
+ // Create the observer in the scope of a method to minimize the chance that
+ // it remains live in a DEX/machine register at the point of the fence guard.
+ // This must be kept to avoid R8 inlining it.
+ @Keep
+ private static void createFinalizationObserver(CountDownLatch fence) {
+ new Object() {
+ @Override
+ protected void finalize() throws Throwable {
+ try {
+ fence.countDown();
+ } finally {
+ super.finalize();
+ }
+ }
+ };
+ }
+
+ @Override
+ public Bundle call(String method) {
+ final Bundle response = new Bundle();
+ switch (method) {
+ case TestProtocol.REQUEST_APP_LIST_FREEZE_FLAGS: {
+ return getLauncherUIProperty(Bundle::putInt,
+ l -> l.getAppsView().getAppsStore().getDeferUpdatesFlags());
+ }
+
+ case TestProtocol.REQUEST_ENABLE_DEBUG_TRACING:
+ TestProtocol.sDebugTracing = true;
+ return response;
+
+ case TestProtocol.REQUEST_DISABLE_DEBUG_TRACING:
+ TestProtocol.sDebugTracing = false;
+ return response;
+
+ case TestProtocol.REQUEST_PID: {
+ response.putInt(TestProtocol.TEST_INFO_RESPONSE_FIELD, Os.getpid());
+ return response;
+ }
+
+ case TestProtocol.REQUEST_TOTAL_PSS_KB: {
+ runGcAndFinalizersSync();
+ Debug.MemoryInfo mem = new Debug.MemoryInfo();
+ Debug.getMemoryInfo(mem);
+ response.putInt(TestProtocol.TEST_INFO_RESPONSE_FIELD, mem.getTotalPss());
+ return response;
+ }
+
+ case TestProtocol.REQUEST_JAVA_LEAK: {
+ if (sLeaks == null) sLeaks = new LinkedList();
+
+ // Allocate and dirty the memory.
+ final int leakSize = 1024 * 1024;
+ final byte[] bytes = new byte[leakSize];
+ for (int i = 0; i < leakSize; i += 239) {
+ bytes[i] = (byte) (i % 256);
+ }
+ sLeaks.add(bytes);
+ return response;
+ }
+
+ case TestProtocol.REQUEST_NATIVE_LEAK: {
+ if (sLeaks == null) sLeaks = new LinkedList();
+
+ // Allocate and dirty a bitmap.
+ final Bitmap bitmap = Bitmap.createBitmap(512, 512, ARGB_8888);
+ bitmap.eraseColor(Color.RED);
+ sLeaks.add(bitmap);
+ return response;
+ }
+
+ case TestProtocol.REQUEST_VIEW_LEAK: {
+ if (sLeaks == null) sLeaks = new LinkedList();
+ sLeaks.add(new View(mContext));
+ return response;
+ }
+
+ default:
+ return super.call(method);
+ }
+ }
+}
diff --git a/quickstep/recents_ui_overrides/src/com/android/quickstep/QuickstepTestInformationHandler.java b/quickstep/recents_ui_overrides/src/com/android/quickstep/QuickstepTestInformationHandler.java
index ebc83c6bad..6f4d34c8c7 100644
--- a/quickstep/recents_ui_overrides/src/com/android/quickstep/QuickstepTestInformationHandler.java
+++ b/quickstep/recents_ui_overrides/src/com/android/quickstep/QuickstepTestInformationHandler.java
@@ -4,21 +4,18 @@ import android.app.Activity;
import android.content.Context;
import android.os.Bundle;
+import com.android.launcher3.LauncherState;
import com.android.launcher3.config.FeatureFlags;
import com.android.launcher3.testing.TestInformationHandler;
import com.android.launcher3.testing.TestProtocol;
import com.android.launcher3.touch.PagedOrientationHandler;
import com.android.launcher3.uioverrides.touchcontrollers.PortraitStatesTouchController;
import com.android.quickstep.util.LayoutUtils;
-import com.android.systemui.shared.recents.model.Task;
-
-import java.util.ArrayList;
-import java.util.concurrent.CountDownLatch;
-import java.util.concurrent.TimeUnit;
public class QuickstepTestInformationHandler extends TestInformationHandler {
- private final Context mContext;
+ protected final Context mContext;
+
public QuickstepTestInformationHandler(Context context) {
mContext = context;
}
@@ -27,6 +24,15 @@ public class QuickstepTestInformationHandler extends TestInformationHandler {
public Bundle call(String method) {
final Bundle response = new Bundle();
switch (method) {
+ case TestProtocol.REQUEST_ALL_APPS_TO_OVERVIEW_SWIPE_HEIGHT: {
+ return getLauncherUIProperty(Bundle::putInt, l -> {
+ final float progress = LauncherState.OVERVIEW.getVerticalProgress(l)
+ - LauncherState.ALL_APPS.getVerticalProgress(l);
+ final float distance = l.getAllAppsController().getShiftRange() * progress;
+ return (int) distance;
+ });
+ }
+
case TestProtocol.REQUEST_HOME_TO_OVERVIEW_SWIPE_HEIGHT: {
final float swipeHeight =
LayoutUtils.getDefaultSwipeHeight(mContext, mDeviceProfile);
@@ -47,26 +53,6 @@ public class QuickstepTestInformationHandler extends TestInformationHandler {
Bundle::putInt, PortraitStatesTouchController::getHotseatTop);
}
- case TestProtocol.REQUEST_RECENT_TASKS_LIST: {
- ArrayList taskBaseIntentComponents = new ArrayList<>();
- CountDownLatch latch = new CountDownLatch(1);
- RecentsModel.INSTANCE.get(mContext).getTasks((tasks) -> {
- for (Task t : tasks) {
- taskBaseIntentComponents.add(
- t.key.baseIntent.getComponent().flattenToString());
- }
- latch.countDown();
- });
- try {
- latch.await(2, TimeUnit.SECONDS);
- } catch (InterruptedException e) {
- throw new RuntimeException(e);
- }
- response.putStringArrayList(TestProtocol.TEST_INFO_RESPONSE_FIELD,
- taskBaseIntentComponents);
- return response;
- }
-
case TestProtocol.REQUEST_OVERVIEW_ACTIONS_ENABLED: {
response.putBoolean(TestProtocol.TEST_INFO_RESPONSE_FIELD,
FeatureFlags.ENABLE_OVERVIEW_ACTIONS.get());
diff --git a/src/com/android/launcher3/testing/TestInformationHandler.java b/src/com/android/launcher3/testing/TestInformationHandler.java
index e786f07237..38b3712f6e 100644
--- a/src/com/android/launcher3/testing/TestInformationHandler.java
+++ b/src/com/android/launcher3/testing/TestInformationHandler.java
@@ -15,27 +15,17 @@
*/
package com.android.launcher3.testing;
-import static android.graphics.Bitmap.Config.ARGB_8888;
-
import static com.android.launcher3.allapps.AllAppsStore.DEFER_UPDATES_TEST;
import static com.android.launcher3.util.Executors.MAIN_EXECUTOR;
import android.annotation.TargetApi;
import android.app.Activity;
import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.Color;
import android.graphics.Insets;
import android.os.Build;
import android.os.Bundle;
-import android.os.Debug;
-import android.system.Os;
-import android.util.Log;
-import android.view.View;
import android.view.WindowInsets;
-import androidx.annotation.Keep;
-
import com.android.launcher3.DeviceProfile;
import com.android.launcher3.InvariantDeviceProfile;
import com.android.launcher3.Launcher;
@@ -44,10 +34,7 @@ import com.android.launcher3.LauncherState;
import com.android.launcher3.R;
import com.android.launcher3.util.ResourceBasedOverride;
-import java.util.LinkedList;
-import java.util.concurrent.CountDownLatch;
import java.util.concurrent.ExecutionException;
-import java.util.concurrent.TimeUnit;
import java.util.function.Function;
import java.util.function.Supplier;
@@ -65,7 +52,6 @@ public class TestInformationHandler implements ResourceBasedOverride {
protected Context mContext;
protected DeviceProfile mDeviceProfile;
protected LauncherAppState mLauncherAppState;
- private static LinkedList mLeaks;
public void init(Context context) {
mContext = context;
@@ -77,15 +63,6 @@ public class TestInformationHandler implements ResourceBasedOverride {
public Bundle call(String method) {
final Bundle response = new Bundle();
switch (method) {
- case TestProtocol.REQUEST_ALL_APPS_TO_OVERVIEW_SWIPE_HEIGHT: {
- return getLauncherUIProperty(Bundle::putInt, l -> {
- final float progress = LauncherState.OVERVIEW.getVerticalProgress(l)
- - LauncherState.ALL_APPS.getVerticalProgress(l);
- final float distance = l.getAllAppsController().getShiftRange() * progress;
- return (int) distance;
- });
- }
-
case TestProtocol.REQUEST_HOME_TO_ALL_APPS_SWIPE_HEIGHT: {
return getLauncherUIProperty(Bundle::putInt, l -> {
final float progress = LauncherState.NORMAL.getVerticalProgress(l)
@@ -99,14 +76,6 @@ public class TestInformationHandler implements ResourceBasedOverride {
return getUIProperty(Bundle::putBoolean, t -> isLauncherInitialized(), () -> true);
}
- case TestProtocol.REQUEST_ENABLE_DEBUG_TRACING:
- TestProtocol.sDebugTracing = true;
- break;
-
- case TestProtocol.REQUEST_DISABLE_DEBUG_TRACING:
- TestProtocol.sDebugTracing = false;
- break;
-
case TestProtocol.REQUEST_FREEZE_APP_LIST:
return getLauncherUIProperty(Bundle::putBoolean, l -> {
l.getAppsView().getAppsStore().enableDeferUpdates(DEFER_UPDATES_TEST);
@@ -118,11 +87,6 @@ public class TestInformationHandler implements ResourceBasedOverride {
return true;
});
- case TestProtocol.REQUEST_APP_LIST_FREEZE_FLAGS: {
- return getLauncherUIProperty(Bundle::putInt,
- l -> l.getAppsView().getAppsStore().getDeferUpdatesFlags());
- }
-
case TestProtocol.REQUEST_APPS_LIST_SCROLL_Y: {
return getLauncherUIProperty(Bundle::putInt,
l -> l.getAppsView().getActiveRecyclerView().getCurrentScrollY());
@@ -137,59 +101,19 @@ public class TestInformationHandler implements ResourceBasedOverride {
}, this::getCurrentActivity);
}
- case TestProtocol.REQUEST_PID: {
- response.putInt(TestProtocol.TEST_INFO_RESPONSE_FIELD, Os.getpid());
- break;
- }
-
- case TestProtocol.REQUEST_TOTAL_PSS_KB: {
- runGcAndFinalizersSync();
- Debug.MemoryInfo mem = new Debug.MemoryInfo();
- Debug.getMemoryInfo(mem);
- response.putInt(TestProtocol.TEST_INFO_RESPONSE_FIELD, mem.getTotalPss());
- break;
- }
-
- case TestProtocol.REQUEST_JAVA_LEAK: {
- if (mLeaks == null) mLeaks = new LinkedList();
-
- // Allocate and dirty the memory.
- final int leakSize = 1024 * 1024;
- final byte[] bytes = new byte[leakSize];
- for (int i = 0; i < leakSize; i += 239) {
- bytes[i] = (byte) (i % 256);
- }
- mLeaks.add(bytes);
- break;
- }
-
- case TestProtocol.REQUEST_NATIVE_LEAK: {
- if (mLeaks == null) mLeaks = new LinkedList();
-
- // Allocate and dirty a bitmap.
- final Bitmap bitmap = Bitmap.createBitmap(512, 512, ARGB_8888);
- bitmap.eraseColor(Color.RED);
- mLeaks.add(bitmap);
- break;
- }
-
- case TestProtocol.REQUEST_VIEW_LEAK: {
- if (mLeaks == null) mLeaks = new LinkedList();
- mLeaks.add(new View(mContext));
- break;
- }
-
case TestProtocol.REQUEST_ICON_HEIGHT: {
response.putInt(TestProtocol.TEST_INFO_RESPONSE_FIELD,
mDeviceProfile.allAppsCellHeightPx);
- break;
+ return response;
}
case TestProtocol.REQUEST_MOCK_SENSOR_ROTATION:
TestProtocol.sDisableSensorRotation = true;
- break;
+ return response;
+
+ default:
+ return null;
}
- return response;
}
protected boolean isLauncherInitialized() {
@@ -201,22 +125,6 @@ public class TestInformationHandler implements ResourceBasedOverride {
return Launcher.ACTIVITY_TRACKER.getCreatedActivity();
}
- private static void runGcAndFinalizersSync() {
- Runtime.getRuntime().gc();
- Runtime.getRuntime().runFinalization();
-
- final CountDownLatch fence = new CountDownLatch(1);
- createFinalizationObserver(fence);
- try {
- do {
- Runtime.getRuntime().gc();
- Runtime.getRuntime().runFinalization();
- } while (!fence.await(100, TimeUnit.MILLISECONDS));
- } catch (InterruptedException ex) {
- throw new RuntimeException(ex);
- }
- }
-
/**
* Returns the result by getting a Launcher property on UI thread
*/
@@ -257,21 +165,4 @@ public class TestInformationHandler implements ResourceBasedOverride {
*/
void set(Bundle b, String key, T value);
}
-
- // Create the observer in the scope of a method to minimize the chance that
- // it remains live in a DEX/machine register at the point of the fence guard.
- // This must be kept to avoid R8 inlining it.
- @Keep
- private static void createFinalizationObserver(CountDownLatch fence) {
- new Object() {
- @Override
- protected void finalize() throws Throwable {
- try {
- fence.countDown();
- } finally {
- super.finalize();
- }
- }
- };
- }
}
diff --git a/tests/src/com/android/launcher3/ui/AbstractLauncherUiTest.java b/tests/src/com/android/launcher3/ui/AbstractLauncherUiTest.java
index 7cce044105..3d39d254b1 100644
--- a/tests/src/com/android/launcher3/ui/AbstractLauncherUiTest.java
+++ b/tests/src/com/android/launcher3/ui/AbstractLauncherUiTest.java
@@ -294,7 +294,8 @@ public abstract class AbstractLauncherUiTest {
// Limits UI tests affecting tests running after them.
mLauncher.waitForLauncherInitialized();
if (mLauncherPid != 0) {
- assertEquals("Launcher crashed, pid mismatch:", mLauncherPid, mLauncher.getPid());
+ assertEquals("Launcher crashed, pid mismatch:",
+ mLauncherPid, mLauncher.getPid().intValue());
}
checkDetectedLeaks(mLauncher);
}
diff --git a/tests/tapl/com/android/launcher3/tapl/AllApps.java b/tests/tapl/com/android/launcher3/tapl/AllApps.java
index 808be6644b..b6c17df730 100644
--- a/tests/tapl/com/android/launcher3/tapl/AllApps.java
+++ b/tests/tapl/com/android/launcher3/tapl/AllApps.java
@@ -18,6 +18,7 @@ package com.android.launcher3.tapl;
import android.graphics.Point;
import android.graphics.Rect;
+import android.os.Bundle;
import android.widget.TextView;
import androidx.annotation.NonNull;
@@ -244,8 +245,8 @@ public class AllApps extends LauncherInstrumentation.VisibleContainer {
}
private void verifyNotFrozen(String message) {
- mLauncher.assertEquals(message, 0, mLauncher.getTestInfo(
- TestProtocol.REQUEST_APP_LIST_FREEZE_FLAGS).
- getInt(TestProtocol.TEST_INFO_RESPONSE_FIELD));
+ final Bundle testInfo = mLauncher.getTestInfo(TestProtocol.REQUEST_APP_LIST_FREEZE_FLAGS);
+ if (testInfo == null) return;
+ mLauncher.assertEquals(message, 0, testInfo.getInt(TestProtocol.TEST_INFO_RESPONSE_FIELD));
}
}
diff --git a/tests/tapl/com/android/launcher3/tapl/LauncherInstrumentation.java b/tests/tapl/com/android/launcher3/tapl/LauncherInstrumentation.java
index 7ddb49275c..9f4d9cea43 100644
--- a/tests/tapl/com/android/launcher3/tapl/LauncherInstrumentation.java
+++ b/tests/tapl/com/android/launcher3/tapl/LauncherInstrumentation.java
@@ -1309,8 +1309,9 @@ public final class LauncherInstrumentation {
getInt(TestProtocol.TEST_INFO_RESPONSE_FIELD);
}
- public int getPid() {
- return getTestInfo(TestProtocol.REQUEST_PID).getInt(TestProtocol.TEST_INFO_RESPONSE_FIELD);
+ public Integer getPid() {
+ final Bundle testInfo = getTestInfo(TestProtocol.REQUEST_PID);
+ return testInfo != null ? testInfo.getInt(TestProtocol.TEST_INFO_RESPONSE_FIELD) : null;
}
public void produceJavaLeak() {
@@ -1338,13 +1339,13 @@ public final class LauncherInstrumentation {
public Closable eventsCheck() {
Assert.assertTrue("Nested event checking", !sCheckingEvents);
disableSensorRotation();
- final int initialPid = getPid();
+ final Integer initialPid = getPid();
if (sEventChecker == null) sEventChecker = new LogEventChecker();
sEventChecker.start();
sCheckingEvents = true;
return () -> {
- if (initialPid != getPid()) {
+ if (initialPid != null && initialPid.intValue() != getPid()) {
if (mOnLauncherCrashed != null) mOnLauncherCrashed.run();
checkForAnomaly();
Assert.fail(