Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
38 changes: 36 additions & 2 deletions compiler/rustc_codegen_llvm/src/attributes.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,16 +3,17 @@ use rustc_hir::attrs::{InlineAttr, InstructionSetAttr, OptimizeAttr, RtsanSettin
use rustc_hir::def_id::DefId;
use rustc_hir::find_attr;
use rustc_middle::middle::codegen_fn_attrs::{
CodegenFnAttrFlags, CodegenFnAttrs, PatchableFunctionEntry, SanitizerFnAttrs,
CodegenFnAttrFlags, CodegenFnAttrs, PatchableFunctionEntry, SanitizerFnAttrs, TargetFeature,
};
use rustc_middle::ty::{self, TyCtxt};
use rustc_session::config::{BranchProtection, FunctionReturn, OptLevel, PAuthKey, PacRet};
use rustc_span::sym;
use rustc_symbol_mangling::mangle_internal_symbol;
use rustc_target::spec::{Arch, FramePointer, SanitizerSet, StackProbeType, StackProtector};
use smallvec::SmallVec;

use crate::context::SimpleCx;
use crate::errors::SanitizerMemtagRequiresMte;
use crate::errors::{PackedStackBackchainNeedsSoftfloat, SanitizerMemtagRequiresMte};
use crate::llvm::AttributePlace::Function;
use crate::llvm::{
self, AllocKindFlags, Attribute, AttributeKind, AttributePlace, MemoryEffects, Value,
Expand Down Expand Up @@ -301,6 +302,36 @@ fn stackprotector_attr<'ll>(cx: &SimpleCx<'ll>, sess: &Session) -> Option<&'ll A
Some(sspattr.create_attr(cx.llcx))
}

fn packed_stack_attr<'ll>(
cx: &SimpleCx<'ll>,
sess: &Session,
function_attributes: &Vec<TargetFeature>,
) -> Option<&'ll Attribute> {
if sess.target.arch != Arch::S390x {
return None;
}
if !sess.opts.unstable_opts.packed_stack {
return None;
}

// The backchain and softfloat flags can be set via -Ctarget-features=...
// or via #[target_features(enable = ...)] so we have to check both possibilities
let have_backchain = sess.unstable_target_features.contains(&sym::backchain)
|| function_attributes.iter().any(|feature| feature.name == sym::backchain);
let have_softfloat = sess.unstable_target_features.contains(&sym::soft_float)
|| function_attributes.iter().any(|feature| feature.name == sym::soft_float);

// If both, backchain and packedstack, are enabled LLVM cannot generate valid function entry points
// with the default ABI. However if the softfloat flag is set LLVM will switch to the softfloat
// ABI, where this works.
if have_backchain && !have_softfloat {
sess.dcx().emit_err(PackedStackBackchainNeedsSoftfloat);
return None;
}

Some(llvm::CreateAttrString(cx.llcx, "packed-stack"))
}

