Python: Add read step for unpacking assignment

This commit is contained in:
Rasmus Lerchedahl Petersen
2020-11-30 15:30:14 +01:00
parent f345e55951
commit 289b9e62f9
3 changed files with 36 additions and 1 deletions

View File

@@ -976,6 +976,8 @@ predicate kwOverflowStoreStep(CfgNode nodeFrom, DictionaryElementContent c, Node
predicate readStep(Node nodeFrom, Content c, Node nodeTo) {
subscriptReadStep(nodeFrom, c, nodeTo)
or
unpackingAssignmentReadStep(nodeFrom, c, nodeTo)
or
popReadStep(nodeFrom, c, nodeTo)
or
comprehensionReadStep(nodeFrom, c, nodeTo)
@@ -1008,6 +1010,27 @@ predicate subscriptReadStep(CfgNode nodeFrom, Content c, CfgNode nodeTo) {
)
}
/** Data flows from an iterable to an assigned variable. */
predicate unpackingAssignmentReadStep(CfgNode nodeFrom, Content c, EssaNode nodeTo) {
// iterable unpacking
// `a, b = iterable`
// nodeFrom is `iterable`, cfg node
// nodeTo is `a` (or `b`), essa var
// c is compatible with `a`s (or `b`s) index
exists(Assign assign, int index, SequenceNode target |
target.getNode() = assign.getATarget() and
nodeTo.getVar().getDefinition().(MultiAssignmentDefinition).indexOf(index, target) and
nodeFrom.asExpr() = assign.getValue() and
(
c instanceof ListElementContent
or
c instanceof SetElementContent
or
c.(TupleElementContent).getIndex() = index
)
)
}
/** Data flows from a sequence to a call to `pop` on the sequence. */
predicate popReadStep(CfgNode nodeFrom, Content c, CfgNode nodeTo) {
// set.pop or list.pop