2

I've got Android code that encrypts/decrypts data. It was written over a year ago by another developer (who has since left) and has worked fine until very recently, when it started crashing with the following exception:

android.security.keystore.AndroidKeyStoreRSAPrivateKey cannot be cast to javax.crypto.SecretKey

This appears to only occur when upgrading the application and an existing key is already present. I ran a diff off the gradle files against the prior release (which works) and no frameworks/sdks have been updated.

The exception occurs in .build():

    private fun getOrGenerateNewKeysetHandle(alias: String): KeysetHandle {
        val keysetName = "${TINK_KEYSET_NAME}_$alias"
        return AndroidKeysetManager.Builder()
                .withSharedPref(reactApplicationContext, keysetName, PREF_FILE_NAME)
                .withKeyTemplate(HybridKeyTemplates.ECIES_P256_HKDF_HMAC_SHA256_AES128_GCM)
                .withMasterKeyUri(MASTER_KEY_URI)
                .build()
                .keysetHandle
    }

I traced the code down to AndroidKeystoreAesGcm and the exception occurs on assignment returned from getKey (which succeeds):

  public AndroidKeystoreAesGcm(String keyId) throws GeneralSecurityException, IOException {
    KeyStore keyStore = KeyStore.getInstance("AndroidKeyStore");
    keyStore.load(null /* param */);
    key = (SecretKey) keyStore.getKey(keyId, null /* password */);
  }

This has left me uncertain of how to proceed. KeyStore has a key and I need it to access application data. I suspect my old arch-nemesis, gradle, is to blame, but... well, any help or insight would be greatly appreciated.

Aaron Hayman
  • 8,492
  • 2
  • 36
  • 63
  • May not solve the problem; just give an idea https://stackoverflow.com/questions/32400689/crash-casting-androidkeystorersaprivatekey-to-rsaprivatekey – ecle Dec 05 '21 at 07:02
  • Hey Aaron, did you manage to solve the issue? I'm facing the exact same crash – Oscar Franco Apr 23 '22 at 09:45
  • @OscarFranco I did, although the issue was oddly specific. We were using the Zoom SDK. When it initializes, it attempts to retrieve a Key using the Application's bundle ID. If it doesn't exist, it creates one. The app crashed because we were doing the same after Zoom, but the one created by Zoom wasn't compatible. If we create a key before Zoom does, Zoom uses that key without issue, thus avoiding the crash. I'm very irritated at Zoom for using our bundle id without any prefix/suffix to differentiate it. – Aaron Hayman Apr 28 '22 at 14:36
  • yeah, at some point I figured out that you can only have one key per bundle (or per shared preferences). Terrible that a library would take over the key of the app. I ended up using the latest Androidx.crypto library, thanks for answering though! – Oscar Franco Apr 28 '22 at 16:28

0 Answers0