Skip to content

Commit

Permalink
Provide prebuilt std for gnullvm targets
Browse files Browse the repository at this point in the history
  • Loading branch information
mati865 committed Mar 18, 2024
1 parent d31b6fb commit 2eba855
Show file tree
Hide file tree
Showing 6 changed files with 49 additions and 15 deletions.
11 changes: 10 additions & 1 deletion src/ci/docker/host-x86_64/dist-various-1/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,9 @@ RUN ./install-riscv64-none-elf.sh
COPY host-x86_64/dist-various-1/install-riscv32-none-elf.sh /build
RUN ./install-riscv32-none-elf.sh

COPY host-x86_64/dist-various-1/install-llvm-mingw.sh /build
RUN ./install-llvm-mingw.sh

# Suppress some warnings in the openwrt toolchains we downloaded
ENV STAGING_DIR=/tmp

Expand Down Expand Up @@ -110,6 +113,9 @@ ENV TARGETS=$TARGETS,armv7r-none-eabi
ENV TARGETS=$TARGETS,armv7r-none-eabihf
ENV TARGETS=$TARGETS,thumbv7neon-unknown-linux-gnueabihf
ENV TARGETS=$TARGETS,armv7a-none-eabi
ENV TARGETS=$TARGETS,aarch64-pc-windows-gnullvm
ENV TARGETS=$TARGETS,i686-pc-windows-gnullvm
ENV TARGETS=$TARGETS,x86_64-pc-windows-gnullvm

ENV CFLAGS_armv5te_unknown_linux_musleabi="-march=armv5te -marm -mfloat-abi=soft" \
CFLAGS_arm_unknown_linux_musleabi="-march=armv6 -marm" \
Expand Down Expand Up @@ -139,7 +145,10 @@ ENV CFLAGS_armv5te_unknown_linux_musleabi="-march=armv5te -marm -mfloat-abi=soft
CC_riscv64imac_unknown_none_elf=riscv64-unknown-elf-gcc \
CFLAGS_riscv64imac_unknown_none_elf=-march=rv64imac -mabi=lp64 \
CC_riscv64gc_unknown_none_elf=riscv64-unknown-elf-gcc \
CFLAGS_riscv64gc_unknown_none_elf=-march=rv64gc -mabi=lp64
CFLAGS_riscv64gc_unknown_none_elf=-march=rv64gc -mabi=lp64 \
CC_aarch64_pc_windows_gnullvm=aarch64-w64-mingw32-clang \
CC_i686_pc_windows_gnullvm=i686-w64-mingw32-clang \
CC_x86_64_pc_windows_gnullvm=x86_64-w64-mingw32-clang

ENV RUST_CONFIGURE_ARGS \
--musl-root-armv5te=/musl-armv5te \
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
#!/usr/bin/env bash

set -ex

