forked from github/codeql
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathUnsafeCertTrustQuery.qll
More file actions
70 lines (58 loc) · 2.68 KB
/
UnsafeCertTrustQuery.qll
File metadata and controls
70 lines (58 loc) · 2.68 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
/** Provides taint tracking configurations to be used by unsafe certificate trust queries. */
import java
import semmle.code.java.dataflow.TaintTracking
import semmle.code.java.security.UnsafeCertTrust
import semmle.code.java.security.Encryption
/**
* A taint flow configuration for SSL connections created without a proper certificate trust configuration.
*/
module SslEndpointIdentificationFlowConfig implements DataFlow::ConfigSig {
predicate isSource(DataFlow::Node source) { source instanceof SslConnectionInit }
predicate isSink(DataFlow::Node sink) { sink instanceof SslConnectionCreation }
predicate isBarrier(DataFlow::Node sanitizer) { sanitizer instanceof SslUnsafeCertTrustSanitizer }
predicate observeDiffInformedIncrementalMode() { any() }
Location getASelectedSourceLocation(DataFlow::Node source) { none() }
}
/**
* Taint flow for SSL connections created without a proper certificate trust configuration.
*/
module SslEndpointIdentificationFlow = TaintTracking::Global<SslEndpointIdentificationFlowConfig>;
/**
* An SSL object that was assigned a safe `SSLParameters` object and can be considered safe.
*/
private class SslConnectionWithSafeSslParameters extends SslUnsafeCertTrustSanitizer {
SslConnectionWithSafeSslParameters() {
exists(DataFlow::Node safe, DataFlow::Node sanitizer |
SafeSslParametersFlow::flowTo(safe) and
sanitizer = DataFlow::exprNode(safe.asExpr().(Argument).getCall().getQualifier()) and
DataFlow::localFlow(sanitizer, this)
)
}
}
private module SafeSslParametersFlowConfig implements DataFlow::ConfigSig {
predicate isSource(DataFlow::Node source) {
exists(MethodCall ma |
ma instanceof SafeSetEndpointIdentificationAlgorithm and
DataFlow::getInstanceArgument(ma) = source.(DataFlow::PostUpdateNode).getPreUpdateNode()
)
}
predicate isSink(DataFlow::Node sink) {
exists(MethodCall ma, RefType t | t instanceof SslSocket or t instanceof SslEngine |
ma.getMethod().hasName("setSSLParameters") and
ma.getMethod().getDeclaringType().getAnAncestor() = t and
ma.getArgument(0) = sink.asExpr()
)
}
}
private module SafeSslParametersFlow = DataFlow::Global<SafeSslParametersFlowConfig>;
/**
* A call to `SSLParameters.setEndpointIdentificationAlgorithm` with a non-null and non-empty parameter.
*/
private class SafeSetEndpointIdentificationAlgorithm extends MethodCall {
SafeSetEndpointIdentificationAlgorithm() {
this.getMethod().hasName("setEndpointIdentificationAlgorithm") and
this.getMethod().getDeclaringType() instanceof SslParameters and
not this.getArgument(0) instanceof NullLiteral and
not this.getArgument(0).(CompileTimeConstantExpr).getStringValue() = ""
}
}