Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Random.__init__() and Base.PCRE.__init__() may be required in Julia >= 1.3 #277

Closed
tkf opened this issue Sep 22, 2019 · 14 comments · Fixed by #304
Closed

Random.__init__() and Base.PCRE.__init__() may be required in Julia >= 1.3 #277

tkf opened this issue Sep 22, 2019 · 14 comments · Fixed by #304

Comments

@tkf
Copy link
Member

tkf commented Sep 22, 2019

FYI:

@asinghvi17
Copy link
Contributor

Interesting. Do they use any of the stdlib's functionality that other packages don't? Makie, for example, while depending on Random, gets by without needing Random.__init__().

@tkf
Copy link
Member Author

tkf commented Sep 22, 2019

If you only require Random and don't call its functions in the --output-o mode, it should be fine. Pkg seems to call shuffle!.

@asinghvi17
Copy link
Contributor

asinghvi17 commented Sep 23, 2019

https://github.com/JuliaLang/julia/blob/784eb57a06aaab95bc4c22f288bd0c9f2b1687ca/stdlib/Random/src/RNGs.jl#L307-L309
is Random.__init__(). It seems like it would fix your issue...not sure what the fix would be on master, though.

const packages_needing_initialization = [:GR, :Unitful]

is what you could edit in sd-notomls.

@tkf
Copy link
Member Author

tkf commented Sep 23, 2019

Thanks, I know why it's causing the trouble and how to work-around the problem (it's already implemented). I should have clarified in the OP that I'm just reporting it because I thought that PackageCompiler.jl maintainers may be interested in incorporating the fix. Like Base.__init__ and Sys.__init__, it is probably a good idea to call them as early as possible.

@KristofferC
Copy link
Member

Out of curiosity, what ends up calling shuffle! in Pkg when output-o is active?

@tkf
Copy link
Member Author

tkf commented Oct 17, 2019

Here is the traceback of the error
https://travis-ci.org/JuliaPy/PyCall.jl/jobs/585892454#L803-L808

Note that PyCall is not using PackageCompiler's snoop-based API because of JuliaLang/julia#31156. It has a custom script for testing sysimage compatibility: https://github.com/JuliaPy/PyCall.jl/blob/9f4387535936f275e3582ebdc87cc2ef1f210030/aot/precompile.jl

Actually, looking at the traceback, it looks like shuffle! is not called via Pkg.jl since the signature is shuffle!(::Array{Symbol,1}). It looks like it is happening via jl_load_ C API so I'm not sure what is going on. Sorry about blaming Pkg.jl without enough investigation.

@KristofferC
Copy link
Member

But that should run in a normal process (without --output-o) but with the --trace-compile flag active. The collected precompile statements are then what is run in the process doing output, but that doesn't run any code.

@tkf
Copy link
Member Author

tkf commented Oct 18, 2019

I know that's the ideal/correct way but as I said snooping generated a precompile statement that broke --output-o (at least in Julia <= 1.1).

But that's what I wanted to look into. Provided that PackageCompiler.jl is invoking __init__ of packages, I thought that was necessary for invoking all top-level statements of downstream packages. I have to admit I was puzzled why that's necessary since in principle the evaluated result of the top level code can be de-serialized from the precompilation cache. I knew I had to look into what's going on inside --output-o process but at the same time I needed a working solution... So, the ad-hoc (maybe incorrect) solution I've been using is to execute code in --output-o process and try to cleanup non-serializable states via atexit_hooks.

@tkf
Copy link
Member Author

tkf commented Oct 18, 2019

JuliaLang/julia#31156 is still reproducible with Julia 1.4-DEV.

@IanButterworth
Copy link
Member

PackageCompiler is highly reliable for me, but I just hit a glitch with this that looks exactly like JuliaLang/julia#33471, without changing anything in the setup

julia 1.6.3

ERROR: LoadError: LoadError: AssertionError: 0 < tid <= length(THREAD_RNGs)
Stacktrace:
  [1] _rng_length_assert()
    @ Random /buildworker/worker/package_linux64/build/usr/share/julia/stdlib/v1.6/Random/src/RNGs.jl:381
  [2] default_rng(tid::Int64)
    @ Random /buildworker/worker/package_linux64/build/usr/share/julia/stdlib/v1.6/Random/src/RNGs.jl:372
  [3] default_rng
    @ /buildworker/worker/package_linux64/build/usr/share/julia/stdlib/v1.6/Random/src/RNGs.jl:370 [inlined]
  [4] rand! (repeats 2 times)
    @ /buildworker/worker/package_linux64/build/usr/share/julia/stdlib/v1.6/Random/src/Random.jl:264 [inlined]
  [5] _rand(#unused#::Type{ColorTypes.Gray{FixedPointNumbers.N0f8}}, sz::Tuple{Int64, Int64})
    @ ColorTypes ~/.julia/packages/ColorTypes/6m8P7/src/operations.jl:97
  [6] rand
    @ ~/.julia/packages/ColorTypes/6m8P7/src/operations.jl:120 [inlined]
  [7] rand(#unused#::Type{ColorTypes.Gray{FixedPointNumbers.N0f8}}, d::Int64, dims::Int64)
    @ Random /buildworker/worker/package_linux64/build/usr/share/julia/stdlib/v1.6/Random/src/Random.jl:292
  [8] (::TiffImages.var"#14#15")(fpath::String, #unused#::IOStream)
    @ TiffImages ~/.julia/packages/TiffImages/XzftO/src/TiffImages.jl:40
  [9] mktemp(fn::TiffImages.var"#14#15", parent::String)
    @ Base.Filesystem ./file.jl:703
 [10] mktemp(fn::Function)
    @ Base.Filesystem ./file.jl:701
 [11] top-level scope
    @ ~/.julia/packages/TiffImages/XzftO/src/TiffImages.jl:37
 [12] include
    @ ./Base.jl:386 [inlined]
 [13] _require(pkg::Base.PkgId)
    @ Base ./loading.jl:1072
 [14] require(uuidkey::Base.PkgId)
    @ Base ./loading.jl:936

@KristofferC
Copy link
Member

This happens when for some reason the package fails to get precompiled before the sysimage is attempted to be created. If the package is not precompiled, Julia will try to run all toplevel code and if that includes a call to rand it will fail because the process generating the sysimage does not run __init__ methods and Random.__init__ is required for a functional RNG.

function ensurecompiled(project, packages, sysimage)
length(packages) == 0 && return
# TODO: Only precompile `packages` (should be available in Pkg 1.8)
cmd = `$(get_julia_cmd()) --sysimage=$sysimage -e 'using Pkg; Pkg.precompile()'`
splitter = Sys.iswindows() ? ';' : ':'
cmd = addenv(cmd, "JULIA_LOAD_PATH" => "$project$(splitter)@stdlib")
run(cmd)
return
end

is meant to ensure everything gets precompiled.

@IanButterworth
Copy link
Member

The error I saw was repeatable on that setup after I first hit it, until I wiped the depot compiled and packages dirs.
Perhaps there was something somehow precompiled with a glitch that was too subtle for stalecache to detect it, but loading to consider it unusable..?

@KristofferC
Copy link
Member

Running with ENV["JULIA_DEBIG"] = "loading" might have given some clue?

@IanButterworth
Copy link
Member

If I come across it again I will. This was a device in the field so didn't have much debug time

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
4 participants