0

我正在使用 sqlcipher 存储来自我的应用程序的数据,首先我遇到了麻烦,生成一个密钥,然后存储在密钥库中。

顺便说一句,需要没有像android 文档中描述的用户交互

这是我试图生成秘密的方式,

KeyGenerator keyGen = KeyGenerator.getInstance("AES");
keyGen.init(128);
SecretKey key = keyGen.generateKey();

在这里,是我设置 sqldatabase 的地方

SQLiteDatabase db = SQLiteDatabase.openOrCreateDatabase(databaseFile, "password_string", null);

那么问题来了,我如何在密码字符串中使用秘密?目前,我只能以字节数组的形式获取秘密。

4

2 回答 2

1

请在下面找到使用 AES 加密/解密的实用程序。您可以使用密钥来加密/解密您的密码。但是,我不建议这样做,因为您还必须存储您的密钥并且问题仍然存在,您如何安全地保存您的密钥?在这种情况下,一种常见的做法是使用哈希函数:SHA-256、MD5... 对您的密码进行哈希处理并存储它。稍后,当您想检查用户是否输入了正确的密码时,只需对他们输入的任何内容进行哈希处理并与您存储的值进行比较。

private static int BLOCKS = 128;

  public static byte[] encryptAES(String seed, String cleartext)
      throws Exception {
    byte[] rawKey = getRawKey(seed.getBytes("UTF8"));
    SecretKeySpec skeySpec = new SecretKeySpec(rawKey, "AES");
    Cipher cipher = Cipher.getInstance("AES");
    cipher.init(Cipher.ENCRYPT_MODE, skeySpec);
    return cipher.doFinal(cleartext.getBytes("UTF8"));
  }

  public static byte[] decryptAES(String seed, byte[] data) throws Exception {
    byte[] rawKey = getRawKey(seed.getBytes("UTF8"));
    SecretKeySpec skeySpec = new SecretKeySpec(rawKey, "AES");
    Cipher cipher = Cipher.getInstance("AES");
    cipher.init(Cipher.DECRYPT_MODE, skeySpec);
    return cipher.doFinal(data);
  }

  private static byte[] getRawKey(byte[] seed) throws Exception {
    KeyGenerator kgen = KeyGenerator.getInstance("AES");
    SecureRandom sr = SecureRandom.getInstance("SHA1PRNG");
    sr.setSeed(seed);
    kgen.init(BLOCKS, sr); // 192 and 256 bits may not be available
    SecretKey skey = kgen.generateKey();
    byte[] raw = skey.getEncoded();
    return raw;
  }
于 2018-03-28T09:17:49.930 回答
0

这是我生成随机和准安全密码的方法:

fun generatePassword(): String{
     val androidId = Settings.Secure.getString(context.contentResolver, Settings.Secure.ANDROID_ID)

     val passPassphraseBase = "${BuildConfig.APPLICATION_ID}_$androidId:"

     val random = SecureRandom()
     val salt = ByteArray(32)
     random.nextBytes(salt)

     val passPhrase = passPassphraseBase.toByteArray() + salt

     val pass = Base64.encodeToString(passPhrase, Base64.NO_WRAP)

     return pass
} 

你可以问我需要什么Application ID和Android ID。只是为了增加我们密码的熵(可能还有长度)。

然后我将此密码加密存储在共享首选项中。我使用密钥库 RSA 算法加密所有共享首选项密钥和值。

毕竟我们最终得到了用非对称算法加密的对称加密密码。

所有这一切都只是一种白盒密码学,我们将密钥和加密数据存储在一个地方。

如果我们为密码的至少一部分添加一些外部来源,我们可以提高安全性。为此,我们可以使用:

  • 来自我们后端的东西
  • 用户输入或生物识别
于 2020-05-27T20:16:16.930 回答