@@ -364,13 +364,45 @@ private predicate typeFlow(TypeFlowNode n, RefType t) {
364364 typeFlowJoin ( lastRank ( n ) , n , t )
365365}
366366
367+ pragma [ nomagic]
368+ predicate erasedTypeBound ( RefType t ) {
369+ exists ( RefType t0 | typeFlow ( _, t0 ) and t = t0 .getErasure ( ) )
370+ }
371+
372+ pragma [ nomagic]
373+ predicate typeBound ( RefType t ) { typeFlow ( _, t ) }
374+
375+ /**
376+ * Holds if we have a bound for `n` that is better than `t`, taking only erased
377+ * types into account.
378+ */
379+ pragma [ nomagic]
380+ private predicate irrelevantErasedBound ( TypeFlowNode n , RefType t ) {
381+ exists ( RefType bound |
382+ typeFlow ( n , bound )
383+ or
384+ n .getType ( ) = bound and typeFlow ( n , _)
385+ |
386+ t = bound .getErasure ( ) .( RefType ) .getASourceSupertype + ( ) and
387+ erasedTypeBound ( t )
388+ )
389+ }
390+
367391/**
368392 * Holds if we have a bound for `n` that is better than `t`.
369393 */
370- pragma [ noinline ]
394+ pragma [ nomagic ]
371395private predicate irrelevantBound ( TypeFlowNode n , RefType t ) {
372- exists ( RefType bound | typeFlow ( n , bound ) or n .getType ( ) = bound |
373- t = bound .getErasure ( ) .( RefType ) .getASourceSupertype + ( )
396+ exists ( RefType bound |
397+ typeFlow ( n , bound ) and
398+ t = bound .getASupertype + ( ) and
399+ typeBound ( t ) and
400+ typeFlow ( n , t ) and
401+ not t .getASupertype * ( ) = bound
402+ or
403+ n .getType ( ) = bound and
404+ typeFlow ( n , t ) and
405+ t = bound .getASupertype * ( )
374406 )
375407}
376408
@@ -380,7 +412,8 @@ private predicate irrelevantBound(TypeFlowNode n, RefType t) {
380412 */
381413private predicate bestTypeFlow ( TypeFlowNode n , RefType t ) {
382414 typeFlow ( n , t ) and
383- not irrelevantBound ( n , t .getErasure ( ) )
415+ not irrelevantErasedBound ( n , t .getErasure ( ) ) and
416+ not irrelevantBound ( n , t )
384417}
385418
386419cached
0 commit comments