Revision a121721f975fc4105ed24ebd0ad1020d08d07a38 authored by Shuhei Kadowaki on 01 November 2021, 10:49:07 UTC, committed by GitHub on 01 November 2021, 10:49:07 UTC
* inference: form `PartialStruct` for extra type information propagation This commit forms `PartialStruct` whenever there is any type-level refinement available about a field, even if it's not "constant" information. In Julia "definitions" are allowed to be abstract whereas "usages" (i.e. callsites) are often concrete. The basic idea is to allow inference to make more use of such precise callsite type information by encoding it as `PartialStruct`. This may increase optimization possibilities of "unidiomatic" Julia code, which may contain poorly-typed definitions, like this very contrived example: ```julia struct Problem n; s; c; t end function main(args...) prob = Problem(args...) s = 0 for i in 1:prob.n m = mod(i, 3) s += m == 0 ? sin(prob.s) : m == 1 ? cos(prob.c) : tan(prob.t) end return prob, s end main(10000, 1, 2, 3) ``` One of the obvious limitation is that this extra type information can be propagated inter-procedurally only as a const-propagation. I'm not sure this kind of "just a type-level" refinement can often make constant-prop' successful (i.e. shape-up a method body and allow it to be inlined, encoding the extra type information into the generated code), thus I didn't not modify any part of const-prop' heuristics. So the improvements from this change might not be very useful for general inter-procedural analysis currently, but they should definitely improve the accuracy of local analysis and very simple inter-procedural analysis.
1 parent 6c274ed
options.jl
# This file is a part of Julia. License is MIT: https://julialang.org/license
# NOTE: This type needs to be kept in sync with jl_options in src/julia.h
struct JLOptions
quiet::Int8
banner::Int8
julia_bindir::Ptr{UInt8}
julia_bin::Ptr{UInt8}
commands::Ptr{Ptr{UInt8}} # (e)eval, (E)print, (L)load
image_file::Ptr{UInt8}
cpu_target::Ptr{UInt8}
nthreads::Int32
nprocs::Int32
machine_file::Ptr{UInt8}
project::Ptr{UInt8}
isinteractive::Int8
color::Int8
historyfile::Int8
startupfile::Int8
compile_enabled::Int8
code_coverage::Int8
malloc_log::Int8
opt_level::Int8
opt_level_min::Int8
debug_level::Int8
check_bounds::Int8
depwarn::Int8
warn_overwrite::Int8
can_inline::Int8
polly::Int8
trace_compile::Ptr{UInt8}
fast_math::Int8
worker::Int8
cookie::Ptr{UInt8}
handle_signals::Int8
use_sysimage_native_code::Int8
use_compiled_modules::Int8
bindto::Ptr{UInt8}
outputbc::Ptr{UInt8}
outputunoptbc::Ptr{UInt8}
outputo::Ptr{UInt8}
outputasm::Ptr{UInt8}
outputji::Ptr{UInt8}
output_code_coverage::Ptr{UInt8}
incremental::Int8
image_file_specified::Int8
warn_scope::Int8
image_codegen::Int8
rr_detach::Int8
end
# This runs early in the sysimage != is not defined yet
if sizeof(JLOptions) === ccall(:jl_sizeof_jl_options, Int, ())
else
ccall(:jl_throw, Cvoid, (Any,), "Option structure mismatch")
end
JLOptions() = unsafe_load(cglobal(:jl_options, JLOptions))
function show(io::IO, opt::JLOptions)
print(io, "JLOptions(")
fields = fieldnames(JLOptions)
nfields = length(fields)
for (i, f) in enumerate(fields)
v = getfield(opt, i)
if isa(v, Ptr{UInt8})
v = (v != C_NULL) ? unsafe_string(v) : ""
elseif isa(v, Ptr{Ptr{UInt8}})
v = unsafe_load_commands(v)
end
print(io, f, " = ", repr(v), i < nfields ? ", " : "")
end
print(io, ")")
end
function unsafe_load_commands(v::Ptr{Ptr{UInt8}})
cmds = Pair{Char, String}[]
v == C_NULL && return cmds
i = 1
while true
s = unsafe_load(v, i)
s == C_NULL && break
e = Char(unsafe_load(s))
push!(cmds, e => unsafe_string(s + 1))
i += 1
end
return cmds
end
Computing file changes ...