Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"ruleKey": "S6437",
"hasTruePositives": true,
"falseNegatives": 63,
"falseNegatives": 62,
"falsePositives": 0
}

This file was deleted.

6 changes: 1 addition & 5 deletions its/ruling/src/test/resources/regex-examples/java-S2068.json
Original file line number Diff line number Diff line change
@@ -1,9 +1,5 @@
{
"org.regex-examples:regex-examples:src/main/java/org/regex/examples/RegexDatabase1.java": [
749
],
"org.regex-examples:regex-examples:src/main/java/org/regex/examples/RegexDatabase8.java": [
727,
1257
727
]
}
4 changes: 4 additions & 0 deletions java-checks-aws/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,10 @@
<artifactId>commons-io</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.sonarsource.analyzer-commons</groupId>
<artifactId>sonar-analyzer-commons</artifactId>
</dependency>
<dependency>
<groupId>org.sonarsource.analyzer-commons</groupId>
<artifactId>sonar-analyzer-recognizers</artifactId>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,9 @@
import org.sonar.java.annotations.VisibleForTesting;
import org.sonar.java.checks.helpers.CredentialMethod;
import org.sonar.java.checks.helpers.CredentialMethodsLoader;
import org.sonar.java.checks.helpers.ExpressionsHelper;
import org.sonar.plugins.java.api.IssuableSubscriptionVisitor;
import org.sonarsource.analyzer.commons.appsec.SecretClassifier;
import org.sonar.plugins.java.api.JavaFileScannerContext;
import org.sonar.plugins.java.api.semantic.MethodMatchers;
import org.sonar.plugins.java.api.tree.Arguments;
Expand Down Expand Up @@ -108,6 +110,10 @@ private void checkArguments(Arguments arguments, CredentialMethod method) {
ExpressionTree argument = arguments.get(targetArgumentIndex);
var secondaryLocations = new ArrayList<JavaFileScannerContext.Location>();
if (isExpressionDerivedFromPlainText(argument, secondaryLocations, new HashSet<>())) {
String value = ExpressionsHelper.getConstantValueAsString(argument).value();
if (value != null && SecretClassifier.isKnownNonSecret(value)) {
continue;
}
reportIssue(argument, ISSUE_MESSAGE, secondaryLocations, null);
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -32,10 +32,11 @@
import static java.lang.System.getProperty;

public class HardCodedCredentialsShouldNotBeUsedCheckSample {
static final String FINAL_SECRET_STRING = "hunter2";
// ^^^^^^^^^>
static final byte[] FINAL_SECRET_BYTE_ARRAY = FINAL_SECRET_STRING.getBytes(StandardCharsets.UTF_8);
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^>
static final String FINAL_SECRET_STRING = "hunter2"; // Compliant, fake value filter
static final String FINAL_SECRET_STRING_2 = "xvxf6_gaa";
Comment on lines +35 to +36

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should one of the names indicate that it's a fake? Alas, that would balloon the diff :-(

// ^^^^^^^^^^^>
static final byte[] FINAL_SECRET_BYTE_ARRAY = FINAL_SECRET_STRING_2.getBytes(StandardCharsets.UTF_8);
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^>
private static String secretStringField = "hunter2";
private static byte[] secretByteArrayField = new byte[]{0xC, 0xA, 0xF, 0xE};
private static char[] secretCharArrayField = new char[]{0xC, 0xA, 0xF, 0xE};
Expand All @@ -54,39 +55,44 @@ public static void nonCompliant(byte[] message, boolean condition, Charset encod
// ^^^
SHA256.getHMAC(effectivelyConstantString.getBytes(), message); // Noncompliant
SHA256.getHMAC("anotherS3cr37".getBytes(), message); // Noncompliant
// FINAL_SECRET_STRING.getBytes() cannot be resolved to the value "hunter2" that should be filtered -> FPs
SHA256.getHMAC(FINAL_SECRET_STRING.getBytes(), message); // Noncompliant
SHA256.getHMAC(FINAL_SECRET_STRING.getBytes(StandardCharsets.UTF_8), message); // Noncompliant
SHA256.getHMAC(FINAL_SECRET_STRING.getBytes("UTF-8"), message); // Noncompliant
SHA256.getHMAC((FINAL_SECRET_STRING).getBytes("UTF-8"), message); // Noncompliant
SHA256.getHMAC(new byte[]{(byte) 0xC, (byte) 0xA, (byte) 0xF, (byte) 0xE}, message); // Noncompliant
// FP should be filtered as short string value
SHA256.getHMAC(new byte[]{(byte) 0xC, (byte) 0xA, (byte) 0xF, (byte) 0xE}, message); // Noncompliant

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
SHA256.getHMAC(new byte[]{(byte) 0xC, (byte) 0xA, (byte) 0xF, (byte) 0xE}, message); // Noncompliant
SHA256.getHMAC(new byte[]{(byte) 0xC, (byte) 0xA, (byte) 0xF, (byte) 0xE}, message); // Noncompliant

This is about a hardcoded key for getHMAC, we probably should not suppress it?


// String based
HttpServletRequest request = new HttpServletRequestWrapper(null);
request.login("user", "password"); // Noncompliant
request.login("user", "password"); // Compliant, fake value filter
request.login("user", "xvxf6_gaa"); // Noncompliant
request.login("user", effectivelyConstantString); // Noncompliant
// ^^^^^^^^^^^^^^^^^^^^^^^^^
request.login("user", FINAL_SECRET_STRING); // Noncompliant
// ^^^^^^^^^^^^^^^^^^^
String plainTextSecret = new String("BOOM");
// ^^^^^^^^^^^^^^^^^^>
request.login("user", plainTextSecret); // Noncompliant
// ^^^^^^^^^^^^^^^
request.login("user", FINAL_SECRET_STRING); // Compliant, fake values filter
request.login("user", FINAL_SECRET_STRING_2); // Noncompliant
// ^^^^^^^^^^^^^^^^^^^^^
String plainTextSecret = new String("BOOM"); // Compliant, short values filter
String plainTextSecret2 = new String("BOOMBOOM");
// ^^^^^^^^^^^^^^^^^^^^^^>
request.login("user", plainTextSecret2); // Noncompliant
// ^^^^^^^^^^^^^^^^
request.login("user", new String("secret")); // Noncompliant

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Was this not already suppressed, even before SonarSource/sonar-analyzer-commons#418?

request.login("user", new String(FINAL_SECRET_BYTE_ARRAY, 0, 7)); // Noncompliant
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^@37<
// ^^^^^^^^^@35<
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^@38<
// ^^^^^^^^^^^@36<
request.login("user", new String(FINAL_SECRET_BYTE_ARRAY, encoding)); // Noncompliant
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^@37<
// ^^^^^^^^^@35<
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^@38<
// ^^^^^^^^^^^@36<

String conditionalButPredictable = condition ? FINAL_SECRET_STRING : plainTextSecret;
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^>
String conditionalButPredictable = condition ? FINAL_SECRET_STRING_2 : plainTextSecret2;
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^>
request.login("user", conditionalButPredictable); // Noncompliant
// ^^^^^^^^^^^^^^^^^^^^^^^^^
// ^^^^^^^^^@35<
// ^^^^^^^^^^^^^^^^^^@70<
// ^^^^^^^^^^^@36<
// ^^^^^^^^^^^^^^^^^^^^^^@76<
request.login("user", Json.MEDIA_TYPE); // Noncompliant
// ^^^^^^^^^^^^^^^
String concatenatedPassword = "abc" + true + ":" + 12 + ":" + 43L + ":" + 'a' + ":" + 0.2f + ":" + 0.2d;
Expand All @@ -95,7 +101,8 @@ public static void nonCompliant(byte[] message, boolean condition, Charset encod
// ^^^^^^^^^^^^^^^^^^^^

jakarta.servlet.http.HttpServletRequest requestJakarta = new jakarta.servlet.http.HttpServletRequestWrapper(null);
requestJakarta.login("user", "password"); // Noncompliant
requestJakarta.login("user", "password"); // Compliant
requestJakarta.login("user", "xvxf6_gaa"); // Noncompliant
KeyStore store = KeyStore.getInstance(null);

store.getKey("", new char[]{0xC, 0xA, 0xF, 0xE}); // Noncompliant
Expand All @@ -118,38 +125,52 @@ public static void nonCompliant(byte[] message, boolean condition, Charset encod

Encryptors.delux(effectivelyConstantString.subSequence(0, effectivelyConstantString.length()), effectivelyConstantString); // Noncompliant
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
// "password".subSequence(0, 0) cannot be resolved to the value "password" that should be filtered -> FPs
Encryptors.delux("password".subSequence(0, 0), "salt"); // Noncompliant
Comment on lines +128 to 129

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
// "password".subSequence(0, 0) cannot be resolved to the value "password" that should be filtered -> FPs
Encryptors.delux("password".subSequence(0, 0), "salt"); // Noncompliant
Encryptors.delux("password".subSequence(0, 0), "salt"); // Noncompliant, FP, subSequence is not resolved to a filtered "password" value.

I would follow the style where the comment for the marker is on the same line, but worth confirming how it is done elsewhere in the project.

// TP
Encryptors.delux("xvxf6_gaa".subSequence(0, 0), "salt"); // Noncompliant
Comment on lines +130 to +131

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
// TP
Encryptors.delux("xvxf6_gaa".subSequence(0, 0), "salt"); // Noncompliant
Encryptors.delux("xvxf6_gaa".subSequence(0, 0), "salt"); // Noncompliant


new Pbkdf2PasswordEncoder("secret"); // Noncompliant
new Pbkdf2PasswordEncoder(("secret")); // Noncompliant
new Pbkdf2PasswordEncoder("secret"); // Compliant, fake value filter
new Pbkdf2PasswordEncoder("xvxf6_gaa"); // Noncompliant
new Pbkdf2PasswordEncoder(("xvxf6_gaa")); // Noncompliant


String notInitialized;
notInitialized = "abc";
new Pbkdf2PasswordEncoder(notInitialized); // Noncompliant
new Pbkdf2PasswordEncoder(notInitialized); // Compliant, short value filter

String notInitialized2;
notInitialized2 = "xvxf6_gaa";
new Pbkdf2PasswordEncoder(notInitialized2); // Noncompliant

String longString = "abcdefghiklmnop";
String longString = "abcdefghiklmnop"; // Cpmpliant fake value contains 'abcd'
// longString.substring(2) cannot be resolved to the value "abcdefghiklmnop" that should be filtered -> FPs

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same as above.

new Pbkdf2PasswordEncoder(longString.substring(2)); // Noncompliant
new Pbkdf2PasswordEncoder(longString.substring(0, 2)); // Noncompliant
new Pbkdf2PasswordEncoder(longString.trim()); // Noncompliant
new Pbkdf2PasswordEncoder(longString.strip()); // Noncompliant
new Pbkdf2PasswordEncoder(longString.stripIndent()); // Noncompliant
new Pbkdf2PasswordEncoder(longString.stripLeading()); // Noncompliant
new Pbkdf2PasswordEncoder(longString.stripTrailing()); // Noncompliant
new Pbkdf2PasswordEncoder(longString.translateEscapes()); // Noncompliant
new Pbkdf2PasswordEncoder(longString.intern()); // Noncompliant
new Pbkdf2PasswordEncoder(longString.toLowerCase()); // Noncompliant
new Pbkdf2PasswordEncoder(longString.toLowerCase(Locale.ROOT)); // Noncompliant
new Pbkdf2PasswordEncoder(longString.toUpperCase()); // Noncompliant
new Pbkdf2PasswordEncoder(longString.toUpperCase(Locale.ROOT)); // Noncompliant
new Pbkdf2PasswordEncoder(longString.toString()); // Noncompliant
String longString2 = "67uLmZeieGxDtp!cUm324D*7vji294";
new Pbkdf2PasswordEncoder(longString2.substring(2)); // Noncompliant
new Pbkdf2PasswordEncoder(longString2.substring(0, 2)); // Noncompliant
new Pbkdf2PasswordEncoder(longString2.trim()); // Noncompliant
new Pbkdf2PasswordEncoder(longString2.strip()); // Noncompliant
new Pbkdf2PasswordEncoder(longString2.stripIndent()); // Noncompliant
new Pbkdf2PasswordEncoder(longString2.stripLeading()); // Noncompliant
new Pbkdf2PasswordEncoder(longString2.stripTrailing()); // Noncompliant
new Pbkdf2PasswordEncoder(longString2.translateEscapes()); // Noncompliant
new Pbkdf2PasswordEncoder(longString2.intern()); // Noncompliant
new Pbkdf2PasswordEncoder(longString2.toLowerCase()); // Noncompliant
new Pbkdf2PasswordEncoder(longString2.toLowerCase(Locale.ROOT)); // Noncompliant
new Pbkdf2PasswordEncoder(longString2.toUpperCase()); // Noncompliant
new Pbkdf2PasswordEncoder(longString2.toUpperCase(Locale.ROOT)); // Noncompliant
new Pbkdf2PasswordEncoder(longString2.toString()); // Noncompliant

Object stringAsObject = "abc";
new Pbkdf2PasswordEncoder(stringAsObject.toString()); // Noncompliant

java.util.function.Consumer<String> lambda = (arg) -> {
new Pbkdf2PasswordEncoder(arg);
String variableWithNullOwner = "abc";
new Pbkdf2PasswordEncoder(variableWithNullOwner); // Noncompliant
new Pbkdf2PasswordEncoder(variableWithNullOwner); // Compliant, short value filter
String variableWithNullOwner2 = "xvxf6_gaa";
new Pbkdf2PasswordEncoder(variableWithNullOwner2); // Noncompliant
};

byte[] secretBytes = FINAL_SECRET_STRING.getBytes("UTF-8");
Expand All @@ -163,7 +184,7 @@ public static void nonCompliant(byte[] message, boolean condition, Charset encod
.signWith(paremSignatureAlgorithm, secretBytes); // Noncompliant

Jwts.builder()
.signWith(SignatureAlgorithm.HS256, FINAL_SECRET_STRING); // Noncompliant
.signWith(SignatureAlgorithm.HS256, FINAL_SECRET_STRING); // Compliant, "hunter2" rejected by the fake value filter

Jwts.builder()
.signWith(SignatureAlgorithm.HS256, TextCodec.BASE64.encode(FINAL_SECRET_STRING)); // Noncompliant
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,8 +8,8 @@
class HardCodedPasswordCheckSample {

private void a(char[] pwd, String var) throws SQLException {
MyUnknownClass.myUnknownMethod("password", "xxxxx"); // Noncompliant
MyUnknownClass.myUnknownMethod("other", "xxxxx"); // Compliant
MyUnknownClass.myUnknownMethod("password", "xvxf6_gaa"); // Noncompliant
MyUnknownClass.myUnknownMethod("other", "xvxf6_gaa"); // Compliant
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -8,35 +8,40 @@ class HardCodedPasswordCheckCustom {
String fieldNameWithBazookaInIt;

private void a(char[] pwd, String var) {
String variable2 = "login=a&password=xxx"; // Compliant
String variable3 = "login=a&passwd=xxx"; // Compliant
String variable4 = "login=a&pwd=xxx"; // Compliant
String variable5 = "login=a&marmalade=xxx"; // Noncompliant {{'marmalade' detected in this expression, review this potentially hard-coded password.}}
// ^^^^^^^^^^^^^^^^^^^^^^^
String variable6 = "login=a&bazooka=xxx "; // Noncompliant

String variableNameWithBazookaInIt = "xxx"; // Noncompliant
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^
String variableNameWithmarMalAdeInIt = "xxx"; // Noncompliant
String variable2 = "login=a&password=xvxf6_gaa"; // Compliant
String variable3 = "login=a&passwd=xvxf6_gaa"; // Compliant
String variable4 = "login=a&pwd=xvxf6_gaa"; // Compliant
Comment on lines +11 to +13

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

These should be noncompliant, right?

String variable5 = "login=a&marmalade=xxx"; // Compliant, short value filter
String variable5_2 = "login=a&marmalade=xvxf6_gaa"; // Noncompliant {{'marmalade' detected in this expression, review this potentially hard-coded password.}}
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
String variable6 = "login=a&bazooka=xxx"; // Compliant, short value filter
String variable6_2 = "login=a&bazooka=xvxf6_gaa"; // Noncompliant

String variableNameWithBazookaInIt = "xxx"; // Compliant, short value filter
String variableNameWithBazookaInIt_2 = "xvxf6_gaa"; // Noncompliant
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
String variableNameWithPwdInIt = "xxx"; // Compliant
String variableNameWithmarMalAdeInIt = "xvxf6_gaa"; // Noncompliant
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
String variableNameWithPwdInIt = "xvxf6_gaa"; // Compliant
String otherVariableNameWithPasswordInIt;
fieldNameWithPasswordInIt = "xx"; // Compliant
this.fieldNameWithBazookaInIt = "xx"; // Noncompliant
fieldNameWithPasswordInIt = "xx";
this.fieldNameWithBazookaInIt = "xx"; // Compliant, , short value filter


HardCodedPasswordCheckCustom myA = new HardCodedPasswordCheckCustom();
myA.setProperty("marmalade", "xxxxx"); // Noncompliant
myA.setProperty("passwd", "xxxxx"); //Compliant
myA.setProperty("pwd", "xxxxx"); // Compliant
myA.setProperty("marmalade", "xxxxx"); // Compliant, short value filter
myA.setProperty("marmalade", "xvxf6_gaa"); // Noncompliant
myA.setProperty("marmalade", "marmalade"); // Compliant
myA.setProperty("passwd", "xvxf6_gaa"); //Compliant
myA.setProperty("pwd", "xvxf6_gaa"); // Compliant


new PasswordAuthentication("userName", "1234".toCharArray()); // Compliant, handled by S6437
new PasswordAuthentication("userName", "xvxf6_gaa".toCharArray()); // Compliant, handled by S6437
new PasswordAuthentication("userName", pwd); // Compliant
new PasswordAuthentication("userName", getPwd(var)); // Compliant
new PasswordAuthentication("userName", var.toCharArray()); // Compliant

new OtherPasswordAuthentication("userName", "1234".toCharArray()); // Compliant
new OtherPasswordAuthentication("userName", "xvxf6_gaa".toCharArray()); // Compliant
}

private void setProperty(Object property, Object Value) { }
Expand Down
Loading
Loading