Skip to content

Commit 46a3ce3

Browse files
authored
Rollup merge of rust-lang#83054 - tmiasko:rustc_layout_scalar_valid_range, r=davidtwco
Validate rustc_layout_scalar_valid_range_{start,end} attributes Fixes rust-lang#82251, fixes rust-lang#82981.
2 parents 3bf9af2 + 4943190 commit 46a3ce3

File tree

4 files changed

+91
-1
lines changed

4 files changed

+91
-1
lines changed

compiler/rustc_ast/src/attr/mod.rs

+1
Original file line numberDiff line numberDiff line change
@@ -120,6 +120,7 @@ impl NestedMetaItem {
120120
}
121121

122122
impl Attribute {
123+
#[inline]
123124
pub fn has_name(&self, name: Symbol) -> bool {
124125
match self.kind {
125126
AttrKind::Normal(ref item, _) => item.path == name,

compiler/rustc_passes/src/check_attr.rs

+36-1
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ use rustc_middle::hir::map::Map;
88
use rustc_middle::ty::query::Providers;
99
use rustc_middle::ty::TyCtxt;
1010

11-
use rustc_ast::{Attribute, LitKind, NestedMetaItem};
11+
use rustc_ast::{Attribute, Lit, LitKind, NestedMetaItem};
1212
use rustc_errors::{pluralize, struct_span_err};
1313
use rustc_hir as hir;
1414
use rustc_hir::def_id::LocalDefId;
@@ -87,6 +87,10 @@ impl CheckAttrVisitor<'tcx> {
8787
self.check_export_name(hir_id, &attr, span, target)
8888
} else if self.tcx.sess.check_name(attr, sym::rustc_args_required_const) {
8989
self.check_rustc_args_required_const(&attr, span, target, item)
90+
} else if self.tcx.sess.check_name(attr, sym::rustc_layout_scalar_valid_range_start) {
91+
self.check_rustc_layout_scalar_valid_range(&attr, span, target)
92+
} else if self.tcx.sess.check_name(attr, sym::rustc_layout_scalar_valid_range_end) {
93+
self.check_rustc_layout_scalar_valid_range(&attr, span, target)
9094
} else if self.tcx.sess.check_name(attr, sym::allow_internal_unstable) {
9195
self.check_allow_internal_unstable(hir_id, &attr, span, target, &attrs)
9296
} else if self.tcx.sess.check_name(attr, sym::rustc_allow_const_fn_unstable) {
@@ -807,6 +811,37 @@ impl CheckAttrVisitor<'tcx> {
807811
}
808812
}
809813

814+
fn check_rustc_layout_scalar_valid_range(
815+
&self,
816+
attr: &Attribute,
817+
span: &Span,
818+
target: Target,
819+
) -> bool {
820+
if target != Target::Struct {
821+
self.tcx
822+
.sess
823+
.struct_span_err(attr.span, "attribute should be applied to a struct")
824+
.span_label(*span, "not a struct")
825+
.emit();
826+
return false;
827+
}
828+
829+
let list = match attr.meta_item_list() {
830+
None => return false,
831+
Some(it) => it,
832+
};
833+
834+
if matches!(&list[..], &[NestedMetaItem::Literal(Lit { kind: LitKind::Int(..), .. })]) {
835+
true
836+
} else {
837+
self.tcx
838+
.sess
839+
.struct_span_err(attr.span, "expected exactly one integer literal argument")
840+
.emit();
841+
false
842+
}
843+
}
844+
810845
/// Checks if `#[rustc_legacy_const_generics]` is applied to a function and has a valid argument.
811846
fn check_rustc_legacy_const_generics(
812847
&self,
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
#![feature(rustc_attrs)]
2+
3+
#[rustc_layout_scalar_valid_range_start(u32::MAX)] //~ ERROR
4+
pub struct A(u32);
5+
6+
#[rustc_layout_scalar_valid_range_end(1, 2)] //~ ERROR
7+
pub struct B(u8);
8+
9+
#[rustc_layout_scalar_valid_range_end(a = "a")] //~ ERROR
10+
pub struct C(i32);
11+
12+
#[rustc_layout_scalar_valid_range_end(1)] //~ ERROR
13+
enum E {
14+
X = 1,
15+
Y = 14,
16+
}
17+
18+
fn main() {
19+
let _ = A(0);
20+
let _ = B(0);
21+
let _ = C(0);
22+
let _ = E::X;
23+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
error: expected exactly one integer literal argument
2+
--> $DIR/invalid_rustc_layout_scalar_valid_range.rs:3:1
3+
|
4+
LL | #[rustc_layout_scalar_valid_range_start(u32::MAX)]
5+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
6+
7+
error: expected exactly one integer literal argument
8+
--> $DIR/invalid_rustc_layout_scalar_valid_range.rs:6:1
9+
|
10+
LL | #[rustc_layout_scalar_valid_range_end(1, 2)]
11+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
12+
13+
error: expected exactly one integer literal argument
14+
--> $DIR/invalid_rustc_layout_scalar_valid_range.rs:9:1
15+
|
16+
LL | #[rustc_layout_scalar_valid_range_end(a = "a")]
17+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
18+
19+
error: attribute should be applied to a struct
20+
--> $DIR/invalid_rustc_layout_scalar_valid_range.rs:12:1
21+
|
22+
LL | #[rustc_layout_scalar_valid_range_end(1)]
23+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
24+
LL | / enum E {
25+
LL | | X = 1,
26+
LL | | Y = 14,
27+
LL | | }
28+
| |_- not a struct
29+
30+
error: aborting due to 4 previous errors
31+

0 commit comments

Comments
 (0)