Languages: Adapt to api changes.

This commit is contained in:
Anders Schack-Mulligen
2025-08-19 10:34:06 +02:00
parent e53b22dfa7
commit f459ddc40a
34 changed files with 454 additions and 368 deletions

View File

@@ -10,6 +10,7 @@ private import internal.ControlFlowGraphImpl as CfgImpl
private import CfgNodes
private import SuccessorTypes
private import CfgImpl::BasicBlocks as BasicBlocksImpl
private import codeql.controlflow.BasicBlock as BB
/**
* A basic block, that is, a maximal straight-line sequence of control flow nodes
@@ -296,3 +297,21 @@ final class ConditionBlock extends BasicBlock, BasicBlocksImpl::ConditionBasicBl
super.edgeDominates(controlled, s)
}
}
private class BasicBlockAlias = BasicBlock;
private class SuccessorTypeAlias = SuccessorType;
module Cfg implements BB::CfgSig<Location> {
class ControlFlowNode = CfgNode;
class SuccessorType = SuccessorTypeAlias;
class BasicBlock = BasicBlockAlias;
predicate dominatingEdge(BasicBlock bb1, BasicBlock bb2) {
BasicBlocksImpl::dominatingEdge(bb1, bb2)
}
predicate entryBlock(BasicBlock bb) { bb instanceof EntryBasicBlock }
}

View File

@@ -280,6 +280,7 @@ predicate isNonConstantExpr(CfgNodes::ExprCfgNode n) {
/** Provides logic related to captured variables. */
module VariableCapture {
private import codeql.dataflow.VariableCapture as Shared
private import codeql.ruby.controlflow.BasicBlocks as BasicBlocks
private predicate closureFlowStep(CfgNodes::ExprCfgNode e1, CfgNodes::ExprCfgNode e2) {
e1 = getALastEvalNode(e2)
@@ -290,23 +291,14 @@ module VariableCapture {
)
}
private module CaptureInput implements Shared::InputSig<Location> {
private module CaptureInput implements Shared::InputSig<Location, BasicBlocks::Cfg::BasicBlock> {
private import codeql.ruby.controlflow.ControlFlowGraph as Cfg
private import codeql.ruby.controlflow.BasicBlocks as BasicBlocks
private import TaintTrackingPrivate as TaintTrackingPrivate
class BasicBlock extends BasicBlocks::BasicBlock {
Callable getEnclosingCallable() { result = this.getScope() }
BasicBlock getASuccessor() { result = super.getASuccessor() }
BasicBlock getImmediateDominator() { result = super.getImmediateDominator() }
predicate inDominanceFrontier(BasicBlock df) { super.inDominanceFrontier(df) }
Callable basicBlockGetEnclosingCallable(BasicBlocks::Cfg::BasicBlock bb) {
result = bb.getScope()
}
class ControlFlowNode = Cfg::CfgNode;
class CapturedVariable extends LocalVariable {
CapturedVariable() {
this.isCaptured() and
@@ -377,7 +369,7 @@ module VariableCapture {
class ClosureExpr = CaptureInput::ClosureExpr;
module Flow = Shared::Flow<Location, CaptureInput>;
module Flow = Shared::Flow<Location, BasicBlocks::Cfg, CaptureInput>;
private Flow::ClosureNode asClosureNode(Node n) {
result = n.(CaptureNode).getSynthesizedCaptureNode()

View File

@@ -4,18 +4,16 @@ module;
private import codeql.ssa.Ssa as SsaImplCommon
private import codeql.ruby.AST
private import codeql.ruby.CFG as Cfg
private import codeql.ruby.controlflow.BasicBlocks as BasicBlocks
private import codeql.ruby.controlflow.internal.ControlFlowGraphImpl as ControlFlowGraphImpl
private import codeql.ruby.dataflow.SSA
private import codeql.ruby.ast.Variable
private import Cfg::CfgNodes::ExprNodes
module SsaInput implements SsaImplCommon::InputSig<Location> {
private class BasicBlock = BasicBlocks::Cfg::BasicBlock;
module SsaInput implements SsaImplCommon::InputSig<Location, BasicBlock> {
private import codeql.ruby.controlflow.ControlFlowGraph as Cfg
private import codeql.ruby.controlflow.BasicBlocks as BasicBlocks
class BasicBlock = BasicBlocks::BasicBlock;
class ControlFlowNode = Cfg::CfgNode;
class SourceVariable = LocalVariable;
@@ -62,7 +60,7 @@ module SsaInput implements SsaImplCommon::InputSig<Location> {
}
}
import SsaImplCommon::Make<Location, SsaInput> as Impl
import SsaImplCommon::Make<Location, BasicBlocks::Cfg, SsaInput> as Impl
class Definition = Impl::Definition;
@@ -216,15 +214,14 @@ private predicate hasVariableReadWithCapturedWrite(
pragma[noinline]
deprecated private predicate adjacentDefReadExt(
Definition def, SsaInput::BasicBlock bb1, int i1, SsaInput::BasicBlock bb2, int i2,
SsaInput::SourceVariable v
Definition def, BasicBlock bb1, int i1, BasicBlock bb2, int i2, SsaInput::SourceVariable v
) {
Impl::adjacentDefReadExt(def, _, bb1, i1, bb2, i2) and
v = def.getSourceVariable()
}
deprecated private predicate adjacentDefReachesReadExt(
Definition def, SsaInput::BasicBlock bb1, int i1, SsaInput::BasicBlock bb2, int i2
Definition def, BasicBlock bb1, int i1, BasicBlock bb2, int i2
) {
exists(SsaInput::SourceVariable v | adjacentDefReadExt(def, bb1, i1, bb2, i2, v) |
def.definesAt(v, bb1, i1)
@@ -232,7 +229,7 @@ deprecated private predicate adjacentDefReachesReadExt(
SsaInput::variableRead(bb1, i1, v, true)
)
or
exists(SsaInput::BasicBlock bb3, int i3 |
exists(BasicBlock bb3, int i3 |
adjacentDefReachesReadExt(def, bb1, i1, bb3, i3) and
SsaInput::variableRead(bb3, i3, _, false) and
Impl::adjacentDefReadExt(def, _, bb3, i3, bb2, i2)
@@ -240,7 +237,7 @@ deprecated private predicate adjacentDefReachesReadExt(
}
deprecated private predicate adjacentDefReachesUncertainReadExt(
Definition def, SsaInput::BasicBlock bb1, int i1, SsaInput::BasicBlock bb2, int i2
Definition def, BasicBlock bb1, int i1, BasicBlock bb2, int i2
) {
adjacentDefReachesReadExt(def, bb1, i1, bb2, i2) and
SsaInput::variableRead(bb2, i2, _, false)
@@ -248,13 +245,11 @@ deprecated private predicate adjacentDefReachesUncertainReadExt(
/** Same as `lastRefRedef`, but skips uncertain reads. */
pragma[nomagic]
deprecated private predicate lastRefSkipUncertainReadsExt(
Definition def, SsaInput::BasicBlock bb, int i
) {
deprecated private predicate lastRefSkipUncertainReadsExt(Definition def, BasicBlock bb, int i) {
Impl::lastRef(def, bb, i) and
not SsaInput::variableRead(bb, i, def.getSourceVariable(), false)
or
exists(SsaInput::BasicBlock bb0, int i0 |
exists(BasicBlock bb0, int i0 |
Impl::lastRef(def, bb0, i0) and
adjacentDefReachesUncertainReadExt(def, bb, i, bb0, i0)
)
@@ -475,7 +470,7 @@ private module DataFlowIntegrationInput implements Impl::DataFlowIntegrationInpu
private import codeql.util.Boolean
class Expr extends Cfg::CfgNodes::ExprCfgNode {
predicate hasCfgNode(SsaInput::BasicBlock bb, int i) { this = bb.getNode(i) }
predicate hasCfgNode(BasicBlock bb, int i) { this = bb.getNode(i) }
}
Expr getARead(Definition def) { result = Cached::getARead(def) }
@@ -491,9 +486,7 @@ private module DataFlowIntegrationInput implements Impl::DataFlowIntegrationInpu
* Holds if the evaluation of this guard to `branch` corresponds to the edge
* from `bb1` to `bb2`.
*/
predicate hasValueBranchEdge(
SsaInput::BasicBlock bb1, SsaInput::BasicBlock bb2, GuardValue branch
) {
predicate hasValueBranchEdge(BasicBlock bb1, BasicBlock bb2, GuardValue branch) {
exists(Cfg::SuccessorTypes::ConditionalSuccessor s |
this.getBasicBlock() = bb1 and
bb2 = bb1.getASuccessor(s) and
@@ -506,15 +499,13 @@ private module DataFlowIntegrationInput implements Impl::DataFlowIntegrationInpu
* branch edge from `bb1` to `bb2`. That is, following the edge from
* `bb1` to `bb2` implies that this guard evaluated to `branch`.
*/
predicate valueControlsBranchEdge(
SsaInput::BasicBlock bb1, SsaInput::BasicBlock bb2, GuardValue branch
) {
predicate valueControlsBranchEdge(BasicBlock bb1, BasicBlock bb2, GuardValue branch) {
this.hasValueBranchEdge(bb1, bb2, branch)
}
}
/** Holds if the guard `guard` controls block `bb` upon evaluating to `branch`. */
predicate guardDirectlyControlsBlock(Guard guard, SsaInput::BasicBlock bb, GuardValue branch) {
predicate guardDirectlyControlsBlock(Guard guard, BasicBlock bb, GuardValue branch) {
Guards::guardControlsBlock(guard, bb, branch)
}
}