mirror of
https://github.com/rust-lang/rust.git
synced 2024-11-22 23:04:33 +00:00
Address attribute naming and use Bound
enum
This commit is contained in:
parent
a2c924b5ae
commit
833dc7e682
@ -15,7 +15,7 @@ use ops::CoerceUnsized;
|
||||
/// A wrapper type for raw pointers and integers that will never be
|
||||
/// NULL or 0 that might allow certain optimizations.
|
||||
#[cfg_attr(stage0, lang = "non_zero")]
|
||||
#[cfg_attr(not(stage0), rustc_layout_scalar_range_start(1))]
|
||||
#[cfg_attr(not(stage0), rustc_layout_scalar_valid_range_start(1))]
|
||||
#[derive(Copy, Clone, Eq, PartialEq, Ord, PartialOrd, Hash)]
|
||||
#[repr(transparent)]
|
||||
pub(crate) struct NonZero<T>(pub(crate) T);
|
||||
|
@ -66,7 +66,7 @@ use std::collections::hash_map::{self, Entry};
|
||||
use std::hash::{Hash, Hasher};
|
||||
use std::fmt;
|
||||
use std::mem;
|
||||
use std::ops::Deref;
|
||||
use std::ops::{Deref, Bound};
|
||||
use std::iter;
|
||||
use std::sync::mpsc;
|
||||
use std::sync::Arc;
|
||||
@ -1083,27 +1083,24 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> {
|
||||
interned
|
||||
}
|
||||
|
||||
/// Returns a range of the start/end indices specified with the `rustc_layout_scalar_range`
|
||||
/// attribute. Missing range ends may be denoted by `None` and will just use the max/min of
|
||||
/// the type.
|
||||
pub fn layout_scalar_range(self, def_id: DefId) -> Option<(Option<u128>, Option<u128>)> {
|
||||
/// Returns a range of the start/end indices specified with the
|
||||
/// `rustc_layout_scalar_valid_range` attribute.
|
||||
pub fn layout_scalar_valid_range(self, def_id: DefId) -> (Bound<u128>, Bound<u128>) {
|
||||
let attrs = self.get_attrs(def_id);
|
||||
let get = |name| -> Option<u128> {
|
||||
let attr = attrs.iter().find(|a| a.check_name(name))?;
|
||||
for meta in attr.meta_item_list().expect("rustc_layout_scalar_range takes args") {
|
||||
match meta.literal().expect("rustc_layout_scalar_range attribute takes lit").node {
|
||||
ast::LitKind::Int(a, _) => return Some(a),
|
||||
_ => span_bug!(attr.span, "rustc_layout_scalar_range expects integer arg"),
|
||||
let get = |name| {
|
||||
let attr = match attrs.iter().find(|a| a.check_name(name)) {
|
||||
Some(attr) => attr,
|
||||
None => return Bound::Unbounded,
|
||||
};
|
||||
for meta in attr.meta_item_list().expect("rustc_layout_scalar_valid_range takes args") {
|
||||
match meta.literal().expect("attribute takes lit").node {
|
||||
ast::LitKind::Int(a, _) => return Bound::Included(a),
|
||||
_ => span_bug!(attr.span, "rustc_layout_scalar_valid_range expects int arg"),
|
||||
}
|
||||
}
|
||||
bug!("no arguments to `rustc_layout_scalar_range` attribute");
|
||||
span_bug!(attr.span, "no arguments to `rustc_layout_scalar_valid_range` attribute");
|
||||
};
|
||||
let start = get("rustc_layout_scalar_range_start");
|
||||
let end = get("rustc_layout_scalar_range_end");
|
||||
if start.is_none() && end.is_none() {
|
||||
return None;
|
||||
}
|
||||
Some((start, end))
|
||||
(get("rustc_layout_scalar_valid_range_start"), get("rustc_layout_scalar_valid_range_end"))
|
||||
}
|
||||
|
||||
pub fn lift<T: ?Sized + Lift<'tcx>>(self, value: &T) -> Option<T::Lifted> {
|
||||
|
@ -20,6 +20,7 @@ use std::fmt;
|
||||
use std::i128;
|
||||
use std::iter;
|
||||
use std::mem;
|
||||
use std::ops::Bound;
|
||||
|
||||
use ich::StableHashingContext;
|
||||
use rustc_data_structures::stable_hasher::{HashStable, StableHasher,
|
||||
@ -761,20 +762,28 @@ impl<'a, 'tcx> LayoutCx<'tcx, TyCtxt<'a, 'tcx, 'tcx>> {
|
||||
|
||||
let mut st = univariant_uninterned(&variants[v], &def.repr, kind)?;
|
||||
st.variants = Variants::Single { index: v };
|
||||
if let Some((start, end)) = self.tcx.layout_scalar_range(def.did) {
|
||||
match st.abi {
|
||||
Abi::Scalar(ref mut scalar) |
|
||||
Abi::ScalarPair(ref mut scalar, _) => {
|
||||
let start = start.unwrap_or(*scalar.valid_range.start());
|
||||
let end = end.unwrap_or(*scalar.valid_range.end());
|
||||
scalar.valid_range = start..=end;
|
||||
let (start, end) = self.tcx.layout_scalar_valid_range(def.did);
|
||||
match st.abi {
|
||||
Abi::Scalar(ref mut scalar) |
|
||||
Abi::ScalarPair(ref mut scalar, _) => {
|
||||
// the asserts ensure that we are not using the
|
||||
// `#[rustc_layout_scalar_valid_range(n)]`
|
||||
// attribute to widen the range of anything as that would probably
|
||||
// result in UB somewhere
|
||||
if let Bound::Included(start) = start {
|
||||
assert!(*scalar.valid_range.start() <= start);
|
||||
scalar.valid_range = start..=*scalar.valid_range.end();
|
||||
}
|
||||
if let Bound::Included(end) = end {
|
||||
assert!(*scalar.valid_range.end() >= end);
|
||||
scalar.valid_range = *scalar.valid_range.start()..=end;
|
||||
}
|
||||
_ => bug!(
|
||||
"nonscalar layout for rustc_layout_scalar_range type {:?}: {:#?}",
|
||||
def,
|
||||
st,
|
||||
),
|
||||
}
|
||||
_ => bug!(
|
||||
"nonscalar layout for layout_scalar_valid_range type {:?}: {:#?}",
|
||||
def,
|
||||
st,
|
||||
),
|
||||
}
|
||||
return Ok(tcx.intern_layout(st));
|
||||
}
|
||||
@ -1353,13 +1362,12 @@ impl<'a, 'tcx> SizeSkeleton<'tcx> {
|
||||
if def.variants.len() == 1 {
|
||||
if let Some(SizeSkeleton::Pointer { non_zero, tail }) = v0 {
|
||||
return Ok(SizeSkeleton::Pointer {
|
||||
non_zero: non_zero ||
|
||||
tcx.layout_scalar_range(def.did).map_or(false, |(start, end)| {
|
||||
// `n..` for `n > 0` or `n..m` for `n > 0 && m > n`
|
||||
start.map_or(true, |start| start > 0 && end.map_or(true, |end| {
|
||||
end > start
|
||||
}))
|
||||
}),
|
||||
non_zero: non_zero || match tcx.layout_scalar_valid_range(def.did) {
|
||||
(Bound::Included(start), Bound::Unbounded) => start > 0,
|
||||
(Bound::Included(start), Bound::Included(end)) =>
|
||||
0 < start && start < end,
|
||||
_ => false,
|
||||
},
|
||||
tail,
|
||||
});
|
||||
} else {
|
||||
|
@ -97,7 +97,7 @@ macro_rules! newtype_index {
|
||||
@vis [$v:vis]
|
||||
@debug_format [$debug_format:tt]) => (
|
||||
#[derive(Copy, Clone, PartialEq, Eq, Hash, PartialOrd, Ord, $($derives),*)]
|
||||
#[rustc_layout_scalar_range_end($max)]
|
||||
#[rustc_layout_scalar_valid_range_end($max)]
|
||||
$v struct $type {
|
||||
private: u32
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user