Auto merge of #80838 - nagisa:nagisa/stack-probe-type, r=cuviper

Target stack-probe support configurable finely

This adds capability to configure the target's stack probe support in a
more precise manner than just on/off. In particular now we allow
choosing between always inline-asm, always call or either one of those
depending on the LLVM version.

Note that this removes the ability to turn off the generation of the
stack-probe attribute. This is valid to replace it with inline-asm for all targets because
`probe-stack="inline-asm"` will not generate any machine code on targets
that do not currently support stack probes. This makes support for stack
probes on targets that don't have any right now automatic with LLVM
upgrades in the future.

(This is valid to do based on the fact that clang unconditionally sets
this attribute when `-fstack-clash-protection` is used, AFAICT)

cc #77885
r? `@cuviper`
This commit is contained in:
bors 2021-01-24 09:44:42 +00:00
commit 72c7b70267
35 changed files with 205 additions and 87 deletions

View File

@ -13,6 +13,7 @@ use rustc_middle::ty::query::Providers;
use rustc_middle::ty::{self, TyCtxt};
use rustc_session::config::{OptLevel, SanitizerSet};
use rustc_session::Session;
use rustc_target::spec::StackProbeType;
use crate::attributes;
use crate::llvm::AttributePlace::Function;
@ -98,12 +99,6 @@ fn set_instrument_function(cx: &CodegenCx<'ll, '_>, llfn: &'ll Value) {
}
fn set_probestack(cx: &CodegenCx<'ll, '_>, llfn: &'ll Value) {
// Only use stack probes if the target specification indicates that we
// should be using stack probes
if !cx.sess().target.stack_probes {
return;
}
// Currently stack probes seem somewhat incompatible with the address
// sanitizer and thread sanitizer. With asan we're already protected from
// stack overflow anyway so we don't really need stack probes regardless.
@ -127,19 +122,31 @@ fn set_probestack(cx: &CodegenCx<'ll, '_>, llfn: &'ll Value) {
return;
}
llvm::AddFunctionAttrStringValue(
llfn,
llvm::AttributePlace::Function,
const_cstr!("probe-stack"),
if llvm_util::get_version() < (11, 0, 1) {
// Flag our internal `__rust_probestack` function as the stack probe symbol.
// This is defined in the `compiler-builtins` crate for each architecture.
const_cstr!("__rust_probestack")
} else {
// On LLVM 11+, emit inline asm for stack probes instead of a function call.
const_cstr!("inline-asm")
},
);
let attr_value = match cx.sess().target.stack_probes {
StackProbeType::None => None,
// Request LLVM to generate the probes inline. If the given LLVM version does not support
// this, no probe is generated at all (even if the attribute is specified).
StackProbeType::Inline => Some(const_cstr!("inline-asm")),
// Flag our internal `__rust_probestack` function as the stack probe symbol.
// This is defined in the `compiler-builtins` crate for each architecture.
StackProbeType::Call => Some(const_cstr!("__rust_probestack")),
// Pick from the two above based on the LLVM version.
StackProbeType::InlineOrCall { min_llvm_version_for_inline } => {
if llvm_util::get_version() < min_llvm_version_for_inline {
Some(const_cstr!("__rust_probestack"))
} else {
Some(const_cstr!("inline-asm"))
}
}
};
if let Some(attr_value) = attr_value {
llvm::AddFunctionAttrStringValue(
llfn,
llvm::AttributePlace::Function,
const_cstr!("probe-stack"),
attr_value,
);
}
}
pub fn llvm_target_features(sess: &Session) -> impl Iterator<Item = &str> {

View File

@ -1,5 +1,5 @@
use super::apple_sdk_base::{opts, Arch};
use crate::spec::{Target, TargetOptions};
use crate::spec::{StackProbeType, Target, TargetOptions};
pub fn target() -> Target {
let base = opts("ios", Arch::I386);
@ -10,6 +10,10 @@ pub fn target() -> Target {
f64:32:64-f80:128-n8:16:32-S128"
.to_string(),
arch: "x86".to_string(),
options: TargetOptions { max_atomic_width: Some(64), stack_probes: true, ..base },
options: TargetOptions {
max_atomic_width: Some(64),
stack_probes: StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) },
..base
},
}
}

