mirror of
https://github.com/github/codeql.git
synced 2025-12-21 19:26:31 +01:00
Merge pull request #12723 from michaelnebel/csharp/refactordataflow2
C#: Re-factor queries to use the new API.
This commit is contained in:
@@ -90,8 +90,12 @@ class ExternalApiDataNode extends DataFlow::Node {
|
|||||||
/** DEPRECATED: Alias for ExternalApiDataNode */
|
/** DEPRECATED: Alias for ExternalApiDataNode */
|
||||||
deprecated class ExternalAPIDataNode = ExternalApiDataNode;
|
deprecated class ExternalAPIDataNode = ExternalApiDataNode;
|
||||||
|
|
||||||
/** A configuration for tracking flow from `RemoteFlowSource`s to `ExternalApiDataNode`s. */
|
/**
|
||||||
class UntrustedDataToExternalApiConfig extends TaintTracking::Configuration {
|
* DEPRECATED: Use `RemoteSourceToExternalApi` instead.
|
||||||
|
*
|
||||||
|
* A configuration for tracking flow from `RemoteFlowSource`s to `ExternalApiDataNode`s.
|
||||||
|
*/
|
||||||
|
deprecated class UntrustedDataToExternalApiConfig extends TaintTracking::Configuration {
|
||||||
UntrustedDataToExternalApiConfig() { this = "UntrustedDataToExternalAPIConfig" }
|
UntrustedDataToExternalApiConfig() { this = "UntrustedDataToExternalAPIConfig" }
|
||||||
|
|
||||||
override predicate isSource(DataFlow::Node source) { source instanceof RemoteFlowSource }
|
override predicate isSource(DataFlow::Node source) { source instanceof RemoteFlowSource }
|
||||||
@@ -99,17 +103,25 @@ class UntrustedDataToExternalApiConfig extends TaintTracking::Configuration {
|
|||||||
override predicate isSink(DataFlow::Node sink) { sink instanceof ExternalApiDataNode }
|
override predicate isSink(DataFlow::Node sink) { sink instanceof ExternalApiDataNode }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** A configuration for tracking flow from `RemoteFlowSource`s to `ExternalApiDataNode`s. */
|
||||||
|
private module RemoteSourceToExternalApiConfig implements DataFlow::ConfigSig {
|
||||||
|
predicate isSource(DataFlow::Node source) { source instanceof RemoteFlowSource }
|
||||||
|
|
||||||
|
predicate isSink(DataFlow::Node sink) { sink instanceof ExternalApiDataNode }
|
||||||
|
}
|
||||||
|
|
||||||
|
/** A module for tracking flow from `RemoteFlowSource`s to `ExternalApiDataNode`s. */
|
||||||
|
module RemoteSourceToExternalApi = TaintTracking::Global<RemoteSourceToExternalApiConfig>;
|
||||||
|
|
||||||
/** DEPRECATED: Alias for UntrustedDataToExternalApiConfig */
|
/** DEPRECATED: Alias for UntrustedDataToExternalApiConfig */
|
||||||
deprecated class UntrustedDataToExternalAPIConfig = UntrustedDataToExternalApiConfig;
|
deprecated class UntrustedDataToExternalAPIConfig = UntrustedDataToExternalApiConfig;
|
||||||
|
|
||||||
/** A node representing untrusted data being passed to an external API. */
|
/** A node representing untrusted data being passed to an external API. */
|
||||||
class UntrustedExternalApiDataNode extends ExternalApiDataNode {
|
class UntrustedExternalApiDataNode extends ExternalApiDataNode {
|
||||||
private UntrustedDataToExternalApiConfig c;
|
UntrustedExternalApiDataNode() { RemoteSourceToExternalApi::flow(_, this) }
|
||||||
|
|
||||||
UntrustedExternalApiDataNode() { c.hasFlow(_, this) }
|
|
||||||
|
|
||||||
/** Gets a source of untrusted data which is passed to this external API data node. */
|
/** Gets a source of untrusted data which is passed to this external API data node. */
|
||||||
DataFlow::Node getAnUntrustedSource() { c.hasFlow(result, this) }
|
DataFlow::Node getAnUntrustedSource() { RemoteSourceToExternalApi::flow(result, this) }
|
||||||
}
|
}
|
||||||
|
|
||||||
/** DEPRECATED: Alias for UntrustedExternalApiDataNode */
|
/** DEPRECATED: Alias for UntrustedExternalApiDataNode */
|
||||||
|
|||||||
@@ -38,9 +38,11 @@ abstract class Sink extends DataFlow::ExprNode {
|
|||||||
abstract class Sanitizer extends DataFlow::ExprNode { }
|
abstract class Sanitizer extends DataFlow::ExprNode { }
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* DEPRECATED: Use `HardcodedCredentials` instead.
|
||||||
|
*
|
||||||
* A taint-tracking configuration for hard coded credentials.
|
* A taint-tracking configuration for hard coded credentials.
|
||||||
*/
|
*/
|
||||||
class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
deprecated class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
||||||
TaintTrackingConfiguration() { this = "HardcodedCredentials" }
|
TaintTrackingConfiguration() { this = "HardcodedCredentials" }
|
||||||
|
|
||||||
override predicate isSource(DataFlow::Node source) { source instanceof Source }
|
override predicate isSource(DataFlow::Node source) { source instanceof Source }
|
||||||
@@ -75,6 +77,56 @@ class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
|||||||
override predicate isSanitizer(DataFlow::Node node) { node instanceof Sanitizer }
|
override predicate isSanitizer(DataFlow::Node node) { node instanceof Sanitizer }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A taint-tracking configuration for hard coded credentials.
|
||||||
|
*/
|
||||||
|
private module HardcodedCredentialsConfig implements DataFlow::ConfigSig {
|
||||||
|
predicate isSource(DataFlow::Node source) { source instanceof Source }
|
||||||
|
|
||||||
|
predicate isSink(DataFlow::Node sink) {
|
||||||
|
sink instanceof Sink and
|
||||||
|
// Ignore values that are ultimately returned by mocks, as they don't represent "real"
|
||||||
|
// credentials.
|
||||||
|
not any(ReturnedByMockObject mock).getAMemberInitializationValue() = sink.asExpr() and
|
||||||
|
not any(ReturnedByMockObject mock).getAnArgument() = sink.asExpr()
|
||||||
|
}
|
||||||
|
|
||||||
|
predicate isBarrier(DataFlow::Node node) { node instanceof Sanitizer }
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A taint-tracking module for hard coded credentials.
|
||||||
|
*/
|
||||||
|
module HardcodedCredentials {
|
||||||
|
import TaintTracking::Global<HardcodedCredentialsConfig> as Super
|
||||||
|
import Super
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Holds if data can flow from `source` to `sink`.
|
||||||
|
*
|
||||||
|
* The corresponding paths are generated from the end-points and the graph
|
||||||
|
* included in the module `PathGraph`.
|
||||||
|
*/
|
||||||
|
predicate flowPath(HardcodedCredentials::PathNode source, HardcodedCredentials::PathNode sink) {
|
||||||
|
Super::flowPath(source, sink) and
|
||||||
|
// Exclude hard-coded credentials in tests if they only flow to calls to methods with a name
|
||||||
|
// like "Add*" "Create*" or "Update*". The rationale is that hard-coded credentials within
|
||||||
|
// tests that are only used for creating or setting values within tests are unlikely to
|
||||||
|
// represent credentials to some accessible system.
|
||||||
|
not (
|
||||||
|
source.getNode().asExpr().getFile() instanceof TestFile and
|
||||||
|
exists(MethodCall createOrAddCall, string createOrAddMethodName |
|
||||||
|
createOrAddMethodName.matches("Update%") or
|
||||||
|
createOrAddMethodName.matches("Create%") or
|
||||||
|
createOrAddMethodName.matches("Add%")
|
||||||
|
|
|
||||||
|
createOrAddCall.getTarget().hasName(createOrAddMethodName) and
|
||||||
|
createOrAddCall.getAnArgument() = sink.getNode().asExpr()
|
||||||
|
)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A string literal that is not empty.
|
* A string literal that is not empty.
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -25,9 +25,11 @@ abstract class Sink extends DataFlow::ExprNode { }
|
|||||||
abstract class Sanitizer extends DataFlow::ExprNode { }
|
abstract class Sanitizer extends DataFlow::ExprNode { }
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* DEPRECATED: Use `LdapInjection` instead.
|
||||||
|
*
|
||||||
* A taint-tracking configuration for unvalidated user input that is used to construct LDAP queries.
|
* A taint-tracking configuration for unvalidated user input that is used to construct LDAP queries.
|
||||||
*/
|
*/
|
||||||
class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
deprecated class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
||||||
TaintTrackingConfiguration() { this = "LDAPInjection" }
|
TaintTrackingConfiguration() { this = "LDAPInjection" }
|
||||||
|
|
||||||
override predicate isSource(DataFlow::Node source) { source instanceof Source }
|
override predicate isSource(DataFlow::Node source) { source instanceof Source }
|
||||||
@@ -37,6 +39,32 @@ class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
|||||||
override predicate isSanitizer(DataFlow::Node node) { node instanceof Sanitizer }
|
override predicate isSanitizer(DataFlow::Node node) { node instanceof Sanitizer }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A taint-tracking configuration for unvalidated user input that is used to construct LDAP queries.
|
||||||
|
*/
|
||||||
|
module LdapInjectionConfig implements DataFlow::ConfigSig {
|
||||||
|
/**
|
||||||
|
* Holds if `source` is a relevant data flow source.
|
||||||
|
*/
|
||||||
|
predicate isSource(DataFlow::Node source) { source instanceof Source }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Holds if `sink` is a relevant data flow sink.
|
||||||
|
*/
|
||||||
|
predicate isSink(DataFlow::Node sink) { sink instanceof Sink }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Holds if data flow through `node` is prohibited. This completely removes
|
||||||
|
* `node` from the data flow graph.
|
||||||
|
*/
|
||||||
|
predicate isBarrier(DataFlow::Node node) { node instanceof Sanitizer }
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A taint-tracking configuration for unvalidated user input that is used to construct LDAP queries.
|
||||||
|
*/
|
||||||
|
module LdapInjection = TaintTracking::Global<LdapInjectionConfig>;
|
||||||
|
|
||||||
/** A source of remote user input. */
|
/** A source of remote user input. */
|
||||||
class RemoteSource extends Source instanceof RemoteFlowSource { }
|
class RemoteSource extends Source instanceof RemoteFlowSource { }
|
||||||
|
|
||||||
|
|||||||
@@ -25,9 +25,11 @@ abstract class Sink extends DataFlow::ExprNode { }
|
|||||||
abstract class Sanitizer extends DataFlow::ExprNode { }
|
abstract class Sanitizer extends DataFlow::ExprNode { }
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* DEPRECATED: Use `LogForging` instead.
|
||||||
|
*
|
||||||
* A taint-tracking configuration for untrusted user input used in log entries.
|
* A taint-tracking configuration for untrusted user input used in log entries.
|
||||||
*/
|
*/
|
||||||
class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
deprecated class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
||||||
TaintTrackingConfiguration() { this = "LogForging" }
|
TaintTrackingConfiguration() { this = "LogForging" }
|
||||||
|
|
||||||
override predicate isSource(DataFlow::Node source) { source instanceof Source }
|
override predicate isSource(DataFlow::Node source) { source instanceof Source }
|
||||||
@@ -37,6 +39,22 @@ class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
|||||||
override predicate isSanitizer(DataFlow::Node node) { node instanceof Sanitizer }
|
override predicate isSanitizer(DataFlow::Node node) { node instanceof Sanitizer }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A taint-tracking configuration for untrusted user input used in log entries.
|
||||||
|
*/
|
||||||
|
private module LogForgingConfig implements DataFlow::ConfigSig {
|
||||||
|
predicate isSource(DataFlow::Node source) { source instanceof Source }
|
||||||
|
|
||||||
|
predicate isSink(DataFlow::Node sink) { sink instanceof Sink }
|
||||||
|
|
||||||
|
predicate isBarrier(DataFlow::Node node) { node instanceof Sanitizer }
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A taint-tracking module for untrusted user input used in log entries.
|
||||||
|
*/
|
||||||
|
module LogForging = TaintTracking::Global<LogForgingConfig>;
|
||||||
|
|
||||||
/** A source of remote user input. */
|
/** A source of remote user input. */
|
||||||
private class RemoteSource extends Source instanceof RemoteFlowSource { }
|
private class RemoteSource extends Source instanceof RemoteFlowSource { }
|
||||||
|
|
||||||
|
|||||||
@@ -29,10 +29,12 @@ abstract class Sink extends DataFlow::ExprNode {
|
|||||||
abstract class Sanitizer extends DataFlow::ExprNode { }
|
abstract class Sanitizer extends DataFlow::ExprNode { }
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* DEPRECATED: Use `MissingXxmlValidation` instead.
|
||||||
|
*
|
||||||
* A taint-tracking configuration for untrusted user input processed as XML without validation against a
|
* A taint-tracking configuration for untrusted user input processed as XML without validation against a
|
||||||
* known schema.
|
* known schema.
|
||||||
*/
|
*/
|
||||||
class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
deprecated class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
||||||
TaintTrackingConfiguration() { this = "MissingXMLValidation" }
|
TaintTrackingConfiguration() { this = "MissingXMLValidation" }
|
||||||
|
|
||||||
override predicate isSource(DataFlow::Node source) { source instanceof Source }
|
override predicate isSource(DataFlow::Node source) { source instanceof Source }
|
||||||
@@ -42,6 +44,24 @@ class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
|||||||
override predicate isSanitizer(DataFlow::Node node) { node instanceof Sanitizer }
|
override predicate isSanitizer(DataFlow::Node node) { node instanceof Sanitizer }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A taint-tracking configuration for untrusted user input processed as XML without validation against a
|
||||||
|
* known schema.
|
||||||
|
*/
|
||||||
|
private module MissingXmlValidationConfig implements DataFlow::ConfigSig {
|
||||||
|
predicate isSource(DataFlow::Node source) { source instanceof Source }
|
||||||
|
|
||||||
|
predicate isSink(DataFlow::Node sink) { sink instanceof Sink }
|
||||||
|
|
||||||
|
predicate isBarrier(DataFlow::Node node) { node instanceof Sanitizer }
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A taint-tracking module for untrusted user input processed as XML without validation against a
|
||||||
|
* known schema.
|
||||||
|
*/
|
||||||
|
module MissingXmlValidation = TaintTracking::Global<MissingXmlValidationConfig>;
|
||||||
|
|
||||||
/** A source of remote user input. */
|
/** A source of remote user input. */
|
||||||
class RemoteSource extends Source instanceof RemoteFlowSource { }
|
class RemoteSource extends Source instanceof RemoteFlowSource { }
|
||||||
|
|
||||||
|
|||||||
@@ -25,9 +25,11 @@ abstract class Sink extends DataFlow::ExprNode { }
|
|||||||
abstract class Sanitizer extends DataFlow::ExprNode { }
|
abstract class Sanitizer extends DataFlow::ExprNode { }
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* DEPRECATED: Use `ReDoS` instead.
|
||||||
|
*
|
||||||
* A taint-tracking configuration for untrusted user input used in dangerous regular expression operations.
|
* A taint-tracking configuration for untrusted user input used in dangerous regular expression operations.
|
||||||
*/
|
*/
|
||||||
class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
deprecated class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
||||||
TaintTrackingConfiguration() { this = "ReDoS" }
|
TaintTrackingConfiguration() { this = "ReDoS" }
|
||||||
|
|
||||||
override predicate isSource(DataFlow::Node source) { source instanceof Source }
|
override predicate isSource(DataFlow::Node source) { source instanceof Source }
|
||||||
@@ -37,6 +39,22 @@ class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
|||||||
override predicate isSanitizer(DataFlow::Node node) { node instanceof Sanitizer }
|
override predicate isSanitizer(DataFlow::Node node) { node instanceof Sanitizer }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A taint-tracking configuration for untrusted user input used in dangerous regular expression operations.
|
||||||
|
*/
|
||||||
|
private module ReDoSConfig implements DataFlow::ConfigSig {
|
||||||
|
predicate isSource(DataFlow::Node source) { source instanceof Source }
|
||||||
|
|
||||||
|
predicate isSink(DataFlow::Node sink) { sink instanceof Sink }
|
||||||
|
|
||||||
|
predicate isBarrier(DataFlow::Node node) { node instanceof Sanitizer }
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A taint-tracking module for untrusted user input used in dangerous regular expression operations.
|
||||||
|
*/
|
||||||
|
module ReDoS = TaintTracking::Global<ReDoSConfig>;
|
||||||
|
|
||||||
/** A source of remote user input. */
|
/** A source of remote user input. */
|
||||||
class RemoteSource extends Source instanceof RemoteFlowSource { }
|
class RemoteSource extends Source instanceof RemoteFlowSource { }
|
||||||
|
|
||||||
|
|||||||
@@ -24,9 +24,11 @@ abstract class Sink extends DataFlow::ExprNode { }
|
|||||||
abstract class Sanitizer extends DataFlow::ExprNode { }
|
abstract class Sanitizer extends DataFlow::ExprNode { }
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* DEPRECATED: Use `RegexInjection` instead.
|
||||||
|
*
|
||||||
* A taint-tracking configuration for untrusted user input used to construct regular expressions.
|
* A taint-tracking configuration for untrusted user input used to construct regular expressions.
|
||||||
*/
|
*/
|
||||||
class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
deprecated class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
||||||
TaintTrackingConfiguration() { this = "RegexInjection" }
|
TaintTrackingConfiguration() { this = "RegexInjection" }
|
||||||
|
|
||||||
override predicate isSource(DataFlow::Node source) { source instanceof Source }
|
override predicate isSource(DataFlow::Node source) { source instanceof Source }
|
||||||
@@ -36,6 +38,22 @@ class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
|||||||
override predicate isSanitizer(DataFlow::Node node) { node instanceof Sanitizer }
|
override predicate isSanitizer(DataFlow::Node node) { node instanceof Sanitizer }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A taint-tracking configuration for untrusted user input used to construct regular expressions.
|
||||||
|
*/
|
||||||
|
private module RegexInjectionConfig implements DataFlow::ConfigSig {
|
||||||
|
predicate isSource(DataFlow::Node source) { source instanceof Source }
|
||||||
|
|
||||||
|
predicate isSink(DataFlow::Node sink) { sink instanceof Sink }
|
||||||
|
|
||||||
|
predicate isBarrier(DataFlow::Node node) { node instanceof Sanitizer }
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A taint-tracking module for untrusted user input used to construct regular expressions.
|
||||||
|
*/
|
||||||
|
module RegexInjection = TaintTracking::Global<RegexInjectionConfig>;
|
||||||
|
|
||||||
/** A source of remote user input. */
|
/** A source of remote user input. */
|
||||||
class RemoteSource extends Source instanceof RemoteFlowSource { }
|
class RemoteSource extends Source instanceof RemoteFlowSource { }
|
||||||
|
|
||||||
|
|||||||
@@ -24,9 +24,11 @@ abstract class Sink extends DataFlow::ExprNode { }
|
|||||||
abstract class Sanitizer extends DataFlow::ExprNode { }
|
abstract class Sanitizer extends DataFlow::ExprNode { }
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* DEPRECATED: Use `ResourceInjection` instead.
|
||||||
|
*
|
||||||
* A taint-tracking configuration for untrusted user input used in resource descriptors.
|
* A taint-tracking configuration for untrusted user input used in resource descriptors.
|
||||||
*/
|
*/
|
||||||
class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
deprecated class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
||||||
TaintTrackingConfiguration() { this = "ResourceInjection" }
|
TaintTrackingConfiguration() { this = "ResourceInjection" }
|
||||||
|
|
||||||
override predicate isSource(DataFlow::Node source) { source instanceof Source }
|
override predicate isSource(DataFlow::Node source) { source instanceof Source }
|
||||||
@@ -36,6 +38,22 @@ class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
|||||||
override predicate isSanitizer(DataFlow::Node node) { node instanceof Sanitizer }
|
override predicate isSanitizer(DataFlow::Node node) { node instanceof Sanitizer }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A taint-tracking configuration for untrusted user input used in resource descriptors.
|
||||||
|
*/
|
||||||
|
private module ResourceInjectionConfig implements DataFlow::ConfigSig {
|
||||||
|
predicate isSource(DataFlow::Node source) { source instanceof Source }
|
||||||
|
|
||||||
|
predicate isSink(DataFlow::Node sink) { sink instanceof Sink }
|
||||||
|
|
||||||
|
predicate isBarrier(DataFlow::Node node) { node instanceof Sanitizer }
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A taint-tracking module for untrusted user input used in resource descriptors.
|
||||||
|
*/
|
||||||
|
module ResourceInjection = TaintTracking::Global<ResourceInjectionConfig>;
|
||||||
|
|
||||||
/** A source of remote user input. */
|
/** A source of remote user input. */
|
||||||
class RemoteSource extends Source instanceof RemoteFlowSource { }
|
class RemoteSource extends Source instanceof RemoteFlowSource { }
|
||||||
|
|
||||||
|
|||||||
@@ -25,9 +25,11 @@ abstract class Sink extends DataFlow::ExprNode { }
|
|||||||
abstract class Sanitizer extends DataFlow::ExprNode { }
|
abstract class Sanitizer extends DataFlow::ExprNode { }
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* DEPRECATED: Use `SqlInjection` instead.
|
||||||
|
*
|
||||||
* A taint-tracking configuration for SQL injection vulnerabilities.
|
* A taint-tracking configuration for SQL injection vulnerabilities.
|
||||||
*/
|
*/
|
||||||
class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
deprecated class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
||||||
TaintTrackingConfiguration() { this = "SqlInjection" }
|
TaintTrackingConfiguration() { this = "SqlInjection" }
|
||||||
|
|
||||||
override predicate isSource(DataFlow::Node source) { source instanceof Source }
|
override predicate isSource(DataFlow::Node source) { source instanceof Source }
|
||||||
@@ -37,6 +39,32 @@ class TaintTrackingConfiguration extends TaintTracking::Configuration {
|
|||||||
override predicate isSanitizer(DataFlow::Node node) { node instanceof Sanitizer }
|
override predicate isSanitizer(DataFlow::Node node) { node instanceof Sanitizer }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A taint-tracking configuration for SQL injection vulnerabilities.
|
||||||
|
*/
|
||||||
|
module SqlInjectionConfig implements DataFlow::ConfigSig {
|
||||||
|
/**
|
||||||
|
* Holds if `source` is a relevant data flow source.
|
||||||
|
*/
|
||||||
|
predicate isSource(DataFlow::Node source) { source instanceof Source }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Holds if `sink` is a relevant data flow sink.
|
||||||
|
*/
|
||||||
|
predicate isSink(DataFlow::Node sink) { sink instanceof Sink }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Holds if data flow through `node` is prohibited. This completely removes
|
||||||
|
* `node` from the data flow graph.
|
||||||
|
*/
|
||||||
|
predicate isBarrier(DataFlow::Node node) { node instanceof Sanitizer }
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A taint-tracking module for SQL injection vulnerabilities.
|
||||||
|
*/
|
||||||
|
module SqlInjection = TaintTracking::Global<SqlInjectionConfig>;
|
||||||
|
|
||||||
/** A source of remote user input. */
|
/** A source of remote user input. */
|
||||||
class RemoteSource extends Source instanceof RemoteFlowSource { }
|
class RemoteSource extends Source instanceof RemoteFlowSource { }
|
||||||
|
|
||||||
|
|||||||
@@ -12,13 +12,13 @@
|
|||||||
import csharp
|
import csharp
|
||||||
import semmle.code.csharp.commons.QualifiedName
|
import semmle.code.csharp.commons.QualifiedName
|
||||||
import semmle.code.csharp.security.dataflow.ExternalAPIsQuery
|
import semmle.code.csharp.security.dataflow.ExternalAPIsQuery
|
||||||
import DataFlow::PathGraph
|
import RemoteSourceToExternalApi::PathGraph
|
||||||
|
|
||||||
from
|
from
|
||||||
UntrustedDataToExternalApiConfig config, DataFlow::PathNode source, DataFlow::PathNode sink,
|
RemoteSourceToExternalApi::PathNode source, RemoteSourceToExternalApi::PathNode sink,
|
||||||
string qualifier, string name
|
string qualifier, string name
|
||||||
where
|
where
|
||||||
config.hasFlowPath(source, sink) and
|
RemoteSourceToExternalApi::flowPath(source, sink) and
|
||||||
sink.getNode().(ExternalApiDataNode).hasQualifiedName(qualifier, name)
|
sink.getNode().(ExternalApiDataNode).hasQualifiedName(qualifier, name)
|
||||||
select sink, source, sink,
|
select sink, source, sink,
|
||||||
"Call to " + getQualifiedName(qualifier, name) + " with untrusted data from $@.", source,
|
"Call to " + getQualifiedName(qualifier, name) + " with untrusted data from $@.", source,
|
||||||
|
|||||||
@@ -12,15 +12,21 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
import csharp
|
import csharp
|
||||||
import semmle.code.csharp.security.dataflow.SqlInjectionQuery as SqlInjection
|
import semmle.code.csharp.security.dataflow.SqlInjectionQuery
|
||||||
import semmle.code.csharp.security.dataflow.flowsources.Stored
|
import semmle.code.csharp.security.dataflow.flowsources.Stored
|
||||||
import semmle.code.csharp.dataflow.DataFlow::DataFlow::PathGraph
|
import StoredSqlInjection::PathGraph
|
||||||
|
|
||||||
class StoredTaintTrackingConfiguration extends SqlInjection::TaintTrackingConfiguration {
|
module StoredSqlInjectionConfig implements DataFlow::ConfigSig {
|
||||||
override predicate isSource(DataFlow::Node source) { source instanceof StoredFlowSource }
|
predicate isSource(DataFlow::Node source) { source instanceof StoredFlowSource }
|
||||||
|
|
||||||
|
predicate isSink = SqlInjectionConfig::isSink/1;
|
||||||
|
|
||||||
|
predicate isBarrier = SqlInjectionConfig::isBarrier/1;
|
||||||
}
|
}
|
||||||
|
|
||||||
from StoredTaintTrackingConfiguration c, DataFlow::PathNode source, DataFlow::PathNode sink
|
module StoredSqlInjection = TaintTracking::Global<StoredSqlInjectionConfig>;
|
||||||
where c.hasFlowPath(source, sink)
|
|
||||||
|
from StoredSqlInjection::PathNode source, StoredSqlInjection::PathNode sink
|
||||||
|
where StoredSqlInjection::flowPath(source, sink)
|
||||||
select sink.getNode(), source, sink, "This SQL query depends on a $@.", source.getNode(),
|
select sink.getNode(), source, sink, "This SQL query depends on a $@.", source.getNode(),
|
||||||
"stored user-provided value"
|
"stored user-provided value"
|
||||||
|
|||||||
@@ -13,7 +13,7 @@
|
|||||||
|
|
||||||
import csharp
|
import csharp
|
||||||
import semmle.code.csharp.security.dataflow.SqlInjectionQuery
|
import semmle.code.csharp.security.dataflow.SqlInjectionQuery
|
||||||
import semmle.code.csharp.dataflow.DataFlow::DataFlow::PathGraph
|
import SqlInjection::PathGraph
|
||||||
import semmle.code.csharp.security.dataflow.flowsources.Remote
|
import semmle.code.csharp.security.dataflow.flowsources.Remote
|
||||||
import semmle.code.csharp.security.dataflow.flowsources.Local
|
import semmle.code.csharp.security.dataflow.flowsources.Local
|
||||||
|
|
||||||
@@ -23,7 +23,7 @@ string getSourceType(DataFlow::Node node) {
|
|||||||
result = node.(LocalFlowSource).getSourceType()
|
result = node.(LocalFlowSource).getSourceType()
|
||||||
}
|
}
|
||||||
|
|
||||||
from TaintTrackingConfiguration c, DataFlow::PathNode source, DataFlow::PathNode sink
|
from SqlInjection::PathNode source, SqlInjection::PathNode sink
|
||||||
where c.hasFlowPath(source, sink)
|
where SqlInjection::flowPath(source, sink)
|
||||||
select sink.getNode(), source, sink, "This query depends on $@.", source,
|
select sink.getNode(), source, sink, "This query depends on $@.", source,
|
||||||
("this " + getSourceType(source.getNode()))
|
("this " + getSourceType(source.getNode()))
|
||||||
|
|||||||
@@ -13,9 +13,9 @@
|
|||||||
|
|
||||||
import csharp
|
import csharp
|
||||||
import semmle.code.csharp.security.dataflow.LDAPInjectionQuery
|
import semmle.code.csharp.security.dataflow.LDAPInjectionQuery
|
||||||
import semmle.code.csharp.dataflow.DataFlow::DataFlow::PathGraph
|
import LdapInjection::PathGraph
|
||||||
|
|
||||||
from TaintTrackingConfiguration c, DataFlow::PathNode source, DataFlow::PathNode sink
|
from LdapInjection::PathNode source, LdapInjection::PathNode sink
|
||||||
where c.hasFlowPath(source, sink)
|
where LdapInjection::flowPath(source, sink)
|
||||||
select sink.getNode(), source, sink, "This LDAP query depends on a $@.", source.getNode(),
|
select sink.getNode(), source, sink, "This LDAP query depends on a $@.", source.getNode(),
|
||||||
"user-provided value"
|
"user-provided value"
|
||||||
|
|||||||
@@ -14,13 +14,19 @@
|
|||||||
import csharp
|
import csharp
|
||||||
import semmle.code.csharp.security.dataflow.LDAPInjectionQuery
|
import semmle.code.csharp.security.dataflow.LDAPInjectionQuery
|
||||||
import semmle.code.csharp.security.dataflow.flowsources.Stored
|
import semmle.code.csharp.security.dataflow.flowsources.Stored
|
||||||
import semmle.code.csharp.dataflow.DataFlow::DataFlow::PathGraph
|
import StoredLdapInjection::PathGraph
|
||||||
|
|
||||||
class StoredTaintTrackingConfiguration extends TaintTrackingConfiguration {
|
module StoredLdapInjectionConfig implements DataFlow::ConfigSig {
|
||||||
override predicate isSource(DataFlow::Node source) { source instanceof StoredFlowSource }
|
predicate isSource(DataFlow::Node source) { source instanceof StoredFlowSource }
|
||||||
|
|
||||||
|
predicate isSink = LdapInjectionConfig::isSink/1;
|
||||||
|
|
||||||
|
predicate isBarrier = LdapInjectionConfig::isBarrier/1;
|
||||||
}
|
}
|
||||||
|
|
||||||
from StoredTaintTrackingConfiguration c, DataFlow::PathNode source, DataFlow::PathNode sink
|
module StoredLdapInjection = TaintTracking::Global<StoredLdapInjectionConfig>;
|
||||||
where c.hasFlowPath(source, sink)
|
|
||||||
|
from StoredLdapInjection::PathNode source, StoredLdapInjection::PathNode sink
|
||||||
|
where StoredLdapInjection::flowPath(source, sink)
|
||||||
select sink.getNode(), source, sink, "This LDAP query depends on a $@.", source.getNode(),
|
select sink.getNode(), source, sink, "This LDAP query depends on a $@.", source.getNode(),
|
||||||
"stored (potentially user-provided) value"
|
"stored (potentially user-provided) value"
|
||||||
|
|||||||
@@ -13,9 +13,9 @@
|
|||||||
|
|
||||||
import csharp
|
import csharp
|
||||||
import semmle.code.csharp.security.dataflow.ResourceInjectionQuery
|
import semmle.code.csharp.security.dataflow.ResourceInjectionQuery
|
||||||
import semmle.code.csharp.dataflow.DataFlow::DataFlow::PathGraph
|
import ResourceInjection::PathGraph
|
||||||
|
|
||||||
from TaintTrackingConfiguration c, DataFlow::PathNode source, DataFlow::PathNode sink
|
from ResourceInjection::PathNode source, ResourceInjection::PathNode sink
|
||||||
where c.hasFlowPath(source, sink)
|
where ResourceInjection::flowPath(source, sink)
|
||||||
select sink.getNode(), source, sink, "This resource descriptor depends on a $@.", source.getNode(),
|
select sink.getNode(), source, sink, "This resource descriptor depends on a $@.", source.getNode(),
|
||||||
"user-provided value"
|
"user-provided value"
|
||||||
|
|||||||
@@ -13,10 +13,10 @@
|
|||||||
|
|
||||||
import csharp
|
import csharp
|
||||||
import semmle.code.csharp.security.dataflow.MissingXMLValidationQuery
|
import semmle.code.csharp.security.dataflow.MissingXMLValidationQuery
|
||||||
import semmle.code.csharp.dataflow.DataFlow::DataFlow::PathGraph
|
import MissingXmlValidation::PathGraph
|
||||||
|
|
||||||
from TaintTrackingConfiguration c, DataFlow::PathNode source, DataFlow::PathNode sink
|
from MissingXmlValidation::PathNode source, MissingXmlValidation::PathNode sink
|
||||||
where c.hasFlowPath(source, sink)
|
where MissingXmlValidation::flowPath(source, sink)
|
||||||
select sink.getNode(), source, sink,
|
select sink.getNode(), source, sink,
|
||||||
"This XML processing depends on a $@ without validation because " +
|
"This XML processing depends on a $@ without validation because " +
|
||||||
sink.getNode().(Sink).getReason(), source.getNode(), "user-provided value"
|
sink.getNode().(Sink).getReason(), source.getNode(), "user-provided value"
|
||||||
|
|||||||
@@ -13,9 +13,9 @@
|
|||||||
|
|
||||||
import csharp
|
import csharp
|
||||||
import semmle.code.csharp.security.dataflow.LogForgingQuery
|
import semmle.code.csharp.security.dataflow.LogForgingQuery
|
||||||
import semmle.code.csharp.dataflow.DataFlow::DataFlow::PathGraph
|
import LogForging::PathGraph
|
||||||
|
|
||||||
from TaintTrackingConfiguration c, DataFlow::PathNode source, DataFlow::PathNode sink
|
from LogForging::PathNode source, LogForging::PathNode sink
|
||||||
where c.hasFlowPath(source, sink)
|
where LogForging::flowPath(source, sink)
|
||||||
select sink.getNode(), source, sink, "This log entry depends on a $@.", source.getNode(),
|
select sink.getNode(), source, sink, "This log entry depends on a $@.", source.getNode(),
|
||||||
"user-provided value"
|
"user-provided value"
|
||||||
|
|||||||
@@ -16,11 +16,11 @@
|
|||||||
import csharp
|
import csharp
|
||||||
import semmle.code.csharp.security.dataflow.ReDoSQuery
|
import semmle.code.csharp.security.dataflow.ReDoSQuery
|
||||||
import semmle.code.csharp.frameworks.system.text.RegularExpressions
|
import semmle.code.csharp.frameworks.system.text.RegularExpressions
|
||||||
import semmle.code.csharp.dataflow.DataFlow::DataFlow::PathGraph
|
import ReDoS::PathGraph
|
||||||
|
|
||||||
from TaintTrackingConfiguration c, DataFlow::PathNode source, DataFlow::PathNode sink
|
from ReDoS::PathNode source, ReDoS::PathNode sink
|
||||||
where
|
where
|
||||||
c.hasFlowPath(source, sink) and
|
ReDoS::flowPath(source, sink) and
|
||||||
// No global timeout set
|
// No global timeout set
|
||||||
not exists(RegexGlobalTimeout r) and
|
not exists(RegexGlobalTimeout r) and
|
||||||
(
|
(
|
||||||
|
|||||||
@@ -16,11 +16,11 @@
|
|||||||
import csharp
|
import csharp
|
||||||
import semmle.code.csharp.security.dataflow.RegexInjectionQuery
|
import semmle.code.csharp.security.dataflow.RegexInjectionQuery
|
||||||
import semmle.code.csharp.frameworks.system.text.RegularExpressions
|
import semmle.code.csharp.frameworks.system.text.RegularExpressions
|
||||||
import semmle.code.csharp.dataflow.DataFlow::DataFlow::PathGraph
|
import RegexInjection::PathGraph
|
||||||
|
|
||||||
from TaintTrackingConfiguration c, DataFlow::PathNode source, DataFlow::PathNode sink
|
from RegexInjection::PathNode source, RegexInjection::PathNode sink
|
||||||
where
|
where
|
||||||
c.hasFlowPath(source, sink) and
|
RegexInjection::flowPath(source, sink) and
|
||||||
// No global timeout set
|
// No global timeout set
|
||||||
not exists(RegexGlobalTimeout r)
|
not exists(RegexGlobalTimeout r)
|
||||||
select sink.getNode(), source, sink, "This regular expression is constructed from a $@.",
|
select sink.getNode(), source, sink, "This regular expression is constructed from a $@.",
|
||||||
|
|||||||
@@ -15,7 +15,7 @@
|
|||||||
import csharp
|
import csharp
|
||||||
import semmle.code.csharp.frameworks.system.Data
|
import semmle.code.csharp.frameworks.system.Data
|
||||||
import semmle.code.csharp.security.dataflow.HardcodedCredentialsQuery
|
import semmle.code.csharp.security.dataflow.HardcodedCredentialsQuery
|
||||||
import semmle.code.csharp.dataflow.DataFlow::DataFlow::PathGraph
|
import ConnectionString::PathGraph
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A string literal containing a username or password field.
|
* A string literal containing a username or password field.
|
||||||
@@ -29,24 +29,24 @@ class ConnectionStringPasswordOrUsername extends NonEmptyStringLiteral {
|
|||||||
/**
|
/**
|
||||||
* A taint-tracking configuration for tracking string literals to a `ConnectionString` property.
|
* A taint-tracking configuration for tracking string literals to a `ConnectionString` property.
|
||||||
*/
|
*/
|
||||||
class ConnectionStringTaintTrackingConfiguration extends TaintTracking::Configuration {
|
module ConnectionStringConfig implements DataFlow::ConfigSig {
|
||||||
ConnectionStringTaintTrackingConfiguration() { this = "connectionstring" }
|
predicate isSource(DataFlow::Node source) { source instanceof ConnectionStringPasswordOrUsername }
|
||||||
|
|
||||||
override predicate isSource(DataFlow::Node source) {
|
predicate isSink(DataFlow::Node sink) {
|
||||||
source instanceof ConnectionStringPasswordOrUsername
|
|
||||||
}
|
|
||||||
|
|
||||||
override predicate isSink(DataFlow::Node sink) {
|
|
||||||
sink.asExpr() =
|
sink.asExpr() =
|
||||||
any(SystemDataConnectionClass connection).getConnectionStringProperty().getAnAssignedValue()
|
any(SystemDataConnectionClass connection).getConnectionStringProperty().getAnAssignedValue()
|
||||||
}
|
}
|
||||||
|
|
||||||
override predicate isSanitizer(DataFlow::Node node) { node instanceof StringFormatSanitizer }
|
predicate isBarrier(DataFlow::Node node) { node instanceof StringFormatSanitizer }
|
||||||
}
|
}
|
||||||
|
|
||||||
from
|
/**
|
||||||
ConnectionStringTaintTrackingConfiguration c, DataFlow::PathNode source, DataFlow::PathNode sink
|
* A taint-tracking module for tracking string literals to a `ConnectionString` property.
|
||||||
where c.hasFlowPath(source, sink)
|
*/
|
||||||
|
module ConnectionString = TaintTracking::Global<ConnectionStringConfig>;
|
||||||
|
|
||||||
|
from ConnectionString::PathNode source, ConnectionString::PathNode sink
|
||||||
|
where ConnectionString::flowPath(source, sink)
|
||||||
select source.getNode(), source, sink,
|
select source.getNode(), source, sink,
|
||||||
"'ConnectionString' property includes hard-coded credentials set in $@.",
|
"'ConnectionString' property includes hard-coded credentials set in $@.",
|
||||||
any(Call call | call.getAnArgument() = sink.getNode().asExpr()) as call, call.toString()
|
any(Call call | call.getAnArgument() = sink.getNode().asExpr()) as call, call.toString()
|
||||||
|
|||||||
@@ -14,15 +14,15 @@
|
|||||||
|
|
||||||
import csharp
|
import csharp
|
||||||
import semmle.code.csharp.security.dataflow.HardcodedCredentialsQuery
|
import semmle.code.csharp.security.dataflow.HardcodedCredentialsQuery
|
||||||
import semmle.code.csharp.dataflow.DataFlow::DataFlow::PathGraph
|
import HardcodedCredentials::PathGraph
|
||||||
|
|
||||||
from
|
from
|
||||||
TaintTrackingConfiguration c, Source source, Sink sink, DataFlow::PathNode sourcePath,
|
Source source, Sink sink, HardcodedCredentials::PathNode sourcePath,
|
||||||
DataFlow::PathNode sinkPath, string value
|
HardcodedCredentials::PathNode sinkPath, string value
|
||||||
where
|
where
|
||||||
source = sourcePath.getNode() and
|
source = sourcePath.getNode() and
|
||||||
sink = sinkPath.getNode() and
|
sink = sinkPath.getNode() and
|
||||||
c.hasFlowPath(sourcePath, sinkPath) and
|
HardcodedCredentials::flowPath(sourcePath, sinkPath) and
|
||||||
// Print the source value if it's available
|
// Print the source value if it's available
|
||||||
if exists(source.asExpr().getValue())
|
if exists(source.asExpr().getValue())
|
||||||
then value = "The hard-coded value \"" + source.asExpr().getValue() + "\""
|
then value = "The hard-coded value \"" + source.asExpr().getValue() + "\""
|
||||||
|
|||||||
@@ -1,19 +1,7 @@
|
|||||||
edges
|
edges
|
||||||
| HardcodedCredentials.cs:47:30:47:60 | array creation of type Byte[] : Byte[] | HardcodedCredentials.cs:50:13:50:23 | access to local variable rawCertData |
|
|
||||||
nodes
|
nodes
|
||||||
| HardcodedCredentials.cs:15:25:15:36 | "myPa55word" | semmle.label | "myPa55word" |
|
|
||||||
| HardcodedCredentials.cs:31:19:31:28 | "username" | semmle.label | "username" |
|
|
||||||
| HardcodedCredentials.cs:45:39:45:53 | "myNewPa55word" | semmle.label | "myNewPa55word" |
|
|
||||||
| HardcodedCredentials.cs:47:30:47:60 | array creation of type Byte[] : Byte[] | semmle.label | array creation of type Byte[] : Byte[] |
|
|
||||||
| HardcodedCredentials.cs:50:13:50:23 | access to local variable rawCertData | semmle.label | access to local variable rawCertData |
|
|
||||||
| HardcodedCredentials.cs:51:13:51:24 | "myPa55word" | semmle.label | "myPa55word" |
|
|
||||||
| HardcodedCredentials.cs:54:48:54:63 | "Password=12345" | semmle.label | "Password=12345" |
|
| HardcodedCredentials.cs:54:48:54:63 | "Password=12345" | semmle.label | "Password=12345" |
|
||||||
| HardcodedCredentials.cs:56:49:56:63 | "User Id=12345" | semmle.label | "User Id=12345" |
|
| HardcodedCredentials.cs:56:49:56:63 | "User Id=12345" | semmle.label | "User Id=12345" |
|
||||||
| HardcodedCredentials.cs:74:31:74:42 | "myusername" | semmle.label | "myusername" |
|
|
||||||
| HardcodedCredentials.cs:74:45:74:56 | "mypassword" | semmle.label | "mypassword" |
|
|
||||||
| TestHardcodedCredentials.cs:21:31:21:42 | "myusername" | semmle.label | "myusername" |
|
|
||||||
| TestHardcodedCredentials.cs:21:45:21:56 | "mypassword" | semmle.label | "mypassword" |
|
|
||||||
| TestHardcodedCredentials.cs:26:19:26:28 | "username" | semmle.label | "username" |
|
|
||||||
subpaths
|
subpaths
|
||||||
#select
|
#select
|
||||||
| HardcodedCredentials.cs:54:48:54:63 | "Password=12345" | HardcodedCredentials.cs:54:48:54:63 | "Password=12345" | HardcodedCredentials.cs:54:48:54:63 | "Password=12345" | 'ConnectionString' property includes hard-coded credentials set in $@. | HardcodedCredentials.cs:54:30:54:64 | object creation of type SqlConnection | object creation of type SqlConnection |
|
| HardcodedCredentials.cs:54:48:54:63 | "Password=12345" | HardcodedCredentials.cs:54:48:54:63 | "Password=12345" | HardcodedCredentials.cs:54:48:54:63 | "Password=12345" | 'ConnectionString' property includes hard-coded credentials set in $@. | HardcodedCredentials.cs:54:30:54:64 | object creation of type SqlConnection | object creation of type SqlConnection |
|
||||||
|
|||||||
Reference in New Issue
Block a user