Skip to content

Commit b7d1941

Browse files
committed
temp3
1 parent 76ed5f3 commit b7d1941

File tree

4 files changed

+54
-89
lines changed

4 files changed

+54
-89
lines changed

ruby/ql/lib/codeql/ruby/dataflow/internal/CapturedVariableFlow.qll

Lines changed: 18 additions & 70 deletions
Original file line numberDiff line numberDiff line change
@@ -78,72 +78,21 @@ private import Cfg::CfgNodes::ExprNodes
7878
private import DataFlowPrivate as DataFlowPrivate
7979
private import codeql.util.Unit
8080

81-
private class CapturedVariableAccess extends LocalVariableAccess {
82-
CapturedVariableAccess() { this.isCapturedAccess() }
83-
}
84-
8581
/** A variable that is captured. */
8682
class CapturedVariable extends LocalVariable {
8783
CapturedVariable() { this.isCaptured() }
8884
}
8985

90-
/** A callable that captures a local variable. */
91-
class CapturingCallable extends Callable {
92-
CapturingCallable() { any(CapturedVariableAccess access).getCfgScope() = this }
93-
94-
/** Gets a local variable captured by this callable. */
95-
CapturedVariable getACapturedVariable() { result.getAnAccess().getCfgScope() = this }
96-
}
97-
98-
// private predicate entryWrite(Cfg::EntryBasicBlock bb, int i, CapturingCallable c) {
99-
// i = -1 and
100-
// (
101-
// bb.getScope() = c
102-
// or
103-
// bb.getScope() = c.getACapturedVariable().getDeclaringScope()
104-
// )
105-
// }
106-
// private predicate entryWrite(Cfg::EntryBasicBlock bb, CapturingCallable c) {
107-
// bb.getScope() instanceof CapturingCallable
108-
// or
109-
// or
110-
// bb.getScope() = c.getACapturedVariable().getDeclaringScope()
111-
// )
112-
// }
113-
private predicate captureRead1(
114-
Cfg::BasicBlock bb, int i, CapturedVariable var, VariableAccessCfgNode access, CapturingCallable c
115-
) {
116-
bb.getNode(i) = access and
117-
access.getNode() = var.getAnAccess() and
118-
var = c.getACapturedVariable() and
119-
(bb.getScope() = c or bb.getScope() = var.getDefiningAccess().getCfgScope())
120-
}
121-
122-
private predicate captureRead2(Cfg::BasicBlock bb, int i, Callable c) {
123-
bb.getNode(i).getNode() = c
124-
}
125-
126-
private predicate captureRead3(Cfg::BasicBlock bb, int i) {
127-
// todo: BlockParameterNode
128-
// DataFlowPrivate::lambdaCall(_, bb.getNode(i)) and
129-
// (
130-
// bb.getScope() = c
131-
// or
132-
// bb.getScope() = c.getACapturedVariable().getDeclaringScope()
133-
// )
134-
bb.getNode(i) instanceof DataFlowPrivate::Argument
135-
or
136-
DataFlowPrivate::isBlockArgument(_, bb.getNode(i))
137-
}
138-
13986
cached
14087
private newtype TCaptureAccess =
14188
TEntryDef(Cfg::EntryBasicBlock bb) or
142-
TVariableAccess(VariableAccessCfgNode access, CapturingCallable v) {
143-
captureRead1(_, _, _, access, v)
144-
} or
145-
TLambdaAccess(Cfg::BasicBlock bb, int i, Callable c) { captureRead2(bb, i, c) } or
146-
TCallAccess(Cfg::BasicBlock bb, int i) { captureRead3(bb, i) }
89+
TVariableAccess(VariableAccessCfgNode access) { access.getVariable() instanceof CapturedVariable } or
90+
TLambdaAccess(Callable c) or
91+
TCallAccess(Cfg::BasicBlock bb, int i) {
92+
bb.getNode(i) instanceof DataFlowPrivate::Argument
93+
or
94+
DataFlowPrivate::isBlockArgument(_, bb.getNode(i))
95+
}
14796

