Auto merge of #63998 - Centril:rollup-pfuwxz3, r=Centril
Rollup of 7 pull requests Successful merges: - #63867 (resolve: Block expansion of a derive container until all its derives are resolved) - #63880 (Validation: check raw wide pointer metadata) - #63914 (ty: use Align for ReprOptions pack and align.) - #63941 (rustbuild: allow disabling deny(warnings) for bootstrap) - #63949 (Fix build src/libtest) - #63984 (Update rust-installer to limit memory use) - #63992 (Small improvement for Ord implementation of integers) Failed merges: r? @ghost
This commit is contained in:
commit
7445622bcb
33 changed files with 485 additions and 380 deletions
|
@ -5,9 +5,6 @@
|
|||
//! parent directory, and otherwise documentation can be found throughout the `build`
|
||||
//! directory in each respective module.
|
||||
|
||||
// NO-RUSTC-WRAPPER
|
||||
#![deny(warnings, rust_2018_idioms, unused_lifetimes)]
|
||||
|
||||
use std::env;
|
||||
|
||||
use bootstrap::{Config, Build};
|
||||
|
|
|
@ -15,9 +15,6 @@
|
|||
//! switching compilers for the bootstrap and for build scripts will probably
|
||||
//! never get replaced.
|
||||
|
||||
// NO-RUSTC-WRAPPER
|
||||
#![deny(warnings, rust_2018_idioms, unused_lifetimes)]
|
||||
|
||||
use std::env;
|
||||
use std::ffi::OsString;
|
||||
use std::io;
|
||||
|
@ -124,8 +121,9 @@ fn main() {
|
|||
|
||||
if env::var_os("RUSTC_DENY_WARNINGS").is_some() &&
|
||||
env::var_os("RUSTC_EXTERNAL_TOOL").is_none() {
|
||||
// When extending this list, search for `NO-RUSTC-WRAPPER` and add the new lints
|
||||
// there as well, some code doesn't go through this `rustc` wrapper.
|
||||
// When extending this list, add the new lints to the RUSTFLAGS of the
|
||||
// build_bootstrap function of src/bootstrap/bootstrap.py as well as
|
||||
// some code doesn't go through this `rustc` wrapper.
|
||||
cmd.arg("-Dwarnings");
|
||||
cmd.arg("-Drust_2018_idioms");
|
||||
cmd.arg("-Dunused_lifetimes");
|
||||
|
|
|
@ -2,9 +2,6 @@
|
|||
//!
|
||||
//! See comments in `src/bootstrap/rustc.rs` for more information.
|
||||
|
||||
// NO-RUSTC-WRAPPER
|
||||
#![deny(warnings, rust_2018_idioms, unused_lifetimes)]
|
||||
|
||||
use std::env;
|
||||
use std::process::Command;
|
||||
use std::path::PathBuf;
|
||||
|
|
|
@ -631,6 +631,8 @@ class RustBuild(object):
|
|||
target_linker = self.get_toml("linker", build_section)
|
||||
if target_linker is not None:
|
||||
env["RUSTFLAGS"] += "-C linker=" + target_linker + " "
|
||||
if self.get_toml("deny-warnings", "rust") != "false":
|
||||
env["RUSTFLAGS"] += "-Dwarnings -Drust_2018_idioms -Dunused_lifetimes "
|
||||
|
||||
env["PATH"] = os.path.join(self.bin_root(), "bin") + \
|
||||
os.pathsep + env["PATH"]
|
||||
|
|
|
@ -34,7 +34,7 @@ impl Step for Std {
|
|||
const DEFAULT: bool = true;
|
||||
|
||||
fn should_run(run: ShouldRun<'_>) -> ShouldRun<'_> {
|
||||
run.all_krates("std")
|
||||
run.all_krates("test")
|
||||
}
|
||||
|
||||
fn make_run(run: RunConfig<'_>) {
|
||||
|
|
|
@ -39,7 +39,7 @@ impl Step for Std {
|
|||
const DEFAULT: bool = true;
|
||||
|
||||
fn should_run(run: ShouldRun<'_>) -> ShouldRun<'_> {
|
||||
run.all_krates("std")
|
||||
run.all_krates("test")
|
||||
}
|
||||
|
||||
fn make_run(run: RunConfig<'_>) {
|
||||
|
|
|
@ -413,7 +413,7 @@ impl Step for Std {
|
|||
|
||||
fn should_run(run: ShouldRun<'_>) -> ShouldRun<'_> {
|
||||
let builder = run.builder;
|
||||
run.all_krates("std").default_condition(builder.config.docs)
|
||||
run.all_krates("test").default_condition(builder.config.docs)
|
||||
}
|
||||
|
||||
fn make_run(run: RunConfig<'_>) {
|
||||
|
|
|
@ -103,9 +103,6 @@
|
|||
//! More documentation can be found in each respective module below, and you can
|
||||
//! also check out the `src/bootstrap/README.md` file for more information.
|
||||
|
||||
// NO-RUSTC-WRAPPER
|
||||
#![deny(warnings, rust_2018_idioms, unused_lifetimes)]
|
||||
|
||||
#![feature(core_intrinsics)]
|
||||
#![feature(drain_filter)]
|
||||
|
||||
|
|
|
@ -1,6 +1,3 @@
|
|||
// NO-RUSTC-WRAPPER
|
||||
#![deny(warnings, rust_2018_idioms, unused_lifetimes)]
|
||||
|
||||
use std::fs::File;
|
||||
use std::path::{Path, PathBuf};
|
||||
use std::process::{Command, Stdio};
|
||||
|
|
|
@ -1015,8 +1015,8 @@ mod impls {
|
|||
// The order here is important to generate more optimal assembly.
|
||||
// See <https://github.com/rust-lang/rust/issues/63758> for more info.
|
||||
if *self < *other { Less }
|
||||
else if *self > *other { Greater }
|
||||
else { Equal }
|
||||
else if *self == *other { Equal }
|
||||
else { Greater }
|
||||
}
|
||||
}
|
||||
)*)
|
||||
|
|
|
@ -273,14 +273,12 @@ impl<'tcx> LayoutCx<'tcx, TyCtxt<'tcx>> {
|
|||
repr: &ReprOptions,
|
||||
kind: StructKind) -> Result<LayoutDetails, LayoutError<'tcx>> {
|
||||
let dl = self.data_layout();
|
||||
let packed = repr.packed();
|
||||
if packed && repr.align > 0 {
|
||||
let pack = repr.pack;
|
||||
if pack.is_some() && repr.align.is_some() {
|
||||
bug!("struct cannot be packed and aligned");
|
||||
}
|
||||
|
||||
let pack = Align::from_bytes(repr.pack as u64).unwrap();
|
||||
|
||||
let mut align = if packed {
|
||||
let mut align = if pack.is_some() {
|
||||
dl.i8_align
|
||||
} else {
|
||||
dl.aggregate_align
|
||||
|
@ -303,7 +301,7 @@ impl<'tcx> LayoutCx<'tcx, TyCtxt<'tcx>> {
|
|||
};
|
||||
let optimizing = &mut inverse_memory_index[..end];
|
||||
let field_align = |f: &TyLayout<'_>| {
|
||||
if packed { f.align.abi.min(pack) } else { f.align.abi }
|
||||
if let Some(pack) = pack { f.align.abi.min(pack) } else { f.align.abi }
|
||||
};
|
||||
match kind {
|
||||
StructKind::AlwaysSized |
|
||||
|
@ -334,7 +332,7 @@ impl<'tcx> LayoutCx<'tcx, TyCtxt<'tcx>> {
|
|||
let mut largest_niche_available = 0;
|
||||
|
||||
if let StructKind::Prefixed(prefix_size, prefix_align) = kind {
|
||||
let prefix_align = if packed {
|
||||
let prefix_align = if let Some(pack) = pack {
|
||||
prefix_align.min(pack)
|
||||
} else {
|
||||
prefix_align
|
||||
|
@ -355,7 +353,7 @@ impl<'tcx> LayoutCx<'tcx, TyCtxt<'tcx>> {
|
|||
}
|
||||
|
||||
// Invariant: offset < dl.obj_size_bound() <= 1<<61
|
||||
let field_align = if packed {
|
||||
let field_align = if let Some(pack) = pack {
|
||||
field.align.min(AbiAndPrefAlign::new(pack))
|
||||
} else {
|
||||
field.align
|
||||
|
@ -379,10 +377,8 @@ impl<'tcx> LayoutCx<'tcx, TyCtxt<'tcx>> {
|
|||
.ok_or(LayoutError::SizeOverflow(ty))?;
|
||||
}
|
||||
|
||||
if repr.align > 0 {
|
||||
let repr_align = repr.align as u64;
|
||||
align = align.max(AbiAndPrefAlign::new(Align::from_bytes(repr_align).unwrap()));
|
||||
debug!("univariant repr_align: {:?}", repr_align);
|
||||
if let Some(repr_align) = repr.align {
|
||||
align = align.max(AbiAndPrefAlign::new(repr_align));
|
||||
}
|
||||
|
||||
debug!("univariant min_size: {:?}", offset);
|
||||
|
@ -730,23 +726,18 @@ impl<'tcx> LayoutCx<'tcx, TyCtxt<'tcx>> {
|
|||
}).collect::<Result<IndexVec<VariantIdx, _>, _>>()?;
|
||||
|
||||
if def.is_union() {
|
||||
let packed = def.repr.packed();
|
||||
if packed && def.repr.align > 0 {
|
||||
bug!("Union cannot be packed and aligned");
|
||||
if def.repr.pack.is_some() && def.repr.align.is_some() {
|
||||
bug!("union cannot be packed and aligned");
|
||||
}
|
||||
|
||||
let pack = Align::from_bytes(def.repr.pack as u64).unwrap();
|
||||
|
||||
let mut align = if packed {
|
||||
let mut align = if def.repr.pack.is_some() {
|
||||
dl.i8_align
|
||||
} else {
|
||||
dl.aggregate_align
|
||||
};
|
||||
|
||||
if def.repr.align > 0 {
|
||||
let repr_align = def.repr.align as u64;
|
||||
align = align.max(
|
||||
AbiAndPrefAlign::new(Align::from_bytes(repr_align).unwrap()));
|
||||
if let Some(repr_align) = def.repr.align {
|
||||
align = align.max(AbiAndPrefAlign::new(repr_align));
|
||||
}
|
||||
|
||||
let optimize = !def.repr.inhibit_union_abi_opt();
|
||||
|
@ -755,13 +746,7 @@ impl<'tcx> LayoutCx<'tcx, TyCtxt<'tcx>> {
|
|||
let index = VariantIdx::new(0);
|
||||
for field in &variants[index] {
|
||||
assert!(!field.is_unsized());
|
||||
|
||||
let field_align = if packed {
|
||||
field.align.min(AbiAndPrefAlign::new(pack))
|
||||
} else {
|
||||
field.align
|
||||
};
|
||||
align = align.max(field_align);
|
||||
align = align.max(field.align);
|
||||
|
||||
// If all non-ZST fields have the same ABI, forward this ABI
|
||||
if optimize && !field.is_zst() {
|
||||
|
@ -796,6 +781,10 @@ impl<'tcx> LayoutCx<'tcx, TyCtxt<'tcx>> {
|
|||
size = cmp::max(size, field.size);
|
||||
}
|
||||
|
||||
if let Some(pack) = def.repr.pack {
|
||||
align = align.min(AbiAndPrefAlign::new(pack));
|
||||
}
|
||||
|
||||
return Ok(tcx.intern_layout(LayoutDetails {
|
||||
variants: Variants::Single { index },
|
||||
fields: FieldPlacement::Union(variants[index].len()),
|
||||
|
@ -1637,7 +1626,7 @@ impl<'tcx> LayoutCx<'tcx, TyCtxt<'tcx>> {
|
|||
};
|
||||
|
||||
let adt_kind = adt_def.adt_kind();
|
||||
let adt_packed = adt_def.repr.packed();
|
||||
let adt_packed = adt_def.repr.pack.is_some();
|
||||
|
||||
let build_variant_info = |n: Option<Ident>,
|
||||
flds: &[ast::Name],
|
||||
|
|
|
@ -33,6 +33,7 @@ use arena::SyncDroplessArena;
|
|||
use crate::session::DataTypeKind;
|
||||
|
||||
use rustc_serialize::{self, Encodable, Encoder};
|
||||
use rustc_target::abi::Align;
|
||||
use std::cell::RefCell;
|
||||
use std::cmp::{self, Ordering};
|
||||
use std::fmt;
|
||||
|
@ -2057,8 +2058,8 @@ impl_stable_hash_for!(struct ReprFlags {
|
|||
#[derive(Copy, Clone, Debug, Eq, PartialEq, RustcEncodable, RustcDecodable, Default)]
|
||||
pub struct ReprOptions {
|
||||
pub int: Option<attr::IntType>,
|
||||
pub align: u32,
|
||||
pub pack: u32,
|
||||
pub align: Option<Align>,
|
||||
pub pack: Option<Align>,
|
||||
pub flags: ReprFlags,
|
||||
}
|
||||
|
||||
|
@ -2073,18 +2074,19 @@ impl ReprOptions {
|
|||
pub fn new(tcx: TyCtxt<'_>, did: DefId) -> ReprOptions {
|
||||
let mut flags = ReprFlags::empty();
|
||||
let mut size = None;
|
||||
let mut max_align = 0;
|
||||
let mut min_pack = 0;
|
||||
let mut max_align: Option<Align> = None;
|
||||
let mut min_pack: Option<Align> = None;
|
||||
for attr in tcx.get_attrs(did).iter() {
|
||||
for r in attr::find_repr_attrs(&tcx.sess.parse_sess, attr) {
|
||||
flags.insert(match r {
|
||||
attr::ReprC => ReprFlags::IS_C,
|
||||
attr::ReprPacked(pack) => {
|
||||
min_pack = if min_pack > 0 {
|
||||
cmp::min(pack, min_pack)
|
||||
let pack = Align::from_bytes(pack as u64).unwrap();
|
||||
min_pack = Some(if let Some(min_pack) = min_pack {
|
||||
min_pack.min(pack)
|
||||
} else {
|
||||
pack
|
||||
};
|
||||
});
|
||||
ReprFlags::empty()
|
||||
},
|
||||
attr::ReprTransparent => ReprFlags::IS_TRANSPARENT,
|
||||
|
@ -2094,7 +2096,7 @@ impl ReprOptions {
|
|||
ReprFlags::empty()
|
||||
},
|
||||
attr::ReprAlign(align) => {
|
||||
max_align = cmp::max(align, max_align);
|
||||
max_align = max_align.max(Some(Align::from_bytes(align as u64).unwrap()));
|
||||
ReprFlags::empty()
|
||||
},
|
||||
});
|
||||
|
@ -2113,7 +2115,7 @@ impl ReprOptions {
|
|||
#[inline]
|
||||
pub fn c(&self) -> bool { self.flags.contains(ReprFlags::IS_C) }
|
||||
#[inline]
|
||||
pub fn packed(&self) -> bool { self.pack > 0 }
|
||||
pub fn packed(&self) -> bool { self.pack.is_some() }
|
||||
#[inline]
|
||||
pub fn transparent(&self) -> bool { self.flags.contains(ReprFlags::IS_TRANSPARENT) }
|
||||
#[inline]
|
||||
|
@ -2133,8 +2135,12 @@ impl ReprOptions {
|
|||
/// Returns `true` if this `#[repr()]` should inhibit struct field reordering
|
||||
/// optimizations, such as with `repr(C)`, `repr(packed(1))`, or `repr(<int>)`.
|
||||
pub fn inhibit_struct_field_reordering_opt(&self) -> bool {
|
||||
self.flags.intersects(ReprFlags::IS_UNOPTIMISABLE) || self.pack == 1 ||
|
||||
self.int.is_some()
|
||||
if let Some(pack) = self.pack {
|
||||
if pack.bytes() == 1 {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
self.flags.intersects(ReprFlags::IS_UNOPTIMISABLE) || self.int.is_some()
|
||||
}
|
||||
|
||||
/// Returns `true` if this `#[repr()]` should inhibit union ABI optimisations.
|
||||
|
|
|
@ -527,9 +527,7 @@ impl<'a, 'tcx> CrateMetadata {
|
|||
attributes.iter().cloned().map(Symbol::intern).collect::<Vec<_>>();
|
||||
(
|
||||
trait_name,
|
||||
SyntaxExtensionKind::Derive(Box::new(ProcMacroDerive {
|
||||
client, attrs: helper_attrs.clone()
|
||||
})),
|
||||
SyntaxExtensionKind::Derive(Box::new(ProcMacroDerive { client })),
|
||||
helper_attrs,
|
||||
)
|
||||
}
|
||||
|
|
|
@ -11,7 +11,7 @@ use std::hash::Hash;
|
|||
|
||||
use super::{
|
||||
GlobalAlloc, InterpResult,
|
||||
OpTy, Machine, InterpCx, ValueVisitor, MPlaceTy,
|
||||
Scalar, OpTy, Machine, InterpCx, ValueVisitor, MPlaceTy,
|
||||
};
|
||||
|
||||
macro_rules! throw_validation_failure {
|
||||
|
@ -250,6 +250,47 @@ impl<'rt, 'mir, 'tcx, M: Machine<'mir, 'tcx>> ValidityVisitor<'rt, 'mir, 'tcx, M
|
|||
self.path.truncate(path_len);
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn check_wide_ptr_meta(
|
||||
&mut self,
|
||||
meta: Option<Scalar<M::PointerTag>>,
|
||||
pointee: TyLayout<'tcx>,
|
||||
) -> InterpResult<'tcx> {
|
||||
let tail = self.ecx.tcx.struct_tail_erasing_lifetimes(pointee.ty, self.ecx.param_env);
|
||||
match tail.sty {
|
||||
ty::Dynamic(..) => {
|
||||
let vtable = meta.unwrap();
|
||||
try_validation!(
|
||||
self.ecx.memory.check_ptr_access(
|
||||
vtable,
|
||||
3*self.ecx.tcx.data_layout.pointer_size, // drop, size, align
|
||||
self.ecx.tcx.data_layout.pointer_align.abi,
|
||||
),
|
||||
"dangling or unaligned vtable pointer in wide pointer or too small vtable",
|
||||
self.path
|
||||
);
|
||||
try_validation!(self.ecx.read_drop_type_from_vtable(vtable),
|
||||
"invalid drop fn in vtable", self.path);
|
||||
try_validation!(self.ecx.read_size_and_align_from_vtable(vtable),
|
||||
"invalid size or align in vtable", self.path);
|
||||
// FIXME: More checks for the vtable.
|
||||
}
|
||||
ty::Slice(..) | ty::Str => {
|
||||
let _len = try_validation!(meta.unwrap().to_usize(self.ecx),
|
||||
"non-integer slice length in wide pointer", self.path);
|
||||
// We do not check that `len * elem_size <= isize::MAX`:
|
||||
// that is only required for references, and there it falls out of the
|
||||
// "dereferencable" check performed by Stacked Borrows.
|
||||
}
|
||||
ty::Foreign(..) => {
|
||||
// Unsized, but not wide.
|
||||
}
|
||||
_ =>
|
||||
bug!("Unexpected unsized type tail: {:?}", tail),
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
impl<'rt, 'mir, 'tcx, M: Machine<'mir, 'tcx>> ValueVisitor<'mir, 'tcx, M>
|
||||
|
@ -341,56 +382,34 @@ impl<'rt, 'mir, 'tcx, M: Machine<'mir, 'tcx>> ValueVisitor<'mir, 'tcx, M>
|
|||
}
|
||||
}
|
||||
ty::RawPtr(..) => {
|
||||
// Check pointer part.
|
||||
if self.ref_tracking_for_consts.is_some() {
|
||||
// Integers/floats in CTFE: For consistency with integers, we do not
|
||||
// accept undef.
|
||||
let _ptr = try_validation!(value.to_scalar_ptr(),
|
||||
"undefined address in raw pointer", self.path);
|
||||
let _meta = try_validation!(value.to_meta(),
|
||||
"uninitialized data in raw fat pointer metadata", self.path);
|
||||
} else {
|
||||
// Remain consistent with `usize`: Accept anything.
|
||||
}
|
||||
|
||||
// Check metadata.
|
||||
let meta = try_validation!(value.to_meta(),
|
||||
"uninitialized data in wide pointer metadata", self.path);
|
||||
let layout = self.ecx.layout_of(value.layout.ty.builtin_deref(true).unwrap().ty)?;
|
||||
if layout.is_unsized() {
|
||||
self.check_wide_ptr_meta(meta, layout)?;
|
||||
}
|
||||
}
|
||||
_ if ty.is_box() || ty.is_region_ptr() => {
|
||||
// Handle fat pointers.
|
||||
// Handle wide pointers.
|
||||
// Check metadata early, for better diagnostics
|
||||
let ptr = try_validation!(value.to_scalar_ptr(),
|
||||
"undefined address in pointer", self.path);
|
||||
let meta = try_validation!(value.to_meta(),
|
||||
"uninitialized data in fat pointer metadata", self.path);
|
||||
"uninitialized data in wide pointer metadata", self.path);
|
||||
let layout = self.ecx.layout_of(value.layout.ty.builtin_deref(true).unwrap().ty)?;
|
||||
if layout.is_unsized() {
|
||||
let tail = self.ecx.tcx.struct_tail_erasing_lifetimes(layout.ty,
|
||||
self.ecx.param_env);
|
||||
match tail.sty {
|
||||
ty::Dynamic(..) => {
|
||||
let vtable = meta.unwrap();
|
||||
try_validation!(
|
||||
self.ecx.memory.check_ptr_access(
|
||||
vtable,
|
||||
3*self.ecx.tcx.data_layout.pointer_size, // drop, size, align
|
||||
self.ecx.tcx.data_layout.pointer_align.abi,
|
||||
),
|
||||
"dangling or unaligned vtable pointer or too small vtable",
|
||||
self.path
|
||||
);
|
||||
try_validation!(self.ecx.read_drop_type_from_vtable(vtable),
|
||||
"invalid drop fn in vtable", self.path);
|
||||
try_validation!(self.ecx.read_size_and_align_from_vtable(vtable),
|
||||
"invalid size or align in vtable", self.path);
|
||||
// FIXME: More checks for the vtable.
|
||||
}
|
||||
ty::Slice(..) | ty::Str => {
|
||||
try_validation!(meta.unwrap().to_usize(self.ecx),
|
||||
"non-integer slice length in fat pointer", self.path);
|
||||
}
|
||||
ty::Foreign(..) => {
|
||||
// Unsized, but not fat.
|
||||
}
|
||||
_ =>
|
||||
bug!("Unexpected unsized type tail: {:?}", tail),
|
||||
}
|
||||
self.check_wide_ptr_meta(meta, layout)?;
|
||||
}
|
||||
// Make sure this is dereferencable and all.
|
||||
let (size, align) = self.ecx.size_and_align_of(meta, layout)?
|
||||
|
|
|
@ -13,7 +13,7 @@ use rustc::{ty, lint, span_bug};
|
|||
use syntax::ast::{self, NodeId, Ident};
|
||||
use syntax::attr::StabilityLevel;
|
||||
use syntax::edition::Edition;
|
||||
use syntax::ext::base::{self, Indeterminate, SpecialDerives};
|
||||
use syntax::ext::base::{self, InvocationRes, Indeterminate, SpecialDerives};
|
||||
use syntax::ext::base::{MacroKind, SyntaxExtension};
|
||||
use syntax::ext::expand::{AstFragment, Invocation, InvocationKind};
|
||||
use syntax::ext::hygiene::{self, ExpnId, ExpnData, ExpnKind};
|
||||
|
@ -142,7 +142,7 @@ impl<'a> base::Resolver for Resolver<'a> {
|
|||
|
||||
fn resolve_macro_invocation(
|
||||
&mut self, invoc: &Invocation, eager_expansion_root: ExpnId, force: bool
|
||||
) -> Result<Option<Lrc<SyntaxExtension>>, Indeterminate> {
|
||||
) -> Result<InvocationRes, Indeterminate> {
|
||||
let invoc_id = invoc.expansion_data.id;
|
||||
let parent_scope = match self.invocation_parent_scopes.get(&invoc_id) {
|
||||
Some(parent_scope) => *parent_scope,
|
||||
|
@ -165,25 +165,24 @@ impl<'a> base::Resolver for Resolver<'a> {
|
|||
InvocationKind::Derive { ref path, .. } =>
|
||||
(path, MacroKind::Derive, &[][..], false),
|
||||
InvocationKind::DeriveContainer { ref derives, .. } => {
|
||||
// Block expansion of derives in the container until we know whether one of them
|
||||
// is a built-in `Copy`. Skip the resolution if there's only one derive - either
|
||||
// it's not a `Copy` and we don't need to do anything, or it's a `Copy` and it
|
||||
// will automatically knows about itself.
|
||||
let mut result = Ok(None);
|
||||
if derives.len() > 1 {
|
||||
for path in derives {
|
||||
match self.resolve_macro_path(path, Some(MacroKind::Derive),
|
||||
&parent_scope, true, force) {
|
||||
Ok((Some(ref ext), _)) if ext.is_derive_copy => {
|
||||
self.add_derives(invoc_id, SpecialDerives::COPY);
|
||||
return Ok(None);
|
||||
}
|
||||
Err(Determinacy::Undetermined) => result = Err(Indeterminate),
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
// Block expansion of the container until we resolve all derives in it.
|
||||
// This is required for two reasons:
|
||||
// - Derive helper attributes are in scope for the item to which the `#[derive]`
|
||||
// is applied, so they have to be produced by the container's expansion rather
|
||||
// than by individual derives.
|
||||
// - Derives in the container need to know whether one of them is a built-in `Copy`.
|
||||
// FIXME: Try to avoid repeated resolutions for derives here and in expansion.
|
||||
let mut exts = Vec::new();
|
||||
for path in derives {
|
||||
exts.push(match self.resolve_macro_path(
|
||||
path, Some(MacroKind::Derive), &parent_scope, true, force
|
||||
) {
|
||||
Ok((Some(ext), _)) => ext,
|
||||
Ok(_) | Err(Determinacy::Determined) => self.dummy_ext(MacroKind::Derive),
|
||||
Err(Determinacy::Undetermined) => return Err(Indeterminate),
|
||||
})
|
||||
}
|
||||
return result;
|
||||
return Ok(InvocationRes::DeriveContainer(exts));
|
||||
}
|
||||
};
|
||||
|
||||
|
@ -203,7 +202,7 @@ impl<'a> base::Resolver for Resolver<'a> {
|
|||
self.definitions.add_parent_module_of_macro_def(invoc_id, normal_module_def_id);
|
||||
}
|
||||
|
||||
Ok(Some(ext))
|
||||
Ok(InvocationRes::Single(ext))
|
||||
}
|
||||
|
||||
fn check_unused_macros(&self) {
|
||||
|
|
|
@ -1859,14 +1859,18 @@ fn check_packed(tcx: TyCtxt<'_>, sp: Span, def_id: DefId) {
|
|||
for attr in tcx.get_attrs(def_id).iter() {
|
||||
for r in attr::find_repr_attrs(&tcx.sess.parse_sess, attr) {
|
||||
if let attr::ReprPacked(pack) = r {
|
||||
if pack != repr.pack {
|
||||
struct_span_err!(tcx.sess, sp, E0634,
|
||||
"type has conflicting packed representation hints").emit();
|
||||
if let Some(repr_pack) = repr.pack {
|
||||
if pack as u64 != repr_pack.bytes() {
|
||||
struct_span_err!(
|
||||
tcx.sess, sp, E0634,
|
||||
"type has conflicting packed representation hints"
|
||||
).emit();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if repr.align > 0 {
|
||||
if repr.align.is_some() {
|
||||
struct_span_err!(tcx.sess, sp, E0587,
|
||||
"type has conflicting packed and align representation hints").emit();
|
||||
}
|
||||
|
@ -1885,7 +1889,7 @@ fn check_packed_inner(tcx: TyCtxt<'_>, def_id: DefId, stack: &mut Vec<DefId>) ->
|
|||
}
|
||||
if let ty::Adt(def, substs) = t.sty {
|
||||
if def.is_struct() || def.is_union() {
|
||||
if tcx.adt_def(def.did).repr.align > 0 {
|
||||
if tcx.adt_def(def.did).repr.align.is_some() {
|
||||
return true;
|
||||
}
|
||||
// push struct def_id before checking fields
|
||||
|
|
|
@ -11,6 +11,7 @@ use crate::ptr::P;
|
|||
use crate::symbol::{kw, sym, Ident, Symbol};
|
||||
use crate::{ThinVec, MACRO_ARGUMENTS};
|
||||
use crate::tokenstream::{self, TokenStream, TokenTree};
|
||||
use crate::visit::Visitor;
|
||||
|
||||
use errors::{DiagnosticBuilder, DiagnosticId};
|
||||
use smallvec::{smallvec, SmallVec};
|
||||
|
@ -72,6 +73,17 @@ impl Annotatable {
|
|||
}
|
||||
}
|
||||
|
||||
pub fn visit_with<'a, V: Visitor<'a>>(&'a self, visitor: &mut V) {
|
||||
match self {
|
||||
Annotatable::Item(item) => visitor.visit_item(item),
|
||||
Annotatable::TraitItem(trait_item) => visitor.visit_trait_item(trait_item),
|
||||
Annotatable::ImplItem(impl_item) => visitor.visit_impl_item(impl_item),
|
||||
Annotatable::ForeignItem(foreign_item) => visitor.visit_foreign_item(foreign_item),
|
||||
Annotatable::Stmt(stmt) => visitor.visit_stmt(stmt),
|
||||
Annotatable::Expr(expr) => visitor.visit_expr(expr),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn expect_item(self) -> P<ast::Item> {
|
||||
match self {
|
||||
Annotatable::Item(i) => i,
|
||||
|
@ -700,6 +712,12 @@ impl SyntaxExtension {
|
|||
|
||||
pub type NamedSyntaxExtension = (Name, SyntaxExtension);
|
||||
|
||||
/// Result of resolving a macro invocation.
|
||||
pub enum InvocationRes {
|
||||
Single(Lrc<SyntaxExtension>),
|
||||
DeriveContainer(Vec<Lrc<SyntaxExtension>>),
|
||||
}
|
||||
|
||||
/// Error type that denotes indeterminacy.
|
||||
pub struct Indeterminate;
|
||||
|
||||
|
@ -727,7 +745,7 @@ pub trait Resolver {
|
|||
|
||||
fn resolve_macro_invocation(
|
||||
&mut self, invoc: &Invocation, eager_expansion_root: ExpnId, force: bool
|
||||
) -> Result<Option<Lrc<SyntaxExtension>>, Indeterminate>;
|
||||
) -> Result<InvocationRes, Indeterminate>;
|
||||
|
||||
fn check_unused_macros(&self);
|
||||
|
||||
|
|
|
@ -4,7 +4,7 @@ use crate::attr::{self, HasAttrs};
|
|||
use crate::source_map::respan;
|
||||
use crate::config::StripUnconfigured;
|
||||
use crate::ext::base::*;
|
||||
use crate::ext::proc_macro::collect_derives;
|
||||
use crate::ext::proc_macro::{collect_derives, MarkAttrs};
|
||||
use crate::ext::hygiene::{ExpnId, SyntaxContext, ExpnData, ExpnKind};
|
||||
use crate::ext::tt::macro_rules::annotate_err_with_kind;
|
||||
use crate::ext::placeholders::{placeholder, PlaceholderExpander};
|
||||
|
@ -307,10 +307,10 @@ impl<'a, 'b> MacroExpander<'a, 'b> {
|
|||
|
||||
let eager_expansion_root =
|
||||
if self.monotonic { invoc.expansion_data.id } else { orig_expansion_data.id };
|
||||
let ext = match self.cx.resolver.resolve_macro_invocation(
|
||||
let res = match self.cx.resolver.resolve_macro_invocation(
|
||||
&invoc, eager_expansion_root, force
|
||||
) {
|
||||
Ok(ext) => ext,
|
||||
Ok(res) => res,
|
||||
Err(Indeterminate) => {
|
||||
undetermined_invocations.push(invoc);
|
||||
continue
|
||||
|
@ -322,54 +322,72 @@ impl<'a, 'b> MacroExpander<'a, 'b> {
|
|||
self.cx.current_expansion = invoc.expansion_data.clone();
|
||||
|
||||
// FIXME(jseyfried): Refactor out the following logic
|
||||
let (expanded_fragment, new_invocations) = if let Some(ext) = ext {
|
||||
let fragment = self.expand_invoc(invoc, &ext.kind);
|
||||
self.collect_invocations(fragment, &[])
|
||||
} else if let InvocationKind::DeriveContainer { derives: traits, item } = invoc.kind {
|
||||
if !item.derive_allowed() {
|
||||
let attr = attr::find_by_name(item.attrs(), sym::derive)
|
||||
.expect("`derive` attribute should exist");
|
||||
let span = attr.span;
|
||||
let mut err = self.cx.mut_span_err(span,
|
||||
"`derive` may only be applied to \
|
||||
structs, enums and unions");
|
||||
if let ast::AttrStyle::Inner = attr.style {
|
||||
let trait_list = traits.iter()
|
||||
.map(|t| t.to_string()).collect::<Vec<_>>();
|
||||
let suggestion = format!("#[derive({})]", trait_list.join(", "));
|
||||
err.span_suggestion(
|
||||
span, "try an outer attribute", suggestion,
|
||||
// We don't 𝑘𝑛𝑜𝑤 that the following item is an ADT
|
||||
Applicability::MaybeIncorrect
|
||||
);
|
||||
let (expanded_fragment, new_invocations) = match res {
|
||||
InvocationRes::Single(ext) => {
|
||||
let fragment = self.expand_invoc(invoc, &ext.kind);
|
||||
self.collect_invocations(fragment, &[])
|
||||
}
|
||||
InvocationRes::DeriveContainer(exts) => {
|
||||
let (derives, item) = match invoc.kind {
|
||||
InvocationKind::DeriveContainer { derives, item } => (derives, item),
|
||||
_ => unreachable!(),
|
||||
};
|
||||
if !item.derive_allowed() {
|
||||
let attr = attr::find_by_name(item.attrs(), sym::derive)
|
||||
.expect("`derive` attribute should exist");
|
||||
let span = attr.span;
|
||||
let mut err = self.cx.mut_span_err(span,
|
||||
"`derive` may only be applied to structs, enums and unions");
|
||||
if let ast::AttrStyle::Inner = attr.style {
|
||||
let trait_list = derives.iter()
|
||||
.map(|t| t.to_string()).collect::<Vec<_>>();
|
||||
let suggestion = format!("#[derive({})]", trait_list.join(", "));
|
||||
err.span_suggestion(
|
||||
span, "try an outer attribute", suggestion,
|
||||
// We don't 𝑘𝑛𝑜𝑤 that the following item is an ADT
|
||||
Applicability::MaybeIncorrect
|
||||
);
|
||||
}
|
||||
err.emit();
|
||||
}
|
||||
err.emit();
|
||||
}
|
||||
|
||||
let mut item = self.fully_configure(item);
|
||||
item.visit_attrs(|attrs| attrs.retain(|a| a.path != sym::derive));
|
||||
let derive_placeholders =
|
||||
all_derive_placeholders.entry(invoc.expansion_data.id).or_default();
|
||||
let mut item = self.fully_configure(item);
|
||||
item.visit_attrs(|attrs| attrs.retain(|a| a.path != sym::derive));
|
||||
let mut helper_attrs = Vec::new();
|
||||
let mut has_copy = false;
|
||||
for ext in exts {
|
||||
helper_attrs.extend(&ext.helper_attrs);
|
||||
has_copy |= ext.is_derive_copy;
|
||||
}
|
||||
// Mark derive helpers inside this item as known and used.
|
||||
// FIXME: This is a hack, derive helpers should be integrated with regular name
|
||||
// resolution instead. For example, helpers introduced by a derive container
|
||||
// can be in scope for all code produced by that container's expansion.
|
||||
item.visit_with(&mut MarkAttrs(&helper_attrs));
|
||||
if has_copy {
|
||||
self.cx.resolver.add_derives(invoc.expansion_data.id, SpecialDerives::COPY);
|
||||
}
|
||||
|
||||
derive_placeholders.reserve(traits.len());
|
||||
invocations.reserve(traits.len());
|
||||
for path in traits {
|
||||
let expn_id = ExpnId::fresh(None);
|
||||
derive_placeholders.push(NodeId::placeholder_from_expn_id(expn_id));
|
||||
invocations.push(Invocation {
|
||||
kind: InvocationKind::Derive { path, item: item.clone() },
|
||||
fragment_kind: invoc.fragment_kind,
|
||||
expansion_data: ExpansionData {
|
||||
id: expn_id,
|
||||
..invoc.expansion_data.clone()
|
||||
},
|
||||
});
|
||||
let derive_placeholders =
|
||||
all_derive_placeholders.entry(invoc.expansion_data.id).or_default();
|
||||
derive_placeholders.reserve(derives.len());
|
||||
invocations.reserve(derives.len());
|
||||
for path in derives {
|
||||
let expn_id = ExpnId::fresh(None);
|
||||
derive_placeholders.push(NodeId::placeholder_from_expn_id(expn_id));
|
||||
invocations.push(Invocation {
|
||||
kind: InvocationKind::Derive { path, item: item.clone() },
|
||||
fragment_kind: invoc.fragment_kind,
|
||||
expansion_data: ExpansionData {
|
||||
id: expn_id,
|
||||
..invoc.expansion_data.clone()
|
||||
},
|
||||
});
|
||||
}
|
||||
let fragment = invoc.fragment_kind
|
||||
.expect_from_annotatables(::std::iter::once(item));
|
||||
self.collect_invocations(fragment, derive_placeholders)
|
||||
}
|
||||
let fragment = invoc.fragment_kind
|
||||
.expect_from_annotatables(::std::iter::once(item));
|
||||
self.collect_invocations(fragment, derive_placeholders)
|
||||
} else {
|
||||
unreachable!()
|
||||
};
|
||||
|
||||
if expanded_fragments.len() < depth {
|
||||
|
|
|
@ -78,7 +78,6 @@ pub struct ProcMacroDerive {
|
|||
pub client: proc_macro::bridge::client::Client<
|
||||
fn(proc_macro::TokenStream) -> proc_macro::TokenStream,
|
||||
>,
|
||||
pub attrs: Vec<ast::Name>,
|
||||
}
|
||||
|
||||
impl MultiItemModifier for ProcMacroDerive {
|
||||
|
@ -111,9 +110,6 @@ impl MultiItemModifier for ProcMacroDerive {
|
|||
}
|
||||
}
|
||||
|
||||
// Mark attributes as known, and used.
|
||||
MarkAttrs(&self.attrs).visit_item(&item);
|
||||
|
||||
let token = token::Interpolated(Lrc::new(token::NtItem(item)));
|
||||
let input = tokenstream::TokenTree::token(token, DUMMY_SP).into();
|
||||
|
||||
|
@ -164,7 +160,7 @@ impl MultiItemModifier for ProcMacroDerive {
|
|||
}
|
||||
}
|
||||
|
||||
struct MarkAttrs<'a>(&'a [ast::Name]);
|
||||
crate struct MarkAttrs<'a>(crate &'a [ast::Name]);
|
||||
|
||||
impl<'a> Visitor<'a> for MarkAttrs<'a> {
|
||||
fn visit_attribute(&mut self, attr: &Attribute) {
|
||||
|
|
|
@ -11,7 +11,7 @@ use std::cmp::Ordering;
|
|||
#[no_mangle]
|
||||
pub fn cmp_signed(a: i64, b: i64) -> Ordering {
|
||||
// CHECK: icmp slt
|
||||
// CHECK: icmp sgt
|
||||
// CHECK: icmp ne
|
||||
// CHECK: zext i1
|
||||
// CHECK: select i1
|
||||
a.cmp(&b)
|
||||
|
@ -21,7 +21,7 @@ pub fn cmp_signed(a: i64, b: i64) -> Ordering {
|
|||
#[no_mangle]
|
||||
pub fn cmp_unsigned(a: u32, b: u32) -> Ordering {
|
||||
// CHECK: icmp ult
|
||||
// CHECK: icmp ugt
|
||||
// CHECK: icmp ne
|
||||
// CHECK: zext i1
|
||||
// CHECK: select i1
|
||||
a.cmp(&b)
|
||||
|
|
|
@ -1,3 +1,4 @@
|
|||
// ignore-tidy-linelength
|
||||
#![allow(unused)]
|
||||
#![allow(const_err)] // make sure we cannot allow away the errors tested here
|
||||
|
||||
|
@ -28,7 +29,9 @@ struct BadSliceRepr {
|
|||
union SliceTransmute {
|
||||
repr: SliceRepr,
|
||||
bad: BadSliceRepr,
|
||||
addr: usize,
|
||||
slice: &'static [u8],
|
||||
raw_slice: *const [u8],
|
||||
str: &'static str,
|
||||
my_str: &'static MyStr,
|
||||
my_slice: &'static MySliceBool,
|
||||
|
@ -59,7 +62,9 @@ union DynTransmute {
|
|||
repr: DynRepr,
|
||||
repr2: DynRepr2,
|
||||
bad: BadDynRepr,
|
||||
addr: usize,
|
||||
rust: &'static dyn Trait,
|
||||
raw_rust: *const dyn Trait,
|
||||
}
|
||||
|
||||
trait Trait {}
|
||||
|
@ -72,39 +77,37 @@ struct MyStr(str);
|
|||
struct MySlice<T: ?Sized>(bool, T);
|
||||
type MySliceBool = MySlice<[bool]>;
|
||||
|
||||
// # str
|
||||
// OK
|
||||
const A: &str = unsafe { SliceTransmute { repr: SliceRepr { ptr: &42, len: 1 } }.str};
|
||||
const STR_VALID: &str = unsafe { SliceTransmute { repr: SliceRepr { ptr: &42, len: 1 } }.str};
|
||||
// bad str
|
||||
const B: &str = unsafe { SliceTransmute { repr: SliceRepr { ptr: &42, len: 999 } }.str};
|
||||
const STR_TOO_LONG: &str = unsafe { SliceTransmute { repr: SliceRepr { ptr: &42, len: 999 } }.str};
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
// bad str
|
||||
const C: &str = unsafe { SliceTransmute { bad: BadSliceRepr { ptr: &42, len: &3 } }.str};
|
||||
const STR_LENGTH_PTR: &str = unsafe { SliceTransmute { bad: BadSliceRepr { ptr: &42, len: &3 } }.str};
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
// bad str in user-defined unsized type
|
||||
const C2: &MyStr = unsafe { SliceTransmute { bad: BadSliceRepr { ptr: &42, len: &3 } }.my_str};
|
||||
const MY_STR_LENGTH_PTR: &MyStr = unsafe { SliceTransmute { bad: BadSliceRepr { ptr: &42, len: &3 } }.my_str};
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
|
||||
// invalid UTF-8
|
||||
const J1: &str = unsafe { SliceTransmute { slice: &[0xFF] }.str };
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
// invalid UTF-8 in user-defined str-like
|
||||
const J2: &MyStr = unsafe { SliceTransmute { slice: &[0xFF] }.my_str };
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
|
||||
// # slice
|
||||
// OK
|
||||
const A2: &[u8] = unsafe { SliceTransmute { repr: SliceRepr { ptr: &42, len: 1 } }.slice};
|
||||
// bad slice
|
||||
const B2: &[u8] = unsafe { SliceTransmute { repr: SliceRepr { ptr: &42, len: 999 } }.slice};
|
||||
const SLICE_VALID: &[u8] = unsafe { SliceTransmute { repr: SliceRepr { ptr: &42, len: 1 } }.slice};
|
||||
// bad slice: length uninit
|
||||
const SLICE_LENGTH_UNINIT: &[u8] = unsafe { SliceTransmute { addr: 42 }.slice};
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
// bad slice
|
||||
const C3: &[u8] = unsafe { SliceTransmute { bad: BadSliceRepr { ptr: &42, len: &3 } }.slice};
|
||||
// bad slice: length too big
|
||||
const SLICE_TOO_LONG: &[u8] = unsafe { SliceTransmute { repr: SliceRepr { ptr: &42, len: 999 } }.slice};
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
|
||||
// bad trait object
|
||||
const D: &dyn Trait = unsafe { DynTransmute { repr: DynRepr { ptr: &92, vtable: &3 } }.rust};
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
// bad trait object
|
||||
const E: &dyn Trait = unsafe { DynTransmute { repr2: DynRepr2 { ptr: &92, vtable: &3 } }.rust};
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
// bad trait object
|
||||
const F: &dyn Trait = unsafe { DynTransmute { bad: BadDynRepr { ptr: &92, vtable: 3 } }.rust};
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
|
||||
// bad data *inside* the trait object
|
||||
const G: &dyn Trait = &unsafe { BoolTransmute { val: 3 }.bl };
|
||||
// bad slice: length not an int
|
||||
const SLICE_LENGTH_PTR: &[u8] = unsafe { SliceTransmute { bad: BadSliceRepr { ptr: &42, len: &3 } }.slice};
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
|
||||
// bad data *inside* the slice
|
||||
|
@ -120,12 +123,34 @@ const I2: &MySliceBool = &MySlice(unsafe { BoolTransmute { val: 3 }.bl }, [false
|
|||
const I3: &MySliceBool = &MySlice(true, [unsafe { BoolTransmute { val: 3 }.bl }]);
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
|
||||
// invalid UTF-8
|
||||
const J1: &str = unsafe { SliceTransmute { slice: &[0xFF] }.str };
|
||||
// # raw slice
|
||||
const RAW_SLICE_VALID: *const [u8] = unsafe { SliceTransmute { repr: SliceRepr { ptr: &42, len: 1 } }.raw_slice}; // ok
|
||||
const RAW_SLICE_TOO_LONG: *const [u8] = unsafe { SliceTransmute { repr: SliceRepr { ptr: &42, len: 999 } }.raw_slice}; // ok because raw
|
||||
const RAW_SLICE_MUCH_TOO_LONG: *const [u8] = unsafe { SliceTransmute { repr: SliceRepr { ptr: &42, len: usize::max_value() } }.raw_slice}; // ok because raw
|
||||
const RAW_SLICE_LENGTH_UNINIT: *const [u8] = unsafe { SliceTransmute { addr: 42 }.raw_slice};
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
// invalid UTF-8 in user-defined str-like
|
||||
const J2: &MyStr = unsafe { SliceTransmute { slice: &[0xFF] }.my_str };
|
||||
|
||||
// # trait object
|
||||
// bad trait object
|
||||
const D: &dyn Trait = unsafe { DynTransmute { repr: DynRepr { ptr: &92, vtable: &3 } }.rust};
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
// bad trait object
|
||||
const E: &dyn Trait = unsafe { DynTransmute { repr2: DynRepr2 { ptr: &92, vtable: &3 } }.rust};
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
// bad trait object
|
||||
const F: &dyn Trait = unsafe { DynTransmute { bad: BadDynRepr { ptr: &92, vtable: 3 } }.rust};
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
|
||||
// bad data *inside* the trait object
|
||||
const G: &dyn Trait = &unsafe { BoolTransmute { val: 3 }.bl };
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
|
||||
// # raw trait object
|
||||
const RAW_TRAIT_OBJ_VTABLE_NULL: *const dyn Trait = unsafe { DynTransmute { bad: BadDynRepr { ptr: &92, vtable: 0 } }.rust};
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
const RAW_TRAIT_OBJ_VTABLE_INVALID: *const dyn Trait = unsafe { DynTransmute { repr2: DynRepr2 { ptr: &92, vtable: &3 } }.raw_rust};
|
||||
//~^ ERROR it is undefined behavior to use this value
|
||||
const RAW_TRAIT_OBJ_CONTENT_INVALID: *const dyn Trait = &unsafe { BoolTransmute { val: 3 }.bl } as *const _; // ok because raw
|
||||
|
||||
fn main() {
|
||||
}
|
|
@ -1,101 +1,29 @@
|
|||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/union-ub-fat-ptr.rs:78:1
|
||||
--> $DIR/ub-wide-ptr.rs:84:1
|
||||
|
|
||||
LL | const B: &str = unsafe { SliceTransmute { repr: SliceRepr { ptr: &42, len: 999 } }.str};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered dangling reference (not entirely in bounds)
|
||||
LL | const STR_TOO_LONG: &str = unsafe { SliceTransmute { repr: SliceRepr { ptr: &42, len: 999 } }.str};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered dangling reference (not entirely in bounds)
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/union-ub-fat-ptr.rs:81:1
|
||||
--> $DIR/ub-wide-ptr.rs:87:1
|
||||
|
|
||||
LL | const C: &str = unsafe { SliceTransmute { bad: BadSliceRepr { ptr: &42, len: &3 } }.str};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered non-integer slice length in fat pointer
|
||||
LL | const STR_LENGTH_PTR: &str = unsafe { SliceTransmute { bad: BadSliceRepr { ptr: &42, len: &3 } }.str};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered non-integer slice length in wide pointer
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/union-ub-fat-ptr.rs:84:1
|
||||
--> $DIR/ub-wide-ptr.rs:90:1
|
||||
|
|
||||
LL | const C2: &MyStr = unsafe { SliceTransmute { bad: BadSliceRepr { ptr: &42, len: &3 } }.my_str};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered non-integer slice length in fat pointer
|
||||
LL | const MY_STR_LENGTH_PTR: &MyStr = unsafe { SliceTransmute { bad: BadSliceRepr { ptr: &42, len: &3 } }.my_str};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered non-integer slice length in wide pointer
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/union-ub-fat-ptr.rs:90:1
|
||||
|
|
||||
LL | const B2: &[u8] = unsafe { SliceTransmute { repr: SliceRepr { ptr: &42, len: 999 } }.slice};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered dangling reference (not entirely in bounds)
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/union-ub-fat-ptr.rs:93:1
|
||||
|
|
||||
LL | const C3: &[u8] = unsafe { SliceTransmute { bad: BadSliceRepr { ptr: &42, len: &3 } }.slice};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered non-integer slice length in fat pointer
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/union-ub-fat-ptr.rs:97:1
|
||||
|
|
||||
LL | const D: &dyn Trait = unsafe { DynTransmute { repr: DynRepr { ptr: &92, vtable: &3 } }.rust};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered dangling or unaligned vtable pointer or too small vtable
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/union-ub-fat-ptr.rs:100:1
|
||||
|
|
||||
LL | const E: &dyn Trait = unsafe { DynTransmute { repr2: DynRepr2 { ptr: &92, vtable: &3 } }.rust};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered dangling or unaligned vtable pointer or too small vtable
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/union-ub-fat-ptr.rs:103:1
|
||||
|
|
||||
LL | const F: &dyn Trait = unsafe { DynTransmute { bad: BadDynRepr { ptr: &92, vtable: 3 } }.rust};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered dangling or unaligned vtable pointer or too small vtable
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/union-ub-fat-ptr.rs:107:1
|
||||
|
|
||||
LL | const G: &dyn Trait = &unsafe { BoolTransmute { val: 3 }.bl };
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered 3 at .<deref>.<dyn-downcast>, but expected something less or equal to 1
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/union-ub-fat-ptr.rs:111:1
|
||||
|
|
||||
LL | const H: &[bool] = &[unsafe { BoolTransmute { val: 3 }.bl }];
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered 3 at .<deref>[0], but expected something less or equal to 1
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/union-ub-fat-ptr.rs:117:1
|
||||
|
|
||||
LL | const I2: &MySliceBool = &MySlice(unsafe { BoolTransmute { val: 3 }.bl }, [false]);
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered 3 at .<deref>.0, but expected something less or equal to 1
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/union-ub-fat-ptr.rs:120:1
|
||||
|
|
||||
LL | const I3: &MySliceBool = &MySlice(true, [unsafe { BoolTransmute { val: 3 }.bl }]);
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered 3 at .<deref>.1[0], but expected something less or equal to 1
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/union-ub-fat-ptr.rs:124:1
|
||||
--> $DIR/ub-wide-ptr.rs:94:1
|
||||
|
|
||||
LL | const J1: &str = unsafe { SliceTransmute { slice: &[0xFF] }.str };
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered uninitialized or non-UTF-8 data in str at .<deref>
|
||||
|
@ -103,13 +31,117 @@ LL | const J1: &str = unsafe { SliceTransmute { slice: &[0xFF] }.str };
|
|||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/union-ub-fat-ptr.rs:127:1
|
||||
--> $DIR/ub-wide-ptr.rs:97:1
|
||||
|
|
||||
LL | const J2: &MyStr = unsafe { SliceTransmute { slice: &[0xFF] }.my_str };
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered uninitialized or non-UTF-8 data in str at .<deref>.0
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error: aborting due to 14 previous errors
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/ub-wide-ptr.rs:104:1
|
||||
|
|
||||
LL | const SLICE_LENGTH_UNINIT: &[u8] = unsafe { SliceTransmute { addr: 42 }.slice};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered uninitialized data in wide pointer metadata
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/ub-wide-ptr.rs:107:1
|
||||
|
|
||||
LL | const SLICE_TOO_LONG: &[u8] = unsafe { SliceTransmute { repr: SliceRepr { ptr: &42, len: 999 } }.slice};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered dangling reference (not entirely in bounds)
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/ub-wide-ptr.rs:110:1
|
||||
|
|
||||
LL | const SLICE_LENGTH_PTR: &[u8] = unsafe { SliceTransmute { bad: BadSliceRepr { ptr: &42, len: &3 } }.slice};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered non-integer slice length in wide pointer
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/ub-wide-ptr.rs:114:1
|
||||
|
|
||||
LL | const H: &[bool] = &[unsafe { BoolTransmute { val: 3 }.bl }];
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered 3 at .<deref>[0], but expected something less or equal to 1
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/ub-wide-ptr.rs:120:1
|
||||
|
|
||||
LL | const I2: &MySliceBool = &MySlice(unsafe { BoolTransmute { val: 3 }.bl }, [false]);
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered 3 at .<deref>.0, but expected something less or equal to 1
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/ub-wide-ptr.rs:123:1
|
||||
|
|
||||
LL | const I3: &MySliceBool = &MySlice(true, [unsafe { BoolTransmute { val: 3 }.bl }]);
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered 3 at .<deref>.1[0], but expected something less or equal to 1
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/ub-wide-ptr.rs:130:1
|
||||
|
|
||||
LL | const RAW_SLICE_LENGTH_UNINIT: *const [u8] = unsafe { SliceTransmute { addr: 42 }.raw_slice};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered uninitialized data in wide pointer metadata
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/ub-wide-ptr.rs:135:1
|
||||
|
|
||||
LL | const D: &dyn Trait = unsafe { DynTransmute { repr: DynRepr { ptr: &92, vtable: &3 } }.rust};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered dangling or unaligned vtable pointer in wide pointer or too small vtable
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/ub-wide-ptr.rs:138:1
|
||||
|
|
||||
LL | const E: &dyn Trait = unsafe { DynTransmute { repr2: DynRepr2 { ptr: &92, vtable: &3 } }.rust};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered dangling or unaligned vtable pointer in wide pointer or too small vtable
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/ub-wide-ptr.rs:141:1
|
||||
|
|
||||
LL | const F: &dyn Trait = unsafe { DynTransmute { bad: BadDynRepr { ptr: &92, vtable: 3 } }.rust};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered dangling or unaligned vtable pointer in wide pointer or too small vtable
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/ub-wide-ptr.rs:145:1
|
||||
|
|
||||
LL | const G: &dyn Trait = &unsafe { BoolTransmute { val: 3 }.bl };
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered 3 at .<deref>.<dyn-downcast>, but expected something less or equal to 1
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/ub-wide-ptr.rs:149:1
|
||||
|
|
||||
LL | const RAW_TRAIT_OBJ_VTABLE_NULL: *const dyn Trait = unsafe { DynTransmute { bad: BadDynRepr { ptr: &92, vtable: 0 } }.rust};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered dangling or unaligned vtable pointer in wide pointer or too small vtable
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error[E0080]: it is undefined behavior to use this value
|
||||
--> $DIR/ub-wide-ptr.rs:151:1
|
||||
|
|
||||
LL | const RAW_TRAIT_OBJ_VTABLE_INVALID: *const dyn Trait = unsafe { DynTransmute { repr2: DynRepr2 { ptr: &92, vtable: &3 } }.raw_rust};
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered dangling or unaligned vtable pointer in wide pointer or too small vtable
|
||||
|
|
||||
= note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rust compiler repository if you believe it should not be considered undefined behavior
|
||||
|
||||
error: aborting due to 18 previous errors
|
||||
|
||||
For more information about this error, try `rustc --explain E0080`.
|
|
@ -1,15 +1,3 @@
|
|||
error: cannot find derive macro `Send` in this scope
|
||||
--> $DIR/deriving-bounds.rs:1:10
|
||||
|
|
||||
LL | #[derive(Send)]
|
||||
| ^^^^
|
||||
|
|
||||
note: unsafe traits like `Send` should be implemented explicitly
|
||||
--> $DIR/deriving-bounds.rs:1:10
|
||||
|
|
||||
LL | #[derive(Send)]
|
||||
| ^^^^
|
||||
|
||||
error: cannot find derive macro `Sync` in this scope
|
||||
--> $DIR/deriving-bounds.rs:5:10
|
||||
|
|
||||
|
@ -22,5 +10,17 @@ note: unsafe traits like `Sync` should be implemented explicitly
|
|||
LL | #[derive(Sync)]
|
||||
| ^^^^
|
||||
|
||||
error: cannot find derive macro `Send` in this scope
|
||||
--> $DIR/deriving-bounds.rs:1:10
|
||||
|
|
||||
LL | #[derive(Send)]
|
||||
| ^^^^
|
||||
|
|
||||
note: unsafe traits like `Send` should be implemented explicitly
|
||||
--> $DIR/deriving-bounds.rs:1:10
|
||||
|
|
||||
LL | #[derive(Send)]
|
||||
| ^^^^
|
||||
|
||||
error: aborting due to 2 previous errors
|
||||
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
error: cannot find derive macro `x3300` in this scope
|
||||
--> $DIR/issue-43106-gating-of-derive-2.rs:4:14
|
||||
--> $DIR/issue-43106-gating-of-derive-2.rs:12:14
|
||||
|
|
||||
LL | #[derive(x3300)]
|
||||
| ^^^^^
|
||||
|
@ -11,7 +11,7 @@ LL | #[derive(x3300)]
|
|||
| ^^^^^
|
||||
|
||||
error: cannot find derive macro `x3300` in this scope
|
||||
--> $DIR/issue-43106-gating-of-derive-2.rs:12:14
|
||||
--> $DIR/issue-43106-gating-of-derive-2.rs:4:14
|
||||
|
|
||||
LL | #[derive(x3300)]
|
||||
| ^^^^^
|
||||
|
|
|
@ -1,9 +1,6 @@
|
|||
// `#![derive]` raises errors when it occurs at contexts other than ADT
|
||||
// definitions.
|
||||
|
||||
#![derive(Debug)]
|
||||
//~^ ERROR `derive` may only be applied to structs, enums and unions
|
||||
|
||||
#[derive(Debug)]
|
||||
//~^ ERROR `derive` may only be applied to structs, enums and unions
|
||||
mod derive {
|
||||
|
|
|
@ -1,38 +1,32 @@
|
|||
error: `derive` may only be applied to structs, enums and unions
|
||||
--> $DIR/issue-43106-gating-of-derive.rs:4:1
|
||||
|
|
||||
LL | #![derive(Debug)]
|
||||
| ^^^^^^^^^^^^^^^^^ help: try an outer attribute: `#[derive(Debug)]`
|
||||
|
||||
error: `derive` may only be applied to structs, enums and unions
|
||||
--> $DIR/issue-43106-gating-of-derive.rs:7:1
|
||||
|
|
||||
LL | #[derive(Debug)]
|
||||
| ^^^^^^^^^^^^^^^^
|
||||
|
||||
error: `derive` may only be applied to structs, enums and unions
|
||||
--> $DIR/issue-43106-gating-of-derive.rs:10:17
|
||||
--> $DIR/issue-43106-gating-of-derive.rs:7:17
|
||||
|
|
||||
LL | mod inner { #![derive(Debug)] }
|
||||
| ^^^^^^^^^^^^^^^^^ help: try an outer attribute: `#[derive(Debug)]`
|
||||
|
||||
error: `derive` may only be applied to structs, enums and unions
|
||||
--> $DIR/issue-43106-gating-of-derive.rs:13:5
|
||||
--> $DIR/issue-43106-gating-of-derive.rs:10:5
|
||||
|
|
||||
LL | #[derive(Debug)]
|
||||
| ^^^^^^^^^^^^^^^^
|
||||
|
||||
error: `derive` may only be applied to structs, enums and unions
|
||||
--> $DIR/issue-43106-gating-of-derive.rs:26:5
|
||||
--> $DIR/issue-43106-gating-of-derive.rs:23:5
|
||||
|
|
||||
LL | #[derive(Debug)]
|
||||
| ^^^^^^^^^^^^^^^^
|
||||
|
||||
error: `derive` may only be applied to structs, enums and unions
|
||||
--> $DIR/issue-43106-gating-of-derive.rs:30:5
|
||||
--> $DIR/issue-43106-gating-of-derive.rs:27:5
|
||||
|
|
||||
LL | #[derive(Debug)]
|
||||
| ^^^^^^^^^^^^^^^^
|
||||
|
||||
error: aborting due to 6 previous errors
|
||||
error: aborting due to 5 previous errors
|
||||
|
||||
|
|
|
@ -1,3 +1,4 @@
|
|||
#![derive(Copy)] //~ ERROR `derive` may only be applied to structs, enums and unions
|
||||
//~| ERROR cannot determine resolution for the derive macro `Copy`
|
||||
|
||||
fn main() {}
|
||||
|
|
|
@ -4,5 +4,13 @@ error: `derive` may only be applied to structs, enums and unions
|
|||
LL | #![derive(Copy)]
|
||||
| ^^^^^^^^^^^^^^^^ help: try an outer attribute: `#[derive(Copy)]`
|
||||
|
||||
error: aborting due to previous error
|
||||
error: cannot determine resolution for the derive macro `Copy`
|
||||
--> $DIR/issue-36617.rs:1:11
|
||||
|
|
||||
LL | #![derive(Copy)]
|
||||
| ^^^^
|
||||
|
|
||||
= note: import resolution is stuck, try simplifying macro imports
|
||||
|
||||
error: aborting due to 2 previous errors
|
||||
|
||||
|
|
18
src/test/ui/proc-macro/derive-helper-configured.rs
Normal file
18
src/test/ui/proc-macro/derive-helper-configured.rs
Normal file
|
@ -0,0 +1,18 @@
|
|||
// Derive helpers are resolved successfully inside `cfg_attr`.
|
||||
|
||||
// check-pass
|
||||
// compile-flats:--cfg TRUE
|
||||
// aux-build:test-macros.rs
|
||||
|
||||
#[macro_use]
|
||||
extern crate test_macros;
|
||||
|
||||
#[cfg_attr(TRUE, empty_helper)]
|
||||
#[derive(Empty)]
|
||||
#[cfg_attr(TRUE, empty_helper)]
|
||||
struct S {
|
||||
#[cfg_attr(TRUE, empty_helper)]
|
||||
field: u8,
|
||||
}
|
||||
|
||||
fn main() {}
|
|
@ -19,7 +19,8 @@ struct S {
|
|||
struct U;
|
||||
|
||||
mod inner {
|
||||
#[empty_helper] //~ ERROR cannot find attribute macro `empty_helper` in this scope
|
||||
// FIXME No ambiguity, attributes in non-macro positions are not resolved properly
|
||||
#[empty_helper]
|
||||
struct V;
|
||||
}
|
||||
|
||||
|
|
|
@ -1,9 +1,3 @@
|
|||
error: cannot find attribute macro `empty_helper` in this scope
|
||||
--> $DIR/derive-helper-shadowing.rs:22:15
|
||||
|
|
||||
LL | #[empty_helper]
|
||||
| ^^^^^^^^^^^^
|
||||
|
||||
error[E0659]: `empty_helper` is ambiguous (derive helper attribute vs any other name)
|
||||
--> $DIR/derive-helper-shadowing.rs:8:3
|
||||
|
|
||||
|
@ -22,6 +16,6 @@ LL | use test_macros::empty_attr as empty_helper;
|
|||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
= help: use `crate::empty_helper` to refer to this attribute macro unambiguously
|
||||
|
||||
error: aborting due to 2 previous errors
|
||||
error: aborting due to previous error
|
||||
|
||||
For more information about this error, try `rustc --explain E0659`.
|
||||
|
|
|
@ -1,50 +1,8 @@
|
|||
error: cannot find derive macro `FooWithLongNan` in this scope
|
||||
--> $DIR/resolve-error.rs:22:10
|
||||
error: cannot find macro `bang_proc_macrp!` in this scope
|
||||
--> $DIR/resolve-error.rs:56:5
|
||||
|
|
||||
LL | #[derive(FooWithLongNan)]
|
||||
| ^^^^^^^^^^^^^^ help: a derive macro with a similar name exists: `FooWithLongName`
|
||||
|
||||
error: cannot find attribute macro `attr_proc_macra` in this scope
|
||||
--> $DIR/resolve-error.rs:27:3
|
||||
|
|
||||
LL | #[attr_proc_macra]
|
||||
| ^^^^^^^^^^^^^^^ help: an attribute macro with a similar name exists: `attr_proc_macro`
|
||||
|
||||
error: cannot find attribute macro `FooWithLongNan` in this scope
|
||||
--> $DIR/resolve-error.rs:31:3
|
||||
|
|
||||
LL | #[FooWithLongNan]
|
||||
| ^^^^^^^^^^^^^^
|
||||
|
||||
error: cannot find derive macro `Dlone` in this scope
|
||||
--> $DIR/resolve-error.rs:34:10
|
||||
|
|
||||
LL | #[derive(Dlone)]
|
||||
| ^^^^^ help: a derive macro with a similar name exists: `Clone`
|
||||
|
||||
error: cannot find derive macro `Dlona` in this scope
|
||||
--> $DIR/resolve-error.rs:38:10
|
||||
|
|
||||
LL | #[derive(Dlona)]
|
||||
| ^^^^^ help: a derive macro with a similar name exists: `Clona`
|
||||
|
||||
error: cannot find derive macro `attr_proc_macra` in this scope
|
||||
--> $DIR/resolve-error.rs:42:10
|
||||
|
|
||||
LL | #[derive(attr_proc_macra)]
|
||||
| ^^^^^^^^^^^^^^^
|
||||
|
||||
error: cannot find macro `FooWithLongNama!` in this scope
|
||||
--> $DIR/resolve-error.rs:47:5
|
||||
|
|
||||
LL | FooWithLongNama!();
|
||||
| ^^^^^^^^^^^^^^^ help: a macro with a similar name exists: `FooWithLongNam`
|
||||
|
||||
error: cannot find macro `attr_proc_macra!` in this scope
|
||||
--> $DIR/resolve-error.rs:50:5
|
||||
|
|
||||
LL | attr_proc_macra!();
|
||||
| ^^^^^^^^^^^^^^^ help: a macro with a similar name exists: `attr_proc_mac`
|
||||
LL | bang_proc_macrp!();
|
||||
| ^^^^^^^^^^^^^^^ help: a macro with a similar name exists: `bang_proc_macro`
|
||||
|
||||
error: cannot find macro `Dlona!` in this scope
|
||||
--> $DIR/resolve-error.rs:53:5
|
||||
|
@ -52,11 +10,53 @@ error: cannot find macro `Dlona!` in this scope
|
|||
LL | Dlona!();
|
||||
| ^^^^^
|
||||
|
||||
error: cannot find macro `bang_proc_macrp!` in this scope
|
||||
--> $DIR/resolve-error.rs:56:5
|
||||
error: cannot find macro `attr_proc_macra!` in this scope
|
||||
--> $DIR/resolve-error.rs:50:5
|
||||
|
|
||||
LL | bang_proc_macrp!();
|
||||
| ^^^^^^^^^^^^^^^ help: a macro with a similar name exists: `bang_proc_macro`
|
||||
LL | attr_proc_macra!();
|
||||
| ^^^^^^^^^^^^^^^ help: a macro with a similar name exists: `attr_proc_mac`
|
||||
|
||||
error: cannot find macro `FooWithLongNama!` in this scope
|
||||
--> $DIR/resolve-error.rs:47:5
|
||||
|
|
||||
LL | FooWithLongNama!();
|
||||
| ^^^^^^^^^^^^^^^ help: a macro with a similar name exists: `FooWithLongNam`
|
||||
|
||||
error: cannot find derive macro `attr_proc_macra` in this scope
|
||||
--> $DIR/resolve-error.rs:42:10
|
||||
|
|
||||
LL | #[derive(attr_proc_macra)]
|
||||
| ^^^^^^^^^^^^^^^
|
||||
|
||||
error: cannot find derive macro `Dlona` in this scope
|
||||
--> $DIR/resolve-error.rs:38:10
|
||||
|
|
||||
LL | #[derive(Dlona)]
|
||||
| ^^^^^ help: a derive macro with a similar name exists: `Clona`
|
||||
|
||||
error: cannot find derive macro `Dlone` in this scope
|
||||
--> $DIR/resolve-error.rs:34:10
|
||||
|
|
||||
LL | #[derive(Dlone)]
|
||||
| ^^^^^ help: a derive macro with a similar name exists: `Clone`
|
||||
|
||||
error: cannot find attribute macro `FooWithLongNan` in this scope
|
||||
--> $DIR/resolve-error.rs:31:3
|
||||
|
|
||||
LL | #[FooWithLongNan]
|
||||
| ^^^^^^^^^^^^^^
|
||||
|
||||
error: cannot find attribute macro `attr_proc_macra` in this scope
|
||||
--> $DIR/resolve-error.rs:27:3
|
||||
|
|
||||
LL | #[attr_proc_macra]
|
||||
| ^^^^^^^^^^^^^^^ help: an attribute macro with a similar name exists: `attr_proc_macro`
|
||||
|
||||
error: cannot find derive macro `FooWithLongNan` in this scope
|
||||
--> $DIR/resolve-error.rs:22:10
|
||||
|
|
||||
LL | #[derive(FooWithLongNan)]
|
||||
| ^^^^^^^^^^^^^^ help: a derive macro with a similar name exists: `FooWithLongName`
|
||||
|
||||
error: aborting due to 10 previous errors
|
||||
|
||||
|
|
|
@ -1 +1 @@
|
|||
Subproject commit 85958b001dbff8523396809bfa844fc34a7869a8
|
||||
Subproject commit 9f66c14c3f91a48a118c7817f434167b311c3515
|
Loading…
Add table
Reference in a new issue