Merge branch 'master' of https://github.com/github/codeql into pr/erik-krogh/3566

This commit is contained in:
Erik Krogh Kristensen
2020-05-27 12:21:14 +00:00
9 changed files with 292 additions and 0 deletions

View File

@@ -48,6 +48,11 @@ private class DefaultHtmlSanitizerCall extends HtmlSanitizerCall {
or
callee = LodashUnderscore::member("escape")
or
exists(DataFlow::PropRead read | read = callee |
read.getPropertyName() = "sanitize" and
read.getBase().asExpr().(VarAccess).getName() = "DOMPurify"
)
or
exists(string name | name = "encode" or name = "encodeNonUTF" |
callee =
DataFlow::moduleMember("html-entities", _).getAnInstantiation().getAPropertyRead(name) or

View File

@@ -827,6 +827,28 @@ module TaintTracking {
override predicate appliesTo(Configuration cfg) { any() }
}
/**
* A test of form `x.length === "0"`, preventing `x` from being tainted.
*/
class IsEmptyGuard extends AdditionalSanitizerGuardNode, DataFlow::ValueNode {
override EqualityTest astNode;
boolean polarity;
Expr operand;
IsEmptyGuard() {
astNode.getPolarity() = polarity and
astNode.getAnOperand().(ConstantExpr).getIntValue() = 0 and
exists(DataFlow::PropRead read | read.asExpr() = astNode.getAnOperand() |
read.getBase().asExpr() = operand and
read.getPropertyName() = "length"
)
}
override predicate sanitizes(boolean outcome, Expr e) { polarity = outcome and e = operand }
override predicate appliesTo(Configuration cfg) { any() }
}
/** DEPRECATED. This class has been renamed to `InclusionSanitizer`. */
deprecated class StringInclusionSanitizer = InclusionSanitizer;

View File

@@ -51,6 +51,10 @@ module DomBasedXss {
prop = urlSuffixPseudoProperty()
)
}
override predicate isSanitizerEdge(DataFlow::Node pred, DataFlow::Node succ) {
DomBasedXss::isOptionallySanitizedEdge(pred, succ)
}
}
private string urlSuffixPseudoProperty() { result = "$UrlSuffix$" }

View File

@@ -329,6 +329,36 @@ module DomBasedXss {
private class UriEncodingSanitizer extends Sanitizer, Shared::UriEncodingSanitizer { }
private class QuoteGuard extends SanitizerGuard, Shared::QuoteGuard { }
/**
* Holds if there exists two dataflow edges to `succ`, where one edges is sanitized, and the other edge starts with `pred`.
*/
predicate isOptionallySanitizedEdge(DataFlow::Node pred, DataFlow::Node succ) {
exists(HtmlSanitizerCall sanitizer |
// sanitized = sanitize ? sanitizer(source) : source;
exists(ConditionalExpr branch, Variable var, VarAccess access |
branch = succ.asExpr() and access = var.getAnAccess()
|
branch.getABranch() = access and
pred.getEnclosingExpr() = access and
sanitizer = branch.getABranch().flow() and
sanitizer.getAnArgument().getEnclosingExpr() = var.getAnAccess()
)
or
// sanitized = source; if (sanitize) {sanitized = sanitizer(source)};
exists(SsaPhiNode phi, SsaExplicitDefinition a, SsaDefinition b |
a = phi.getAnInput().getDefinition() and
b = phi.getAnInput().getDefinition() and
count(phi.getAnInput()) = 2 and
not a = b and
sanitizer = DataFlow::valueNode(a.getDef().getSource()) and
sanitizer.getAnArgument().asExpr().(VarAccess).getVariable() = b.getSourceVariable()
|
pred = DataFlow::ssaDefinitionNode(b) and
succ = DataFlow::ssaDefinitionNode(phi)
)
)
}
}
/** Provides classes and predicates for the reflected XSS query. */

View File

@@ -34,6 +34,10 @@ module XssThroughDom {
guard instanceof UnsafeJQuery::PropertyPresenceSanitizer or
guard instanceof DomBasedXss::SanitizerGuard
}
override predicate isSanitizerEdge(DataFlow::Node pred, DataFlow::Node succ) {
DomBasedXss::isOptionallySanitizedEdge(pred, succ)
}
}
/**