From 1dacf6686fbea3519d4b042a1abd53c5b7153077 Mon Sep 17 00:00:00 2001 From: Jeff Bezanson Date: Fri, 5 Feb 2021 16:47:16 -0500 Subject: [PATCH] fix #39521, obvious_subtype issue with `Type{}` and diagonal (#39525) (cherry picked from commit 6159633f6f8125eaffa5bd7e9d7964323409c01f) --- src/subtype.c | 10 ++++++---- test/subtype.jl | 4 ++++ 2 files changed, 10 insertions(+), 4 deletions(-) diff --git a/src/subtype.c b/src/subtype.c index 8a3300cad8bac..5148232fa58c8 100644 --- a/src/subtype.c +++ b/src/subtype.c @@ -1788,17 +1788,19 @@ static int obvious_subtype(jl_value_t *x, jl_value_t *y, jl_value_t *y0, int *su *subtype = 0; return 1; } - if (jl_is_type_type(a1) && jl_is_type(jl_tparam0(a1))) { - a1 = jl_typeof(jl_tparam0(a1)); + jl_value_t *a1u = jl_unwrap_unionall(a1); + if (jl_is_type_type(a1u) && jl_is_type(jl_tparam0(a1u))) { + a1 = jl_typeof(jl_tparam0(a1u)); } for (; i < nparams_expanded_x; i++) { jl_value_t *a = (vx != JL_VARARG_NONE && i >= npx - 1) ? vxt : jl_tparam(x, i); if (i > npy && jl_is_typevar(b)) { // i == npy implies a == a1 // diagonal rule: all the later parameters are also constrained to be type-equal to the first jl_value_t *a2 = a; - if (jl_is_type_type(a) && jl_is_type(jl_tparam0(a))) { + jl_value_t *au = jl_unwrap_unionall(a); + if (jl_is_type_type(au) && jl_is_type(jl_tparam0(au))) { // if a is exactly Type{T}, then use the concrete typeof(T) instead here - a2 = jl_typeof(jl_tparam0(a)); + a2 = jl_typeof(jl_tparam0(au)); } if (!obviously_egal(a1, a2)) { if (obvious_subtype(a2, a1, y0, subtype)) { diff --git a/test/subtype.jl b/test/subtype.jl index c99fc780799e6..6298097b9b3d9 100644 --- a/test/subtype.jl +++ b/test/subtype.jl @@ -1861,3 +1861,7 @@ f39218(::T, ::T) where {T<:AB39218} = false g39218(a, b) = (@nospecialize; if a isa AB39218 && b isa AB39218; f39218(a, b); end;) @test g39218(A39218(), A39218()) === false @test_throws MethodError g39218(A39218(), B39218()) + +# issue #39521 +@test Tuple{Type{Tuple{A}} where A, DataType, DataType} <: Tuple{Vararg{B}} where B +@test Tuple{DataType, Type{Tuple{A}} where A, DataType} <: Tuple{Vararg{B}} where B