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
@@ -0,0 +1,5 @@
---
category: majorAnalysis
---
* The `java/log-injection` query now excludes calls to DEBUG and TRACE level logging methods (`debug`, `trace`, `fine`, `finer`, `finest`) from its sinks, since these log levels are typically disabled in production.
* Added `java.net.URLEncoder.encode()` as a sanitizer for the `java/log-injection` query, since URL encoding replaces line breaks with percent-encoded equivalents.
26 changes: 25 additions & 1 deletion java/ql/lib/semmle/code/java/security/LogInjection.qll
Original file line number Diff line number Diff line change
Expand Up @@ -30,12 +30,36 @@ class LogInjectionAdditionalTaintStep extends Unit {
}

private class DefaultLogInjectionSink extends LogInjectionSink {
DefaultLogInjectionSink() { sinkNode(this, "log-injection") }
DefaultLogInjectionSink() {
sinkNode(this, "log-injection") and
not exists(MethodCall mc |
this.asExpr() = mc.getAnArgument() and
mc.getMethod().getName() in [
"debug", "trace", // SLF4J, Log4j, Commons Logging, JBoss Logging
"fine", "finer", "finest" // java.util.logging
]
)
}
}

private class DefaultLogInjectionSanitizer extends LogInjectionSanitizer instanceof SimpleTypeSanitizer
{ }

/**
* A call to `java.net.URLEncoder.encode(...)` is considered a sanitizer for log injection,
* since URL encoding replaces line breaks and other special characters with percent-encoded
* equivalents that cannot be used to forge log entries.
*/
private class UrlEncoderSanitizer extends LogInjectionSanitizer {
UrlEncoderSanitizer() {
exists(MethodCall mc |
mc.getMethod().getDeclaringType().hasQualifiedName("java.net", "URLEncoder") and
mc.getMethod().hasName("encode") and
this.asExpr() = mc
)
}
}

private class LineBreaksLogInjectionSanitizer extends LogInjectionSanitizer {
LineBreaksLogInjectionSanitizer() {
logInjectionSanitizer(this.asExpr())
Expand Down
5 changes: 4 additions & 1 deletion java/ql/src/Security/CWE/CWE-117/LogInjection.ql
Original file line number Diff line number Diff line change
Expand Up @@ -13,9 +13,12 @@

import java
import semmle.code.java.security.LogInjectionQuery
import semmle.code.java.dataflow.internal.ModelExclusions
import LogInjectionFlow::PathGraph

from LogInjectionFlow::PathNode source, LogInjectionFlow::PathNode sink
where LogInjectionFlow::flowPath(source, sink)
where
LogInjectionFlow::flowPath(source, sink) and
not isInTestFile(sink.getNode().getLocation().getFile())
select sink.getNode(), source, sink, "This log entry depends on a $@.", source.getNode(),
"user-provided value"
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
---
category: majorAnalysis
---
* The `java/log-injection` query now excludes calls to DEBUG and TRACE level logging methods (`debug`, `trace`, `fine`, `finer`, `finest`) from its results, since these log levels are typically disabled in production and do not present a realistic log injection attack surface.
* The `java/log-injection` query now recognizes `java.net.URLEncoder.encode()` as a sanitizer, since URL encoding replaces line breaks and other special characters with percent-encoded equivalents.
* The `java/log-injection` query now excludes results in test files to reduce noise from non-production code.
Loading