DocStringExtensions.jl icon indicating copy to clipboard operation
DocStringExtensions.jl copied to clipboard

ERROR: TypeError: in <:, expected Type, got a value of type TypeVar

Open kdheepak opened this issue 4 years ago • 1 comments

$TYPEDSIGNATURES causes error when calling Base.return_type when typesig is UnionAll with generic types.

I think the easy hacky solution to this is to wrap the following in a try except.

https://github.com/JuliaDocs/DocStringExtensions.jl/blob/339cd6ddd9549d52503cf02782733a0cecd481da/src/utilities.jl#L308-L311

A better solution is to pass the right typesig to Base.return_types. The issue here is that local typesig = doc.data[:typesig] doesn't exactly return what we want. And I think we are currently missing some corner case. Specifically, generic UnionAll types are converted to Tuples without the TypeVar var. This causes some issues.

I'm not able to reproduce an example in isolation, since I believe it is tied to return_types, which depends on the code path. But the function signature looks something like this.

"""
$TYPEDSIGNATURES
"""
function f(x::ParametricType{M}) where M <: Union{A, B}
...
return result
end

calls Base.return_types throws an exception in the core compiler.

help?> Module.f
ERROR: TypeError: in <:, expected Type, got a value of type TypeVar
Stacktrace:
 [1] ⊑(::Any, ::Any) at ./compiler/typelattice.jl:177
 [2] tmerge(::Any, ::Any) at ./compiler/typelimits.jl:286
 [3] getfield_tfunc(::Any, ::Any) at ./compiler/tfuncs.jl:827
 [4] builtin_tfunction(::Any, ::Array{Any,1}, ::Union{Nothing, Core.Compiler.InferenceState}, ::Core.Compiler.Params) at ./compiler/tfuncs.jl:1428
 [5] builtin_tfunction at ./compiler/tfuncs.jl:1342 [inlined]
 [6] abstract_call_known(::Any, ::Array{Any,1}, ::Array{Any,1}, ::Array{Any,1}, ::Core.Compiler.InferenceState, ::Int64) at ./compiler/abstractinterpretation.jl:720
 [7] abstract_call(::Array{Any,1}, ::Array{Any,1}, ::Array{Any,1}, ::Core.Compiler.InferenceState, ::Int64) at ./compiler/abstractinterpretation.jl:926
 [8] abstract_call(::Array{Any,1}, ::Array{Any,1}, ::Array{Any,1}, ::Core.Compiler.InferenceState) at ./compiler/abstractinterpretation.jl:911
 [9] abstract_eval(::Any, ::Array{Any,1}, ::Core.Compiler.InferenceState) at ./compiler/abstractinterpretation.jl:1005
 [10] typeinf_local(::Core.Compiler.InferenceState) at ./compiler/abstractinterpretation.jl:1270
 [11] typeinf_nocycle(::Core.Compiler.InferenceState) at ./compiler/abstractinterpretation.jl:1326
 [12] typeinf(::Core.Compiler.InferenceState) at ./compiler/typeinfer.jl:12
 [13] typeinf_edge(::Method, ::Any, ::Core.SimpleVector, ::Core.Compiler.InferenceState) at ./compiler/typeinfer.jl:484
 [14] abstract_call_method(::Method, ::Any, ::Core.SimpleVector, ::Bool, ::Core.Compiler.InferenceState) at ./compiler/abstractinterpretation.jl:419
 [15] abstract_call_gf_by_type(::Any, ::Array{Any,1}, ::Any, ::Core.Compiler.InferenceState, ::Int64) at ./compiler/abstractinterpretation.jl:111
 [16] abstract_call_known(::Any, ::Array{Any,1}, ::Array{Any,1}, ::Array{Any,1}, ::Core.Compiler.InferenceState, ::Int64) at ./compiler/abstractinterpretation.jl:904
 [17] abstract_call(::Array{Any,1}, ::Array{Any,1}, ::Array{Any,1}, ::Core.Compiler.InferenceState, ::Int64) at ./compiler/abstractinterpretation.jl:926
 [18] abstract_call(::Array{Any,1}, ::Array{Any,1}, ::Array{Any,1}, ::Core.Compiler.InferenceState) at ./compiler/abstractinterpretation.jl:911
 [19] abstract_eval(::Any, ::Array{Any,1}, ::Core.Compiler.InferenceState) at ./compiler/abstractinterpretation.jl:1005
 [20] typeinf_local(::Core.Compiler.InferenceState) at ./compiler/abstractinterpretation.jl:1270
 [21] typeinf_nocycle(::Core.Compiler.InferenceState) at ./compiler/abstractinterpretation.jl:1326
 [22] typeinf(::Core.Compiler.InferenceState) at ./compiler/typeinfer.jl:12
 [23] typeinf_edge(::Method, ::Any, ::Core.SimpleVector, ::Core.Compiler.InferenceState) at ./compiler/typeinfer.jl:484
 [24] abstract_call_method(::Method, ::Any, ::Core.SimpleVector, ::Bool, ::Core.Compiler.InferenceState) at ./compiler/abstractinterpretation.jl:419
 [25] abstract_call_gf_by_type(::Any, ::Array{Any,1}, ::Any, ::Core.Compiler.InferenceState, ::Int64) at ./compiler/abstractinterpretation.jl:111
 [26] abstract_call_known(::Any, ::Array{Any,1}, ::Array{Any,1}, ::Array{Any,1}, ::Core.Compiler.InferenceState, ::Int64) at ./compiler/abstractinterpretation.jl:904
 [27] abstract_call(::Array{Any,1}, ::Array{Any,1}, ::Array{Any,1}, ::Core.Compiler.InferenceState, ::Int64) at ./compiler/abstractinterpretation.jl:926
 [28] abstract_call(::Array{Any,1}, ::Array{Any,1}, ::Array{Any,1}, ::Core.Compiler.InferenceState) at ./compiler/abstractinterpretation.jl:911
 [29] abstract_eval(::Any, ::Array{Any,1}, ::Core.Compiler.InferenceState) at ./compiler/abstractinterpretation.jl:1005
 [30] typeinf_local(::Core.Compiler.InferenceState) at ./compiler/abstractinterpretation.jl:1270
 [31] typeinf_nocycle(::Core.Compiler.InferenceState) at ./compiler/abstractinterpretation.jl:1326
 [32] typeinf(::Core.Compiler.InferenceState) at ./compiler/typeinfer.jl:12
 [33] typeinf at ./compiler/typeinfer.jl:8 [inlined]
 [34] typeinf_type(::Method, ::Any, ::Core.SimpleVector, ::Core.Compiler.Params) at ./compiler/typeinfer.jl:592
 [35] return_types(::Any, ::Any) at ./reflection.jl:1133
 [36] printmethod(::Base.GenericIOBuffer{Array{UInt8,1}}, ::Base.Docs.Binding, ::Function, ::Method, ::Type{T} where T) at /Users/USER/.julia/packages/DocStringExtensions/c3W3t/src/utilities.jl:308
 [37] format(::DocStringExtensions.TypedMethodSignatures, ::Base.GenericIOBuffer{Array{UInt8,1}}, ::Base.Docs.DocStr) at /Users/USER/.julia/packages/DocStringExtensions/c3W3t/src/abbreviations.jl:391
 [38] formatdoc(::Base.GenericIOBuffer{Array{UInt8,1}}, ::Base.Docs.DocStr, ::DocStringExtensions.TypedMethodSignatures) at /Users/USER/.julia/packages/DocStringExtensions/c3W3t/src/abbreviations.jl:25
 [39] format(::DocStringExtensions.Template{:before}, ::Base.GenericIOBuffer{Array{UInt8,1}}, ::Base.Docs.DocStr) at /Users/USER/.julia/packages/DocStringExtensions/c3W3t/src/abbreviations.jl:639
 [40] formatdoc(::Base.GenericIOBuffer{Array{UInt8,1}}, ::Base.Docs.DocStr, ::DocStringExtensions.Template{:before}) at /Users/USER/.julia/packages/DocStringExtensions/c3W3t/src/abbreviations.jl:25
 [41] formatdoc(::Base.Docs.DocStr) at /Users/julia/buildbot/worker/package_macos64/build/usr/share/julia/stdlib/v1.5/REPL/src/docview.jl:83
 [42] parsedoc(::Base.Docs.DocStr) at /Users/julia/buildbot/worker/package_macos64/build/usr/share/julia/stdlib/v1.5/REPL/src/docview.jl:91
 [43] iterate at ./generator.jl:47 [inlined]
 [44] _collect(::Array{Base.Docs.DocStr,1}, ::Base.Generator{Array{Base.Docs.DocStr,1},typeof(Base.Docs.parsedoc)}, ::Base.EltypeUnknown, ::Base.HasShape{1}) at ./array.jl:699
 [45] collect_similar at ./array.jl:628 [inlined]
 [46] map at ./abstractarray.jl:2162 [inlined]
 [47] doc(::Base.Docs.Binding, ::Type{T} where T) at /Users/julia/buildbot/worker/package_macos64/build/usr/share/julia/stdlib/v1.5/REPL/src/docview.jl:185
 [48] doc(::Base.Docs.Binding) at /Users/julia/buildbot/worker/package_macos64/build/usr/share/julia/stdlib/v1.5/REPL/src/docview.jl:153
 [49] top-level scope at /Users/julia/buildbot/worker/package_macos64/build/usr/share/julia/stdlib/v1.5/REPL/src/docview.jl:438

I'll take a closer look at this when I get the chance.

Related: https://github.com/JuliaDocs/DocStringExtensions.jl/pull/88

kdheepak avatar Aug 19 '20 20:08 kdheepak

A better solution is to pass the right typesig to Base.return_types.

Yes, I'd prefer that to using try as a form of control flow here. It should definitely be possible to extract the correct signature out of typesig.

MichaelHatherly avatar Aug 20 '20 08:08 MichaelHatherly