Skip to content

Commit e5beb8a

Browse files
committed
Extend CallInfo interface with add_uncovered_edges!
We need to add MT edges for any (handled, but) not fully-covered edges in the union-split of a `CallInfo`
1 parent b5e10c8 commit e5beb8a

File tree

5 files changed

+23
-11
lines changed

5 files changed

+23
-11
lines changed

base/compiler/abstractinterpretation.jl

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -331,15 +331,15 @@ function find_union_split_method_matches(interp::AbstractInterpreter, argtypes::
331331
end
332332
valid_worlds = intersect(valid_worlds, matches.valid_worlds)
333333
thisfullmatch = any(match::MethodMatch->match.fully_covers, matches)
334-
found = false
334+
mt_found = false
335335
for (i, mt′) in enumerate(mts)
336336
if mt′ === mt
337337
fullmatches[i] &= thisfullmatch
338-
found = true
338+
mt_found = true
339339
break
340340
end
341341
end
342-
if !found
342+
if !mt_found
343343
push!(mts, mt)
344344
push!(fullmatches, thisfullmatch)
345345
end

base/compiler/ssair/inlining.jl

Lines changed: 1 addition & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1399,14 +1399,7 @@ function compute_inlining_cases(@nospecialize(info::CallInfo), flag::UInt32, sig
13991399
if !fully_covered
14001400
atype = argtypes_to_type(sig.argtypes)
14011401
# We will emit an inline MethodError so we need a backedge to the MethodTable
1402-
unwrapped_info = info isa ConstCallInfo ? info.call : info
1403-
if unwrapped_info isa UnionSplitInfo
1404-
for (fullmatch, mt) in zip(unwrapped_info.fullmatches, unwrapped_info.mts)
1405-
!fullmatch && push!(state.edges, mt, atype)
1406-
end
1407-
elseif unwrapped_info isa MethodMatchInfo
1408-
push!(state.edges, unwrapped_info.mt, atype)
1409-
else @assert false end
1402+
add_uncovered_edges!(state.edges, info, atype)
14101403
end
14111404
elseif !isempty(cases)
14121405
# if we've not seen all candidates, union split is valid only for dispatch tuples

base/compiler/stmtinfo.jl

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,7 @@ end
3939
nsplit_impl(info::MethodMatchInfo) = 1
4040
getsplit_impl(info::MethodMatchInfo, idx::Int) = (@assert idx == 1; info.results)
4141
getresult_impl(::MethodMatchInfo, ::Int) = nothing
42+
add_uncovered_edges_impl(edges::Vector{Any}, info::MethodMatchInfo, @nospecialize(atype)) = (!info.fullmatch && push!(edges, info.mt, atype); )
4243

4344
"""
4445
info::UnionSplitInfo <: CallInfo
@@ -66,6 +67,11 @@ end
6667
nsplit_impl(info::UnionSplitInfo) = length(info.matches)
6768
getsplit_impl(info::UnionSplitInfo, idx::Int) = info.matches[idx]
6869
getresult_impl(::UnionSplitInfo, ::Int) = nothing
70+
function add_uncovered_edges_impl(edges::Vector{Any}, info::UnionSplitInfo, @nospecialize(atype))
71+
for (mt, fullmatch) in zip(info.mts, info.fullmatches)
72+
!fullmatch && push!(edges, mt, atype)
73+
end
74+
end
6975

7076
abstract type ConstResult end
7177

@@ -109,6 +115,7 @@ end
109115
nsplit_impl(info::ConstCallInfo) = nsplit(info.call)
110116
getsplit_impl(info::ConstCallInfo, idx::Int) = getsplit(info.call, idx)
111117
getresult_impl(info::ConstCallInfo, idx::Int) = info.results[idx]
118+
add_uncovered_edges_impl(edges::Vector{Any}, info::ConstCallInfo, @nospecialize(atype)) = add_uncovered_edges!(edges, info.call, atype)
112119

113120
"""
114121
info::MethodResultPure <: CallInfo

base/compiler/types.jl

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -451,9 +451,12 @@ abstract type CallInfo end
451451
nsplit(info::CallInfo) = nsplit_impl(info)::Union{Nothing,Int}
452452
getsplit(info::CallInfo, idx::Int) = getsplit_impl(info, idx)::MethodLookupResult
453453
getresult(info::CallInfo, idx::Int) = getresult_impl(info, idx)
454+
add_uncovered_edges!(edges::Vector{Any}, info::CallInfo, @nospecialize(atype)) = add_uncovered_edges_impl(edges, info, atype)
455+
454456

455457
nsplit_impl(::CallInfo) = nothing
456458
getsplit_impl(::CallInfo, ::Int) = error("unexpected call into `getsplit`")
457459
getresult_impl(::CallInfo, ::Int) = nothing
460+
add_uncovered_edges_impl(edges::Vector{Any}, info::CallInfo, @nospecialize(atype)) = nothing
458461

459462
@specialize

test/compiler/AbstractInterpreter.jl

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -409,6 +409,7 @@ end
409409
CC.nsplit_impl(info::NoinlineCallInfo) = CC.nsplit(info.info)
410410
CC.getsplit_impl(info::NoinlineCallInfo, idx::Int) = CC.getsplit(info.info, idx)
411411
CC.getresult_impl(info::NoinlineCallInfo, idx::Int) = CC.getresult(info.info, idx)
412+
CC.add_uncovered_edges_impl(edges::Vector{Any}, info::NoinlineCallInfo, @nospecialize(atype)) = CC.add_uncovered_edges!(edges, info.info, atype)
412413

413414
function CC.abstract_call(interp::NoinlineInterpreter,
414415
arginfo::CC.ArgInfo, si::CC.StmtInfo, sv::CC.InferenceState, max_methods::Int)
@@ -431,6 +432,8 @@ end
431432
@inline function inlined_usually(x, y, z)
432433
return x * y + z
433434
end
435+
foo_split(x::Float64) = 1
436+
foo_split(x::Int) = 2
434437

435438
# check if the inlining algorithm works as expected
436439
let src = code_typed1((Float64,Float64,Float64)) do x, y, z
@@ -444,6 +447,7 @@ let NoinlineModule = Module()
444447
main_func(x, y, z) = inlined_usually(x, y, z)
445448
@eval NoinlineModule noinline_func(x, y, z) = $inlined_usually(x, y, z)
446449
@eval OtherModule other_func(x, y, z) = $inlined_usually(x, y, z)
450+
@eval NoinlineModule bar_split_error() = $foo_split(Core.compilerbarrier(:type, nothing))
447451

448452
interp = NoinlineInterpreter(Set((NoinlineModule,)))
449453

@@ -473,6 +477,11 @@ let NoinlineModule = Module()
473477
@test count(isinvoke(:inlined_usually), src.code) == 0
474478
@test count(iscall((src, inlined_usually)), src.code) == 0
475479
end
480+
481+
let src = code_typed1(NoinlineModule.bar_split_error)
482+
@test count(iscall((src, foo_split)), src.code) == 0
483+
@test count(iscall((src, Core.throw_methoderror)), src.code) > 0
484+
end
476485
end
477486

478487
# Make sure that Core.Compiler has enough NamedTuple infrastructure

0 commit comments

Comments
 (0)