Android   发布时间:2022-04-28  发布网站:大佬教程  code.js-code.com
大佬教程收集整理的这篇文章主要介绍了在FingerprintManager.authenticate()中的android – UserNotAuthenticatedException大佬教程大佬觉得挺不错的,现在分享给大家,也给大家做个参考。
@H_403_0@
我有一个加密密码存储Android KeyStore.

我想通过使用指纹API验证用户来解密该密码.

据我所知,我必须调用FingerprintManager.authenticate(CryptoObject cryptoObject)方法来开始侦听指纹结果. CryptoObject参数是这样创建的:

public static Cipher getDecryptionCipher(Context context) throws KeyStoreException {
    try {
        Cipher cipher = Cipher.geTinstance(TRANSFORMATION);
        SecretKey secretKey = getKeyFromKeyStore();
        final IvParameterSpec ivParameterSpec = getIvParameterSpec(context);

        cipher.init(Cipher.DECRYPT_MODE,secretKey,ivParameterSpec);
        return cipher;

    } catch (NoSuchAlgorithmException | NoSuchPaddingException | IOException | UnrecoverableKeyException | CertificateException | InvalidAlgorithmParameterException | InvalidKeyException E) {
        e.printStackTrace();

    }

    return null;
}

Cipher cipher = FingerprintCryptoHelper.getDecryptionCipher(getContext());
FingerprintManager.CryptoObject cryptoObject = new FingerprintManager.CryptoObject(cipher);
fingerprintManager.authenticate(cryptoObject,...);

getDecryptionCipher()方法正常工作,直到cipher.init()调用.在这调用上,我得到一个UserNotAuthenticatedException,因为用户没有为这个secretKey进行身份验证.这是有道理的.但这不是一个循环,不可能实现:

要认证用户,我想使用他/她的指纹
>要听他/她的指纹,我需要初始化Cipher,这个返回需要一个经过身份验证的用户

这里有什么问题?

编辑:

我使用模拟器(Nexus 4,API 23).

这是我用来创建密钥的代码.

private SecretKey createKey() {
    try {
        KeyGenerator keyGenerator = KeyGenerator.geTinstance(KeyProperties.KEY_ALGORITHM_AES,ANDROID_KEY_STORE);
        keyGenerator.init(new KeyGenParameterSpec.builder(
                KEY_NAME,KeyProperties.PURPOSE_ENCRYPT | KeyProperties.PURPOSE_DECRYPT
        )
                .setBlockmodes(KeyProperties.bLOCK_MODE_CBC)
                .setUserAuthenticationrequired(true)
                .setUserAuthenticationValidityDurationSeconds(AUTHENTICATION_DURATION_SECONDS)
                .setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_PKCS7)
                .build());
        return keyGenerator.generateKey();
    } catch (NoSuchAlgorithmException | NoSuchProviderException | InvalidAlgorithmParameterException E) {
        throw new RuntimeException("Failed to create a symmetric key",E);
    }
}

解决方法

事实证明,这个问题与KeyGenParameterSpec的一个已知问题有关,防止在没有认证的情况下使用公共密钥(这正是公钥不需要的).

一个相关的问题/答案可以在这里找到:Android Fingerprint API Encryption and Decryption

解决方法是从最初创建的密钥创建一个PublicKey,并使用这个无限制的PublicKey来初始化密码.
所以我的最终密码使用AES / CBC / PKCS7Padding,并通过这种方法初始化:

public Boolean initCipher(int opModE) {
    try {
        Key key = mKeyStore.getKey(KEY_NAME,null);

        if (opMode == Cipher.ENCRYPT_MODE) {
            final byte[] encoded = key.getEncoded();
            final String algorithm = key.getAlgorithm();
            final X509EncodedKeySpec keySpec = new X509EncodedKeySpec(encoded);
            PublicKey unreStricted = KeyFactory.geTinstance(algorithm).generatePublic(keySpec);

            mCipher.init(opMode,unreStricted);

        } else {
            final IvParameterSpec ivParameterSpec = getIvParameterSpec();
            mCipher.init(opMode,key,ivParameterSpec);

        }

        return true;

    } catch (KeyPeRMANentlyInvalidatedException exception) {
        return false;

    } catch ( NoSuchAlgorithmException | InvalidKeyException
            | InvalidKeySpecException | InvalidAlgorithmParameterException | UnrecoverableKeyException | KeyStoreException exception) {
        throw new RuntimeException("Failed to initialize Cipher or Key: ",exception);
    }
}

@NonNull
public IvParameterSpec getIvParameterSpec() {
    // the IV is stored in the Preferences after encoding.
    String base64EncryptionIv = PreferenceHelper.getEncryptionIv(mContext);
    byte[] encryptionIv = Base64.decode(base64EncryptionIv,Base64.DEFAULT);
    return new IvParameterSpec(encryptionIv);
}

大佬总结

以上是大佬教程为你收集整理的在FingerprintManager.authenticate()中的android – UserNotAuthenticatedException全部内容,希望文章能够帮你解决在FingerprintManager.authenticate()中的android – UserNotAuthenticatedException所遇到的程序开发问题。

如果觉得大佬教程网站内容还不错,欢迎将大佬教程推荐给程序员好友。

本图文内容来源于网友网络收集整理提供,作为学习参考使用,版权属于原作者。
如您有任何意见或建议可联系处理。小编QQ:384754419,请注明来意。