archive=llvm-mingw-20231128-ucrt-ubuntu-20.04-x86_64.tar.xz
curl -L https://github.com/mstorsjo/llvm-mingw/releases/download/20231128/${archive} | \
tar --extract --lzma --strip 1 --directory /usr/local
8 changes: 5 additions & 3 deletions src/doc/rustc/src/platform-support.md
Original file line number Diff line number Diff line change
Expand Up @@ -138,6 +138,7 @@ target | std | notes
`aarch64-fuchsia` | ✓ | Alias for `aarch64-unknown-fuchsia`
[`aarch64-unknown-fuchsia`](platform-support/fuchsia.md) | ✓ | ARM64 Fuchsia
[`aarch64-linux-android`](platform-support/android.md) | ✓ | ARM64 Android
[`aarch64-pc-windows-gnullvm`](platform-support/pc-windows-gnullvm.md) | ✓ | ARM64 MinGW (Windows 10+), LLVM ABI
[`aarch64-unknown-linux-ohos`](platform-support/openharmony.md) | ✓ | ARM64 OpenHarmony
`aarch64-unknown-none-softfloat` | * | Bare ARM64, softfloat
`aarch64-unknown-none` | * | Bare ARM64, hardfloat
Expand All @@ -161,6 +162,7 @@ target | std | notes
`i586-unknown-linux-gnu` | ✓ | 32-bit Linux w/o SSE (kernel 3.2, glibc 2.17) [^x86_32-floats-x87]
`i586-unknown-linux-musl` | ✓ | 32-bit Linux w/o SSE, musl 1.2.3 [^x86_32-floats-x87]
[`i686-linux-android`](platform-support/android.md) | ✓ | 32-bit x86 Android [^x86_32-floats-return-ABI]
[`i686-pc-windows-gnullvm`](platform-support/pc-windows-gnullvm.md) | ✓ | 32-bit x86 MinGW (Windows 10+), LLVM ABI [^x86_32-floats-return-ABI]
`i686-unknown-freebsd` | ✓ | 32-bit FreeBSD [^x86_32-floats-return-ABI]
`i686-unknown-linux-musl` | ✓ | 32-bit Linux with musl 1.2.3 [^x86_32-floats-return-ABI]
[`i686-unknown-uefi`](platform-support/unknown-uefi.md) | ? | 32-bit UEFI
Expand Down Expand Up @@ -196,6 +198,7 @@ target | std | notes
[`x86_64-unknown-fuchsia`](platform-support/fuchsia.md) | ✓ | 64-bit x86 Fuchsia
[`x86_64-linux-android`](platform-support/android.md) | ✓ | 64-bit x86 Android
`x86_64-pc-solaris` | ✓ | 64-bit Solaris 11, illumos
[`x86_64-pc-windows-gnullvm`](platform-support/pc-windows-gnullvm.md) | ✓ | 64-bit x86 MinGW (Windows 10+), LLVM ABI
`x86_64-unknown-linux-gnux32` | ✓ | 64-bit Linux (x32 ABI) (kernel 4.15, glibc 2.27)
[`x86_64-unknown-linux-ohos`](platform-support/openharmony.md) | ✓ | x86_64 OpenHarmony
[`x86_64-unknown-none`](platform-support/x86_64-unknown-none.md) | * | Freestanding/bare-metal x86_64, softfloat
Expand Down Expand Up @@ -244,7 +247,7 @@ target | std | host | notes
[`aarch64-apple-watchos-sim`](platform-support/apple-watchos.md) | ✓ | | ARM64 Apple WatchOS Simulator
[`aarch64-kmc-solid_asp3`](platform-support/kmc-solid.md) | ✓ | | ARM64 SOLID with TOPPERS/ASP3
[`aarch64-nintendo-switch-freestanding`](platform-support/aarch64-nintendo-switch-freestanding.md) | * | | ARM64 Nintendo Switch, Horizon
[`aarch64-pc-windows-gnullvm`](platform-support/pc-windows-gnullvm.md) | ✓ | |
[`aarch64-unknown-linux-ohos`](platform-support/openharmony.md) | ✓ | | ARM64 OpenHarmony |
[`aarch64-unknown-teeos`](platform-support/aarch64-unknown-teeos.md) | ? | | ARM64 TEEOS |
[`aarch64-unknown-nto-qnx710`](platform-support/nto-qnx.md) | ✓ | | ARM64 QNX Neutrino 7.1 RTOS |
`aarch64-unknown-freebsd` | ✓ | ✓ | ARM64 FreeBSD
Expand Down Expand Up @@ -291,7 +294,7 @@ target | std | host | notes
[`i586-pc-nto-qnx700`](platform-support/nto-qnx.md) | * | | 32-bit x86 QNX Neutrino 7.0 RTOS [^x86_32-floats-return-ABI]
[`i586-unknown-netbsd`](platform-support/netbsd.md) | ✓ | | 32-bit x86, restricted to Pentium
`i686-apple-darwin` | ✓ | ✓ | 32-bit macOS (10.12+, Sierra+) [^x86_32-floats-return-ABI]
[`i686-pc-windows-gnullvm`](platform-support/pc-windows-gnullvm.md) | | ✓ | [^x86_32-floats-return-ABI]
`i686-pc-windows-msvc` | * | | 32-bit Windows XP support [^x86_32-floats-return-ABI]
`i686-unknown-haiku` | ✓ | ✓ | 32-bit Haiku [^x86_32-floats-return-ABI]
[`i686-unknown-hurd-gnu`](platform-support/hurd.md) | ✓ | ✓ | 32-bit GNU/Hurd [^x86_32-floats-return-ABI]
[`i686-unknown-netbsd`](platform-support/netbsd.md) | ✓ | ✓ | NetBSD/i386 with SSE2 [^x86_32-floats-return-ABI]
Expand Down Expand Up @@ -366,7 +369,6 @@ target | std | host | notes
[`x86_64-apple-tvos`](platform-support/apple-tvos.md) | ? | | x86 64-bit tvOS
[`x86_64-apple-watchos-sim`](platform-support/apple-watchos.md) | ✓ | | x86 64-bit Apple WatchOS simulator
[`x86_64-pc-nto-qnx710`](platform-support/nto-qnx.md) | ✓ | | x86 64-bit QNX Neutrino 7.1 RTOS |
[`x86_64-pc-windows-gnullvm`](platform-support/pc-windows-gnullvm.md) | ✓ | ✓ |
[`x86_64-unikraft-linux-musl`](platform-support/unikraft-linux-musl.md) | ✓ | | 64-bit Unikraft with musl 1.2.3
`x86_64-unknown-dragonfly` | ✓ | ✓ | 64-bit DragonFlyBSD
`x86_64-unknown-haiku` | ✓ | ✓ | 64-bit Haiku
Expand Down
36 changes: 25 additions & 11 deletions src/doc/rustc/src/platform-support/pc-windows-gnullvm.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# \*-pc-windows-gnullvm

