From 3dcce377b1af854376ee6d27d87b5609ac47d87a Mon Sep 17 00:00:00 2001 From: Chun-wei Fan Date: Wed, 7 Jun 2023 16:56:20 +0800 Subject: [PATCH] NMake Builds: Use rustc to query the required system libs Extend the helper batch file that we use to query the default Rust toolchain so that we can use the rustc that corresponds to the Rust toolchain that we are using to query the system libraries (i.e. from the Windows SDK), in order to ensure that the final librvg DLL links, as Rust might involve changes that require more system libraries to be required for the build, such as in issue [1]: https://github.com/rust-lang/rust/pull/108262 Fixes issue #968. Part-of: --- win32/Makefile.am | 2 +- win32/build-rules-msvc.mak | 3 +- win32/config-msvc.mak.in | 7 +--- win32/rsvg-rust.mak | 58 ++++++++++++-------------- win32/rust-default-target.bat | 36 ---------------- win32/rust-query-cfg.bat | 78 +++++++++++++++++++++++++++++++++++ 6 files changed, 108 insertions(+), 76 deletions(-) delete mode 100644 win32/rust-default-target.bat create mode 100644 win32/rust-query-cfg.bat diff --git a/win32/Makefile.am b/win32/Makefile.am index 7260300ba..2176758d1 100644 --- a/win32/Makefile.am +++ b/win32/Makefile.am @@ -15,7 +15,7 @@ EXTRA_DIST = \ Makefile.vc \ MSVC-Builds.md \ rsvg-rust.mak \ - rust-default-target.bat \ + rust-query-cfg.bat \ pc_base.py \ replace.py \ rsvgpc.py diff --git a/win32/build-rules-msvc.mak b/win32/build-rules-msvc.mak index 910e385e4..328c66725 100644 --- a/win32/build-rules-msvc.mak +++ b/win32/build-rules-msvc.mak @@ -42,8 +42,9 @@ $(LIBRSVG_LIB): $(LIBRSVG_DLL) # $(dependent_objects) # << # @-if exist $@.manifest mt /manifest $@.manifest /outputresource:$@;2 + $(LIBRSVG_DLL): $(RSVG_INTERNAL_LIB) $(librsvg_OBJS) $(LIBRSVG_DEF) - link /DLL $(LDFLAGS) $(LIBRSVG_DEP_LIBS) \ + link /DLL $(LDFLAGS) $(LIBRSVG_DEP_LIBS) $(LIBRSVG_SYSTEM_DEP_LIBS) \ /implib:$(LIBRSVG_LIB) \ -out:$@ /def:$(LIBRSVG_DEF) @<< $(librsvg_OBJS) diff --git a/win32/config-msvc.mak.in b/win32/config-msvc.mak.in index 314a152fa..ab20c5668 100644 --- a/win32/config-msvc.mak.in +++ b/win32/config-msvc.mak.in @@ -116,12 +116,7 @@ LIBRSVG_DEP_LIBS = \ $(LIBRSVG_EXTRA_DEP_LIBS) \ pango-1.0.lib \ cairo-gobject.lib \ - $(BASE_DEP_LIBS) \ - libxml2.lib \ - advapi32.lib \ - userenv.lib \ - bcrypt.lib \ - ws2_32.lib + $(BASE_DEP_LIBS) RSVG_PIXBUF_LOADER_CFLAGS = \ $(BASE_CFLAGS) \ diff --git a/win32/rsvg-rust.mak b/win32/rsvg-rust.mak index fdafd81c0..9e06aa391 100644 --- a/win32/rsvg-rust.mak +++ b/win32/rsvg-rust.mak @@ -13,12 +13,6 @@ CARGO = %HOMEPATH%\.cargo\bin\cargo RUSTUP = %HOMEPATH%\.cargo\bin\rustup !endif -!if [call rust-default-target.bat $(RUSTUP)] -!endif -!include rust-cfg.mak -!if [del /f/q rust-cfg.mak] -!endif - # For those who wish to use a particular toolchain version to build librsvg !if defined(TOOLCHAIN_VERSION) TOOLCHAIN_TYPE = $(TOOLCHAIN_VERSION) @@ -27,19 +21,28 @@ TOOLCHAIN_TYPE = !endif !if "$(TOOLCHAIN_TYPE)" == "" +!if [call rust-query-cfg.bat use-rustup $(RUSTUP)] +!endif +!include rust-cfg.mak +!if [del /f/q rust-cfg.mak] +!endif !if "$(RUST_DEFAULT_COMPILER)" != "pc-windows-msvc" !error The default Rust toolchain is not an MSVC toolchain. Please use `rustup` to set the default to an MSVC toolchain !endif TOOLCHAIN_TYPE = $(RUST_DEFAULT_CHANNEL) -BUILD_HOST = $(RUST_DEFAULT_TARGET) +BUILD_HOST = $(RUST_DEFAULT_MSVC_TARGET) +RUST_HOST = $(RUST_DEFAULT_TARGET) # non-default toolchain requested !else !if "$(PROCESSOR_ARCHITECTURE)" == "x64" || "$(PROCESSOR_ARCHITECTURE)" == "X64" || "$(PROCESSOR_ARCHITECTURE)" == "AMD64" BUILD_HOST = x64 +RUST_HOST = x86_64 !elseif "$(PROCESSOR_ARCHITECTURE)" == "ARM64" BUILD_HOST = arm64 +RUST_HOST = aarch64 !elseif "$(PROCESSOR_ARCHITECTURE)" == "x86" BUILD_HOST = Win32 +RUST_HOST = i686 !endif !endif @@ -55,34 +58,13 @@ FORCE_CROSS = 0 # Setup cross builds if needed !if "$(PLAT)" == "x64" RUST_TARGET = x86_64 -!if "$(BUILD_HOST)" != "$(PLAT)" -FORCE_CROSS = 1 -!if "$(BUILD_HOST)" == "arm64" -RUST_HOST = aarch64 -!elseif "$(BUILD_HOST)" == "Win32" -RUST_HOST = i686 -!endif -!endif !elseif "$(PLAT)" == "arm64" RUST_TARGET = aarch64 -!if "$(BUILD_HOST)" != "$(PLAT)" -FORCE_CROSS = 1 -!if "$(BUILD_HOST)" == "x64" -RUST_HOST = x86_64 -!elseif "$(BUILD_HOST)" == "Win32" -RUST_HOST = i686 -!endif -!endif !else RUST_TARGET = i686 +!endif !if "$(BUILD_HOST)" != "$(PLAT)" FORCE_CROSS = 1 -!if "$(BUILD_HOST)" == "arm64" -RUST_HOST = aarch64 -!elseif "$(BUILD_HOST)" == "x64" -RUST_HOST = x86_64 -!endif -!endif !endif !if "$(VALID_CFGSET)" == "TRUE" @@ -92,11 +74,8 @@ BUILD_RUST = 0 !endif !if "$(BUILD_RUST)" == "1" - CARGO_TARGET = $(RUST_TARGET)-pc-windows-msvc -CARGO_TARGET_TOOLCHAIN = +$(TOOLCHAIN_TYPE)-$(CARGO_TARGET) -RUSTUP_CMD = $(RUSTUP) default $(DEFAULT_TARGET) CARGO_TARGET_DIR = vs$(VSVER)\$(CFG)\$(PLAT)\obj\rsvg_c_api CARGO_TARGET_DIR_FLAG = --target-dir=$(CARGO_TARGET_DIR) @@ -109,10 +88,25 @@ CARGO_CMD = $(CARGO) $(RUST_HOST_TOOLCHAIN) --locked build $(CARGO_TARGET_CMD) $ CARGO_CLEAN_CMD = $(CARGO) $(RUST_HOST_TOOLCHAIN) clean $(CARGO_TARGET_CMD) $(MANIFEST_PATH_FLAG) $(CARGO_TARGET_DIR_FLAG) CARGO_TARGET_OUTPUT_DIR = $(CARGO_TARGET_DIR)\$(CARGO_TARGET)\$(CFG) !else +CARGO_TARGET_TOOLCHAIN = +$(TOOLCHAIN_TYPE)-$(CARGO_TARGET) + CARGO_CMD = $(CARGO) $(CARGO_TARGET_TOOLCHAIN) --locked build $(MANIFEST_PATH_FLAG) $(CARGO_TARGET_DIR_FLAG) CARGO_CLEAN_CMD = $(CARGO) $(CARGO_TARGET_TOOLCHAIN) clean $(MANIFEST_PATH_FLAG) $(CARGO_TARGET_DIR_FLAG) CARGO_TARGET_OUTPUT_DIR = $(CARGO_TARGET_DIR)\$(CFG) !endif + +# Query the system libs that we will be using to link the librsvg DLL +!if $(FORCE_CROSS) > 0 +!if [call rust-query-cfg.bat check-syslibs $(RUSTUP) $(RUST_HOST_TOOLCHAIN) $(RUST_TARGET)] +!endif +!else +!if [call rust-query-cfg.bat check-syslibs $(RUSTUP) $(CARGO_TARGET_TOOLCHAIN) $(RUST_TARGET)] +!endif +!endif +!include rust-sys-libs.mak +!if [del /f/q rust-sys-libs.mak] +!endif + !if "$(CFG)" == "release" || "$(CFG)" == "Release" CARGO_CMD = $(CARGO_CMD) --release !endif diff --git a/win32/rust-default-target.bat b/win32/rust-default-target.bat deleted file mode 100644 index 2f8107592..000000000 --- a/win32/rust-default-target.bat +++ /dev/null @@ -1,36 +0,0 @@ -@echo off -:: SETLOCAL ENABLEDELAYEDEXPANSION -set RUSTUP=%1 - -FOR /F "tokens=* USEBACKQ" %%F IN (`%RUSTUP% default`) DO ( -SET RUST_DEFAULT_TOOLCHAIN=%%F -) - -:: We want to be very sure that if we are using the default -:: Rust toolchain for the build, we are indeed using an msvc -:: one! - -FOR /F "tokens=1,2,3,4,5* delims=-" %%a IN ("%RUST_DEFAULT_TOOLCHAIN%") do ( -:: --pc-windows-msvc (default) or stable--pc-windows-msvc (default) -if not "%%a" == "nightly" set CHANNEL=%%a -if not "%%a" == "nightly" set TARGET=%%b -if not "%%a" == "nightly" FOR /F "tokens=1,2 delims= " %%o IN ("%%e") do ( -set TOOLCHAIN_COMPILER=%%c-%%d-%%o -) - -:: nightly-yyyy-mm-dd--pc-windows-msvc (default) -if "%%a" == "nightly" set CHANNEL=%%a-%%b-%%c -if "%%a" == "nightly" set TARGET=%%e -if "%%a" == "nightly" FOR /F "tokens=1,2 delims= " %%o IN ("%%f") do ( -set TOOLCHAIN_COMPILER=%%o -) -) - -if "%TARGET%" == "aarch64" set NMAKE_TGT=amd64 -if "%TARGET%" == "x86_64" set NMAKE_TGT=x64 -if "%TARGET%" == "i686" set NMAKE_TGT=Win32 - -if exist rust-cfg.mak goto :EOF -echo RUST_DEFAULT_CHANNEL=%CHANNEL%>>rust-cfg.mak -echo RUST_DEFAULT_TARGET=%NMAKE_TGT%>>rust-cfg.mak -echo RUST_DEFAULT_COMPILER=%TOOLCHAIN_COMPILER%>>rust-cfg.mak diff --git a/win32/rust-query-cfg.bat b/win32/rust-query-cfg.bat new file mode 100644 index 000000000..020d66f65 --- /dev/null +++ b/win32/rust-query-cfg.bat @@ -0,0 +1,78 @@ +@echo off +if not "%1" == "use-rustup" if not "%1" == "check-syslibs" goto :err_badopt +if "%2" == "" goto :err_badopt + +set RUSTUP=%2 +if "%1" == "check-syslibs" goto :check_syslibs + +FOR /F "tokens=* USEBACKQ" %%F IN (`%RUSTUP% default`) DO ( +SET RUST_DEFAULT_TOOLCHAIN=%%F +) + +:: We want to be very sure that if we are using the default +:: Rust toolchain for the build, we are indeed using an msvc +:: one! + +FOR /F "tokens=1,2,3,4,5* delims=-" %%a IN ("%RUST_DEFAULT_TOOLCHAIN%") do ( +:: --pc-windows-msvc (default) or stable--pc-windows-msvc (default) +if not "%%a" == "nightly" set CHANNEL=%%a +if not "%%a" == "nightly" set TARGET=%%b +if not "%%a" == "nightly" FOR /F "tokens=1,2 delims= " %%o IN ("%%e") do ( +set TOOLCHAIN_COMPILER=%%c-%%d-%%o +) + +:: nightly-yyyy-mm-dd--pc-windows-msvc (default) +if "%%a" == "nightly" set CHANNEL=%%a-%%b-%%c +if "%%a" == "nightly" set TARGET=%%e +if "%%a" == "nightly" FOR /F "tokens=1,2 delims= " %%o IN ("%%f") do ( +set TOOLCHAIN_COMPILER=%%o +) +) + +if "%TARGET%" == "aarch64" set NMAKE_TGT=amd64 +if "%TARGET%" == "x86_64" set NMAKE_TGT=x64 +if "%TARGET%" == "i686" set NMAKE_TGT=Win32 + +if exist rust-cfg.mak goto :EOF +echo RUST_DEFAULT_CHANNEL=%CHANNEL%>>rust-cfg.mak +echo RUST_DEFAULT_TARGET=%TARGET%>>rust-cfg.mak +echo RUST_DEFAULT_MSVC_TARGET=%NMAKE_TGT%>>rust-cfg.mak +echo RUST_DEFAULT_COMPILER=%TOOLCHAIN_COMPILER%>>rust-cfg.mak +goto :EOF + +:check_syslibs +if "%3" == "" goto :err_badopt +if "%4" == "" goto :err_badopt +if not "%4" == "x86_64" if not "%4" == "aarch64" if not "%4" == "i686" goto :err_badopt + +:: grab the results from the following command to extract the needed system +:: libs for linking for Rust builds (this is printed in stderr) +if exist rust-libs.txt goto :check_libs +%RUSTUP:rustup=rustc% %3 --target=%4-pc-windows-msvc ^ +--crate-type staticlib --print native-static-libs - < nul 2>>rust-libs.txt + +:check_libs +for /f "tokens=1,2*" %%l in ('findstr /ic:"note: native-static-libs:" /b rust-libs.txt') DO ( +set ALL_SYS_LIBS=%%n +) +SETLOCAL ENABLEDELAYEDEXPANSION +set LINK_SYS_LIBS= +del /f/q rust-libs.txt +del /f/q rust_out.lib +:: Filter out kernel32.lib, msvcrt.lib and legacy_stdio_definitions.lib +:: they will be pulled in automatically +for %%q in (%ALL_SYS_LIBS%) do ( +if not "%%q" == "kernel32.lib" if not "%%q" == "msvcrt.lib" ^ +if not "%%q" == "legacy_stdio_definitions.lib" ^ +if not "!LINK_SYS_LIBS!" == "" set LINK_SYS_LIBS=!LINK_SYS_LIBS! %%q + +if not "%%q" == "kernel32.lib" if not "%%q" == "msvcrt.lib" ^ +if not "%%q" == "legacy_stdio_definitions.lib" ^ +if "!LINK_SYS_LIBS!" == "" set LINK_SYS_LIBS=%%q +) + +echo LIBRSVG_SYSTEM_DEP_LIBS=%LINK_SYS_LIBS%>rust-sys-libs.mak +goto :EOF + +:err_badopt +echo Usage: %0 [use-rustup^|check-syslibs] rustup-executable ^ ^