Skip to content

Commit 5341aaf

Browse files
committed
fix incorrect static parameter definedness check (#49097)
We use the specialized signature of a method for accurate analysis of whether a static parameter is constrained or not. However, it turns out that we can only use it when it doesn't contain any free type variables (which it sometimes does, e.g., when the inference entry is given a signature with a free type variable). In such cases, we should use the method signature, which, by design, never contains any free type variables.
1 parent 13b89aa commit 5341aaf

File tree

2 files changed

+32
-1
lines changed

2 files changed

+32
-1
lines changed

base/compiler/inferencestate.jl

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -459,7 +459,18 @@ function sptypes_from_meth_instance(linfo::MethodInstance)
459459
v = sp[i]
460460
if v isa TypeVar
461461
fromArg = 0
462-
maybe_undef = !constrains_param(v, linfo.specTypes, #=covariant=#true)
462+
maybe_undef = !(let sig=sig
463+
# if the specialized signature `linfo.specTypes` doesn't contain any free
464+
# type variables, we can use it for a more accurate analysis of whether `v`
465+
# is constrained or not, otherwise we should use `def.sig` which always
466+
# doesn't contain any free type variables
467+
if !has_free_typevars(linfo.specTypes)
468+
sig = linfo.specTypes
469+
else
470+
@assert !has_free_typevars(sig)
471+
end
472+
constrains_param(v, sig, #=covariant=#true)
473+
end)
463474
temp = sig
464475
for j = 1:i-1
465476
temp = temp.body

test/compiler/inference.jl

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4294,6 +4294,26 @@ unknown_sparam_nothrow2(x::Ref{Ref{T}}) where T = @isdefined(T) ? T::Type : noth
42944294
@test only(Base.return_types(unknown_sparam_nothrow1, (Ref,))) === Type
42954295
@test only(Base.return_types(unknown_sparam_nothrow2, (Ref{Ref{T}} where T,))) === Type
42964296

4297+
struct Issue49027{Ty<:Number}
4298+
x::Ty
4299+
end
4300+
function issue49027(::Type{<:Issue49027{Ty}}) where Ty
4301+
if @isdefined Ty # should be false when `Ty` is given as a free type var.
4302+
return Ty::DataType
4303+
end
4304+
return nothing
4305+
end
4306+
@test only(Base.return_types(issue49027, (Type{Issue49027{TypeVar(:Ty)}},))) >: Nothing
4307+
@test isnothing(issue49027(Issue49027{TypeVar(:Ty)}))
4308+
function issue49027_integer(::Type{<:Issue49027{Ty}}) where Ty<:Integer
4309+
if @isdefined Ty # should be false when `Ty` is given as a free type var.
4310+
return Ty::DataType
4311+
end
4312+
nothing
4313+
end
4314+
@test only(Base.return_types(issue49027_integer, (Type{Issue49027{TypeVar(:Ty,Int)}},))) >: Nothing
4315+
@test isnothing(issue49027_integer(Issue49027{TypeVar(:Ty,Int)}))
4316+
42974317
# Issue #47688: Abstract iteration should take into account `iterate` effects
42984318
global it_count47688 = 0
42994319
struct CountsIterate47688{N}; end

0 commit comments

Comments
 (0)