You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Python: remove getAFlowNode() — bridge AST→CFG only via CFG-side getNode()
Option 2: eliminates the AST→CFG bridge from the AST layer. Previously
'AstNode.getAFlowNode()' returned a 'ControlFlowNode' from the legacy
'Flow.qll' CFG via 'py_flow_bb_node' — this hardcoded the AST to know
about the legacy CFG, preventing files from cleanly switching to the
new shared CFG.
Removes:
* 'AstNode.getAFlowNode()' from 'AstExtended.qll'
* Type-narrowing overrides on 'Attribute' / 'Subscript' / 'Call' /
'IfExp' / 'Name' / 'NameConstant' / 'ImportMember' (in Exprs.qll
and Import.qll)
Rewrites ~130 call sites across 'python/ql/lib/' and 'python/ql/src/'
to bridge from the CFG side instead:
Before: node = expr.getAFlowNode()
After: node.getNode() = expr
Before: expr.getAFlowNode().(DefinitionNode).getValue()
After: exists(DefinitionNode d | d.getNode() = expr | d.getValue())
Before: cn.operands(const.getAFlowNode(), op, x)
After: exists(ControlFlowNode c | c.getNode() = const | cn.operands(c, op, x))
This is semantically a no-op — both forms are duals of the same predicate.
Verified by passing all library tests:
* 64 dataflow tests
* 28 ControlFlow + dataflow-new-ssa tests
* 1 essa SSA-compute test
* 93 tests total in the focused suite
Once committed, files that want to switch from the legacy 'Flow' CFG
to the new 'Cfg' facade only need to change their imports — the
bridge sites are CFG-side and respect whichever ControlFlowNode is in
scope.
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
0 commit comments