@@ -207,81 +207,58 @@ private Type inferAssignmentOperationType(AstNode n, TypePath path) {
207
207
}
208
208
209
209
/**
210
- * Holds if the type of `n1` at `path1` is the same as the type of `n2` at
211
- * `path2` and type information should propagate in both directions through the
212
- * type equality.
210
+ * Holds if the type tree of `n1` at `prefix1` should be equal to the type tree
211
+ * of `n2` at `prefix2` and type information should propagate in both directions
212
+ * through the type equality.
213
213
*/
214
- bindingset [ path1]
215
- bindingset [ path2]
216
- private predicate typeEquality ( AstNode n1 , TypePath path1 , AstNode n2 , TypePath path2 ) {
217
- exists ( Variable v |
218
- path1 = path2 and
219
- n1 = v .getAnAccess ( )
220
- |
221
- n2 = v .getPat ( )
214
+ private predicate typeEquality ( AstNode n1 , TypePath prefix1 , AstNode n2 , TypePath prefix2 ) {
215
+ prefix1 .isEmpty ( ) and
216
+ prefix2 .isEmpty ( ) and
217
+ (
218
+ exists ( Variable v | n1 = v .getAnAccess ( ) |
219
+ n2 = v .getPat ( )
220
+ or
221
+ n2 = v .getParameter ( ) .( SelfParam )
222
+ )
222
223
or
223
- n2 = v .getParameter ( ) .( SelfParam )
224
- )
225
- or
226
- exists ( LetStmt let |
227
- let .getPat ( ) = n1 and
228
- let .getInitializer ( ) = n2 and
229
- path1 = path2
230
- )
231
- or
232
- n1 = n2 .( ParenExpr ) .getExpr ( ) and
233
- path1 = path2
234
- or
235
- n1 = n2 .( BlockExpr ) .getStmtList ( ) .getTailExpr ( ) and
236
- path1 = path2
237
- or
238
- n1 = n2 .( IfExpr ) .getABranch ( ) and
239
- path1 = path2
240
- or
241
- n1 = n2 .( MatchExpr ) .getAnArm ( ) .getExpr ( ) and
242
- path1 = path2
243
- or
244
- exists ( BreakExpr break |
245
- break .getExpr ( ) = n1 and
246
- break .getTarget ( ) = n2 .( LoopExpr ) and
247
- path1 = path2
248
- )
249
- or
250
- exists ( AssignmentExpr be |
251
- n1 = be .getLhs ( ) and
252
- n2 = be .getRhs ( ) and
253
- path1 = path2
254
- )
255
- }
256
-
257
- bindingset [ path1]
258
- private predicate typeEqualityLeft ( AstNode n1 , TypePath path1 , AstNode n2 , TypePath path2 ) {
259
- typeEquality ( n1 , path1 , n2 , path2 )
260
- or
261
- n2 =
262
- any ( DerefExpr pe |
263
- pe .getExpr ( ) = n1 and
264
- path1 .isCons ( TRefTypeParameter ( ) , path2 )
224
+ exists ( LetStmt let |
225
+ let .getPat ( ) = n1 and
226
+ let .getInitializer ( ) = n2
265
227
)
266
- }
267
-
268
- bindingset [ path2]
269
- private predicate typeEqualityRight ( AstNode n1 , TypePath path1 , AstNode n2 , TypePath path2 ) {
270
- typeEquality ( n1 , path1 , n2 , path2 )
271
- or
272
- n2 =
273
- any ( DerefExpr pe |
274
- pe .getExpr ( ) = n1 and
275
- path1 = TypePath:: cons ( TRefTypeParameter ( ) , path2 )
228
+ or
229
+ n1 = n2 .( ParenExpr ) .getExpr ( )
230
+ or
231
+ n1 = n2 .( BlockExpr ) .getStmtList ( ) .getTailExpr ( )
232
+ or
233
+ n1 = n2 .( IfExpr ) .getABranch ( )
234
+ or
235
+ n1 = n2 .( MatchExpr ) .getAnArm ( ) .getExpr ( )
236
+ or
237
+ exists ( BreakExpr break |
238
+ break .getExpr ( ) = n1 and
239
+ break .getTarget ( ) = n2 .( LoopExpr )
240
+ )
241
+ or
242
+ exists ( AssignmentExpr be |
243
+ n1 = be .getLhs ( ) and
244
+ n2 = be .getRhs ( )
276
245
)
246
+ )
247
+ or
248
+ n1 = n2 .( DerefExpr ) .getExpr ( ) and
249
+ prefix1 = TypePath:: singleton ( TRefTypeParameter ( ) ) and
250
+ prefix2 .isEmpty ( )
277
251
}
278
252
279
253
pragma [ nomagic]
280
254
private Type inferTypeEquality ( AstNode n , TypePath path ) {
281
- exists ( AstNode n2 , TypePath path2 | result = inferType ( n2 , path2 ) |
282
- typeEqualityRight ( n , path , n2 , path2 )
255
+ exists ( TypePath prefix1 , AstNode n2 , TypePath prefix2 , TypePath suffix |
256
+ result = inferType ( n2 , prefix2 .appendInverse ( suffix ) ) and
257
+ path = prefix1 .append ( suffix )
258
+ |
259
+ typeEquality ( n , prefix1 , n2 , prefix2 )
283
260
or
284
- typeEqualityLeft ( n2 , path2 , n , path )
261
+ typeEquality ( n2 , prefix2 , n , prefix1 )
285
262
)
286
263
}
287
264
0 commit comments