Loading Android.mk +1 −1 Original line number Diff line number Diff line Loading @@ -25,7 +25,7 @@ LOCAL_SRC_FILES := $(call all-java-files-under, src/java) \ $(call all-logtags-files-under, src/java) \ $(call all-proto-files-under, proto) LOCAL_JAVA_LIBRARIES := voip-common ims-common services LOCAL_JAVA_LIBRARIES := voip-common ims-common services bouncycastle LOCAL_STATIC_JAVA_LIBRARIES := \ android.hardware.radio-V1.0-java \ android.hardware.radio-V1.1-java \ Loading src/java/com/android/internal/telephony/CarrierKeyDownloadManager.java +38 −15 Original line number Diff line number Diff line Loading @@ -16,8 +16,6 @@ package com.android.internal.telephony; import static android.preference.PreferenceManager.getDefaultSharedPreferences; import android.app.AlarmManager; import android.app.DownloadManager; import android.app.PendingIntent; Loading @@ -34,11 +32,11 @@ import android.telephony.ImsiEncryptionInfo; import android.telephony.SubscriptionManager; import android.telephony.TelephonyManager; import android.text.TextUtils; import android.util.Base64; import android.util.Log; import android.util.Pair; import com.android.internal.annotations.VisibleForTesting; import com.android.org.bouncycastle.util.io.pem.PemReader; import org.json.JSONArray; import org.json.JSONException; Loading @@ -50,11 +48,14 @@ import java.io.FileInputStream; import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader; import java.io.Reader; import java.security.PublicKey; import java.security.cert.CertificateFactory; import java.security.cert.X509Certificate; import java.util.Date; import static android.preference.PreferenceManager.getDefaultSharedPreferences; /** * This class contains logic to get Certificates and keep them current. * The class will be instantiated by various Phone implementations. Loading @@ -81,8 +82,11 @@ public class CarrierKeyDownloadManager { private static final String SEPARATOR = ":"; private static final String JSON_CERTIFICATE = "certificate"; private static final String JSON_TYPE = "type"; private static final String JSON_IDENTIFIER = "identifier"; // This is a hack to accomodate Verizon. Verizon insists on using the public-key // field to store the certificate. We'll just use which-ever is not null. private static final String JSON_CERTIFICATE_ALTERNATE = "public-key"; private static final String JSON_TYPE = "key-type"; private static final String JSON_IDENTIFIER = "key-identifier"; private static final String JSON_CARRIER_KEYS = "carrier-keys"; private static final String JSON_TYPE_VALUE_WLAN = "WLAN"; private static final String JSON_TYPE_VALUE_EPDG = "EPDG"; Loading Loading @@ -373,12 +377,12 @@ public class CarrierKeyDownloadManager { * Converts the string into a json object to retreive the nodes. The Json should have 3 nodes, * including the Carrier public key, the key type and the key identifier. Once the nodes have * been extracted, they get persisted to the database. Sample: * "carrier-keys": [ { "key": "", * "type": "WLAN", * "identifier": "" * "carrier-keys": [ { "certificate": "", * "key-type": "WLAN", * "key-identifier": "" * } ] * @param jsonStr the json string. * @param mccMnc contains the mcc, mnc * @param mccMnc contains the mcc, mnc. */ @VisibleForTesting public void parseJsonAndPersistKey(String jsonStr, String mccMnc) { Loading @@ -386,6 +390,7 @@ public class CarrierKeyDownloadManager { Log.e(LOG_TAG, "jsonStr or mcc, mnc: is empty"); return; } PemReader reader = null; try { String mcc = ""; String mnc = ""; Loading @@ -394,10 +399,16 @@ public class CarrierKeyDownloadManager { mnc = splitValue[1]; JSONObject jsonObj = new JSONObject(jsonStr); JSONArray keys = jsonObj.getJSONArray(JSON_CARRIER_KEYS); for (int i = 0; i < keys.length(); i++) { JSONObject key = keys.getJSONObject(i); String cert = key.getString(JSON_CERTIFICATE); // This is a hack to accomodate Verizon. Verizon insists on using the public-key // field to store the certificate. We'll just use which-ever is not null. String cert = null; if (key.has(JSON_CERTIFICATE)) { cert = key.getString(JSON_CERTIFICATE); } else { cert = key.getString(JSON_CERTIFICATE_ALTERNATE); } String typeString = key.getString(JSON_TYPE); int type = UNINITIALIZED_KEY_TYPE; if (typeString.equals(JSON_TYPE_VALUE_WLAN)) { Loading @@ -406,13 +417,26 @@ public class CarrierKeyDownloadManager { type = TelephonyManager.KEY_TYPE_EPDG; } String identifier = key.getString(JSON_IDENTIFIER); Pair<PublicKey, Long> keyInfo = getKeyInformation(cert); ByteArrayInputStream inStream = new ByteArrayInputStream(cert.getBytes()); Reader fReader = new BufferedReader(new InputStreamReader(inStream)); reader = new PemReader(fReader); Pair<PublicKey, Long> keyInfo = getKeyInformation(reader.readPemObject().getContent()); reader.close(); savePublicKey(keyInfo.first, type, identifier, keyInfo.second, mcc, mnc); } } catch (final JSONException e) { Log.e(LOG_TAG, "Json parsing error: " + e.getMessage()); } catch (final Exception e) { Log.e(LOG_TAG, "Exception getting certificate: " + e); } finally { try { if (reader != null) { reader.close(); } } catch (final Exception e) { Log.e(LOG_TAG, "Exception getting certificate: " + e); } } } Loading Loading @@ -491,9 +515,8 @@ public class CarrierKeyDownloadManager { * @return Pair containing the Public Key and the expiration date. **/ @VisibleForTesting public static Pair<PublicKey, Long> getKeyInformation(String certificate) throws Exception { byte[] derCert = Base64.decode(certificate.getBytes(), Base64.DEFAULT); InputStream inStream = new ByteArrayInputStream(derCert); public static Pair<PublicKey, Long> getKeyInformation(byte[] certificate) throws Exception { InputStream inStream = new ByteArrayInputStream(certificate); CertificateFactory cf = CertificateFactory.getInstance("X.509"); X509Certificate cert = (X509Certificate) cf.generateCertificate(inStream); Pair<PublicKey, Long> keyInformation = Loading tests/telephonytests/Android.mk +1 −1 Original line number Diff line number Diff line Loading @@ -7,7 +7,7 @@ LOCAL_SRC_FILES := $(call all-subdir-java-files) #LOCAL_STATIC_JAVA_LIBRARIES := librilproto-java LOCAL_JAVA_LIBRARIES := android.test.runner telephony-common ims-common services.core LOCAL_JAVA_LIBRARIES := android.test.runner telephony-common ims-common services.core bouncycastle LOCAL_STATIC_JAVA_LIBRARIES := guava \ frameworks-base-testutils \ mockito-target-minus-junit4 \ Loading tests/telephonytests/src/com/android/internal/telephony/CarrierKeyDownloadMgrTest.java +44 −7 Original line number Diff line number Diff line Loading @@ -15,8 +15,6 @@ */ package com.android.internal.telephony; import static android.preference.PreferenceManager.getDefaultSharedPreferences; import android.app.DownloadManager; import android.content.Context; import android.content.Intent; Loading @@ -28,18 +26,25 @@ import android.telephony.ImsiEncryptionInfo; import android.test.suitebuilder.annotation.SmallTest; import android.util.Pair; import com.android.org.bouncycastle.util.io.pem.PemReader; import org.junit.After; import org.junit.Before; import org.junit.Test; import org.mockito.Matchers; import org.mockito.MockitoAnnotations; import java.io.BufferedReader; import java.io.ByteArrayInputStream; import java.io.InputStreamReader; import java.io.Reader; import java.security.PublicKey; import java.text.SimpleDateFormat; import java.util.Calendar; import java.util.Date; import java.util.GregorianCalendar; import static android.preference.PreferenceManager.getDefaultSharedPreferences; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; Loading @@ -58,7 +63,12 @@ public class CarrierKeyDownloadMgrTest extends TelephonyTest { private String mURL = "http://www.google.com"; private String mJsonStr = "{ \"carrier-keys\": [ { \"certificate\": \"MIIFjzCCBHegAwIBAgIUPxj3SLif82Ky1RlUy8p2EWJCh8MwDQYJKoZIhvcNAQELBQAwgY0xCzAJBgNVBAYTAk5MMRIwEAYDVQQHEwlBbXN0ZXJkYW0xJTAjBgNVBAoTHFZlcml6b24gRW50ZXJwcmlzZSBTb2x1dGlvbnMxEzARBgNVBAsTCkN5YmVydHJ1c3QxLjAsBgNVBAMTJVZlcml6b24gUHVibGljIFN1cmVTZXJ2ZXIgQ0EgRzE0LVNIQTIwHhcNMTcwODE0MTc0MzM4WhcNMTkwODE0MTc0MzM4WjCBmTELMAkGA1UEBhMCVVMxEzARBgNVBAgTCk5ldyBKZXJzZXkxFjAUBgNVBAcTDUJhc2tpbmcgUmlkZ2UxIjAgBgNVBAoTGVZlcml6b24gRGF0YSBTZXJ2aWNlcyBMTEMxHzAdBgNVBAsTFk5ldHdvcmsgU3lzdGVtIFN1cHBvcnQxGDAWBgNVBAMTD3ZpMWx2Lmltc3ZtLmNvbTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBALUQKWTHi4Hjpd1LQwJ87RXa0Rs3rVonvVevliqdUH5BikjhAzvIqwPSXeRQqkaRTFIyp0NKcNqGdjAaHRo43gdHeWSH331sS6CMZDg988gZznskzCqJJo6ii5FuLC8qe2YDsHxT+CefXev2rn6Bj1ei2X74uZsy5KlkBRZfFHtPdK6/EK5TpzrvcXfDyOK1rn8FTno1bQOTAhL39GPcLhdrXV7AN+lu+EBpdCqlTdcoDxsqavi/91MwUIVEzxJmycKloT6OWfU44r7+L5SYYgc88NTaGL/BvCFwHRIa1ZgYSGeAPes45792MGG7tfr/ttAGp9UEwTv2zWTxzWnRP/UCAwEAAaOCAdcwggHTMAwGA1UdEwEB/wQCMAAwTAYDVR0gBEUwQzBBBgkrBgEEAbE+ATIwNDAyBggrBgEFBQcCARYmaHR0cHM6Ly9zZWN1cmUub21uaXJvb3QuY29tL3JlcG9zaXRvcnkwgakGCCsGAQUFBwEBBIGcMIGZMC0GCCsGAQUFBzABhiFodHRwOi8vdnBzc2cxNDIub2NzcC5vbW5pcm9vdC5jb20wMwYIKwYBBQUHMAKGJ2h0dHA6Ly9jYWNlcnQub21uaXJvb3QuY29tL3Zwc3NnMTQyLmNydDAzBggrBgEFBQcwAoYnaHR0cDovL2NhY2VydC5vbW5pcm9vdC5jb20vdnBzc2cxNDIuZGVyMBoGA1UdEQQTMBGCD3ZpMWx2Lmltc3ZtLmNvbTAOBgNVHQ8BAf8EBAMCBaAwHQYDVR0lBBYwFAYIKwYBBQUHAwEGCCsGAQUFBwMCMB8GA1UdIwQYMBaAFOQtu5EBZSYftHo/oxUlpM6MRDM7MD4GA1UdHwQ3MDUwM6AxoC+GLWh0dHA6Ly92cHNzZzE0Mi5jcmwub21uaXJvb3QuY29tL3Zwc3NnMTQyLmNybDAdBgNVHQ4EFgQUv5SaSyNM/yXw1v0N9TNpjsFCaPcwDQYJKoZIhvcNAQELBQADggEBACNJusTULj1KyV4RwiskKfp4wI9Hsz3ESbZS/ijF9D57BQ0UwkELU9r6rEAhsYLUvMq4sDhDbYIdupgP4MBzFnjkKult7VQm5W3nCcuHgXYFAJ9Y1a4OZAo/4hrHj70W9TsQ1ioSMjUT4F8bDUYZI0kcyH8e/+2DaTsLUpHw3L+Keu8PsJVBLnvcKJjWrZD/Bgd6JuaTX2G84i0rY0GJuO9CxLNJa6n61Mz5cqLYIuwKgiVgTA2n71YITyFICOFPFX1vSx35AWvD6aVYblxtC8mpCdF2h4s1iyrpXeji2GCJLwsNVtTtNQ4zWX3Gnq683wzkYZeyOHUyftIgAQZ+HsY=\", \"type\": \"WLAN\", \"identifier\": \"key1=value\"}]}"; private static final String CERT = "-----BEGIN CERTIFICATE-----\r\nMIIFjzCCBHegAwIBAgIUPxj3SLif82Ky1RlUy8p2EWJCh8MwDQYJKoZIhvcNAQELBQAwgY0xCzAJBgNVBAYTAk5MMRIwEAYDVQQHEwlBbXN0ZXJkYW0xJTAjBgNVBAoTHFZlcml6b24gRW50ZXJwcmlzZSBTb2x1dGlvbnMxEzARBgNVBAsTCkN5YmVydHJ1c3QxLjAsBgNVBAMTJVZlcml6b24gUHVibGljIFN1cmVTZXJ2ZXIgQ0EgRzE0LVNIQTIwHhcNMTcwODE0MTc0MzM4WhcNMTkwODE0MTc0MzM4WjCBmTELMAkGA1UEBhMCVVMxEzARBgNVBAgTCk5ldyBKZXJzZXkxFjAUBgNVBAcTDUJhc2tpbmcgUmlkZ2UxIjAgBgNVBAoTGVZlcml6b24gRGF0YSBTZXJ2aWNlcyBMTEMxHzAdBgNVBAsTFk5ldHdvcmsgU3lzdGVtIFN1cHBvcnQxGDAWBgNVBAMTD3ZpMWx2Lmltc3ZtLmNvbTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBALUQKWTHi4Hjpd1LQwJ87RXa0Rs3rVonvVevliqdUH5BikjhAzvIqwPSXeRQqkaRTFIyp0NKcNqGdjAaHRo43gdHeWSH331sS6CMZDg988gZznskzCqJJo6ii5FuLC8qe2YDsHxT+CefXev2rn6Bj1ei2X74uZsy5KlkBRZfFHtPdK6/EK5TpzrvcXfDyOK1rn8FTno1bQOTAhL39GPcLhdrXV7AN+lu+EBpdCqlTdcoDxsqavi/91MwUIVEzxJmycKloT6OWfU44r7+L5SYYgc88NTaGL/BvCFwHRIa1ZgYSGeAPes45792MGG7tfr/ttAGp9UEwTv2zWTxzWnRP/UCAwEAAaOCAdcwggHTMAwGA1UdEwEB/wQCMAAwTAYDVR0gBEUwQzBBBgkrBgEEAbE+ATIwNDAyBggrBgEFBQcCARYmaHR0cHM6Ly9zZWN1cmUub21uaXJvb3QuY29tL3JlcG9zaXRvcnkwgakGCCsGAQUFBwEBBIGcMIGZMC0GCCsGAQUFBzABhiFodHRwOi8vdnBzc2cxNDIub2NzcC5vbW5pcm9vdC5jb20wMwYIKwYBBQUHMAKGJ2h0dHA6Ly9jYWNlcnQub21uaXJvb3QuY29tL3Zwc3NnMTQyLmNydDAzBggrBgEFBQcwAoYnaHR0cDovL2NhY2VydC5vbW5pcm9vdC5jb20vdnBzc2cxNDIuZGVyMBoGA1UdEQQTMBGCD3ZpMWx2Lmltc3ZtLmNvbTAOBgNVHQ8BAf8EBAMCBaAwHQYDVR0lBBYwFAYIKwYBBQUHAwEGCCsGAQUFBwMCMB8GA1UdIwQYMBaAFOQtu5EBZSYftHo/oxUlpM6MRDM7MD4GA1UdHwQ3MDUwM6AxoC+GLWh0dHA6Ly92cHNzZzE0Mi5jcmwub21uaXJvb3QuY29tL3Zwc3NnMTQyLmNybDAdBgNVHQ4EFgQUv5SaSyNM/yXw1v0N9TNpjsFCaPcwDQYJKoZIhvcNAQELBQADggEBACNJusTULj1KyV4RwiskKfp4wI9Hsz3ESbZS/ijF9D57BQ0UwkELU9r6rEAhsYLUvMq4sDhDbYIdupgP4MBzFnjkKult7VQm5W3nCcuHgXYFAJ9Y1a4OZAo/4hrHj70W9TsQ1ioSMjUT4F8bDUYZI0kcyH8e/+2DaTsLUpHw3L+Keu8PsJVBLnvcKJjWrZD/Bgd6JuaTX2G84i0rY0GJuO9CxLNJa6n61Mz5cqLYIuwKgiVgTA2n71YITyFICOFPFX1vSx35AWvD6aVYblxtC8mpCdF2h4s1iyrpXeji2GCJLwsNVtTtNQ4zWX3Gnq683wzkYZeyOHUyftIgAQZ+HsY=\r\n-----END CERTIFICATE-----"; private String mJsonStr = "{ \"carrier-keys\": [ { \"certificate\": \"" + CERT + "\", \"key-type\": \"WLAN\", \"key-identifier\": \"key1=value\", \"expiration-date\": 1502577746000 }, { \"certificate\": \"" + CERT + "\", \"key-type\": \"WLAN\", \"key-identifier\": \"key1=value\", \"expiration-date\": 1502577746000 }]}"; private String mJsonStr1 = "{ \"carrier-keys\": [ { \"public-key\": \"" + CERT + "\", \"key-type\": \"WLAN\", \"key-identifier\": \"key1=value\", \"expiration-date\": 1502577746000 }, { \"public-key\": \"" + CERT + "\", \"key-type\": \"WLAN\", \"key-identifier\": \"key1=value\", \"expiration-date\": 1502577746000 }]}"; private class CarrierActionAgentHandler extends HandlerThread { Loading Loading @@ -134,17 +144,20 @@ public class CarrierKeyDownloadMgrTest extends TelephonyTest { Date expirationDate = new Date(mCarrierKeyDM.getExpirationDate()); assertTrue(dt.format(expirationDate).equals(dateExpected)); } /** * Checks if the json is parse correctly. * Verify if the savePublicKey method is called with the right params. * Verify that setCarrierInfoForImsiEncryption is called with the right params **/ @Test @SmallTest public void testParseJson() { String certificate = "MIIFjzCCBHegAwIBAgIUPxj3SLif82Ky1RlUy8p2EWJCh8MwDQYJKoZIhvcNAQELBQAwgY0xCzAJBgNVBAYTAk5MMRIwEAYDVQQHEwlBbXN0ZXJkYW0xJTAjBgNVBAoTHFZlcml6b24gRW50ZXJwcmlzZSBTb2x1dGlvbnMxEzARBgNVBAsTCkN5YmVydHJ1c3QxLjAsBgNVBAMTJVZlcml6b24gUHVibGljIFN1cmVTZXJ2ZXIgQ0EgRzE0LVNIQTIwHhcNMTcwODE0MTc0MzM4WhcNMTkwODE0MTc0MzM4WjCBmTELMAkGA1UEBhMCVVMxEzARBgNVBAgTCk5ldyBKZXJzZXkxFjAUBgNVBAcTDUJhc2tpbmcgUmlkZ2UxIjAgBgNVBAoTGVZlcml6b24gRGF0YSBTZXJ2aWNlcyBMTEMxHzAdBgNVBAsTFk5ldHdvcmsgU3lzdGVtIFN1cHBvcnQxGDAWBgNVBAMTD3ZpMWx2Lmltc3ZtLmNvbTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBALUQKWTHi4Hjpd1LQwJ87RXa0Rs3rVonvVevliqdUH5BikjhAzvIqwPSXeRQqkaRTFIyp0NKcNqGdjAaHRo43gdHeWSH331sS6CMZDg988gZznskzCqJJo6ii5FuLC8qe2YDsHxT+CefXev2rn6Bj1ei2X74uZsy5KlkBRZfFHtPdK6/EK5TpzrvcXfDyOK1rn8FTno1bQOTAhL39GPcLhdrXV7AN+lu+EBpdCqlTdcoDxsqavi/91MwUIVEzxJmycKloT6OWfU44r7+L5SYYgc88NTaGL/BvCFwHRIa1ZgYSGeAPes45792MGG7tfr/ttAGp9UEwTv2zWTxzWnRP/UCAwEAAaOCAdcwggHTMAwGA1UdEwEB/wQCMAAwTAYDVR0gBEUwQzBBBgkrBgEEAbE+ATIwNDAyBggrBgEFBQcCARYmaHR0cHM6Ly9zZWN1cmUub21uaXJvb3QuY29tL3JlcG9zaXRvcnkwgakGCCsGAQUFBwEBBIGcMIGZMC0GCCsGAQUFBzABhiFodHRwOi8vdnBzc2cxNDIub2NzcC5vbW5pcm9vdC5jb20wMwYIKwYBBQUHMAKGJ2h0dHA6Ly9jYWNlcnQub21uaXJvb3QuY29tL3Zwc3NnMTQyLmNydDAzBggrBgEFBQcwAoYnaHR0cDovL2NhY2VydC5vbW5pcm9vdC5jb20vdnBzc2cxNDIuZGVyMBoGA1UdEQQTMBGCD3ZpMWx2Lmltc3ZtLmNvbTAOBgNVHQ8BAf8EBAMCBaAwHQYDVR0lBBYwFAYIKwYBBQUHAwEGCCsGAQUFBwMCMB8GA1UdIwQYMBaAFOQtu5EBZSYftHo/oxUlpM6MRDM7MD4GA1UdHwQ3MDUwM6AxoC+GLWh0dHA6Ly92cHNzZzE0Mi5jcmwub21uaXJvb3QuY29tL3Zwc3NnMTQyLmNybDAdBgNVHQ4EFgQUv5SaSyNM/yXw1v0N9TNpjsFCaPcwDQYJKoZIhvcNAQELBQADggEBACNJusTULj1KyV4RwiskKfp4wI9Hsz3ESbZS/ijF9D57BQ0UwkELU9r6rEAhsYLUvMq4sDhDbYIdupgP4MBzFnjkKult7VQm5W3nCcuHgXYFAJ9Y1a4OZAo/4hrHj70W9TsQ1ioSMjUT4F8bDUYZI0kcyH8e/+2DaTsLUpHw3L+Keu8PsJVBLnvcKJjWrZD/Bgd6JuaTX2G84i0rY0GJuO9CxLNJa6n61Mz5cqLYIuwKgiVgTA2n71YITyFICOFPFX1vSx35AWvD6aVYblxtC8mpCdF2h4s1iyrpXeji2GCJLwsNVtTtNQ4zWX3Gnq683wzkYZeyOHUyftIgAQZ+HsY="; ByteArrayInputStream certBytes = new ByteArrayInputStream(CERT.getBytes()); Reader fRd = new BufferedReader(new InputStreamReader(certBytes)); PemReader reader = new PemReader(fRd); Pair<PublicKey, Long> keyInfo = null; try { keyInfo = CarrierKeyDownloadManager.getKeyInformation(certificate); keyInfo = mCarrierKeyDM.getKeyInformation(reader.readPemObject().getContent()); } catch (Exception e) { fail(LOG_TAG + "exception creating public key"); } Loading @@ -152,7 +165,31 @@ public class CarrierKeyDownloadMgrTest extends TelephonyTest { "key1=value", keyInfo.first, new Date(keyInfo.second)); String mccMnc = "310:270"; mCarrierKeyDM.parseJsonAndPersistKey(mJsonStr, mccMnc); verify(mPhone, times(1)).setCarrierInfoForImsiEncryption( verify(mPhone, times(2)).setCarrierInfoForImsiEncryption( (Matchers.refEq(imsiEncryptionInfo))); } /** * Checks if the json is parse correctly. * Same as testParseJason, except that the test looks for the "public-key" field. **/ @Test @SmallTest public void testParseJsonPublicKey() { ByteArrayInputStream certBytes = new ByteArrayInputStream(CERT.getBytes()); Reader fRd = new BufferedReader(new InputStreamReader(certBytes)); PemReader reader = new PemReader(fRd); Pair<PublicKey, Long> keyInfo = null; try { keyInfo = mCarrierKeyDM.getKeyInformation(reader.readPemObject().getContent()); } catch (Exception e) { fail(LOG_TAG + "exception creating public key"); } ImsiEncryptionInfo imsiEncryptionInfo = new ImsiEncryptionInfo("310", "270", 2, "key1=value", keyInfo.first, new Date(keyInfo.second)); String mccMnc = "310:270"; mCarrierKeyDM.parseJsonAndPersistKey(mJsonStr1, mccMnc); verify(mPhone, times(2)).setCarrierInfoForImsiEncryption( (Matchers.refEq(imsiEncryptionInfo))); } Loading Loading
Android.mk +1 −1 Original line number Diff line number Diff line Loading @@ -25,7 +25,7 @@ LOCAL_SRC_FILES := $(call all-java-files-under, src/java) \ $(call all-logtags-files-under, src/java) \ $(call all-proto-files-under, proto) LOCAL_JAVA_LIBRARIES := voip-common ims-common services LOCAL_JAVA_LIBRARIES := voip-common ims-common services bouncycastle LOCAL_STATIC_JAVA_LIBRARIES := \ android.hardware.radio-V1.0-java \ android.hardware.radio-V1.1-java \ Loading
src/java/com/android/internal/telephony/CarrierKeyDownloadManager.java +38 −15 Original line number Diff line number Diff line Loading @@ -16,8 +16,6 @@ package com.android.internal.telephony; import static android.preference.PreferenceManager.getDefaultSharedPreferences; import android.app.AlarmManager; import android.app.DownloadManager; import android.app.PendingIntent; Loading @@ -34,11 +32,11 @@ import android.telephony.ImsiEncryptionInfo; import android.telephony.SubscriptionManager; import android.telephony.TelephonyManager; import android.text.TextUtils; import android.util.Base64; import android.util.Log; import android.util.Pair; import com.android.internal.annotations.VisibleForTesting; import com.android.org.bouncycastle.util.io.pem.PemReader; import org.json.JSONArray; import org.json.JSONException; Loading @@ -50,11 +48,14 @@ import java.io.FileInputStream; import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader; import java.io.Reader; import java.security.PublicKey; import java.security.cert.CertificateFactory; import java.security.cert.X509Certificate; import java.util.Date; import static android.preference.PreferenceManager.getDefaultSharedPreferences; /** * This class contains logic to get Certificates and keep them current. * The class will be instantiated by various Phone implementations. Loading @@ -81,8 +82,11 @@ public class CarrierKeyDownloadManager { private static final String SEPARATOR = ":"; private static final String JSON_CERTIFICATE = "certificate"; private static final String JSON_TYPE = "type"; private static final String JSON_IDENTIFIER = "identifier"; // This is a hack to accomodate Verizon. Verizon insists on using the public-key // field to store the certificate. We'll just use which-ever is not null. private static final String JSON_CERTIFICATE_ALTERNATE = "public-key"; private static final String JSON_TYPE = "key-type"; private static final String JSON_IDENTIFIER = "key-identifier"; private static final String JSON_CARRIER_KEYS = "carrier-keys"; private static final String JSON_TYPE_VALUE_WLAN = "WLAN"; private static final String JSON_TYPE_VALUE_EPDG = "EPDG"; Loading Loading @@ -373,12 +377,12 @@ public class CarrierKeyDownloadManager { * Converts the string into a json object to retreive the nodes. The Json should have 3 nodes, * including the Carrier public key, the key type and the key identifier. Once the nodes have * been extracted, they get persisted to the database. Sample: * "carrier-keys": [ { "key": "", * "type": "WLAN", * "identifier": "" * "carrier-keys": [ { "certificate": "", * "key-type": "WLAN", * "key-identifier": "" * } ] * @param jsonStr the json string. * @param mccMnc contains the mcc, mnc * @param mccMnc contains the mcc, mnc. */ @VisibleForTesting public void parseJsonAndPersistKey(String jsonStr, String mccMnc) { Loading @@ -386,6 +390,7 @@ public class CarrierKeyDownloadManager { Log.e(LOG_TAG, "jsonStr or mcc, mnc: is empty"); return; } PemReader reader = null; try { String mcc = ""; String mnc = ""; Loading @@ -394,10 +399,16 @@ public class CarrierKeyDownloadManager { mnc = splitValue[1]; JSONObject jsonObj = new JSONObject(jsonStr); JSONArray keys = jsonObj.getJSONArray(JSON_CARRIER_KEYS); for (int i = 0; i < keys.length(); i++) { JSONObject key = keys.getJSONObject(i); String cert = key.getString(JSON_CERTIFICATE); // This is a hack to accomodate Verizon. Verizon insists on using the public-key // field to store the certificate. We'll just use which-ever is not null. String cert = null; if (key.has(JSON_CERTIFICATE)) { cert = key.getString(JSON_CERTIFICATE); } else { cert = key.getString(JSON_CERTIFICATE_ALTERNATE); } String typeString = key.getString(JSON_TYPE); int type = UNINITIALIZED_KEY_TYPE; if (typeString.equals(JSON_TYPE_VALUE_WLAN)) { Loading @@ -406,13 +417,26 @@ public class CarrierKeyDownloadManager { type = TelephonyManager.KEY_TYPE_EPDG; } String identifier = key.getString(JSON_IDENTIFIER); Pair<PublicKey, Long> keyInfo = getKeyInformation(cert); ByteArrayInputStream inStream = new ByteArrayInputStream(cert.getBytes()); Reader fReader = new BufferedReader(new InputStreamReader(inStream)); reader = new PemReader(fReader); Pair<PublicKey, Long> keyInfo = getKeyInformation(reader.readPemObject().getContent()); reader.close(); savePublicKey(keyInfo.first, type, identifier, keyInfo.second, mcc, mnc); } } catch (final JSONException e) { Log.e(LOG_TAG, "Json parsing error: " + e.getMessage()); } catch (final Exception e) { Log.e(LOG_TAG, "Exception getting certificate: " + e); } finally { try { if (reader != null) { reader.close(); } } catch (final Exception e) { Log.e(LOG_TAG, "Exception getting certificate: " + e); } } } Loading Loading @@ -491,9 +515,8 @@ public class CarrierKeyDownloadManager { * @return Pair containing the Public Key and the expiration date. **/ @VisibleForTesting public static Pair<PublicKey, Long> getKeyInformation(String certificate) throws Exception { byte[] derCert = Base64.decode(certificate.getBytes(), Base64.DEFAULT); InputStream inStream = new ByteArrayInputStream(derCert); public static Pair<PublicKey, Long> getKeyInformation(byte[] certificate) throws Exception { InputStream inStream = new ByteArrayInputStream(certificate); CertificateFactory cf = CertificateFactory.getInstance("X.509"); X509Certificate cert = (X509Certificate) cf.generateCertificate(inStream); Pair<PublicKey, Long> keyInformation = Loading
tests/telephonytests/Android.mk +1 −1 Original line number Diff line number Diff line Loading @@ -7,7 +7,7 @@ LOCAL_SRC_FILES := $(call all-subdir-java-files) #LOCAL_STATIC_JAVA_LIBRARIES := librilproto-java LOCAL_JAVA_LIBRARIES := android.test.runner telephony-common ims-common services.core LOCAL_JAVA_LIBRARIES := android.test.runner telephony-common ims-common services.core bouncycastle LOCAL_STATIC_JAVA_LIBRARIES := guava \ frameworks-base-testutils \ mockito-target-minus-junit4 \ Loading
tests/telephonytests/src/com/android/internal/telephony/CarrierKeyDownloadMgrTest.java +44 −7 Original line number Diff line number Diff line Loading @@ -15,8 +15,6 @@ */ package com.android.internal.telephony; import static android.preference.PreferenceManager.getDefaultSharedPreferences; import android.app.DownloadManager; import android.content.Context; import android.content.Intent; Loading @@ -28,18 +26,25 @@ import android.telephony.ImsiEncryptionInfo; import android.test.suitebuilder.annotation.SmallTest; import android.util.Pair; import com.android.org.bouncycastle.util.io.pem.PemReader; import org.junit.After; import org.junit.Before; import org.junit.Test; import org.mockito.Matchers; import org.mockito.MockitoAnnotations; import java.io.BufferedReader; import java.io.ByteArrayInputStream; import java.io.InputStreamReader; import java.io.Reader; import java.security.PublicKey; import java.text.SimpleDateFormat; import java.util.Calendar; import java.util.Date; import java.util.GregorianCalendar; import static android.preference.PreferenceManager.getDefaultSharedPreferences; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; Loading @@ -58,7 +63,12 @@ public class CarrierKeyDownloadMgrTest extends TelephonyTest { private String mURL = "http://www.google.com"; private String mJsonStr = "{ \"carrier-keys\": [ { \"certificate\": \"MIIFjzCCBHegAwIBAgIUPxj3SLif82Ky1RlUy8p2EWJCh8MwDQYJKoZIhvcNAQELBQAwgY0xCzAJBgNVBAYTAk5MMRIwEAYDVQQHEwlBbXN0ZXJkYW0xJTAjBgNVBAoTHFZlcml6b24gRW50ZXJwcmlzZSBTb2x1dGlvbnMxEzARBgNVBAsTCkN5YmVydHJ1c3QxLjAsBgNVBAMTJVZlcml6b24gUHVibGljIFN1cmVTZXJ2ZXIgQ0EgRzE0LVNIQTIwHhcNMTcwODE0MTc0MzM4WhcNMTkwODE0MTc0MzM4WjCBmTELMAkGA1UEBhMCVVMxEzARBgNVBAgTCk5ldyBKZXJzZXkxFjAUBgNVBAcTDUJhc2tpbmcgUmlkZ2UxIjAgBgNVBAoTGVZlcml6b24gRGF0YSBTZXJ2aWNlcyBMTEMxHzAdBgNVBAsTFk5ldHdvcmsgU3lzdGVtIFN1cHBvcnQxGDAWBgNVBAMTD3ZpMWx2Lmltc3ZtLmNvbTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBALUQKWTHi4Hjpd1LQwJ87RXa0Rs3rVonvVevliqdUH5BikjhAzvIqwPSXeRQqkaRTFIyp0NKcNqGdjAaHRo43gdHeWSH331sS6CMZDg988gZznskzCqJJo6ii5FuLC8qe2YDsHxT+CefXev2rn6Bj1ei2X74uZsy5KlkBRZfFHtPdK6/EK5TpzrvcXfDyOK1rn8FTno1bQOTAhL39GPcLhdrXV7AN+lu+EBpdCqlTdcoDxsqavi/91MwUIVEzxJmycKloT6OWfU44r7+L5SYYgc88NTaGL/BvCFwHRIa1ZgYSGeAPes45792MGG7tfr/ttAGp9UEwTv2zWTxzWnRP/UCAwEAAaOCAdcwggHTMAwGA1UdEwEB/wQCMAAwTAYDVR0gBEUwQzBBBgkrBgEEAbE+ATIwNDAyBggrBgEFBQcCARYmaHR0cHM6Ly9zZWN1cmUub21uaXJvb3QuY29tL3JlcG9zaXRvcnkwgakGCCsGAQUFBwEBBIGcMIGZMC0GCCsGAQUFBzABhiFodHRwOi8vdnBzc2cxNDIub2NzcC5vbW5pcm9vdC5jb20wMwYIKwYBBQUHMAKGJ2h0dHA6Ly9jYWNlcnQub21uaXJvb3QuY29tL3Zwc3NnMTQyLmNydDAzBggrBgEFBQcwAoYnaHR0cDovL2NhY2VydC5vbW5pcm9vdC5jb20vdnBzc2cxNDIuZGVyMBoGA1UdEQQTMBGCD3ZpMWx2Lmltc3ZtLmNvbTAOBgNVHQ8BAf8EBAMCBaAwHQYDVR0lBBYwFAYIKwYBBQUHAwEGCCsGAQUFBwMCMB8GA1UdIwQYMBaAFOQtu5EBZSYftHo/oxUlpM6MRDM7MD4GA1UdHwQ3MDUwM6AxoC+GLWh0dHA6Ly92cHNzZzE0Mi5jcmwub21uaXJvb3QuY29tL3Zwc3NnMTQyLmNybDAdBgNVHQ4EFgQUv5SaSyNM/yXw1v0N9TNpjsFCaPcwDQYJKoZIhvcNAQELBQADggEBACNJusTULj1KyV4RwiskKfp4wI9Hsz3ESbZS/ijF9D57BQ0UwkELU9r6rEAhsYLUvMq4sDhDbYIdupgP4MBzFnjkKult7VQm5W3nCcuHgXYFAJ9Y1a4OZAo/4hrHj70W9TsQ1ioSMjUT4F8bDUYZI0kcyH8e/+2DaTsLUpHw3L+Keu8PsJVBLnvcKJjWrZD/Bgd6JuaTX2G84i0rY0GJuO9CxLNJa6n61Mz5cqLYIuwKgiVgTA2n71YITyFICOFPFX1vSx35AWvD6aVYblxtC8mpCdF2h4s1iyrpXeji2GCJLwsNVtTtNQ4zWX3Gnq683wzkYZeyOHUyftIgAQZ+HsY=\", \"type\": \"WLAN\", \"identifier\": \"key1=value\"}]}"; private static final String CERT = "-----BEGIN CERTIFICATE-----\r\nMIIFjzCCBHegAwIBAgIUPxj3SLif82Ky1RlUy8p2EWJCh8MwDQYJKoZIhvcNAQELBQAwgY0xCzAJBgNVBAYTAk5MMRIwEAYDVQQHEwlBbXN0ZXJkYW0xJTAjBgNVBAoTHFZlcml6b24gRW50ZXJwcmlzZSBTb2x1dGlvbnMxEzARBgNVBAsTCkN5YmVydHJ1c3QxLjAsBgNVBAMTJVZlcml6b24gUHVibGljIFN1cmVTZXJ2ZXIgQ0EgRzE0LVNIQTIwHhcNMTcwODE0MTc0MzM4WhcNMTkwODE0MTc0MzM4WjCBmTELMAkGA1UEBhMCVVMxEzARBgNVBAgTCk5ldyBKZXJzZXkxFjAUBgNVBAcTDUJhc2tpbmcgUmlkZ2UxIjAgBgNVBAoTGVZlcml6b24gRGF0YSBTZXJ2aWNlcyBMTEMxHzAdBgNVBAsTFk5ldHdvcmsgU3lzdGVtIFN1cHBvcnQxGDAWBgNVBAMTD3ZpMWx2Lmltc3ZtLmNvbTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBALUQKWTHi4Hjpd1LQwJ87RXa0Rs3rVonvVevliqdUH5BikjhAzvIqwPSXeRQqkaRTFIyp0NKcNqGdjAaHRo43gdHeWSH331sS6CMZDg988gZznskzCqJJo6ii5FuLC8qe2YDsHxT+CefXev2rn6Bj1ei2X74uZsy5KlkBRZfFHtPdK6/EK5TpzrvcXfDyOK1rn8FTno1bQOTAhL39GPcLhdrXV7AN+lu+EBpdCqlTdcoDxsqavi/91MwUIVEzxJmycKloT6OWfU44r7+L5SYYgc88NTaGL/BvCFwHRIa1ZgYSGeAPes45792MGG7tfr/ttAGp9UEwTv2zWTxzWnRP/UCAwEAAaOCAdcwggHTMAwGA1UdEwEB/wQCMAAwTAYDVR0gBEUwQzBBBgkrBgEEAbE+ATIwNDAyBggrBgEFBQcCARYmaHR0cHM6Ly9zZWN1cmUub21uaXJvb3QuY29tL3JlcG9zaXRvcnkwgakGCCsGAQUFBwEBBIGcMIGZMC0GCCsGAQUFBzABhiFodHRwOi8vdnBzc2cxNDIub2NzcC5vbW5pcm9vdC5jb20wMwYIKwYBBQUHMAKGJ2h0dHA6Ly9jYWNlcnQub21uaXJvb3QuY29tL3Zwc3NnMTQyLmNydDAzBggrBgEFBQcwAoYnaHR0cDovL2NhY2VydC5vbW5pcm9vdC5jb20vdnBzc2cxNDIuZGVyMBoGA1UdEQQTMBGCD3ZpMWx2Lmltc3ZtLmNvbTAOBgNVHQ8BAf8EBAMCBaAwHQYDVR0lBBYwFAYIKwYBBQUHAwEGCCsGAQUFBwMCMB8GA1UdIwQYMBaAFOQtu5EBZSYftHo/oxUlpM6MRDM7MD4GA1UdHwQ3MDUwM6AxoC+GLWh0dHA6Ly92cHNzZzE0Mi5jcmwub21uaXJvb3QuY29tL3Zwc3NnMTQyLmNybDAdBgNVHQ4EFgQUv5SaSyNM/yXw1v0N9TNpjsFCaPcwDQYJKoZIhvcNAQELBQADggEBACNJusTULj1KyV4RwiskKfp4wI9Hsz3ESbZS/ijF9D57BQ0UwkELU9r6rEAhsYLUvMq4sDhDbYIdupgP4MBzFnjkKult7VQm5W3nCcuHgXYFAJ9Y1a4OZAo/4hrHj70W9TsQ1ioSMjUT4F8bDUYZI0kcyH8e/+2DaTsLUpHw3L+Keu8PsJVBLnvcKJjWrZD/Bgd6JuaTX2G84i0rY0GJuO9CxLNJa6n61Mz5cqLYIuwKgiVgTA2n71YITyFICOFPFX1vSx35AWvD6aVYblxtC8mpCdF2h4s1iyrpXeji2GCJLwsNVtTtNQ4zWX3Gnq683wzkYZeyOHUyftIgAQZ+HsY=\r\n-----END CERTIFICATE-----"; private String mJsonStr = "{ \"carrier-keys\": [ { \"certificate\": \"" + CERT + "\", \"key-type\": \"WLAN\", \"key-identifier\": \"key1=value\", \"expiration-date\": 1502577746000 }, { \"certificate\": \"" + CERT + "\", \"key-type\": \"WLAN\", \"key-identifier\": \"key1=value\", \"expiration-date\": 1502577746000 }]}"; private String mJsonStr1 = "{ \"carrier-keys\": [ { \"public-key\": \"" + CERT + "\", \"key-type\": \"WLAN\", \"key-identifier\": \"key1=value\", \"expiration-date\": 1502577746000 }, { \"public-key\": \"" + CERT + "\", \"key-type\": \"WLAN\", \"key-identifier\": \"key1=value\", \"expiration-date\": 1502577746000 }]}"; private class CarrierActionAgentHandler extends HandlerThread { Loading Loading @@ -134,17 +144,20 @@ public class CarrierKeyDownloadMgrTest extends TelephonyTest { Date expirationDate = new Date(mCarrierKeyDM.getExpirationDate()); assertTrue(dt.format(expirationDate).equals(dateExpected)); } /** * Checks if the json is parse correctly. * Verify if the savePublicKey method is called with the right params. * Verify that setCarrierInfoForImsiEncryption is called with the right params **/ @Test @SmallTest public void testParseJson() { String certificate = "MIIFjzCCBHegAwIBAgIUPxj3SLif82Ky1RlUy8p2EWJCh8MwDQYJKoZIhvcNAQELBQAwgY0xCzAJBgNVBAYTAk5MMRIwEAYDVQQHEwlBbXN0ZXJkYW0xJTAjBgNVBAoTHFZlcml6b24gRW50ZXJwcmlzZSBTb2x1dGlvbnMxEzARBgNVBAsTCkN5YmVydHJ1c3QxLjAsBgNVBAMTJVZlcml6b24gUHVibGljIFN1cmVTZXJ2ZXIgQ0EgRzE0LVNIQTIwHhcNMTcwODE0MTc0MzM4WhcNMTkwODE0MTc0MzM4WjCBmTELMAkGA1UEBhMCVVMxEzARBgNVBAgTCk5ldyBKZXJzZXkxFjAUBgNVBAcTDUJhc2tpbmcgUmlkZ2UxIjAgBgNVBAoTGVZlcml6b24gRGF0YSBTZXJ2aWNlcyBMTEMxHzAdBgNVBAsTFk5ldHdvcmsgU3lzdGVtIFN1cHBvcnQxGDAWBgNVBAMTD3ZpMWx2Lmltc3ZtLmNvbTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBALUQKWTHi4Hjpd1LQwJ87RXa0Rs3rVonvVevliqdUH5BikjhAzvIqwPSXeRQqkaRTFIyp0NKcNqGdjAaHRo43gdHeWSH331sS6CMZDg988gZznskzCqJJo6ii5FuLC8qe2YDsHxT+CefXev2rn6Bj1ei2X74uZsy5KlkBRZfFHtPdK6/EK5TpzrvcXfDyOK1rn8FTno1bQOTAhL39GPcLhdrXV7AN+lu+EBpdCqlTdcoDxsqavi/91MwUIVEzxJmycKloT6OWfU44r7+L5SYYgc88NTaGL/BvCFwHRIa1ZgYSGeAPes45792MGG7tfr/ttAGp9UEwTv2zWTxzWnRP/UCAwEAAaOCAdcwggHTMAwGA1UdEwEB/wQCMAAwTAYDVR0gBEUwQzBBBgkrBgEEAbE+ATIwNDAyBggrBgEFBQcCARYmaHR0cHM6Ly9zZWN1cmUub21uaXJvb3QuY29tL3JlcG9zaXRvcnkwgakGCCsGAQUFBwEBBIGcMIGZMC0GCCsGAQUFBzABhiFodHRwOi8vdnBzc2cxNDIub2NzcC5vbW5pcm9vdC5jb20wMwYIKwYBBQUHMAKGJ2h0dHA6Ly9jYWNlcnQub21uaXJvb3QuY29tL3Zwc3NnMTQyLmNydDAzBggrBgEFBQcwAoYnaHR0cDovL2NhY2VydC5vbW5pcm9vdC5jb20vdnBzc2cxNDIuZGVyMBoGA1UdEQQTMBGCD3ZpMWx2Lmltc3ZtLmNvbTAOBgNVHQ8BAf8EBAMCBaAwHQYDVR0lBBYwFAYIKwYBBQUHAwEGCCsGAQUFBwMCMB8GA1UdIwQYMBaAFOQtu5EBZSYftHo/oxUlpM6MRDM7MD4GA1UdHwQ3MDUwM6AxoC+GLWh0dHA6Ly92cHNzZzE0Mi5jcmwub21uaXJvb3QuY29tL3Zwc3NnMTQyLmNybDAdBgNVHQ4EFgQUv5SaSyNM/yXw1v0N9TNpjsFCaPcwDQYJKoZIhvcNAQELBQADggEBACNJusTULj1KyV4RwiskKfp4wI9Hsz3ESbZS/ijF9D57BQ0UwkELU9r6rEAhsYLUvMq4sDhDbYIdupgP4MBzFnjkKult7VQm5W3nCcuHgXYFAJ9Y1a4OZAo/4hrHj70W9TsQ1ioSMjUT4F8bDUYZI0kcyH8e/+2DaTsLUpHw3L+Keu8PsJVBLnvcKJjWrZD/Bgd6JuaTX2G84i0rY0GJuO9CxLNJa6n61Mz5cqLYIuwKgiVgTA2n71YITyFICOFPFX1vSx35AWvD6aVYblxtC8mpCdF2h4s1iyrpXeji2GCJLwsNVtTtNQ4zWX3Gnq683wzkYZeyOHUyftIgAQZ+HsY="; ByteArrayInputStream certBytes = new ByteArrayInputStream(CERT.getBytes()); Reader fRd = new BufferedReader(new InputStreamReader(certBytes)); PemReader reader = new PemReader(fRd); Pair<PublicKey, Long> keyInfo = null; try { keyInfo = CarrierKeyDownloadManager.getKeyInformation(certificate); keyInfo = mCarrierKeyDM.getKeyInformation(reader.readPemObject().getContent()); } catch (Exception e) { fail(LOG_TAG + "exception creating public key"); } Loading @@ -152,7 +165,31 @@ public class CarrierKeyDownloadMgrTest extends TelephonyTest { "key1=value", keyInfo.first, new Date(keyInfo.second)); String mccMnc = "310:270"; mCarrierKeyDM.parseJsonAndPersistKey(mJsonStr, mccMnc); verify(mPhone, times(1)).setCarrierInfoForImsiEncryption( verify(mPhone, times(2)).setCarrierInfoForImsiEncryption( (Matchers.refEq(imsiEncryptionInfo))); } /** * Checks if the json is parse correctly. * Same as testParseJason, except that the test looks for the "public-key" field. **/ @Test @SmallTest public void testParseJsonPublicKey() { ByteArrayInputStream certBytes = new ByteArrayInputStream(CERT.getBytes()); Reader fRd = new BufferedReader(new InputStreamReader(certBytes)); PemReader reader = new PemReader(fRd); Pair<PublicKey, Long> keyInfo = null; try { keyInfo = mCarrierKeyDM.getKeyInformation(reader.readPemObject().getContent()); } catch (Exception e) { fail(LOG_TAG + "exception creating public key"); } ImsiEncryptionInfo imsiEncryptionInfo = new ImsiEncryptionInfo("310", "270", 2, "key1=value", keyInfo.first, new Date(keyInfo.second)); String mccMnc = "310:270"; mCarrierKeyDM.parseJsonAndPersistKey(mJsonStr1, mccMnc); verify(mPhone, times(2)).setCarrierInfoForImsiEncryption( (Matchers.refEq(imsiEncryptionInfo))); } Loading