【发布时间】:2016-08-18 00:54:45
【问题描述】:
抱歉再次提出这个话题,我已经仔细阅读了另一个类似的问题 Why does JPasswordField.getPassword() create a String with the password in it?
但是我仍然认为 JpasswordField 实现存在漏洞。我仍然看到密码存储在内存中可能是不同的数据类型,而不是字符串。
我做的步骤: 从 Oracle 下载 JPasswordField 演示代码 https://docs.oracle.com/javase/tutorial/displayCode.html?code=https://docs.oracle.com/javase/tutorial/uiswing/examples/components/PasswordDemoProject/src/components/PasswordDemo.java
并运行它。它将弹出密码对话框。
输入“bugaboo”
按回车键,查看密码是否正确。 (我删除了输入的密码,有/没有这个delete的结果都是一样的)
此时,由于代码中清除密码内容的原因
//Zero out the password.
Arrays.fill(correctPassword,'0');
我希望内存中没有剩余的 bugaboo,但确实存在。 我用http://www.sweetscape.com/010editor/检查了内存内容,仍然看到明文的“bugaboo”
结论:原因是 JpasswordField 在内部使用 PlainDocument,它会在你的记忆中留下所输入内容的全部历史记录。因此你无法完全清除内存中的密码明文。
因此,将 getPassword() 用作 char[] 并在之后清除它并没有多大好处。
请赐教。
【问题讨论】:
-
它必须存储在某个地方,nu?
-
@EJP 关键是您无法可靠地清除
PlainDocument。所以这个问题的答案是“是”。 (FWIW IIRC,如果您添加ActionListener,您还将获得String。) -
@TomHawtin-tackline 关键是它无法受到保护,如果“受保护”的意思是“内存中没有密码”。可以完成的只是提供一个基于
char[]的API,以避免更明显的基于String的漏洞利用。
标签: java security memory jpasswordfield