@@ -8,6 +8,7 @@ private import codeql.util.Boolean
8
8
private import codeql.dataflow.DataFlow
9
9
private import codeql.dataflow.internal.DataFlowImpl
10
10
private import rust
11
+ private import codeql.rust.elements.Call
11
12
private import SsaImpl as SsaImpl
12
13
private import codeql.rust.controlflow.internal.Scope as Scope
13
14
private import codeql.rust.internal.PathResolution
@@ -55,11 +56,7 @@ final class DataFlowCallable extends TDataFlowCallable {
55
56
56
57
final class DataFlowCall extends TDataFlowCall {
57
58
/** Gets the underlying call in the CFG, if any. */
58
- CallExprCfgNode asCallExprCfgNode ( ) { result = this .asCallBaseExprCfgNode ( ) }
59
-
60
- MethodCallExprCfgNode asMethodCallExprCfgNode ( ) { result = this .asCallBaseExprCfgNode ( ) }
61
-
62
- CallExprBaseCfgNode asCallBaseExprCfgNode ( ) { this = TCall ( result ) }
59
+ CallCfgNode asCallCfgNode ( ) { this = TCall ( result ) }
63
60
64
61
predicate isSummaryCall (
65
62
FlowSummaryImpl:: Public:: SummarizedCallable c , FlowSummaryImpl:: Private:: SummaryNode receiver
@@ -68,7 +65,7 @@ final class DataFlowCall extends TDataFlowCall {
68
65
}
69
66
70
67
DataFlowCallable getEnclosingCallable ( ) {
71
- result = TCfgScope ( this .asCallBaseExprCfgNode ( ) .getExpr ( ) .getEnclosingCfgScope ( ) )
68
+ result = TCfgScope ( this .asCallCfgNode ( ) .getExpr ( ) .getEnclosingCfgScope ( ) )
72
69
or
73
70
exists ( FlowSummaryImpl:: Public:: SummarizedCallable c |
74
71
this .isSummaryCall ( c , _) and
@@ -77,7 +74,7 @@ final class DataFlowCall extends TDataFlowCall {
77
74
}
78
75
79
76
string toString ( ) {
80
- result = this .asCallBaseExprCfgNode ( ) .toString ( )
77
+ result = this .asCallCfgNode ( ) .toString ( )
81
78
or
82
79
exists (
83
80
FlowSummaryImpl:: Public:: SummarizedCallable c , FlowSummaryImpl:: Private:: SummaryNode receiver
@@ -87,7 +84,7 @@ final class DataFlowCall extends TDataFlowCall {
87
84
)
88
85
}
89
86
90
- Location getLocation ( ) { result = this .asCallBaseExprCfgNode ( ) .getLocation ( ) }
87
+ Location getLocation ( ) { result = this .asCallCfgNode ( ) .getLocation ( ) }
91
88
}
92
89
93
90
/**
@@ -135,38 +132,23 @@ final class ParameterPosition extends TParameterPosition {
135
132
*/
136
133
final class ArgumentPosition extends ParameterPosition {
137
134
/** Gets the argument of `call` at this position, if any. */
138
- Expr getArgument ( CallExprBase call ) {
139
- result = call .getArgList ( ) . getArg ( this .getPosition ( ) )
135
+ Expr getArgument ( Call call ) {
136
+ result = call .getArgument ( this .getPosition ( ) )
140
137
or
141
- this .isSelf ( ) and
142
- result = call .( MethodCallExpr ) .getReceiver ( )
138
+ result = call .getReceiver ( ) and this .isSelf ( )
143
139
}
144
140
}
145
141
146
- /** Holds if `call` invokes a qualified path that resolves to a method. */
147
- private predicate callToMethod ( CallExpr call ) {
148
- exists ( Path path |
149
- path = call .getFunction ( ) .( PathExpr ) .getPath ( ) and
150
- path .hasQualifier ( ) and
151
- resolvePath ( path ) .( Function ) .getParamList ( ) .hasSelfParam ( )
152
- )
153
- }
154
-
155
142
/**
156
143
* Holds if `arg` is an argument of `call` at the position `pos`.
157
144
*
158
145
* Note that this does not hold for the receiever expression of a method call
159
146
* as the synthetic `ReceiverNode` is the argument for the `self` parameter.
160
147
*/
161
- predicate isArgumentForCall ( ExprCfgNode arg , CallExprBaseCfgNode call , ParameterPosition pos ) {
162
- if callToMethod ( call .( CallExprCfgNode ) .getCallExpr ( ) )
163
- then
164
- // The first argument is for the `self` parameter
165
- arg = call .getArgument ( 0 ) and pos .isSelf ( )
166
- or
167
- // Succeeding arguments are shifted left
168
- arg = call .getArgument ( pos .getPosition ( ) + 1 )
169
- else arg = call .getArgument ( pos .getPosition ( ) )
148
+ predicate isArgumentForCall ( ExprCfgNode arg , CallCfgNode call , ParameterPosition pos ) {
149
+ call .getArgument ( pos .getPosition ( ) ) = arg
150
+ or
151
+ call .getReceiver ( ) = arg and pos .isSelf ( ) and not call .getCall ( ) .receiverImplicitlyBorrowed ( )
170
152
}
171
153
172
154
/** Provides logic related to SSA. */
@@ -419,9 +401,9 @@ module RustDataFlow implements InputSig<Location> {
419
401
420
402
/** Gets a viable implementation of the target of the given `Call`. */
421
403
DataFlowCallable viableCallable ( DataFlowCall call ) {
422
- result .asCfgScope ( ) = call .asCallBaseExprCfgNode ( ) .getCallExprBase ( ) .getStaticTarget ( )
404
+ result .asCfgScope ( ) = call .asCallCfgNode ( ) .getCall ( ) .getStaticTarget ( )
423
405
or
424
- result .asLibraryCallable ( ) .getACall ( ) = call .asCallBaseExprCfgNode ( ) .getCallExprBase ( )
406
+ result .asLibraryCallable ( ) .getACall ( ) = call .asCallCfgNode ( ) .getCall ( )
425
407
}
426
408
427
409
/**
@@ -812,7 +794,7 @@ module RustDataFlow implements InputSig<Location> {
812
794
*/
813
795
predicate lambdaCall ( DataFlowCall call , LambdaCallKind kind , Node receiver ) {
814
796
(
815
- receiver .asExpr ( ) = call .asCallExprCfgNode ( ) .getFunction ( ) and
797
+ receiver .asExpr ( ) = call .asCallCfgNode ( ) . ( CallExprCfgNode ) .getFunction ( ) and
816
798
// All calls to complex expressions and local variable accesses are lambda call.
817
799
exists ( Expr f | f = receiver .asExpr ( ) .getExpr ( ) |
818
800
f instanceof PathExpr implies f = any ( Variable v ) .getAnAccess ( )
@@ -976,7 +958,7 @@ private module Cached {
976
958
977
959
cached
978
960
newtype TDataFlowCall =
979
- TCall ( CallExprBaseCfgNode c ) { Stages:: DataFlowStage:: ref ( ) } or
961
+ TCall ( CallCfgNode c ) { Stages:: DataFlowStage:: ref ( ) } or
980
962
TSummaryCall (
981
963
FlowSummaryImpl:: Public:: SummarizedCallable c , FlowSummaryImpl:: Private:: SummaryNode receiver
982
964
) {
0 commit comments