Skip to content

Commit 4b13d15

Browse files
committed
Add support for specifying arch
E.g., for bundling for i686 on x86_64. Also, * Added support for being explicit about arch (if arch is not explicitly specified in PackageBundler.toml juliaup.channel field. * Added platform-dependent IntType to TestPackage, where Serialization fails to deserialize if WORD_SIZE differs from bundling arch to install arch.
1 parent c0ac7d6 commit 4b13d15

File tree

6 files changed

+159
-67
lines changed

6 files changed

+159
-67
lines changed

src/PackageBundler.jl

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -91,6 +91,9 @@ options, each of which are tried in turn until one is found that can be used to
9191
select the correct Julia version. If no multiplexer is found then the current
9292
`julia` is used.
9393
94+
The `arch_explicit` field is a boolean flag that determines whether the architecture
95+
used for bundling should be explicitly defined in the generated bundle.
96+
9497
The `handlers` field is a list of paths to handler scripts that are used to
9598
inject or transform code in the bundled packages. The handler scripts must be
9699
valid Julia files that return a `Function` accepting the required arguments as
@@ -109,6 +112,8 @@ listed below. The valid names for handlers are:
109112
function bundle(
110113
config::AbstractString = "PackageBundler.toml";
111114
clean::Bool = false,
115+
arch::Union{Symbol,Nothing} = nothing,
116+
arch_explicit::Bool = false,
112117
artifacts_url::Union{String,Nothing} = nothing,
113118
)
114119
config = abspath(config)
@@ -178,6 +183,9 @@ function bundle(
178183
# `julia_version`.
179184
multiplexers = String.(get(Vector{String}, config, "multiplexers"))
180185

186+
# Explicitly define the architecture used for bundling.
187+
arch_explicit = get(config, "arch_explicit", arch_explicit)::Bool
188+
181189
# Ensure handler scripts valid files and adjust paths to be absolute.
182190
handlers = Dict{String,String}()
183191
for file in String.(get(Vector{String}, config, "handlers"))
@@ -205,6 +213,8 @@ function bundle(
205213
key_pair = (; private, public),
206214
handlers = handlers,
207215
multiplexers = multiplexers,
216+
arch = arch,
217+
arch_explicit = arch_explicit,
208218
)
209219
for output in outputs
210220
output = normpath(joinpath(dir, output))

src/code_stripping.jl

Lines changed: 36 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,8 @@ function _generate_stripped_bundle(;
1111
key_pair::@NamedTuple{private::String, public::String},
1212
handlers::Dict,
1313
multiplexers::Vector{String},
14+
arch::Union{Symbol,Nothing} = nothing,
15+
arch_explicit::Bool = false,
1416
)
1517
output_dir = abspath(output_dir)
1618

@@ -31,6 +33,8 @@ function _generate_stripped_bundle(;
3133
key_pair = key_pair,
3234
handlers = handlers,
3335
multiplexers = multiplexers,
36+
arch = arch,
37+
arch_explicit = arch_explicit,
3438
)
3539

3640
for (k, v) in new_pkg_version_info
@@ -320,6 +324,8 @@ function _process_project_env(;
320324
key_pair::@NamedTuple{private::String, public::String},
321325
handlers::Dict,
322326
multiplexers::Vector{String},
327+
arch::Union{Symbol,Nothing} = nothing,
328+
arch_explicit::Bool = false
323329
)
324330
project_dir = normpath(project_dir)
325331
output_dir = normpath(output_dir)
@@ -349,7 +355,7 @@ function _process_project_env(;
349355
_sign_file(joinpath(named_environment, "Manifest.toml"), key_pair.private)
350356
write(joinpath(named_environment, basename(key_pair.public)), read(key_pair.public))
351357

352-
package_paths = _sniff_versions(project_dir, multiplexers)
358+
package_paths = _sniff_versions(project_dir, multiplexers, arch)
353359

354360
packagebundler_file = joinpath(project_dir, "PackageBundler.toml")
355361
packagebundler_toml =
@@ -358,6 +364,16 @@ function _process_project_env(;
358364
julia_version = TOML.parsefile(manifest_toml)["julia_version"]
359365
julia_version =
360366
get(get(Dict{String,Any}, packagebundler_toml, "juliaup"), "channel", julia_version)
367+
if arch_explicit
368+
packagebundler_toml = merge(packagebundler_toml, Dict(
369+
"juliaup" => Dict(
370+
"channel" => _juliaup_channel(julia_version, arch)
371+
)
372+
))
373+
open(joinpath(named_environment, "PackageBundler.toml"), "w") do io
374+
TOML.print(io, packagebundler_toml)
375+
end
376+
end
361377

362378
pkg_version_info = Dict()
363379
for (each_uuid, each_name) in stripped
@@ -374,6 +390,7 @@ function _process_project_env(;
374390
key_pair,
375391
handlers,
376392
multiplexers,
393+
arch,
377394
)
378395
versions = get!(Dict{String,Any}, pkg_version_info, each_name)
379396
versions[version_info["project"]["version"]] = version_info
@@ -395,14 +412,14 @@ end
395412
# "julia_version" => v"<version>"
396413
# ))
397414
#
398-
function _sniff_versions(environment::AbstractString, multiplexers)
415+
function _sniff_versions(environment::AbstractString, multiplexers, arch::Union{Symbol,Nothing} = nothing)
399416
registries = Dict(
400417
reg.uuid => _process_reg_info_uuid_mapping(reg) for
401418
reg in Pkg.Registry.reachable_registries()
402419
)
403420
project = Base.env_project_file(environment)
404421
env = Pkg.Types.EnvCache(project)
405-
stdlib_path = _get_stdlib_path(env, environment, multiplexers)
422+
stdlib_path = _get_stdlib_path(env, environment, multiplexers, arch)
406423
output = Dict{String,Dict{String,Any}}()
407424
for (uuid, entry) in env.manifest.deps
408425
name = "$(entry.name)"
@@ -455,13 +472,13 @@ function _sniff_versions(environment::AbstractString, multiplexers)
455472
return output
456473
end
457474

458-
function _get_stdlib_path(env, environment, multiplexers)
475+
function _get_stdlib_path(env, environment, multiplexers, arch::Union{Symbol,Nothing} = nothing)
459476
toml_file = joinpath(environment, "PackageBundler.toml")
460477
toml = isfile(toml_file) ? TOML.parsefile(toml_file) : Dict()
461478
juliaup = get(Dict, toml, "juliaup")
462479
channel = get(juliaup, "channel", nothing)
463480
version = something(channel, env.manifest.julia_version)
464-
julia_bin = _process_multiplexers(multiplexers, version)
481+
julia_bin = _process_multiplexers(multiplexers, version, arch)
465482
return read(
466483
`$julia_bin --startup-file=no -e 'import Pkg; print(Pkg.stdlib_dir())'`,
467484
String,
@@ -575,8 +592,9 @@ function _strip_package(
575592
key_pair::@NamedTuple{private::String, public::String},
576593
handlers::Dict,
577594
multiplexers::Vector{String},
595+
arch::Union{Symbol,Nothing} = nothing,
578596
)
579-
@info "Stripping source code." julia_version package
597+
@info "Stripping source code." Sys.ARCH arch julia_version package
580598

581599
package = abspath(package)
582600
output = abspath(output)
@@ -695,7 +713,7 @@ function _strip_package(
695713
)
696714
end
697715
script = joinpath(@__DIR__, "serializer.jl")
698-
binary = _process_multiplexers(multiplexers, julia_version)
716+
binary = _process_multiplexers(multiplexers, julia_version, arch)
699717
run(`$(binary) --startup-file=no $(script) $(toml_file)`)
700718
finally
701719
rm(toml_file; force = true)
@@ -744,12 +762,13 @@ end
744762
function _process_multiplexers(
745763
multiplexers::Vector{String},
746764
julia_version::Union{String,VersionNumber},
765+
arch::Union{Symbol,Nothing} = nothing,
747766
)
748767
for multiplexer in multiplexers
749768
exists = Sys.which(multiplexer)
750769
if !isnothing(exists)
751770
if multiplexer == "juliaup"
752-
return `julia +$(julia_version)`
771+
return `julia +$(_juliaup_channel(julia_version, arch))`
753772
elseif multiplexer == "asdf"
754773
return withenv("ASDF_JULIA_VERSION" => "$(julia_version)") do
755774
path = readchomp(`asdf which julia`)
@@ -771,3 +790,12 @@ function _process_multiplexers(
771790
error("no multiplexers found: $(repr(multiplexers))")
772791
end
773792
end
793+
794+
function _juliaup_channel(julia_version::Union{String,VersionNumber}, arch::Union{Symbol,Nothing} = nothing)
795+
if isnothing(arch)
796+
return julia_version
797+
end
798+
799+
juliaup_arch = if arch == :i686; :x86; elseif arch == :x86_64; :x64; else arch; end
800+
return "$(julia_version)~$juliaup_arch"
801+
end

src/utilities.jl

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ version as specified in the `Manifest.toml` file. This uses either `juliaup` or
77
`asdf` to switch between `julia` versions as needed. Make sure to have either of
88
those installed, as well as the expected `julia` versions.
99
"""
10-
function instantiate(environments::String)
10+
function instantiate(environments::String; arch::Union{Symbol,Nothing} = nothing)
1111
if ispath(environments)
1212
if isfile(environments)
1313
error("The path '$environments' is a file, not a directory.")
@@ -35,11 +35,12 @@ function instantiate(environments::String)
3535
)
3636

3737
if !isnothing(Sys.which("juliaup"))
38-
@info "Checking whether Julia '$julia_version' is installed, if not, installing it."
39-
run(`juliaup add $julia_version`)
38+
juliaup_channel = _juliaup_channel(julia_version, arch)
39+
@info "Checking whether Julia '$juliaup_channel' is installed, if not, installing it."
40+
run(`juliaup add $juliaup_channel`)
4041
withenv("JULIA_PKG_PRECOMPILE_AUTO" => 0) do
4142
run(
42-
`julia +$(julia_version) --project=$each -e 'import Pkg; Pkg.instantiate()'`,
43+
`julia +$juliaup_channel --project=$each -e 'import Pkg; Pkg.instantiate()'`,
4344
)
4445
end
4546
elseif !isnothing(Sys.which("asdf"))

test/packages/TestPackage/0.1.0/src/TestPackage.jl

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,4 +4,10 @@ import Example
44

55
greet() = print(Example.hello("0.1.0!"))
66

7+
struct IntType
8+
i::Int
9+
end
10+
11+
const INT_VALUE = IntType(42)
12+
713
end # module TestPackage

test/packages/TestPackage/0.2.0/src/TestPackage.jl

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,4 +4,10 @@ import Example
44

55
greet() = print(Example.hello("0.2.0!"))
66

7+
struct IntType
8+
i::Int
9+
end
10+
11+
const INT_VALUE = IntType(42)
12+
713
end # module TestPackage

0 commit comments

Comments
 (0)