pub(crate) fn target_cpu_attr<'ll>(cx: &SimpleCx<'ll>, sess: &Session) -> &'ll Attribute {
let target_cpu = llvm_util::target_cpu(sess);
llvm::CreateAttrStringValue(cx.llcx, "target-cpu", target_cpu)
Expand Down Expand Up @@ -516,6 +547,9 @@ pub(crate) fn llfn_attrs_from_instance<'ll, 'tcx>(
if let Some(align) = codegen_fn_attrs.alignment {
llvm::set_alignment(llfn, align);
}
if let Some(packed_stack) = packed_stack_attr(cx, sess, &codegen_fn_attrs.target_features) {
to_add.push(packed_stack);
}
to_add.extend(patchable_function_entry_attrs(
cx,
sess,
Expand Down
7 changes: 7 additions & 0 deletions compiler/rustc_codegen_llvm/src/errors.rs
Original file line number Diff line number Diff line change
Expand Up @@ -204,3 +204,10 @@ pub(crate) struct MismatchedDataLayout<'a> {
pub(crate) struct FixedX18InvalidArch<'a> {
pub arch: &'a str,
}

#[derive(Diagnostic)]
#[diag("`-Zpacked-stack` is incompatible with `backchain` target feature")]
#[note(
"enabling both `-Zpacked-stack` and the `backchain` target feature is incompatible with the default s390x ABI. Switch to s390x-unknown-none-softfloat if you need both attributes"
)]
pub(crate) struct PackedStackBackchainNeedsSoftfloat;
4 changes: 4 additions & 0 deletions compiler/rustc_session/src/errors.rs
Original file line number Diff line number Diff line change
Expand Up @@ -530,3 +530,7 @@ pub(crate) struct UnexpectedBuiltinCfg {
#[derive(Diagnostic)]
#[diag("ThinLTO is not supported by the codegen backend, using fat LTO instead")]
pub(crate) struct ThinLtoNotSupportedByBackend;

#[derive(Diagnostic)]
#[diag("`-Zpacked-stack` is only supported on s390x")]
pub(crate) struct UnsupportedPackedStack;
2 changes: 2 additions & 0 deletions compiler/rustc_session/src/options.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2543,6 +2543,8 @@ options! {
"pass `-install_name @rpath/...` to the macOS linker (default: no)"),
packed_bundled_libs: bool = (false, parse_bool, [TRACKED],
"change rlib format to store native libraries as archives"),
packed_stack: bool = (false, parse_bool, [TRACKED],
"use packed stack frames (s390x only) (default: no)"),
panic_abort_tests: bool = (false, parse_bool, [TRACKED],
"support compiling tests with panic=abort (default: no)"),
panic_in_drop: PanicStrategy = (PanicStrategy::Unwind, parse_panic_strategy, [TRACKED],
Expand Down
6 changes: 6 additions & 0 deletions compiler/rustc_session/src/session.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1360,6 +1360,12 @@ fn validate_commandline_args_with_session_available(sess: &Session) {
}
}
}

if sess.opts.unstable_opts.packed_stack {
if sess.target.arch != Arch::S390x {
sess.dcx().emit_err(errors::UnsupportedPackedStack);
}
}
}