14897
class CaptureAccess extends TCaptureAccess {
14998
string toString() { result = "<captured variable>" }
@@ -154,12 +103,12 @@ class CaptureAccess extends TCaptureAccess {
154103
result = bb.getLocation()
155104
)
156105
or
157-
exists(VariableAccessCfgNode access | this = TVariableAccess(access, _) |
106+
exists(VariableAccessCfgNode access | this = TVariableAccess(access) |
158107
result = access.getLocation()
159108
)
160109
or
161110
exists(Callable c |
162-
this = TLambdaAccess(_, _, c) and
111+
this = TLambdaAccess(c) and
163112
result = c.getLocation()
164113
)
165114
or
@@ -175,13 +124,13 @@ class CaptureAccess extends TCaptureAccess {
175124
result = bb.getScope()
176125
)
177126
or
178-
exists(VariableAccessCfgNode access | this = TVariableAccess(access, _) |
127+
exists(VariableAccessCfgNode access | this = TVariableAccess(access) |
179128
result = access.getScope()
180129
)
181130
or
182-
exists(Cfg::BasicBlock bb |
183-
this = TLambdaAccess(bb, _, _) and
184-
result = bb.getScope()
131+
exists(Callable c |
132+
this = TLambdaAccess(c) and
133+
result = c.getCfgScope()
185134
)
186135
or
187136
exists(Cfg::BasicBlock bb |
@@ -190,17 +139,16 @@ class CaptureAccess extends TCaptureAccess {
190139
)
191140
}
192141

193-
predicate isLambdaAccess(Cfg::BasicBlock bb, int i, Callable c) { this = TLambdaAccess(bb, i, c) }
142+
predicate isLambdaAccess(Cfg::BasicBlock bb, int i) {
143+
this = TLambdaAccess(bb.getNode(i).getNode())
144+
}
194145

195146
predicate isCallAccess(Cfg::BasicBlock bb, int i) { this = TCallAccess(bb, i) }
196147

197148
predicate isRead(Cfg::BasicBlock bb, int i) {
198-
exists(VariableAccessCfgNode acc, CapturingCallable v |
199-
captureRead1(bb, i, _, acc, v) and
200-
this = TVariableAccess(acc, v)
201-
)
149+
this = TVariableAccess(bb.getNode(i))
202150
or
203-
this.isLambdaAccess(bb, i, _)
151+
this.isLambdaAccess(bb, i)
204152
or
205153
this.isCallAccess(bb, i)
206154
}

ruby/ql/lib/codeql/ruby/dataflow/internal/DataFlowDispatch.qll

Lines changed: 14 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -421,7 +421,8 @@ private module Cached {
421421
THashSplatArgumentPosition() or
422422
TSplatAllArgumentPosition() or
423423
TAnyArgumentPosition() or
424-
TAnyKeywordArgumentPosition()
424+
TAnyKeywordArgumentPosition() or
425+
TCapturedVariableArgumentPosition()
425426

426427
cached
427428
newtype TParameterPosition =
@@ -443,7 +444,8 @@ private module Cached {
443444
THashSplatParameterPosition() or
444445
TSplatAllParameterPosition() or
445446
TAnyParameterPosition() or
446-
TAnyKeywordParameterPosition()
447+
TAnyKeywordParameterPosition() or
448+
TCapturedVariableParameterPosition()
447449
}
448450

449451
import Cached
@@ -1249,6 +1251,8 @@ class ParameterPosition extends TParameterPosition {
12491251
/** Holds if this position represents any positional parameter. */
12501252
predicate isAnyNamed() { this = TAnyKeywordParameterPosition() }
12511253

1254+
predicate isCapturedVariable() { this = TCapturedVariableParameterPosition() }
1255+
12521256
/** Gets a textual representation of this position. */
12531257
string toString() {
12541258
this.isSelf() and result = "self"
@@ -1268,6 +1272,8 @@ class ParameterPosition extends TParameterPosition {
12681272
this.isAny() and result = "any"
12691273
or
12701274
this.isAnyNamed() and result = "any-named"
1275+
or
1276+
this.isCapturedVariable() and result = "captured variable"
12711277
}
12721278
}
12731279

@@ -1294,6 +1300,8 @@ class ArgumentPosition extends TArgumentPosition {
12941300
/** Holds if this position represents any positional parameter. */
12951301
predicate isAnyNamed() { this = TAnyKeywordArgumentPosition() }
12961302

1303+
predicate isCapturedVariable() { this = TCapturedVariableArgumentPosition() }
1304+
12971305
/**
12981306
* Holds if this position represents a synthesized argument containing all keyword
12991307
* arguments wrapped in a hash.
@@ -1319,6 +1327,8 @@ class ArgumentPosition extends TArgumentPosition {
13191327
this.isHashSplat() and result = "**"
13201328
or
13211329
this.isSplatAll() and result = "*"
1330+
or
1331+
this.isCapturedVariable() and result = "captured variable"
13221332
}
13231333
}
13241334

@@ -1354,4 +1364,6 @@ predicate parameterMatch(ParameterPosition ppos, ArgumentPosition apos) {
13541364
ppos.isAnyNamed() and apos.isKeyword(_)
13551365
or
13561366
apos.isAnyNamed() and ppos.isKeyword(_)
1367+
or
1368+
ppos.isCapturedVariable() and apos.isCapturedVariable()
13571369
}

ruby/ql/lib/codeql/ruby/dataflow/internal/DataFlowPrivate.qll

Lines changed: 21 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,3 @@
1-
private import codeql.util.Boolean
21
private import codeql.ruby.AST
32
private import codeql.ruby.ast.internal.Synthesis
43
private import codeql.ruby.CFG
@@ -325,7 +324,14 @@ private module Cached {
325324
or
326325
c.getAnArgument() instanceof CfgNodes::ExprNodes::PairCfgNode
327326
} or
328-
TCapturedVariableAcccessNode(CapturedVariableFlow::CaptureAccess access, Boolean post)
327+
TCapturedVariableAcccessNode(CapturedVariableFlow::CaptureAccess access) {
328+
// not access.isCallAccess(_, _)
329+
any()
330+
} or
331+
TCapturedVariableAcccessPostUpdateNode(CapturedVariableFlow::CaptureAccess access) {
332+
// access.isCallAccess(_, _)
333+
any()
334+
}
329335

330336
class TParameterNode =
331337
TNormalParameterNode or TBlockParameterNode or TSelfParameterNode or
@@ -377,7 +383,7 @@ private module Cached {
377383
nodeTo = nodeFrom.(CapturedVariableAcccessPostUpdateNode).getPreUpdateNode().getANextAccess()
378384
or
379385
exists(BasicBlock bb, int i |
380-
nodeFrom.(CapturedVariableAcccessNode).getAccess().isLambdaAccess(bb, i, _) and
386+
nodeFrom.(CapturedVariableAcccessNode).getAccess().isLambdaAccess(bb, i) and
381387
nodeTo.asExpr() = bb.getNode(i)
382388
)
383389
or
@@ -550,12 +556,6 @@ import Cached
550556
predicate nodeIsHidden(Node n) {
551557
n instanceof SsaDefinitionExtNode
552558
or
553-
// exists(SsaImpl::DefinitionExt def | def = n.(SsaDefinitionExtNode).getDefinitionExt() |
554-
// def instanceof Ssa::PhiNode or
555-
// def instanceof SsaImpl::PhiReadNode or
556-
// def instanceof Ssa::CapturedEntryDefinition or
557-
// def instanceof Ssa::CapturedCallDefinition
558-
// )
559559
n = LocalFlow::getParameterDefNode(_)
560560
or
561561
isDesugarNode(n.(ExprNode).getExprNode().getExpr())
@@ -571,6 +571,8 @@ predicate nodeIsHidden(Node n) {
571571
n instanceof SynthHashSplatArgumentNode
572572
or
573573
n instanceof TCapturedVariableAcccessNode
574+
or
575+
n instanceof TCapturedVariableAcccessPostUpdateNode
574576
}
575577

576578
/** An SSA definition, viewed as a node in a data flow graph. */
@@ -628,7 +630,7 @@ class ReturningStatementNode extends NodeImpl, TReturningNode {
628630
class CapturedVariableAcccessNode extends NodeImpl, TCapturedVariableAcccessNode {
629631
private CapturedVariableFlow::CaptureAccess access;
630632

631-
CapturedVariableAcccessNode() { this = TCapturedVariableAcccessNode(access, false) }
633+
CapturedVariableAcccessNode() { this = TCapturedVariableAcccessNode(access) }
632634

633635
CapturedVariableFlow::CaptureAccess getAccess() { result = access }
634636

@@ -645,16 +647,17 @@ class CapturedVariableAcccessNode extends NodeImpl, TCapturedVariableAcccessNode
645647

646648
/** A data-flow node used to model flow summaries. */
647649
class CapturedVariableAcccessPostUpdateNode extends NodeImpl, PostUpdateNodeImpl,
648-
TCapturedVariableAcccessNode
650+
TCapturedVariableAcccessPostUpdateNode
649651
{
650652
private CapturedVariableFlow::CaptureAccess access;
651653

652-
CapturedVariableAcccessPostUpdateNode() { this = TCapturedVariableAcccessNode(access, true) }
654+
CapturedVariableAcccessPostUpdateNode() { this = TCapturedVariableAcccessPostUpdateNode(access) }
653655

654656
CapturedVariableFlow::CaptureAccess getAccess() { result = access }
655657

656658
override CapturedVariableAcccessNode getPreUpdateNode() {
657-
result = TCapturedVariableAcccessNode(access, false)
659+
result = TCapturedVariableAcccessNode(access)
660+
// result = TCapturedVariableAcccessNode(access, false)
658661
}
659662

660663
override CfgScope getCfgScope() { result = access.getCfgScope() }
@@ -886,7 +889,7 @@ private module ParameterNodes {
886889

887890
override predicate isParameterOf(DataFlowCallable c, ParameterPosition pos) {
888891
c.asCallable() = this.getCfgScope() and
889-
pos.isSelf()
892+
pos.isCapturedVariable()
890893
}
891894
}
892895
}
@@ -1018,7 +1021,7 @@ private module ArgumentNodes {
10181021

10191022
override predicate argumentOf(DataFlowCall call, ArgumentPosition pos) {
10201023
lambdaCall(call, _, this) and
1021-
pos.isSelf()
1024+
pos.isCapturedVariable()
10221025
}
10231026

10241027
override predicate sourceArgumentOf(CfgNodes::ExprNodes::CallCfgNode call, ArgumentPosition pos) {
@@ -1400,9 +1403,11 @@ predicate expectsContent(Node n, ContentSet c) {
14001403
FlowSummaryImpl::Private::Steps::summaryExpectsContent(n, c)
14011404
or
14021405
exists(CapturedVariableFlow::CaptureAccess access |
1403-
n = TCapturedVariableAcccessNode(access, _) and
14041406
access.isReadOrWrite(_, _) and
14051407
c.isAnyCapturedVariable()
1408+
|
1409+
n = TCapturedVariableAcccessNode(access) or
1410+
n = TCapturedVariableAcccessPostUpdateNode(access)
14061411
)
14071412
}
14081413

ruby/ql/lib/codeql/ruby/dataflow/internal/FlowSummaryImplSpecific.qll

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@ class SummarizedCallableBase = string;
1616
DataFlowCallable inject(SummarizedCallable c) { result.asLibraryCallable() = c }
1717

1818
/** Gets the parameter position of the instance parameter. */
19-
ArgumentPosition instanceParameterPosition() { result.isSelf() }
19+
ArgumentPosition instanceParameterPosition() { result.isCapturedVariable() }
2020

2121
/** Gets the synthesized summary data-flow node for the given values. */
2222
Node summaryNode(SummarizedCallable c, SummaryNodeState state) { result = TSummaryNode(c, state) }

0 commit comments

Comments
 (0)