**Tier: 3**
**Tier: 2 (without host tools)**

Windows targets similar to `*-pc-windows-gnu` but using UCRT as the runtime and various LLVM tools/libraries instead of GCC/Binutils.

Expand All @@ -12,38 +12,52 @@ Target triples available so far:
## Target maintainers

- [@mati865](https://github.com/mati865)
- [@thomcc](https://github.com/thomcc)

## Requirements

The easiest way to obtain these targets is cross-compilation but native build from `x86_64-pc-windows-gnu` is possible with few hacks which I don't recommend.
The easiest way to obtain these targets is cross-compilation, but native build from `x86_64-pc-windows-gnu` is possible with few hacks which I don't recommend.
Std support is expected to be on pair with `*-pc-windows-gnu`.

Binaries for this target should be at least on pair with `*-pc-windows-gnu` in terms of requirements and functionality.

Those targets follow Windows calling convention for `extern "C"`.

Like with any other Windows target created binaries are in PE format.
Like with any other Windows target, created binaries are in PE format.

## Building the target

For cross-compilation I recommend using [llvm-mingw](https://github.com/mstorsjo/llvm-mingw) toolchain, one change that seems necessary beside configuring cross compilers is disabling experimental `m86k` target. Otherwise LLVM build fails with `multiple definition ...` errors.
Native bootstrapping builds require rather fragile hacks until host artifacts are available so I won't describe them here.
These targets can be easily cross-compiled
using [llvm-mingw](https://github.com/mstorsjo/llvm-mingw) toolchain or [MSYS2 CLANG*](https://www.msys2.org/docs/environments/) environments.
Just fill `[target.*]` sections for both build and resulting compiler and set installation prefix in `config.toml`.
Then run `./x.py install`.
In my case I had ran `./x.py install --host x86_64-pc-windows-gnullvm --target x86_64-pc-windows-gnullvm` inside MSYS2 MINGW64 shell
so `x86_64-pc-windows-gnu` was my build toolchain.

Native bootstrapping is doable in two ways:
- cross-compile gnullvm host toolchain and use it as build toolchain for the next build,
- copy libunwind libraries and rename them to mimic libgcc like here: https://github.com/msys2/MINGW-packages/blob/68e640756df2df6df6afa60f025e3f936e7b977c/mingw-w64-rust/PKGBUILD#L108-L109, stage0 compiler will be mostly broken but good enough to build the next stage.

The second option might stop working anytime, so it's not recommended.

## Building Rust programs

Rust does not yet ship pre-compiled artifacts for this target. To compile for
this target, you will either need to build Rust with the target enabled (see
"Building the target" above), or build your own copy of `core` by using
`build-std` or similar.
Rust does ship a pre-compiled std library for those targets.
That means one can easily cross-compile for those targets from other hosts if C proper toolchain is installed.

Alternatively full toolchain can be built as described in the previous section.

## Testing

Created binaries work fine on Windows or Wine using native hardware. Testing AArch64 on x86_64 is problematic though and requires spending some time with QEMU.
Once these targets bootstrap themselves on native hardware they should pass Rust testsuite.
Most of x86_64 testsuite does pass when cross-compiling,
with exception for `rustdoc` and `ui-fulldeps` that fail with and error regarding a missing library,
they do pass in native builds though.
The only failing test is std's `process::tests::test_proc_thread_attributes` for unknown reason.

## Cross-compilation toolchains and C code

Compatible C code can be built with Clang's `aarch64-pc-windows-gnu`, `i686-pc-windows-gnullvm` and `x86_64-pc-windows-gnu` targets as long as LLVM based C toolchains are used.
Compatible C code can be built with Clang's `aarch64-pc-windows-gnu`, `i686-pc-windows-gnullvm` and `x86_64-pc-windows-gnu` targets as long as LLVM-based C toolchains are used.
Those include:
- [llvm-mingw](https://github.com/mstorsjo/llvm-mingw)
- [MSYS2 with CLANG* environment](https://www.msys2.org/docs/environments)
1 change: 1 addition & 0 deletions tests/ui/rfcs/rfc-2627-raw-dylib/dlltool-failed.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
//@ only-gnu
//@ only-windows
//@ needs-dlltool
//@ ignore-llvm
//@ compile-flags: --crate-type lib --emit link
//@ normalize-stderr-test: "[^ ']*/dlltool.exe" -> "$$DLLTOOL"
//@ normalize-stderr-test: "[^ ]*/foo.def" -> "$$DEF_FILE"
Expand Down
1 change: 1 addition & 0 deletions tests/ui/rfcs/rfc-2627-raw-dylib/invalid-dlltool.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

//@ only-gnu
//@ only-windows
//@ ignore-llvm
//@ compile-flags: --crate-type lib --emit link -Cdlltool=does_not_exit.exe
#[link(name = "foo", kind = "raw-dylib")]
extern "C" {
Expand Down

0 comments on commit 2eba855

Please sign in to comment.