Add CalleeAccessPathSimpleFromArgumentTraversal

This commit is contained in:
Esben Sparre Andreasen
2022-03-29 08:32:23 +02:00
committed by Stephan Brandauer
parent e1a38bd4d6
commit 5204346e1f

View File

@@ -296,7 +296,8 @@ private newtype TEndPointFeature =
TCalleeApiName() or
TCalleeAccessPath() or
TCalleeAccessPathWithStructuralInfo() or
TEnclosingFunctionBody()
TEnclosingFunctionBody() or
TCalleeAccessPathSimpleFromArgumentTraversal()
abstract class EndPointFeature extends TEndPointFeature {
abstract string getEncoding();
@@ -381,3 +382,47 @@ class EnclosingFunctionBody extends EndPointFeature, TEnclosingFunctionBody {
FunctionBodyFeatures::getBodyTokensFeature(FunctionBodyFeatures::getRepresentativeFunctionForEndpoint(endpoint))
}
}
private module SyntacticUtilities {
Expr getANestedProperty(ObjectExpr o) {
exists(Expr init | init = o.getAProperty().getInit().getUnderlyingValue() |
result = [init, getANestedProperty(init)]
)
}
string getSimpleAccessPath(DataFlow::Node node) {
result = node.asExpr().(VarAccess).getName()
or
exists(DataFlow::PropRead p |
p = node and
result = getSimpleAccessPath(p.getBase()) + "." + p.getPropertyName()
)
or
exists(DataFlow::MethodCallNode p |
p = node and
result = getSimpleAccessPath(p.getReceiver()) + "." + p.getMethodName() + "()"
)
or
exists(DataFlow::CallNode p |
p = node and
not p instanceof DataFlow::MethodCallNode and
result = p.getCalleeName() + "()"
)
}
}
class CalleeAccessPathSimpleFromArgumentTraversal extends EndPointFeature,
TCalleeAccessPathSimpleFromArgumentTraversal {
override string getEncoding() { result = "calleeAccessPathSimpleFromArgumentTraversal" }
override string getValue(DataFlow::Node endpoint) {
exists(DataFlow::InvokeNode invk |
result = SyntacticUtilities::getSimpleAccessPath(invk.getCalleeNode()) and
(
invk.getAnArgument() = endpoint or
SyntacticUtilities::getANestedProperty(invk.getAnArgument().asExpr().getUnderlyingValue())
.flow() = endpoint
)
)
}
}