带有setIsStrongBoxBacked的AES密钥-解密失败

问题描述 投票:1回答:1

我在带有setIsStrongBoxBacked=true的StrongBox(像素4)的Android 10设备上生成了AES密钥,如下所示:

fun generateKey(): SecretKey {
        val generator = KeyGenerator.getInstance("AES", "AndroidKeyStore")
        generator.init(
                KeyGenParameterSpec.Builder("alias", PURPOSE_ENCRYPT or PURPOSE_DECRYPT)
                        .setBlockModes(BLOCK_MODE_GCM)
                        .setEncryptionPaddings(ENCRYPTION_PADDING_NONE)
                        .setIsStrongBoxBacked(true)
                        .build()
        )
        return generator.generateKey()
}

[接下来,使用此密钥,我对ByteArray进行了加密。一段时间后,在使用相同的密钥和相同的IV向量进行解密的过程中,我得到了错误的ByteArray,结果无一例外。

两种加密和解密方法都是非常标准的:

fun encrypt(plaintext: ByteArray, iv: ByteArray, key: SecretKey): ByteArray {
        val cipher = Cipher.getInstance("AES/GCM/NoPadding")
        cipher.init(ENCRYPT_MODE, key, GCMParameterSpec(128, iv))
        return cipher.doFinal(plaintext)
}

fun decrypt(ciphertext: ByteArray, iv: ByteArray, key: SecretKey): ByteArray {
        val cipher = Cipher.getInstance("AES/GCM/NoPadding")
        cipher.init(DECRYPT_MODE, key, GCMParameterSpec(128, iv))
        return cipher.doFinal(ciphertext)
}

奇怪的是,使用相同的密钥生成代码,但使用setIsStrongBoxBacked=false,并且使用相同的加密/解密逻辑,一切都按预期工作。

官方文档中没有任何内容对我的情况有所帮助。现在,我可以禁用StrongBox支持逻辑,但是我想知道问题出在哪里-我的代码缺少某些关键信息还是Android 10 / Pixel 4问题?

P.S。

[进一步检查后,我意识到加密逻辑也有问题。使用setIsStrongBoxBacked=true,每次我使用AES / GCM / NoPadding算法加密任何ByteArray时,即使IV是随机生成的,密文也看起来相同(只有身份验证标签部分不同)。根据我对GCM模式的了解,有些事情是不正确的。

使用setIsStrongBoxBacked=true加密1:

IV=[40, 91, -4, -98, 104, 94, -39, -83, -34, 22, -33, 12]

ciphertext=[13, -48, -83, -34, 13, -48, -83, -34, 13, -48, -83, -34, 13, -48, -83, -34, 13, -48, -83, -34, 13, -48, -83, -34, 13, -48, -83, -34, 13, -48, -83, -34, 12, -86, -16, -38, 93, 100, 82, 108, 101, -27, -42, -107, 36, 49, 109, 47]

使用setIsStrongBoxBacked=true加密2:

IV=[-123, -96, -66, -87, 43, -103, -126, -107, 8, -73, 68, -49]

ciphertext=[13, -48, -83, -34, 13, -48, -83, -34, 13, -48, -83, -34, 13, -48, -83, -34, 13, -48, -83, -34, 13, -48, -83, -34, 13, -48, -83, -34, 13, -48, -83, -34, 85, 108, -23, -62, 18, 74, -81, -2, 111, -94, 7, 15, -56, 106, -114, -69]

使用setIsStrongBoxBacked=false,只要IV每次都不同,相同的加密逻辑就生成完全不同的密文,就像它应该这样:

使用setIsStrongBoxBacked=false加密1:

IV=[-113, -48, -5, -106, -86, -1, 121, -40, -13, -54, -56, 10]

ciphertext=[126, -97, 118, 42, -110, 67, 77, 9, 120, -79, 74, -101, -123, 106, -21, -18, -49, -123, -10, -33, -4, -99, 58, -125, 69, -37, 111, -66, -114, -47, 17, 41, -3, 72, -52, -36, -67, 47, 39, -108, -46, -113, 114, -46, -114, 24, -51, -95]

使用setIsStrongBoxBacked=false加密2:

IV=[-106, 12, -84, -108, -102, -11, 38, 30, 10, 22, -123, -28]

ciphertext=[-51, -85, -125, -34, -72, 47, -13, 6, -111, 14, -85, 53, -8, -68, -17, -81, -106, 50, -94, -22, 66, 74, -39, 12, 12, 74, 48, -41, -41, -55, -28, 2, 61, 11, 120, -3, 124, 8, -46, 78, -93, 97, 87, -97, -26, -42, -105, 74]

P.S.2

仅当使用AES / GCM / NoPadding算法时,才会出现此问题。对于其他AES模式(CBC,CRT等),即使对于setIsStrongBoxBacked=true

,加密和解密均能按预期工作

P.S.3问题-https://issuetracker.google.com/issues/147039506

P.S.4应用适用于Pixel 4的最新安全补丁之后,问题就消失了。

android cryptography pixel
1个回答
0
投票

似乎您已经重新发现了CVE-2019-9465。如您所见,将AES-GCM与Strongbox一起使用时,会产生可预测的伪造密文。如果在密码初始化和使用之间存在延迟,则似乎会发生这种情况,但是尚不清楚此错误的确切原因,因为它在Titan M芯片的固件中是一样的。]

[Pixel 3及更高版本在2019年12月的Android安全更新中已修复。我写了一篇有关此内容的文章,内容更深入:https://alexbakker.me/post/mysterious-google-titan-m-bug-cve-2019-9465.html

© www.soinside.com 2019 - 2024. All rights reserved.