使用 6 位数 PIN 保护 Android 应用程序上的数据

信息安全 加密 安卓 密钥生成 pbkdf2
2021-08-27 12:35:39

假设在 Android 应用上,用户必须在启动时输入 6 位 PIN。假设我们在这个应用程序中有一些我们想要加密的敏感数据。

我会这样做的方式是:

  • 使用密钥派生函数(例如 PBKDF2),我们从 PIN 生成密钥。
  • 使用密钥(以及像 CBC+padding 这样的配置)使用 AES 加密敏感数据。
  • 将加密数据存储在任何地方,例如在共享首选项中。

我在这里看到的主要问题:6 位 PIN 的原始 PIN 空间是 10^6,这对于用作加密的基础来说太小了……

我们真的可以对此进行微调,以使存储的数据在一段时间内相当安全吗?

即使我们调整我们的 KDF 使得一个简单的推导需要 1 秒(我认为我们不能期望我们的用户在应用程序启动期间等待更长的时间),那么通过其中的 1'000'000 只需要 11.5 天(假设与手机相同的处理能力,这不太可能......)。

限制:
显然,使用更长/更强的 PIN会有所帮助 - 但遗憾的是,即使是 6 位数的 PIN 也会被用户视为障碍,因此这不太可能是一种选择。此外,KDF 强度受到我们可以预期用户在应用程序启动期间等待的时间量的限制,我会说这是 1 秒的数量级。

2个回答

我推荐的选择是存储数据,或者至少存储它们的关键服务器端。

由于这对您来说是不可能的,因此我会将其带回管理层,即存在相互冲突的要求。我认为密钥空间太小,加密无法提供任何实际价值。我建议给管理层一个每秒 156 次猜测的真实世界估计(来自这篇文章https://arstechnica.com/security/2015/08/cracking-all-hacked-ashley-madison-passwords-could-take-a- life/ ),这意味着一个饼干将在两小时内得到所有可能的结果。定制破解硬件将比移动设备快得多。有关示例,请参见此处:https ://sagitta.pw/hardware/gpu-compute-nodes/brutalis/ 。

我会通知管理层,具有如此小的密钥空间的离线要求将妨碍正确保护数据。如果他们希望数据是安全的,他们将需要在 6 位密码上做出让步,或者他们需要在离线要求上做出让步。

PIN 码不应被视为安全令牌。它只是一个 UI 的东西,因此,您可以限制不成功的尝试进入它的次数和/或在这些尝试之间引入增量等待。

数据本身可以(并且应该)使用强密钥进行加密。这可以保护本地数据免受离线破解(恶意代理试图直接读取磁盘)。在 Android 7.0 及更高版本上,您可以依赖Direct Boot您的应用可以检查存储加密状态并采取相应的行为。

这并不能完全保护那些在有根设备上安装您的应用程序并想要解密其数据的恶意用户。绝对鼓励您检查设备是否已植根,但您必须知道确定的代理(用户或恶意软件)可以启用您的检查无法检测到的根。