Use Symbol for target features in asm handling
This saves a couple of Symbol::intern calls
This commit is contained in:
parent
a34c079752
commit
991cbd1503
20 changed files with 91 additions and 69 deletions
|
@ -6,7 +6,7 @@ use rustc_data_structures::stable_set::FxHashSet;
|
||||||
use rustc_errors::struct_span_err;
|
use rustc_errors::struct_span_err;
|
||||||
use rustc_hir as hir;
|
use rustc_hir as hir;
|
||||||
use rustc_session::parse::feature_err;
|
use rustc_session::parse::feature_err;
|
||||||
use rustc_span::{sym, Span, Symbol};
|
use rustc_span::{sym, Span};
|
||||||
use rustc_target::asm;
|
use rustc_target::asm;
|
||||||
use std::collections::hash_map::Entry;
|
use std::collections::hash_map::Entry;
|
||||||
use std::fmt::Write;
|
use std::fmt::Write;
|
||||||
|
@ -66,7 +66,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||||
for (abi_name, abi_span) in &asm.clobber_abis {
|
for (abi_name, abi_span) in &asm.clobber_abis {
|
||||||
match asm::InlineAsmClobberAbi::parse(
|
match asm::InlineAsmClobberAbi::parse(
|
||||||
asm_arch,
|
asm_arch,
|
||||||
|feature| self.sess.target_features.contains(&Symbol::intern(feature)),
|
|feature| self.sess.target_features.contains(&feature),
|
||||||
&self.sess.target,
|
&self.sess.target,
|
||||||
*abi_name,
|
*abi_name,
|
||||||
) {
|
) {
|
||||||
|
@ -134,7 +134,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||||
asm::InlineAsmRegOrRegClass::Reg(if let Some(asm_arch) = asm_arch {
|
asm::InlineAsmRegOrRegClass::Reg(if let Some(asm_arch) = asm_arch {
|
||||||
asm::InlineAsmReg::parse(
|
asm::InlineAsmReg::parse(
|
||||||
asm_arch,
|
asm_arch,
|
||||||
|feature| sess.target_features.contains(&Symbol::intern(feature)),
|
|feature| sess.target_features.contains(&feature),
|
||||||
&sess.target,
|
&sess.target,
|
||||||
s,
|
s,
|
||||||
)
|
)
|
||||||
|
|
|
@ -6,7 +6,7 @@ use std::fmt::Write;
|
||||||
|
|
||||||
use rustc_ast::ast::{InlineAsmOptions, InlineAsmTemplatePiece};
|
use rustc_ast::ast::{InlineAsmOptions, InlineAsmTemplatePiece};
|
||||||
use rustc_middle::mir::InlineAsmOperand;
|
use rustc_middle::mir::InlineAsmOperand;
|
||||||
use rustc_span::Symbol;
|
use rustc_span::sym;
|
||||||
use rustc_target::asm::*;
|
use rustc_target::asm::*;
|
||||||
|
|
||||||
pub(crate) fn codegen_inline_asm<'tcx>(
|
pub(crate) fn codegen_inline_asm<'tcx>(
|
||||||
|
@ -184,7 +184,7 @@ impl<'tcx> InlineAssemblyGenerator<'_, 'tcx> {
|
||||||
let sess = self.tcx.sess;
|
let sess = self.tcx.sess;
|
||||||
let map = allocatable_registers(
|
let map = allocatable_registers(
|
||||||
self.arch,
|
self.arch,
|
||||||
|feature| sess.target_features.contains(&Symbol::intern(feature)),
|
|feature| sess.target_features.contains(&feature),
|
||||||
&sess.target,
|
&sess.target,
|
||||||
);
|
);
|
||||||
let mut allocated = FxHashMap::<_, (bool, bool)>::default();
|
let mut allocated = FxHashMap::<_, (bool, bool)>::default();
|
||||||
|
@ -319,9 +319,9 @@ impl<'tcx> InlineAssemblyGenerator<'_, 'tcx> {
|
||||||
// Allocate stack slots for saving clobbered registers
|
// Allocate stack slots for saving clobbered registers
|
||||||
let abi_clobber = InlineAsmClobberAbi::parse(
|
let abi_clobber = InlineAsmClobberAbi::parse(
|
||||||
self.arch,
|
self.arch,
|
||||||
|feature| self.tcx.sess.target_features.contains(&Symbol::intern(feature)),
|
|feature| self.tcx.sess.target_features.contains(&feature),
|
||||||
&self.tcx.sess.target,
|
&self.tcx.sess.target,
|
||||||
Symbol::intern("C"),
|
sym::C,
|
||||||
)
|
)
|
||||||
.unwrap()
|
.unwrap()
|
||||||
.clobbered_regs();
|
.clobbered_regs();
|
||||||
|
|
|
@ -5,7 +5,7 @@ use rustc_codegen_ssa::mir::place::PlaceRef;
|
||||||
use rustc_codegen_ssa::traits::{AsmBuilderMethods, AsmMethods, BaseTypeMethods, BuilderMethods, GlobalAsmOperandRef, InlineAsmOperandRef};
|
use rustc_codegen_ssa::traits::{AsmBuilderMethods, AsmMethods, BaseTypeMethods, BuilderMethods, GlobalAsmOperandRef, InlineAsmOperandRef};
|
||||||
|
|
||||||
use rustc_middle::{bug, ty::Instance};
|
use rustc_middle::{bug, ty::Instance};
|
||||||
use rustc_span::{Span, Symbol};
|
use rustc_span::Span;
|
||||||
use rustc_target::asm::*;
|
use rustc_target::asm::*;
|
||||||
|
|
||||||
use std::borrow::Cow;
|
use std::borrow::Cow;
|
||||||
|
@ -172,7 +172,7 @@ impl<'a, 'gcc, 'tcx> AsmBuilderMethods<'tcx> for Builder<'a, 'gcc, 'tcx> {
|
||||||
let is_target_supported = reg.reg_class().supported_types(asm_arch).iter()
|
let is_target_supported = reg.reg_class().supported_types(asm_arch).iter()
|
||||||
.any(|&(_, feature)| {
|
.any(|&(_, feature)| {
|
||||||
if let Some(feature) = feature {
|
if let Some(feature) = feature {
|
||||||
self.tcx.sess.target_features.contains(&Symbol::intern(feature))
|
self.tcx.sess.target_features.contains(&feature)
|
||||||
} else {
|
} else {
|
||||||
true // Register class is unconditionally supported
|
true // Register class is unconditionally supported
|
||||||
}
|
}
|
||||||
|
|
|
@ -13,7 +13,7 @@ use rustc_codegen_ssa::traits::*;
|
||||||
use rustc_data_structures::fx::FxHashMap;
|
use rustc_data_structures::fx::FxHashMap;
|
||||||
use rustc_middle::ty::layout::TyAndLayout;
|
use rustc_middle::ty::layout::TyAndLayout;
|
||||||
use rustc_middle::{bug, span_bug, ty::Instance};
|
use rustc_middle::{bug, span_bug, ty::Instance};
|
||||||
use rustc_span::{Pos, Span, Symbol};
|
use rustc_span::{Pos, Span};
|
||||||
use rustc_target::abi::*;
|
use rustc_target::abi::*;
|
||||||
use rustc_target::asm::*;
|
use rustc_target::asm::*;
|
||||||
|
|
||||||
|
@ -45,9 +45,8 @@ impl<'ll, 'tcx> AsmBuilderMethods<'tcx> for Builder<'_, 'll, 'tcx> {
|
||||||
for &(_, feature) in reg_class.supported_types(asm_arch) {
|
for &(_, feature) in reg_class.supported_types(asm_arch) {
|
||||||
if let Some(feature) = feature {
|
if let Some(feature) = feature {
|
||||||
let codegen_fn_attrs = self.tcx.codegen_fn_attrs(instance.def_id());
|
let codegen_fn_attrs = self.tcx.codegen_fn_attrs(instance.def_id());
|
||||||
let feature_name = Symbol::intern(feature);
|
if self.tcx.sess.target_features.contains(&feature)
|
||||||
if self.tcx.sess.target_features.contains(&feature_name)
|
|| codegen_fn_attrs.target_features.contains(&feature)
|
||||||
|| codegen_fn_attrs.target_features.contains(&feature_name)
|
|
||||||
{
|
{
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
|
@ -294,9 +294,8 @@ impl<'tcx> ExprVisitor<'tcx> {
|
||||||
// (!). In that case we still need the earlier check to verify that the
|
// (!). In that case we still need the earlier check to verify that the
|
||||||
// register class is usable at all.
|
// register class is usable at all.
|
||||||
if let Some(feature) = feature {
|
if let Some(feature) = feature {
|
||||||
let feat_sym = Symbol::intern(feature);
|
if !self.tcx.sess.target_features.contains(&feature)
|
||||||
if !self.tcx.sess.target_features.contains(&feat_sym)
|
&& !target_features.contains(&feature)
|
||||||
&& !target_features.contains(&feat_sym)
|
|
||||||
{
|
{
|
||||||
let msg = &format!("`{}` target feature is not enabled", feature);
|
let msg = &format!("`{}` target feature is not enabled", feature);
|
||||||
let mut err = self.tcx.sess.struct_span_err(expr.span, msg);
|
let mut err = self.tcx.sess.struct_span_err(expr.span, msg);
|
||||||
|
@ -377,9 +376,8 @@ impl<'tcx> ExprVisitor<'tcx> {
|
||||||
{
|
{
|
||||||
match feature {
|
match feature {
|
||||||
Some(feature) => {
|
Some(feature) => {
|
||||||
let feat_sym = Symbol::intern(feature);
|
if self.tcx.sess.target_features.contains(&feature)
|
||||||
if self.tcx.sess.target_features.contains(&feat_sym)
|
|| attrs.target_features.contains(&feature)
|
||||||
|| attrs.target_features.contains(&feat_sym)
|
|
||||||
{
|
{
|
||||||
missing_required_features.clear();
|
missing_required_features.clear();
|
||||||
break;
|
break;
|
||||||
|
@ -413,7 +411,7 @@ impl<'tcx> ExprVisitor<'tcx> {
|
||||||
let msg = format!(
|
let msg = format!(
|
||||||
"register class `{}` requires at least one of the following target features: {}",
|
"register class `{}` requires at least one of the following target features: {}",
|
||||||
reg_class.name(),
|
reg_class.name(),
|
||||||
features.join(", ")
|
features.iter().map(|f| f.as_str()).collect::<Vec<_>>().join(", ")
|
||||||
);
|
);
|
||||||
self.tcx.sess.struct_span_err(*op_sp, &msg).emit();
|
self.tcx.sess.struct_span_err(*op_sp, &msg).emit();
|
||||||
// register isn't enabled, don't do more checks
|
// register isn't enabled, don't do more checks
|
||||||
|
|
|
@ -316,6 +316,7 @@ symbols! {
|
||||||
allow_internal_unsafe,
|
allow_internal_unsafe,
|
||||||
allow_internal_unstable,
|
allow_internal_unstable,
|
||||||
allowed,
|
allowed,
|
||||||
|
alu32,
|
||||||
always,
|
always,
|
||||||
and,
|
and,
|
||||||
and_then,
|
and_then,
|
||||||
|
@ -361,7 +362,10 @@ symbols! {
|
||||||
augmented_assignments,
|
augmented_assignments,
|
||||||
auto_traits,
|
auto_traits,
|
||||||
automatically_derived,
|
automatically_derived,
|
||||||
|
avx,
|
||||||
avx512_target_feature,
|
avx512_target_feature,
|
||||||
|
avx512bw,
|
||||||
|
avx512f,
|
||||||
await_macro,
|
await_macro,
|
||||||
bang,
|
bang,
|
||||||
begin_panic,
|
begin_panic,
|
||||||
|
@ -592,6 +596,7 @@ symbols! {
|
||||||
dylib,
|
dylib,
|
||||||
dyn_metadata,
|
dyn_metadata,
|
||||||
dyn_trait,
|
dyn_trait,
|
||||||
|
e,
|
||||||
edition_macro_pats,
|
edition_macro_pats,
|
||||||
edition_panic,
|
edition_panic,
|
||||||
eh_catch_typeinfo,
|
eh_catch_typeinfo,
|
||||||
|
@ -682,6 +687,7 @@ symbols! {
|
||||||
format_args_macro,
|
format_args_macro,
|
||||||
format_args_nl,
|
format_args_nl,
|
||||||
format_macro,
|
format_macro,
|
||||||
|
fp,
|
||||||
freeze,
|
freeze,
|
||||||
freg,
|
freg,
|
||||||
frem_fast,
|
frem_fast,
|
||||||
|
@ -907,6 +913,7 @@ symbols! {
|
||||||
neg,
|
neg,
|
||||||
negate_unsigned,
|
negate_unsigned,
|
||||||
negative_impls,
|
negative_impls,
|
||||||
|
neon,
|
||||||
never,
|
never,
|
||||||
never_type,
|
never_type,
|
||||||
never_type_fallback,
|
never_type_fallback,
|
||||||
|
@ -1101,6 +1108,7 @@ symbols! {
|
||||||
repr_packed,
|
repr_packed,
|
||||||
repr_simd,
|
repr_simd,
|
||||||
repr_transparent,
|
repr_transparent,
|
||||||
|
reserved_r9: "reserved-r9",
|
||||||
residual,
|
residual,
|
||||||
result,
|
result,
|
||||||
rhs,
|
rhs,
|
||||||
|
@ -1294,6 +1302,7 @@ symbols! {
|
||||||
sqrtf64,
|
sqrtf64,
|
||||||
sreg,
|
sreg,
|
||||||
sreg_low16,
|
sreg_low16,
|
||||||
|
sse,
|
||||||
sse4a_target_feature,
|
sse4a_target_feature,
|
||||||
stable,
|
stable,
|
||||||
staged_api,
|
staged_api,
|
||||||
|
@ -1360,6 +1369,8 @@ symbols! {
|
||||||
thread,
|
thread,
|
||||||
thread_local,
|
thread_local,
|
||||||
thread_local_macro,
|
thread_local_macro,
|
||||||
|
thumb2,
|
||||||
|
thumb_mode: "thumb-mode",
|
||||||
todo_macro,
|
todo_macro,
|
||||||
tool_attributes,
|
tool_attributes,
|
||||||
tool_lints,
|
tool_lints,
|
||||||
|
@ -1453,6 +1464,7 @@ symbols! {
|
||||||
vec,
|
vec,
|
||||||
vec_macro,
|
vec_macro,
|
||||||
version,
|
version,
|
||||||
|
vfp2,
|
||||||
vis,
|
vis,
|
||||||
visible_private_types,
|
visible_private_types,
|
||||||
volatile,
|
volatile,
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
use super::{InlineAsmArch, InlineAsmType};
|
use super::{InlineAsmArch, InlineAsmType};
|
||||||
use crate::spec::Target;
|
use crate::spec::Target;
|
||||||
use rustc_macros::HashStable_Generic;
|
use rustc_macros::HashStable_Generic;
|
||||||
|
use rustc_span::Symbol;
|
||||||
use std::fmt;
|
use std::fmt;
|
||||||
|
|
||||||
def_reg_class! {
|
def_reg_class! {
|
||||||
|
@ -58,11 +59,11 @@ impl AArch64InlineAsmRegClass {
|
||||||
pub fn supported_types(
|
pub fn supported_types(
|
||||||
self,
|
self,
|
||||||
_arch: InlineAsmArch,
|
_arch: InlineAsmArch,
|
||||||
) -> &'static [(InlineAsmType, Option<&'static str>)] {
|
) -> &'static [(InlineAsmType, Option<Symbol>)] {
|
||||||
match self {
|
match self {
|
||||||
Self::reg => types! { _: I8, I16, I32, I64, F32, F64; },
|
Self::reg => types! { _: I8, I16, I32, I64, F32, F64; },
|
||||||
Self::vreg | Self::vreg_low16 => types! {
|
Self::vreg | Self::vreg_low16 => types! {
|
||||||
"fp": I8, I16, I32, I64, F32, F64,
|
fp: I8, I16, I32, I64, F32, F64,
|
||||||
VecI8(8), VecI16(4), VecI32(2), VecI64(1), VecF32(2), VecF64(1),
|
VecI8(8), VecI16(4), VecI32(2), VecI64(1), VecF32(2), VecF64(1),
|
||||||
VecI8(16), VecI16(8), VecI32(4), VecI64(2), VecF32(4), VecF64(2);
|
VecI8(16), VecI16(8), VecI32(4), VecI64(2), VecF32(4), VecF64(2);
|
||||||
},
|
},
|
||||||
|
@ -73,7 +74,7 @@ impl AArch64InlineAsmRegClass {
|
||||||
|
|
||||||
pub fn reserved_x18(
|
pub fn reserved_x18(
|
||||||
_arch: InlineAsmArch,
|
_arch: InlineAsmArch,
|
||||||
_has_feature: impl FnMut(&str) -> bool,
|
_has_feature: impl FnMut(Symbol) -> bool,
|
||||||
target: &Target,
|
target: &Target,
|
||||||
) -> Result<(), &'static str> {
|
) -> Result<(), &'static str> {
|
||||||
if target.os == "android"
|
if target.os == "android"
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
use super::{InlineAsmArch, InlineAsmType};
|
use super::{InlineAsmArch, InlineAsmType};
|
||||||
use crate::spec::Target;
|
use crate::spec::Target;
|
||||||
use rustc_macros::HashStable_Generic;
|
use rustc_macros::HashStable_Generic;
|
||||||
|
use rustc_span::{sym, Symbol};
|
||||||
use std::fmt;
|
use std::fmt;
|
||||||
|
|
||||||
def_reg_class! {
|
def_reg_class! {
|
||||||
|
@ -44,28 +45,28 @@ impl ArmInlineAsmRegClass {
|
||||||
pub fn supported_types(
|
pub fn supported_types(
|
||||||
self,
|
self,
|
||||||
_arch: InlineAsmArch,
|
_arch: InlineAsmArch,
|
||||||
) -> &'static [(InlineAsmType, Option<&'static str>)] {
|
) -> &'static [(InlineAsmType, Option<Symbol>)] {
|
||||||
match self {
|
match self {
|
||||||
Self::reg => types! { _: I8, I16, I32, F32; },
|
Self::reg => types! { _: I8, I16, I32, F32; },
|
||||||
Self::sreg | Self::sreg_low16 => types! { "vfp2": I32, F32; },
|
Self::sreg | Self::sreg_low16 => types! { vfp2: I32, F32; },
|
||||||
Self::dreg | Self::dreg_low16 | Self::dreg_low8 => types! {
|
Self::dreg | Self::dreg_low16 | Self::dreg_low8 => types! {
|
||||||
"vfp2": I64, F64, VecI8(8), VecI16(4), VecI32(2), VecI64(1), VecF32(2);
|
vfp2: I64, F64, VecI8(8), VecI16(4), VecI32(2), VecI64(1), VecF32(2);
|
||||||
},
|
},
|
||||||
Self::qreg | Self::qreg_low8 | Self::qreg_low4 => types! {
|
Self::qreg | Self::qreg_low8 | Self::qreg_low4 => types! {
|
||||||
"neon": VecI8(16), VecI16(8), VecI32(4), VecI64(2), VecF32(4);
|
neon: VecI8(16), VecI16(8), VecI32(4), VecI64(2), VecF32(4);
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// This uses the same logic as useR7AsFramePointer in LLVM
|
// This uses the same logic as useR7AsFramePointer in LLVM
|
||||||
fn frame_pointer_is_r7(mut has_feature: impl FnMut(&str) -> bool, target: &Target) -> bool {
|
fn frame_pointer_is_r7(mut has_feature: impl FnMut(Symbol) -> bool, target: &Target) -> bool {
|
||||||
target.is_like_osx || (!target.is_like_windows && has_feature("thumb-mode"))
|
target.is_like_osx || (!target.is_like_windows && has_feature(sym::thumb_mode))
|
||||||
}
|
}
|
||||||
|
|
||||||
fn frame_pointer_r11(
|
fn frame_pointer_r11(
|
||||||
_arch: InlineAsmArch,
|
_arch: InlineAsmArch,
|
||||||
has_feature: impl FnMut(&str) -> bool,
|
has_feature: impl FnMut(Symbol) -> bool,
|
||||||
target: &Target,
|
target: &Target,
|
||||||
) -> Result<(), &'static str> {
|
) -> Result<(), &'static str> {
|
||||||
if !frame_pointer_is_r7(has_feature, target) {
|
if !frame_pointer_is_r7(has_feature, target) {
|
||||||
|
@ -77,7 +78,7 @@ fn frame_pointer_r11(
|
||||||
|
|
||||||
fn frame_pointer_r7(
|
fn frame_pointer_r7(
|
||||||
_arch: InlineAsmArch,
|
_arch: InlineAsmArch,
|
||||||
has_feature: impl FnMut(&str) -> bool,
|
has_feature: impl FnMut(Symbol) -> bool,
|
||||||
target: &Target,
|
target: &Target,
|
||||||
) -> Result<(), &'static str> {
|
) -> Result<(), &'static str> {
|
||||||
if frame_pointer_is_r7(has_feature, target) {
|
if frame_pointer_is_r7(has_feature, target) {
|
||||||
|
@ -89,10 +90,10 @@ fn frame_pointer_r7(
|
||||||
|
|
||||||
fn not_thumb1(
|
fn not_thumb1(
|
||||||
_arch: InlineAsmArch,
|
_arch: InlineAsmArch,
|
||||||
mut has_feature: impl FnMut(&str) -> bool,
|
mut has_feature: impl FnMut(Symbol) -> bool,
|
||||||
_target: &Target,
|
_target: &Target,
|
||||||
) -> Result<(), &'static str> {
|
) -> Result<(), &'static str> {
|
||||||
if has_feature("thumb-mode") && !has_feature("thumb2") {
|
if has_feature(sym::thumb_mode) && !has_feature(sym::thumb2) {
|
||||||
Err("high registers (r8+) cannot be used in Thumb-1 code")
|
Err("high registers (r8+) cannot be used in Thumb-1 code")
|
||||||
} else {
|
} else {
|
||||||
Ok(())
|
Ok(())
|
||||||
|
@ -101,14 +102,14 @@ fn not_thumb1(
|
||||||
|
|
||||||
fn reserved_r9(
|
fn reserved_r9(
|
||||||
arch: InlineAsmArch,
|
arch: InlineAsmArch,
|
||||||
mut has_feature: impl FnMut(&str) -> bool,
|
mut has_feature: impl FnMut(Symbol) -> bool,
|
||||||
target: &Target,
|
target: &Target,
|
||||||
) -> Result<(), &'static str> {
|
) -> Result<(), &'static str> {
|
||||||
not_thumb1(arch, &mut has_feature, target)?;
|
not_thumb1(arch, &mut has_feature, target)?;
|
||||||
|
|
||||||
// We detect this using the reserved-r9 feature instead of using the target
|
// We detect this using the reserved-r9 feature instead of using the target
|
||||||
// because the relocation model can be changed with compiler options.
|
// because the relocation model can be changed with compiler options.
|
||||||
if has_feature("reserved-r9") {
|
if has_feature(sym::reserved_r9) {
|
||||||
Err("the RWPI static base register (r9) cannot be used as an operand for inline asm")
|
Err("the RWPI static base register (r9) cannot be used as an operand for inline asm")
|
||||||
} else {
|
} else {
|
||||||
Ok(())
|
Ok(())
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
use super::{InlineAsmArch, InlineAsmType};
|
use super::{InlineAsmArch, InlineAsmType};
|
||||||
use rustc_macros::HashStable_Generic;
|
use rustc_macros::HashStable_Generic;
|
||||||
|
use rustc_span::Symbol;
|
||||||
use std::fmt;
|
use std::fmt;
|
||||||
|
|
||||||
def_reg_class! {
|
def_reg_class! {
|
||||||
|
@ -39,7 +40,7 @@ impl AvrInlineAsmRegClass {
|
||||||
pub fn supported_types(
|
pub fn supported_types(
|
||||||
self,
|
self,
|
||||||
_arch: InlineAsmArch,
|
_arch: InlineAsmArch,
|
||||||
) -> &'static [(InlineAsmType, Option<&'static str>)] {
|
) -> &'static [(InlineAsmType, Option<Symbol>)] {
|
||||||
match self {
|
match self {
|
||||||
Self::reg => types! { _: I8; },
|
Self::reg => types! { _: I8; },
|
||||||
Self::reg_upper => types! { _: I8; },
|
Self::reg_upper => types! { _: I8; },
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
use super::{InlineAsmArch, InlineAsmType, Target};
|
use super::{InlineAsmArch, InlineAsmType, Target};
|
||||||
use rustc_macros::HashStable_Generic;
|
use rustc_macros::HashStable_Generic;
|
||||||
|
use rustc_span::{sym, Symbol};
|
||||||
use std::fmt;
|
use std::fmt;
|
||||||
|
|
||||||
def_reg_class! {
|
def_reg_class! {
|
||||||
|
@ -33,20 +34,20 @@ impl BpfInlineAsmRegClass {
|
||||||
pub fn supported_types(
|
pub fn supported_types(
|
||||||
self,
|
self,
|
||||||
_arch: InlineAsmArch,
|
_arch: InlineAsmArch,
|
||||||
) -> &'static [(InlineAsmType, Option<&'static str>)] {
|
) -> &'static [(InlineAsmType, Option<Symbol>)] {
|
||||||
match self {
|
match self {
|
||||||
Self::reg => types! { _: I8, I16, I32, I64; },
|
Self::reg => types! { _: I8, I16, I32, I64; },
|
||||||
Self::wreg => types! { "alu32": I8, I16, I32; },
|
Self::wreg => types! { alu32: I8, I16, I32; },
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn only_alu32(
|
fn only_alu32(
|
||||||
_arch: InlineAsmArch,
|
_arch: InlineAsmArch,
|
||||||
mut has_feature: impl FnMut(&str) -> bool,
|
mut has_feature: impl FnMut(Symbol) -> bool,
|
||||||
_target: &Target,
|
_target: &Target,
|
||||||
) -> Result<(), &'static str> {
|
) -> Result<(), &'static str> {
|
||||||
if !has_feature("alu32") {
|
if !has_feature(sym::alu32) {
|
||||||
Err("register can't be used without the `alu32` target feature")
|
Err("register can't be used without the `alu32` target feature")
|
||||||
} else {
|
} else {
|
||||||
Ok(())
|
Ok(())
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
use super::{InlineAsmArch, InlineAsmType};
|
use super::{InlineAsmArch, InlineAsmType};
|
||||||
use rustc_macros::HashStable_Generic;
|
use rustc_macros::HashStable_Generic;
|
||||||
|
use rustc_span::Symbol;
|
||||||
use std::fmt;
|
use std::fmt;
|
||||||
|
|
||||||
def_reg_class! {
|
def_reg_class! {
|
||||||
|
@ -32,7 +33,7 @@ impl HexagonInlineAsmRegClass {
|
||||||
pub fn supported_types(
|
pub fn supported_types(
|
||||||
self,
|
self,
|
||||||
_arch: InlineAsmArch,
|
_arch: InlineAsmArch,
|
||||||
) -> &'static [(InlineAsmType, Option<&'static str>)] {
|
) -> &'static [(InlineAsmType, Option<Symbol>)] {
|
||||||
match self {
|
match self {
|
||||||
Self::reg => types! { _: I8, I16, I32, F32; },
|
Self::reg => types! { _: I8, I16, I32, F32; },
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
use super::{InlineAsmArch, InlineAsmType};
|
use super::{InlineAsmArch, InlineAsmType};
|
||||||
use rustc_macros::HashStable_Generic;
|
use rustc_macros::HashStable_Generic;
|
||||||
|
use rustc_span::Symbol;
|
||||||
use std::fmt;
|
use std::fmt;
|
||||||
|
|
||||||
def_reg_class! {
|
def_reg_class! {
|
||||||
|
@ -33,7 +34,7 @@ impl MipsInlineAsmRegClass {
|
||||||
pub fn supported_types(
|
pub fn supported_types(
|
||||||
self,
|
self,
|
||||||
arch: InlineAsmArch,
|
arch: InlineAsmArch,
|
||||||
) -> &'static [(InlineAsmType, Option<&'static str>)] {
|
) -> &'static [(InlineAsmType, Option<Symbol>)] {
|
||||||
match (self, arch) {
|
match (self, arch) {
|
||||||
(Self::reg, InlineAsmArch::Mips64) => types! { _: I8, I16, I32, I64, F32, F64; },
|
(Self::reg, InlineAsmArch::Mips64) => types! { _: I8, I16, I32, I64, F32, F64; },
|
||||||
(Self::reg, _) => types! { _: I8, I16, I32, F32; },
|
(Self::reg, _) => types! { _: I8, I16, I32, F32; },
|
||||||
|
|
|
@ -81,7 +81,7 @@ macro_rules! def_regs {
|
||||||
|
|
||||||
pub fn parse(
|
pub fn parse(
|
||||||
_arch: super::InlineAsmArch,
|
_arch: super::InlineAsmArch,
|
||||||
mut _has_feature: impl FnMut(&str) -> bool,
|
mut _has_feature: impl FnMut(rustc_span::Symbol) -> bool,
|
||||||
_target: &crate::spec::Target,
|
_target: &crate::spec::Target,
|
||||||
name: &str,
|
name: &str,
|
||||||
) -> Result<Self, &'static str> {
|
) -> Result<Self, &'static str> {
|
||||||
|
@ -102,7 +102,7 @@ macro_rules! def_regs {
|
||||||
|
|
||||||
pub(super) fn fill_reg_map(
|
pub(super) fn fill_reg_map(
|
||||||
_arch: super::InlineAsmArch,
|
_arch: super::InlineAsmArch,
|
||||||
mut _has_feature: impl FnMut(&str) -> bool,
|
mut _has_feature: impl FnMut(rustc_span::Symbol) -> bool,
|
||||||
_target: &crate::spec::Target,
|
_target: &crate::spec::Target,
|
||||||
_map: &mut rustc_data_structures::fx::FxHashMap<
|
_map: &mut rustc_data_structures::fx::FxHashMap<
|
||||||
super::InlineAsmRegClass,
|
super::InlineAsmRegClass,
|
||||||
|
@ -130,7 +130,7 @@ macro_rules! def_regs {
|
||||||
macro_rules! types {
|
macro_rules! types {
|
||||||
(
|
(
|
||||||
$(_ : $($ty:expr),+;)?
|
$(_ : $($ty:expr),+;)?
|
||||||
$($feature:literal: $($ty2:expr),+;)*
|
$($feature:ident: $($ty2:expr),+;)*
|
||||||
) => {
|
) => {
|
||||||
{
|
{
|
||||||
use super::InlineAsmType::*;
|
use super::InlineAsmType::*;
|
||||||
|
@ -139,7 +139,7 @@ macro_rules! types {
|
||||||
($ty, None),
|
($ty, None),
|
||||||
)*)?
|
)*)?
|
||||||
$($(
|
$($(
|
||||||
($ty2, Some($feature)),
|
($ty2, Some(rustc_span::sym::$feature)),
|
||||||
)*)*
|
)*)*
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
@ -289,7 +289,7 @@ impl InlineAsmReg {
|
||||||
|
|
||||||
pub fn parse(
|
pub fn parse(
|
||||||
arch: InlineAsmArch,
|
arch: InlineAsmArch,
|
||||||
has_feature: impl FnMut(&str) -> bool,
|
has_feature: impl FnMut(Symbol) -> bool,
|
||||||
target: &Target,
|
target: &Target,
|
||||||
name: Symbol,
|
name: Symbol,
|
||||||
) -> Result<Self, &'static str> {
|
) -> Result<Self, &'static str> {
|
||||||
|
@ -510,7 +510,7 @@ impl InlineAsmRegClass {
|
||||||
pub fn supported_types(
|
pub fn supported_types(
|
||||||
self,
|
self,
|
||||||
arch: InlineAsmArch,
|
arch: InlineAsmArch,
|
||||||
) -> &'static [(InlineAsmType, Option<&'static str>)] {
|
) -> &'static [(InlineAsmType, Option<Symbol>)] {
|
||||||
match self {
|
match self {
|
||||||
Self::X86(r) => r.supported_types(arch),
|
Self::X86(r) => r.supported_types(arch),
|
||||||
Self::Arm(r) => r.supported_types(arch),
|
Self::Arm(r) => r.supported_types(arch),
|
||||||
|
@ -695,7 +695,7 @@ impl fmt::Display for InlineAsmType {
|
||||||
// falling back to an external assembler.
|
// falling back to an external assembler.
|
||||||
pub fn allocatable_registers(
|
pub fn allocatable_registers(
|
||||||
arch: InlineAsmArch,
|
arch: InlineAsmArch,
|
||||||
has_feature: impl FnMut(&str) -> bool,
|
has_feature: impl FnMut(Symbol) -> bool,
|
||||||
target: &crate::spec::Target,
|
target: &crate::spec::Target,
|
||||||
) -> FxHashMap<InlineAsmRegClass, FxHashSet<InlineAsmReg>> {
|
) -> FxHashMap<InlineAsmRegClass, FxHashSet<InlineAsmReg>> {
|
||||||
match arch {
|
match arch {
|
||||||
|
@ -794,7 +794,7 @@ impl InlineAsmClobberAbi {
|
||||||
/// clobber ABIs for the target.
|
/// clobber ABIs for the target.
|
||||||
pub fn parse(
|
pub fn parse(
|
||||||
arch: InlineAsmArch,
|
arch: InlineAsmArch,
|
||||||
has_feature: impl FnMut(&str) -> bool,
|
has_feature: impl FnMut(Symbol) -> bool,
|
||||||
target: &Target,
|
target: &Target,
|
||||||
name: Symbol,
|
name: Symbol,
|
||||||
) -> Result<Self, &'static [&'static str]> {
|
) -> Result<Self, &'static [&'static str]> {
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
use super::{InlineAsmArch, InlineAsmType};
|
use super::{InlineAsmArch, InlineAsmType};
|
||||||
use rustc_macros::HashStable_Generic;
|
use rustc_macros::HashStable_Generic;
|
||||||
|
use rustc_span::Symbol;
|
||||||
|
|
||||||
def_reg_class! {
|
def_reg_class! {
|
||||||
Nvptx NvptxInlineAsmRegClass {
|
Nvptx NvptxInlineAsmRegClass {
|
||||||
|
@ -33,7 +34,7 @@ impl NvptxInlineAsmRegClass {
|
||||||
pub fn supported_types(
|
pub fn supported_types(
|
||||||
self,
|
self,
|
||||||
_arch: InlineAsmArch,
|
_arch: InlineAsmArch,
|
||||||
) -> &'static [(InlineAsmType, Option<&'static str>)] {
|
) -> &'static [(InlineAsmType, Option<Symbol>)] {
|
||||||
match self {
|
match self {
|
||||||
Self::reg16 => types! { _: I8, I16; },
|
Self::reg16 => types! { _: I8, I16; },
|
||||||
Self::reg32 => types! { _: I8, I16, I32, F32; },
|
Self::reg32 => types! { _: I8, I16, I32, F32; },
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
use super::{InlineAsmArch, InlineAsmType};
|
use super::{InlineAsmArch, InlineAsmType};
|
||||||
use rustc_macros::HashStable_Generic;
|
use rustc_macros::HashStable_Generic;
|
||||||
|
use rustc_span::Symbol;
|
||||||
use std::fmt;
|
use std::fmt;
|
||||||
|
|
||||||
def_reg_class! {
|
def_reg_class! {
|
||||||
|
@ -36,7 +37,7 @@ impl PowerPCInlineAsmRegClass {
|
||||||
pub fn supported_types(
|
pub fn supported_types(
|
||||||
self,
|
self,
|
||||||
arch: InlineAsmArch,
|
arch: InlineAsmArch,
|
||||||
) -> &'static [(InlineAsmType, Option<&'static str>)] {
|
) -> &'static [(InlineAsmType, Option<Symbol>)] {
|
||||||
match self {
|
match self {
|
||||||
Self::reg | Self::reg_nonzero => {
|
Self::reg | Self::reg_nonzero => {
|
||||||
if arch == InlineAsmArch::PowerPC {
|
if arch == InlineAsmArch::PowerPC {
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
use super::{InlineAsmArch, InlineAsmType};
|
use super::{InlineAsmArch, InlineAsmType};
|
||||||
use crate::spec::Target;
|
use crate::spec::Target;
|
||||||
use rustc_macros::HashStable_Generic;
|
use rustc_macros::HashStable_Generic;
|
||||||
|
use rustc_span::{sym, Symbol};
|
||||||
use std::fmt;
|
use std::fmt;
|
||||||
|
|
||||||
def_reg_class! {
|
def_reg_class! {
|
||||||
|
@ -35,7 +36,7 @@ impl RiscVInlineAsmRegClass {
|
||||||
pub fn supported_types(
|
pub fn supported_types(
|
||||||
self,
|
self,
|
||||||
arch: InlineAsmArch,
|
arch: InlineAsmArch,
|
||||||
) -> &'static [(InlineAsmType, Option<&'static str>)] {
|
) -> &'static [(InlineAsmType, Option<Symbol>)] {
|
||||||
match self {
|
match self {
|
||||||
Self::reg => {
|
Self::reg => {
|
||||||
if arch == InlineAsmArch::RiscV64 {
|
if arch == InlineAsmArch::RiscV64 {
|
||||||
|
@ -44,7 +45,7 @@ impl RiscVInlineAsmRegClass {
|
||||||
types! { _: I8, I16, I32, F32; }
|
types! { _: I8, I16, I32, F32; }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Self::freg => types! { "f": F32; "d": F64; },
|
Self::freg => types! { f: F32; d: F64; },
|
||||||
Self::vreg => &[],
|
Self::vreg => &[],
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -52,10 +53,10 @@ impl RiscVInlineAsmRegClass {
|
||||||
|
|
||||||
fn not_e(
|
fn not_e(
|
||||||
_arch: InlineAsmArch,
|
_arch: InlineAsmArch,
|
||||||
mut has_feature: impl FnMut(&str) -> bool,
|
mut has_feature: impl FnMut(Symbol) -> bool,
|
||||||
_target: &Target,
|
_target: &Target,
|
||||||
) -> Result<(), &'static str> {
|
) -> Result<(), &'static str> {
|
||||||
if has_feature("e") {
|
if has_feature(sym::e) {
|
||||||
Err("register can't be used with the `e` target feature")
|
Err("register can't be used with the `e` target feature")
|
||||||
} else {
|
} else {
|
||||||
Ok(())
|
Ok(())
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
use super::{InlineAsmArch, InlineAsmType};
|
use super::{InlineAsmArch, InlineAsmType};
|
||||||
use rustc_macros::HashStable_Generic;
|
use rustc_macros::HashStable_Generic;
|
||||||
|
use rustc_span::Symbol;
|
||||||
use std::fmt;
|
use std::fmt;
|
||||||
|
|
||||||
def_reg_class! {
|
def_reg_class! {
|
||||||
|
@ -33,7 +34,7 @@ impl S390xInlineAsmRegClass {
|
||||||
pub fn supported_types(
|
pub fn supported_types(
|
||||||
self,
|
self,
|
||||||
arch: InlineAsmArch,
|
arch: InlineAsmArch,
|
||||||
) -> &'static [(InlineAsmType, Option<&'static str>)] {
|
) -> &'static [(InlineAsmType, Option<Symbol>)] {
|
||||||
match (self, arch) {
|
match (self, arch) {
|
||||||
(Self::reg, _) => types! { _: I8, I16, I32, I64; },
|
(Self::reg, _) => types! { _: I8, I16, I32, I64; },
|
||||||
(Self::freg, _) => types! { _: F32, F64; },
|
(Self::freg, _) => types! { _: F32, F64; },
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
use super::{InlineAsmArch, InlineAsmType};
|
use super::{InlineAsmArch, InlineAsmType};
|
||||||
use rustc_macros::HashStable_Generic;
|
use rustc_macros::HashStable_Generic;
|
||||||
|
use rustc_span::Symbol;
|
||||||
|
|
||||||
def_reg_class! {
|
def_reg_class! {
|
||||||
SpirV SpirVInlineAsmRegClass {
|
SpirV SpirVInlineAsmRegClass {
|
||||||
|
@ -31,7 +32,7 @@ impl SpirVInlineAsmRegClass {
|
||||||
pub fn supported_types(
|
pub fn supported_types(
|
||||||
self,
|
self,
|
||||||
_arch: InlineAsmArch,
|
_arch: InlineAsmArch,
|
||||||
) -> &'static [(InlineAsmType, Option<&'static str>)] {
|
) -> &'static [(InlineAsmType, Option<Symbol>)] {
|
||||||
match self {
|
match self {
|
||||||
Self::reg => {
|
Self::reg => {
|
||||||
types! { _: I8, I16, I32, I64, F32, F64; }
|
types! { _: I8, I16, I32, I64, F32, F64; }
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
use super::{InlineAsmArch, InlineAsmType};
|
use super::{InlineAsmArch, InlineAsmType};
|
||||||
use rustc_macros::HashStable_Generic;
|
use rustc_macros::HashStable_Generic;
|
||||||
|
use rustc_span::Symbol;
|
||||||
|
|
||||||
def_reg_class! {
|
def_reg_class! {
|
||||||
Wasm WasmInlineAsmRegClass {
|
Wasm WasmInlineAsmRegClass {
|
||||||
|
@ -31,7 +32,7 @@ impl WasmInlineAsmRegClass {
|
||||||
pub fn supported_types(
|
pub fn supported_types(
|
||||||
self,
|
self,
|
||||||
_arch: InlineAsmArch,
|
_arch: InlineAsmArch,
|
||||||
) -> &'static [(InlineAsmType, Option<&'static str>)] {
|
) -> &'static [(InlineAsmType, Option<Symbol>)] {
|
||||||
match self {
|
match self {
|
||||||
Self::local => {
|
Self::local => {
|
||||||
types! { _: I8, I16, I32, I64, F32, F64; }
|
types! { _: I8, I16, I32, I64, F32, F64; }
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
use super::{InlineAsmArch, InlineAsmType};
|
use super::{InlineAsmArch, InlineAsmType};
|
||||||
use crate::spec::Target;
|
use crate::spec::Target;
|
||||||
use rustc_macros::HashStable_Generic;
|
use rustc_macros::HashStable_Generic;
|
||||||
|
use rustc_span::Symbol;
|
||||||
use std::fmt;
|
use std::fmt;
|
||||||
|
|
||||||
def_reg_class! {
|
def_reg_class! {
|
||||||
|
@ -101,7 +102,7 @@ impl X86InlineAsmRegClass {
|
||||||
pub fn supported_types(
|
pub fn supported_types(
|
||||||
self,
|
self,
|
||||||
arch: InlineAsmArch,
|
arch: InlineAsmArch,
|
||||||
) -> &'static [(InlineAsmType, Option<&'static str>)] {
|
) -> &'static [(InlineAsmType, Option<Symbol>)] {
|
||||||
match self {
|
match self {
|
||||||
Self::reg | Self::reg_abcd => {
|
Self::reg | Self::reg_abcd => {
|
||||||
if arch == InlineAsmArch::X86_64 {
|
if arch == InlineAsmArch::X86_64 {
|
||||||
|
@ -112,23 +113,23 @@ impl X86InlineAsmRegClass {
|
||||||
}
|
}
|
||||||
Self::reg_byte => types! { _: I8; },
|
Self::reg_byte => types! { _: I8; },
|
||||||
Self::xmm_reg => types! {
|
Self::xmm_reg => types! {
|
||||||
"sse": I32, I64, F32, F64,
|
sse: I32, I64, F32, F64,
|
||||||
VecI8(16), VecI16(8), VecI32(4), VecI64(2), VecF32(4), VecF64(2);
|
VecI8(16), VecI16(8), VecI32(4), VecI64(2), VecF32(4), VecF64(2);
|
||||||
},
|
},
|
||||||
Self::ymm_reg => types! {
|
Self::ymm_reg => types! {
|
||||||
"avx": I32, I64, F32, F64,
|
avx: I32, I64, F32, F64,
|
||||||
VecI8(16), VecI16(8), VecI32(4), VecI64(2), VecF32(4), VecF64(2),
|
VecI8(16), VecI16(8), VecI32(4), VecI64(2), VecF32(4), VecF64(2),
|
||||||
VecI8(32), VecI16(16), VecI32(8), VecI64(4), VecF32(8), VecF64(4);
|
VecI8(32), VecI16(16), VecI32(8), VecI64(4), VecF32(8), VecF64(4);
|
||||||
},
|
},
|
||||||
Self::zmm_reg => types! {
|
Self::zmm_reg => types! {
|
||||||
"avx512f": I32, I64, F32, F64,
|
avx512f: I32, I64, F32, F64,
|
||||||
VecI8(16), VecI16(8), VecI32(4), VecI64(2), VecF32(4), VecF64(2),
|
VecI8(16), VecI16(8), VecI32(4), VecI64(2), VecF32(4), VecF64(2),
|
||||||
VecI8(32), VecI16(16), VecI32(8), VecI64(4), VecF32(8), VecF64(4),
|
VecI8(32), VecI16(16), VecI32(8), VecI64(4), VecF32(8), VecF64(4),
|
||||||
VecI8(64), VecI16(32), VecI32(16), VecI64(8), VecF32(16), VecF64(8);
|
VecI8(64), VecI16(32), VecI32(16), VecI64(8), VecF32(16), VecF64(8);
|
||||||
},
|
},
|
||||||
Self::kreg => types! {
|
Self::kreg => types! {
|
||||||
"avx512f": I8, I16;
|
avx512f: I8, I16;
|
||||||
"avx512bw": I32, I64;
|
avx512bw: I32, I64;
|
||||||
},
|
},
|
||||||
Self::mmx_reg | Self::x87_reg => &[],
|
Self::mmx_reg | Self::x87_reg => &[],
|
||||||
}
|
}
|
||||||
|
@ -137,7 +138,7 @@ impl X86InlineAsmRegClass {
|
||||||
|
|
||||||
fn x86_64_only(
|
fn x86_64_only(
|
||||||
arch: InlineAsmArch,
|
arch: InlineAsmArch,
|
||||||
_has_feature: impl FnMut(&str) -> bool,
|
_has_feature: impl FnMut(Symbol) -> bool,
|
||||||
_target: &Target,
|
_target: &Target,
|
||||||
) -> Result<(), &'static str> {
|
) -> Result<(), &'static str> {
|
||||||
match arch {
|
match arch {
|
||||||
|
@ -149,7 +150,7 @@ fn x86_64_only(
|
||||||
|
|
||||||
fn high_byte(
|
fn high_byte(
|
||||||
arch: InlineAsmArch,
|
arch: InlineAsmArch,
|
||||||
_has_feature: impl FnMut(&str) -> bool,
|
_has_feature: impl FnMut(Symbol) -> bool,
|
||||||
_target: &Target,
|
_target: &Target,
|
||||||
) -> Result<(), &'static str> {
|
) -> Result<(), &'static str> {
|
||||||
match arch {
|
match arch {
|
||||||
|
@ -160,7 +161,7 @@ fn high_byte(
|
||||||
|
|
||||||
fn rbx_reserved(
|
fn rbx_reserved(
|
||||||
arch: InlineAsmArch,
|
arch: InlineAsmArch,
|
||||||
_has_feature: impl FnMut(&str) -> bool,
|
_has_feature: impl FnMut(Symbol) -> bool,
|
||||||
_target: &Target,
|
_target: &Target,
|
||||||
) -> Result<(), &'static str> {
|
) -> Result<(), &'static str> {
|
||||||
match arch {
|
match arch {
|
||||||
|
@ -174,7 +175,7 @@ fn rbx_reserved(
|
||||||
|
|
||||||
fn esi_reserved(
|
fn esi_reserved(
|
||||||
arch: InlineAsmArch,
|
arch: InlineAsmArch,
|
||||||
_has_feature: impl FnMut(&str) -> bool,
|
_has_feature: impl FnMut(Symbol) -> bool,
|
||||||
_target: &Target,
|
_target: &Target,
|
||||||
) -> Result<(), &'static str> {
|
) -> Result<(), &'static str> {
|
||||||
match arch {
|
match arch {
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue