Skip to content

Overload of Base.iterate making broadcast type unstable #14

@islent

Description

@islent
module Test

import Base: length, iterate, real

abstract type AbstractType{T} end

@inline length(p::T) where T <: AbstractType = 1
@inline iterate(p::T) where T <: AbstractType = (p,nothing)
#@inline iterate(p::T,st) where T <: AbstractType = nothing
@inline real(p::T) where T <: AbstractType = p

end # module Test


import .Test.AbstractType

struct S{T<:Number} <: AbstractType{T}
    x::T
end

test(x, y) = x

@code_warntype test.(S(0), [0])

Gives output:

julia> @code_warntype test.(S(0), [0])
Variables
  #self#::Core.Const(var"##dotfunction#245#5"())
  x1::S{Int64}     
  x2::Vector{Int64}

Body::Union{}
1 ─     Base.broadcasted(Main.test, x1, x2)
│       Core.Const(:(Base.materialize(%1)))
└──     Core.Const(:(return %2))

If uncomment @inline iterate(p::T,st) where T <: AbstractType = nothing, it gives a type unstable warning:

julia> @code_warntype test.(S(0), [0])
Variables
  #self#::Core.Const(var"##dotfunction#245#5"())
  x1::S{Int64}     
  x2::Vector{Int64}

Body::AbstractVector{var"#s827"} where var"#s827"
1%1 = Base.broadcasted(Main.test, x1, x2)::Base.Broadcast.Broadcasted{Base.Broadcast.DefaultArrayStyle{1}, Nothing, typeof(test), Tuple{Vector{Any}, Vector{Int64}}}%2 = Base.materialize(%1)::AbstractVector{var"#s827"} where var"#s827"
└──      return %2
julia> versioninfo()
Julia Version 1.6.0-beta1.0
Commit b84990e1ac (2021-01-08 12:42 UTC)
Platform Info:
  OS: Windows (x86_64-w64-mingw32)
  CPU: Intel(R) Xeon(R) W-10885M CPU @ 2.40GHz
  WORD_SIZE: 64
  LIBM: libopenlibm
  LLVM: libLLVM-11.0.0 (ORCJIT, skylake)
Environment:
  JULIA_DEPOT_PATH = E:\.julia
  JULIA_NUM_THREADS = 4
  JULIA_EDITOR = "D:\Programs\Microsoft VS Code\Code.exe"

julia 1.7.0-DEV.334 gives unstable warning:

julia> @code_warntype test.(S(0), [0])
Variables
  #self#::Core.Const(var"##dotfunction#257#1"())
  x1::S{Int64}
  x2::Vector{Int64}

Body::AbstractVector{var"#s829"} where var"#s829"
1%1 = Base.broadcasted(Main.test, x1, x2)::Base.Broadcast.Broadcasted{Base.Broadcast.DefaultArrayStyle{1}, Nothing, typeof(test), Tuple{Vector{Any}, Vector{Int64}}}%2 = Base.materialize(%1)::AbstractVector{var"#s829"} where var"#s829"
└──      return %2

julia 1.5.2 gives a different unstable warning:

julia> @code_warntype test.(S(0), [0])
Variables
  #self#::Core.Compiler.Const(var"##dotfunction#253#1"(), false)
  x1::S{Int64}
  x2::Array{Int64,1}

Body::Union{BitArray{1}, Array}
1%1 = Base.broadcasted(Main.test, x1, x2)::Base.Broadcast.Broadcasted{Base.Broadcast.DefaultArrayStyle{1},Nothing,typeof(test),Tuple{Array{Any,1},Array{Int64,1}}}%2 = Base.materialize(%1)::Union{BitArray{1}, Array}
└──      return %2

It seems that the compiler is confused with BitArray and Array.

Metadata

Metadata

Assignees

Labels

bugSomething isn't workinghelp wantedExtra attention is needed

Type

No type
No fields configured for issues without a type.

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions