diff options
| author | Jubilee <workingjubilee@gmail.com> | 2025-06-17 00:28:20 -0700 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2025-06-17 00:28:20 -0700 |
| commit | 38000833992f90ab20713a6ad0af48e898737b64 (patch) | |
| tree | fe8485d2fff66d9c6be64d0baf092dc7091dacaa /compiler/rustc_codegen_llvm/src/common.rs | |
| parent | 99c8475e529bfbaf738b12276431fe14d2e98bc3 (diff) | |
| parent | 9c1180b6238d163fc384d60d85647385d9210343 (diff) | |
| download | rust-38000833992f90ab20713a6ad0af48e898737b64.tar.gz rust-38000833992f90ab20713a6ad0af48e898737b64.zip | |
Rollup merge of #142598 - ostylk:fix/ppc64_llvmabi, r=nikic,workingjubilee
Set elf e_flags on ppc64 targets according to abi
(This PR contains the non user-facing changes of https://github.com/rust-lang/rust/pull/142321)
Fixes https://github.com/rust-lang/rust/issues/85589 by making sure that ld.lld errors out instead of generating a broken binary.
Basically the problem is that ld.lld assumes that all ppc64 object files with e_flags=0 are object files which use the ELFv2 ABI (this here is the check https://github.com/llvm/llvm-project/blob/main/lld/ELF/Arch/PPC64.cpp#L639).
This pull request sets the correct e_flags to indicate the used ABI so ld.lld errors out when encountering ELFv1 ABI files instead of generating a broken binary.
For example compare code generation for this program (file name ``min.rs``):
```rust
#![feature(no_core, lang_items, repr_simd)]
#![crate_type = "bin"]
#![no_core]
#![no_main]
#[lang = "sized"]
trait Sized {}
#[lang = "copy"]
trait Copy {}
#[lang = "panic_cannot_unwind"]
pub fn panic() -> ! {
loop {}
}
pub fn my_rad_unmangled_function() {
loop {}
}
pub fn my_rad_function() {
loop {}
}
#[no_mangle]
pub fn _start() {
my_rad_unmangled_function();
my_rad_function();
}
```
Compile with ``rustc --target=powerpc64-unknown-linux-gnu -C linker=ld.lld -C relocation-model=static min.rs``
Before change:
```
$ llvm-objdump -d min
Disassembly of section .text:
000000001001030c <.text>:
...
10010334: 7c 08 02 a6 mflr 0
10010338: f8 21 ff 91 stdu 1, -112(1)
1001033c: f8 01 00 80 std 0, 128(1)
10010340: 48 02 00 39 bl 0x10030378 <_ZN3min25my_rad_unmangled_function17h7471c49af58039f5E>
10010344: 60 00 00 00 nop
10010348: 48 02 00 49 bl 0x10030390 <_ZN3min15my_rad_function17h37112b8fd1008c9bE>
1001034c: 60 00 00 00 nop
...
```
The branch instructions ``bl 0x10030378`` and ``bl 0x10030390`` are jumping into the ``.opd`` section which is data. That is a broken binary (because fixing those branches is the task of the linker).
After change:
```
error: linking with `ld.lld` failed: exit status: 1
|
= note: "ld.lld" "/tmp/rustcNYKZCS/symbols.o" "<1 object files omitted>" "--as-needed" "-L" "/tmp/rustcNYKZCS/raw-dylibs" "-Bdynamic" "--eh-frame-hdr" "-z" "noexecstack" "-L" "<sysroot>/lib/rustlib/powerpc64-unknown-linux-gnu/lib" "-o" "min" "--gc-sections" "-z" "relro" "-z" "now"
= note: some arguments are omitted. use `--verbose` to show all linker arguments
= note: ld.lld: error: /tmp/rustcNYKZCS/symbols.o: ABI version 1 is not supported
```
Which is correct because ld.lld doesn't support ELFv1 ABI.
Diffstat (limited to 'compiler/rustc_codegen_llvm/src/common.rs')
0 files changed, 0 insertions, 0 deletions
