Add test for Network Security Config integration with DownloadManager

Bug: 29505888
Change-Id: Iebe96bcec21c33d913d381c9eee36beca950c5fd
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/Android.mk b/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/Android.mk
new file mode 100644
index 0000000..3993d00
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/Android.mk
@@ -0,0 +1,34 @@
+# 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 := CtsNetSecConfigDownloadManagerTestCases
+
+LOCAL_MODULE_TAGS := tests
+LOCAL_MODULE_PATH := $(TARGET_OUT_DATA_APPS)
+
+LOCAL_STATIC_JAVA_LIBRARIES := ctstestrunner org.apache.http.legacy android-support-test
+
+LOCAL_SRC_FILES := $(call all-java-files-under, src)
+LOCAL_SRC_FILES += $(call all-java-files-under, ../src)
+
+LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res/
+
+# Tag this module as a cts test artifact
+LOCAL_COMPATIBILITY_SUITE := cts
+
+LOCAL_SDK_VERSION := current
+include $(BUILD_CTS_PACKAGE)
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/AndroidManifest.xml b/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/AndroidManifest.xml
new file mode 100644
index 0000000..e18ff4d
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/AndroidManifest.xml
@@ -0,0 +1,32 @@
+<?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.CtsNetSecConfigDownloadManagerTestCases">
+  <application android:networkSecurityConfig="@xml/network_security_config">
+      <uses-library android:name="android.test.runner"/>
+  </application>
+
+  <uses-permission android:name="android.permission.INTERNET" />
+  <instrumentation android:name="android.support.test.runner.AndroidJUnitRunner"
+                   android:targetPackage="android.security.net.config.cts.CtsNetSecConfigDownloadManagerTestCases"
+                   android:label="">
+        <meta-data android:name="listener"
+            android:value="com.android.cts.runner.CtsTestRunListener" />
+    </instrumentation>
+</manifest>
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/AndroidTest.xml b/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/AndroidTest.xml
new file mode 100644
index 0000000..e966baa
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/AndroidTest.xml
@@ -0,0 +1,24 @@
+<?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.
+-->
+<configuration description="Config for CTS CtsNetSecConfigDownloadManagerTestCases test cases">
+    <target_preparer class="com.android.compatibility.common.tradefed.targetprep.ApkInstaller">
+        <option name="cleanup-apks" value="true" />
+        <option name="test-file-name" value="CtsNetSecConfigDownloadManagerTestCases.apk" />
+    </target_preparer>
+    <test class="com.android.tradefed.testtype.AndroidJUnitTest" >
+        <option name="package" value="android.security.net.config.cts.CtsNetSecConfigDownloadManagerTestCases" />
+    </test>
+</configuration>
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/res/raw/invalid_chain.pem b/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/res/raw/invalid_chain.pem
new file mode 100644
index 0000000..ed33e7f
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/res/raw/invalid_chain.pem
@@ -0,0 +1,35 @@
+-----BEGIN CERTIFICATE-----
+MIICvjCCAaagAwIBAgIDDUD7MA0GCSqGSIb3DQEBCwUAMCMxITAfBgNVBAMTGEFu
+ZHJvaWQgQ1RTIHVudHJ1c3RlZCBDQTAqGBMyMDE1MDEwMTAwMDAwMCswMDAwGBMy
+MDI1MDEwMTAwMDAwMCswMDAwMBQxEjAQBgNVBAMTCWxvY2FsaG9zdDCCASIwDQYJ
+KoZIhvcNAQEBBQADggEPADCCAQoCggEBAKH+IdnzoDeGaE1SWn4L8dhfd59AJVYO
+Wxz88ntK55iPCxPGdNdqL5MX0On9K0iBf+e839mRMIdjY1BtEo5Ln9MA6RTLQwt6
+OPaWF/HQQHkmrLOOShNZcerea+rJHPfN7NedSg6Ufb2bcVn7DrKBwUigAJDWVn02
+IB6wHO9slF+NsAcpyecxtvY/p7t0lguAe0j1IiVfX+xGdNFU7WjmGRQzk5KavFi3
+BwDc25rXP7JJ/6M66TnzI54iRI918P0AbhE+3K/5Bbe8qPFtdlEOChP6npUW1Nhm
+z99KolkcW/uCXUBHAsm27QPdW3wYX6hwa5eS8VGTWuhEOddPdBvGGPcCAwEAATAN
+BgkqhkiG9w0BAQsFAAOCAQEAgABDM5HU2+XE6Hx/Ti8LpnJXLdNk6Y1uZro2Vvmz
+MqwdKBC/k5RrdIyalN5lZzCRWKi4f4wgWGGnqbxlAugwa5N0+LWgw2Em4W8HEk6c
+DK9TPVnh7y87ibwGmyeU+bHMyFuVV8Yp+tXUCV2aQhM/yBEyCOEei/twWeZ7uVaw
+ANraJ0UDDeznqJX3rTsvwwBfKLmFm98YhzB3EYVo332oCuvC90RLmEerI5JmpNAw
+jg6Z0DMShcfdN2kIW1NEUTGBbd5sGsPRJVba0giEwXtDKorPLe+kJJMzji8HRk0x
+51tpxEseBrS3DjiIS7CT1RuiBfVJAdfzOHyDeFCX9t7tFQ==
+-----END CERTIFICATE-----
+-----BEGIN CERTIFICATE-----
+MIIC4jCCAcqgAwIBAgIDBxMgMA0GCSqGSIb3DQEBCwUAMCMxITAfBgNVBAMTGEFu
+ZHJvaWQgQ1RTIHVudHJ1c3RlZCBDQTAqGBMyMDE1MDEwMTAwMDAwMCswMDAwGBMy
+MDI1MDEwMTAwMDAwMCswMDAwMCMxITAfBgNVBAMTGEFuZHJvaWQgQ1RTIHVudHJ1
+c3RlZCBDQTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAMWCkHZZHBs7
+m1njBgF2yh4zEHOO1jN3nl9tNJwXWK6O3qAr4UC/CbokIu4onG26I9kHbaCAcM3L
+7qmuz2cL5gqSrwUD7nVC38+EnP8WpMt/SFljJYlbNqGMep8/ZvybtK8wJm+dAY3w
+Cj4vU9w9XPakG6m0FkSLtS5+XaAIM0rRbWGcPWBv+nHOwXBNpggoe63L2uJ6wra7
+NwW0epXT4FuMzY+f3/ZSdNbhMs4/gJbLHYMt81w7YZ2DY/fgGbZGjLc6PQvV8bZb
++Wib/Lg0o2rFb9O+pdU0azZQ/kyD/+CBjuEewJCcl6dsQX5k8A71di4uWBHaopVr
+gN2MTL2pqRECAwEAAaMTMBEwDwYDVR0TAQH/BAUwAwEB/zANBgkqhkiG9w0BAQsF
+AAOCAQEAORmso2dZmTmaUHQKRnbpDoVcUDeDJWSnkgCbP1ZgpQ+B7t5ZWnLXqpVy
+eyK/ENscNPMpbyyQ8eaeydpSD6jipJfmH3O8NhtWZPA/1oY0Wm4/lsosZGFSadWg
+nSLfqxZtBy+VIZBGZrhPhlJ2U2WKmrTaMYS7TJy1t9RcQIw79pnnLKXAAhZx72U5
+FtPMAGREDaFMt7pVcM63ipytUPtrXH6nzOFHmsGGT0sbA0+/QkN5NkYYbHbFP6oI
+BJ4xZHVLCoyt+5kscsIZXsLb6jd1d/8RoD1w+559uE3T5AyPmfGRnq9+QjKbf0hx
+MC5lBV/nTWSf+GM0Q/hy2CPvvB7WNA==
+-----END CERTIFICATE-----
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/res/raw/test_key.pkcs8 b/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/res/raw/test_key.pkcs8
new file mode 100644
index 0000000..c4e2d08
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/res/raw/test_key.pkcs8
Binary files differ
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/res/raw/valid_ca.pem b/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/res/raw/valid_ca.pem
new file mode 100644
index 0000000..d70b4d6
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/res/raw/valid_ca.pem
@@ -0,0 +1,46 @@
+-----BEGIN CERTIFICATE-----
+MIIC3jCCAcagAwIBAgIDDGqSMA0GCSqGSIb3DQEBCwUAMCExHzAdBgNVBAMTFkFu
+ZHJvaWQgQ1RTIHRydXN0ZWQgQ0EwKhgTMjAxNTAxMDEwMDAwMDArMDAwMBgTMjAy
+NTAxMDEwMDAwMDArMDAwMDAhMR8wHQYDVQQDExZBbmRyb2lkIENUUyB0cnVzdGVk
+IENBMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAyu1Eg5wKieyro7qL
+XIx+qaqbE8mPqRL81i0mtQBjnq3gsXV3f7okUssg/8QRzYiYGP/shly70MOqKURP
+/gl7OtUj8SXLwQFzZ6B9hnWTXGRnBY4JFcgSy6LJMwo+ZPgwVtbjf1DAWNOLRhqY
+J9Uxr0PX5KZ5AafFVh0Y+JVmaFfGPxJ/UBi83GQ7ToKBvHTFN5SQjg5QtlW5DaEN
+cbO7lzB/OuKnIlLP6WlEVwCS+cToZAzaTafOVZaUarWHit0kq+8xyxl+koxgLcCK
+lkDYpZCezY3UAxGheRnmSuah6LK9BRx2cSMOKkeN3sAoVB6ARi7F30MYj7RH2XRz
+LumXLQIDAQABoxMwETAPBgNVHRMBAf8EBTADAQH/MA0GCSqGSIb3DQEBCwUAA4IB
+AQBJi4SF/k1KVUZrweqUZ/QJ5HBDxWo4kE4iNw415qw2fAfNsKJknH1bcqgHa7Ea
+nokT8a1KOQlicInptNRbkwBd3Xakt9k9aCWRqyqBzZZersakZ1cB3SNxameelGzl
+a3dvGqVreE3LWhiQR7A3g84hS1kH5oNiY6GVZRk8BsmUUsvKaS6FJSMb9bAGSijQ
+EZwsBk+HoSuLSVxUDtLZgbs1NYVK8jCG6GPv8cWis03pK3VKqjTi3DDs7mHioViG
+G/TUZPq5ok8BemctNPLZAMLVlWPVB389iTOmgJWdR2Lu7LKh4B952+SeHMo3huUR
+Hn/e+Sq5FmJfDVvFG6U3PEDd
+-----END CERTIFICATE-----
+-----BEGIN PRIVATE KEY-----
+MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDK7USDnAqJ7Kuj
+uotcjH6pqpsTyY+pEvzWLSa1AGOereCxdXd/uiRSyyD/xBHNiJgY/+yGXLvQw6op
+RE/+CXs61SPxJcvBAXNnoH2GdZNcZGcFjgkVyBLLoskzCj5k+DBW1uN/UMBY04tG
+Gpgn1TGvQ9fkpnkBp8VWHRj4lWZoV8Y/En9QGLzcZDtOgoG8dMU3lJCODlC2VbkN
+oQ1xs7uXMH864qciUs/paURXAJL5xOhkDNpNp85VlpRqtYeK3SSr7zHLGX6SjGAt
+wIqWQNilkJ7NjdQDEaF5GeZK5qHosr0FHHZxIw4qR43ewChUHoBGLsXfQxiPtEfZ
+dHMu6ZctAgMBAAECggEAezX1E7P68iOxU4hAdcEYZwwffLQ1dgMBYUmo5t2FnyMT
++qvIEtWCmIKdVq5F4PW+4+8APdSwdOFYwBWqPCSlneMsH49DV7z5xUG89ZcOElsj
+8kt7WK5SOzJr14GwwL2xHAj9uJ/fKg/H0Jj1KbpYoIIg48PwVQD44IBqWQTdWRxd
+QVbxczDIHAjXSD14P4uUAXQrFyYEQXgksu4FNNGFr6JnuNe6eSreKxrw8/7J9OXZ
+7VUfN0Iuw/M4HF1dKQKVK2R0W34wuS2KyI3fKUS7RoSrfXfBuZ1hQ1gWoATiXkbR
+AAMUSWuaj5RQ4lj0wxdRAO+e4QB2yUXHgzCr8pH6QQKBgQDuiXtcdZ2FVN9ezxJt
+XDd6225Rvh8XtWEUwTaJmOtZz2AKlKTQr06u/BqqpKWc5SWQSf88K7WPxF6EMizB
+4D3wVGzCFkeRMMriZmrRe+8IVCq+mAZnRahV4SSH35ZQoNd8/3Mv6o59/UR0x7Nl
+5yTqruROK0Ycz8S0GlvfKiDyywKBgQDZyGaIYqZ63piagmRx3EB1Z+8yfXnn8g2d
+iVYU3UTDWxAFtzq6cfPRUdDxGHgAjmVmLvSGEaxqYNOftxwC3zk1E03w4/KvXg+y
+Vt+1qPZ7Hj1OcGMYA+1/Qy6+GMneYnUkmO9zHoNzSDG5hfNkQ+3SyMx53FfTO8oA
+Lrpl4gFG5wKBgQCtCGXIKDlf4rU13RgM5HwKTuqzuSps1FHb8FxTa+4tc9TDWBhG
+mSSGorHlXxITwdWB2WughkRqSZQWaR82dCf6EgPitq6rj61cldaepzw52nQ3Vagv
+ecQmp+8L8RDk5Afs0JEKDSfYFMR3wfVM0mNhKgTK/3EYrU6PJx/FvpWwCQKBgDrk
+ICXdV1t+ehG+FN9dSej1tA8ZMy/vmpLxIl/9/aw+IbUJ+U2VpvMBhtjLXxf3aaAa
+LnFash8KE+/qmh6EsnmRwM/VNDkL3H7DUzdSe2SLptRhO8qwtTZmumsZVO1X/olo
++cdNhwpTiW67tDd2zwbi2bhSR0WNs3AdMrZ+SQ4dAoGBANkjgWwzVN8KGOe9GdEo
+opcwVzC1l9xkUcB6ykIG+DKw5p1ChGLA+2uufdpNWfPqXixCt5X3qIOy1q/VIdlj
+EHNurGEld93H86V0ieLMRPg5llXWfKND2W8vezZSCGqFcSo+bAVi0YzA6XbLu+TV
+GyyCD8Jk/efmdN0DKjERIKDH
+-----END PRIVATE KEY-----
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/res/raw/valid_chain.pem b/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/res/raw/valid_chain.pem
new file mode 100644
index 0000000..e974055
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/res/raw/valid_chain.pem
@@ -0,0 +1,35 @@
+-----BEGIN CERTIFICATE-----
+MIICvDCCAaSgAwIBAgIDAQdvMA0GCSqGSIb3DQEBCwUAMCExHzAdBgNVBAMTFkFu
+ZHJvaWQgQ1RTIHRydXN0ZWQgQ0EwKhgTMjAxNTAxMDEwMDAwMDArMDAwMBgTMjAy
+NTAxMDEwMDAwMDArMDAwMDAUMRIwEAYDVQQDEwlsb2NhbGhvc3QwggEiMA0GCSqG
+SIb3DQEBAQUAA4IBDwAwggEKAoIBAQCh/iHZ86A3hmhNUlp+C/HYX3efQCVWDlsc
+/PJ7SueYjwsTxnTXai+TF9Dp/StIgX/nvN/ZkTCHY2NQbRKOS5/TAOkUy0MLejj2
+lhfx0EB5JqyzjkoTWXHq3mvqyRz3zezXnUoOlH29m3FZ+w6ygcFIoACQ1lZ9NiAe
+sBzvbJRfjbAHKcnnMbb2P6e7dJYLgHtI9SIlX1/sRnTRVO1o5hkUM5OSmrxYtwcA
+3Nua1z+ySf+jOuk58yOeIkSPdfD9AG4RPtyv+QW3vKjxbXZRDgoT+p6VFtTYZs/f
+SqJZHFv7gl1ARwLJtu0D3Vt8GF+ocGuXkvFRk1roRDnXT3Qbxhj3AgMBAAEwDQYJ
+KoZIhvcNAQELBQADggEBALSYVeSPW5+SHhMiOo6tvF0BDKCVqFwmggdpgxM660mp
+NXLoStfFNZSNkcWsLDsGPQC1RXuHDWq7GmMpaKGRtQDnVrArGvPTRn4iJIRQZ+/F
+uMBllitSPCoae4qcFfwEXotO+OuLZsaaBd/r58F0NqDmX/UOY9EP7NulyuUZmeBK
+OOaeOKOln6BXQoMWp5irEd8tGBze1sOJLWNejquyViWuCTHvHlafBi0fM3jAE5dL
+pnXStZFOCzU2J/DnfbLJmwbScYtYc9FiB3jMLM6vZZGGXT5Go3uiffcOAFSkJgxx
+l0BCRobyePW7RdxULA8THkg9tm044I28EeJEkKmaWrQ=
+-----END CERTIFICATE-----
+-----BEGIN CERTIFICATE-----
+MIIC3jCCAcagAwIBAgIDDGqSMA0GCSqGSIb3DQEBCwUAMCExHzAdBgNVBAMTFkFu
+ZHJvaWQgQ1RTIHRydXN0ZWQgQ0EwKhgTMjAxNTAxMDEwMDAwMDArMDAwMBgTMjAy
+NTAxMDEwMDAwMDArMDAwMDAhMR8wHQYDVQQDExZBbmRyb2lkIENUUyB0cnVzdGVk
+IENBMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAyu1Eg5wKieyro7qL
+XIx+qaqbE8mPqRL81i0mtQBjnq3gsXV3f7okUssg/8QRzYiYGP/shly70MOqKURP
+/gl7OtUj8SXLwQFzZ6B9hnWTXGRnBY4JFcgSy6LJMwo+ZPgwVtbjf1DAWNOLRhqY
+J9Uxr0PX5KZ5AafFVh0Y+JVmaFfGPxJ/UBi83GQ7ToKBvHTFN5SQjg5QtlW5DaEN
+cbO7lzB/OuKnIlLP6WlEVwCS+cToZAzaTafOVZaUarWHit0kq+8xyxl+koxgLcCK
+lkDYpZCezY3UAxGheRnmSuah6LK9BRx2cSMOKkeN3sAoVB6ARi7F30MYj7RH2XRz
+LumXLQIDAQABoxMwETAPBgNVHRMBAf8EBTADAQH/MA0GCSqGSIb3DQEBCwUAA4IB
+AQBJi4SF/k1KVUZrweqUZ/QJ5HBDxWo4kE4iNw415qw2fAfNsKJknH1bcqgHa7Ea
+nokT8a1KOQlicInptNRbkwBd3Xakt9k9aCWRqyqBzZZersakZ1cB3SNxameelGzl
+a3dvGqVreE3LWhiQR7A3g84hS1kH5oNiY6GVZRk8BsmUUsvKaS6FJSMb9bAGSijQ
+EZwsBk+HoSuLSVxUDtLZgbs1NYVK8jCG6GPv8cWis03pK3VKqjTi3DDs7mHioViG
+G/TUZPq5ok8BemctNPLZAMLVlWPVB389iTOmgJWdR2Lu7LKh4B952+SeHMo3huUR
+Hn/e+Sq5FmJfDVvFG6U3PEDd
+-----END CERTIFICATE-----
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/res/xml/network_security_config.xml b/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/res/xml/network_security_config.xml
new file mode 100644
index 0000000..6c064f9
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/res/xml/network_security_config.xml
@@ -0,0 +1,9 @@
+<?xml version="1.0" encoding="utf-8"?>
+<network-security-config>
+  <domain-config>
+    <domain>localhost</domain>
+    <trust-anchors>
+      <certificates src="@raw/valid_ca" />
+    </trust-anchors>
+  </domain-config>
+</network-security-config>
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/src/android/security/net/config/cts/DownloadManagerTest.java b/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/src/android/security/net/config/cts/DownloadManagerTest.java
new file mode 100644
index 0000000..28c8eb8
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-downloadmanager/src/android/security/net/config/cts/DownloadManagerTest.java
@@ -0,0 +1,221 @@
+/*
+ * 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.net.config.cts.CtsNetSecConfigDownloadManagerTestCases.R;
+
+import android.app.DownloadManager;
+import android.content.BroadcastReceiver;
+import android.content.Context;
+import android.content.Intent;
+import android.content.IntentFilter;
+import android.database.Cursor;
+import android.net.Uri;
+import android.os.SystemClock;
+import android.test.AndroidTestCase;
+import android.text.format.DateUtils;
+import android.util.Log;
+
+import java.io.ByteArrayOutputStream;
+import java.io.InputStream;
+import java.net.Socket;
+import java.security.KeyFactory;
+import java.security.KeyStore;
+import java.security.PrivateKey;
+import java.security.Provider;
+import java.security.Security;
+import java.security.Signature;
+import java.security.cert.Certificate;
+import java.security.cert.CertificateFactory;
+import java.security.cert.X509Certificate;
+import java.security.spec.PKCS8EncodedKeySpec;
+import java.util.Collection;
+import java.util.HashSet;
+import java.util.concurrent.Callable;
+import java.util.concurrent.ExecutionException;
+import java.util.concurrent.FutureTask;
+import java.util.concurrent.TimeUnit;
+import java.util.concurrent.TimeoutException;
+
+import javax.net.ssl.KeyManagerFactory;
+import javax.net.ssl.SSLContext;
+import javax.net.ssl.SSLServerSocket;
+import javax.net.ssl.TrustManager;
+import javax.net.ssl.TrustManagerFactory;
+import javax.net.ssl.X509TrustManager;
+
+public class DownloadManagerTest extends AndroidTestCase {
+
+    private static final String HTTP_RESPONSE =
+            "HTTP/1.0 200 OK\r\nContent-Type: text/plain\r\nContent-length: 5\r\n\r\nhello";
+    private static final long TIMEOUT = 3 * DateUtils.SECOND_IN_MILLIS;
+
+    public void testConfigTrustedCaAccepted() throws Exception {
+        runDownloadManagerTest(R.raw.valid_chain, R.raw.test_key);
+    }
+
+    public void testUntrustedCaRejected() throws Exception {
+        try {
+            runDownloadManagerTest(R.raw.invalid_chain, R.raw.test_key);
+            fail("Invalid CA should be rejected");
+        } catch (Exception expected) {
+        }
+    }
+
+    private void runDownloadManagerTest(int chainResId, int keyResId) throws Exception {
+        DownloadManager dm =
+                (DownloadManager) getContext().getSystemService(Context.DOWNLOAD_SERVICE);
+        DownloadCompleteReceiver receiver = new DownloadCompleteReceiver();
+        final SSLServerSocket serverSocket = bindTLSServer(chainResId, keyResId);
+        FutureTask<Void> serverFuture = new FutureTask<Void>(new Callable() {
+            @Override
+            public Void call() throws Exception {
+                runServer(serverSocket);
+                return null;
+            }
+        });
+        try {
+            IntentFilter filter = new IntentFilter(DownloadManager.ACTION_DOWNLOAD_COMPLETE);
+            getContext().registerReceiver(receiver, filter);
+            new Thread(serverFuture).start();
+            Uri destination = Uri.parse("https://localhost:" + serverSocket.getLocalPort());
+            long id = dm.enqueue(new DownloadManager.Request(destination));
+            try {
+                serverFuture.get(TIMEOUT, TimeUnit.MILLISECONDS);
+                // Check that the download was successful.
+                receiver.waitForDownloadComplete(TIMEOUT, id);
+                assertSuccessfulDownload(id);
+            } catch (InterruptedException e) {
+                // Wrap InterruptedException since otherwise it gets eaten by AndroidTest
+                throw new RuntimeException(e);
+            } finally {
+                dm.remove(id);
+            }
+        } finally {
+            getContext().unregisterReceiver(receiver);
+            serverFuture.cancel(true);
+            try {
+                serverSocket.close();
+            } catch (Exception ignored) {}
+        }
+    }
+
+    private void runServer(SSLServerSocket server) throws Exception {
+        Socket s = server.accept();
+        s.getOutputStream().write(HTTP_RESPONSE.getBytes());
+        s.getOutputStream().flush();
+        s.close();
+    }
+
+    private SSLServerSocket bindTLSServer(int chainResId, int keyResId) throws Exception {
+        // Load certificate chain.
+        CertificateFactory fact = CertificateFactory.getInstance("X.509");
+        Collection<? extends Certificate> certs;
+        try (InputStream is = getContext().getResources().openRawResource(chainResId)) {
+            certs = fact.generateCertificates(is);
+        }
+        X509Certificate[] chain = new X509Certificate[certs.size()];
+        int i = 0;
+        for (Certificate cert : certs) {
+            chain[i++] = (X509Certificate) cert;
+        }
+
+        // Load private key for the leaf.
+        PrivateKey key;
+        try (InputStream is = getContext().getResources().openRawResource(keyResId)) {
+            ByteArrayOutputStream keyout = new ByteArrayOutputStream();
+            byte[] buffer = new byte[4096];
+            int chunk_size;
+            while ((chunk_size = is.read(buffer)) != -1) {
+                keyout.write(buffer, 0, chunk_size);
+            }
+            is.close();
+            byte[] keyBytes = keyout.toByteArray();
+            key = KeyFactory.getInstance("RSA")
+                    .generatePrivate(new PKCS8EncodedKeySpec(keyBytes));
+        }
+
+        // Create KeyStore based on the private key/chain.
+        KeyStore ks = KeyStore.getInstance(KeyStore.getDefaultType());
+        ks.load(null);
+        ks.setKeyEntry("name", key, null, chain);
+
+        // Create SSLContext.
+        TrustManagerFactory tmf = TrustManagerFactory.getInstance("PKIX");
+        tmf.init(ks);
+        KeyManagerFactory kmf =
+                KeyManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm());
+        kmf.init(ks, null);
+        SSLContext context = SSLContext.getInstance("TLS");
+        context.init(kmf.getKeyManagers(), tmf.getTrustManagers(), null);
+
+        SSLServerSocket s = (SSLServerSocket) context.getServerSocketFactory().createServerSocket();
+        s.bind(null);
+        return s;
+    }
+
+    private void assertSuccessfulDownload(long id) throws Exception {
+        Cursor cursor = null;
+        DownloadManager dm =
+                (DownloadManager) getContext().getSystemService(Context.DOWNLOAD_SERVICE);
+        try {
+            cursor = dm.query(new DownloadManager.Query().setFilterById(id));
+            assertTrue(cursor.moveToNext());
+            assertEquals(DownloadManager.STATUS_SUCCESSFUL, cursor.getInt(
+                    cursor.getColumnIndex(DownloadManager.COLUMN_STATUS)));
+        } finally {
+            if (cursor != null) {
+                cursor.close();
+            }
+        }
+    }
+
+    private static final class DownloadCompleteReceiver extends BroadcastReceiver {
+        private HashSet<Long> mCompletedDownloads = new HashSet<>();
+
+        public DownloadCompleteReceiver() {
+        }
+
+        @Override
+        public void onReceive(Context context, Intent intent) {
+            synchronized(mCompletedDownloads) {
+                mCompletedDownloads.add(intent.getLongExtra(DownloadManager.EXTRA_DOWNLOAD_ID, -1));
+                mCompletedDownloads.notifyAll();
+            }
+        }
+
+        public void waitForDownloadComplete(long timeout, long id)
+                throws TimeoutException, InterruptedException  {
+            long deadline = SystemClock.elapsedRealtime() + timeout;
+            do {
+                synchronized (mCompletedDownloads) {
+                    long millisTillTimeout = deadline - SystemClock.elapsedRealtime();
+                    if (millisTillTimeout > 0) {
+                        mCompletedDownloads.wait(millisTillTimeout);
+                    }
+                    if (mCompletedDownloads.contains(id)) {
+                        return;
+                    }
+                }
+            } while (SystemClock.elapsedRealtime() < deadline);
+
+            throw new TimeoutException("Timed out waiting for download complete");
+        }
+    }
+
+
+}