mirror of
https://github.com/github/codeql.git
synced 2026-06-23 21:57:01 +02:00
Preparatory refactor for the shared-CFG dataflow migration. Deprecates the AstNode.getAFlowNode() cached predicate on the public Python QL API and rewrites all ~140 internal callers across lib/, src/, test/, and tools/ from `expr.getAFlowNode() = cfgNode` to `cfgNode.getNode() = expr`, using ControlFlowNode.getNode() which already exists in Flow.qll. The predicate itself is preserved (with a deprecation note pointing at the new pattern) so external users do not experience churn — they can migrate at their own pace and the AST/CFG hierarchies still get the intended untangling once the deprecation eventually elapses. Semantic noop verified by: - All 361 lib/ + src/ queries compile clean. - All 122 ControlFlow + PointsTo library-tests pass. - All 64 dataflow library-tests pass. - All 113 Variables/Exceptions/Expressions/Statements/Functions/Imports/ Security/CWE-798/ModificationOfParameterWithDefault query-tests pass. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
95 lines
2.9 KiB
Plaintext
95 lines
2.9 KiB
Plaintext
/**
|
|
* Utilities to support queries about instance attribute accesses of
|
|
* the form `self.attr`.
|
|
*/
|
|
|
|
import python
|
|
private import semmle.python.pointsto.Filters
|
|
private import LegacyPointsTo
|
|
|
|
/**
|
|
* An attribute access where the left hand side of the attribute expression
|
|
* is `self`.
|
|
*/
|
|
class SelfAttribute extends Attribute {
|
|
SelfAttribute() { self_attribute(this, _) }
|
|
|
|
Class getClass() { self_attribute(this, result) }
|
|
}
|
|
|
|
/** Whether variable 'self' is the self variable in method 'method' */
|
|
private predicate self_variable(Function method, Variable self) {
|
|
self.isParameter() and
|
|
method.isMethod() and
|
|
method.getArg(0).asName() = self.getAnAccess()
|
|
}
|
|
|
|
/** Whether attribute is an access of the form `self.attr` in the body of the class 'cls' */
|
|
private predicate self_attribute(Attribute attr, Class cls) {
|
|
exists(Function f, Variable self | self_variable(f, self) |
|
|
self.getAnAccess() = attr.getObject() and
|
|
cls = f.getScope+()
|
|
)
|
|
}
|
|
|
|
/** A helper class for UndefinedClassAttribute.ql & MaybeUndefinedClassAttribute.ql */
|
|
class SelfAttributeRead extends SelfAttribute {
|
|
SelfAttributeRead() {
|
|
this.getCtx() instanceof Load and
|
|
// Be stricter for loads.
|
|
// We want to generous as to what is defined (i.e. stores),
|
|
// but strict as to what needs to be defined (i.e. loads).
|
|
exists(ClassObject cls, FunctionObject func | cls.declaredAttribute(_) = func |
|
|
func.getFunction() = this.getScope() and
|
|
cls.getPyClass() = this.getClass()
|
|
)
|
|
}
|
|
|
|
predicate guardedByHasattr() {
|
|
exists(Variable var, ControlFlowNode n, ControlFlowNode this_, ControlFlowNode obj_ |
|
|
this_.getNode() = this and obj_.getNode() = this.getObject()
|
|
|
|
|
var.getAUse() = obj_ and
|
|
hasattr(n, var.getAUse(), this.getName()) and
|
|
n.strictlyDominates(this_)
|
|
)
|
|
}
|
|
|
|
pragma[noinline]
|
|
predicate locallyDefined() {
|
|
exists(SelfAttributeStore store, ControlFlowNode store_, ControlFlowNode this_ |
|
|
store_.getNode() = store and this_.getNode() = this
|
|
|
|
|
this.getName() = store.getName() and
|
|
this.getScope() = store.getScope() and
|
|
store_.strictlyDominates(this_)
|
|
)
|
|
}
|
|
}
|
|
|
|
class SelfAttributeStore extends SelfAttribute {
|
|
SelfAttributeStore() { this.getCtx() instanceof Store }
|
|
|
|
Expr getAssignedValue() { exists(Assign a | a.getATarget() = this | result = a.getValue()) }
|
|
}
|
|
|
|
private predicate attr_assigned_in_method_arg_n(FunctionObject method, string name, int n) {
|
|
exists(SsaVariable param |
|
|
method.getFunction().getArg(n).asName() = param.getDefinition().getNode()
|
|
|
|
|
exists(AttrNode attr |
|
|
attr.getObject(name) = param.getAUse() and
|
|
attr.isStore()
|
|
)
|
|
or
|
|
exists(FunctionObject callee, int m |
|
|
callee.getArgumentForCall(_, m) = param.getAUse() and
|
|
attr_assigned_in_method_arg_n(callee, name, m)
|
|
)
|
|
)
|
|
}
|
|
|
|
predicate attribute_assigned_in_method(FunctionObject method, string name) {
|
|
attr_assigned_in_method_arg_n(method, name, 0)
|
|
}
|