@@ -113,16 +113,17 @@ module Impl {
113
113
*/
114
114
IdentPat getPat ( ) { variableDecl ( definingNode , result , name ) }
115
115
116
+ /** Gets the `let` statement that introduces this variable, if any. */
117
+ LetStmt getLetStmt ( ) { this .getPat ( ) = result .getPat ( ) }
118
+
116
119
/** Gets the initial value of this variable, if any. */
117
- Expr getInitializer ( ) {
118
- exists ( LetStmt let |
119
- this .getPat ( ) = let .getPat ( ) and
120
- result = let .getInitializer ( )
121
- )
122
- }
120
+ Expr getInitializer ( ) { result = this .getLetStmt ( ) .getInitializer ( ) }
123
121
124
122
/** Holds if this variable is captured. */
125
123
predicate isCaptured ( ) { this .getAnAccess ( ) .isCapture ( ) }
124
+
125
+ /** Gets the parameter that introduces this variable, if any. */
126
+ Param getParameter ( ) { parameterDeclInScope ( result , this , _) }
126
127
}
127
128
128
129
/** A path expression that may access a local variable. */
@@ -175,6 +176,27 @@ module Impl {
175
176
)
176
177
}
177
178
179
+ /**
180
+ * Holds if parameter `p` introduces the variable `v` inside variable scope
181
+ * `scope`.
182
+ */
183
+ private predicate parameterDeclInScope ( Param p , Variable v , VariableScope scope ) {
184
+ exists ( Pat pat |
185
+ pat = getAVariablePatAncestor ( v ) and
186
+ p .getPat ( ) = pat
187
+ |
188
+ exists ( Function f |
189
+ f .getParamList ( ) .getAParam ( ) = p and
190
+ scope = f .getBody ( )
191
+ )
192
+ or
193
+ exists ( ClosureExpr ce |
194
+ ce .getParamList ( ) .getAParam ( ) = p and
195
+ scope = ce .getBody ( )
196
+ )
197
+ )
198
+ }
199
+
178
200
/**
179
201
* Holds if `v` is named `name` and is declared inside variable scope
180
202
* `scope`, and `v` is bound starting from `(line, column)`.
@@ -183,51 +205,44 @@ module Impl {
183
205
Variable v , VariableScope scope , string name , int line , int column
184
206
) {
185
207
name = v .getName ( ) and
186
- exists ( Pat pat | pat = getAVariablePatAncestor ( v ) |
187
- scope =
188
- any ( MatchArmScope arm |
189
- arm .getPat ( ) = pat and
190
- arm .getLocation ( ) .hasLocationInfo ( _, line , column , _, _)
191
- )
192
- or
193
- exists ( Function f |
194
- f .getParamList ( ) .getAParam ( ) .getPat ( ) = pat and
195
- scope = f .getBody ( ) and
196
- scope .getLocation ( ) .hasLocationInfo ( _, line , column , _, _)
197
- )
198
- or
199
- exists ( LetStmt let |
200
- let .getPat ( ) = pat and
201
- scope = getEnclosingScope ( let ) and
202
- // for `let` statements, variables are bound _after_ the statement, i.e.
203
- // not in the RHS
204
- let .getLocation ( ) .hasLocationInfo ( _, _, _, line , column )
205
- )
206
- or
207
- exists ( IfExpr ie , LetExpr let |
208
- let .getPat ( ) = pat and
209
- ie .getCondition ( ) = let and
210
- scope = ie .getThen ( ) and
211
- scope .getLocation ( ) .hasLocationInfo ( _, line , column , _, _)
212
- )
213
- or
214
- exists ( ForExpr fe |
215
- fe .getPat ( ) = pat and
216
- scope = fe .getLoopBody ( ) and
217
- scope .getLocation ( ) .hasLocationInfo ( _, line , column , _, _)
218
- )
219
- or
220
- exists ( ClosureExpr ce |
221
- ce .getParamList ( ) .getAParam ( ) .getPat ( ) = pat and
222
- scope = ce .getBody ( ) and
223
- scope .getLocation ( ) .hasLocationInfo ( _, line , column , _, _)
224
- )
208
+ (
209
+ parameterDeclInScope ( _, v , scope ) and
210
+ scope .getLocation ( ) .hasLocationInfo ( _, line , column , _, _)
225
211
or
226
- exists ( WhileExpr we , LetExpr let |
227
- let .getPat ( ) = pat and
228
- we .getCondition ( ) = let and
229
- scope = we .getLoopBody ( ) and
230
- scope .getLocation ( ) .hasLocationInfo ( _, line , column , _, _)
212
+ exists ( Pat pat | pat = getAVariablePatAncestor ( v ) |
213
+ scope =
214
+ any ( MatchArmScope arm |
215
+ arm .getPat ( ) = pat and
216
+ arm .getLocation ( ) .hasLocationInfo ( _, line , column , _, _)
217
+ )
218
+ or
219
+ exists ( LetStmt let |
220
+ let .getPat ( ) = pat and
221
+ scope = getEnclosingScope ( let ) and
222
+ // for `let` statements, variables are bound _after_ the statement, i.e.
223
+ // not in the RHS
224
+ let .getLocation ( ) .hasLocationInfo ( _, _, _, line , column )
225
+ )
226
+ or
227
+ exists ( IfExpr ie , LetExpr let |
228
+ let .getPat ( ) = pat and
229
+ ie .getCondition ( ) = let and
230
+ scope = ie .getThen ( ) and
231
+ scope .getLocation ( ) .hasLocationInfo ( _, line , column , _, _)
232
+ )
233
+ or
234
+ exists ( ForExpr fe |
235
+ fe .getPat ( ) = pat and
236
+ scope = fe .getLoopBody ( ) and
237
+ scope .getLocation ( ) .hasLocationInfo ( _, line , column , _, _)
238
+ )
239
+ or
240
+ exists ( WhileExpr we , LetExpr let |
241
+ let .getPat ( ) = pat and
242
+ we .getCondition ( ) = let and
243
+ scope = we .getLoopBody ( ) and
244
+ scope .getLocation ( ) .hasLocationInfo ( _, line , column , _, _)
245
+ )
231
246
)
232
247
)
233
248
}
@@ -422,7 +437,8 @@ module Impl {
422
437
exists ( Expr mid |
423
438
assignmentExprDescendant ( mid ) and
424
439
getImmediateParent ( e ) = mid and
425
- not mid .( PrefixExpr ) .getOperatorName ( ) = "*"
440
+ not mid .( PrefixExpr ) .getOperatorName ( ) = "*" and
441
+ not mid instanceof FieldExpr
426
442
)
427
443
}
428
444
0 commit comments