View File

@ -1,4 +1,4 @@
use crate::spec::{LinkerFlavor, Target, TargetOptions};
use crate::spec::{LinkerFlavor, StackProbeType, Target, TargetOptions};
pub fn target() -> Target {
let mut base = super::apple_base::opts("macos");
@ -6,7 +6,7 @@ pub fn target() -> Target {
base.max_atomic_width = Some(64);
base.pre_link_args.insert(LinkerFlavor::Gcc, vec!["-m32".to_string()]);
base.link_env_remove.extend(super::apple_base::macos_link_env_remove());
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
base.eliminate_frame_pointer = false;
// Clang automatically chooses a more specific target based on

View File

@ -1,4 +1,4 @@
use crate::spec::Target;
use crate::spec::{StackProbeType, Target};
// See https://developer.android.com/ndk/guides/abis.html#x86
// for target ABI requirements.
@ -11,7 +11,7 @@ pub fn target() -> Target {
// http://developer.android.com/ndk/guides/abis.html#x86
base.cpu = "pentiumpro".to_string();
base.features = "+mmx,+sse,+sse2,+sse3,+ssse3".to_string();
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "i686-linux-android".to_string(),

View File

@ -1,4 +1,4 @@
use crate::spec::{LinkerFlavor, Target};
use crate::spec::{LinkerFlavor, StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::freebsd_base::opts();
@ -7,7 +7,7 @@ pub fn target() -> Target {
let pre_link_args = base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap();
pre_link_args.push("-m32".to_string());
pre_link_args.push("-Wl,-znotext".to_string());
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "i686-unknown-freebsd".to_string(),

View File

@ -1,11 +1,11 @@
use crate::spec::{LinkerFlavor, Target};
use crate::spec::{LinkerFlavor, StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::haiku_base::opts();
base.cpu = "pentium4".to_string();
base.max_atomic_width = Some(64);
base.pre_link_args.insert(LinkerFlavor::Gcc, vec!["-m32".to_string()]);
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "i686-unknown-haiku".to_string(),

View File

@ -1,11 +1,11 @@
use crate::spec::{LinkerFlavor, Target};
use crate::spec::{LinkerFlavor, StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::linux_gnu_base::opts();
base.cpu = "pentium4".to_string();
base.max_atomic_width = Some(64);
base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-m32".to_string());
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "i686-unknown-linux-gnu".to_string(),

View File

@ -1,4 +1,4 @@
use crate::spec::{LinkerFlavor, Target};
use crate::spec::{LinkerFlavor, StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::linux_musl_base::opts();
@ -6,7 +6,7 @@ pub fn target() -> Target {
base.max_atomic_width = Some(64);
base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-m32".to_string());
base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-Wl,-melf_i386".to_string());
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
// The unwinder used by i686-unknown-linux-musl, the LLVM libunwind
// implementation, apparently relies on frame pointers existing... somehow.

View File

@ -1,11 +1,11 @@
use crate::spec::{LinkerFlavor, Target, TargetOptions};
use crate::spec::{LinkerFlavor, StackProbeType, Target, TargetOptions};
pub fn target() -> Target {
let mut base = super::netbsd_base::opts();
base.cpu = "pentium4".to_string();
base.max_atomic_width = Some(64);
base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-m32".to_string());
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "i686-unknown-netbsdelf".to_string(),

View File

@ -1,4 +1,4 @@
use crate::spec::{LinkerFlavor, Target};
use crate::spec::{LinkerFlavor, StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::openbsd_base::opts();
@ -6,7 +6,7 @@ pub fn target() -> Target {
base.max_atomic_width = Some(64);
base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-m32".to_string());
base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-fuse-ld=lld".to_string());
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "i686-unknown-openbsd".to_string(),

View File

@ -1,11 +1,11 @@
use crate::spec::{LinkerFlavor, Target};
use crate::spec::{LinkerFlavor, StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::vxworks_base::opts();
base.cpu = "pentium4".to_string();
base.max_atomic_width = Some(64);
base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-m32".to_string());
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "i686-unknown-linux-gnu".to_string(),

View File

@ -1,4 +1,6 @@
use crate::spec::{LinkArgs, LinkerFlavor, PanicStrategy, RelocModel, RelroLevel, TargetOptions};
use crate::spec::{
LinkArgs, LinkerFlavor, PanicStrategy, RelocModel, RelroLevel, StackProbeType, TargetOptions,
};
pub fn opts() -> TargetOptions {
let mut pre_link_args = LinkArgs::new();
@ -11,7 +13,7 @@ pub fn opts() -> TargetOptions {
env: "gnu".to_string(),
disable_redzone: true,
panic_strategy: PanicStrategy::Abort,
stack_probes: true,
stack_probes: StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) },
eliminate_frame_pointer: false,
linker_is_gnu: true,
position_independent_executables: true,

View File

@ -40,6 +40,7 @@ use crate::spec::crt_objects::{CrtObjects, CrtObjectsFallback};
use rustc_serialize::json::{Json, ToJson};
use rustc_span::symbol::{sym, Symbol};
use std::collections::BTreeMap;
use std::convert::TryFrom;
use std::ops::{Deref, DerefMut};
use std::path::{Path, PathBuf};
use std::str::FromStr;
@ -479,6 +480,83 @@ macro_rules! supported_targets {
};
}
#[derive(Clone, Debug, PartialEq, Eq)]
pub enum StackProbeType {
/// Don't emit any stack probes.
None,
/// It is harmless to use this option even on targets that do not have backend support for
/// stack probes as the failure mode is the same as if no stack-probe option was specified in
/// the first place.
Inline,
/// Call `__rust_probestack` whenever stack needs to be probed.
Call,
/// Use inline option for LLVM versions later than specified in `min_llvm_version_for_inline`
/// and call `__rust_probestack` otherwise.
InlineOrCall { min_llvm_version_for_inline: (u32, u32, u32) },
}
impl StackProbeType {
fn from_json(json: &Json) -> Result<Self, String> {
let object = json.as_object().ok_or_else(|| "expected a JSON object")?;
let kind = object
.get("kind")
.and_then(|o| o.as_string())
.ok_or_else(|| "expected `kind` to be a string")?;
match kind {
"none" => Ok(StackProbeType::None),
"inline" => Ok(StackProbeType::Inline),
"call" => Ok(StackProbeType::Call),
"inline-or-call" => {
let min_version = object
.get("min-llvm-version-for-inline")
.and_then(|o| o.as_array())
.ok_or_else(|| "expected `min-llvm-version-for-inline` to be an array")?;
let mut iter = min_version.into_iter().map(|v| {
let int = v.as_u64().ok_or_else(
|| "expected `min-llvm-version-for-inline` values to be integers",
)?;
u32::try_from(int)
.map_err(|_| "`min-llvm-version-for-inline` values don't convert to u32")
});
let min_llvm_version_for_inline = (
iter.next().unwrap_or(Ok(11))?,
iter.next().unwrap_or(Ok(0))?,
iter.next().unwrap_or(Ok(0))?,
);
Ok(StackProbeType::InlineOrCall { min_llvm_version_for_inline })
}
_ => Err(String::from(
"`kind` expected to be one of `inline-or-none`, `call` or `inline-or-call`",
)),
}
}
}
impl ToJson for StackProbeType {
fn to_json(&self) -> Json {
Json::Object(match self {
StackProbeType::None => {
vec![(String::from("kind"), "none".to_json())].into_iter().collect()
}
StackProbeType::Inline => {
vec![(String::from("kind"), "inline".to_json())].into_iter().collect()
}
StackProbeType::Call => {
vec![(String::from("kind"), "call".to_json())].into_iter().collect()
}
StackProbeType::InlineOrCall { min_llvm_version_for_inline } => vec![
(String::from("kind"), "inline-or-call".to_json()),
(
String::from("min-llvm-version-for-inline"),
min_llvm_version_for_inline.to_json(),
),
]
.into_iter()
.collect(),
})
}
}
supported_targets! {
("x86_64-unknown-linux-gnu", x86_64_unknown_linux_gnu),
("x86_64-unknown-linux-gnux32", x86_64_unknown_linux_gnux32),
@ -926,8 +1004,8 @@ pub struct TargetOptions {
/// Whether or not crt-static is respected by the compiler (or is a no-op).
pub crt_static_respected: bool,
/// Whether or not stack probes (__rust_probestack) are enabled
pub stack_probes: bool,
/// The implementation of stack probes to use.
pub stack_probes: StackProbeType,
/// The minimum alignment for global symbols.
pub min_global_align: Option<u64>,
@ -1085,7 +1163,7 @@ impl Default for TargetOptions {
crt_static_allows_dylibs: false,
crt_static_default: false,
crt_static_respected: false,
stack_probes: false,
stack_probes: StackProbeType::None,
min_global_align: None,
default_codegen_units: None,
trap_unreachable: true,
@ -1361,6 +1439,18 @@ impl Target {
Some(Ok(()))
})).unwrap_or(Ok(()))
} );
($key_name:ident, StackProbeType) => ( {
let name = (stringify!($key_name)).replace("_", "-");
obj.find(&name[..]).and_then(|o| match StackProbeType::from_json(o) {
Ok(v) => {
base.$key_name = v;
Some(Ok(()))
},
Err(s) => Some(Err(
format!("`{:?}` is not a valid value for `{}`: {}", o, name, s)
)),
}).unwrap_or(Ok(()))
} );
($key_name:ident, crt_objects_fallback) => ( {
let name = (stringify!($key_name)).replace("_", "-");
obj.find(&name[..]).and_then(|o| o.as_string().and_then(|s| {
@ -1516,7 +1606,7 @@ impl Target {
key!(crt_static_allows_dylibs, bool);
key!(crt_static_default, bool);
key!(crt_static_respected, bool);
key!(stack_probes, bool);
key!(stack_probes, StackProbeType)?;
key!(min_global_align, Option<u64>);
key!(default_codegen_units, Option<u64>);
key!(trap_unreachable, bool);

View File

@ -9,7 +9,7 @@
// the timer-interrupt. Device-drivers are required to use polling-based models. Furthermore, all
// code runs in the same environment, no process separation is supported.
use crate::spec::{LinkerFlavor, LldFlavor, PanicStrategy, TargetOptions};
use crate::spec::{LinkerFlavor, LldFlavor, PanicStrategy, StackProbeType, TargetOptions};
pub fn opts() -> TargetOptions {
let mut base = super::msvc_base::opts();
@ -43,7 +43,9 @@ pub fn opts() -> TargetOptions {
exe_suffix: ".efi".to_string(),
allows_weak_linkage: false,
panic_strategy: PanicStrategy::Abort,
stack_probes: true,
// LLVM does not emit inline assembly because the LLVM target does not get considered as…
// "Windows".
stack_probes: StackProbeType::Call,
singlethread: true,
linker: Some("rust-lld".to_string()),
..base

View File

@ -1,4 +1,4 @@
use crate::spec::{LinkerFlavor, Target, TargetOptions};
use crate::spec::{LinkerFlavor, StackProbeType, Target, TargetOptions};
pub fn target() -> Target {
let mut base = super::apple_base::opts("macos");
@ -10,7 +10,7 @@ pub fn target() -> Target {
vec!["-m64".to_string(), "-arch".to_string(), "x86_64".to_string()],
);
base.link_env_remove.extend(super::apple_base::macos_link_env_remove());
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
// Clang automatically chooses a more specific target based on
// MACOSX_DEPLOYMENT_TARGET. To enable cross-language LTO to work

View File

@ -1,5 +1,5 @@
use super::apple_sdk_base::{opts, Arch};
use crate::spec::{Target, TargetOptions};
use crate::spec::{StackProbeType, Target, TargetOptions};
pub fn target() -> Target {
let base = opts("ios", Arch::X86_64);
@ -9,6 +9,10 @@ pub fn target() -> Target {
data_layout: "e-m:o-p270:32:32-p271:32:32-p272:64:64-i64:64-f80:128-n8:16:32:64-S128"
.to_string(),
arch: "x86_64".to_string(),
options: TargetOptions { max_atomic_width: Some(64), stack_probes: true, ..base },
options: TargetOptions {
max_atomic_width: Some(64),
stack_probes: StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) },
..base
},
}
}

View File

@ -1,5 +1,5 @@
use super::apple_sdk_base::{opts, Arch};
use crate::spec::{Target, TargetOptions};
use crate::spec::{StackProbeType, Target, TargetOptions};
pub fn target() -> Target {
let base = opts("ios", Arch::X86_64_macabi);
@ -9,6 +9,10 @@ pub fn target() -> Target {
data_layout: "e-m:o-p270:32:32-p271:32:32-p272:64:64-i64:64-f80:128-n8:16:32:64-S128"
.to_string(),
arch: "x86_64".to_string(),
options: TargetOptions { max_atomic_width: Some(64), stack_probes: true, ..base },
options: TargetOptions {
max_atomic_width: Some(64),
stack_probes: StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) },
..base
},
}
}

View File

@ -1,5 +1,5 @@
use super::apple_sdk_base::{opts, Arch};
use crate::spec::{Target, TargetOptions};
use crate::spec::{StackProbeType, Target, TargetOptions};
pub fn target() -> Target {
let base = opts("tvos", Arch::X86_64);
@ -8,6 +8,10 @@ pub fn target() -> Target {
pointer_width: 64,
data_layout: "e-m:o-i64:64-f80:128-n8:16:32:64-S128".to_string(),
arch: "x86_64".to_string(),
options: TargetOptions { max_atomic_width: Some(64), stack_probes: true, ..base },
options: TargetOptions {
max_atomic_width: Some(64),
stack_probes: StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) },
..base
},
}
}

View File

@ -1,10 +1,10 @@
use crate::spec::Target;
use crate::spec::{StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::fuchsia_base::opts();
base.cpu = "x86-64".to_string();
base.max_atomic_width = Some(64);
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "x86_64-fuchsia".to_string(),

View File

@ -1,4 +1,4 @@
use crate::spec::{LinkerFlavor, Target};
use crate::spec::{LinkerFlavor, StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::android_base::opts();
@ -7,7 +7,7 @@ pub fn target() -> Target {
base.features = "+mmx,+sse,+sse2,+sse3,+ssse3,+sse4.1,+sse4.2,+popcnt".to_string();
base.max_atomic_width = Some(64);
base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-m64".to_string());
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "x86_64-linux-android".to_string(),

View File

@ -1,4 +1,4 @@
use crate::spec::{LinkerFlavor, Target, TargetOptions};
use crate::spec::{LinkerFlavor, StackProbeType, Target, TargetOptions};
pub fn target() -> Target {
let mut base = super::netbsd_base::opts();
@ -12,7 +12,7 @@ pub fn target() -> Target {
base.has_rpath = false;
base.position_independent_executables = false;
base.disable_redzone = true;
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "x86_64-rumprun-netbsd".to_string(),

View File

@ -1,11 +1,11 @@
use crate::spec::{LinkerFlavor, Target};
use crate::spec::{LinkerFlavor, StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::solaris_base::opts();
base.pre_link_args.insert(LinkerFlavor::Gcc, vec!["-m64".to_string()]);
base.cpu = "x86-64".to_string();
base.max_atomic_width = Some(64);
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "x86_64-pc-solaris".to_string(),

View File

@ -1,11 +1,11 @@
use crate::spec::{LinkerFlavor, Target};
use crate::spec::{LinkerFlavor, StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::dragonfly_base::opts();
base.cpu = "x86-64".to_string();
base.max_atomic_width = Some(64);
base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-m64".to_string());
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "x86_64-unknown-dragonfly".to_string(),

View File

@ -1,11 +1,11 @@
use crate::spec::{LinkerFlavor, Target};
use crate::spec::{LinkerFlavor, StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::freebsd_base::opts();
base.cpu = "x86-64".to_string();
base.max_atomic_width = Some(64);
base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-m64".to_string());
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "x86_64-unknown-freebsd".to_string(),

View File

@ -1,11 +1,11 @@
use crate::spec::{LinkerFlavor, Target};
use crate::spec::{LinkerFlavor, StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::haiku_base::opts();
base.cpu = "x86-64".to_string();
base.max_atomic_width = Some(64);
base.pre_link_args.insert(LinkerFlavor::Gcc, vec!["-m64".to_string()]);
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
// This option is required to build executables on Haiku x86_64
base.position_independent_executables = true;

View File

@ -1,11 +1,11 @@
use crate::spec::Target;
use crate::spec::{StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::hermit_base::opts();
base.cpu = "x86-64".to_string();
base.max_atomic_width = Some(64);
base.features = "+rdrnd,+rdseed".to_string();
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "x86_64-unknown-hermit".to_string(),

View File

@ -1,4 +1,4 @@
use crate::spec::Target;
use crate::spec::{StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::hermit_kernel_base::opts();
@ -7,7 +7,7 @@ pub fn target() -> Target {
base.features =
"-mmx,-sse,-sse2,-sse3,-ssse3,-sse4.1,-sse4.2,-3dnow,-3dnowa,-avx,-avx2,+soft-float"
.to_string();
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "x86_64-unknown-hermit".to_string(),

View File

@ -1,11 +1,11 @@
use crate::spec::{LinkerFlavor, Target};
use crate::spec::{LinkerFlavor, StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::linux_gnu_base::opts();
base.cpu = "x86-64".to_string();
base.max_atomic_width = Some(64);
base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-m64".to_string());
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "x86_64-unknown-linux-gnu".to_string(),

View File

@ -1,11 +1,11 @@
use crate::spec::{LinkerFlavor, Target};
use crate::spec::{LinkerFlavor, StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::linux_gnu_base::opts();
base.cpu = "x86-64".to_string();
base.max_atomic_width = Some(64);
base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-mx32".to_string());
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
base.has_elf_tls = false;
// BUG(GabrielMajeri): disabling the PLT on x86_64 Linux with x32 ABI
// breaks code gen. See LLVM bug 36743

View File

@ -1,11 +1,11 @@
use crate::spec::{LinkerFlavor, Target};
use crate::spec::{LinkerFlavor, StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::linux_musl_base::opts();
base.cpu = "x86-64".to_string();
base.max_atomic_width = Some(64);
base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-m64".to_string());
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
base.static_position_independent_executables = true;
Target {

View File

@ -1,11 +1,11 @@
use crate::spec::{LinkerFlavor, Target, TargetOptions};
use crate::spec::{LinkerFlavor, StackProbeType, Target, TargetOptions};
pub fn target() -> Target {
let mut base = super::netbsd_base::opts();
base.cpu = "x86-64".to_string();
base.max_atomic_width = Some(64);
base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-m64".to_string());
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "x86_64-unknown-netbsd".to_string(),

View File

@ -1,11 +1,11 @@
use crate::spec::{LinkerFlavor, Target};
use crate::spec::{LinkerFlavor, StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::openbsd_base::opts();
base.cpu = "x86-64".to_string();
base.max_atomic_width = Some(64);
base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-m64".to_string());
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "x86_64-unknown-openbsd".to_string(),

View File

@ -1,11 +1,11 @@
use crate::spec::{LinkerFlavor, Target};
use crate::spec::{LinkerFlavor, StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::redox_base::opts();
base.cpu = "x86-64".to_string();
base.max_atomic_width = Some(64);
base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-m64".to_string());
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
Target {
llvm_target: "x86_64-unknown-redox".to_string(),

View File

@ -1,11 +1,11 @@
use crate::spec::{LinkerFlavor, Target};
use crate::spec::{LinkerFlavor, StackProbeType, Target};
pub fn target() -> Target {
let mut base = super::vxworks_base::opts();
base.cpu = "x86-64".to_string();
base.max_atomic_width = Some(64);
base.pre_link_args.get_mut(&LinkerFlavor::Gcc).unwrap().push("-m64".to_string());
base.stack_probes = true;
base.stack_probes = StackProbeType::InlineOrCall { min_llvm_version_for_inline: (11, 0, 1) };
base.disable_redzone = true;
Target {

View File

@ -1,4 +1,5 @@
// run-pass
// Tests that we can compare various kinds of extern fn signatures.
#![allow(non_camel_case_types)]