diff --git a/Compiler/src/tfuncs.jl b/Compiler/src/tfuncs.jl index 7cac43e642117..ed7c830984a92 100644 --- a/Compiler/src/tfuncs.jl +++ b/Compiler/src/tfuncs.jl @@ -2425,10 +2425,6 @@ const _INCONSISTENT_INTRINSICS = Any[ # Intrinsics.muladd_float, # this is not interprocedurally consistent ] -const _SPECIAL_BUILTINS = Any[ - Core._apply_iterate, -] - # Intrinsics that require all arguments to be floats const _FLOAT_INTRINSICS = Any[ Intrinsics.neg_float, @@ -2535,6 +2531,71 @@ function getfield_effects(𝕃::AbstractLattice, argtypes::Vector{Any}, @nospeci return Effects(EFFECTS_TOTAL; consistent, nothrow, inaccessiblememonly, noub) end +# add a new builtin function to this list only after making sure that +# `builtin_effects` is properly implemented for it +const _EFFECTS_KNOWN_BUILTINS = Any[ + <:, + ===, + # Core._abstracttype, + # _apply_iterate, + # Core._call_in_world_total, + # Core._compute_sparams, + # Core._defaultctors, + # Core._equiv_typedef, + Core._expr, + # Core._primitivetype, + # Core._setsuper!, + # Core._structtype, + # Core._svec_ref, + # Core._typebody!, + Core._typevar, + apply_type, + compilerbarrier, + Core.current_scope, + donotdelete, + Core.finalizer, + Core.get_binding_type, + Core.ifelse, + # Core.invoke_in_world, + # invokelatest, + Core.memorynew, + memoryref_isassigned, + memoryrefget, + # Core.memoryrefmodify!, + memoryrefnew, + memoryrefoffset, + # Core.memoryrefreplace!, + memoryrefset!, + # Core.memoryrefsetonce!, + # Core.memoryrefswap!, + Core.sizeof, + svec, + Core.throw_methoderror, + applicable, + fieldtype, + getfield, + getglobal, + # invoke, + isa, + isdefined, + # isdefinedglobal, + modifyfield!, + # modifyglobal!, + nfields, + replacefield!, + # replaceglobal!, + setfield!, + # setfieldonce!, + # setglobal!, + # setglobalonce!, + swapfield!, + # swapglobal!, + throw, + tuple, + typeassert, + typeof +] + """ builtin_effects(𝕃::AbstractLattice, f::Builtin, argtypes::Vector{Any}, rt) -> Effects @@ -2545,7 +2606,9 @@ function builtin_effects(𝕃::AbstractLattice, @nospecialize(f::Builtin), argty return intrinsic_effects(f, argtypes) end - @assert !contains_is(_SPECIAL_BUILTINS, f) + if !(f in _EFFECTS_KNOWN_BUILTINS) + return Effects() + end if f === getfield return getfield_effects(𝕃, argtypes, rt) diff --git a/Compiler/test/effects.jl b/Compiler/test/effects.jl index ce2f94b8e355a..49a9628ba97c5 100644 --- a/Compiler/test/effects.jl +++ b/Compiler/test/effects.jl @@ -1461,3 +1461,9 @@ end let effects = Base.infer_effects(Base._unsetindex!, (MemoryRef{String},)) @test !Compiler.is_effect_free(effects) end + +# builtin functions that can do arbitrary things should have the top effects +@test Base.infer_effects(Core._call_in_world_total, Tuple{Vararg{Any}}) == Compiler.Effects() +@test Base.infer_effects(Core.invoke_in_world, Tuple{Vararg{Any}}) == Compiler.Effects() +@test Base.infer_effects(invokelatest, Tuple{Vararg{Any}}) == Compiler.Effects() +@test Base.infer_effects(invoke, Tuple{Vararg{Any}}) == Compiler.Effects()