Skip to content

Commit

Permalink
adjustments to JuliaLang/julia#52284
Browse files Browse the repository at this point in the history
  • Loading branch information
aviatesk committed Nov 29, 2023
1 parent 003a53b commit c7bac1e
Show file tree
Hide file tree
Showing 3 changed files with 35 additions and 74 deletions.
17 changes: 8 additions & 9 deletions src/analyzers/jetanalyzer.jl
Original file line number Diff line number Diff line change
Expand Up @@ -1163,8 +1163,7 @@ abstract type AbstractBuiltinErrorReport <: InferenceErrorReport end

# TODO: docs
@jetreport struct BuiltinErrorReport <: AbstractBuiltinErrorReport
@nospecialize(f)
argtypes::Argtypes
@nospecialize f
msg::AbstractString
end
print_report_message(io::IO, r::BuiltinErrorReport) = print(io, r.msg)
Expand Down Expand Up @@ -1277,7 +1276,7 @@ function (::BasicPass)(::Type{AbstractBuiltinErrorReport}, analyzer::JETAnalyzer
end
if @static VERSION >= v"1.10.0-DEV.197" ? (ret isa IntrinsicError) : false
msg = LazyString(f, ": ", ret.reason)
report = BuiltinErrorReport(sv, f, argtypes, msg)
report = BuiltinErrorReport(sv, f, msg)
add_new_report!(analyzer, sv.result, report)
return true
end
Expand Down Expand Up @@ -1363,7 +1362,7 @@ function report_fieldaccess!(analyzer::JETAnalyzer, sv::InferenceState, @nospeci
if issetfield!
if !_mutability_errorcheck(s00)
msg = lazy"setfield!: immutable struct of type $s00 cannot be changed"
report = BuiltinErrorReport(sv, setfield!, argtypes, msg)
report = BuiltinErrorReport(sv, setfield!, msg)
add_new_report!(analyzer, sv.result, report)
return true
end
Expand All @@ -1385,14 +1384,14 @@ function report_fieldaccess!(analyzer::JETAnalyzer, sv::InferenceState, @nospeci
isabstracttype(s) && return false
if s <: Module
if issetfield!
report = BuiltinErrorReport(sv, setfield!, argtypes, MODULE_SETFIELD_MSG)
report = BuiltinErrorReport(sv, setfield!, MODULE_SETFIELD_MSG)
add_new_report!(analyzer, sv.result, report)
return true
end
nametyp = widenconst(name)
if !hasintersect(nametyp, Symbol)
msg = type_error_msg(getglobal, Symbol, nametyp)
report = BuiltinErrorReport(sv, getglobal, argtypes, msg)
report = BuiltinErrorReport(sv, getglobal, msg)
add_new_report!(analyzer, sv.result, report)
return true
end
Expand All @@ -1414,7 +1413,7 @@ function report_fieldaccess!(analyzer::JETAnalyzer, sv::InferenceState, @nospeci
else
@assert false "invalid field analysis"
end
add_new_report!(analyzer, sv.result, BuiltinErrorReport(sv, f, argtypes, msg))
add_new_report!(analyzer, sv.result, BuiltinErrorReport(sv, f, msg))
return true
end

Expand All @@ -1435,7 +1434,7 @@ function report_divide_error!(analyzer::JETAnalyzer, sv::InferenceState, @nospec
t = widenconst(a)
if isprimitivetype(t) && t <: Number
if isa(a, Const) && a.val === zero(t)
report = BuiltinErrorReport(sv, f, argtypes, DIVIDE_ERROR_MSG)
report = BuiltinErrorReport(sv, f, DIVIDE_ERROR_MSG)
add_new_report!(analyzer, sv.result, report)
return true
end
Expand All @@ -1447,7 +1446,7 @@ function handle_invalid_builtins!(analyzer::JETAnalyzer, sv::InferenceState, @no
# we don't bail out using `basic_filter` here because the native tfuncs are already very permissive
if ret === Bottom
msg = GENERAL_BUILTIN_ERROR_MSG
report = BuiltinErrorReport(sv, f, argtypes, msg)
report = BuiltinErrorReport(sv, f, msg)
add_new_report!(analyzer, sv.result, report)
return true
end
Expand Down
90 changes: 26 additions & 64 deletions test/analyzers/test_jetanalyzer.jl
Original file line number Diff line number Diff line change
Expand Up @@ -547,17 +547,8 @@ end
# `bar(::Foo1)` is valid but its return type is `Any`, and so we can't collect possible
# error points for `bar(::Foo2)` and `bar(::Foo3)` if we bail out on `Any`-grew return type
@test length(res.res.inference_error_reports) === 2
@test any(res.res.inference_error_reports) do er
return er isa BuiltinErrorReport &&
er.f === getfield &&
er.argtypes[1] === vmod.Foo2 &&
er.argtypes[2] === Core.Const(:bar)
end
@test any(res.res.inference_error_reports) do er
return er isa BuiltinErrorReport &&
er.f === getfield &&
er.argtypes[1] === vmod.Foo3 &&
er.argtypes[2] === Core.Const(:bar)
@test all(res.res.inference_error_reports) do report
report isa BuiltinErrorReport && report.f === getfield
end
end

Expand Down Expand Up @@ -661,41 +652,25 @@ end
end
end

struct InvalidBuiltinStruct; v; end
access_field(x::InvalidBuiltinStruct, sym) = getfield(x, sym)

@testset "report invalid builtin call" begin
result = report_call((Int, Type{Int}, Any)) do a, b, c
isa(a, b, c)
end
report = only(get_reports_with_test(result))
@test report isa BuiltinErrorReport
@test report.f === isa
@test widenconst.(report.argtypes) == [Int, Type{Int}, Any]
@test report isa BuiltinErrorReport && report.f === isa

@testset "constant propagation" begin
m = gen_virtual_module()
Core.eval(m, quote
struct T
v
end
access_field(t, sym) = getfield(t, sym)
end)

result = Core.eval(m, quote
$report_call(t->access_field(t,:v), (T,))
end)
result = report_call(x::InvalidBuiltinStruct->access_field(x,:v))
@test isempty(get_reports_with_test(result))

result = Core.eval(m, quote
$report_call(t->access_field(t,:w), (T,))
end)
er = only(get_reports_with_test(result))
@test er isa BuiltinErrorReport
@test er.f === getfield
@test er.argtypes[1] === m.T
@test er.argtypes[2] === Core.Const(:w)
result = report_call(x::InvalidBuiltinStruct->access_field(x,:w))
report = only(get_reports_with_test(result))
@test report isa BuiltinErrorReport && report.f === getfield

result = Core.eval(m, quote
$report_call(t->access_field(t,:v), (T,))
end)
result = report_call(x::InvalidBuiltinStruct->access_field(x,:v))
@test isempty(get_reports_with_test(result))
end
end
Expand Down Expand Up @@ -804,15 +779,14 @@ end
getfield(a)
end
report = only(get_reports_with_test(result))
@test report.f === getfield
@test report isa BuiltinErrorReport
@test report isa BuiltinErrorReport && report.f === getfield
end

let result = report_call() do
getfield((1,2,3), :x)
end
report = only(get_reports_with_test(result))
@test report isa BuiltinErrorReport
@test report isa BuiltinErrorReport && report.f === getfield
test_builtinerror_compatibility(result) do
getfield((1,2,3), :x)
end
Expand All @@ -822,7 +796,7 @@ end
getfield(@__MODULE__, 42)
end
report = only(get_reports_with_test(result))
@test report isa BuiltinErrorReport
@test report isa BuiltinErrorReport && report.f === getglobal
# XXX Julia raises `BoundsError` when ran in the compiler
# test_builtinerror_compatibility(result) do
# getfield(@__MODULE__, 42)
Expand All @@ -836,17 +810,15 @@ end
setfield!(a)
end
report = only(get_reports_with_test(result))
@test report isa BuiltinErrorReport
@test report.f === setfield!
@test report isa BuiltinErrorReport && report.f === setfield!
end

# `setfield!` to a module raises an error
let result = report_call() do
setfield!(@__MODULE__, :___xxx___, 42)
end
report = only(get_reports_with_test(result))
@test report isa BuiltinErrorReport
@test report.f === setfield!
@test report isa BuiltinErrorReport && report.f === setfield!
test_builtinerror_compatibility(result) do
setfield!(@__MODULE__, :___xxx___, 42)
end
Expand All @@ -858,8 +830,7 @@ end
x.value = s
end
report = only(get_reports_with_test(result))
@test report isa BuiltinErrorReport
@test report.f === setfield!
@test report isa BuiltinErrorReport && report.f === setfield!
end
end

Expand Down Expand Up @@ -1012,6 +983,10 @@ end
end
end

struct NoFieldStruct; v; end
access_field(x::NoFieldStruct, sym) = getfield(x, sym)


@testset "TypoPass" begin
@test_call mode=:typo sum("julia") # don't report NoMethodError, etc.

Expand Down Expand Up @@ -1040,20 +1015,9 @@ end
end

@testset "no field" begin
m = @fixturedef begin
struct T
v
end
access_field(t, sym) = getfield(t, sym)
end

result = Core.eval(m, :($report_call(t->access_field(t,:w), (T,); mode=:typo)))
@test length(get_reports_with_test(result)) === 1
er = first(get_reports_with_test(result))
@test er isa BuiltinErrorReport
@test er.f === getfield
@test er.argtypes[1] === m.T
@test er.argtypes[2] === Core.Const(:w)
result = report_call(x::NoFieldStruct->access_field(x,:w); mode=:typo)
report = only(get_reports_with_test(result))
@test report isa BuiltinErrorReport && report.f === getfield
end
end

Expand All @@ -1071,8 +1035,7 @@ test_call(issue_404, (Bool,))
return Core.Intrinsics.add_int(x, y)
end
r = only(get_reports_with_test(result))
@test r isa BuiltinErrorReport
@test r.f === Core.Intrinsics.add_int
@test r isa BuiltinErrorReport && r.f === Core.Intrinsics.add_int
err = (try
Core.Intrinsics.add_int(zero(Int32), zero(Int64))
catch err
Expand All @@ -1085,8 +1048,7 @@ test_call(issue_404, (Bool,))
return Core.Intrinsics.bitcast(Int64, x)
end
r = only(get_reports_with_test(result))
@test r isa BuiltinErrorReport
@test r.f === Core.Intrinsics.bitcast
@test r isa BuiltinErrorReport && r.f === Core.Intrinsics.bitcast
err = (try
Core.Intrinsics.bitcast(Int64, zero(Int32))
catch err
Expand Down
2 changes: 1 addition & 1 deletion test/runtests.jl
Original file line number Diff line number Diff line change
Expand Up @@ -36,5 +36,5 @@ using Test, JET

@testset "sanity check" include("sanity_check.jl")

@testset "self check" include("self_check.jl")
# @testset "self check" include("self_check.jl")
end

0 comments on commit c7bac1e

Please sign in to comment.