ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

从AndroidKeystore加载私钥时出现问题

2019-07-27 18:26:49  阅读:489  来源: 互联网

标签:android


Android提供了一个API,用于为加密操作生成密钥,并在Androids Systemkeystore中存储/加载它们.

我按照KeyGenParameterSpec类的JavaDocs中的Example进行操作.密钥的生成,存储和加载工作.但是如果我尝试使用密钥,则密码对象的init()调用将失败.我调试了一下,我可以看到,加载的Key的类型为“android.security.keystore.AndroidKeyStoreSecretKey”.此实现可防止密钥的byte []被暴露.我出于安全原因理解这一点,但如果我想使用密钥,我必须获得关键内容.所以,我必须做错事.也许,在Android中使用加密操作还有另一种方法吗?或者Key的加载代码是错误的?

这是代码:

KeyGenerator keyGenerator = KeyGenerator.getInstance(
                KeyProperties.KEY_ALGORITHM_AES, "AndroidKeyStore");

KeyGenParameterSpec.Builder builder = new KeyGenParameterSpec.Builder("demo-alias", KeyProperties.PURPOSE_ENCRYPT | KeyProperties.PURPOSE_DECRYPT);
builder.setKeySize(256);
builder.setBlockModes(KeyProperties.BLOCK_MODE_CBC);
builder.setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_PKCS7);
keyGenerator.init(builder.build());

// this key will work with a CipherObject ...
SecretKey key = keyGenerator.generateKey();

// Load the key from the Keystore
KeyStore keyStore = KeyStore.getInstance("AndroidKeyStore");
keyStore.load(null);

// This key will not work with the Cipher Object
SecretKey notWorkingKey = (SecretKey) keyStore.getKey("demo-alias", null);

Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
// That call fails
cipher.init(Cipher.ENCRYPT_MODE, key, new IvParameterSpec(new byte[]{87, 99, -94, 23, -17, 26, 84, -117, 59, -59, 25, -88, -66, 86, -42, 78}));

byte[] crypted = cipher.doFinal("testdata".getBytes());

密码的init(…)失败,出现以下异常:

java.lang.NullPointerException: Attempt to get length of null array
    at com.android.org.bouncycastle.crypto.params.KeyParameter.<init>(KeyParameter.java:13)
    at com.android.org.bouncycastle.jcajce.provider.symmetric.util.BaseBlockCipher.engineInit(BaseBlockCipher.java:557)
    at javax.crypto.Cipher.tryTransformWithProvider(Cipher.java:608)
    at javax.crypto.Cipher.tryCombinations(Cipher.java:532)
    at javax.crypto.Cipher.getSpi(Cipher.java:437)
    at javax.crypto.Cipher.init(Cipher.java:909)
    at javax.crypto.Cipher.init(Cipher.java:859)
    at de.demo.crypt.LoginActivity.executeLogin(LoginActivity.java:95)
    at de.demo.crypt.LoginActivity.access$000(LoginActivity.java:37)
    at de.demo.crypt.LoginActivity$1.onClick(LoginActivity.java:58)
    at de.demo.crypt.ActionButton.buttonClicked(ActionButton.java:104)
    at de.demo.crypt.ActionButton.access$000(ActionButton.java:17)
    at de.demo.crypt.ActionButton$1.onClick(ActionButton.java:60)
    at android.view.View.performClick(View.java:5198)
    at android.view.View$PerformClick.run(View.java:21147)
    at android.os.Handler.handleCallback(Handler.java:739)
    at android.os.Handler.dispatchMessage(Handler.java:95)
    at android.os.Looper.loop(Looper.java:148)
    at android.app.ActivityThread.main(ActivityThread.java:5417)
    at java.lang.reflect.Method.invoke(Native Method)
    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:726)
    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:616)

解决方法:

对Cipher.getInstance使用“AES / CBC / PKCS7Padding”或“AES / CBC /”KeyProperties.ENCRYPTION_PADDING_PKCS7.

Android Keystore仅支持AES的PKCS#7填充(请参阅https://developer.android.com/training/articles/keystore.html#SupportedCiphers).对于大于64位的块大小(AES使用128位块),技术上没有定义PKCS#5填充.通常情况下,当人们说PKCS#5填充时,他们​​的意思是PKCS#7填充.

您看到的特殊错误是因为Bouncy Castle错误地声称支持AES / CBC / PKCS5Padding的Android Keystore密钥(请参阅Bouncy Castle问题跟踪器问题BJA-543).

P. S.最佳做法是让加密密码实现为您生成随机IV,而不是自己为密码提供IV – 您可以稍后使用Cipher.getIV()查询生成的IV.如果由于某种原因,您必须在加密时提供自己的IV,则在生成密钥时,您需要禁用密钥上的随机加密的默认要求(https://developer.android.com/reference/android/security/keystore/KeyGenParameterSpec.Builder.html#setRandomizedEncryptionRequired(boolean)).

标签:android
来源: https://codeday.me/bug/20190727/1556316.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有