ski*_*iwi 4 java security passwords client-server bcrypt
我想知道我目前对BCrypt的实现是否正确,我知道我没有使用BCrypt.checkpw()哪个可能导致问题,所以这是我在这里验证它的主要原因.
Hasher.java容器类:
abstract public class Hasher {
public static String hash(final char[] input) {
String output = Hasher.hash(new String(input));
for (int i = 0; i < input.length; i++) {
input[i] = 0;
}
return output;
}
public static String hash(final String input) {
return BCrypt.hashpw(input, BCrypt.gensalt());
}
}
Run Code Online (Sandbox Code Playgroud)
这里有一个问题:出于安全原因JPasswordField给我一个char[]但是BCrypt.hashpw()只接受字符串.如何避免String在我的记忆中漂浮?
登录的客户端实现:
String hashedPassword = Hasher.hash(password);
Network.getInstance().send("login " + username + " " + hashedPassword);
Run Code Online (Sandbox Code Playgroud)
因此哈希通过网络发送,目前网络没有加密,但我计划添加它.
帐户创建时的服务器实现:
public static Account createAccount(final String username, final String password) {
String hashedPassword = Hasher.hash(password.toCharArray());
return new Account(username, hashedPassword);
}
Run Code Online (Sandbox Code Playgroud)
检查密码的服务器实现:
public boolean checkPassword(final String hashedPassword) {
return this.hashedPassword.equals(hashedPassword);
}
Run Code Online (Sandbox Code Playgroud)
使用this.hashedPassword服务器内存中的哈希值(来自启动时的数据库).
我的设置属性:
BCrypt.gensalt().请核实我的假设.
问候.
Aur*_*and 11
此设置存在一些问题.
1)salt应该是在散列过程中随机生成的值(因为它似乎在您的实现中.由于客户端无法访问存储哈希的数据库,客户端将无法知道创建时使用的salt登录哈希.
2)此实现实际上并未检查客户端传递的密码,它正在检查客户端传递的密码哈希值.这意味着如果有人获得了哈希数据库,他们可以立即使用这些哈希值登录.然后不需要破解它们来提取密码,因为你不检查密码.
通过移动所有散列服务器端,可以轻松解决这两个问题.
更新
关于你提到的问题.
1)如果您打算创建安全系统,则应使用SSL/TLS.在clear中发送密码哈希几乎与在明文中发送密码完全不安全.两者都是一个糟糕的主意.使用HTTPS.
2)执行服务器端散列是一种非常普通的做法.散列过程的计算成本非常高,使得详尽的搜索不切实际,但它不应该妨碍您的身份验证工作流程.如果您真的担心遭遇DoSed,请跟踪给定用户在最近N秒内尝试登录的次数.如果他们失败了一定次数,请锁定他们的帐户.