mirror of https://github.com/rust-lang/rust.git
remove cmse validation from rustc_codegen_ssa
it was moved to hir_analysis in the previous commit
This commit is contained in:
parent
7b63734961
commit
6b6b8422ba
|
@ -16,18 +16,6 @@ codegen_ssa_cgu_not_recorded =
|
||||||
|
|
||||||
codegen_ssa_check_installed_visual_studio = please ensure that Visual Studio 2017 or later, or Build Tools for Visual Studio were installed with the Visual C++ option.
|
codegen_ssa_check_installed_visual_studio = please ensure that Visual Studio 2017 or later, or Build Tools for Visual Studio were installed with the Visual C++ option.
|
||||||
|
|
||||||
codegen_ssa_cmse_call_inputs_stack_spill =
|
|
||||||
arguments for `C-cmse-nonsecure-call` function too large to pass via registers
|
|
||||||
.label = this function uses the `C-cmse-nonsecure-call` ABI
|
|
||||||
.call = but its arguments don't fit in the available registers
|
|
||||||
.note = functions with the `C-cmse-nonsecure-call` ABI must pass all their arguments via the 4 32-bit available argument registers
|
|
||||||
|
|
||||||
codegen_ssa_cmse_call_output_stack_spill =
|
|
||||||
return value of `C-cmse-nonsecure-call` function too large to pass via registers
|
|
||||||
.label = this function uses the `C-cmse-nonsecure-call` ABI
|
|
||||||
.call = but its return value doesn't fit in the available registers
|
|
||||||
.note = functions with the `C-cmse-nonsecure-call` ABI must pass their result via the available return registers
|
|
||||||
|
|
||||||
codegen_ssa_compiler_builtins_cannot_call =
|
codegen_ssa_compiler_builtins_cannot_call =
|
||||||
`compiler_builtins` cannot call functions through upstream monomorphizations; encountered invalid call from `{$caller}` to `{$callee}`
|
`compiler_builtins` cannot call functions through upstream monomorphizations; encountered invalid call from `{$caller}` to `{$callee}`
|
||||||
|
|
||||||
|
|
|
@ -1033,25 +1033,3 @@ pub struct CompilerBuiltinsCannotCall {
|
||||||
pub caller: String,
|
pub caller: String,
|
||||||
pub callee: String,
|
pub callee: String,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Diagnostic)]
|
|
||||||
#[diag(codegen_ssa_cmse_call_inputs_stack_spill, code = E0798)]
|
|
||||||
#[note]
|
|
||||||
pub struct CmseCallInputsStackSpill {
|
|
||||||
#[primary_span]
|
|
||||||
#[label(codegen_ssa_call)]
|
|
||||||
pub call_site_span: Span,
|
|
||||||
#[label]
|
|
||||||
pub function_definition_span: Span,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Diagnostic)]
|
|
||||||
#[diag(codegen_ssa_cmse_call_output_stack_spill, code = E0798)]
|
|
||||||
#[note]
|
|
||||||
pub struct CmseCallOutputStackSpill {
|
|
||||||
#[primary_span]
|
|
||||||
#[label(codegen_ssa_call)]
|
|
||||||
pub call_site_span: Span,
|
|
||||||
#[label]
|
|
||||||
pub function_definition_span: Span,
|
|
||||||
}
|
|
||||||
|
|
|
@ -7,7 +7,6 @@ use crate::base;
|
||||||
use crate::common::{self, IntPredicate};
|
use crate::common::{self, IntPredicate};
|
||||||
use crate::errors::CompilerBuiltinsCannotCall;
|
use crate::errors::CompilerBuiltinsCannotCall;
|
||||||
use crate::meth;
|
use crate::meth;
|
||||||
use crate::mir::cmse;
|
|
||||||
use crate::traits::*;
|
use crate::traits::*;
|
||||||
use crate::MemFlags;
|
use crate::MemFlags;
|
||||||
|
|
||||||
|
@ -870,9 +869,6 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
|
||||||
let sig = callee.layout.ty.fn_sig(bx.tcx());
|
let sig = callee.layout.ty.fn_sig(bx.tcx());
|
||||||
let abi = sig.abi();
|
let abi = sig.abi();
|
||||||
|
|
||||||
// emit errors if cmse ABI conditions are violated
|
|
||||||
cmse::validate_cmse_abi(bx, &sig.skip_binder(), span, func.span(self.mir));
|
|
||||||
|
|
||||||
let extra_args = &args[sig.inputs().skip_binder().len()..];
|
let extra_args = &args[sig.inputs().skip_binder().len()..];
|
||||||
let extra_args = bx.tcx().mk_type_list_from_iter(extra_args.iter().map(|op_arg| {
|
let extra_args = bx.tcx().mk_type_list_from_iter(extra_args.iter().map(|op_arg| {
|
||||||
let op_ty = op_arg.node.ty(self.mir, bx.tcx());
|
let op_ty = op_arg.node.ty(self.mir, bx.tcx());
|
||||||
|
|
|
@ -1,72 +0,0 @@
|
||||||
use rustc_middle::ty::FnSig;
|
|
||||||
use rustc_span::Span;
|
|
||||||
|
|
||||||
use crate::errors::{CmseCallInputsStackSpill, CmseCallOutputStackSpill};
|
|
||||||
use crate::traits::BuilderMethods;
|
|
||||||
|
|
||||||
/// Check conditions on inputs and outputs that the cmse ABIs impose: arguments and results MUST be
|
|
||||||
/// returned via registers (i.e. MUST NOT spill to the stack). LLVM will also validate these
|
|
||||||
/// conditions, but by checking them here rustc can emit nicer error messages.
|
|
||||||
pub fn validate_cmse_abi<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>>(
|
|
||||||
bx: &Bx,
|
|
||||||
fn_sig: &FnSig<'tcx>,
|
|
||||||
call_site_span: Span,
|
|
||||||
function_definition_span: Span,
|
|
||||||
) {
|
|
||||||
if let rustc_target::spec::abi::Abi::CCmseNonSecureCall = fn_sig.abi {
|
|
||||||
if !has_valid_inputs(bx, fn_sig) {
|
|
||||||
let err = CmseCallInputsStackSpill { call_site_span, function_definition_span };
|
|
||||||
bx.tcx().dcx().emit_err(err);
|
|
||||||
}
|
|
||||||
|
|
||||||
if !has_valid_output(bx, fn_sig) {
|
|
||||||
let err = CmseCallOutputStackSpill { call_site_span, function_definition_span };
|
|
||||||
bx.tcx().dcx().emit_err(err);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Returns whether the inputs will fit into the available registers
|
|
||||||
fn has_valid_inputs<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>>(bx: &Bx, fn_sig: &FnSig<'tcx>) -> bool {
|
|
||||||
let mut accum = 0u64;
|
|
||||||
|
|
||||||
for arg_def in fn_sig.inputs().iter() {
|
|
||||||
let layout = bx.layout_of(*arg_def);
|
|
||||||
|
|
||||||
let align = layout.layout.align().abi.bytes();
|
|
||||||
let size = layout.layout.size().bytes();
|
|
||||||
|
|
||||||
accum += size;
|
|
||||||
accum = accum.next_multiple_of(Ord::max(4, align));
|
|
||||||
}
|
|
||||||
|
|
||||||
// the available argument space is 16 bytes (4 32-bit registers) in total
|
|
||||||
let available_space = 16;
|
|
||||||
|
|
||||||
accum <= available_space
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Returns whether the output will fit into the available registers
|
|
||||||
fn has_valid_output<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>>(bx: &Bx, fn_sig: &FnSig<'tcx>) -> bool {
|
|
||||||
let mut ret_layout = bx.layout_of(fn_sig.output());
|
|
||||||
|
|
||||||
// unwrap any `repr(transparent)` wrappers
|
|
||||||
loop {
|
|
||||||
if ret_layout.is_transparent::<Bx>() {
|
|
||||||
match ret_layout.non_1zst_field(bx) {
|
|
||||||
None => break,
|
|
||||||
Some((_, layout)) => ret_layout = layout,
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Fundamental types of size 8 can be passed via registers according to the ABI
|
|
||||||
let valid_2register_return_types = [bx.tcx().types.i64, bx.tcx().types.u64, bx.tcx().types.f64];
|
|
||||||
|
|
||||||
// A Composite Type larger than 4 bytes is stored in memory at an address
|
|
||||||
// passed as an extra argument when the function was called. That is not allowed
|
|
||||||
// for cmse_nonsecure_entry functions.
|
|
||||||
ret_layout.layout.size().bytes() <= 4 || valid_2register_return_types.contains(&ret_layout.ty)
|
|
||||||
}
|
|
|
@ -16,7 +16,6 @@ use std::iter;
|
||||||
|
|
||||||
mod analyze;
|
mod analyze;
|
||||||
mod block;
|
mod block;
|
||||||
mod cmse;
|
|
||||||
pub mod constant;
|
pub mod constant;
|
||||||
pub mod coverageinfo;
|
pub mod coverageinfo;
|
||||||
pub mod debuginfo;
|
pub mod debuginfo;
|
||||||
|
|
|
@ -1287,10 +1287,9 @@ pub(super) fn check_transparent<'tcx>(tcx: TyCtxt<'tcx>, adt: ty::AdtDef<'tcx>)
|
||||||
(span, trivial, check_non_exhaustive(tcx, ty).break_value())
|
(span, trivial, check_non_exhaustive(tcx, ty).break_value())
|
||||||
});
|
});
|
||||||
|
|
||||||
let non_trivial_fields =
|
let non_trivial_fields = field_infos
|
||||||
field_infos.clone().filter_map(
|
.clone()
|
||||||
|(span, trivial, _non_exhaustive)| if !trivial { Some(span) } else { None },
|
.filter_map(|(span, trivial, _non_exhaustive)| if !trivial { Some(span) } else { None });
|
||||||
);
|
|
||||||
let non_trivial_count = non_trivial_fields.clone().count();
|
let non_trivial_count = non_trivial_fields.clone().count();
|
||||||
if non_trivial_count >= 2 {
|
if non_trivial_count >= 2 {
|
||||||
bad_non_zero_sized_fields(
|
bad_non_zero_sized_fields(
|
||||||
|
|
|
@ -1749,11 +1749,7 @@ impl<'tcx> dyn HirTyLowerer<'tcx> + '_ {
|
||||||
generic_segments.iter().map(|GenericPathSegment(_, index)| index).collect();
|
generic_segments.iter().map(|GenericPathSegment(_, index)| index).collect();
|
||||||
let _ = self.prohibit_generic_args(
|
let _ = self.prohibit_generic_args(
|
||||||
path.segments.iter().enumerate().filter_map(|(index, seg)| {
|
path.segments.iter().enumerate().filter_map(|(index, seg)| {
|
||||||
if !indices.contains(&index) {
|
if !indices.contains(&index) { Some(seg) } else { None }
|
||||||
Some(seg)
|
|
||||||
} else {
|
|
||||||
None
|
|
||||||
}
|
|
||||||
}),
|
}),
|
||||||
GenericsArgsErrExtend::DefVariant,
|
GenericsArgsErrExtend::DefVariant,
|
||||||
);
|
);
|
||||||
|
|
Loading…
Reference in New Issue