Sử dụng phản chiếu để chà một String
có sử dụng String
an toàn khi sử dụng char[]
cho mật khẩu không? Từ khía cạnh bảo mật, thường được coi là thực tiễn tốt nhất để sử dụng char[]
để lưu trữ/chuyển mật khẩu, vì người ta có thể xóa nội dung của nó sớm nhất có thể trong mã, điều này có thể đáng kể trước khi thu gom rác dọn dẹp và bộ nhớ được tái sử dụng (xóa tất cả dấu vết), giới hạn thời gian để tấn công bộ nhớ.Sử dụng an toàn String cho mật khẩu bằng cách sử dụng phản chiếu để lọc nội dung trước khi thu gom rác
Tuy nhiên, char[]
là không thuận tiện như String
, vì vậy nó sẽ có ích nếu người ta có thể "chà" một String
nếu cần thiết, do đó làm cho String
an toàn như char[]
.
Dưới đây là phương pháp sử dụng sự phản chiếu để không ra các trường của String
.
Phương pháp này là "OK" và có đạt được mục tiêu làm cho String
an toàn như char[]
cho mật khẩu không?
public static void scrub(String str) throws NoSuchFieldException, IllegalAccessException {
Field valueField = String.class.getDeclaredField("value");
Field offsetField = String.class.getDeclaredField("offset");
Field countField = String.class.getDeclaredField("count");
Field hashField = String.class.getDeclaredField("hash");
valueField.setAccessible(true);
offsetField.setAccessible(true);
countField.setAccessible(true);
hashField.setAccessible(true);
char[] value = (char[]) valueField.get(str);
// overwrite the relevant array contents with null chars
Arrays.fill(value, offsetField.getInt(str), countField.getInt(str), '\0');
countField.set(str, 0); // scrub password length too
hashField.set(str, 0); // the hash could be used to crack a password
valueField.setAccessible(false);
offsetField.setAccessible(false);
countField.setAccessible(false);
hashField.setAccessible(false);
}
Dưới đây là một thử nghiệm đơn giản:
String str = "password";
scrub(str);
System.out.println('"' + str + '"');
Output:
""
Lưu ý: Bạn có thể giả định rằng mật khẩu là không String
hằng số và do đó gọi phương pháp này sẽ không có tác dụng phụ có hiệu lực trên các chuỗi nội bộ.
Ngoài ra, tôi đã rời phương pháp này là trạng thái "thô" khá đơn giản vì mục đích đơn giản. Nếu tôi sử dụng nó, tôi sẽ không khai báo các ngoại lệ được ném (try/catch/bỏ qua chúng) và mã lặp lại cấu trúc lại.
Vâng, dường như không tìm ra các ký tự, nhưng không phải là hoàn toàn phụ thuộc vào việc thực hiện JVM? – fge
snooping bộ nhớ? đó là một cuộc tấn công tưởng tượng. tại sao không phải lo lắng về một cái gì đó thực tế hơn, như NSA snooping lưu lượng truy cập mạng của bạn. – ZhongYu
Screams "hành vi không xác định" tại tôi. Chúc may mắn với rồng, velociraptors và lỗ đen :) – CodesInChaos