Merge "Tests for set/get organization color"
diff --git a/CtsTestCaseList.mk b/CtsTestCaseList.mk
index c5dc051..39a58ad 100644
--- a/CtsTestCaseList.mk
+++ b/CtsTestCaseList.mk
@@ -182,6 +182,12 @@
CtsNetTestCases \
CtsNetTestCasesLegacyApi22 \
CtsNetTestCasesLegacyPermission22 \
+ CtsNetSecConfigAttributeTestCases \
+ CtsNetSecConfigBasicDebugDisabledTestCases \
+ CtsNetSecConfigBasicDebugEnabledTestCases \
+ CtsNetSecConfigBasicDomainConfigTestCases \
+ CtsNetSecConfigInvalidPinTestCases \
+ CtsNetSecConfigNestedDomainConfigTestCases \
CtsOpenGLTestCases \
CtsOpenGlPerfTestCases \
CtsOpenGlPerf2TestCases \
diff --git a/apps/CtsVerifier/res/values-television/strings.xml b/apps/CtsVerifier/res/values-television/strings.xml
index 1042fa8..50f7628 100644
--- a/apps/CtsVerifier/res/values-television/strings.xml
+++ b/apps/CtsVerifier/res/values-television/strings.xml
@@ -18,5 +18,6 @@
<string-array name="disabled_tests">
<item>com.android.cts.verifier.notifications.NotificationAttentionManagementVerifierActivity</item>
<item>com.android.cts.verifier.notifications.NotificationListenerVerifierActivity</item>
+ <item>com.android.cts.verifier.widget.WidgetTestActivity</item>
</string-array>
-</resources>
\ No newline at end of file
+</resources>
diff --git a/common/device-side/util/src/com/android/compatibility/common/util/DynamicConfigDeviceSide.java b/common/device-side/util/src/com/android/compatibility/common/util/DynamicConfigDeviceSide.java
index 303efec..b50b4f7 100644
--- a/common/device-side/util/src/com/android/compatibility/common/util/DynamicConfigDeviceSide.java
+++ b/common/device-side/util/src/com/android/compatibility/common/util/DynamicConfigDeviceSide.java
@@ -28,6 +28,7 @@
* Load dynamic config for device side test cases
*/
public class DynamicConfigDeviceSide extends DynamicConfig {
+
private static String LOG_TAG = DynamicConfigDeviceSide.class.getSimpleName();
public DynamicConfigDeviceSide(String moduleName) throws XmlPullParserException, IOException {
@@ -35,6 +36,6 @@
throw new IOException("External storage is not mounted");
}
File configFile = getConfigFile(new File(CONFIG_FOLDER_ON_DEVICE), moduleName);
- initConfigFromXml(configFile);
+ initializeConfig(configFile);
}
}
diff --git a/common/host-side/tradefed/src/com/android/compatibility/common/tradefed/targetprep/DynamicConfigPusher.java b/common/host-side/tradefed/src/com/android/compatibility/common/tradefed/targetprep/DynamicConfigPusher.java
index 8c455cd..fabc4e1 100644
--- a/common/host-side/tradefed/src/com/android/compatibility/common/tradefed/targetprep/DynamicConfigPusher.java
+++ b/common/host-side/tradefed/src/com/android/compatibility/common/tradefed/targetprep/DynamicConfigPusher.java
@@ -88,11 +88,11 @@
}
String apfeConfigInJson = null;
- String OriginUrl = buildHelper.getDynamicConfigUrl();
+ String originUrl = buildHelper.getDynamicConfigUrl();
- if (OriginUrl != null) {
+ if (originUrl != null) {
try {
- String requestUrl = OriginUrl
+ String requestUrl = originUrl
.replace("{module-name}", mModuleName).replace("{version-name}", mVersion);
java.net.URL request = new URL(requestUrl);
apfeConfigInJson = StreamUtil.getStringFromStream(request.openStream());
@@ -128,7 +128,9 @@
case HOST:
File storageDir = new File(DynamicConfig.CONFIG_FOLDER_ON_HOST);
- if (!storageDir.exists()) storageDir.mkdir();
+ if (!storageDir.exists()) {
+ storageDir.mkdir();
+ }
File hostDest = new File(DynamicConfig.CONFIG_FOLDER_ON_HOST + src.getName());
try {
FileUtil.copyFile(src, hostDest);
@@ -159,4 +161,4 @@
new File(mFilePushed).delete();
}
}
-}
\ No newline at end of file
+}
diff --git a/common/host-side/util/src/com/android/compatibility/common/util/DynamicConfigHandler.java b/common/host-side/util/src/com/android/compatibility/common/util/DynamicConfigHandler.java
index b42faca..bedcecd 100644
--- a/common/host-side/util/src/com/android/compatibility/common/util/DynamicConfigHandler.java
+++ b/common/host-side/util/src/com/android/compatibility/common/util/DynamicConfigHandler.java
@@ -37,90 +37,66 @@
private static final String LOG_TAG = DynamicConfigHandler.class.getSimpleName();
- // xml constant
- private static final String NS = null; //representing null namespace
+ private static final String NS = null; //xml constant representing null namespace
private static final String ENCODING = "UTF-8";
- public static File getMergedDynamicConfigFile(File localConfigFile, String apfeConfigJson,
+ public static File getMergedDynamicConfigFile(File localConfigFile, String apbsConfigJson,
String moduleName) throws IOException, XmlPullParserException, JSONException {
- DynamicConfig.Params localConfig = DynamicConfig.genParamsFromFile(localConfigFile);
- DynamicConfig.Params apfeOverride = parseJsonToParam(apfeConfigJson);
-
- localConfig.mDynamicParams.putAll(apfeOverride.mDynamicParams);
- localConfig.mDynamicArrayParams.putAll(apfeOverride.mDynamicArrayParams);
-
- File mergedConfigFile = storeMergedConfigFile(localConfig, moduleName);
- return mergedConfigFile;
+ Map<String, List<String>> localConfig = DynamicConfig.createConfigMap(localConfigFile);
+ Map<String, List<String>> apbsConfig = parseJsonToConfigMap(apbsConfigJson);
+ localConfig.putAll(apbsConfig);
+ return storeMergedConfigFile(localConfig, moduleName);
}
- private static DynamicConfig.Params parseJsonToParam(String apfeConfigJson)
+ private static Map<String, List<String>> parseJsonToConfigMap(String apbsConfigJson)
throws JSONException {
- if (apfeConfigJson == null) return new DynamicConfig.Params();
- Map<String, String> configMap = new HashMap<>();
- Map<String, List<String>> configListMap = new HashMap<>();
-
- JSONObject rootObj = new JSONObject(new JSONTokener(apfeConfigJson));
- if (rootObj.has("config")) {
- JSONArray configArr = rootObj.getJSONArray("config");
- for (int i = 0; i < configArr.length(); i++) {
- JSONObject config = configArr.getJSONObject(i);
- configMap.put(config.getString("key"), config.getString("value"));
- }
- }
- if (rootObj.has("configList")) {
- JSONArray configListArr = rootObj.getJSONArray("configList");
- for (int i = 0; i < configListArr.length(); i++) {
- JSONObject configList = configListArr.getJSONObject(i);
- String key = configList.getString("key");
- List<String> values = new ArrayList<>();
- JSONArray configListValuesArr = configList.getJSONArray("value");
- for (int j = 0; j < configListValuesArr.length(); j++) {
- values.add(configListValuesArr.getString(j));
- }
- configListMap.put(key, values);
- }
+ Map<String, List<String>> configMap = new HashMap<String, List<String>>();
+ if (apbsConfigJson == null) {
+ return configMap;
}
- DynamicConfig.Params param = new DynamicConfig.Params();
- param.mDynamicParams = configMap;
- param.mDynamicArrayParams = configListMap;
- return param;
+ JSONObject rootObj = new JSONObject(new JSONTokener(apbsConfigJson));
+ JSONArray configEntries = rootObj.getJSONArray("dynamicConfigEntries");
+ for (int i = 0; i < configEntries.length(); i++) {
+ JSONObject configEntry = configEntries.getJSONObject(i);
+ String key = configEntry.getString("configAttribute");
+ JSONArray configValues = configEntry.getJSONArray("configValues");
+ List<String> values = new ArrayList<>();
+ for (int j = 0; j < configValues.length(); j++) {
+ values.add(configValues.getString(j));
+ }
+ configMap.put(key, values);
+ }
+ return configMap;
}
- private static File storeMergedConfigFile(DynamicConfig.Params p, String moduleName)
- throws XmlPullParserException, IOException {
- XmlSerializer serializer = XmlPullParserFactory.newInstance().newSerializer();
+ private static File storeMergedConfigFile(Map<String, List<String>> configMap,
+ String moduleName) throws XmlPullParserException, IOException {
- File parentFolder = new File(DynamicConfig.CONFIG_FOLDER_ON_HOST);
- if (!parentFolder.exists()) parentFolder.mkdir();
File folder = new File(DynamicConfig.MERGED_CONFIG_FILE_FOLDER);
- if (!folder.exists()) folder.mkdir();
- File mergedConfigFile = new File(folder, moduleName+".dynamic");
+ folder.mkdirs();
+
+ File mergedConfigFile = new File(folder, moduleName + ".dynamic");
OutputStream stream = new FileOutputStream(mergedConfigFile);
+ XmlSerializer serializer = XmlPullParserFactory.newInstance().newSerializer();
serializer.setOutput(stream, ENCODING);
serializer.setFeature("http://xmlpull.org/v1/doc/features.html#indent-output", true);
serializer.startDocument(ENCODING, false);
- serializer.startTag(NS, DynamicConfig.DYNAMIC_CONFIG_TAG);
- for (String key : p.mDynamicParams.keySet()) {
- serializer.startTag(NS, DynamicConfig.CONFIG_TAG);
+ serializer.startTag(NS, DynamicConfig.CONFIG_TAG);
+ for (String key : configMap.keySet()) {
+ serializer.startTag(NS, DynamicConfig.ENTRY_TAG);
serializer.attribute(NS, DynamicConfig.KEY_ATTR, key);
- serializer.text(p.mDynamicParams.get(key));
- serializer.endTag(NS, DynamicConfig.CONFIG_TAG);
- }
- for (String key : p.mDynamicArrayParams.keySet()) {
- serializer.startTag(NS, DynamicConfig.CONFIG_LIST_TAG);
- serializer.attribute(NS, DynamicConfig.KEY_ATTR, key);
- for (String item: p.mDynamicArrayParams.get(key)) {
- serializer.startTag(NS, DynamicConfig.ITEM_TAG);
- serializer.text(item);
- serializer.endTag(NS, DynamicConfig.ITEM_TAG);
+ for (String value : configMap.get(key)) {
+ serializer.startTag(NS, DynamicConfig.VALUE_TAG);
+ serializer.text(value);
+ serializer.endTag(NS, DynamicConfig.VALUE_TAG);
}
- serializer.endTag(NS, DynamicConfig.CONFIG_LIST_TAG);
+ serializer.endTag(NS, DynamicConfig.ENTRY_TAG);
}
- serializer.endTag(NS, DynamicConfig.DYNAMIC_CONFIG_TAG);
+ serializer.endTag(NS, DynamicConfig.CONFIG_TAG);
serializer.endDocument();
return mergedConfigFile;
}
diff --git a/common/host-side/util/src/com/android/compatibility/common/util/DynamicConfigHostSide.java b/common/host-side/util/src/com/android/compatibility/common/util/DynamicConfigHostSide.java
index ac69034..3e94d36 100644
--- a/common/host-side/util/src/com/android/compatibility/common/util/DynamicConfigHostSide.java
+++ b/common/host-side/util/src/com/android/compatibility/common/util/DynamicConfigHostSide.java
@@ -25,10 +25,11 @@
* Load dynamic config for device side test cases
*/
public class DynamicConfigHostSide extends DynamicConfig {
+
private static String LOG_TAG = DynamicConfigHostSide.class.getSimpleName();
public DynamicConfigHostSide(String moduleName) throws IOException, XmlPullParserException {
File configFile = getConfigFile(new File(CONFIG_FOLDER_ON_HOST), moduleName);
- initConfigFromXml(configFile);
+ initializeConfig(configFile);
}
}
diff --git a/common/util/src/com/android/compatibility/common/util/DynamicConfig.java b/common/util/src/com/android/compatibility/common/util/DynamicConfig.java
index a0b1d5e..a72216d 100644
--- a/common/util/src/com/android/compatibility/common/util/DynamicConfig.java
+++ b/common/util/src/com/android/compatibility/common/util/DynamicConfig.java
@@ -34,14 +34,14 @@
* Load dynamic config for test cases
*/
public class DynamicConfig {
+
public final static String MODULE_NAME = "module-name";
//XML constant
public static final String NS = null;
- public static final String DYNAMIC_CONFIG_TAG = "DynamicConfig";
- public static final String CONFIG_TAG = "Config";
- public static final String CONFIG_LIST_TAG = "ConfigList";
- public static final String ITEM_TAG = "Item";
+ public static final String CONFIG_TAG = "dynamicConfig";
+ public static final String ENTRY_TAG = "entry";
+ public static final String VALUE_TAG = "value";
public static final String KEY_ATTR = "key";
public final static String CONFIG_FOLDER_ON_DEVICE = "/sdcard/dynamic-config-files/";
@@ -50,19 +50,18 @@
public final static String MERGED_CONFIG_FILE_FOLDER =
System.getProperty("java.io.tmpdir") + "/dynamic-config-files/merged";
+ protected Map<String, List<String>> mDynamicConfigMap = new HashMap<String, List<String>>();
- protected Params params;
-
- protected void initConfigFromXml(File file) throws XmlPullParserException, IOException {
- params = genParamsFromFile(file);
+ protected void initializeConfig(File file) throws XmlPullParserException, IOException {
+ mDynamicConfigMap = createConfigMap(file);
}
- public String getConfig(String key) {
- return params.mDynamicParams.get(key);
+ public String getValue(String key) {
+ return mDynamicConfigMap.get(key).get(0);
}
- public List<String> getConfigList(String key) {
- return params.mDynamicArrayParams.get(key);
+ public List<String> getValues(String key) {
+ return mDynamicConfigMap.get(key);
}
public static File getConfigFile(File configFolder, String moduleName)
@@ -74,44 +73,31 @@
return config;
}
- public static class Params {
- public Map<String, String> mDynamicParams = new HashMap<>();
- public Map<String, List<String>> mDynamicArrayParams = new HashMap<>();
- }
+ public static Map<String, List<String>> createConfigMap(File file)
+ throws XmlPullParserException, IOException {
- public static Params genParamsFromFile(File file) throws XmlPullParserException, IOException {
- Params param = new Params();
-
+ Map<String, List<String>> dynamicConfigMap = new HashMap<String, List<String>>();
XmlPullParser parser = XmlPullParserFactory.newInstance().newPullParser();
parser.setInput(new InputStreamReader(new FileInputStream(file)));
-
parser.nextTag();
- parser.require(XmlPullParser.START_TAG, NS, DYNAMIC_CONFIG_TAG);
+ parser.require(XmlPullParser.START_TAG, NS, CONFIG_TAG);
while (parser.nextTag() == XmlPullParser.START_TAG) {
- if (parser.getName().equals(CONFIG_TAG)) {
- String key = parser.getAttributeValue(NS, KEY_ATTR);
- String value = parser.nextText();
- parser.require(XmlPullParser.END_TAG, NS, CONFIG_TAG);
- if (key != null && !key.isEmpty()) {
- param.mDynamicParams.put(key, value);
- }
- } else {
- List<String> arrayValue = new ArrayList<>();
- parser.require(XmlPullParser.START_TAG, NS, CONFIG_LIST_TAG);
- String key = parser.getAttributeValue(NS, KEY_ATTR);
- while (parser.nextTag() == XmlPullParser.START_TAG) {
- parser.require(XmlPullParser.START_TAG, NS, ITEM_TAG);
- arrayValue.add(parser.nextText());
- parser.require(XmlPullParser.END_TAG, NS, ITEM_TAG);
- }
- parser.require(XmlPullParser.END_TAG, NS, CONFIG_LIST_TAG);
- if (key != null && !key.isEmpty()) {
- param.mDynamicArrayParams.put(key, arrayValue);
- }
+ parser.require(XmlPullParser.START_TAG, NS, ENTRY_TAG);
+ String key = parser.getAttributeValue(NS, KEY_ATTR);
+ List<String> valueList = new ArrayList<String>();
+ while (parser.nextTag() == XmlPullParser.START_TAG) {
+ parser.require(XmlPullParser.START_TAG, NS, VALUE_TAG);
+ valueList.add(parser.nextText());
+ parser.require(XmlPullParser.END_TAG, NS, VALUE_TAG);
+ }
+ parser.require(XmlPullParser.END_TAG, NS, ENTRY_TAG);
+ if (key != null && !key.isEmpty() && !valueList.isEmpty()) {
+ dynamicConfigMap.put(key, valueList);
}
}
- parser.require(XmlPullParser.END_TAG, NS, DYNAMIC_CONFIG_TAG);
- return param;
+
+ parser.require(XmlPullParser.END_TAG, NS, CONFIG_TAG);
+ return dynamicConfigMap;
}
}
diff --git a/common/util/tests/src/com/android/compatibility/common/util/DynamicConfigTest.java b/common/util/tests/src/com/android/compatibility/common/util/DynamicConfigTest.java
index 6d6ba2d..cf1892a 100644
--- a/common/util/tests/src/com/android/compatibility/common/util/DynamicConfigTest.java
+++ b/common/util/tests/src/com/android/compatibility/common/util/DynamicConfigTest.java
@@ -30,56 +30,64 @@
public class DynamicConfigTest extends TestCase {
private static final String correctConfig =
"<?xml version=\"1.0\" encoding=\"utf-8\"?>\n" +
- "<DynamicConfig>\n" +
- " <Config key=\"test-config-1\">test config 1</Config>\n" +
- " <Config key=\"test-config-2\">testconfig2</Config>\n" +
- " <ConfigList key=\"config-list\">\n" +
- " <Item>config0</Item>\n" +
- " <Item>config1</Item>\n" +
- " <Item>config2</Item>\n" +
- " <Item>config3</Item>\n" +
- " <Item>config4</Item>\n" +
- " </ConfigList>\n" +
- " <ConfigList key=\"config-list-2\">\n" +
- " <Item>A</Item>\n" +
- " <Item>B</Item>\n" +
- " <Item>C</Item>\n" +
- " <Item>D</Item>\n" +
- " <Item>E</Item>\n" +
- " </ConfigList>\n" +
- "</DynamicConfig>\n";
+ "<dynamicConfig>\n" +
+ " <entry key=\"test-config-1\">\n" +
+ " <value>test config 1</value>\n" +
+ " </entry>\n" +
+ " <entry key=\"test-config-2\">\n" +
+ " <value>testconfig2</value>\n" +
+ " </entry>\n" +
+ " <entry key=\"config-list\">\n" +
+ " <value>config0</value>\n" +
+ " <value>config1</value>\n" +
+ " <value>config2</value>\n" +
+ " <value>config3</value>\n" +
+ " <value>config4</value>\n" +
+ " </entry>\n" +
+ " <entry key=\"config-list-2\">\n" +
+ " <value>A</value>\n" +
+ " <value>B</value>\n" +
+ " <value>C</value>\n" +
+ " <value>D</value>\n" +
+ " <value>E</value>\n" +
+ " </entry>\n" +
+ "</dynamicConfig>\n";
private static final String configWrongNodeName =
"<?xml version=\"1.0\" encoding=\"utf-8\"?>\n" +
- "<DynamicCsonfig>\n" + //The node name DynamicConfig is intentionally mistyped
- " <Config key=\"test-config-1\">test config 1</Config>\n" +
- " <Config key=\"test-config-2\">testconfig2</Config>\n" +
- " <ConfigList key=\"config-list\">\n" +
- " <Item>Nevermore</Item>\n" +
- " <Item>Puck</Item>\n" +
- " <Item>Zeus</Item>\n" +
- " <Item>Earth Shaker</Item>\n" +
- " <Item>Vengeful Spirit</Item>\n" +
- " </ConfigList>\n" +
- " <ConfigList key=\"config-list-2\">\n" +
- " <Item>A</Item>\n" +
- " <Item>B</Item>\n" +
- " <Item>C</Item>\n" +
- " <Item>D</Item>\n" +
- " <Item>E</Item>\n" +
- " </ConfigList>\n" +
- "</DynamicConfig>\n";
+ "<dynamicCsonfig>\n" + //The node name dynamicConfig is intentionally mistyped
+ " <entry key=\"test-config-1\">\n" +
+ " <value>test config 1</value>\n" +
+ " </entry>\n" +
+ " <entry key=\"test-config-2\">\n" +
+ " <value>testconfig2</value>\n" +
+ " </entry>\n" +
+ " <entry key=\"config-list\">\n" +
+ " <value>Nevermore</value>\n" +
+ " <value>Puck</value>\n" +
+ " <value>Zeus</value>\n" +
+ " <value>Earth Shaker</value>\n" +
+ " <value>Vengeful Spirit</value>\n" +
+ " </entry>\n" +
+ " <entry key=\"config-list-2\">\n" +
+ " <value>A</value>\n" +
+ " <value>B</value>\n" +
+ " <value>C</value>\n" +
+ " <value>D</value>\n" +
+ " <value>E</value>\n" +
+ " </entry>\n" +
+ "</dynamicConfig>\n";
public void testCorrectConfig() throws Exception {
DynamicConfig config = new DynamicConfig();
File file = createFileFromStr(correctConfig);
- config.initConfigFromXml(file);
+ config.initializeConfig(file);
- assertEquals("Wrong Config", config.getConfig("test-config-1"), "test config 1");
- assertEquals("Wrong Config", config.getConfig("test-config-2"), "testconfig2");
- assertEquals("Wrong Config List", config.getConfigList("config-list").get(0), "config0");
- assertEquals("Wrong Config List", config.getConfigList("config-list").get(2), "config2");
- assertEquals("Wrong Config List", config.getConfigList("config-list-2").get(2), "C");
+ assertEquals("Wrong Config", config.getValue("test-config-1"), "test config 1");
+ assertEquals("Wrong Config", config.getValue("test-config-2"), "testconfig2");
+ assertEquals("Wrong Config List", config.getValues("config-list").get(0), "config0");
+ assertEquals("Wrong Config List", config.getValues("config-list").get(2), "config2");
+ assertEquals("Wrong Config List", config.getValues("config-list-2").get(2), "C");
}
public void testConfigWithWrongNodeName() throws Exception {
@@ -87,7 +95,7 @@
File file = createFileFromStr(configWrongNodeName);
try {
- config.initConfigFromXml(file);
+ config.initializeConfig(file);
fail("Cannot detect error when config file has wrong node name");
} catch (XmlPullParserException e) {
//expected
diff --git a/tests/accessibility/src/android/view/accessibility/cts/AccessibilityNodeInfoTest.java b/tests/accessibility/src/android/view/accessibility/cts/AccessibilityNodeInfoTest.java
index 30847a5..6b28541 100644
--- a/tests/accessibility/src/android/view/accessibility/cts/AccessibilityNodeInfoTest.java
+++ b/tests/accessibility/src/android/view/accessibility/cts/AccessibilityNodeInfoTest.java
@@ -35,7 +35,7 @@
public class AccessibilityNodeInfoTest extends AndroidTestCase {
/** The number of properties of the {@link AccessibilityNodeInfo} class. */
- private static final int NON_STATIC_FIELD_COUNT = 30;
+ private static final int NON_STATIC_FIELD_COUNT = 31;
@SmallTest
public void testMarshaling() throws Exception {
@@ -198,6 +198,7 @@
info.setLabeledBy(new View(getContext()));
info.setLabelFor(new View(getContext()));
info.setViewIdResourceName("foo.bar:id/baz");
+ info.setDrawingOrder(5);
}
/**
@@ -260,6 +261,8 @@
receivedInfo.getMovementGranularities());
assertEquals("viewId has incorrect value", expectedInfo.getViewIdResourceName(),
receivedInfo.getViewIdResourceName());
+ assertEquals("drawing order has incorrect value", expectedInfo.getDrawingOrder(),
+ receivedInfo.getDrawingOrder());
}
/**
@@ -293,5 +296,6 @@
assertSame("movementGranularities not properly recycled", 0,
info.getMovementGranularities());
assertNull("viewId not properly recycled", info.getViewIdResourceName());
+ assertEquals(0, info.getDrawingOrder());
}
}
diff --git a/tests/accessibilityservice/src/android/accessibilityservice/cts/AccessibilityViewTreeReportingTest.java b/tests/accessibilityservice/src/android/accessibilityservice/cts/AccessibilityViewTreeReportingTest.java
index 04a9d9d..2a35e93 100644
--- a/tests/accessibilityservice/src/android/accessibilityservice/cts/AccessibilityViewTreeReportingTest.java
+++ b/tests/accessibilityservice/src/android/accessibilityservice/cts/AccessibilityViewTreeReportingTest.java
@@ -14,10 +14,18 @@
package android.accessibilityservice.cts;
+import android.accessibilityservice.AccessibilityServiceInfo;
+import android.app.UiAutomation;
+import android.content.Context;
import android.test.suitebuilder.annotation.MediumTest;
+import android.view.View;
import android.view.accessibility.AccessibilityNodeInfo;
import android.accessibilityservice.cts.R;
+import android.widget.LinearLayout;
+import android.widget.TextView;
+
+import java.util.ArrayList;
/**
* Test cases for testing the accessibility focus APIs exposed to accessibility
@@ -33,88 +41,230 @@
@MediumTest
public void testDescendantsOfNotImportantViewReportedInOrder1() throws Exception {
- AccessibilityNodeInfo firstFrameLayout = getInstrumentation().getUiAutomation()
- .getRootInActiveWindow().findAccessibilityNodeInfosByText(
- getString(R.string.firstFrameLayout)).get(0);
+ UiAutomation uiAutomation = getUiAutomation(false);
+ AccessibilityNodeInfo firstFrameLayout =
+ getNodeByText(uiAutomation, R.string.firstFrameLayout);
assertNotNull(firstFrameLayout);
assertSame(3, firstFrameLayout.getChildCount());
// Check if the first child is the right one.
- AccessibilityNodeInfo firstTextView = getInstrumentation().getUiAutomation()
- .getRootInActiveWindow().findAccessibilityNodeInfosByText(getString(
- R.string.firstTextView)).get(0);
+ AccessibilityNodeInfo firstTextView = getNodeByText(uiAutomation, R.string.firstTextView);
assertEquals(firstTextView, firstFrameLayout.getChild(0));
// Check if the second child is the right one.
- AccessibilityNodeInfo firstEditText = getInstrumentation().getUiAutomation()
- .getRootInActiveWindow().findAccessibilityNodeInfosByText(getString(
- R.string.firstEditText)).get(0);
+ AccessibilityNodeInfo firstEditText = getNodeByText(uiAutomation, R.string.firstEditText);
assertEquals(firstEditText, firstFrameLayout.getChild(1));
// Check if the third child is the right one.
- AccessibilityNodeInfo firstButton = getInstrumentation().getUiAutomation()
- .getRootInActiveWindow().findAccessibilityNodeInfosByText(
- getString(R.string.firstButton)).get(0);
+ AccessibilityNodeInfo firstButton = getNodeByText(uiAutomation, R.string.firstButton);
assertEquals(firstButton, firstFrameLayout.getChild(2));
}
@MediumTest
public void testDescendantsOfNotImportantViewReportedInOrder2() throws Exception {
- AccessibilityNodeInfo secondFrameLayout = getInstrumentation().getUiAutomation()
- .getRootInActiveWindow().findAccessibilityNodeInfosByText(
- getString(R.string.secondFrameLayout)).get(0);
+ UiAutomation uiAutomation = getUiAutomation(false);
+ AccessibilityNodeInfo secondFrameLayout =
+ getNodeByText(uiAutomation, R.string.secondFrameLayout);
assertNotNull(secondFrameLayout);
assertSame(3, secondFrameLayout.getChildCount());
// Check if the first child is the right one.
- AccessibilityNodeInfo secondTextView = getInstrumentation().getUiAutomation()
- .getRootInActiveWindow().findAccessibilityNodeInfosByText(
- getString(R.string.secondTextView)).get(0);
+ AccessibilityNodeInfo secondTextView = getNodeByText(uiAutomation, R.string.secondTextView);
assertEquals(secondTextView, secondFrameLayout.getChild(0));
// Check if the second child is the right one.
- AccessibilityNodeInfo secondEditText = getInstrumentation().getUiAutomation()
- .getRootInActiveWindow().findAccessibilityNodeInfosByText(
- getString(R.string.secondEditText)).get(0);
+ AccessibilityNodeInfo secondEditText = getNodeByText(uiAutomation, R.string.secondEditText);
assertEquals(secondEditText, secondFrameLayout.getChild(1));
// Check if the third child is the right one.
- AccessibilityNodeInfo secondButton = getInstrumentation().getUiAutomation()
- .getRootInActiveWindow().findAccessibilityNodeInfosByText(
- getString(R.string.secondButton)).get(0);
+ AccessibilityNodeInfo secondButton = getNodeByText(uiAutomation, R.string.secondButton);
assertEquals(secondButton, secondFrameLayout.getChild(2));
}
@MediumTest
public void testDescendantsOfNotImportantViewReportedInOrder3() throws Exception {
- AccessibilityNodeInfo rootLinearLayout = getInstrumentation().getUiAutomation()
- .getRootInActiveWindow().findAccessibilityNodeInfosByText(
- getString(R.string.rootLinearLayout)).get(0);
+ UiAutomation uiAutomation = getUiAutomation(false);
+ AccessibilityNodeInfo rootLinearLayout =
+ getNodeByText(uiAutomation, R.string.rootLinearLayout);
assertNotNull(rootLinearLayout);
assertSame(4, rootLinearLayout.getChildCount());
// Check if the first child is the right one.
- AccessibilityNodeInfo firstFrameLayout = getInstrumentation().getUiAutomation()
- .getRootInActiveWindow().findAccessibilityNodeInfosByText(
- getString(R.string.firstFrameLayout)).get(0);
+ AccessibilityNodeInfo firstFrameLayout =
+ getNodeByText(uiAutomation, R.string.firstFrameLayout);
assertEquals(firstFrameLayout, rootLinearLayout.getChild(0));
// Check if the second child is the right one.
- AccessibilityNodeInfo secondTextView = getInstrumentation().getUiAutomation()
- .getRootInActiveWindow().findAccessibilityNodeInfosByText(
- getString(R.string.secondTextView)).get(0);
+ AccessibilityNodeInfo secondTextView = getNodeByText(uiAutomation, R.string.secondTextView);
assertEquals(secondTextView, rootLinearLayout.getChild(1));
// Check if the third child is the right one.
- AccessibilityNodeInfo secondEditText = getInstrumentation().getUiAutomation()
- .getRootInActiveWindow().findAccessibilityNodeInfosByText(
- getString(R.string.secondEditText)).get(0);
+ AccessibilityNodeInfo secondEditText = getNodeByText(uiAutomation, R.string.secondEditText);
assertEquals(secondEditText, rootLinearLayout.getChild(2));
// Check if the fourth child is the right one.
- AccessibilityNodeInfo secondButton = getInstrumentation().getUiAutomation()
- .getRootInActiveWindow().findAccessibilityNodeInfosByText(
- getString(R.string.secondButton)).get(0);
+ AccessibilityNodeInfo secondButton = getNodeByText(uiAutomation, R.string.secondButton);
assertEquals(secondButton, rootLinearLayout.getChild(3));
}
+
+ @MediumTest
+ public void testDrawingOrderInImportantParentFollowsXmlOrder() throws Exception {
+ getInstrumentation().runOnMainSync(new Runnable() {
+ @Override
+ public void run() {
+ getActivity().findViewById(R.id.firstLinearLayout)
+ .setImportantForAccessibility(View.IMPORTANT_FOR_ACCESSIBILITY_YES);
+ }
+ });
+
+ UiAutomation uiAutomation = getUiAutomation(false);
+ AccessibilityNodeInfo firstTextView = getNodeByText(uiAutomation, R.string.firstTextView);
+ AccessibilityNodeInfo firstEditText = getNodeByText(uiAutomation, R.string.firstEditText);
+ AccessibilityNodeInfo firstButton = getNodeByText(uiAutomation, R.string.firstButton);
+
+ // Drawing order is: firstTextView, firstEditText, firstButton
+ assertTrue(firstTextView.getDrawingOrder() < firstEditText.getDrawingOrder());
+ assertTrue(firstEditText.getDrawingOrder() < firstButton.getDrawingOrder());
+
+ // Confirm that obtaining copies doesn't change our results
+ AccessibilityNodeInfo copyOfFirstEditText = AccessibilityNodeInfo.obtain(firstEditText);
+ assertTrue(firstTextView.getDrawingOrder() < copyOfFirstEditText.getDrawingOrder());
+ assertTrue(copyOfFirstEditText.getDrawingOrder() < firstButton.getDrawingOrder());
+ }
+
+ @MediumTest
+ public void testDrawingOrderGettingAllViewsFollowsXmlOrder() throws Exception {
+ UiAutomation uiAutomation = getUiAutomation(true);
+ AccessibilityNodeInfo firstTextView = getNodeByText(uiAutomation, R.string.firstTextView);
+ AccessibilityNodeInfo firstEditText = getNodeByText(uiAutomation, R.string.firstEditText);
+ AccessibilityNodeInfo firstButton = getNodeByText(uiAutomation, R.string.firstButton);
+
+ // Drawing order is: firstTextView, firstEditText, firstButton
+ assertTrue(firstTextView.getDrawingOrder() < firstEditText.getDrawingOrder());
+ assertTrue(firstEditText.getDrawingOrder() < firstButton.getDrawingOrder());
+ }
+
+ @MediumTest
+ public void testDrawingOrderWithZCoordsDrawsHighestZLast() throws Exception {
+ getInstrumentation().runOnMainSync(new Runnable() {
+ @Override
+ public void run() {
+ AccessibilityViewTreeReportingActivity activity = getActivity();
+ activity.findViewById(R.id.firstTextView).setZ(50);
+ activity.findViewById(R.id.firstEditText).setZ(100);
+ }
+ });
+
+ UiAutomation uiAutomation = getUiAutomation(true);
+ AccessibilityNodeInfo firstTextView = getNodeByText(uiAutomation, R.string.firstTextView);
+ AccessibilityNodeInfo firstEditText = getNodeByText(uiAutomation, R.string.firstEditText);
+ AccessibilityNodeInfo firstButton = getNodeByText(uiAutomation, R.string.firstButton);
+
+ // Drawing order is firstButton (no z), firstTextView (z=50), firstEditText (z=100)
+ assertTrue(firstButton.getDrawingOrder() < firstTextView.getDrawingOrder());
+ assertTrue(firstTextView.getDrawingOrder() < firstEditText.getDrawingOrder());
+ }
+
+ @MediumTest
+ public void testDrawingOrderWithCustomDrawingOrder() throws Exception {
+ getInstrumentation().runOnMainSync(new Runnable() {
+ @Override
+ public void run() {
+ // Reorganize the hiearchy to replace firstLinearLayout with one that allows us to
+ // control the draw order
+ AccessibilityViewTreeReportingActivity activity = getActivity();
+ LinearLayout rootLinearLayout =
+ (LinearLayout) activity.findViewById(R.id.rootLinearLayout);
+ LinearLayout firstLinearLayout =
+ (LinearLayout) activity.findViewById(R.id.firstLinearLayout);
+ View firstTextView = activity.findViewById(R.id.firstTextView);
+ View firstEditText = activity.findViewById(R.id.firstEditText);
+ View firstButton = activity.findViewById(R.id.firstButton);
+ firstLinearLayout.removeAllViews();
+ LinearLayoutWithDrawingOrder layoutWithDrawingOrder =
+ new LinearLayoutWithDrawingOrder(activity);
+ rootLinearLayout.addView(layoutWithDrawingOrder);
+ layoutWithDrawingOrder.addView(firstTextView);
+ layoutWithDrawingOrder.addView(firstEditText);
+ layoutWithDrawingOrder.addView(firstButton);
+ layoutWithDrawingOrder.childDrawingOrder = new int[] {2, 0, 1};
+ }
+ });
+
+ UiAutomation uiAutomation = getUiAutomation(true);
+ AccessibilityNodeInfo firstTextView = getNodeByText(uiAutomation, R.string.firstTextView);
+ AccessibilityNodeInfo firstEditText = getNodeByText(uiAutomation, R.string.firstEditText);
+ AccessibilityNodeInfo firstButton = getNodeByText(uiAutomation, R.string.firstButton);
+
+ // Drawing order is firstEditText, firstButton, firstTextView
+ assertTrue(firstEditText.getDrawingOrder() < firstButton.getDrawingOrder());
+ assertTrue(firstButton.getDrawingOrder() < firstTextView.getDrawingOrder());
+ }
+
+ @MediumTest
+ public void testDrawingOrderWithNotImportantSiblingConsidersItsChildren() throws Exception {
+ getInstrumentation().runOnMainSync(new Runnable() {
+ @Override
+ public void run() {
+ // Make the first frame layout a higher Z so it's drawn last
+ getActivity().findViewById(R.id.firstFrameLayout).setZ(100);
+ }
+ });
+ UiAutomation uiAutomation = getUiAutomation(false);
+ AccessibilityNodeInfo secondTextView = getNodeByText(uiAutomation, R.string.secondTextView);
+ AccessibilityNodeInfo secondEditText = getNodeByText(uiAutomation, R.string.secondEditText);
+ AccessibilityNodeInfo secondButton = getNodeByText(uiAutomation, R.string.secondButton);
+ AccessibilityNodeInfo firstFrameLayout =
+ getNodeByText(uiAutomation, R.string.firstFrameLayout);
+ assertTrue(secondTextView.getDrawingOrder() < firstFrameLayout.getDrawingOrder());
+ assertTrue(secondEditText.getDrawingOrder() < firstFrameLayout.getDrawingOrder());
+ assertTrue(secondButton.getDrawingOrder() < firstFrameLayout.getDrawingOrder());
+ }
+
+ @MediumTest
+ public void testDrawingOrderWithNotImportantParentConsidersParentSibling() throws Exception {
+ UiAutomation uiAutomation = getUiAutomation(false);
+ AccessibilityNodeInfo firstFrameLayout =
+ getNodeByText(uiAutomation, R.string.firstFrameLayout);
+ AccessibilityNodeInfo secondTextView = getNodeByText(uiAutomation, R.string.secondTextView);
+ AccessibilityNodeInfo secondEditText = getNodeByText(uiAutomation, R.string.secondEditText);
+ AccessibilityNodeInfo secondButton = getNodeByText(uiAutomation, R.string.secondButton);
+
+ assertTrue(secondTextView.getDrawingOrder() > firstFrameLayout.getDrawingOrder());
+ assertTrue(secondEditText.getDrawingOrder() > firstFrameLayout.getDrawingOrder());
+ assertTrue(secondButton.getDrawingOrder() > firstFrameLayout.getDrawingOrder());
+ }
+
+ @MediumTest
+ public void testDrawingOrderRootNodeHasIndex0() throws Exception {
+ assertEquals(0, getUiAutomation(false).getRootInActiveWindow().getDrawingOrder());
+ }
+
+ private UiAutomation getUiAutomation(boolean getNonImportantViews) {
+ UiAutomation uiAutomation = getInstrumentation().getUiAutomation();
+ AccessibilityServiceInfo serviceInfo = uiAutomation.getServiceInfo();
+ serviceInfo.flags &= ~AccessibilityServiceInfo.FLAG_INCLUDE_NOT_IMPORTANT_VIEWS;
+ serviceInfo.flags |= getNonImportantViews ?
+ AccessibilityServiceInfo.FLAG_INCLUDE_NOT_IMPORTANT_VIEWS : 0;
+ uiAutomation.setServiceInfo(serviceInfo);
+ return uiAutomation;
+ }
+
+ private AccessibilityNodeInfo getNodeByText(UiAutomation uiAutomation, int stringId) {
+ return uiAutomation.getRootInActiveWindow()
+ .findAccessibilityNodeInfosByText(getString(stringId)).get(0);
+ }
+
+ class LinearLayoutWithDrawingOrder extends LinearLayout {
+ public int[] childDrawingOrder;
+ LinearLayoutWithDrawingOrder(Context context) {
+ super(context);
+ setChildrenDrawingOrderEnabled(true);
+ }
+
+ @Override
+ protected int getChildDrawingOrder(int childCount, int i) {
+ return childDrawingOrder[i];
+ }
+ }
}
diff --git a/tests/camera/src/android/hardware/camera2/cts/CaptureResultTest.java b/tests/camera/src/android/hardware/camera2/cts/CaptureResultTest.java
index 199552f..8510016 100644
--- a/tests/camera/src/android/hardware/camera2/cts/CaptureResultTest.java
+++ b/tests/camera/src/android/hardware/camera2/cts/CaptureResultTest.java
@@ -463,6 +463,9 @@
waiverKeys.add(CaptureResult.JPEG_QUALITY);
waiverKeys.add(CaptureResult.JPEG_THUMBNAIL_QUALITY);
waiverKeys.add(CaptureResult.JPEG_THUMBNAIL_SIZE);
+ // Waived until framework implemented deriving logic for this key
+ // b/26625646
+ waiverKeys.add(CaptureResult.CONTROL_POST_RAW_SENSITIVITY_BOOST);
// Keys only present when corresponding control is on are being
// verified in its own functional test
@@ -748,6 +751,7 @@
resultKeys.add(CaptureResult.CONTROL_AE_STATE);
resultKeys.add(CaptureResult.CONTROL_AF_STATE);
resultKeys.add(CaptureResult.CONTROL_AWB_STATE);
+ resultKeys.add(CaptureResult.CONTROL_POST_RAW_SENSITIVITY_BOOST);
resultKeys.add(CaptureResult.EDGE_MODE);
resultKeys.add(CaptureResult.FLASH_MODE);
resultKeys.add(CaptureResult.FLASH_STATE);
diff --git a/tests/tests/media/DynamicConfig.xml b/tests/tests/media/DynamicConfig.xml
index 702157d..1299440 100644
--- a/tests/tests/media/DynamicConfig.xml
+++ b/tests/tests/media/DynamicConfig.xml
@@ -13,17 +13,41 @@
limitations under the License.
-->
-<DynamicConfig>
- <Config key="DecoderTest-VIDEO_URL">http://redirector.gvt1.com/videoplayback?id=c80658495af60617&itag=18&source=youtube&ip=0.0.0.0&ipbits=0&expire=19000000000&sparams=ip,ipbits,expire,id,itag,source&signature=46A04ED550CA83B79B60060BA80C79FDA5853D26.49582D382B4A9AFAA163DED38D2AE531D85603C0&key=ik0&user=android-device-test</Config>
- <Config key="StreamingMediaPlayerTest-testHTTP_H264Base_AAC_Video1">http://redirector.gvt1.com/videoplayback?id=271de9756065677e&itag=18&source=youtube&ip=0.0.0.0&ipbits=0&expire=19000000000&sparams=ip,ipbits,expire,id,itag,source&signature=667AEEF54639926662CE62361400B8F8C1753B3F.15F46C382C68A9F121BA17BF1F56BEDEB4B06091&key=ik0&user=android-device-test</Config>
- <Config key="StreamingMediaPlayerTest-testHTTP_H264Base_AAC_Video2">http://www.youtube.com/api/manifest/hls_variant/id/0168724d02bd9945/itag/5/source/youtube/playlist_type/DVR/ip/0.0.0.0/ipbits/0/expire/19000000000/sparams/ip,ipbits,expire,id,itag,source,playlist_type/signature/773AB8ACC68A96E5AA481996AD6A1BBCB70DCB87.95733B544ACC5F01A1223A837D2CF04DF85A3360/key/ik0/file/m3u8</Config>
- <Config key="MediaCodecCapabilitiesTest-testAvcHigh31">http://redirector.gvt1.com/videoplayback?id=271de9756065677e&itag=22&source=youtube&user=android-device-test&sparams=ip,ipbits,expire,id,itag,source,user&ip=0.0.0.0&ipbits=0&expire=19000000000&signature=179525311196616BD8E1381759B0E5F81A9E91B5.C4A50E44059FEBCC6BBC78E3B3A4E0E0065777&key=ik0</Config>
- <Config key="StreamingMediaPlayerTest-testHTTP_MPEG4SP_AAC_Video2">http://redirector.gvt1.com/videoplayback?id=c80658495af60617&itag=17&source=youtube&ip=0.0.0.0&ipbits=0&expire=19000000000&sparams=ip,ipbits,expire,id,itag,source&signature=70E979A621001201BC18622BDBF914FA870BDA40.6E78890B80F4A33A18835F775B1FF64F0A4D0003&key=ik0&user=android-device-test</Config>
- <Config key="StreamingMediaPlayerTest-testHTTP_MPEG4SP_AAC_Video1">http://redirector.gvt1.com/videoplayback?id=271de9756065677e&itag=17&source=youtube&ip=0.0.0.0&ipbits=0&expire=19000000000&sparams=ip,ipbits,expire,id,itag,source&signature=837198AAADF6F36BA6B2D324F690A7C5B7AFE3FF.7138CE5E36D718220726C1FC305497FF2D082249&key=ik0&user=android-device-test</Config>
- <Config key="MediaCodecCapabilitiesTest-testAvcBaseline12">http://redirector.gvt1.com/videoplayback?id=271de9756065677e&itag=160&source=youtube&user=android-device-test&sparams=ip,ipbits,expire,id,itag,source,user&ip=0.0.0.0&ipbits=0&expire=19000000000&signature=9EDCA0B395B8A949C511FD5E59B9F805CFF797FD.702DE9BA7AF96785FD6930AD2DD693A0486C880E&key=ik0</Config>
- <Config key="DecoderTest-AUDIO_URL">http://redirector.gvt1.com/videoplayback?id=c80658495af60617&itag=18&source=youtube&ip=0.0.0.0&ipbits=0&expire=19000000000&sparams=ip,ipbits,expire,id,itag,source&signature=46A04ED550CA83B79B60060BA80C79FDA5853D26.49582D382B4A9AFAA163DED38D2AE531D85603C0&key=ik0&user=android-device-test</Config>
- <Config key="MediaCodecCapabilitiesTest-testAvcBaseline30">http://redirector.gvt1.com/videoplayback?id=271de9756065677e&itag=18&source=youtube&user=android-device-test&sparams=ip,ipbits,expire,id,itag,source,user&ip=0.0.0.0&ipbits=0&expire=19000000000&signature=7DCDE3A6594D0B91A27676A3CDC3A87B149F82EA.7A83031734CB1EDCE06766B6228842F954927960&key=ik0</Config>
- <Config key="MediaCodecCapabilitiesTest-testAvcHigh40">http://redirector.gvt1.com/videoplayback?id=271de9756065677e&itag=137&source=youtube&user=android-device-test&sparams=ip,ipbits,expire,id,itag,source,user&ip=0.0.0.0&ipbits=0&expire=19000000000&signature=B0976085596DD42DEA3F08307F76587241CB132B.043B719C039E8B92F45391ADC0BE3665E2332930&key=ik0</Config>
- <Config key="StreamingMediaPlayerTest-testHTTP_H263_AMR_Video2">http://redirector.gvt1.com/videoplayback?id=c80658495af60617&itag=13&source=youtube&ip=0.0.0.0&ipbits=0&expire=19000000000&sparams=ip,ipbits,expire,id,itag,source&signature=508D82AB36939345BF6B8D0623CB6CABDD9C64C3.9B3336A96846DF38E5343C46AA57F6CF2956E427&key=ik0&user=android-device-test</Config>
- <Config key="StreamingMediaPlayerTest-testHTTP_H263_AMR_Video1">http://redirector.gvt1.com/videoplayback?id=271de9756065677e&itag=13&source=youtube&ip=0.0.0.0&ipbits=0&expire=19000000000&sparams=ip,ipbits,expire,id,itag,source&signature=5729247E22691EBB3E804DDD523EC42DC17DD8CE.443B81C1E8E6D64E4E1555F568BA46C206507D78&key=ik0&user=android-device-test</Config>
-</DynamicConfig>
+<dynamicConfig>
+ <entry key="DecoderTest-VIDEO_URL">
+ <value>http://redirector.gvt1.com/videoplayback?id=c80658495af60617&itag=18&source=youtube&ip=0.0.0.0&ipbits=0&expire=19000000000&sparams=ip,ipbits,expire,id,itag,source&signature=46A04ED550CA83B79B60060BA80C79FDA5853D26.49582D382B4A9AFAA163DED38D2AE531D85603C0&key=ik0&user=android-device-test</value>
+ </entry>
+ <entry key="StreamingMediaPlayerTest-testHTTP_H264Base_AAC_Video1">
+ <value>http://redirector.gvt1.com/videoplayback?id=271de9756065677e&itag=18&source=youtube&ip=0.0.0.0&ipbits=0&expire=19000000000&sparams=ip,ipbits,expire,id,itag,source&signature=667AEEF54639926662CE62361400B8F8C1753B3F.15F46C382C68A9F121BA17BF1F56BEDEB4B06091&key=ik0&user=android-device-test</value>
+ </entry>
+ <entry key="StreamingMediaPlayerTest-testHTTP_H264Base_AAC_Video2">
+ <value>http://www.youtube.com/api/manifest/hls_variant/id/0168724d02bd9945/itag/5/source/youtube/playlist_type/DVR/ip/0.0.0.0/ipbits/0/expire/19000000000/sparams/ip,ipbits,expire,id,itag,source,playlist_type/signature/773AB8ACC68A96E5AA481996AD6A1BBCB70DCB87.95733B544ACC5F01A1223A837D2CF04DF85A3360/key/ik0/file/m3u8</value>
+ </entry>
+ <entry key="MediaCodecCapabilitiesTest-testAvcHigh31">
+ <value>http://redirector.gvt1.com/videoplayback?id=271de9756065677e&itag=22&source=youtube&user=android-device-test&sparams=ip,ipbits,expire,id,itag,source,user&ip=0.0.0.0&ipbits=0&expire=19000000000&signature=179525311196616BD8E1381759B0E5F81A9E91B5.C4A50E44059FEBCC6BBC78E3B3A4E0E0065777&key=ik0</value>
+ </entry>
+ <entry key="StreamingMediaPlayerTest-testHTTP_MPEG4SP_AAC_Video2">
+ <value>http://redirector.gvt1.com/videoplayback?id=c80658495af60617&itag=17&source=youtube&ip=0.0.0.0&ipbits=0&expire=19000000000&sparams=ip,ipbits,expire,id,itag,source&signature=70E979A621001201BC18622BDBF914FA870BDA40.6E78890B80F4A33A18835F775B1FF64F0A4D0003&key=ik0&user=android-device-test</value>
+ </entry>
+ <entry key="StreamingMediaPlayerTest-testHTTP_MPEG4SP_AAC_Video1">
+ <value>http://redirector.gvt1.com/videoplayback?id=271de9756065677e&itag=17&source=youtube&ip=0.0.0.0&ipbits=0&expire=19000000000&sparams=ip,ipbits,expire,id,itag,source&signature=837198AAADF6F36BA6B2D324F690A7C5B7AFE3FF.7138CE5E36D718220726C1FC305497FF2D082249&key=ik0&user=android-device-test</value>
+ </entry>
+ <entry key="MediaCodecCapabilitiesTest-testAvcBaseline12">
+ <value>http://redirector.gvt1.com/videoplayback?id=271de9756065677e&itag=160&source=youtube&user=android-device-test&sparams=ip,ipbits,expire,id,itag,source,user&ip=0.0.0.0&ipbits=0&expire=19000000000&signature=9EDCA0B395B8A949C511FD5E59B9F805CFF797FD.702DE9BA7AF96785FD6930AD2DD693A0486C880E&key=ik0</value>
+ </entry>
+ <entry key="DecoderTest-AUDIO_URL">
+ <value>http://redirector.gvt1.com/videoplayback?id=c80658495af60617&itag=18&source=youtube&ip=0.0.0.0&ipbits=0&expire=19000000000&sparams=ip,ipbits,expire,id,itag,source&signature=46A04ED550CA83B79B60060BA80C79FDA5853D26.49582D382B4A9AFAA163DED38D2AE531D85603C0&key=ik0&user=android-device-test</value>
+ </entry>
+ <entry key="MediaCodecCapabilitiesTest-testAvcBaseline30">
+ <value>http://redirector.gvt1.com/videoplayback?id=271de9756065677e&itag=18&source=youtube&user=android-device-test&sparams=ip,ipbits,expire,id,itag,source,user&ip=0.0.0.0&ipbits=0&expire=19000000000&signature=7DCDE3A6594D0B91A27676A3CDC3A87B149F82EA.7A83031734CB1EDCE06766B6228842F954927960&key=ik0</value>
+ </entry>
+ <entry key="MediaCodecCapabilitiesTest-testAvcHigh40">
+ <value>http://redirector.gvt1.com/videoplayback?id=271de9756065677e&itag=137&source=youtube&user=android-device-test&sparams=ip,ipbits,expire,id,itag,source,user&ip=0.0.0.0&ipbits=0&expire=19000000000&signature=B0976085596DD42DEA3F08307F76587241CB132B.043B719C039E8B92F45391ADC0BE3665E2332930&key=ik0</value>
+ </entry>
+ <entry key="StreamingMediaPlayerTest-testHTTP_H263_AMR_Video2">
+ <value>http://redirector.gvt1.com/videoplayback?id=c80658495af60617&itag=13&source=youtube&ip=0.0.0.0&ipbits=0&expire=19000000000&sparams=ip,ipbits,expire,id,itag,source&signature=508D82AB36939345BF6B8D0623CB6CABDD9C64C3.9B3336A96846DF38E5343C46AA57F6CF2956E427&key=ik0&user=android-device-test</value>
+ </entry>
+ <entry key="StreamingMediaPlayerTest-testHTTP_H263_AMR_Video1">
+ <value>http://redirector.gvt1.com/videoplayback?id=271de9756065677e&itag=13&source=youtube&ip=0.0.0.0&ipbits=0&expire=19000000000&sparams=ip,ipbits,expire,id,itag,source&signature=5729247E22691EBB3E804DDD523EC42DC17DD8CE.443B81C1E8E6D64E4E1555F568BA46C206507D78&key=ik0&user=android-device-test</value>
+ </entry>
+</dynamicConfig>
diff --git a/tests/tests/mediastress/preconditions/src/android/mediastress/cts/preconditions/MediaPreparer.java b/tests/tests/mediastress/preconditions/src/android/mediastress/cts/preconditions/MediaPreparer.java
index ab5b65d..b996e4a 100644
--- a/tests/tests/mediastress/preconditions/src/android/mediastress/cts/preconditions/MediaPreparer.java
+++ b/tests/tests/mediastress/preconditions/src/android/mediastress/cts/preconditions/MediaPreparer.java
@@ -229,7 +229,7 @@
URL url;
try {
DynamicConfigHostSide config = new DynamicConfigHostSide(DYNAMIC_CONFIG_MODULE);
- String mediaUrlString = config.getConfig(MEDIA_FILES_URL_KEY);
+ String mediaUrlString = config.getValue(MEDIA_FILES_URL_KEY);
url = new URL(mediaUrlString);
} catch (IOException | XmlPullParserException e) {
throw new TargetSetupError("Trouble finding media file download location with " +
diff --git a/tests/tests/networksecurityconfig/Android.mk b/tests/tests/networksecurityconfig/Android.mk
new file mode 100644
index 0000000..4312beb
--- /dev/null
+++ b/tests/tests/networksecurityconfig/Android.mk
@@ -0,0 +1,15 @@
+# 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.
+#
+include $(call all-subdir-makefiles)
diff --git a/tests/tests/networksecurityconfig/build_apk.mk b/tests/tests/networksecurityconfig/build_apk.mk
new file mode 100644
index 0000000..3c7c230
--- /dev/null
+++ b/tests/tests/networksecurityconfig/build_apk.mk
@@ -0,0 +1,24 @@
+# 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_MODULE_TAGS := optional
+LOCAL_MODULE_PATH := $(TARGET_OUT_DATA_APPS)
+LOCAL_CTS_TEST_PACKAGE := android.security.net.config
+LOCAL_STATIC_JAVA_LIBRARIES := ctstestrunner \
+ org.apache.http.legacy
+LOCAL_SRC_FILES := $(call all-java-files-under, src)
+LOCAL_SRC_FILES += $(call all-java-files-under, ../src)
+LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res/
+LOCAL_SDK_VERSION := current
+include $(BUILD_CTS_PACKAGE)
diff --git a/tests/tests/networksecurityconfig/manifest.xml b/tests/tests/networksecurityconfig/manifest.xml
new file mode 100644
index 0000000..0c1e85d
--- /dev/null
+++ b/tests/tests/networksecurityconfig/manifest.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="utf-8"?>
+
+<!--
+ * 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.
+ -->
+
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+ package="android.security.net.config.cts">
+ <application>
+ <uses-library android:name="android.test.runner"/>
+ <meta-data android:name="android.security.net.config"
+ android:resource="@xml/network_security_config" />
+ </application>
+
+ <uses-permission android:name="android.permission.INTERNET" />
+ <instrumentation android:name="android.support.test.runner.AndroidJUnitRunner"
+ android:targetPackage="android.security.net.config.cts"
+ android:label="">
+ <meta-data android:name="listener"
+ android:value="com.android.cts.runner.CtsTestRunListener" />
+ </instrumentation>
+</manifest>
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-attributes/Android.mk b/tests/tests/networksecurityconfig/networksecurityconfig-attributes/Android.mk
new file mode 100644
index 0000000..6c0a92b
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-attributes/Android.mk
@@ -0,0 +1,19 @@
+# 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_PACKAGE_NAME := CtsNetSecConfigAttributeTestCases
+include $(LOCAL_PATH)/../build_apk.mk
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-attributes/AndroidManifest.xml b/tests/tests/networksecurityconfig/networksecurityconfig-attributes/AndroidManifest.xml
new file mode 100644
index 0000000..c2018ba
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-attributes/AndroidManifest.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="utf-8"?>
+
+<!--
+ * 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.
+ -->
+
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+ package="android.security.net.config.cts.CtsNetSecConfigAttributeTestCases">
+ <application>
+ <uses-library android:name="android.test.runner"/>
+ <meta-data android:name="android.security.net.config"
+ android:resource="@xml/network_security_config" />
+ </application>
+
+ <uses-permission android:name="android.permission.INTERNET" />
+ <instrumentation android:name="android.support.test.runner.AndroidJUnitRunner"
+ android:targetPackage="android.security.net.config.cts.CtsNetSecConfigAttributeTestCases"
+ android:label="">
+ <meta-data android:name="listener"
+ android:value="com.android.cts.runner.CtsTestRunListener" />
+ </instrumentation>
+</manifest>
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-attributes/res/xml/network_security_config.xml b/tests/tests/networksecurityconfig/networksecurityconfig-attributes/res/xml/network_security_config.xml
new file mode 100644
index 0000000..1e68b7d
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-attributes/res/xml/network_security_config.xml
@@ -0,0 +1,17 @@
+<?xml version="1.0" encoding="utf-8"?>
+<network-security-config>
+ <base-config cleartextTrafficPermitted="true">
+ </base-config>
+ <!-- Cleartext traffic is not permitted for connections to foo.bar -->
+ <domain-config cleartextTrafficPermitted="false">
+ <domain includeSubdomains="false">foo.bar</domain>
+ </domain-config>
+ <!-- cleartextTrafficPermitted not set, should inherit from the base-config -->
+ <domain-config>
+ <domain includeSubdomains="true">android.com</domain>
+ </domain-config>
+ <!-- Cleartext traffic is explicitly permitted to google.com and all subdomains -->
+ <domain-config cleartextTrafficPermitted="true">
+ <domain includeSubdomains="true">google.com</domain>
+ </domain-config>
+</network-security-config>
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-attributes/src/android/security/net/config/cts/TestAttributes.java b/tests/tests/networksecurityconfig/networksecurityconfig-attributes/src/android/security/net/config/cts/TestAttributes.java
new file mode 100644
index 0000000..4d23e5b
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-attributes/src/android/security/net/config/cts/TestAttributes.java
@@ -0,0 +1,42 @@
+/*
+ * 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.
+ */
+
+package android.security.net.config.cts;
+
+import android.security.NetworkSecurityPolicy;
+import junit.framework.TestCase;
+
+public class TestAttributes extends TestCase {
+ public void testCleartextTrafficPermitted() throws Exception {
+ NetworkSecurityPolicy instance = NetworkSecurityPolicy.getInstance();
+ // Since there are some configs that do not allow cleartext the non-hostname aware version
+ // should return False.
+ assertFalse(instance.isCleartextTrafficPermitted());
+ // Domain that explicitly does not allow cleartext traffic.
+ assertFalse(instance.isCleartextTrafficPermitted("foo.bar"));
+ // Subdomains are not included in the above rule, they should use the base-config's value.
+ assertTrue(instance.isCleartextTrafficPermitted("example.foo.bar"));
+ // Domains in a domain-config that do not specify the flag, should inherit from the
+ // base-config.
+ assertTrue(instance.isCleartextTrafficPermitted("android.com"));
+ assertTrue(instance.isCleartextTrafficPermitted("foo.android.com"));
+ // Domains in a domain-config that explicitly allow cleartext.
+ assertTrue(instance.isCleartextTrafficPermitted("google.com"));
+ assertTrue(instance.isCleartextTrafficPermitted("test.google.com"));
+ // Domain not specified in a domain-config, should use the base-config's value.
+ assertTrue(instance.isCleartextTrafficPermitted("example.com"));
+ }
+}
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-basic-domain/Android.mk b/tests/tests/networksecurityconfig/networksecurityconfig-basic-domain/Android.mk
new file mode 100644
index 0000000..1224198
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-basic-domain/Android.mk
@@ -0,0 +1,19 @@
+# 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_PACKAGE_NAME := CtsNetSecConfigBasicDomainConfigTestCases
+include $(LOCAL_PATH)/../build_apk.mk
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-basic-domain/AndroidManifest.xml b/tests/tests/networksecurityconfig/networksecurityconfig-basic-domain/AndroidManifest.xml
new file mode 100644
index 0000000..0fd1a59
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-basic-domain/AndroidManifest.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="utf-8"?>
+
+<!--
+ * 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.
+ -->
+
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+ package="android.security.net.config.cts.CtsNetSecConfigBasicDomainConfigTestCases">
+ <application>
+ <uses-library android:name="android.test.runner"/>
+ <meta-data android:name="android.security.net.config"
+ android:resource="@xml/network_security_config" />
+ </application>
+
+ <uses-permission android:name="android.permission.INTERNET" />
+ <instrumentation android:name="android.support.test.runner.AndroidJUnitRunner"
+ android:targetPackage="android.security.net.config.cts.CtsNetSecConfigBasicDomainConfigTestCases"
+ android:label="">
+ <meta-data android:name="listener"
+ android:value="com.android.cts.runner.CtsTestRunListener" />
+ </instrumentation>
+</manifest>
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-basic-domain/res/xml/network_security_config.xml b/tests/tests/networksecurityconfig/networksecurityconfig-basic-domain/res/xml/network_security_config.xml
new file mode 100644
index 0000000..6d8565c
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-basic-domain/res/xml/network_security_config.xml
@@ -0,0 +1,14 @@
+<?xml version="1.0" encoding="utf-8"?>
+<network-security-config>
+ <base-config>
+ <trust-anchors>
+ </trust-anchors>
+ </base-config>
+ <domain-config>
+ <domain>android.com</domain>
+ <trust-anchors>
+ <certificates src="system" />
+ <certificates src="user" />
+ </trust-anchors>
+ </domain-config>
+</network-security-config>
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-basic-domain/src/android/security/net/config/cts/DomainConfigTest.java b/tests/tests/networksecurityconfig/networksecurityconfig-basic-domain/src/android/security/net/config/cts/DomainConfigTest.java
new file mode 100644
index 0000000..73ddd33
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-basic-domain/src/android/security/net/config/cts/DomainConfigTest.java
@@ -0,0 +1,47 @@
+/*
+ * 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.
+ */
+
+package android.security.net.config.cts;
+
+import java.security.cert.CertificateException;
+import java.security.cert.X509Certificate;
+import javax.net.ssl.X509TrustManager;
+import junit.framework.TestCase;
+
+public class DomainConfigTest extends TestCase {
+
+ public void testDomainConfig() throws Exception {
+ TestUtils.assertTlsConnectionSucceeds("android.com", 443);
+ }
+
+ public void testDefaultConfig() throws Exception {
+ // The default config in this case has no trusted CAs, so all connections should fail.
+ TestUtils.assertTlsConnectionFails("developer.android.com", 443);
+ TestUtils.assertTlsConnectionFails("google.com", 443);
+ }
+
+ public void testHostnameAwareCheckServerTrustedRequired() throws Exception {
+ X509TrustManager x509tm = TestUtils.getDefaultTrustManager();
+ try {
+ x509tm.checkServerTrusted(new X509Certificate[] {}, "RSA");
+ fail("checkServerTrusted passed");
+ } catch (CertificateException e) {
+ if (!e.getMessage().contains("hostname aware checkServerTrusted")) {
+ fail("Hostname aware checkServerTrusted not required with a domain config");
+ }
+ }
+ }
+}
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-disabled/Android.mk b/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-disabled/Android.mk
new file mode 100644
index 0000000..70b9060
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-disabled/Android.mk
@@ -0,0 +1,19 @@
+# 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_PACKAGE_NAME := CtsNetSecConfigBasicDebugDisabledTestCases
+include $(LOCAL_PATH)/../build_apk.mk
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-disabled/AndroidManifest.xml b/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-disabled/AndroidManifest.xml
new file mode 100644
index 0000000..9464950
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-disabled/AndroidManifest.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="utf-8"?>
+
+<!--
+ * 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.
+ -->
+
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+ package="android.security.net.config.cts.CtsNetSecConfigBasicDebugDisabledTestCases">
+ <application android:debuggable="false">
+ <uses-library android:name="android.test.runner"/>
+ <meta-data android:name="android.security.net.config"
+ android:resource="@xml/network_security_config" />
+ </application>
+
+ <uses-permission android:name="android.permission.INTERNET" />
+ <instrumentation android:name="android.support.test.runner.AndroidJUnitRunner"
+ android:targetPackage="android.security.net.config.cts.CtsNetSecConfigBasicDebugDisabledTestCases"
+ android:label="">
+ <meta-data android:name="listener"
+ android:value="com.android.cts.runner.CtsTestRunListener" />
+ </instrumentation>
+</manifest>
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-disabled/res/xml/network_security_config.xml b/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-disabled/res/xml/network_security_config.xml
new file mode 100644
index 0000000..c44d9de
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-disabled/res/xml/network_security_config.xml
@@ -0,0 +1,14 @@
+<?xml version="1.0" encoding="utf-8"?>
+<network-security-config>
+ <!-- default config that trusts nothing. Will always cause TLS errors -->
+ <base-config>
+ <trust-anchors>
+ </trust-anchors>
+ </base-config>
+ <!-- debug overrides, should be ignored in this case since the app is not debuggable -->
+ <debug-overrides>
+ <trust-anchors>
+ <certificates src="system" />
+ </trust-anchors>
+ </debug-overrides>
+</network-security-config>
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-disabled/src/android/security/net/config/cts/BasicDebugOverrideDisabledTest.java b/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-disabled/src/android/security/net/config/cts/BasicDebugOverrideDisabledTest.java
new file mode 100644
index 0000000..862dd9b
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-disabled/src/android/security/net/config/cts/BasicDebugOverrideDisabledTest.java
@@ -0,0 +1,26 @@
+/*
+ * 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.
+ */
+
+package android.security.net.config.cts;
+
+import junit.framework.TestCase;
+
+public class BasicDebugOverrideDisabledTest extends TestCase {
+
+ public void testDefaultConfig() throws Exception {
+ TestUtils.assertTlsConnectionFails("android.com", 443);
+ }
+}
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-enabled/Android.mk b/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-enabled/Android.mk
new file mode 100644
index 0000000..433cf84
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-enabled/Android.mk
@@ -0,0 +1,19 @@
+# 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_PACKAGE_NAME := CtsNetSecConfigBasicDebugEnabledTestCases
+include $(LOCAL_PATH)/../build_apk.mk
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-enabled/AndroidManifest.xml b/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-enabled/AndroidManifest.xml
new file mode 100644
index 0000000..2a46c8c
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-enabled/AndroidManifest.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="utf-8"?>
+
+<!--
+ * 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.
+ -->
+
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+ package="android.security.net.config.cts.CtsNetSecConfigBasicDebugEnabledTestCases">
+ <application android:debuggable="true">
+ <uses-library android:name="android.test.runner"/>
+ <meta-data android:name="android.security.net.config"
+ android:resource="@xml/network_security_config" />
+ </application>
+
+ <uses-permission android:name="android.permission.INTERNET" />
+ <instrumentation android:name="android.support.test.runner.AndroidJUnitRunner"
+ android:targetPackage="android.security.net.config.cts.CtsNetSecConfigBasicDebugEnabledTestCases"
+ android:label="">
+ <meta-data android:name="listener"
+ android:value="com.android.cts.runner.CtsTestRunListener" />
+ </instrumentation>
+</manifest>
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-enabled/res/xml/network_security_config.xml b/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-enabled/res/xml/network_security_config.xml
new file mode 100644
index 0000000..f2c800a
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-enabled/res/xml/network_security_config.xml
@@ -0,0 +1,15 @@
+<?xml version="1.0" encoding="utf-8"?>
+<network-security-config>
+ <!-- default config that trusts nothing. Will always cause TLS errors -->
+ <base-config>
+ <trust-anchors>
+ </trust-anchors>
+ </base-config>
+ <!-- debug override that trusts the system CA store. Connections will work as normal when the
+ application is debuggable. -->
+ <debug-overrides>
+ <trust-anchors>
+ <certificates src="system" />
+ </trust-anchors>
+ </debug-overrides>
+</network-security-config>
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-enabled/src/android/security/net/config/cts/BasicDebugOverrideEnabledTest.java b/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-enabled/src/android/security/net/config/cts/BasicDebugOverrideEnabledTest.java
new file mode 100644
index 0000000..c0d9814
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-debug-basic-enabled/src/android/security/net/config/cts/BasicDebugOverrideEnabledTest.java
@@ -0,0 +1,27 @@
+/*
+ * 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.
+ */
+
+package android.security.net.config.cts;
+
+import junit.framework.TestCase;
+
+public class BasicDebugOverrideEnabledTest extends TestCase {
+
+ public void testDefaultConfig() throws Exception {
+ // Connections should work thanks to the debug overrides adding the system CA store.
+ TestUtils.assertTlsConnectionSucceeds("android.com", 443);
+ }
+}
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-invalid-pin/Android.mk b/tests/tests/networksecurityconfig/networksecurityconfig-invalid-pin/Android.mk
new file mode 100644
index 0000000..3d7febb
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-invalid-pin/Android.mk
@@ -0,0 +1,19 @@
+# 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_PACKAGE_NAME := CtsNetSecConfigInvalidPinTestCases
+include $(LOCAL_PATH)/../build_apk.mk
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-invalid-pin/AndroidManifest.xml b/tests/tests/networksecurityconfig/networksecurityconfig-invalid-pin/AndroidManifest.xml
new file mode 100644
index 0000000..e01dc07
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-invalid-pin/AndroidManifest.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="utf-8"?>
+
+<!--
+ * 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.
+ -->
+
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+ package="android.security.net.config.cts.CtsNetSecConfigInvalidPinTestCases">
+ <application>
+ <uses-library android:name="android.test.runner"/>
+ <meta-data android:name="android.security.net.config"
+ android:resource="@xml/network_security_config" />
+ </application>
+
+ <uses-permission android:name="android.permission.INTERNET" />
+ <instrumentation android:name="android.support.test.runner.AndroidJUnitRunner"
+ android:targetPackage="android.security.net.config.cts.CtsNetSecConfigInvalidPinTestCases"
+ android:label="">
+ <meta-data android:name="listener"
+ android:value="com.android.cts.runner.CtsTestRunListener" />
+ </instrumentation>
+</manifest>
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-invalid-pin/res/xml/network_security_config.xml b/tests/tests/networksecurityconfig/networksecurityconfig-invalid-pin/res/xml/network_security_config.xml
new file mode 100644
index 0000000..163b238
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-invalid-pin/res/xml/network_security_config.xml
@@ -0,0 +1,10 @@
+<?xml version="1.0" encoding="utf-8"?>
+<network-security-config>
+ <domain-config>
+ <domain>android.com</domain>
+ <pin-set>
+ <!-- Invalid pin for android.com -->
+ <pin digest="SHA-256">1HIpactkIAq2Y49orFOOQKurWxmmSFZhBCoQYcRhJ3Y=</pin>
+ </pin-set>
+ </domain-config>
+</network-security-config>
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-invalid-pin/src/android/security/net/config/cts/InvalidPinTest.java b/tests/tests/networksecurityconfig/networksecurityconfig-invalid-pin/src/android/security/net/config/cts/InvalidPinTest.java
new file mode 100644
index 0000000..fb0444a
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-invalid-pin/src/android/security/net/config/cts/InvalidPinTest.java
@@ -0,0 +1,31 @@
+/*
+ * 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.
+ */
+
+package android.security.net.config.cts;
+
+import junit.framework.TestCase;
+
+public class InvalidPinTest extends TestCase {
+
+ public void testPinFailure() throws Exception {
+ TestUtils.assertTlsConnectionFails("android.com", 443);
+ }
+
+ public void testDefaultDomainUnaffected() throws Exception {
+ TestUtils.assertTlsConnectionSucceeds("google.com", 443);
+ TestUtils.assertTlsConnectionSucceeds("developer.android.com", 443);
+ }
+}
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-nested-domains/Android.mk b/tests/tests/networksecurityconfig/networksecurityconfig-nested-domains/Android.mk
new file mode 100644
index 0000000..66fef09
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-nested-domains/Android.mk
@@ -0,0 +1,19 @@
+# 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_PACKAGE_NAME := CtsNetSecConfigNestedDomainConfigTestCases
+include $(LOCAL_PATH)/../build_apk.mk
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-nested-domains/AndroidManifest.xml b/tests/tests/networksecurityconfig/networksecurityconfig-nested-domains/AndroidManifest.xml
new file mode 100644
index 0000000..358644e
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-nested-domains/AndroidManifest.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="utf-8"?>
+
+<!--
+ * 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.
+ -->
+
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+ package="android.security.net.config.cts.CtsNetSecConfigNestedDomainConfigTestCases">
+ <application>
+ <uses-library android:name="android.test.runner"/>
+ <meta-data android:name="android.security.net.config"
+ android:resource="@xml/network_security_config" />
+ </application>
+
+ <uses-permission android:name="android.permission.INTERNET" />
+ <instrumentation android:name="android.support.test.runner.AndroidJUnitRunner"
+ android:targetPackage="android.security.net.config.cts.CtsNetSecConfigNestedDomainConfigTestCases"
+ android:label="">
+ <meta-data android:name="listener"
+ android:value="com.android.cts.runner.CtsTestRunListener" />
+ </instrumentation>
+</manifest>
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-nested-domains/res/xml/network_security_config.xml b/tests/tests/networksecurityconfig/networksecurityconfig-nested-domains/res/xml/network_security_config.xml
new file mode 100644
index 0000000..9e91dc7
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-nested-domains/res/xml/network_security_config.xml
@@ -0,0 +1,15 @@
+<?xml version="1.0" encoding="utf-8"?>
+<network-security-config>
+ <domain-config cleartextTrafficPermitted="true">
+ <domain includeSubdomains="true">android.com</domain>
+ <!-- Empty trust anchors, all TLS connections will fail -->
+ <trust-anchors>
+ </trust-anchors>
+ <!-- Nested config, should inherit all unset values from the parent domain -->
+ <domain-config cleartextTrafficPermitted="false">
+ <domain>developer.android.com</domain>
+ </domain-config>
+ </domain-config>
+ <base-config>
+ </base-config>
+</network-security-config>
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-nested-domains/src/android/security/net/config/cts/NestedDomainConfigTest.java b/tests/tests/networksecurityconfig/networksecurityconfig-nested-domains/src/android/security/net/config/cts/NestedDomainConfigTest.java
new file mode 100644
index 0000000..b77ad5a
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-nested-domains/src/android/security/net/config/cts/NestedDomainConfigTest.java
@@ -0,0 +1,36 @@
+/*
+ * 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.
+ */
+
+package android.security.net.config.cts;
+
+import android.security.NetworkSecurityPolicy;
+
+import junit.framework.TestCase;
+
+public class NestedDomainConfigTest extends TestCase {
+
+ public void testRootDomainConfig() throws Exception {
+ TestUtils.assertTlsConnectionFails("android.com", 443);
+ NetworkSecurityPolicy instance = NetworkSecurityPolicy.getInstance();
+ assertTrue(instance.isCleartextTrafficPermitted("android.com"));
+ }
+
+ public void testNestedDomainConfig() throws Exception {
+ TestUtils.assertTlsConnectionFails("developer.android.com", 443);
+ NetworkSecurityPolicy instance = NetworkSecurityPolicy.getInstance();
+ assertFalse(instance.isCleartextTrafficPermitted("developer.android.com"));
+ }
+}
diff --git a/tests/tests/networksecurityconfig/src/android/security/net/config/cts/TestUtils.java b/tests/tests/networksecurityconfig/src/android/security/net/config/cts/TestUtils.java
new file mode 100644
index 0000000..0952cd3
--- /dev/null
+++ b/tests/tests/networksecurityconfig/src/android/security/net/config/cts/TestUtils.java
@@ -0,0 +1,137 @@
+/*
+ * 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.
+ */
+
+package android.security.net.config.cts;
+
+import android.net.http.AndroidHttpClient;
+
+import java.io.InputStream;
+import java.io.IOException;
+import java.net.Socket;
+import java.net.URL;
+import java.security.KeyStore;
+import java.security.cert.Certificate;
+import java.security.cert.CertificateFactory;
+import java.security.cert.X509Certificate;
+import java.util.List;
+import java.util.ArrayList;
+import javax.net.ssl.HttpsURLConnection;
+import javax.net.ssl.SSLContext;
+import javax.net.ssl.SSLHandshakeException;
+import javax.net.ssl.TrustManager;
+import javax.net.ssl.TrustManagerFactory;
+import javax.net.ssl.X509TrustManager;
+
+import junit.framework.Assert;
+
+import org.apache.http.HttpResponse;
+import org.apache.http.client.methods.HttpGet;
+
+public final class TestUtils extends Assert {
+
+ private TestUtils() {
+ }
+
+
+ public static void assertTlsConnectionSucceeds(String host, int port) throws Exception {
+ assertSslSocketSucceeds(host, port);
+ assertHttpClientHttpsSucceeds(host, port);
+ assertUrlConnectionHttpsSucceeds(host, port);
+ }
+
+ public static void assertTlsConnectionFails(String host, int port) throws Exception {
+ assertSslSocketFails(host, port);
+ assertHttpClientHttpsFails(host, port);
+ assertUrlConnectionHttpsFails(host, port);
+ }
+
+ public static X509TrustManager getDefaultTrustManager() throws Exception {
+ TrustManagerFactory tmf = TrustManagerFactory.getInstance("PKIX");
+ tmf.init((KeyStore)null);
+ for (TrustManager tm : tmf.getTrustManagers()) {
+ if (tm instanceof X509TrustManager) {
+ return (X509TrustManager) tm;
+ }
+ }
+ fail("Unable to find X509TrustManager");
+ return null;
+ }
+
+ public static List<X509Certificate> loadCertificates(InputStream is) throws Exception {
+ CertificateFactory factory = CertificateFactory.getInstance("X.509");
+ ArrayList<X509Certificate> result = new ArrayList<>();
+ for (Certificate c : factory.generateCertificates(is)) {
+ result.add((X509Certificate) c);
+ }
+ return result;
+ }
+
+ private static void assertSslSocketFails(String host, int port)
+ throws Exception {
+ try {
+ Socket s = SSLContext.getDefault().getSocketFactory().createSocket(host, port);
+ s.getInputStream();
+ fail("Connection to " + host + ":" + port + " succeeded");
+ } catch (SSLHandshakeException expected) {
+ }
+ }
+
+ private static void assertSslSocketSucceeds(String host, int port)
+ throws Exception {
+ Socket s = SSLContext.getDefault().getSocketFactory().createSocket(host, port);
+ s.getInputStream();
+ }
+
+ private static void assertUrlConnectionHttpsFails(String host, int port)
+ throws Exception {
+ URL url = new URL("https://" + host + ":" + port);
+ HttpsURLConnection connection = (HttpsURLConnection) url.openConnection();
+ try {
+ connection.getInputStream();
+ fail("Connection to " + host + ":" + port + " succeeded");
+ } catch (SSLHandshakeException expected) {
+ }
+ }
+
+ private static void assertUrlConnectionHttpsSucceeds(String host, int port)
+ throws Exception {
+ URL url = new URL("https://" + host + ":" + port);
+ HttpsURLConnection connection = (HttpsURLConnection) url.openConnection();
+ connection.getInputStream();
+ }
+
+ private static void assertHttpClientHttpsSucceeds(String host, int port) throws Exception {
+ URL url = new URL("https://" + host + ":" + port);
+ AndroidHttpClient httpClient = AndroidHttpClient.newInstance(null);
+ try {
+ HttpResponse response = httpClient.execute(new HttpGet(url.toString()));
+ } finally {
+ httpClient.close();
+ }
+ }
+
+ private static void assertHttpClientHttpsFails(String host, int port) throws Exception {
+ URL url = new URL("https://" + host + ":" + port);
+ AndroidHttpClient httpClient = AndroidHttpClient.newInstance(null);
+ try {
+ HttpResponse response = httpClient.execute(new HttpGet(url.toString()));
+ fail("Connection to " + host + ":" + port + " succeeded");
+ } catch (IOException expected) {
+ } finally {
+ httpClient.close();
+ }
+ }
+}
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/SingleSourceAllocationTest.java b/tests/tests/renderscript/src/android/renderscript/cts/SingleSourceAllocationTest.java
new file mode 100644
index 0000000..88b96ac
--- /dev/null
+++ b/tests/tests/renderscript/src/android/renderscript/cts/SingleSourceAllocationTest.java
@@ -0,0 +1,76 @@
+/*
+ * Copyright (C) 2015-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.
+ */
+
+package android.renderscript.cts;
+
+import android.util.Log;
+import android.renderscript.Allocation;
+import android.renderscript.Element;
+import android.renderscript.Script;
+import android.renderscript.Type;
+import android.renderscript.Type.Builder;
+
+public class SingleSourceAllocationTest extends RSBaseCompute {
+
+ private static final String TAG = "SingleSourceAllocationTest";
+
+ private ScriptC_single_source_alloc s;
+ private static final int dimX = 3;
+ private static final int dimY = 4;
+ private static final int dimZ = 5;
+ private static final int start = 23;
+
+ @Override
+ protected void setUp() throws Exception {
+ super.setUp();
+
+ s = new ScriptC_single_source_alloc(mRS);
+ s.set_gDimX(dimX);
+ s.set_gDimY(dimY);
+ s.set_gDimZ(dimZ);
+ s.set_gStart(start);
+ }
+
+ public void testElementCreation() {
+ s.invoke_TestElementCreation();
+ waitForMessage();
+ checkForErrors();
+ }
+
+ public void testTypeCreation() {
+ s.invoke_TestTypeCreation();
+ waitForMessage();
+ checkForErrors();
+ }
+
+ public void testAllocationCreationWithUsage() {
+ s.invoke_TestAllocationCreationWithUsage();
+ waitForMessage();
+ checkForErrors();
+ }
+
+ public void testAllocationCreationHelperFunctions() {
+ s.invoke_TestHelperFunctions();
+ waitForMessage();
+ checkForErrors();
+ }
+
+ public void testAllocationCreationAndAccess() {
+ s.invoke_TestAllocationCreationAndAccess();
+ waitForMessage();
+ checkForErrors();
+ }
+}
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/SingleSourceForEachTest.java b/tests/tests/renderscript/src/android/renderscript/cts/SingleSourceForEachTest.java
new file mode 100644
index 0000000..e005013
--- /dev/null
+++ b/tests/tests/renderscript/src/android/renderscript/cts/SingleSourceForEachTest.java
@@ -0,0 +1,112 @@
+/*
+ * Copyright (C) 2015-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.
+ */
+
+package android.renderscript.cts;
+
+import android.renderscript.Allocation;
+import android.renderscript.Element;
+import android.renderscript.Script;
+import android.renderscript.Type;
+import android.renderscript.Type.Builder;
+
+public class SingleSourceForEachTest extends RSBaseCompute {
+
+ private static final int X = 1024;
+ private static final int Y = 768;
+
+ private Allocation testInputAlloc;
+ private Allocation testInputAlloc2;
+ private Allocation testOutputAlloc;
+ private Allocation baselineOutputAlloc;
+ private int testInputArray[];
+ private int testInputArray2[];
+ private int testOutputArray[];
+ private int baselineOutputArray[];
+ private ScriptC_single_source_script s;
+
+ @Override
+ protected void setUp() throws Exception {
+ super.setUp();
+
+ Type.Builder i32TypeBuilder = new Type.Builder(mRS, Element.I32(mRS));
+ i32TypeBuilder.setX(X).setY(Y);
+ testInputAlloc = Allocation.createTyped(mRS, i32TypeBuilder.create());
+ testInputAlloc2 = Allocation.createTyped(mRS, i32TypeBuilder.create());
+ testOutputAlloc = Allocation.createTyped(mRS, i32TypeBuilder.create());
+ baselineOutputAlloc = Allocation.createTyped(mRS, i32TypeBuilder.create());
+
+ testInputArray = new int[X * Y];
+ testInputArray2 = new int[X * Y];
+ testOutputArray = new int[X * Y];
+ baselineOutputArray = new int[X * Y];
+
+ s = new ScriptC_single_source_script(mRS);
+
+ RSUtils.genRandomInts(0x900d5eed, testInputArray, true, 32);
+ testInputAlloc.copyFrom(testInputArray);
+
+ for (int i = 0; i < testInputArray2.length; i++) {
+ testInputArray2[i] = i + 1;
+ }
+ testInputAlloc2.copyFrom(testInputArray2);
+ }
+
+ public void testSingleInputKernelLaunch() {
+ s.forEach_foo(testInputAlloc, baselineOutputAlloc);
+ s.invoke_testSingleInput(testInputAlloc, testOutputAlloc);
+ testOutputAlloc.copyTo(testOutputArray);
+ baselineOutputAlloc.copyTo(baselineOutputArray);
+ checkArray(baselineOutputArray, testOutputArray, Y, X, X);
+ }
+
+ public void testMultiInputKernelLaunch() {
+ s.forEach_goo(testInputAlloc, testInputAlloc2,
+ baselineOutputAlloc);
+ s.invoke_testMultiInput(testInputAlloc, testInputAlloc2,
+ testOutputAlloc);
+ testOutputAlloc.copyTo(testOutputArray);
+ baselineOutputAlloc.copyTo(baselineOutputArray);
+ checkArray(baselineOutputArray, testOutputArray, Y, X, X);
+ }
+
+ public void testKernelLaunchWithOptions() {
+ Script.LaunchOptions sc = new Script.LaunchOptions();
+ sc.setX(0, X);
+ sc.setY(0, Y / 2);
+ s.forEach_foo(testInputAlloc, baselineOutputAlloc, sc);
+ s.invoke_testLaunchOptions(testInputAlloc, testOutputAlloc, X, Y);
+ testOutputAlloc.copyTo(testOutputArray);
+ baselineOutputAlloc.copyTo(baselineOutputArray);
+ checkArray(baselineOutputArray, testOutputArray, Y, X, X);
+ }
+
+ public void testAllocationlessKernelLaunch() {
+ baselineOutputAlloc.copyFrom(testInputArray);
+ testOutputAlloc.copyFrom(testInputArray);
+
+ Script.LaunchOptions sc = new Script.LaunchOptions();
+ sc.setX(0, X);
+ sc.setY(0, Y);
+ s.set_gAllocOut(baselineOutputAlloc);
+ s.forEach_bar(sc);
+
+ s.invoke_testAllocationlessLaunch(testOutputAlloc, X, Y);
+
+ testOutputAlloc.copyTo(testOutputArray);
+ baselineOutputAlloc.copyTo(baselineOutputArray);
+ checkArray(baselineOutputArray, testOutputArray, Y, X, X);
+ }
+}
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/get_allocation.rs b/tests/tests/renderscript/src/android/renderscript/cts/get_allocation.rs
index 0149e6c..01cb47c 100644
--- a/tests/tests/renderscript/src/android/renderscript/cts/get_allocation.rs
+++ b/tests/tests/renderscript/src/android/renderscript/cts/get_allocation.rs
@@ -6,11 +6,11 @@
rs_allocation alloc_in;
rs_allocation alloc_out;
-void root(const int* in, int *out) {
- *out = *in;
+int __attribute__((kernel)) copy(int in) {
+ return in;
}
void start() {
alloc_in = rsGetAllocation(pointer);
- rsForEach(script, alloc_in, alloc_out);
+ rsForEach(copy, alloc_in, alloc_out);
}
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/shared.rsh b/tests/tests/renderscript/src/android/renderscript/cts/shared.rsh
index 2ad81fc..6fd78f6 100644
--- a/tests/tests/renderscript/src/android/renderscript/cts/shared.rsh
+++ b/tests/tests/renderscript/src/android/renderscript/cts/shared.rsh
@@ -21,6 +21,9 @@
\
} while (0)
+#define _RS_ASSERT_EQU(e1, e2) \
+ (((e1) != (e2)) ? (failed = true, rsDebug(#e1 " != " #e2, (e1), (e2)), false) : true)
+
/* These constants must match those in UnitTest.java */
static const int RS_MSG_TEST_PASSED = 100;
static const int RS_MSG_TEST_FAILED = 101;
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/single_source_alloc.rs b/tests/tests/renderscript/src/android/renderscript/cts/single_source_alloc.rs
new file mode 100644
index 0000000..2575d54
--- /dev/null
+++ b/tests/tests/renderscript/src/android/renderscript/cts/single_source_alloc.rs
@@ -0,0 +1,463 @@
+/*
+ * Copyright (C) 2015-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.
+ */
+
+#include "shared.rsh"
+
+int gDimX;
+int gDimY;
+int gDimZ;
+int gStart;
+static bool failed = false;
+
+// For each type, define 4 kernels, one per vector variant, that walk an
+// allocation and validate each cell. The value in a cell must be gStart +
+// "index-of-the-cell-starting-from-zero". For vector types, the 'x' field
+// must have this value. The expected values for 'y', 'z' and 'w' follow the
+// 'x' value in increments of one.
+//
+// 'z' will be zero for 2D and 1D allocations. 'y' will be zero for 1D
+// allocations.
+
+#define VERIFY_KERNEL(CT) \
+ void RS_KERNEL verify_##CT(CT in, int x, int y, int z) { \
+ int val = (gStart + x + y * gDimX + z * gDimY * gDimX); \
+ _RS_ASSERT_EQU(in, (CT) val); \
+ } \
+ void RS_KERNEL verify_##CT##2(CT##2 in, int x, int y, int z) { \
+ int val = (gStart + x + y * gDimX + z * gDimY * gDimX); \
+ _RS_ASSERT_EQU(in.x, (CT) val); \
+ _RS_ASSERT_EQU(in.y, (CT) (val + 1)); \
+ } \
+ void RS_KERNEL verify_##CT##3(CT##3 in, int x, int y, int z) { \
+ int val = (gStart + x + y * gDimX + z * gDimY * gDimX); \
+ _RS_ASSERT_EQU(in.x, (CT) val); \
+ _RS_ASSERT_EQU(in.y, (CT) (val + 1)); \
+ _RS_ASSERT_EQU(in.z, (CT) (val + 2)); \
+ } \
+ void RS_KERNEL verify_##CT##4(CT##4 in, int x, int y, int z) { \
+ int val = (gStart + x + y * gDimX + z * gDimY * gDimX); \
+ _RS_ASSERT_EQU(in.x, (CT) val); \
+ _RS_ASSERT_EQU(in.y, (CT) (val + 1)); \
+ _RS_ASSERT_EQU(in.z, (CT) (val + 2)); \
+ _RS_ASSERT_EQU(in.w, (CT) (val + 3)); \
+ } \
+
+VERIFY_KERNEL(float)
+VERIFY_KERNEL(double)
+VERIFY_KERNEL(char)
+VERIFY_KERNEL(short)
+VERIFY_KERNEL(int)
+VERIFY_KERNEL(long)
+VERIFY_KERNEL(uchar)
+VERIFY_KERNEL(ushort)
+VERIFY_KERNEL(uint)
+VERIFY_KERNEL(ulong)
+
+// Store to an allocation based on the vector size and dimensionality being
+// tested. SETELEMENTAT, STORE_TO_ALLOC capture the following variables from
+// the context where they get instantiated:
+// vecSize, gAlloc, val, x, y, z
+
+#define SETELEMENTAT(CT) \
+ if (gDimZ != 0) { \
+ rsSetElementAt_##CT(gAlloc, storeVal, x, y, z); \
+ } \
+ else if (gDimY != 0) { \
+ rsSetElementAt_##CT(gAlloc, storeVal, x, y); \
+ } \
+ else { \
+ rsSetElementAt_##CT(gAlloc, storeVal, x); \
+ }
+
+#define STORE_TO_ALLOC(RST, CT) \
+ case RST: \
+ switch (vecSize) { \
+ case 1: { \
+ CT storeVal = (CT) val; \
+ SETELEMENTAT(CT); \
+ } \
+ break; \
+ case 2: { \
+ CT##2 storeVal = {(CT) val, (CT) (val + 1)}; \
+ SETELEMENTAT(CT##2); \
+ } \
+ break; \
+ case 3: { \
+ CT##3 storeVal = {(CT) val, (CT) (val + 1), (CT) (val + 2)}; \
+ SETELEMENTAT(CT##3); \
+ } \
+ break; \
+ case 4: { \
+ CT##4 storeVal = {(CT) val, (CT) (val + 1), (CT) (val + 2), \
+ (CT) (val + 3)}; \
+ SETELEMENTAT(CT##4); \
+ } \
+ break; \
+ } \
+ break; \
+
+
+// Launch the verify_kernel based on the appropriate type and vector size.
+#define LAUNCH_VERIFY_KERNEL(RST, CT) \
+ case RST: \
+ if (vecSize == 1) rsForEach(verify_##CT, gAlloc); \
+ else if (vecSize == 2) rsForEach(verify_##CT##2, gAlloc); \
+ else if (vecSize == 3) rsForEach(verify_##CT##3, gAlloc); \
+ else if (vecSize == 4) rsForEach(verify_##CT##4, gAlloc); \
+ break;
+
+void checkAndSendResult() {
+ if (failed) {
+ rsDebug("Single Source Alloc Test Failed", 0);
+ rsSendToClientBlocking(RS_MSG_TEST_FAILED);
+ }
+ else {
+ rsDebug("Single Source Alloc Test Passed", 0);
+ rsSendToClientBlocking(RS_MSG_TEST_PASSED);
+ }
+}
+
+static void CreateAndTestAlloc(rs_data_type dt, int vecSize, int dimX, int dimY, int dimZ) {
+ failed = false;
+
+ if (dimZ != 0 && dimY == 0) {
+ _RS_ASSERT(false); // Invalid test
+ return;
+ }
+
+ if (dimX == 0) {
+ _RS_ASSERT(false); // Invalid test
+ return;
+ }
+
+ rs_element element;
+ rs_type type;
+ rs_allocation gAlloc;
+
+ // Create and validate the rs_element object
+ if (vecSize == 1)
+ element = rsCreateElement((rs_data_type) dt);
+ else
+ element = rsCreateVectorElement((rs_data_type) dt, vecSize);
+ _RS_ASSERT(rsIsObject(element));
+ if (!rsIsObject(element)) {
+ return;
+ }
+
+ // Create and validate the rs_type object
+ type = rsCreateType(element, dimX, dimY, dimZ);
+ _RS_ASSERT(rsIsObject(type));
+ if (!rsIsObject(type)) {
+ return;
+ }
+
+ // Create and validate the rs_allocation object
+ gAlloc = rsCreateAllocation(type);
+ if (!rsIsObject(gAlloc)) {
+ return;
+ }
+
+ // Handle RenderScript's distinction between Y or Z dimension being absent
+ // and having a size of 1
+ int zEnd = (dimZ != 0) ? dimZ: 1;
+ int yEnd = (dimY != 0) ? dimY: 1;
+ for (int z = 0; z < zEnd; z ++) {
+ for (int y = 0; y < yEnd; y ++) {
+ for (int x = 0; x < dimX; x ++) {
+ int val = gStart + (x + y * dimX + z * dimY * dimX);
+
+ // Store to a cell based on the type, vector size and
+ // dimensionality
+ switch (dt) {
+ STORE_TO_ALLOC(RS_TYPE_FLOAT_32, float);
+ STORE_TO_ALLOC(RS_TYPE_FLOAT_64, double);
+ STORE_TO_ALLOC(RS_TYPE_SIGNED_8, char);
+ STORE_TO_ALLOC(RS_TYPE_SIGNED_16, short);
+ STORE_TO_ALLOC(RS_TYPE_SIGNED_32, int);
+ STORE_TO_ALLOC(RS_TYPE_SIGNED_64, long);
+ STORE_TO_ALLOC(RS_TYPE_UNSIGNED_8, uchar);
+ STORE_TO_ALLOC(RS_TYPE_UNSIGNED_16, ushort);
+ STORE_TO_ALLOC(RS_TYPE_UNSIGNED_32, uint);
+ STORE_TO_ALLOC(RS_TYPE_UNSIGNED_64, ulong);
+ default:
+ // Invalid test
+ _RS_ASSERT(false);
+ break;
+ }
+ }
+ }
+ }
+
+ // Launch the appropriate verify_ kernel
+ switch (dt) {
+ LAUNCH_VERIFY_KERNEL(RS_TYPE_FLOAT_32, float);
+ LAUNCH_VERIFY_KERNEL(RS_TYPE_FLOAT_64, double);
+ LAUNCH_VERIFY_KERNEL(RS_TYPE_SIGNED_8, char);
+ LAUNCH_VERIFY_KERNEL(RS_TYPE_SIGNED_16, short);
+ LAUNCH_VERIFY_KERNEL(RS_TYPE_SIGNED_32, int);
+ LAUNCH_VERIFY_KERNEL(RS_TYPE_SIGNED_64, long);
+ LAUNCH_VERIFY_KERNEL(RS_TYPE_UNSIGNED_8, uchar);
+ LAUNCH_VERIFY_KERNEL(RS_TYPE_UNSIGNED_16, ushort);
+ LAUNCH_VERIFY_KERNEL(RS_TYPE_UNSIGNED_32, uint);
+ LAUNCH_VERIFY_KERNEL(RS_TYPE_UNSIGNED_64, ulong);
+
+ default:
+ // Invalid test
+ _RS_ASSERT(false);
+ break;
+ }
+}
+
+void TestAllocationCreationAndAccess() {
+ rs_data_type all_types[] = {
+ RS_TYPE_BOOLEAN,
+ // Bug 24862914: Uncomment the following line to add half once the bug is fixed
+ // RS_TYPE_FLOAT_16,
+ RS_TYPE_FLOAT_32,
+ RS_TYPE_FLOAT_64,
+ RS_TYPE_SIGNED_8,
+ RS_TYPE_SIGNED_16,
+ RS_TYPE_SIGNED_32,
+ RS_TYPE_SIGNED_64,
+ RS_TYPE_UNSIGNED_8,
+ RS_TYPE_UNSIGNED_16,
+ RS_TYPE_UNSIGNED_32,
+ RS_TYPE_UNSIGNED_64,
+ };
+
+ for (int i = 0; i < sizeof(all_types) / sizeof(all_types[0]); i++) {
+ for (int vecSize = 1; vecSize <= 4; vecSize ++) {
+ for (int nDims = 1; nDims <= 3; nDims ++) {
+ int dimY = nDims > 1 ? gDimY : 0;
+ int dimZ = nDims > 2 ? gDimZ : 0;
+ CreateAndTestAlloc(all_types[i], vecSize, gDimX, dimY, dimZ);
+ }
+ }
+ }
+
+ checkAndSendResult();
+}
+
+#define TEST_DATA_TYPE(dt, allowSimple, allowVector, allowPixel) { \
+ if (allowSimple) \
+ _RS_ASSERT(rsIsObject(rsCreateElement(dt))); \
+ else \
+ _RS_ASSERT(!rsIsObject(rsCreateElement(dt))); \
+ if (allowVector) \
+ _RS_ASSERT(rsIsObject(rsCreateVectorElement(dt, 3))); \
+ else \
+ _RS_ASSERT(!rsIsObject(rsCreateVectorElement(dt, 3))); \
+ if (allowPixel) \
+ _RS_ASSERT(rsIsObject(rsCreatePixelElement(dt, RS_KIND_PIXEL_DEPTH))); \
+ else \
+ _RS_ASSERT(!rsIsObject(rsCreatePixelElement(dt, RS_KIND_PIXEL_DEPTH)));\
+}
+
+#define TEST_SUPPORTED_PIXEL(dt, dk) { \
+ _RS_ASSERT(rsIsObject(rsCreatePixelElement(dt, dk))); \
+}
+
+#define TEST_UNSUPPORTED_PIXEL(dt, dk) { \
+ _RS_ASSERT(!rsIsObject(rsCreatePixelElement(dt, dk))); \
+}
+
+#define TEST_HELPER(suffix) { \
+ _RS_ASSERT(rsIsObject(rsCreateAllocation_##suffix(3))); \
+ _RS_ASSERT(rsIsObject(rsCreateAllocation_##suffix(3, 4))); \
+ _RS_ASSERT(rsIsObject(rsCreateAllocation_##suffix(3, 4, 5))); \
+ }
+
+#define TEST_HELPERS(CT) { \
+ TEST_HELPER(CT); \
+ TEST_HELPER(CT##2); \
+ TEST_HELPER(CT##3); \
+ TEST_HELPER(CT##4); \
+}
+
+void TestElementCreation() {
+ failed = false;
+
+ // vector_width must be at least 2
+ rs_element oneElt = rsCreateVectorElement(RS_TYPE_SIGNED_32, 1);
+ _RS_ASSERT(!rsIsObject(oneElt));
+
+ // vector_width must be at most 4
+ rs_element fiveElt = rsCreateVectorElement(RS_TYPE_SIGNED_32, 5);
+ _RS_ASSERT(!rsIsObject(fiveElt));
+
+ /////////////////////////////////////////////////////////////////
+ // Element validation
+ /////////////////////////////////////////////////////////////////
+ // These types are valid for scalar and vectors, but don't support pixel
+ TEST_DATA_TYPE(RS_TYPE_BOOLEAN, true, true, false);
+ TEST_DATA_TYPE(RS_TYPE_FLOAT_32, true, true, false);
+ TEST_DATA_TYPE(RS_TYPE_FLOAT_64, true, true, false);
+ TEST_DATA_TYPE(RS_TYPE_SIGNED_8, true, true, false);
+ TEST_DATA_TYPE(RS_TYPE_SIGNED_16, true, true, false);
+ TEST_DATA_TYPE(RS_TYPE_SIGNED_32, true, true, false);
+ TEST_DATA_TYPE(RS_TYPE_SIGNED_64, true, true, false);
+ TEST_DATA_TYPE(RS_TYPE_UNSIGNED_32, true, true, false);
+ TEST_DATA_TYPE(RS_TYPE_UNSIGNED_64, true, true, false);
+
+ // These types are valid only for scalars
+ TEST_DATA_TYPE(RS_TYPE_MATRIX_4X4, true, false, false);
+ TEST_DATA_TYPE(RS_TYPE_MATRIX_3X3, true, false, false);
+ TEST_DATA_TYPE(RS_TYPE_MATRIX_2X2, true, false, false);
+ TEST_DATA_TYPE(RS_TYPE_ELEMENT, true, false, false);
+ TEST_DATA_TYPE(RS_TYPE_TYPE, true, false, false);
+ TEST_DATA_TYPE(RS_TYPE_ALLOCATION, true, false, false);
+ TEST_DATA_TYPE(RS_TYPE_SCRIPT, true, false, false);
+
+ // U8, U16 are valid for scalar, vector and pixel
+ TEST_DATA_TYPE(RS_TYPE_UNSIGNED_8, true, true, true);
+ TEST_DATA_TYPE(RS_TYPE_UNSIGNED_16, true, true, true);
+
+ // These data types are only for pixels and a particular data_kind
+ TEST_SUPPORTED_PIXEL (RS_TYPE_UNSIGNED_5_6_5, RS_KIND_PIXEL_RGB);
+ TEST_UNSUPPORTED_PIXEL(RS_TYPE_UNSIGNED_5_6_5, RS_KIND_PIXEL_L);
+ TEST_SUPPORTED_PIXEL (RS_TYPE_UNSIGNED_5_5_5_1, RS_KIND_PIXEL_RGBA);
+ TEST_UNSUPPORTED_PIXEL(RS_TYPE_UNSIGNED_5_5_5_1, RS_KIND_PIXEL_L);
+ TEST_SUPPORTED_PIXEL (RS_TYPE_UNSIGNED_4_4_4_4, RS_KIND_PIXEL_RGBA);
+ TEST_UNSUPPORTED_PIXEL(RS_TYPE_UNSIGNED_4_4_4_4, RS_KIND_PIXEL_L);
+ TEST_SUPPORTED_PIXEL (RS_TYPE_UNSIGNED_16, RS_KIND_PIXEL_DEPTH);
+ TEST_UNSUPPORTED_PIXEL(RS_TYPE_UNSIGNED_4_4_4_4, RS_KIND_PIXEL_L);
+
+ // These data types are not supported from single-source
+ TEST_DATA_TYPE(RS_TYPE_NONE, false, false, false);
+ TEST_DATA_TYPE(RS_TYPE_SAMPLER, false, false, false);
+ TEST_DATA_TYPE(RS_TYPE_MESH, false, false, false);
+ TEST_DATA_TYPE(RS_TYPE_PROGRAM_FRAGMENT, false, false, false);
+ TEST_DATA_TYPE(RS_TYPE_PROGRAM_VERTEX, false, false, false);
+ TEST_DATA_TYPE(RS_TYPE_PROGRAM_RASTER, false, false, false);
+ TEST_DATA_TYPE(RS_TYPE_PROGRAM_STORE, false, false, false);
+ TEST_DATA_TYPE(RS_TYPE_FONT, false, false, false);
+ TEST_DATA_TYPE(RS_TYPE_INVALID, false, false, false);
+
+ checkAndSendResult();
+}
+
+void TestTypeCreation() {
+ failed = false;
+
+ /////////////////////////////////////////////////////////////////
+ // Test rs_type creation
+ /////////////////////////////////////////////////////////////////
+ rs_element I32_3 = rsCreateVectorElement(RS_TYPE_SIGNED_32, 3);
+
+ // Create 1D, 2D, 3D types
+ _RS_ASSERT(rsIsObject(rsCreateType(I32_3, 3)));
+ _RS_ASSERT(rsIsObject(rsCreateType(I32_3, 3, 4)));
+ _RS_ASSERT(rsIsObject(rsCreateType(I32_3, 3, 4, 5)));
+ _RS_ASSERT(rsIsObject(rsCreateType(I32_3, 0))); // x = 0 is allowed
+
+ // Invalid dimensionality
+ _RS_ASSERT(!rsIsObject(rsCreateType(I32_3, 0, 4))); // x is 0 but y isn't
+ _RS_ASSERT(!rsIsObject(rsCreateType(I32_3, 0, 4, 5))); // x is 0 but z isn't
+ _RS_ASSERT(!rsIsObject(rsCreateType(I32_3, 3, 0, 5))); // y is 0 but z isn't
+
+ // shape attributes
+ // Valid yuv_format
+ _RS_ASSERT(rsIsObject(rsCreateType(I32_3, 3, 4, 0, false, false,
+ RS_YUV_NONE)));
+ _RS_ASSERT(rsIsObject(rsCreateType(I32_3, 3, 4, 0, false, false,
+ RS_YUV_YV12)));
+ _RS_ASSERT(rsIsObject(rsCreateType(I32_3, 3, 4, 0, false, false,
+ RS_YUV_NV21)));
+ _RS_ASSERT(rsIsObject(rsCreateType(I32_3, 3, 4, 0, false, false,
+ RS_YUV_420_888)));
+
+ // Invalid yuv_format
+ _RS_ASSERT(!rsIsObject(rsCreateType(I32_3, 3, 4, 5, false, false, 1024)));
+ // yuv_format with 1D or 3D is invalid
+ _RS_ASSERT(!rsIsObject(rsCreateType(I32_3, 3, 0, 0, false, false,
+ RS_YUV_YV12)));
+ _RS_ASSERT(!rsIsObject(rsCreateType(I32_3, 3, 4, 5, false, false,
+ RS_YUV_YV12)));
+
+ // yuv_format with mipmaps or cubemap is invalid
+ _RS_ASSERT(!rsIsObject(rsCreateType(I32_3, 3, 4, 0, false, true,
+ RS_YUV_YV12)));
+ _RS_ASSERT(!rsIsObject(rsCreateType(I32_3, 3, 4, 0, true, false,
+ RS_YUV_YV12)));
+
+ // mipmaps with 1D or 3D is invalid
+ _RS_ASSERT(!rsIsObject(rsCreateType(I32_3, 3, 0, 0, true, false,
+ RS_YUV_NONE)));
+ _RS_ASSERT(!rsIsObject(rsCreateType(I32_3, 3, 4, 5, true, false,
+ RS_YUV_NONE)));
+
+ // cubemap with 1D or 3D is invalid
+ _RS_ASSERT(!rsIsObject(rsCreateType(I32_3, 3, 0, 0, false, true,
+ RS_YUV_NONE)));
+ _RS_ASSERT(!rsIsObject(rsCreateType(I32_3, 3, 4, 5, false, true,
+ RS_YUV_NONE)));
+
+ checkAndSendResult();
+}
+
+void TestAllocationCreationWithUsage() {
+ failed = false;
+
+ /////////////////////////////////////////////////////////////////
+ // Test rs_allocation creation
+ /////////////////////////////////////////////////////////////////
+ rs_element I32_3 = rsCreateVectorElement(RS_TYPE_SIGNED_32, 3);
+ rs_type I32_3_2D = rsCreateType(I32_3, 3, 4);
+
+ // Valid uses
+ _RS_ASSERT(rsIsObject(rsCreateAllocation(I32_3_2D)));
+ _RS_ASSERT(rsIsObject(rsCreateAllocation(I32_3_2D,\
+ (uint32_t) RS_ALLOCATION_USAGE_SCRIPT)));
+ _RS_ASSERT(rsIsObject(rsCreateAllocation(I32_3_2D,\
+ (uint32_t) RS_ALLOCATION_USAGE_GRAPHICS_TEXTURE)));
+ _RS_ASSERT(rsIsObject(rsCreateAllocation(I32_3_2D,
+ (uint32_t) RS_ALLOCATION_USAGE_GRAPHICS_TEXTURE |
+ RS_ALLOCATION_USAGE_SCRIPT)));
+
+ // Invalid uses
+ _RS_ASSERT(!rsIsObject(rsCreateAllocation(I32_3_2D,
+ (uint32_t) RS_ALLOCATION_USAGE_GRAPHICS_VERTEX)));
+ _RS_ASSERT(!rsIsObject(rsCreateAllocation(I32_3_2D,
+ (uint32_t) RS_ALLOCATION_USAGE_GRAPHICS_CONSTANTS)));
+ _RS_ASSERT(!rsIsObject(rsCreateAllocation(I32_3_2D,
+ (uint32_t) RS_ALLOCATION_USAGE_GRAPHICS_RENDER_TARGET)));
+ _RS_ASSERT(!rsIsObject(rsCreateAllocation(I32_3_2D,
+ (uint32_t) RS_ALLOCATION_USAGE_IO_INPUT)));
+ _RS_ASSERT(!rsIsObject(rsCreateAllocation(I32_3_2D,
+ (uint32_t) RS_ALLOCATION_USAGE_IO_OUTPUT)));
+ _RS_ASSERT(!rsIsObject(rsCreateAllocation(I32_3_2D,
+ (uint32_t) RS_ALLOCATION_USAGE_SHARED)));
+
+ checkAndSendResult();
+}
+
+void TestHelperFunctions() {
+ failed = false;
+
+ // Bug: 24862914: Add half once the bug is fixed
+ TEST_HELPERS(float);
+ TEST_HELPERS(double);
+ TEST_HELPERS(char);
+ TEST_HELPERS(short);
+ TEST_HELPERS(int);
+ TEST_HELPERS(long);
+ TEST_HELPERS(uchar);
+ TEST_HELPERS(ushort);
+ TEST_HELPERS(uint);
+ TEST_HELPERS(ulong);
+
+ checkAndSendResult();
+}
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/single_source_script.rs b/tests/tests/renderscript/src/android/renderscript/cts/single_source_script.rs
new file mode 100644
index 0000000..5e35aa3
--- /dev/null
+++ b/tests/tests/renderscript/src/android/renderscript/cts/single_source_script.rs
@@ -0,0 +1,60 @@
+/*
+ * Copyright (C) 2015-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.
+ */
+
+#include "shared.rsh"
+
+rs_allocation gAllocOut;
+
+int RS_KERNEL foo(int a) {
+ return a * 2;
+}
+
+int RS_KERNEL goo(int a, int b) {
+ return a + b;
+}
+
+void RS_KERNEL bar(int x, int y) {
+ int a = rsGetElementAt_int(gAllocOut, x, y);
+ a++;
+ rsSetElementAt_int(gAllocOut, a, x, y);
+}
+
+void testSingleInput(rs_allocation in, rs_allocation out) {
+ rsForEach(foo, in, out);
+}
+
+void testMultiInput(rs_allocation in1, rs_allocation in2, rs_allocation out) {
+ rsForEach(goo, in1, in2, out);
+}
+
+void testLaunchOptions(rs_allocation in, rs_allocation out, int dimX, int dimY) {
+ rs_script_call_t opts = {};
+ opts.xStart = 0;
+ opts.xEnd = dimX;
+ opts.yStart = 0;
+ opts.yEnd = dimY / 2;
+ rsForEachWithOptions(foo, &opts, in, out);
+}
+
+void testAllocationlessLaunch(rs_allocation inAndOut, int dimX, int dimY) {
+ gAllocOut = inAndOut;
+ rs_script_call_t opts = {};
+ opts.xStart = 0;
+ opts.xEnd = dimX;
+ opts.yStart = 0;
+ opts.yEnd = dimY;
+ rsForEachWithOptions(bar, &opts);
+}
diff --git a/tests/tests/transition/res/layout/scene6.xml b/tests/tests/transition/res/layout/scene6.xml
new file mode 100644
index 0000000..8cffee5
--- /dev/null
+++ b/tests/tests/transition/res/layout/scene6.xml
@@ -0,0 +1,38 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- 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.
+-->
+
+<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent"
+ android:transitionName="holder"
+ android:id="@+id/holder">
+ <View android:layout_width="30dp"
+ android:layout_height="30dp"
+ android:background="#0F0"
+ android:transitionName="green"
+ android:id="@+id/greenSquare" />
+ <View android:layout_width="30dp"
+ android:layout_height="30dp"
+ android:background="#F00"
+ android:transitionName="red"
+ android:id="@+id/redSquare"
+ android:layout_below="@+id/greenSquare" />
+ <TextView android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:transitionName="hello"
+ android:text="@string/hello"
+ android:id="@+id/hello"/>
+</RelativeLayout>
diff --git a/tests/tests/transition/src/android/transition/cts/BaseTransitionTest.java b/tests/tests/transition/src/android/transition/cts/BaseTransitionTest.java
index 13badf3..9f41f21 100644
--- a/tests/tests/transition/src/android/transition/cts/BaseTransitionTest.java
+++ b/tests/tests/transition/src/android/transition/cts/BaseTransitionTest.java
@@ -19,6 +19,7 @@
import android.animation.ObjectAnimator;
import android.test.ActivityInstrumentationTestCase2;
import android.transition.Scene;
+import android.transition.Transition;
import android.transition.TransitionManager;
import android.transition.TransitionValues;
import android.transition.Visibility;
@@ -38,7 +39,8 @@
protected FrameLayout mSceneRoot;
public float mAnimatedValue;
protected ArrayList<View> mTargets = new ArrayList<View>();
- protected TestTransition mTransition;
+ protected Transition mTransition;
+ protected SimpleTransitionListener mListener;
public BaseTransitionTest() {
super(TransitionActivity.class);
@@ -52,18 +54,21 @@
mSceneRoot = (FrameLayout) mActivity.findViewById(R.id.container);
mTargets.clear();
mTransition = new TestTransition();
+ mListener = new SimpleTransitionListener();
+ mTransition.addListener(mListener);
}
protected void waitForStart() throws InterruptedException {
- waitForStart(mTransition.listener);
+ waitForStart(mListener);
}
protected void waitForStart(SimpleTransitionListener listener) throws InterruptedException {
- assertTrue(listener.startLatch.await(100, TimeUnit.MILLISECONDS));
+ assertTrue(listener.startLatch.await(4000, TimeUnit.MILLISECONDS));
}
protected void waitForEnd(long waitMillis) throws InterruptedException {
- waitForEnd(mTransition.listener, waitMillis);
+ waitForEnd(mListener, waitMillis);
+ getInstrumentation().waitForIdleSync();
}
protected static void waitForEnd(SimpleTransitionListener listener, long waitMillis)
@@ -121,10 +126,8 @@
}
public class TestTransition extends Visibility {
- public final SimpleTransitionListener listener = new SimpleTransitionListener();
public TestTransition() {
- addListener(listener);
setDuration(200);
}
diff --git a/tests/tests/transition/src/android/transition/cts/ChangeBoundsTest.java b/tests/tests/transition/src/android/transition/cts/ChangeBoundsTest.java
new file mode 100644
index 0000000..a99f175
--- /dev/null
+++ b/tests/tests/transition/src/android/transition/cts/ChangeBoundsTest.java
@@ -0,0 +1,293 @@
+/*
+ * 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 android.transition.cts;
+
+import android.content.res.Resources;
+import android.graphics.Rect;
+import android.transition.ChangeBounds;
+import android.transition.cts.R;
+import android.util.TypedValue;
+import android.view.View;
+
+public class ChangeBoundsTest extends BaseTransitionTest {
+ private static final int SMALL_SQUARE_SIZE_DP = 10;
+ private static final int LARGE_SQUARE_SIZE_DP = 30;
+ private static final int SMALL_OFFSET_DP = 2;
+
+ ChangeBounds mChangeBounds;
+
+ public ChangeBoundsTest() {
+ }
+
+ @Override
+ protected void setUp() throws Exception {
+ super.setUp();
+ resetChangeBoundsTransition();
+ }
+
+ private void resetChangeBoundsTransition() {
+ mListener = new SimpleTransitionListener();
+ mChangeBounds = new ChangeBounds();
+ mChangeBounds.setDuration(400);
+ mChangeBounds.addListener(mListener);
+ mTransition = mChangeBounds;
+ }
+
+ public void testBasicChangeBounds() throws Throwable {
+ enterScene(R.layout.scene1);
+
+ validateInScene1();
+
+ startTransition(R.layout.scene6);
+
+ // now delay for at least a few frames before checking intermediate values:
+ Thread.sleep(150);
+ validateNormalIntermediate();
+ waitForEnd(400);
+
+ validateInScene6();
+ }
+
+ public void testResizeClip() throws Throwable {
+ mChangeBounds.setResizeClip(true);
+ enterScene(R.layout.scene1);
+
+ validateInScene1();
+
+ startTransition(R.layout.scene6);
+
+ // now delay for at least a few frames before checking intermediate values:
+ Thread.sleep(150);
+ validateClippedIntermediate();
+ waitForEnd(400);
+
+ validateInScene6();
+ }
+
+ public void testResizeClipSmaller() throws Throwable {
+ mChangeBounds.setResizeClip(true);
+ enterScene(R.layout.scene6);
+
+ validateInScene6();
+
+ startTransition(R.layout.scene1);
+
+ // now delay for at least a few frames before checking intermediate values:
+ Thread.sleep(150);
+ validateClippedIntermediate();
+ waitForEnd(400);
+
+ validateInScene1();
+ }
+
+ public void testInterruptSameDestination() throws Throwable {
+ enterScene(R.layout.scene1);
+
+ validateInScene1();
+
+ startTransition(R.layout.scene6);
+
+ // now delay for at least a few frames before interrupting the transition
+ Thread.sleep(150);
+ resetChangeBoundsTransition();
+ startTransition(R.layout.scene6);
+
+ assertFalse(isRestartingAnimation());
+ waitForEnd(500);
+ validateInScene6();
+ }
+
+ public void testInterruptSameDestinationResizeClip() throws Throwable {
+ mChangeBounds.setResizeClip(true);
+ enterScene(R.layout.scene1);
+
+ validateInScene1();
+
+ startTransition(R.layout.scene6);
+
+ // now delay for at least a few frames before interrupting the transition
+ Thread.sleep(150);
+
+ resetChangeBoundsTransition();
+ mChangeBounds.setResizeClip(true);
+ startTransition(R.layout.scene6);
+
+ assertFalse(isRestartingAnimation());
+ assertFalse(isRestartingClip());
+ waitForEnd(500);
+ validateInScene6();
+ }
+
+ public void testInterruptWithReverse() throws Throwable {
+ enterScene(R.layout.scene1);
+
+ validateInScene1();
+
+ startTransition(R.layout.scene6);
+
+ // now delay for at least a few frames before reversing
+ Thread.sleep(150);
+ // reverse the transition back to scene1
+ resetChangeBoundsTransition();
+ startTransition(R.layout.scene1);
+
+ assertFalse(isRestartingAnimation());
+ waitForEnd(500);
+ validateInScene1();
+ }
+
+ public void testInterruptWithReverseResizeClip() throws Throwable {
+ mChangeBounds.setResizeClip(true);
+ enterScene(R.layout.scene1);
+
+ validateInScene1();
+
+ startTransition(R.layout.scene6);
+
+ // now delay for at least a few frames before reversing
+ Thread.sleep(150);
+
+ // reverse the transition back to scene1
+ resetChangeBoundsTransition();
+ mChangeBounds.setResizeClip(true);
+ startTransition(R.layout.scene1);
+
+ assertFalse(isRestartingAnimation());
+ assertFalse(isRestartingClip());
+ waitForEnd(500);
+ validateInScene1();
+ }
+
+ private boolean isRestartingAnimation() {
+ View red = mActivity.findViewById(R.id.redSquare);
+ View green = mActivity.findViewById(R.id.greenSquare);
+ Resources resources = mActivity.getResources();
+ float closestDistance = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP,
+ SMALL_OFFSET_DP, resources.getDisplayMetrics());
+ return red.getTop() < closestDistance || green.getTop() < closestDistance;
+ }
+
+ private boolean isRestartingClip() {
+ Resources resources = mActivity.getResources();
+ float smallDim = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP,
+ SMALL_SQUARE_SIZE_DP + SMALL_OFFSET_DP, resources.getDisplayMetrics());
+ float largeDim = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP,
+ LARGE_SQUARE_SIZE_DP - SMALL_OFFSET_DP, resources.getDisplayMetrics());
+
+ View red = mActivity.findViewById(R.id.redSquare);
+ Rect redClip = red.getClipBounds();
+ View green = mActivity.findViewById(R.id.greenSquare);
+ Rect greenClip = green.getClipBounds();
+ return redClip == null || redClip.width() < smallDim || redClip.width() > largeDim ||
+ greenClip == null || greenClip.width() < smallDim || greenClip.width() > largeDim;
+ }
+
+ private void validateInScene1() {
+ validateViewPlacement(R.id.redSquare, R.id.greenSquare, SMALL_SQUARE_SIZE_DP);
+ }
+
+ private void validateInScene6() {
+ validateViewPlacement(R.id.greenSquare, R.id.redSquare, LARGE_SQUARE_SIZE_DP);
+ }
+
+ private void validateViewPlacement(int topViewResource, int bottomViewResource, int dim) {
+ Resources resources = mActivity.getResources();
+ float expectedDim = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, dim,
+ resources.getDisplayMetrics());
+ View aboveSquare = mActivity.findViewById(topViewResource);
+ assertEquals(0, aboveSquare.getLeft());
+ assertEquals(0, aboveSquare.getTop());
+ assertTrue(aboveSquare.getRight() != 0);
+ final int aboveSquareBottom = aboveSquare.getBottom();
+ assertTrue(aboveSquareBottom != 0);
+
+ View belowSquare = mActivity.findViewById(bottomViewResource);
+ assertEquals(0, belowSquare.getLeft());
+ assertEquals(aboveSquareBottom, belowSquare.getTop());
+ assertEquals(aboveSquareBottom + aboveSquare.getHeight(), belowSquare.getBottom());
+ assertEquals(aboveSquare.getRight(), belowSquare.getRight());
+
+ assertTrue(isWithinAPixel(expectedDim, aboveSquare.getHeight()));
+ assertTrue(isWithinAPixel(expectedDim, aboveSquare.getWidth()));
+ assertTrue(isWithinAPixel(expectedDim, belowSquare.getHeight()));
+ assertTrue(isWithinAPixel(expectedDim, belowSquare.getWidth()));
+
+ assertNull(aboveSquare.getClipBounds());
+ assertNull(belowSquare.getClipBounds());
+ }
+
+ private void validateIntermediatePosition() {
+ Resources resources = mActivity.getResources();
+ float smallDim = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP,
+ SMALL_SQUARE_SIZE_DP, resources.getDisplayMetrics());
+ float largeDim = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP,
+ LARGE_SQUARE_SIZE_DP, resources.getDisplayMetrics());
+
+ View redSquare = mActivity.findViewById(R.id.redSquare);
+ View greenSquare = mActivity.findViewById(R.id.greenSquare);
+ assertTrue(redSquare.getTop() != 0);
+ assertTrue(greenSquare.getTop() != 0);
+ assertFalse(isWithinAPixel(smallDim, redSquare.getTop()));
+ assertFalse(isWithinAPixel(largeDim, redSquare.getTop()));
+ assertFalse(isWithinAPixel(smallDim, greenSquare.getTop()));
+ assertFalse(isWithinAPixel(largeDim, greenSquare.getTop()));
+ }
+
+ private void validateClippedIntermediate() {
+ validateIntermediatePosition();
+ Resources resources = mActivity.getResources();
+ float largeDim = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP,
+ LARGE_SQUARE_SIZE_DP, resources.getDisplayMetrics());
+ View redSquare = mActivity.findViewById(R.id.redSquare);
+ View greenSquare = mActivity.findViewById(R.id.greenSquare);
+
+ assertTrue(isWithinAPixel(largeDim, redSquare.getWidth()));
+ assertTrue(isWithinAPixel(largeDim, redSquare.getHeight()));
+ assertTrue(isWithinAPixel(largeDim, greenSquare.getWidth()));
+ assertTrue(isWithinAPixel(largeDim, greenSquare.getHeight()));
+
+ assertNotNull(redSquare.getClipBounds());
+ assertNotNull(greenSquare.getClipBounds());
+ }
+
+ private void validateNormalIntermediate() {
+ validateIntermediatePosition();
+ Resources resources = mActivity.getResources();
+ float smallDim = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP,
+ SMALL_SQUARE_SIZE_DP, resources.getDisplayMetrics());
+ float largeDim = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP,
+ LARGE_SQUARE_SIZE_DP, resources.getDisplayMetrics());
+ View redSquare = mActivity.findViewById(R.id.redSquare);
+ View greenSquare = mActivity.findViewById(R.id.greenSquare);
+ assertFalse(isWithinAPixel(smallDim, redSquare.getWidth()));
+ assertFalse(isWithinAPixel(smallDim, redSquare.getHeight()));
+ assertFalse(isWithinAPixel(largeDim, redSquare.getWidth()));
+ assertFalse(isWithinAPixel(largeDim, redSquare.getHeight()));
+
+ assertFalse(isWithinAPixel(smallDim, greenSquare.getWidth()));
+ assertFalse(isWithinAPixel(smallDim, greenSquare.getHeight()));
+ assertFalse(isWithinAPixel(largeDim, greenSquare.getWidth()));
+ assertFalse(isWithinAPixel(largeDim, greenSquare.getHeight()));
+
+ assertNull(redSquare.getClipBounds());
+ assertNull(greenSquare.getClipBounds());
+ }
+
+ private static boolean isWithinAPixel(float expectedDim, int dim) {
+ return (Math.abs(dim - expectedDim) < 1);
+ }
+}
+
diff --git a/tests/tests/transition/src/android/transition/cts/TransitionManagerTest.java b/tests/tests/transition/src/android/transition/cts/TransitionManagerTest.java
index 8e545ec..9eacd1b 100644
--- a/tests/tests/transition/src/android/transition/cts/TransitionManagerTest.java
+++ b/tests/tests/transition/src/android/transition/cts/TransitionManagerTest.java
@@ -42,12 +42,12 @@
waitForStart();
waitForEnd(300);
- assertEquals(1, mTransition.listener.resumeLatch.getCount());
- assertEquals(1, mTransition.listener.pauseLatch.getCount());
- assertEquals(1, mTransition.listener.cancelLatch.getCount());
- assertNotNull(mTransition.listener.transition);
- assertEquals(TestTransition.class, mTransition.listener.transition.getClass());
- assertTrue(mTransition != mTransition.listener.transition);
+ assertEquals(1, mListener.resumeLatch.getCount());
+ assertEquals(1, mListener.pauseLatch.getCount());
+ assertEquals(1, mListener.cancelLatch.getCount());
+ assertNotNull(mListener.transition);
+ assertEquals(TestTransition.class, mListener.transition.getClass());
+ assertTrue(mTransition != mListener.transition);
runTestOnUiThread(new Runnable() {
@Override
public void run() {
@@ -62,12 +62,12 @@
waitForStart();
waitForEnd(300);
- assertEquals(1, mTransition.listener.resumeLatch.getCount());
- assertEquals(1, mTransition.listener.pauseLatch.getCount());
- assertEquals(1, mTransition.listener.cancelLatch.getCount());
- assertNotNull(mTransition.listener.transition);
- assertEquals(TestTransition.class, mTransition.listener.transition.getClass());
- assertTrue(mTransition != mTransition.listener.transition);
+ assertEquals(1, mListener.resumeLatch.getCount());
+ assertEquals(1, mListener.pauseLatch.getCount());
+ assertEquals(1, mListener.cancelLatch.getCount());
+ assertNotNull(mListener.transition);
+ assertEquals(TestTransition.class, mListener.transition.getClass());
+ assertTrue(mTransition != mListener.transition);
runTestOnUiThread(new Runnable() {
@Override
public void run() {
@@ -91,24 +91,24 @@
waitForStart();
waitForEnd(300);
- assertEquals(1, mTransition.listener.resumeLatch.getCount());
- assertEquals(1, mTransition.listener.pauseLatch.getCount());
- assertEquals(1, mTransition.listener.cancelLatch.getCount());
- assertNotNull(mTransition.listener.transition);
- assertEquals(TestTransition.class, mTransition.listener.transition.getClass());
- assertTrue(mTransition != mTransition.listener.transition);
+ assertEquals(1, mListener.resumeLatch.getCount());
+ assertEquals(1, mListener.pauseLatch.getCount());
+ assertEquals(1, mListener.cancelLatch.getCount());
+ assertNotNull(mListener.transition);
+ assertEquals(TestTransition.class, mListener.transition.getClass());
+ assertTrue(mTransition != mListener.transition);
runTestOnUiThread(new Runnable() {
@Override
public void run() {
- mTransition.listener.startLatch = new CountDownLatch(1);
- mTransition.listener.endLatch = new CountDownLatch(1);
+ mListener.startLatch = new CountDownLatch(1);
+ mListener.endLatch = new CountDownLatch(1);
assertNotNull(mActivity.findViewById(R.id.redSquare));
assertNotNull(mActivity.findViewById(R.id.greenSquare));
Scene scene = Scene.getSceneForLayout(mSceneRoot, R.layout.scene2, mActivity);
transitionManager.transitionTo(scene);
}
});
- assertFalse(mTransition.listener.startLatch.await(50, TimeUnit.MILLISECONDS));
+ assertFalse(mListener.startLatch.await(50, TimeUnit.MILLISECONDS));
endTransition();
}
@@ -126,7 +126,7 @@
transitionManager.transitionTo(scenes[0]);
}
});
- assertFalse(mTransition.listener.startLatch.await(100, TimeUnit.MILLISECONDS));
+ assertFalse(mListener.startLatch.await(100, TimeUnit.MILLISECONDS));
runTestOnUiThread(new Runnable() {
@Override
@@ -137,21 +137,21 @@
waitForStart();
waitForEnd(300);
- assertEquals(1, mTransition.listener.resumeLatch.getCount());
- assertEquals(1, mTransition.listener.pauseLatch.getCount());
- assertEquals(1, mTransition.listener.cancelLatch.getCount());
- assertNotNull(mTransition.listener.transition);
- assertEquals(TestTransition.class, mTransition.listener.transition.getClass());
- assertTrue(mTransition != mTransition.listener.transition);
+ assertEquals(1, mListener.resumeLatch.getCount());
+ assertEquals(1, mListener.pauseLatch.getCount());
+ assertEquals(1, mListener.cancelLatch.getCount());
+ assertNotNull(mListener.transition);
+ assertEquals(TestTransition.class, mListener.transition.getClass());
+ assertTrue(mTransition != mListener.transition);
runTestOnUiThread(new Runnable() {
@Override
public void run() {
- mTransition.listener.startLatch = new CountDownLatch(1);
- mTransition.listener.endLatch = new CountDownLatch(1);
+ mListener.startLatch = new CountDownLatch(1);
+ mListener.endLatch = new CountDownLatch(1);
transitionManager.transitionTo(scenes[2]);
}
});
- assertFalse(mTransition.listener.startLatch.await(50, TimeUnit.MILLISECONDS));
+ assertFalse(mListener.startLatch.await(50, TimeUnit.MILLISECONDS));
endTransition();
}
@@ -175,8 +175,8 @@
TransitionManager.endTransitions(mSceneRoot);
}
});
- assertFalse(mTransition.listener.startLatch.await(100, TimeUnit.MILLISECONDS));
- assertFalse(mTransition.listener.endLatch.await(10, TimeUnit.MILLISECONDS));
+ assertFalse(mListener.startLatch.await(100, TimeUnit.MILLISECONDS));
+ assertFalse(mListener.endLatch.await(10, TimeUnit.MILLISECONDS));
}
}
diff --git a/tests/tests/transition/src/android/transition/cts/TransitionTest.java b/tests/tests/transition/src/android/transition/cts/TransitionTest.java
index 71c85c5..e87be84 100644
--- a/tests/tests/transition/src/android/transition/cts/TransitionTest.java
+++ b/tests/tests/transition/src/android/transition/cts/TransitionTest.java
@@ -54,11 +54,11 @@
waitForStart(listener2);
- assertEquals(0, mTransition.listener.pauseLatch.getCount());
- assertEquals(0, mTransition.listener.resumeLatch.getCount());
- assertEquals(1, mTransition.listener.cancelLatch.getCount());
- assertEquals(1, mTransition.listener.endLatch.getCount());
- assertEquals(0, mTransition.listener.startLatch.getCount());
+ assertEquals(0, mListener.pauseLatch.getCount());
+ assertEquals(0, mListener.resumeLatch.getCount());
+ assertEquals(1, mListener.cancelLatch.getCount());
+ assertEquals(1, mListener.endLatch.getCount());
+ assertEquals(0, mListener.startLatch.getCount());
assertEquals(1, listener2.pauseLatch.getCount());
assertEquals(1, listener2.resumeLatch.getCount());
@@ -75,11 +75,11 @@
runTestOnUiThread(new Runnable() {
@Override
public void run() {
- mTransition.removeListener(mTransition.listener);
+ mTransition.removeListener(mListener);
}
});
- assertFalse(mTransition.listener.endLatch.await(250, TimeUnit.MILLISECONDS));
+ assertFalse(mListener.endLatch.await(250, TimeUnit.MILLISECONDS));
}
public void testAddTargetId() throws Throwable {
diff --git a/tests/tests/view/Android.mk b/tests/tests/view/Android.mk
index 24a351f..e57e10e 100644
--- a/tests/tests/view/Android.mk
+++ b/tests/tests/view/Android.mk
@@ -26,7 +26,7 @@
LOCAL_JAVA_LIBRARIES := android.test.runner
-LOCAL_STATIC_JAVA_LIBRARIES := ctsdeviceutil ctstestrunner
+LOCAL_STATIC_JAVA_LIBRARIES := ctsdeviceutil ctstestrunner mockito-target
LOCAL_SRC_FILES := $(call all-java-files-under, src)
diff --git a/tests/tests/view/res/layout/focus_finder_layout.xml b/tests/tests/view/res/layout/focus_finder_layout.xml
index 0502fd8..610ffc8 100644
--- a/tests/tests/view/res/layout/focus_finder_layout.xml
+++ b/tests/tests/view/res/layout/focus_finder_layout.xml
@@ -22,21 +22,21 @@
android:layout_centerInParent="true">
<TableRow>
<android.view.cts.TestButton android:id="@+id/top_left_button"
- android:layout_width="match_parent"
+ android:layout_width="60dp"
android:layout_height="match_parent"
android:text="TL" />
<android.view.cts.TestButton android:id="@+id/top_right_button"
- android:layout_width="match_parent"
+ android:layout_width="60dp"
android:layout_height="match_parent"
android:text="TR" />
</TableRow>
<TableRow>
<android.view.cts.TestButton android:id="@+id/bottom_left_button"
- android:layout_width="match_parent"
+ android:layout_width="60dp"
android:layout_height="match_parent"
android:text="BL" />
<android.view.cts.TestButton android:id="@+id/bottom_right_button"
- android:layout_width="match_parent"
+ android:layout_width="60dp"
android:layout_height="match_parent"
android:text="BR" />
</TableRow>
diff --git a/tests/tests/view/src/android/view/cts/ViewGroupTest.java b/tests/tests/view/src/android/view/cts/ViewGroupTest.java
index f688d1f..10e743a 100644
--- a/tests/tests/view/src/android/view/cts/ViewGroupTest.java
+++ b/tests/tests/view/src/android/view/cts/ViewGroupTest.java
@@ -16,20 +16,18 @@
package android.view.cts;
-import android.view.cts.util.XmlUtils;
-
-
import android.content.Context;
import android.content.Intent;
-import android.cts.util.CTSResult;
import android.content.res.XmlResourceParser;
+import android.cts.util.CTSResult;
import android.graphics.Bitmap;
+import android.graphics.Bitmap.Config;
import android.graphics.Canvas;
import android.graphics.Point;
import android.graphics.Rect;
import android.graphics.Region;
-import android.graphics.Bitmap.Config;
import android.graphics.drawable.BitmapDrawable;
+import android.os.Build;
import android.os.Parcelable;
import android.os.SystemClock;
import android.test.InstrumentationTestCase;
@@ -44,22 +42,22 @@
import android.view.MenuItem;
import android.view.MotionEvent;
import android.view.View;
-import android.view.ViewGroup;
-import android.view.WindowManager;
import android.view.View.BaseSavedState;
import android.view.View.MeasureSpec;
import android.view.View.OnTouchListener;
+import android.view.ViewGroup;
import android.view.ViewGroup.LayoutParams;
import android.view.ViewGroup.OnHierarchyChangeListener;
+import android.view.WindowManager;
import android.view.animation.AlphaAnimation;
import android.view.animation.Animation;
+import android.view.animation.Animation.AnimationListener;
import android.view.animation.LayoutAnimationController;
import android.view.animation.RotateAnimation;
import android.view.animation.Transformation;
-import android.view.animation.Animation.AnimationListener;
+import android.view.cts.util.XmlUtils;
import android.widget.TextView;
-import java.lang.IndexOutOfBoundsException;
import java.util.ArrayList;
public class ViewGroupTest extends InstrumentationTestCase implements CTSResult{
@@ -536,6 +534,7 @@
MockTextView textView = new MockTextView(mContext);
mMotionEvent = null;
textView.setOnTouchListener(new OnTouchListener() {
+ @Override
public boolean onTouch(View v, MotionEvent event) {
mMotionEvent = event;
return true;
@@ -812,12 +811,15 @@
AnimationListener al = new AnimationListener() {
+ @Override
public void onAnimationEnd(Animation animation) {
}
+ @Override
public void onAnimationRepeat(Animation animation) {
}
+ @Override
public void onAnimationStart(Animation animation) {
}
};
@@ -1009,6 +1011,18 @@
assertEquals(2, rect.top);
assertEquals(1, rect.left);
assertEquals(1, rect.right);
+
+ if (Build.VERSION.SDK_INT > Build.VERSION_CODES.M || Build.VERSION.CODENAME.equals("N")) {
+ textView.setTranslationX(2);
+ textView.setTranslationY(1);
+
+ rect.setEmpty();
+ vg.offsetDescendantRectToMyCoords(textView, rect);
+ assertEquals(3, rect.bottom);
+ assertEquals(3, rect.top);
+ assertEquals(3, rect.left);
+ assertEquals(3, rect.right);
+ }
}
public void testOffsetRectIntoDescendantCoords() {
@@ -1032,6 +1046,18 @@
assertEquals(4, rect.top);
assertEquals(4, rect.left);
assertEquals(6, rect.right);
+
+ if (Build.VERSION.SDK_INT > Build.VERSION_CODES.M || Build.VERSION.CODENAME.equals("N")) {
+ textView.setTranslationX(2);
+ textView.setTranslationY(1);
+
+ rect.set(5, 6, 7, 8);
+ vg.offsetRectIntoDescendantCoords(textView, rect);
+ assertEquals(5, rect.bottom);
+ assertEquals(3, rect.top);
+ assertEquals(2, rect.left);
+ assertEquals(4, rect.right);
+ }
}
public void testOnAnimationEnd() {
@@ -1172,9 +1198,11 @@
public View sParent;
public View sChild;
+ @Override
public void onChildViewAdded(View parent, View child) {
}
+ @Override
public void onChildViewRemoved(View parent, View child) {
sParent = parent;
sChild = child;
@@ -2021,7 +2049,6 @@
public int debugDepth;
public int drawChildCalledTime;
public Canvas canvas;
- public boolean isInvalidateChildInParentCalled;
public boolean isDrawableStateChangedCalled;
public boolean isRequestLayoutCalled;
public boolean isOnLayoutCalled;
@@ -2420,6 +2447,7 @@
}
}
+ @Override
public void setResult(int resultCode) {
synchronized (mSync) {
mSync.mHasNotify = true;
diff --git a/tests/tests/view/src/android/view/cts/ViewTest.java b/tests/tests/view/src/android/view/cts/ViewTest.java
index 0191072..18868e4 100644
--- a/tests/tests/view/src/android/view/cts/ViewTest.java
+++ b/tests/tests/view/src/android/view/cts/ViewTest.java
@@ -16,8 +16,8 @@
package android.view.cts;
-import android.view.ViewTreeObserver;
-import android.view.cts.R;
+import static org.mockito.Mockito.*;
+
import com.android.internal.view.menu.ContextMenuBuilder;
import android.content.Context;
@@ -74,10 +74,12 @@
import android.view.ViewConfiguration;
import android.view.ViewGroup;
import android.view.ViewParent;
+import android.view.ViewTreeObserver;
import android.view.WindowManager;
import android.view.accessibility.AccessibilityEvent;
import android.view.animation.AlphaAnimation;
import android.view.animation.Animation;
+import android.view.cts.R;
import android.view.inputmethod.EditorInfo;
import android.view.inputmethod.InputConnection;
import android.view.inputmethod.InputMethodManager;
@@ -160,6 +162,7 @@
final CountDownLatch latch = new CountDownLatch(1);
sCtorException = null;
new Thread() {
+ @Override
public void run() {
final Class<?>[] ctorSignature = new Class[] {
Context.class, AttributeSet.class};
@@ -258,6 +261,7 @@
// check whether it has started
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.startAnimation(animation);
}
@@ -326,6 +330,7 @@
final int WRAP_CONTENT = ViewGroup.LayoutParams.WRAP_CONTENT;
final int btnHeight = view.getHeight()/3;
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
mActivity.addContentView(button,
new LinearLayout.LayoutParams(WRAP_CONTENT, btnHeight));
@@ -407,6 +412,7 @@
assertEquals(-1, mockView.getOldWOnSizeChanged());
assertEquals(-1, mockView.getOldHOnSizeChanged());
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
viewGroup.addView(mockView);
}
@@ -425,6 +431,7 @@
int oldh = view.getHeight();
final LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(200, 100);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setLayoutParams(layoutParams);
}
@@ -499,6 +506,7 @@
view.reset();
assertFalse(view.hasCalledOnLayout());
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.requestLayout();
}
@@ -647,6 +655,7 @@
// width is 0
final LinearLayout.LayoutParams layoutParams1 = new LinearLayout.LayoutParams(0, 300);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setLayoutParams(layoutParams1);
}
@@ -657,6 +666,7 @@
// height is -10
final LinearLayout.LayoutParams layoutParams2 = new LinearLayout.LayoutParams(200, -10);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setLayoutParams(layoutParams2);
}
@@ -671,6 +681,7 @@
final LinearLayout.LayoutParams layoutParams3 =
new LinearLayout.LayoutParams(halfWidth, halfHeight);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setLayoutParams(layoutParams3);
}
@@ -701,6 +712,7 @@
// width is 0
final LinearLayout.LayoutParams layoutParams1 = new LinearLayout.LayoutParams(0, 300);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setLayoutParams(layoutParams1);
}
@@ -711,6 +723,7 @@
// height is -10
final LinearLayout.LayoutParams layoutParams2 = new LinearLayout.LayoutParams(200, -10);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setLayoutParams(layoutParams2);
}
@@ -725,6 +738,7 @@
final LinearLayout.LayoutParams layoutParams3 =
new LinearLayout.LayoutParams(halfWidth, halfHeight);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setLayoutParams(layoutParams3);
}
@@ -745,6 +759,7 @@
assertEquals(view.getWidth(), view.computeHorizontalScrollExtent());
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.scrollTo(12, 0);
}
@@ -755,6 +770,7 @@
assertEquals(view.getWidth(), view.computeHorizontalScrollExtent());
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.scrollBy(12, 0);
}
@@ -767,6 +783,7 @@
int newWidth = 200;
final LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(newWidth, 100);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setLayoutParams(layoutParams);
}
@@ -787,6 +804,7 @@
final int scrollToY = 34;
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.scrollTo(0, scrollToY);
}
@@ -798,6 +816,7 @@
final int scrollByY = 200;
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.scrollBy(0, scrollByY);
}
@@ -810,6 +829,7 @@
int newHeight = 333;
final LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(200, newHeight);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setLayoutParams(layoutParams);
}
@@ -830,6 +850,7 @@
assertEquals(0f, view.getBottomFadingEdgeStrength());
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.scrollTo(10, 10);
}
@@ -841,6 +862,7 @@
assertEquals(0f, view.getBottomFadingEdgeStrength());
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.scrollTo(-10, -10);
}
@@ -997,7 +1019,7 @@
public void testAddFocusables() {
View view = new View(mActivity);
- ArrayList<View> viewList = new ArrayList<View>();
+ ArrayList<View> viewList = new ArrayList<>();
// view is not focusable
assertFalse(view.isFocusable());
@@ -1307,6 +1329,24 @@
assertTrue(mMockParent.hasShowContextMenuForChild());
}
+ public void testShowContextMenuXY() {
+ MockViewParent parent = new MockViewParent(mActivity);
+ MockView view = new MockView(mActivity);
+
+ assertNull(view.getParent());
+ try {
+ view.showContextMenu(0, 0);
+ fail("should throw NullPointerException");
+ } catch (NullPointerException e) {
+ }
+
+ view.setParent(parent);
+ assertFalse(parent.hasShowContextMenuForChildXY());
+
+ assertFalse(view.showContextMenu(0, 0));
+ assertTrue(parent.hasShowContextMenuForChildXY());
+ }
+
public void testFitSystemWindows() {
final XmlResourceParser parser = mResources.getLayout(R.layout.view_layout);
final AttributeSet attrs = Xml.asAttributeSet(parser);
@@ -1375,6 +1415,41 @@
assertTrue(listener.hasOnLongClick());
}
+ public void testPerformLongClickXY() {
+ MockViewParent parent = new MockViewParent(mActivity);
+ MockView view = new MockView(mActivity);
+
+ try {
+ view.performLongClick(0, 0);
+ fail("should throw NullPointerException");
+ } catch (NullPointerException e) {
+ }
+
+ parent.addView(view);
+ assertFalse(parent.hasShowContextMenuForChildXY());
+
+ // Verify default context menu behavior.
+ assertFalse(view.performLongClick(0, 0));
+ assertTrue(parent.hasShowContextMenuForChildXY());
+ }
+
+ public void testPerformLongClickXY_WithListener() {
+ OnLongClickListener listener = mock(OnLongClickListener.class);
+ MockViewParent parent = new MockViewParent(mActivity);
+ MockView view = new MockView(mActivity);
+
+ view.setOnLongClickListener(listener);
+ verify(listener, never()).onLongClick(any(View.class));
+
+ parent.addView(view);
+ assertFalse(parent.hasShowContextMenuForChildXY());
+
+ // Verify listener is preferred over default context menu.
+ assertTrue(view.performLongClick(0, 0));
+ assertFalse(parent.hasShowContextMenuForChildXY());
+ verify(listener).onLongClick(view);
+ }
+
public void testSetOnLongClickListener() {
MockView view = new MockView(mActivity);
view.setParent(mMockParent);
@@ -1503,6 +1578,7 @@
view.reset();
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.requestLayout();
}
@@ -1515,6 +1591,7 @@
view.reset();
final LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(200, 100);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setLayoutParams(layoutParams);
}
@@ -1572,6 +1649,7 @@
View view = new View(mActivity);
Drawable drawable = new StateListDrawable();
Runnable what = new Runnable() {
+ @Override
public void run() {
// do nothing
}
@@ -1599,6 +1677,7 @@
View view = new View(mActivity);
Drawable drawable = new StateListDrawable();
Runnable what = new Runnable() {
+ @Override
public void run() {
// do nothing
}
@@ -1759,7 +1838,6 @@
}
public void testGetLocationOnScreen() {
- View view = new View(mActivity);
int[] location = new int[] { -1, -1 };
// mAttachInfo is not null
@@ -1792,7 +1870,7 @@
public void testAddTouchables() {
View view = new View(mActivity);
- ArrayList<View> result = new ArrayList<View>();
+ ArrayList<View> result = new ArrayList<>();
assertEquals(0, result.size());
view.addTouchables(result);
@@ -1938,6 +2016,7 @@
public void testOnKeyShortcut() throws Throwable {
final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setFocusable(true);
view.requestFocus();
@@ -1956,6 +2035,7 @@
public void testOnKeyMultiple() throws Throwable {
final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setFocusable(true);
}
@@ -1985,6 +2065,7 @@
public void testOnTrackballEvent() throws Throwable {
final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setEnabled(true);
view.setFocusable(true);
@@ -2036,6 +2117,7 @@
public void testDispatchUnhandledMove() throws Throwable {
final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setFocusable(true);
view.requestFocus();
@@ -2054,6 +2136,7 @@
final ViewGroup viewGroup = (ViewGroup) mActivity.findViewById(R.id.viewlayout_root);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
viewGroup.addView(mockView);
}
@@ -2063,6 +2146,7 @@
mockView.reset();
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
getActivity().setVisible(false);
}
@@ -2073,6 +2157,7 @@
mockView.reset();
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
getActivity().setVisible(true);
}
@@ -2083,6 +2168,7 @@
mockView.reset();
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
viewGroup.removeView(mockView);
}
@@ -2103,6 +2189,7 @@
final LinearLayout.LayoutParams layoutParams1 = new LinearLayout.LayoutParams(0, 300);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setLayoutParams(layoutParams1);
}
@@ -2112,6 +2199,7 @@
final LinearLayout.LayoutParams layoutParams2 = new LinearLayout.LayoutParams(200, -10);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setLayoutParams(layoutParams2);
}
@@ -2126,6 +2214,7 @@
final LinearLayout.LayoutParams layoutParams3 =
new LinearLayout.LayoutParams(halfWidth, halfHeight);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setLayoutParams(layoutParams3);
view.scrollTo(20, -30);
@@ -2184,7 +2273,7 @@
public void testSaveAndRestoreHierarchyState() {
int viewId = R.id.mock_view;
MockView view = (MockView) mActivity.findViewById(viewId);
- SparseArray<Parcelable> container = new SparseArray<Parcelable>();
+ SparseArray<Parcelable> container = new SparseArray<>();
view.saveHierarchyState(container);
assertTrue(view.hasCalledDispatchSaveInstanceState());
assertTrue(view.hasCalledOnSaveInstanceState());
@@ -2228,6 +2317,7 @@
public void testOnKeyDownOrUp() throws Throwable {
final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setFocusable(true);
view.requestFocus();
@@ -2254,6 +2344,7 @@
assertTrue(view.hasCalledOnKeyDown());
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setEnabled(true);
view.setClickable(true);
@@ -2328,6 +2419,7 @@
// Remove the child view from the parent, test that parent is 0xparentHeight
final CountDownLatch countDownLatch1 = new CountDownLatch(1);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
viewGroup.removeAllViews();
viewGroup.addView(parent);
@@ -2338,6 +2430,7 @@
final CountDownLatch countDownLatch2 = new CountDownLatch(1);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
parent.addView(child);
checkBounds(viewGroup, parent, countDownLatch2, 0, 0, childWidth, parentHeight);
@@ -2347,6 +2440,7 @@
final CountDownLatch countDownLatch3 = new CountDownLatch(1);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
parent.removeView(child);
checkBounds(viewGroup, parent, countDownLatch3, 0, 0, 0, parentHeight);
@@ -2463,6 +2557,7 @@
view.reset();
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.invalidate();
}
@@ -2477,6 +2572,7 @@
view.reset();
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setVisibility(View.INVISIBLE);
view.invalidate();
@@ -2500,6 +2596,7 @@
final Rect dirty = new Rect(view.getLeft() + 1, view.getTop() + 1,
view.getLeft() + view.getWidth() / 2, view.getTop() + view.getHeight() / 2);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.invalidate(dirty);
}
@@ -2514,6 +2611,7 @@
view.reset();
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setVisibility(View.INVISIBLE);
view.invalidate(dirty);
@@ -2531,6 +2629,7 @@
final Rect dirty = new Rect(view.getLeft() + 1, view.getTop() + 1,
view.getLeft() + view.getWidth() / 2, view.getTop() + view.getHeight() / 2);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.invalidate(dirty.left, dirty.top, dirty.right, dirty.bottom);
}
@@ -2545,6 +2644,7 @@
view.reset();
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setVisibility(View.INVISIBLE);
view.invalidate(dirty.left, dirty.top, dirty.right, dirty.bottom);
@@ -2561,6 +2661,7 @@
view.reset();
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setBackgroundDrawable(d1);
view.invalidateDrawable(d1);
@@ -2576,6 +2677,7 @@
view.reset();
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.invalidateDrawable(d2);
}
@@ -2650,6 +2752,7 @@
}.run();
new PollingCheck() {
+ @Override
protected boolean check() {
return view.hasCalledOnWindowFocusChanged();
}
@@ -2681,6 +2784,7 @@
public void testDraw() throws Throwable {
final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.requestLayout();
}
@@ -2807,6 +2911,7 @@
assertTrue(view.hasCalledOnTouchEvent());
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setEnabled(true);
view.setClickable(true);
@@ -3096,6 +3201,7 @@
Context.INPUT_METHOD_SERVICE);
final LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(300, 500);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
mockView.setBackgroundDrawable(d);
mockView.setHorizontalFadingEdgeEnabled(true);
@@ -3115,6 +3221,7 @@
// FIXME: why the size of view doesn't change?
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
imm.hideSoftInputFromInputMethod(mockView.getWindowToken(), 0);
}
@@ -3126,6 +3233,7 @@
final MockView mockView = (MockView) mActivity.findViewById(R.id.mock_view);
final View fitWindowsView = mActivity.findViewById(R.id.fit_windows);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
mockView.setFocusableInTouchMode(true);
fitWindowsView.setFocusable(true);
@@ -3146,6 +3254,7 @@
assertFalse(fitWindowsView.isFocused());
assertFalse(mockView.isFocused());
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
mockView.requestFocus();
}
@@ -3153,6 +3262,7 @@
getInstrumentation().waitForIdleSync();
assertTrue(mockView.isFocused());
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
fitWindowsView.requestFocus();
}
@@ -3167,6 +3277,7 @@
assertTrue(mockView.isFocused());
assertFalse(fitWindowsView.isFocused());
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
fitWindowsView.requestFocus();
}
@@ -3320,9 +3431,10 @@
items.add("1");
items.add("2");
items.add("3");
- final Adapter<String> adapter = new Adapter<String>(mActivity, 0, items);
+ final Adapter<String> adapter = new Adapter<>(mActivity, 0, items);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
mActivity.setContentView(listView);
listView.setAdapter(adapter);
@@ -3332,6 +3444,7 @@
final MockView focusChild = (MockView) listView.getChildAt(0);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
focusChild.requestFocus();
}
@@ -3340,6 +3453,7 @@
assertTrue(listView.getChildAt(0).isFocused());
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
listView.detachViewFromParent(focusChild);
}
@@ -3389,7 +3503,7 @@
}
private static class Adapter<T> extends ArrayAdapter<T> {
- ArrayList<MockView> views = new ArrayList<MockView>();
+ ArrayList<MockView> views = new ArrayList<>();
public Adapter(Context context, int textViewResourceId, List<T> objects) {
super(context, textViewResourceId, objects);
@@ -3419,6 +3533,7 @@
final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
view.setFocusable(true);
view.requestFocus();
@@ -3642,6 +3757,7 @@
final MockView view2 = new MockView(mActivity);
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
viewGroup.addView(view2);
}
@@ -3668,6 +3784,7 @@
assertTrue(view2.hasCalledOnHoverEvent());
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
viewGroup.removeView(view2);
}
@@ -3677,6 +3794,7 @@
assertFalse(view2.hasPointerCapture());
runTestOnUiThread(new Runnable() {
+ @Override
public void run() {
viewGroup.addView(view2);
}
@@ -3873,19 +3991,16 @@
}
private final static class MockViewParent extends ViewGroup {
- private boolean mHasClearChildFocus = false;
private boolean mHasRequestLayout = false;
private boolean mHasCreateContextMenu = false;
private boolean mHasShowContextMenuForChild = false;
- private boolean mHasGetChildVisibleRect = false;
- private boolean mHasInvalidateChild = false;
- private boolean mHasOnCreateDrawableState = false;
+ private boolean mHasShowContextMenuForChildXY = false;
private boolean mHasChildDrawableStateChanged = false;
private boolean mHasBroughtChildToFront = false;
- private Rect mTempRect;
private final static int[] DEFAULT_PARENT_STATE_SET = new int[] { 789 };
+ @Override
public boolean requestChildRectangleOnScreen(View child, Rect rectangle,
boolean immediate) {
return false;
@@ -3895,6 +4010,7 @@
super(context);
}
+ @Override
public void bringChildToFront(View child) {
mHasBroughtChildToFront = true;
}
@@ -3903,6 +4019,7 @@
return mHasBroughtChildToFront;
}
+ @Override
public void childDrawableStateChanged(View child) {
mHasChildDrawableStateChanged = true;
}
@@ -3921,14 +4038,12 @@
super.dispatchSetSelected(selected);
}
+ @Override
public void clearChildFocus(View child) {
- mHasClearChildFocus = true;
+
}
- public boolean hasClearChildFocus() {
- return mHasClearChildFocus;
- }
-
+ @Override
public void createContextMenu(ContextMenu menu) {
mHasCreateContextMenu = true;
}
@@ -3937,16 +4052,18 @@
return mHasCreateContextMenu;
}
+ @Override
public View focusSearch(View v, int direction) {
return v;
}
+ @Override
public void focusableViewAvailable(View v) {
}
+ @Override
public boolean getChildVisibleRect(View child, Rect r, Point offset) {
- mHasGetChildVisibleRect = true;
return false;
}
@@ -3955,26 +4072,27 @@
}
- public boolean hasGetChildVisibleRect() {
- return mHasGetChildVisibleRect;
- }
-
+ @Override
public ViewParent invalidateChildInParent(int[] location, Rect r) {
return null;
}
+ @Override
public boolean isLayoutRequested() {
return false;
}
+ @Override
public void recomputeViewAttributes(View child) {
}
+ @Override
public void requestChildFocus(View child, View focused) {
}
+ @Override
public void requestDisallowInterceptTouchEvent(boolean disallowIntercept) {
}
@@ -3988,20 +4106,30 @@
return mHasRequestLayout;
}
+ @Override
public void requestTransparentRegion(View child) {
}
+ @Override
public boolean showContextMenuForChild(View originalView) {
mHasShowContextMenuForChild = true;
return false;
}
+ @Override
+ public boolean showContextMenuForChild(View originalView, float x, float y) {
+ mHasShowContextMenuForChildXY = true;
+ return false;
+ }
+
+ @Override
public ActionMode startActionModeForChild(View originalView,
ActionMode.Callback callback) {
return null;
}
+ @Override
public ActionMode startActionModeForChild(View originalView,
ActionMode.Callback callback, int type) {
return null;
@@ -4011,40 +4139,29 @@
return mHasShowContextMenuForChild;
}
+ public boolean hasShowContextMenuForChildXY() {
+ return mHasShowContextMenuForChildXY;
+ }
+
@Override
protected int[] onCreateDrawableState(int extraSpace) {
- mHasOnCreateDrawableState = true;
return DEFAULT_PARENT_STATE_SET;
}
+ @Override
public boolean requestSendAccessibilityEvent(View child, AccessibilityEvent event) {
return false;
}
- public static int[] getDefaultParentStateSet() {
- return DEFAULT_PARENT_STATE_SET;
- }
-
- public boolean hasOnCreateDrawableState() {
- return mHasOnCreateDrawableState;
- }
-
public void reset() {
- mHasClearChildFocus = false;
mHasRequestLayout = false;
mHasCreateContextMenu = false;
mHasShowContextMenuForChild = false;
- mHasGetChildVisibleRect = false;
- mHasInvalidateChild = false;
- mHasOnCreateDrawableState = false;
+ mHasShowContextMenuForChildXY = false;
mHasChildDrawableStateChanged = false;
mHasBroughtChildToFront = false;
}
- public void childOverlayStateChanged(View child) {
-
- }
-
@Override
public void childHasTransientStateChanged(View child, boolean hasTransientState) {
@@ -4103,6 +4220,7 @@
private final class OnCreateContextMenuListenerImpl implements OnCreateContextMenuListener {
private boolean mHasOnCreateContextMenu = false;
+ @Override
public void onCreateContextMenu(ContextMenu menu, View v, ContextMenuInfo menuInfo) {
mHasOnCreateContextMenu = true;
}
@@ -4152,6 +4270,7 @@
private static final class OnClickListenerImpl implements OnClickListener {
private boolean mHasOnClick = false;
+ @Override
public void onClick(View v) {
mHasOnClick = true;
}
@@ -4176,6 +4295,7 @@
mHasOnLongClick = false;
}
+ @Override
public boolean onLongClick(View v) {
mHasOnLongClick = true;
return true;
@@ -4195,6 +4315,7 @@
mLastViewContextClicked = null;
}
+ @Override
public boolean onContextClick(View v) {
mHasContextClick = true;
mLastViewContextClicked = v;
@@ -4209,6 +4330,7 @@
private static final class OnFocusChangeListenerImpl implements OnFocusChangeListener {
private boolean mHasOnFocusChange = false;
+ @Override
public void onFocusChange(View v, boolean hasFocus) {
mHasOnFocusChange = true;
}
@@ -4225,6 +4347,7 @@
private static final class OnKeyListenerImpl implements OnKeyListener {
private boolean mHasOnKey = false;
+ @Override
public boolean onKey(View v, int keyCode, KeyEvent event) {
mHasOnKey = true;
return true;
@@ -4242,6 +4365,7 @@
private static final class OnTouchListenerImpl implements OnTouchListener {
private boolean mHasOnTouch = false;
+ @Override
public boolean onTouch(View v, MotionEvent event) {
mHasOnTouch = true;
return true;
@@ -4276,7 +4400,7 @@
public void reset() {
mCalledOnTouchEvent = false;
}
- };
+ }
private static final class ViewData {
public int childCount;
@@ -4287,6 +4411,7 @@
private static final class MockRunnable implements Runnable {
public boolean hasRun = false;
+ @Override
public void run() {
hasRun = true;
}
diff --git a/tools/cts-tradefed/DynamicConfig.xml b/tools/cts-tradefed/DynamicConfig.xml
index 6acffc0..e02d61e 100644
--- a/tools/cts-tradefed/DynamicConfig.xml
+++ b/tools/cts-tradefed/DynamicConfig.xml
@@ -13,6 +13,8 @@
limitations under the License.
-->
-<DynamicConfig>
- <Config key="MediaFilesUrl">https://dl.google.com/dl/android/cts/android-cts-media-1.1.zip</Config>
-</DynamicConfig>
+<dynamicConfig>
+ <entry key="MediaFilesUrl">
+ <value>https://dl.google.com/dl/android/cts/android-cts-media-1.1.zip</value>
+ </entry>
+</dynamicConfig>
diff --git a/tools/vm-tests-tf/Android.mk b/tools/vm-tests-tf/Android.mk
index 7578fa9..1e7be8a 100644
--- a/tools/vm-tests-tf/Android.mk
+++ b/tools/vm-tests-tf/Android.mk
@@ -66,7 +66,6 @@
intermediates := $(call intermediates-dir-for,JAVA_LIBRARIES,vm-tests-tf,HOST)
vmteststf_jar := $(intermediates)/android.core.vm-tests-tf.jar
vmteststf_dep_jars := $(addprefix $(HOST_OUT_JAVA_LIBRARIES)/, cts-tf-dalvik-buildutil.jar dasm.jar dx.jar cfassembler.jar junit.jar)
-vmteststf_dep_jars += $(addprefix $(HOST_OUT_JAVA_LIBRARIES)/, jack.jar)
vmteststf_dep_jars += $(private_jill_jarjar_asm)
$(vmteststf_jar): PRIVATE_JACK_EXTRA_ARGS := $(LOCAL_JACK_EXTRA_ARGS)
@@ -83,7 +82,7 @@
$(vmteststf_jar): PRIVATE_INTERMEDIATES_HOSTJUNIT_FILES := $(intermediates)/hostjunit_files
$(vmteststf_jar): PRIVATE_CLASS_PATH := $(subst $(space),:,$(vmteststf_dep_jars)):$(HOST_JDK_TOOLS_JAR)
ifndef LOCAL_JACK_ENABLED
-$(vmteststf_jar) : $(vmteststf_dep_jars) $(JACK_JAR) $(JILL_JAR) $(HOST_OUT_JAVA_LIBRARIES)/tradefed-prebuilt.jar
+$(vmteststf_jar) : $(vmteststf_dep_jars) $(JILL_JAR) $(HOST_OUT_JAVA_LIBRARIES)/tradefed-prebuilt.jar
$(hide) rm -rf $(dir $@) && mkdir -p $(dir $@)
$(hide) mkdir -p $(PRIVATE_INTERMEDIATES_HOSTJUNIT_FILES)/dot/junit $(dir $(PRIVATE_INTERMEDIATES_DEXCORE_JAR))
# generated and compile the host side junit tests
@@ -102,12 +101,12 @@
oj_jack := $(call intermediates-dir-for,JAVA_LIBRARIES,core-oj,,COMMON)/classes.jack
libart_jack := $(call intermediates-dir-for,JAVA_LIBRARIES,core-libart,,COMMON)/classes.jack
$(vmteststf_jar): PRIVATE_DALVIK_SUITE_CLASSPATH := $(oj_jack):$(libart_jack):$(cts-tf-dalvik-lib.jack):$(HOST_OUT_JAVA_LIBRARIES)/tradefed-prebuilt.jar
-$(vmteststf_jar) : $(vmteststf_dep_jars) $(JACK_JAR) $(JILL_JAR) $(oj_jack) $(libart_jack) $(HOST_OUT_JAVA_LIBRARIES)/tradefed-prebuilt.jar
+$(vmteststf_jar) : $(vmteststf_dep_jars) $(JACK) $(JILL_JAR) $(oj_jack) $(libart_jack) $(HOST_OUT_JAVA_LIBRARIES)/tradefed-prebuilt.jar | setup-jack-server
$(hide) rm -rf $(dir $@) && mkdir -p $(dir $@)
$(hide) mkdir -p $(PRIVATE_INTERMEDIATES_HOSTJUNIT_FILES)/dot/junit $(dir $(PRIVATE_INTERMEDIATES_DEXCORE_JAR))
# generated and compile the host side junit tests
@echo "Write generated Main_*.java files to $(PRIVATE_INTERMEDIATES_MAIN_FILES)"
- $(hide) java -cp $(PRIVATE_CLASS_PATH) util.build.JackBuildDalvikSuite $(PRIVATE_SRC_FOLDER) $(PRIVATE_INTERMEDIATES) \
+ $(hide) JACK_VERSION=$(JACK_DEFAULT_VERSION) java -cp $(PRIVATE_CLASS_PATH) util.build.JackBuildDalvikSuite $(PRIVATE_SRC_FOLDER) $(PRIVATE_INTERMEDIATES) \
$(PRIVATE_DALVIK_SUITE_CLASSPATH) \
$(PRIVATE_INTERMEDIATES_MAIN_FILES) $(PRIVATE_INTERMEDIATES_CLASSES) $(PRIVATE_INTERMEDIATES_HOSTJUNIT_FILES) $$RUN_VM_TESTS_RTO
@echo "Generate $(PRIVATE_INTERMEDIATES_DEXCORE_JAR)"
diff --git a/tools/vm-tests-tf/src/util/build/BytesStreamSucker.java b/tools/vm-tests-tf/src/util/build/BytesStreamSucker.java
new file mode 100644
index 0000000..f243c17
--- /dev/null
+++ b/tools/vm-tests-tf/src/util/build/BytesStreamSucker.java
@@ -0,0 +1,68 @@
+/*
+ * Copyright (C) 2012 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 util.build;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+
+import javax.annotation.Nonnull;
+
+/**
+ * Class that continuously read an {@link InputStream} and optionally could write the input in a
+ * {@link OutputStream}.
+ */
+public class BytesStreamSucker {
+
+ private static final int BUFFER_SIZE = 4096;
+
+ @Nonnull
+ private final byte[] buffer = new byte[BUFFER_SIZE];
+
+ @Nonnull
+ private final InputStream is;
+
+ @Nonnull
+ private final OutputStream os;
+
+ private final boolean toBeClose;
+
+ public BytesStreamSucker(
+ @Nonnull InputStream is, @Nonnull OutputStream os, boolean toBeClose) {
+ this.is = is;
+ this.os = os;
+ this.toBeClose = toBeClose;
+ }
+
+ public BytesStreamSucker(@Nonnull InputStream is, @Nonnull OutputStream os) {
+ this(is, os, false);
+ }
+
+ public void suck() throws IOException {
+ try {
+ int bytesRead;
+ while ((bytesRead = is.read(buffer)) >= 0) {
+ os.write(buffer, 0, bytesRead);
+ os.flush();
+ }
+ } finally {
+ if (toBeClose) {
+ os.close();
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/tools/vm-tests-tf/src/util/build/CharactersStreamSucker.java b/tools/vm-tests-tf/src/util/build/CharactersStreamSucker.java
new file mode 100644
index 0000000..ce4dfb1
--- /dev/null
+++ b/tools/vm-tests-tf/src/util/build/CharactersStreamSucker.java
@@ -0,0 +1,65 @@
+/*
+ * Copyright (C) 2012 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 util.build;
+
+import java.io.BufferedReader;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.io.PrintStream;
+
+import javax.annotation.Nonnull;
+
+/**
+ * Class that continuously read an {@link InputStream} and optionally could print the input in a
+ * {@link PrintStream}.
+ */
+public class CharactersStreamSucker {
+
+ @Nonnull
+ private final BufferedReader ir;
+
+ @Nonnull
+ private final PrintStream os;
+
+ private final boolean toBeClose;
+
+ public CharactersStreamSucker(
+ @Nonnull InputStream is, @Nonnull PrintStream os, boolean toBeClose) {
+ this.ir = new BufferedReader(new InputStreamReader(is));
+ this.os = os;
+ this.toBeClose = toBeClose;
+ }
+
+ public CharactersStreamSucker(@Nonnull InputStream is, @Nonnull PrintStream os) {
+ this(is, os, false);
+ }
+
+ public void suck() throws IOException {
+ String line;
+
+ try {
+ while ((line = ir.readLine()) != null) {
+ os.println(line);
+ }
+ } finally {
+ if (toBeClose) {
+ os.close();
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/tools/vm-tests-tf/src/util/build/ExecuteFile.java b/tools/vm-tests-tf/src/util/build/ExecuteFile.java
new file mode 100644
index 0000000..a0e5ce5
--- /dev/null
+++ b/tools/vm-tests-tf/src/util/build/ExecuteFile.java
@@ -0,0 +1,274 @@
+/*
+ * Copyright (C) 2012 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 util.build;
+
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileNotFoundException;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.io.PrintStream;
+import java.io.StreamTokenizer;
+import java.io.StringReader;
+import java.util.ArrayList;
+import java.util.logging.Level;
+import java.util.logging.Logger;
+
+import javax.annotation.CheckForNull;
+import javax.annotation.Nonnull;
+
+/**
+ * Class to handle the execution of an external process
+ */
+public class ExecuteFile {
+ @Nonnull
+ private final String[] cmdLine;
+
+ @CheckForNull
+ private File workDir;
+
+ @CheckForNull
+ private InputStream inStream;
+ private boolean inToBeClose;
+
+ @CheckForNull
+ private OutputStream outStream;
+ private boolean outToBeClose;
+
+ @CheckForNull
+ private OutputStream errStream;
+ private boolean errToBeClose;
+ private boolean verbose;
+
+ @Nonnull
+ private final Logger logger = Logger.getLogger(this.getClass().getName());
+
+ public void setErr(@Nonnull File file) throws FileNotFoundException {
+ errStream = new FileOutputStream(file);
+ errToBeClose = true;
+ }
+
+ public void setOut(@Nonnull File file) throws FileNotFoundException {
+ outStream = new FileOutputStream(file);
+ outToBeClose = true;
+ }
+
+ public void setIn(@Nonnull File file) throws FileNotFoundException {
+ inStream = new FileInputStream(file);
+ inToBeClose = true;
+ }
+
+ public void setErr(@Nonnull OutputStream stream) {
+ errStream = stream;
+ }
+
+ public void setOut(@Nonnull OutputStream stream) {
+ outStream = stream;
+ }
+
+ public void setIn(@Nonnull InputStream stream) {
+ inStream = stream;
+ }
+
+ public void setWorkingDir(@Nonnull File dir, boolean create) throws IOException {
+ if (!dir.isDirectory()) {
+ if (create && !dir.exists()) {
+ if (!dir.mkdirs()) {
+ throw new IOException("Directory creation failed");
+ }
+ } else {
+ throw new FileNotFoundException(dir.getPath() + " is not a directory");
+ }
+ }
+
+ workDir = dir;
+ }
+
+ public void setVerbose(boolean verbose) {
+ this.verbose = verbose;
+ }
+
+ public ExecuteFile(@Nonnull File exec, @Nonnull String[] args) {
+ cmdLine = new String[args.length + 1];
+ System.arraycopy(args, 0, cmdLine, 1, args.length);
+
+ cmdLine[0] = exec.getAbsolutePath();
+ }
+
+ public ExecuteFile(@Nonnull String exec, @Nonnull String[] args) {
+ cmdLine = new String[args.length + 1];
+ System.arraycopy(args, 0, cmdLine, 1, args.length);
+
+ cmdLine[0] = exec;
+ }
+
+ public ExecuteFile(@Nonnull File exec) {
+ cmdLine = new String[1];
+ cmdLine[0] = exec.getAbsolutePath();
+ }
+
+ public ExecuteFile(@Nonnull String[] cmdLine) {
+ this.cmdLine = cmdLine.clone();
+ }
+
+ public ExecuteFile(@Nonnull String cmdLine) throws IOException {
+ StringReader reader = new StringReader(cmdLine);
+ StreamTokenizer tokenizer = new StreamTokenizer(reader);
+ tokenizer.resetSyntax();
+ // Only standard spaces are recognized as whitespace chars
+ tokenizer.whitespaceChars(' ', ' ');
+ // Matches alphanumerical and common special symbols like '(' and ')'
+ tokenizer.wordChars('!', 'z');
+ // Quote chars will be ignored when parsing strings
+ tokenizer.quoteChar('\'');
+ tokenizer.quoteChar('\"');
+ ArrayList<String> tokens = new ArrayList<String>();
+ while (tokenizer.nextToken() != StreamTokenizer.TT_EOF) {
+ String token = tokenizer.sval;
+ if (token != null) {
+ tokens.add(token);
+ }
+ }
+ this.cmdLine = tokens.toArray(new String[0]);
+ }
+
+ public boolean run() {
+ int ret;
+ Process proc = null;
+ Thread suckOut = null;
+ Thread suckErr = null;
+ Thread suckIn = null;
+
+ try {
+ StringBuilder cmdLineBuilder = new StringBuilder();
+ for (String arg : cmdLine) {
+ cmdLineBuilder.append(arg).append(' ');
+ }
+ if (verbose) {
+ PrintStream printStream;
+ if (outStream instanceof PrintStream) {
+ printStream = (PrintStream) outStream;
+ } else {
+ printStream = System.out;
+ }
+
+ if (printStream != null) {
+ printStream.println(cmdLineBuilder);
+ }
+ } else {
+ logger.log(Level.FINE, "Execute: {0}", cmdLineBuilder);
+ }
+
+ proc = Runtime.getRuntime().exec(cmdLine, null, workDir);
+
+ InputStream localInStream = inStream;
+ if (localInStream != null) {
+ suckIn = new Thread(
+ new ThreadBytesStreamSucker(localInStream, proc.getOutputStream(), inToBeClose));
+ } else {
+ proc.getOutputStream().close();
+ }
+
+ OutputStream localOutStream = outStream;
+ if (localOutStream != null) {
+ if (localOutStream instanceof PrintStream) {
+ suckOut = new Thread(new ThreadCharactersStreamSucker(proc.getInputStream(),
+ (PrintStream) localOutStream, outToBeClose));
+ } else {
+ suckOut = new Thread(
+ new ThreadBytesStreamSucker(proc.getInputStream(), localOutStream, outToBeClose));
+ }
+ }
+
+ OutputStream localErrStream = errStream;
+ if (localErrStream != null) {
+ if (localErrStream instanceof PrintStream) {
+ suckErr = new Thread(new ThreadCharactersStreamSucker(proc.getErrorStream(),
+ (PrintStream) localErrStream, errToBeClose));
+ } else {
+ suckErr = new Thread(
+ new ThreadBytesStreamSucker(proc.getErrorStream(), localErrStream, errToBeClose));
+ }
+ }
+
+ if (suckIn != null) {
+ suckIn.start();
+ }
+ if (suckOut != null) {
+ suckOut.start();
+ }
+ if (suckErr != null) {
+ suckErr.start();
+ }
+
+ proc.waitFor();
+ if (suckIn != null) {
+ suckIn.join();
+ }
+ if (suckOut != null) {
+ suckOut.join();
+ }
+ if (suckErr != null) {
+ suckErr.join();
+ }
+
+ ret = proc.exitValue();
+ proc.destroy();
+
+ return ret == 0;
+ } catch (Throwable e) {
+ return false;
+ }
+ }
+
+ private static class ThreadBytesStreamSucker extends BytesStreamSucker implements Runnable {
+
+ public ThreadBytesStreamSucker(@Nonnull InputStream is, @Nonnull OutputStream os,
+ boolean toBeClose) {
+ super(is, os, toBeClose);
+ }
+
+ @Override
+ public void run() {
+ try {
+ suck();
+ } catch (IOException e) {
+ // Best effort
+ }
+ }
+ }
+
+ private static class ThreadCharactersStreamSucker extends CharactersStreamSucker implements
+ Runnable {
+
+ public ThreadCharactersStreamSucker(@Nonnull InputStream is, @Nonnull PrintStream ps,
+ boolean toBeClose) {
+ super(is, ps, toBeClose);
+ }
+
+ @Override
+ public void run() {
+ try {
+ suck();
+ } catch (IOException e) {
+ // Best effort
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/tools/vm-tests-tf/src/util/build/JackBuildStep.java b/tools/vm-tests-tf/src/util/build/JackBuildStep.java
index 061ff07..29df8260 100644
--- a/tools/vm-tests-tf/src/util/build/JackBuildStep.java
+++ b/tools/vm-tests-tf/src/util/build/JackBuildStep.java
@@ -16,16 +16,10 @@
package util.build;
-import com.android.jack.CLILogConfiguration;
-import com.android.jack.CLILogConfiguration.LogConfigurationException;
-
-import util.build.BuildStep.BuildFile;
-
-import com.android.jack.Jack;
-import com.android.jack.Main;
-import com.android.jack.Options;
import java.io.File;
+import java.io.FileWriter;
import java.io.IOException;
+import java.io.Writer;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
@@ -33,14 +27,6 @@
public class JackBuildStep extends SourceBuildStep {
- static {
- try {
- CLILogConfiguration.setupLogs();
- } catch (LogConfigurationException e) {
- throw new Error("Failed to setup logs", e);
- }
- }
-
private final String destPath;
private final String classPath;
private final Set<String> sourceFiles = new HashSet<String>();
@@ -78,7 +64,18 @@
}
File tmpDex = new File(tmpOutDir, "classes.dex");
+ File tmpArgs = new File(outDir, outputFile.fileName.getName() + ".args");
+
+ Writer argsOut = null;
try {
+ argsOut = new FileWriter(tmpArgs);
+ for (String source : sourceFiles) {
+ argsOut.append(source);
+ argsOut.append('\n');
+ }
+ argsOut.close();
+ argsOut = null;
+
List<String> commandLine = new ArrayList<String>(6 + sourceFiles.size());
commandLine.add("--verbose");
commandLine.add("error");
@@ -86,10 +83,14 @@
commandLine.add(classPath);
commandLine.add("--output-dex");
commandLine.add(tmpOutDir.getAbsolutePath());
- commandLine.addAll(sourceFiles);
+ commandLine.add("@" + tmpArgs.getPath());
- Options options = Main.parseCommandLine(commandLine);
- Jack.checkAndRun(options);
+ ExecuteFile exec = new ExecuteFile("jack", commandLine.toArray(new String[commandLine.size()]));
+ exec.setErr(System.err);
+ exec.setOut(System.out);
+ if (!exec.run()) {
+ return false;
+ }
JarBuildStep jarStep = new JarBuildStep(
new BuildFile(tmpDex),
@@ -104,8 +105,16 @@
ex.printStackTrace();
return false;
} finally {
- tmpDex.delete();
- tmpOutDir.delete();
+ tmpDex.delete();
+ tmpArgs.delete();
+ tmpOutDir.delete();
+ if (argsOut != null) {
+ try {
+ argsOut.close();
+ } catch (IOException io) {
+ // Ignore, don't override already thrown exception
+ }
+ }
}
}
return false;
diff --git a/tools/vm-tests-tf/src/util/build/JackDexBuildStep.java b/tools/vm-tests-tf/src/util/build/JackDexBuildStep.java
index 8734cf0..3702973 100644
--- a/tools/vm-tests-tf/src/util/build/JackDexBuildStep.java
+++ b/tools/vm-tests-tf/src/util/build/JackDexBuildStep.java
@@ -16,10 +16,6 @@
package util.build;
-import com.android.jack.Jack;
-import com.android.jack.Main;
-import com.android.jack.Options;
-
import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
@@ -69,8 +65,12 @@
commandLine.add("--import");
commandLine.add(inputFile.fileName.getAbsolutePath());
- Options options = Main.parseCommandLine(commandLine);
- Jack.checkAndRun(options);
+ ExecuteFile exec = new ExecuteFile("jack", commandLine.toArray(new String[commandLine.size()]));
+ exec.setErr(System.err);
+ exec.setOut(System.out);
+ if (!exec.run()) {
+ return false;
+ }
JarBuildStep jarStep = new JarBuildStep(
new BuildFile(tmpDex),