/// Holds data on the current incremental compilation session, if there is one.
Expand Down
2 changes: 2 additions & 0 deletions compiler/rustc_span/src/symbol.rs
Original file line number Diff line number Diff line change
Expand Up @@ -505,6 +505,7 @@ symbols! {
avx512bw,
avx512f,
await_macro,
backchain,
bang,
begin_panic,
bench,
Expand Down Expand Up @@ -1917,6 +1918,7 @@ symbols! {
slice_len_fn,
slice_patterns,
slicing_syntax,
soft_float: "soft-float",
sparc,
sparc64,
sparc_target_feature,
Expand Down
37 changes: 37 additions & 0 deletions tests/assembly-llvm/s390x-packedstack-toggle.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
//@ add-minicore
//@ revisions: enable-packedstack default-packedstack
//@ assembly-output: emit-asm
//@ compile-flags: -Copt-level=3 --crate-type=lib --target=s390x-unknown-linux-gnu -Cforce-unwind-tables=no
//@ needs-llvm-components: systemz
//@[enable-packedstack] compile-flags: -Zpacked-stack
#![feature(no_core, lang_items)]
#![no_std]
#![no_core]

extern crate minicore;
use minicore::*;

extern "C" {
fn extern_func() -> i32;
}

// CHECK-LABEL: test_packedstack
#[no_mangle]
extern "C" fn test_packedstack() -> i32 {
// test the creation of call stack with and without packed-stack

// without packed-stack we always reserve a least the maximal space of 160 bytes
// default-packedstack: stmg %r14, %r15, 112(%r15)
// default-packedstack-NEXT: aghi %r15, -160
// default-packedstack-NEXT: brasl %r14, extern_func

// with packed-stack only the actually needed registers are reserved on the stack
// enable-packedstack: stmg %r14, %r15, 144(%r15)
// enable-packedstack-NEXT: aghi %r15, -16
// enable-packedstack-NEXT: brasl %r14, extern_func
unsafe {
extern_func();
}
1
// CHECK: br %r{{.*}}
}
18 changes: 18 additions & 0 deletions tests/codegen-llvm/packedstack.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
//@ add-minicore
//@ compile-flags: -Copt-level=3 --crate-type=lib --target=s390x-unknown-none-softfloat -Zpacked-stack
//@ needs-llvm-components: systemz
#![feature(s390x_target_feature)]
#![crate_type = "lib"]
#![feature(no_core, lang_items)]
#![no_core]

extern crate minicore;
use minicore::*;

#[no_mangle]

pub fn test_packedstack() {
// CHECK: @test_packedstack() unnamed_addr #0
}

// CHECK: attributes #0 = { {{.*}}"packed-stack"{{.*}} }
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
error: `-Zpacked-stack` is incompatible with `backchain` target feature
|
= note: enabling both `-Zpacked-stack` and the `backchain` target feature is incompatible with the default s390x ABI. Switch to s390x-unknown-none-softfloat if you need both attributes

error: aborting due to 1 previous error

Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
warning: unstable feature specified for `-Ctarget-feature`: `backchain`
|
= note: this feature is not stably supported; its behavior can change in the future

error: packedstack with backchain needs softfloat
|
= note: enabling both `-Zpacked-stack` and the `backchain` target feature is incompatible with the default s390x ABI. Switch to s390x-unknown-none-softfloat if you need both attributes

error: aborting due to 1 previous error; 1 warning emitted

44 changes: 44 additions & 0 deletions tests/ui/target-feature/packedstack-combinations.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
//@ add-minicore
//@ revisions: wrong_arch only_packedstack backchain_attr backchain_cli with_softfloat
//@ compile-flags: -Zpacked-stack --crate-type=rlib
//@ ignore-backends: gcc

//@ [wrong_arch] compile-flags: --target=x86_64-unknown-linux-gnu
//@ [wrong_arch] should-fail
//@ [wrong_arch] needs-llvm-components: x86

//@ [only_packedstack] compile-flags: --target=s390x-unknown-linux-gnu
//@ [only_packedstack] build-pass
//@ [only_packedstack] needs-llvm-components: systemz

//@ [backchain_attr] compile-flags: --target=s390x-unknown-linux-gnu
//@ [backchain_attr] build-fail
//@ [backchain_attr] needs-llvm-components: systemz

//@ [backchain_cli] compile-flags: -Ctarget-feature=+backchain --target=s390x-unknown-linux-gnu
//@ [backchain_cli] should-fail
//@ [backchain_cli] needs-llvm-components: systemz

//@ [with_softfloat] compile-flags: -Ctarget-feature=+backchain
//@ [with_softfloat] compile-flags: --target=s390x-unknown-none-softfloat
//@ [with_softfloat] build-pass
//@ [with_softfloat] needs-llvm-components: systemz

#![feature(s390x_target_feature)]
#![crate_type = "rlib"]
#![feature(no_core,lang_items)]
#![no_core]

extern crate minicore;
use minicore::*;

#[no_mangle]
#[cfg_attr(backchain_attr,target_feature(enable = "backchain"))]
pub fn test() {
}

//[wrong_arch]~? ERROR `-Zpacked-stack` is only supported on s390x
//[backchain_cli]~? WARN unstable feature specified for `-Ctarget-feature`: `backchain`
//[backchain_cli]~? ERROR `-Zpacked-stack` is incompatible with `backchain` target feature
//[backchain_attr]~? ERROR `-Zpacked-stack` is incompatible with `backchain` target feature
//[with_softfloat]~? WARN unstable feature specified for `-Ctarget-feature`: `backchain`
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
warning: unstable feature specified for `-Ctarget-feature`: `backchain`
|
= note: this feature is not stably supported; its behavior can change in the future

warning: 1 warning emitted

Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
error: `-Zpacked-stack` is only supported on s390x

error: aborting due to 1 previous error

Loading