From 696380b98290f109204369283a9d40abec229eb1 Mon Sep 17 00:00:00 2001 From: Cody Tapscott Date: Thu, 20 Feb 2025 14:31:35 -0500 Subject: [PATCH 1/2] juliac: Add rudimentary Windows support This was essentially working as-is, except for our reliance on a C compiler. --- contrib/Artifacts.toml | 19 +++++++++++++ contrib/juliac.jl | 62 ++++++++++++++++++++++++++++++++++++++---- 2 files changed, 76 insertions(+), 5 deletions(-) create mode 100644 contrib/Artifacts.toml diff --git a/contrib/Artifacts.toml b/contrib/Artifacts.toml new file mode 100644 index 0000000000000..54771b41b21f7 --- /dev/null +++ b/contrib/Artifacts.toml @@ -0,0 +1,19 @@ +[[mingw-w64]] +arch = "x86_64" +git-tree-sha1 = "b17bda08a19173572926f43a48aad5ef3d845e7c" +os = "windows" +lazy = true + + [[mingw-w64.download]] + sha256 = "53645e06775a55733580426341395c67dda20a664af83bcda76a1d052b618b59" + url = "https://github.com/JuliaLang/PackageCompiler.jl/releases/download/v2.1.24/x86_64-14.2.0-release-posix-seh-msvcrt-rt_v12-rev0.tar.gz" + +[[mingw-w64]] +arch = "i686" +git-tree-sha1 = "76b9f278e7de1d7dfdfe3a786afbe9c1e29003ea" +os = "windows" +lazy = true + + [[mingw-w64.download]] + sha256 = "d049bd771e01b02f2ca9274435f0e6f9f4f295bf2af72a8059dd851c52144910" + url = "https://github.com/JuliaLang/PackageCompiler.jl/releases/download/v2.1.24/i686-14.2.0-release-posix-dwarf-msvcrt-rt_v12-rev0.tar.gz" diff --git a/contrib/juliac.jl b/contrib/juliac.jl index d637f1f1bf3a2..4e111c7b140a6 100644 --- a/contrib/juliac.jl +++ b/contrib/juliac.jl @@ -3,6 +3,8 @@ # Julia compiler wrapper script # NOTE: The interface and location of this script are considered unstable/experimental +using LazyArtifacts + module JuliaConfig include(joinpath(@__DIR__, "julia-config.jl")) end @@ -30,6 +32,57 @@ if help !== nothing exit(0) end +# Copied from PackageCompiler +# https://github.com/JuliaLang/PackageCompiler.jl/blob/1c35331d8ef81494f054bbc71214811253101993/src/PackageCompiler.jl#L147-L190 +function get_compiler_cmd(; cplusplus::Bool=false) + cc = get(ENV, "JULIA_CC", nothing) + path = nothing + @static if Sys.iswindows() + path = joinpath(LazyArtifacts.artifact"mingw-w64", + "extracted_files", + (Int==Int64 ? "mingw64" : "mingw32"), + "bin", + cplusplus ? "g++.exe" : "gcc.exe") + compiler_cmd = `$path` + end + if cc !== nothing + compiler_cmd = Cmd(Base.shell_split(cc)) + path = nothing + elseif !Sys.iswindows() + compilers_cpp = ("g++", "clang++") + compilers_c = ("gcc", "clang") + found_compiler = false + if cplusplus + for compiler in compilers_cpp + if Sys.which(compiler) !== nothing + compiler_cmd = `$compiler` + found_compiler = true + break + end + end + end + if !found_compiler + for compiler in compilers_c + if Sys.which(compiler) !== nothing + compiler_cmd = `$compiler` + found_compiler = true + if cplusplus && !WARNED_CPP_COMPILER[] + @warn "could not find a c++ compiler (g++ or clang++), falling back to $compiler, this might cause link errors" + WARNED_CPP_COMPILER[] = true + end + break + end + end + end + found_compiler || error("could not find a compiler, looked for ", + join(((cplusplus ? compilers_cpp : ())..., compilers_c...), ", ", " and ")) + end + if path !== nothing + compiler_cmd = addenv(compiler_cmd, "PATH" => string(ENV["PATH"], ";", dirname(path))) + end + return compiler_cmd +end + # arguments to forward to julia compilation process julia_args = [] enable_trim::Bool = false @@ -82,6 +135,7 @@ function get_rpath(; relative::Bool = false) end end +cc = get_compiler_cmd() absfile = abspath(file) cflags = JuliaConfig.cflags(; framework=false) cflags = Base.shell_split(cflags) @@ -93,7 +147,6 @@ tmpdir = mktempdir(cleanup=false) img_path = joinpath(tmpdir, "img.a") bc_path = joinpath(tmpdir, "img-bc.a") - function precompile_env() # Pre-compile the environment # (otherwise obscure error messages will occur) @@ -121,7 +174,6 @@ function compile_products(enable_trim::Bool) println(stderr, "\nFailed to compile $file") exit(1) end - end function link_products() @@ -137,11 +189,11 @@ function link_products() julia_libs = Base.shell_split(Base.isdebugbuild() ? "-ljulia-debug -ljulia-internal-debug" : "-ljulia -ljulia-internal") try if output_type == "--output-lib" - cmd2 = `cc $(allflags) $(rpath) -o $outname -shared -Wl,$(Base.Linking.WHOLE_ARCHIVE) $img_path -Wl,$(Base.Linking.NO_WHOLE_ARCHIVE) $(julia_libs)` + cmd2 = `$(cc) $(allflags) $(rpath) -o $outname -shared -Wl,$(Base.Linking.WHOLE_ARCHIVE) $img_path -Wl,$(Base.Linking.NO_WHOLE_ARCHIVE) $(julia_libs)` elseif output_type == "--output-sysimage" - cmd2 = `cc $(allflags) $(rpath) -o $outname -shared -Wl,$(Base.Linking.WHOLE_ARCHIVE) $img_path -Wl,$(Base.Linking.NO_WHOLE_ARCHIVE) $(julia_libs)` + cmd2 = `$(cc) $(allflags) $(rpath) -o $outname -shared -Wl,$(Base.Linking.WHOLE_ARCHIVE) $img_path -Wl,$(Base.Linking.NO_WHOLE_ARCHIVE) $(julia_libs)` else - cmd2 = `cc $(allflags) $(rpath) -o $outname -Wl,$(Base.Linking.WHOLE_ARCHIVE) $img_path -Wl,$(Base.Linking.NO_WHOLE_ARCHIVE) $(julia_libs)` + cmd2 = `$(cc) $(allflags) $(rpath) -o $outname -Wl,$(Base.Linking.WHOLE_ARCHIVE) $img_path -Wl,$(Base.Linking.NO_WHOLE_ARCHIVE) $(julia_libs)` end verbose && println("Running: $cmd2") run(cmd2) From e5fd9aca55ebc51b2939663718d5f7f7fe1cc27f Mon Sep 17 00:00:00 2001 From: Cody Tapscott Date: Mon, 30 Jun 2025 19:02:35 -0400 Subject: [PATCH 2/2] Move `juliac` utilities to `contrib/juliac/` --- Makefile | 3 ++- contrib/{ => juliac}/Artifacts.toml | 0 contrib/{ => juliac}/juliac-buildscript.jl | 0 contrib/{ => juliac}/juliac-trim-base.jl | 0 contrib/{ => juliac}/juliac-trim-stdlib.jl | 0 contrib/{ => juliac}/juliac.jl | 2 +- doc/src/devdocs/sysimg.md | 2 +- test/trimming/Makefile | 2 +- 8 files changed, 5 insertions(+), 4 deletions(-) rename contrib/{ => juliac}/Artifacts.toml (100%) rename contrib/{ => juliac}/juliac-buildscript.jl (100%) rename contrib/{ => juliac}/juliac-trim-base.jl (100%) rename contrib/{ => juliac}/juliac-trim-stdlib.jl (100%) rename contrib/{ => juliac}/juliac.jl (99%) diff --git a/Makefile b/Makefile index fc73b897c3aa3..39f34b5372262 100644 --- a/Makefile +++ b/Makefile @@ -89,7 +89,7 @@ julia-deps: | $(DIRS) $(build_datarootdir)/julia/base $(build_datarootdir)/julia julia-stdlib: | $(DIRS) julia-deps @$(MAKE) $(QUIET_MAKE) -C $(BUILDROOT)/stdlib -julia-base: julia-deps $(build_sysconfdir)/julia/startup.jl $(build_man1dir)/julia.1 $(build_datarootdir)/julia/julia-config.jl $(build_datarootdir)/julia/juliac.jl $(build_datarootdir)/julia/juliac-buildscript.jl $(build_datarootdir)/julia/juliac-trim-base.jl $(build_datarootdir)/julia/juliac-trim-stdlib.jl +julia-base: julia-deps $(build_sysconfdir)/julia/startup.jl $(build_man1dir)/julia.1 $(build_datarootdir)/julia/julia-config.jl $(build_datarootdir)/julia/juliac/juliac.jl $(build_datarootdir)/julia/juliac/juliac-buildscript.jl $(build_datarootdir)/julia/juliac/juliac-trim-base.jl $(build_datarootdir)/julia/juliac/juliac-trim-stdlib.jl @$(MAKE) $(QUIET_MAKE) -C $(BUILDROOT)/base julia-libccalltest: julia-deps @@ -184,6 +184,7 @@ $(build_sysconfdir)/julia/startup.jl: $(JULIAHOME)/etc/startup.jl | $(build_sysc @cp $< $@ $(build_datarootdir)/julia/%: $(JULIAHOME)/contrib/% | $(build_datarootdir)/julia + mkdir -p $(dir $@) $(INSTALL_M) $< $(dir $@) $(build_depsbindir)/stringreplace: $(JULIAHOME)/contrib/stringreplace.c | $(build_depsbindir) diff --git a/contrib/Artifacts.toml b/contrib/juliac/Artifacts.toml similarity index 100% rename from contrib/Artifacts.toml rename to contrib/juliac/Artifacts.toml diff --git a/contrib/juliac-buildscript.jl b/contrib/juliac/juliac-buildscript.jl similarity index 100% rename from contrib/juliac-buildscript.jl rename to contrib/juliac/juliac-buildscript.jl diff --git a/contrib/juliac-trim-base.jl b/contrib/juliac/juliac-trim-base.jl similarity index 100% rename from contrib/juliac-trim-base.jl rename to contrib/juliac/juliac-trim-base.jl diff --git a/contrib/juliac-trim-stdlib.jl b/contrib/juliac/juliac-trim-stdlib.jl similarity index 100% rename from contrib/juliac-trim-stdlib.jl rename to contrib/juliac/juliac-trim-stdlib.jl diff --git a/contrib/juliac.jl b/contrib/juliac/juliac.jl similarity index 99% rename from contrib/juliac.jl rename to contrib/juliac/juliac.jl index 4e111c7b140a6..ed80d88444639 100644 --- a/contrib/juliac.jl +++ b/contrib/juliac/juliac.jl @@ -6,7 +6,7 @@ using LazyArtifacts module JuliaConfig - include(joinpath(@__DIR__, "julia-config.jl")) + include(joinpath(@__DIR__, "..", "julia-config.jl")) end julia_cmd = `$(Base.julia_cmd()) --startup-file=no --history-file=no` diff --git a/doc/src/devdocs/sysimg.md b/doc/src/devdocs/sysimg.md index 2cbba2744d4a1..e8202736e57e1 100644 --- a/doc/src/devdocs/sysimg.md +++ b/doc/src/devdocs/sysimg.md @@ -176,7 +176,7 @@ debug info, respectively, and so will make debugging more difficult. We have identified many small changes to Base that significantly increase the set of programs that can be reliably trimmed. Unfortunately some of those changes would be considered breaking, and so are only applied when trimming is requested (this is done by an external build script, -currently maintained inside the test suite as `contrib/juliac-buildscript.jl`). +currently maintained inside the test suite as `contrib/juliac/juliac-buildscript.jl`). Therefore in many cases trimming will require you to opt in to new variants of Base and some standard libraries. diff --git a/test/trimming/Makefile b/test/trimming/Makefile index e3c7536bbc92c..c3145765655e7 100644 --- a/test/trimming/Makefile +++ b/test/trimming/Makefile @@ -29,7 +29,7 @@ CFLAGS_ADD = $(shell $(JULIA_CONFIG) --cflags) LDFLAGS_ADD = -lm $(shell $(JULIA_CONFIG) --ldflags --ldlibs) -ljulia-internal # get the JuliaC build script -JULIAC_BUILDSCRIPT := $(shell $(JULIA) -e 'print(joinpath(Sys.BINDIR, Base.DATAROOTDIR, "julia", "juliac-buildscript.jl"))') +JULIAC_BUILDSCRIPT := $(shell $(JULIA) -e 'print(joinpath(Sys.BINDIR, Base.DATAROOTDIR, "julia", "juliac", "juliac-buildscript.jl"))') #=============================================================================