@@ -1314,7 +1314,7 @@ static int subtype(jl_value_t *x, jl_value_t *y, jl_stenv_t *e, int param)
1314
1314
if (jl_is_uniontype (x )) {
1315
1315
if (obviously_egal (x , y ))
1316
1316
return 1 ;
1317
- if (e -> Runions .depth == 0 && jl_is_typevar (y ) && !jl_has_free_typevars (x ) && ! jl_has_free_typevars ((( jl_tvar_t * ) y ) -> ub ) ) {
1317
+ if (e -> Runions .depth == 0 && jl_is_typevar (y ) && !jl_has_free_typevars (x )) {
1318
1318
// Similar to fast path for repeated elements: if there have been no outer
1319
1319
// unions on the right, and the right side is a typevar, then we can handle the
1320
1320
// typevar first before picking a union element, under the theory that it may
@@ -1325,7 +1325,17 @@ static int subtype(jl_value_t *x, jl_value_t *y, jl_stenv_t *e, int param)
1325
1325
// free typevars, since the typevars presence might lead to those elements
1326
1326
// getting eliminated (omit_bad_union) or degenerate (Union{Ptr{T}, Ptr}) or
1327
1327
// combined (Union{T, S} where {T, S <: T}).
1328
- return subtype_var ((jl_tvar_t * )y , x , e , 1 , param );
1328
+ jl_tvar_t * yvar = (jl_tvar_t * )yvar ;
1329
+ jl_varbinding_t * yb = lookup (e , yvar );
1330
+ while (e -> intersection && yb != NULL && yb -> lb == yb -> ub && jl_is_typevar (yb -> lb )) {
1331
+ yvar = yb -> lb ;
1332
+ yb = lookup (e , yvar );
1333
+ }
1334
+ // Note: `x <: ∃y` performs a local ∀-∃ check between `x` and `yb->ub`.
1335
+ // We need to ensure that there's no ∃ typevar as otherwise that check
1336
+ // might cause false alarm due to the accumulated env change.
1337
+ if (yb == NULL || yb -> right == 0 || !has_exists_typevar (yb -> ub , e ))
1338
+ return subtype_var (yvar , x , e , 1 , param );
1329
1339
}
1330
1340
x = pick_union_element (x , e , 0 );
1331
1341
}
0 commit comments