Skip to content

Commit 00eba52

Browse files
Alexey BakhtinRealCLanger
authored andcommitted
8369575: Enhance crypto algorithm support
Reviewed-by: andrew Backport-of: 3dcdbc5943a21b3ef7a0cf3a03883c4d71111ef4
1 parent 7e8d154 commit 00eba52

1 file changed

Lines changed: 42 additions & 5 deletions

File tree

src/java.base/share/classes/com/sun/crypto/provider/PBES1Core.java

Lines changed: 42 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright (c) 2002, 2021, Oracle and/or its affiliates. All rights reserved.
2+
* Copyright (c) 2002, 2025, Oracle and/or its affiliates. All rights reserved.
33
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
44
*
55
* This code is free software; you can redistribute it and/or modify it
@@ -51,6 +51,36 @@ final class PBES1Core {
5151
// RFC 8018 and NIST SP 800-132 sec 5.2 recommend 1000 as the minimum
5252
private int iCount = PKCS12PBECipherCore.DEFAULT_COUNT;
5353

54+
// utility method for checking weak salts of PBEWithMD5AndTripleDES cipher
55+
private static boolean isWeak(byte[] s) {
56+
// consider salts weak if it met both of the following conditions:
57+
// 1) s[0...3] == s[4...7]
58+
// 2) s[0] == s[3] && s[1] == s[2]
59+
if (Arrays.equals(s, 0, 4, s, 4, 8)) {
60+
return (s[0] == s[3]) && (s[1] == s[2]);
61+
}
62+
return false;
63+
}
64+
65+
// utility method for generating 8-byte salts
66+
private static byte[] generateSalt(String algo, SecureRandom sr) {
67+
byte[] salt = new byte[8];
68+
sr.nextBytes(salt);
69+
// check and re-generate for DESede if necessary
70+
if (algo.equals("DESede")) {
71+
// prevent an infinite-loop in case of a rigged SecureRandom
72+
int numAttempts = 50;
73+
while (isWeak(salt)) {
74+
sr.nextBytes(salt);
75+
if (numAttempts-- < 0) {
76+
throw new ProviderException(
77+
"Unable to find salts after 50 attempts");
78+
}
79+
}
80+
}
81+
return salt;
82+
}
83+
5484
/**
5585
* Creates an instance of PBE Cipher using the specified CipherSpi
5686
* instance.
@@ -165,8 +195,7 @@ byte[] getIV() {
165195
AlgorithmParameters getParameters() {
166196
AlgorithmParameters params = null;
167197
if (salt == null) {
168-
salt = new byte[8];
169-
SunJCE.getRandom().nextBytes(salt);
198+
salt = generateSalt(algo, SunJCE.getRandom());
170199
}
171200
PBEParameterSpec pbeSpec = new PBEParameterSpec(salt, iCount);
172201
try {
@@ -229,8 +258,7 @@ void init(int opmode, Key key, AlgorithmParameterSpec params,
229258

230259
if (params == null) {
231260
// create random salt and use default iteration count
232-
salt = new byte[8];
233-
random.nextBytes(salt);
261+
salt = generateSalt(algo, random);
234262
} else {
235263
if (!(params instanceof PBEParameterSpec)) {
236264
throw new InvalidAlgorithmParameterException
@@ -242,6 +270,15 @@ void init(int opmode, Key key, AlgorithmParameterSpec params,
242270
throw new InvalidAlgorithmParameterException
243271
("Salt must be 8 bytes long");
244272
}
273+
// for DESede, reject weak salts for encryption
274+
if (algo.equals("DESede") &&
275+
(opmode == Cipher.ENCRYPT_MODE ||
276+
opmode == Cipher.WRAP_MODE) &&
277+
isWeak(salt)) {
278+
throw new InvalidAlgorithmParameterException(
279+
"Weak salts cannot be used for encryption");
280+
}
281+
245282
iCount = ((PBEParameterSpec) params).getIterationCount();
246283
if (iCount <= 0) {
247284
throw new InvalidAlgorithmParameterException

0 commit comments

Comments
 (0)