Skip to content

Commit da4a223

Browse files
committed
Address PR review: add Signature.getInstance sink, HMAC/PBKDF2 whitelist, fix test APIs
- Model Signature.getInstance() as CryptoAlgoSpec sink (previously only Signature constructor was modeled) - Add HMAC-based algorithms (HMACSHA1/256/384/512, HmacSHA1/256/384/512) and PBKDF2 to the secure algorithm whitelist - Fix XDH/X25519/X448 tests to use KeyAgreement.getInstance() instead of KeyPairGenerator.getInstance() to match their key agreement semantics - Add test cases for SHA384withECDSA, HMACSHA*, and PBKDF2WithHmacSHA1 from user-reported false positives - Update change note to document all additions
1 parent a9449cc commit da4a223

File tree

3 files changed

+25
-9
lines changed

3 files changed

+25
-9
lines changed
Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
---
22
category: minorAnalysis
33
---
4-
* The `java/potentially-weak-cryptographic-algorithm` query no longer flags Elliptic Curve algorithms (`EC`, `ECDSA`, `ECDH`, `EdDSA`, `Ed25519`, `Ed448`, `XDH`, `X25519`, `X448`) as potentially insecure. These are modern, secure algorithms recommended by NIST SP 800-57 and other standards bodies. Previously, these algorithms were not included in the secure algorithm whitelist, causing false positives when using standard Java cryptographic APIs such as `KeyPairGenerator.getInstance("EC")`.
4+
* The `java/potentially-weak-cryptographic-algorithm` query no longer flags Elliptic Curve algorithms (`EC`, `ECDSA`, `ECDH`, `EdDSA`, `Ed25519`, `Ed448`, `XDH`, `X25519`, `X448`), HMAC-based algorithms (`HMACSHA1`, `HMACSHA256`, `HMACSHA384`, `HMACSHA512`), or PBKDF2 key derivation as potentially insecure. These are modern, secure algorithms recommended by NIST and other standards bodies. Previously, these algorithms were not included in the secure algorithm whitelist, causing false positives when using standard Java cryptographic APIs such as `KeyPairGenerator.getInstance("EC")` or `new SecretKeySpec(key, "HMACSHA256")`.
5+
* The `Signature.getInstance(...)` method is now modeled as a `CryptoAlgoSpec` sink, alongside the existing `Signature` constructor sink. This ensures that algorithm strings passed to `Signature.getInstance(...)` are also checked by the query.

java/ql/lib/semmle/code/java/security/Encryption.qll

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -263,7 +263,9 @@ string getASecureAlgorithmName() {
263263
// Elliptic Curve algorithms: EC (key generation), ECDSA (signatures), ECDH (key agreement),
264264
// EdDSA/Ed25519/Ed448 (Edwards-curve signatures), XDH/X25519/X448 (key agreement).
265265
// These are modern, secure algorithms recommended by NIST and other standards bodies.
266-
"EC", "ECDSA", "ECDH", "EdDSA", "Ed25519", "Ed448", "XDH", "X25519", "X448"
266+
"EC", "ECDSA", "ECDH", "EdDSA", "Ed25519", "Ed448", "XDH", "X25519", "X448",
267+
// HMAC-based algorithms and key derivation functions.
268+
"HMACSHA(1|256|384|512)", "HmacSHA(1|256|384|512)", "PBKDF2"
267269
]
268270
}
269271

@@ -370,9 +372,13 @@ class JavaSecuritySignature extends JavaSecurityAlgoSpec {
370372
exists(Constructor c | c.getAReference() = this |
371373
c.getDeclaringType().hasQualifiedName("java.security", "Signature")
372374
)
375+
or
376+
exists(Method m | m.getAReference() = this |
377+
m.hasQualifiedName("java.security", "Signature", "getInstance")
378+
)
373379
}
374380

375-
override Expr getAlgoSpec() { result = this.(ConstructorCall).getArgument(0) }
381+
override Expr getAlgoSpec() { result = this.(Call).getArgument(0) }
376382
}
377383

378384
/** A call to the `getInstance` method declared in `java.security.KeyPairGenerator`. */

java/ql/test/query-tests/security/CWE-327/semmle/tests/Test.java

Lines changed: 15 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@ public void test() {
5252
// GOOD: EC is a secure algorithm for key pair generation
5353
keyPairGenerator = KeyPairGenerator.getInstance("EC");
5454

55-
// GOOD: ECDSA is a secure algorithm for digital signatures
55+
// GOOD: ECDSA is a secure signature algorithm
5656
Signature ecdsaSig = Signature.getInstance("ECDSA");
5757

5858
// GOOD: ECDH is a secure algorithm for key agreement
@@ -61,24 +61,33 @@ public void test() {
6161
// GOOD: EdDSA is a secure algorithm (Edwards-curve Digital Signature Algorithm)
6262
keyPairGenerator = KeyPairGenerator.getInstance("EdDSA");
6363

64-
// GOOD: Ed25519 is a secure algorithm
64+
// GOOD: Ed25519 is a secure algorithm for key pair generation
6565
keyPairGenerator = KeyPairGenerator.getInstance("Ed25519");
6666

67-
// GOOD: Ed448 is a secure algorithm
67+
// GOOD: Ed448 is a secure algorithm for key pair generation
6868
keyPairGenerator = KeyPairGenerator.getInstance("Ed448");
6969

7070
// GOOD: XDH is a secure algorithm for key agreement
71-
keyPairGenerator = KeyPairGenerator.getInstance("XDH");
71+
KeyAgreement xdhKa = KeyAgreement.getInstance("XDH");
7272

7373
// GOOD: X25519 is a secure algorithm for key agreement
74-
keyPairGenerator = KeyPairGenerator.getInstance("X25519");
74+
KeyAgreement x25519Ka = KeyAgreement.getInstance("X25519");
7575

7676
// GOOD: X448 is a secure algorithm for key agreement
77-
keyPairGenerator = KeyPairGenerator.getInstance("X448");
77+
KeyAgreement x448Ka = KeyAgreement.getInstance("X448");
7878

7979
// GOOD: SHA256withECDSA is a secure signature algorithm
8080
Signature sha256Ecdsa = Signature.getInstance("SHA256withECDSA");
8181

82+
// GOOD: HMAC-based SecretKeySpec should not be flagged
83+
new SecretKeySpec(null, "HMACSHA1");
84+
new SecretKeySpec(null, "HMACSHA256");
85+
new SecretKeySpec(null, "HMACSHA384");
86+
new SecretKeySpec(null, "SHA384withECDSA");
87+
88+
// GOOD: PBKDF2 key derivation is a secure algorithm
89+
SecretKeyFactory.getInstance("PBKDF2WithHmacSHA1");
90+
8291
} catch (Exception e) {
8392
// fail
8493
}

0 commit comments

Comments
 (0)