Loading core/java/android/security/IKeystoreService.java +26 −0 Original line number Diff line number Diff line Loading @@ -148,6 +148,10 @@ public interface IKeystoreService extends IInterface { for (int i = 0; i < size; i++) { _result[i] = _reply.readString(); } int _ret = _reply.readInt(); if (_ret != 1) { return null; } } finally { _reply.recycle(); _data.recycle(); Loading Loading @@ -401,6 +405,25 @@ public interface IKeystoreService extends IInterface { } return _result; } @Override public int migrate(String name, int targetUid) throws RemoteException { Parcel _data = Parcel.obtain(); Parcel _reply = Parcel.obtain(); int _result; try { _data.writeInterfaceToken(DESCRIPTOR); _data.writeString(name); _data.writeInt(targetUid); mRemote.transact(Stub.TRANSACTION_migrate, _data, _reply, 0); _reply.readException(); _result = _reply.readInt(); } finally { _reply.recycle(); _data.recycle(); } return _result; } } private static final String DESCRIPTOR = "android.security.keystore"; Loading @@ -425,6 +448,7 @@ public interface IKeystoreService extends IInterface { static final int TRANSACTION_grant = IBinder.FIRST_CALL_TRANSACTION + 17; static final int TRANSACTION_ungrant = IBinder.FIRST_CALL_TRANSACTION + 18; static final int TRANSACTION_getmtime = IBinder.FIRST_CALL_TRANSACTION + 19; static final int TRANSACTION_migrate = IBinder.FIRST_CALL_TRANSACTION + 20; /** * Cast an IBinder object into an IKeystoreService interface, generating Loading Loading @@ -509,4 +533,6 @@ public interface IKeystoreService extends IInterface { public int ungrant(String name, int granteeUid) throws RemoteException; public long getmtime(String name) throws RemoteException; public int migrate(String name, int targetUid) throws RemoteException; } keystore/java/android/security/AndroidKeyStore.java +25 −20 Original line number Diff line number Diff line Loading @@ -453,6 +453,7 @@ public class AndroidKeyStore extends KeyStoreSpi { * convention. */ final String[] certAliases = mKeyStore.saw(Credentials.USER_CERTIFICATE); if (certAliases != null) { for (String alias : certAliases) { final byte[] certBytes = mKeyStore.get(Credentials.USER_CERTIFICATE + alias); if (certBytes == null) { Loading @@ -466,12 +467,14 @@ public class AndroidKeyStore extends KeyStoreSpi { return alias; } } } /* * Look at all the TrustedCertificateEntry types. Skip all the * PrivateKeyEntry we looked at above. */ final String[] caAliases = mKeyStore.saw(Credentials.CA_CERTIFICATE); if (certAliases != null) { for (String alias : caAliases) { if (nonCaEntries.contains(alias)) { continue; Loading @@ -482,11 +485,13 @@ public class AndroidKeyStore extends KeyStoreSpi { continue; } final Certificate c = toCertificate(mKeyStore.get(Credentials.CA_CERTIFICATE + alias)); final Certificate c = toCertificate(mKeyStore.get(Credentials.CA_CERTIFICATE + alias)); if (cert.equals(c)) { return alias; } } } return null; } Loading keystore/java/android/security/KeyStore.java +51 −14 Original line number Diff line number Diff line Loading @@ -87,42 +87,58 @@ public class KeyStore { } } public boolean put(String key, byte[] value) { public boolean put(String key, byte[] value, int uid) { try { return mBinder.insert(key, value, -1) == NO_ERROR; return mBinder.insert(key, value, uid) == NO_ERROR; } catch (RemoteException e) { Log.w(TAG, "Cannot connect to keystore", e); return false; } } public boolean delete(String key) { public boolean put(String key, byte[] value) { return put(key, value, -1); } public boolean delete(String key, int uid) { try { return mBinder.del(key, -1) == NO_ERROR; return mBinder.del(key, uid) == NO_ERROR; } catch (RemoteException e) { Log.w(TAG, "Cannot connect to keystore", e); return false; } } public boolean contains(String key) { public boolean delete(String key) { return delete(key, -1); } public boolean contains(String key, int uid) { try { return mBinder.exist(key, -1) == NO_ERROR; return mBinder.exist(key, uid) == NO_ERROR; } catch (RemoteException e) { Log.w(TAG, "Cannot connect to keystore", e); return false; } } public String[] saw(String prefix) { public boolean contains(String key) { return contains(key, -1); } public String[] saw(String prefix, int uid) { try { return mBinder.saw(prefix, -1); return mBinder.saw(prefix, uid); } catch (RemoteException e) { Log.w(TAG, "Cannot connect to keystore", e); return null; } } public String[] saw(String prefix) { return saw(prefix, -1); } public boolean reset() { try { return mBinder.reset() == NO_ERROR; Loading Loading @@ -169,24 +185,32 @@ public class KeyStore { } } public boolean generate(String key) { public boolean generate(String key, int uid) { try { return mBinder.generate(key, -1) == NO_ERROR; return mBinder.generate(key, uid) == NO_ERROR; } catch (RemoteException e) { Log.w(TAG, "Cannot connect to keystore", e); return false; } } public boolean importKey(String keyName, byte[] key) { public boolean generate(String key) { return generate(key, -1); } public boolean importKey(String keyName, byte[] key, int uid) { try { return mBinder.import_key(keyName, key, -1) == NO_ERROR; return mBinder.import_key(keyName, key, uid) == NO_ERROR; } catch (RemoteException e) { Log.w(TAG, "Cannot connect to keystore", e); return false; } } public boolean importKey(String keyName, byte[] key) { return importKey(keyName, key, -1); } public byte[] getPubkey(String key) { try { return mBinder.get_pubkey(key); Loading @@ -196,15 +220,19 @@ public class KeyStore { } } public boolean delKey(String key) { public boolean delKey(String key, int uid) { try { return mBinder.del_key(key, -1) == NO_ERROR; return mBinder.del_key(key, uid) == NO_ERROR; } catch (RemoteException e) { Log.w(TAG, "Cannot connect to keystore", e); return false; } } public boolean delKey(String key) { return delKey(key, -1); } public byte[] sign(String key, byte[] data) { try { return mBinder.sign(key, data); Loading Loading @@ -259,6 +287,15 @@ public class KeyStore { } } public boolean migrate(String key, int uid) { try { return mBinder.migrate(key, uid) == NO_ERROR; } catch (RemoteException e) { Log.w(TAG, "Cannot connect to keystore", e); return false; } } public int getLastError() { return mError; } Loading keystore/tests/src/android/security/AndroidKeyPairGeneratorTest.java +3 −1 Original line number Diff line number Diff line Loading @@ -67,7 +67,9 @@ public class AndroidKeyPairGeneratorTest extends AndroidTestCase { assertTrue(mAndroidKeyStore.password("1111")); assertTrue(mAndroidKeyStore.isUnlocked()); assertEquals(0, mAndroidKeyStore.saw("").length); String[] aliases = mAndroidKeyStore.saw(""); assertNotNull(aliases); assertEquals(0, aliases.length); mGenerator = java.security.KeyPairGenerator.getInstance(AndroidKeyPairGenerator.NAME); } Loading keystore/tests/src/android/security/KeyStoreTest.java +185 −6 Original line number Diff line number Diff line Loading @@ -17,6 +17,7 @@ package android.security; import android.app.Activity; import android.os.Process; import android.security.KeyStore; import android.test.ActivityUnitTestCase; import android.test.AssertionFailedError; Loading Loading @@ -128,7 +129,7 @@ public class KeyStoreTest extends ActivityUnitTestCase<Activity> { super.tearDown(); } public void teststate() throws Exception { public void testState() throws Exception { assertEquals(KeyStore.State.UNINITIALIZED, mKeyStore.state()); } Loading @@ -154,6 +155,24 @@ public class KeyStoreTest extends ActivityUnitTestCase<Activity> { assertTrue(Arrays.equals(TEST_KEYVALUE, mKeyStore.get(TEST_KEYNAME))); } public void testPut_grantedUid_Wifi() throws Exception { assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); assertFalse(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE, Process.WIFI_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); mKeyStore.password(TEST_PASSWD); assertTrue(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE, Process.WIFI_UID)); assertTrue(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); } public void testPut_ungrantedUid_Bluetooth() throws Exception { assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); mKeyStore.password(TEST_PASSWD); assertFalse(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); } public void testI18n() throws Exception { assertFalse(mKeyStore.put(TEST_I18N_KEY, TEST_I18N_VALUE)); assertFalse(mKeyStore.contains(TEST_I18N_KEY)); Loading @@ -167,22 +186,64 @@ public class KeyStoreTest extends ActivityUnitTestCase<Activity> { mKeyStore.password(TEST_PASSWD); assertFalse(mKeyStore.delete(TEST_KEYNAME)); mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE); assertTrue(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE)); assertTrue(Arrays.equals(TEST_KEYVALUE, mKeyStore.get(TEST_KEYNAME))); assertTrue(mKeyStore.delete(TEST_KEYNAME)); assertNull(mKeyStore.get(TEST_KEYNAME)); } public void testDelete_grantedUid_Wifi() throws Exception { assertFalse(mKeyStore.delete(TEST_KEYNAME, Process.WIFI_UID)); mKeyStore.password(TEST_PASSWD); assertFalse(mKeyStore.delete(TEST_KEYNAME, Process.WIFI_UID)); assertTrue(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE, Process.WIFI_UID)); assertTrue(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); assertTrue(mKeyStore.delete(TEST_KEYNAME, Process.WIFI_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); } public void testDelete_ungrantedUid_Bluetooth() throws Exception { assertFalse(mKeyStore.delete(TEST_KEYNAME, Process.BLUETOOTH_UID)); mKeyStore.password(TEST_PASSWD); assertFalse(mKeyStore.delete(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.delete(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); } public void testContains() throws Exception { assertFalse(mKeyStore.contains(TEST_KEYNAME)); mKeyStore.password(TEST_PASSWD); assertTrue(mKeyStore.password(TEST_PASSWD)); assertFalse(mKeyStore.contains(TEST_KEYNAME)); mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE); assertTrue(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE)); assertTrue(mKeyStore.contains(TEST_KEYNAME)); } public void testContains_grantedUid_Wifi() throws Exception { assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); assertTrue(mKeyStore.password(TEST_PASSWD)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); assertTrue(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE, Process.WIFI_UID)); assertTrue(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); } public void testContains_grantedUid_Bluetooth() throws Exception { assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertTrue(mKeyStore.password(TEST_PASSWD)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); } public void testSaw() throws Exception { String[] emptyResult = mKeyStore.saw(TEST_KEYNAME); assertNotNull(emptyResult); Loading @@ -198,6 +259,48 @@ public class KeyStoreTest extends ActivityUnitTestCase<Activity> { new HashSet(Arrays.asList(results))); } public void testSaw_ungrantedUid_Bluetooth() throws Exception { String[] results1 = mKeyStore.saw(TEST_KEYNAME, Process.BLUETOOTH_UID); assertNull(results1); mKeyStore.password(TEST_PASSWD); mKeyStore.put(TEST_KEYNAME1, TEST_KEYVALUE); mKeyStore.put(TEST_KEYNAME2, TEST_KEYVALUE); String[] results2 = mKeyStore.saw(TEST_KEYNAME, Process.BLUETOOTH_UID); assertNull(results2); } public void testSaw_grantedUid_Wifi() throws Exception { String[] results1 = mKeyStore.saw(TEST_KEYNAME, Process.WIFI_UID); assertNotNull(results1); assertEquals(0, results1.length); mKeyStore.password(TEST_PASSWD); mKeyStore.put(TEST_KEYNAME1, TEST_KEYVALUE, Process.WIFI_UID); mKeyStore.put(TEST_KEYNAME2, TEST_KEYVALUE, Process.WIFI_UID); String[] results2 = mKeyStore.saw(TEST_KEYNAME, Process.WIFI_UID); assertEquals(new HashSet(Arrays.asList(TEST_KEYNAME1.substring(TEST_KEYNAME.length()), TEST_KEYNAME2.substring(TEST_KEYNAME.length()))), new HashSet(Arrays.asList(results2))); } public void testSaw_grantedUid_Vpn() throws Exception { String[] results1 = mKeyStore.saw(TEST_KEYNAME, Process.VPN_UID); assertNotNull(results1); assertEquals(0, results1.length); mKeyStore.password(TEST_PASSWD); mKeyStore.put(TEST_KEYNAME1, TEST_KEYVALUE, Process.VPN_UID); mKeyStore.put(TEST_KEYNAME2, TEST_KEYVALUE, Process.VPN_UID); String[] results2 = mKeyStore.saw(TEST_KEYNAME, Process.VPN_UID); assertEquals(new HashSet(Arrays.asList(TEST_KEYNAME1.substring(TEST_KEYNAME.length()), TEST_KEYNAME2.substring(TEST_KEYNAME.length()))), new HashSet(Arrays.asList(results2))); } public void testLock() throws Exception { assertFalse(mKeyStore.lock()); Loading Loading @@ -239,17 +342,57 @@ public class KeyStoreTest extends ActivityUnitTestCase<Activity> { } public void testGenerate_Success() throws Exception { mKeyStore.password(TEST_PASSWD); assertTrue(mKeyStore.password(TEST_PASSWD)); assertTrue("Should be able to generate key when unlocked", mKeyStore.generate(TEST_KEYNAME)); assertTrue(mKeyStore.contains(TEST_KEYNAME)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); } public void testGenerate_grantedUid_Wifi_Success() throws Exception { assertTrue(mKeyStore.password(TEST_PASSWD)); assertTrue("Should be able to generate key when unlocked", mKeyStore.generate(TEST_KEYNAME, Process.WIFI_UID)); assertTrue(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME)); } public void testGenerate_ungrantedUid_Bluetooth_Failure() throws Exception { assertTrue(mKeyStore.password(TEST_PASSWD)); assertFalse(mKeyStore.generate(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME)); } public void testImport_Success() throws Exception { mKeyStore.password(TEST_PASSWD); assertTrue(mKeyStore.password(TEST_PASSWD)); assertTrue("Should be able to import key when unlocked", mKeyStore.importKey(TEST_KEYNAME, PRIVKEY_BYTES)); assertTrue(mKeyStore.contains(TEST_KEYNAME)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); } public void testImport_grantedUid_Wifi_Success() throws Exception { assertTrue(mKeyStore.password(TEST_PASSWD)); assertTrue("Should be able to import key when unlocked", mKeyStore.importKey(TEST_KEYNAME, PRIVKEY_BYTES, Process.WIFI_UID)); assertTrue(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME)); } public void testImport_ungrantedUid_Bluetooth_Failure() throws Exception { assertTrue(mKeyStore.password(TEST_PASSWD)); assertFalse(mKeyStore.importKey(TEST_KEYNAME, PRIVKEY_BYTES, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME)); } public void testImport_Failure_BadEncoding() throws Exception { Loading @@ -257,12 +400,15 @@ public class KeyStoreTest extends ActivityUnitTestCase<Activity> { assertFalse("Invalid DER-encoded key should not be imported", mKeyStore.importKey(TEST_KEYNAME, TEST_DATA)); assertFalse(mKeyStore.contains(TEST_KEYNAME)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); } public void testSign_Success() throws Exception { mKeyStore.password(TEST_PASSWD); assertTrue(mKeyStore.generate(TEST_KEYNAME)); assertTrue(mKeyStore.contains(TEST_KEYNAME)); final byte[] signature = mKeyStore.sign(TEST_KEYNAME, TEST_DATA); assertNotNull("Signature should not be null", signature); Loading @@ -272,6 +418,7 @@ public class KeyStoreTest extends ActivityUnitTestCase<Activity> { mKeyStore.password(TEST_PASSWD); assertTrue(mKeyStore.generate(TEST_KEYNAME)); assertTrue(mKeyStore.contains(TEST_KEYNAME)); final byte[] signature = mKeyStore.sign(TEST_KEYNAME, TEST_DATA); assertNotNull("Signature should not be null", signature); Loading Loading @@ -406,6 +553,38 @@ public class KeyStoreTest extends ActivityUnitTestCase<Activity> { mKeyStore.ungrant(TEST_KEYNAME, 0)); } public void testMigrate_grantedUid_Wifi_Success() throws Exception { assertTrue(mKeyStore.password(TEST_PASSWD)); assertFalse(mKeyStore.contains(TEST_KEYNAME)); assertTrue(mKeyStore.generate(TEST_KEYNAME)); assertTrue(mKeyStore.contains(TEST_KEYNAME)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); assertTrue(mKeyStore.migrate(TEST_KEYNAME, Process.WIFI_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME)); assertTrue(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); } public void testMigrate_ungrantedUid_Bluetooth_Failure() throws Exception { assertTrue(mKeyStore.password(TEST_PASSWD)); assertFalse(mKeyStore.contains(TEST_KEYNAME)); assertTrue(mKeyStore.generate(TEST_KEYNAME)); assertTrue(mKeyStore.contains(TEST_KEYNAME)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.migrate(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertTrue(mKeyStore.contains(TEST_KEYNAME)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); } /** * The amount of time to allow before and after expected time for variance * in timing tests. Loading Loading
core/java/android/security/IKeystoreService.java +26 −0 Original line number Diff line number Diff line Loading @@ -148,6 +148,10 @@ public interface IKeystoreService extends IInterface { for (int i = 0; i < size; i++) { _result[i] = _reply.readString(); } int _ret = _reply.readInt(); if (_ret != 1) { return null; } } finally { _reply.recycle(); _data.recycle(); Loading Loading @@ -401,6 +405,25 @@ public interface IKeystoreService extends IInterface { } return _result; } @Override public int migrate(String name, int targetUid) throws RemoteException { Parcel _data = Parcel.obtain(); Parcel _reply = Parcel.obtain(); int _result; try { _data.writeInterfaceToken(DESCRIPTOR); _data.writeString(name); _data.writeInt(targetUid); mRemote.transact(Stub.TRANSACTION_migrate, _data, _reply, 0); _reply.readException(); _result = _reply.readInt(); } finally { _reply.recycle(); _data.recycle(); } return _result; } } private static final String DESCRIPTOR = "android.security.keystore"; Loading @@ -425,6 +448,7 @@ public interface IKeystoreService extends IInterface { static final int TRANSACTION_grant = IBinder.FIRST_CALL_TRANSACTION + 17; static final int TRANSACTION_ungrant = IBinder.FIRST_CALL_TRANSACTION + 18; static final int TRANSACTION_getmtime = IBinder.FIRST_CALL_TRANSACTION + 19; static final int TRANSACTION_migrate = IBinder.FIRST_CALL_TRANSACTION + 20; /** * Cast an IBinder object into an IKeystoreService interface, generating Loading Loading @@ -509,4 +533,6 @@ public interface IKeystoreService extends IInterface { public int ungrant(String name, int granteeUid) throws RemoteException; public long getmtime(String name) throws RemoteException; public int migrate(String name, int targetUid) throws RemoteException; }
keystore/java/android/security/AndroidKeyStore.java +25 −20 Original line number Diff line number Diff line Loading @@ -453,6 +453,7 @@ public class AndroidKeyStore extends KeyStoreSpi { * convention. */ final String[] certAliases = mKeyStore.saw(Credentials.USER_CERTIFICATE); if (certAliases != null) { for (String alias : certAliases) { final byte[] certBytes = mKeyStore.get(Credentials.USER_CERTIFICATE + alias); if (certBytes == null) { Loading @@ -466,12 +467,14 @@ public class AndroidKeyStore extends KeyStoreSpi { return alias; } } } /* * Look at all the TrustedCertificateEntry types. Skip all the * PrivateKeyEntry we looked at above. */ final String[] caAliases = mKeyStore.saw(Credentials.CA_CERTIFICATE); if (certAliases != null) { for (String alias : caAliases) { if (nonCaEntries.contains(alias)) { continue; Loading @@ -482,11 +485,13 @@ public class AndroidKeyStore extends KeyStoreSpi { continue; } final Certificate c = toCertificate(mKeyStore.get(Credentials.CA_CERTIFICATE + alias)); final Certificate c = toCertificate(mKeyStore.get(Credentials.CA_CERTIFICATE + alias)); if (cert.equals(c)) { return alias; } } } return null; } Loading
keystore/java/android/security/KeyStore.java +51 −14 Original line number Diff line number Diff line Loading @@ -87,42 +87,58 @@ public class KeyStore { } } public boolean put(String key, byte[] value) { public boolean put(String key, byte[] value, int uid) { try { return mBinder.insert(key, value, -1) == NO_ERROR; return mBinder.insert(key, value, uid) == NO_ERROR; } catch (RemoteException e) { Log.w(TAG, "Cannot connect to keystore", e); return false; } } public boolean delete(String key) { public boolean put(String key, byte[] value) { return put(key, value, -1); } public boolean delete(String key, int uid) { try { return mBinder.del(key, -1) == NO_ERROR; return mBinder.del(key, uid) == NO_ERROR; } catch (RemoteException e) { Log.w(TAG, "Cannot connect to keystore", e); return false; } } public boolean contains(String key) { public boolean delete(String key) { return delete(key, -1); } public boolean contains(String key, int uid) { try { return mBinder.exist(key, -1) == NO_ERROR; return mBinder.exist(key, uid) == NO_ERROR; } catch (RemoteException e) { Log.w(TAG, "Cannot connect to keystore", e); return false; } } public String[] saw(String prefix) { public boolean contains(String key) { return contains(key, -1); } public String[] saw(String prefix, int uid) { try { return mBinder.saw(prefix, -1); return mBinder.saw(prefix, uid); } catch (RemoteException e) { Log.w(TAG, "Cannot connect to keystore", e); return null; } } public String[] saw(String prefix) { return saw(prefix, -1); } public boolean reset() { try { return mBinder.reset() == NO_ERROR; Loading Loading @@ -169,24 +185,32 @@ public class KeyStore { } } public boolean generate(String key) { public boolean generate(String key, int uid) { try { return mBinder.generate(key, -1) == NO_ERROR; return mBinder.generate(key, uid) == NO_ERROR; } catch (RemoteException e) { Log.w(TAG, "Cannot connect to keystore", e); return false; } } public boolean importKey(String keyName, byte[] key) { public boolean generate(String key) { return generate(key, -1); } public boolean importKey(String keyName, byte[] key, int uid) { try { return mBinder.import_key(keyName, key, -1) == NO_ERROR; return mBinder.import_key(keyName, key, uid) == NO_ERROR; } catch (RemoteException e) { Log.w(TAG, "Cannot connect to keystore", e); return false; } } public boolean importKey(String keyName, byte[] key) { return importKey(keyName, key, -1); } public byte[] getPubkey(String key) { try { return mBinder.get_pubkey(key); Loading @@ -196,15 +220,19 @@ public class KeyStore { } } public boolean delKey(String key) { public boolean delKey(String key, int uid) { try { return mBinder.del_key(key, -1) == NO_ERROR; return mBinder.del_key(key, uid) == NO_ERROR; } catch (RemoteException e) { Log.w(TAG, "Cannot connect to keystore", e); return false; } } public boolean delKey(String key) { return delKey(key, -1); } public byte[] sign(String key, byte[] data) { try { return mBinder.sign(key, data); Loading Loading @@ -259,6 +287,15 @@ public class KeyStore { } } public boolean migrate(String key, int uid) { try { return mBinder.migrate(key, uid) == NO_ERROR; } catch (RemoteException e) { Log.w(TAG, "Cannot connect to keystore", e); return false; } } public int getLastError() { return mError; } Loading
keystore/tests/src/android/security/AndroidKeyPairGeneratorTest.java +3 −1 Original line number Diff line number Diff line Loading @@ -67,7 +67,9 @@ public class AndroidKeyPairGeneratorTest extends AndroidTestCase { assertTrue(mAndroidKeyStore.password("1111")); assertTrue(mAndroidKeyStore.isUnlocked()); assertEquals(0, mAndroidKeyStore.saw("").length); String[] aliases = mAndroidKeyStore.saw(""); assertNotNull(aliases); assertEquals(0, aliases.length); mGenerator = java.security.KeyPairGenerator.getInstance(AndroidKeyPairGenerator.NAME); } Loading
keystore/tests/src/android/security/KeyStoreTest.java +185 −6 Original line number Diff line number Diff line Loading @@ -17,6 +17,7 @@ package android.security; import android.app.Activity; import android.os.Process; import android.security.KeyStore; import android.test.ActivityUnitTestCase; import android.test.AssertionFailedError; Loading Loading @@ -128,7 +129,7 @@ public class KeyStoreTest extends ActivityUnitTestCase<Activity> { super.tearDown(); } public void teststate() throws Exception { public void testState() throws Exception { assertEquals(KeyStore.State.UNINITIALIZED, mKeyStore.state()); } Loading @@ -154,6 +155,24 @@ public class KeyStoreTest extends ActivityUnitTestCase<Activity> { assertTrue(Arrays.equals(TEST_KEYVALUE, mKeyStore.get(TEST_KEYNAME))); } public void testPut_grantedUid_Wifi() throws Exception { assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); assertFalse(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE, Process.WIFI_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); mKeyStore.password(TEST_PASSWD); assertTrue(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE, Process.WIFI_UID)); assertTrue(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); } public void testPut_ungrantedUid_Bluetooth() throws Exception { assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); mKeyStore.password(TEST_PASSWD); assertFalse(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); } public void testI18n() throws Exception { assertFalse(mKeyStore.put(TEST_I18N_KEY, TEST_I18N_VALUE)); assertFalse(mKeyStore.contains(TEST_I18N_KEY)); Loading @@ -167,22 +186,64 @@ public class KeyStoreTest extends ActivityUnitTestCase<Activity> { mKeyStore.password(TEST_PASSWD); assertFalse(mKeyStore.delete(TEST_KEYNAME)); mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE); assertTrue(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE)); assertTrue(Arrays.equals(TEST_KEYVALUE, mKeyStore.get(TEST_KEYNAME))); assertTrue(mKeyStore.delete(TEST_KEYNAME)); assertNull(mKeyStore.get(TEST_KEYNAME)); } public void testDelete_grantedUid_Wifi() throws Exception { assertFalse(mKeyStore.delete(TEST_KEYNAME, Process.WIFI_UID)); mKeyStore.password(TEST_PASSWD); assertFalse(mKeyStore.delete(TEST_KEYNAME, Process.WIFI_UID)); assertTrue(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE, Process.WIFI_UID)); assertTrue(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); assertTrue(mKeyStore.delete(TEST_KEYNAME, Process.WIFI_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); } public void testDelete_ungrantedUid_Bluetooth() throws Exception { assertFalse(mKeyStore.delete(TEST_KEYNAME, Process.BLUETOOTH_UID)); mKeyStore.password(TEST_PASSWD); assertFalse(mKeyStore.delete(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.delete(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); } public void testContains() throws Exception { assertFalse(mKeyStore.contains(TEST_KEYNAME)); mKeyStore.password(TEST_PASSWD); assertTrue(mKeyStore.password(TEST_PASSWD)); assertFalse(mKeyStore.contains(TEST_KEYNAME)); mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE); assertTrue(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE)); assertTrue(mKeyStore.contains(TEST_KEYNAME)); } public void testContains_grantedUid_Wifi() throws Exception { assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); assertTrue(mKeyStore.password(TEST_PASSWD)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); assertTrue(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE, Process.WIFI_UID)); assertTrue(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); } public void testContains_grantedUid_Bluetooth() throws Exception { assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertTrue(mKeyStore.password(TEST_PASSWD)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.put(TEST_KEYNAME, TEST_KEYVALUE, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); } public void testSaw() throws Exception { String[] emptyResult = mKeyStore.saw(TEST_KEYNAME); assertNotNull(emptyResult); Loading @@ -198,6 +259,48 @@ public class KeyStoreTest extends ActivityUnitTestCase<Activity> { new HashSet(Arrays.asList(results))); } public void testSaw_ungrantedUid_Bluetooth() throws Exception { String[] results1 = mKeyStore.saw(TEST_KEYNAME, Process.BLUETOOTH_UID); assertNull(results1); mKeyStore.password(TEST_PASSWD); mKeyStore.put(TEST_KEYNAME1, TEST_KEYVALUE); mKeyStore.put(TEST_KEYNAME2, TEST_KEYVALUE); String[] results2 = mKeyStore.saw(TEST_KEYNAME, Process.BLUETOOTH_UID); assertNull(results2); } public void testSaw_grantedUid_Wifi() throws Exception { String[] results1 = mKeyStore.saw(TEST_KEYNAME, Process.WIFI_UID); assertNotNull(results1); assertEquals(0, results1.length); mKeyStore.password(TEST_PASSWD); mKeyStore.put(TEST_KEYNAME1, TEST_KEYVALUE, Process.WIFI_UID); mKeyStore.put(TEST_KEYNAME2, TEST_KEYVALUE, Process.WIFI_UID); String[] results2 = mKeyStore.saw(TEST_KEYNAME, Process.WIFI_UID); assertEquals(new HashSet(Arrays.asList(TEST_KEYNAME1.substring(TEST_KEYNAME.length()), TEST_KEYNAME2.substring(TEST_KEYNAME.length()))), new HashSet(Arrays.asList(results2))); } public void testSaw_grantedUid_Vpn() throws Exception { String[] results1 = mKeyStore.saw(TEST_KEYNAME, Process.VPN_UID); assertNotNull(results1); assertEquals(0, results1.length); mKeyStore.password(TEST_PASSWD); mKeyStore.put(TEST_KEYNAME1, TEST_KEYVALUE, Process.VPN_UID); mKeyStore.put(TEST_KEYNAME2, TEST_KEYVALUE, Process.VPN_UID); String[] results2 = mKeyStore.saw(TEST_KEYNAME, Process.VPN_UID); assertEquals(new HashSet(Arrays.asList(TEST_KEYNAME1.substring(TEST_KEYNAME.length()), TEST_KEYNAME2.substring(TEST_KEYNAME.length()))), new HashSet(Arrays.asList(results2))); } public void testLock() throws Exception { assertFalse(mKeyStore.lock()); Loading Loading @@ -239,17 +342,57 @@ public class KeyStoreTest extends ActivityUnitTestCase<Activity> { } public void testGenerate_Success() throws Exception { mKeyStore.password(TEST_PASSWD); assertTrue(mKeyStore.password(TEST_PASSWD)); assertTrue("Should be able to generate key when unlocked", mKeyStore.generate(TEST_KEYNAME)); assertTrue(mKeyStore.contains(TEST_KEYNAME)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); } public void testGenerate_grantedUid_Wifi_Success() throws Exception { assertTrue(mKeyStore.password(TEST_PASSWD)); assertTrue("Should be able to generate key when unlocked", mKeyStore.generate(TEST_KEYNAME, Process.WIFI_UID)); assertTrue(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME)); } public void testGenerate_ungrantedUid_Bluetooth_Failure() throws Exception { assertTrue(mKeyStore.password(TEST_PASSWD)); assertFalse(mKeyStore.generate(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME)); } public void testImport_Success() throws Exception { mKeyStore.password(TEST_PASSWD); assertTrue(mKeyStore.password(TEST_PASSWD)); assertTrue("Should be able to import key when unlocked", mKeyStore.importKey(TEST_KEYNAME, PRIVKEY_BYTES)); assertTrue(mKeyStore.contains(TEST_KEYNAME)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); } public void testImport_grantedUid_Wifi_Success() throws Exception { assertTrue(mKeyStore.password(TEST_PASSWD)); assertTrue("Should be able to import key when unlocked", mKeyStore.importKey(TEST_KEYNAME, PRIVKEY_BYTES, Process.WIFI_UID)); assertTrue(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME)); } public void testImport_ungrantedUid_Bluetooth_Failure() throws Exception { assertTrue(mKeyStore.password(TEST_PASSWD)); assertFalse(mKeyStore.importKey(TEST_KEYNAME, PRIVKEY_BYTES, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME)); } public void testImport_Failure_BadEncoding() throws Exception { Loading @@ -257,12 +400,15 @@ public class KeyStoreTest extends ActivityUnitTestCase<Activity> { assertFalse("Invalid DER-encoded key should not be imported", mKeyStore.importKey(TEST_KEYNAME, TEST_DATA)); assertFalse(mKeyStore.contains(TEST_KEYNAME)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); } public void testSign_Success() throws Exception { mKeyStore.password(TEST_PASSWD); assertTrue(mKeyStore.generate(TEST_KEYNAME)); assertTrue(mKeyStore.contains(TEST_KEYNAME)); final byte[] signature = mKeyStore.sign(TEST_KEYNAME, TEST_DATA); assertNotNull("Signature should not be null", signature); Loading @@ -272,6 +418,7 @@ public class KeyStoreTest extends ActivityUnitTestCase<Activity> { mKeyStore.password(TEST_PASSWD); assertTrue(mKeyStore.generate(TEST_KEYNAME)); assertTrue(mKeyStore.contains(TEST_KEYNAME)); final byte[] signature = mKeyStore.sign(TEST_KEYNAME, TEST_DATA); assertNotNull("Signature should not be null", signature); Loading Loading @@ -406,6 +553,38 @@ public class KeyStoreTest extends ActivityUnitTestCase<Activity> { mKeyStore.ungrant(TEST_KEYNAME, 0)); } public void testMigrate_grantedUid_Wifi_Success() throws Exception { assertTrue(mKeyStore.password(TEST_PASSWD)); assertFalse(mKeyStore.contains(TEST_KEYNAME)); assertTrue(mKeyStore.generate(TEST_KEYNAME)); assertTrue(mKeyStore.contains(TEST_KEYNAME)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); assertTrue(mKeyStore.migrate(TEST_KEYNAME, Process.WIFI_UID)); assertFalse(mKeyStore.contains(TEST_KEYNAME)); assertTrue(mKeyStore.contains(TEST_KEYNAME, Process.WIFI_UID)); } public void testMigrate_ungrantedUid_Bluetooth_Failure() throws Exception { assertTrue(mKeyStore.password(TEST_PASSWD)); assertFalse(mKeyStore.contains(TEST_KEYNAME)); assertTrue(mKeyStore.generate(TEST_KEYNAME)); assertTrue(mKeyStore.contains(TEST_KEYNAME)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertFalse(mKeyStore.migrate(TEST_KEYNAME, Process.BLUETOOTH_UID)); assertTrue(mKeyStore.contains(TEST_KEYNAME)); assertFalse(mKeyStore.contains(TEST_KEYNAME, Process.BLUETOOTH_UID)); } /** * The amount of time to allow before and after expected time for variance * in timing tests. Loading