Skip to content

Commit 438826f

Browse files
committed
add more tests and make used(linker/compiler) mutually exclusive
1 parent e075586 commit 438826f

File tree

7 files changed

+88
-4
lines changed

7 files changed

+88
-4
lines changed

compiler/rustc_passes/src/check_attr.rs

+34
Original file line numberDiff line numberDiff line change
@@ -1741,12 +1741,46 @@ impl CheckAttrVisitor<'_> {
17411741
}
17421742

17431743
fn check_used(&self, attrs: &[Attribute], target: Target) {
1744+
let mut used_linker_span = None;
1745+
let mut used_compiler_span = None;
17441746
for attr in attrs {
17451747
if attr.has_name(sym::used) && target != Target::Static {
17461748
self.tcx
17471749
.sess
17481750
.span_err(attr.span, "attribute must be applied to a `static` variable");
17491751
}
1752+
let inner = attr.meta_item_list();
1753+
match inner.as_deref() {
1754+
Some([item]) if item.has_name(sym::linker) => {
1755+
if used_linker_span.is_none() {
1756+
used_linker_span = Some(attr.span);
1757+
}
1758+
}
1759+
Some([item]) if item.has_name(sym::compiler) => {
1760+
if used_compiler_span.is_none() {
1761+
used_compiler_span = Some(attr.span);
1762+
}
1763+
}
1764+
Some(_) => {
1765+
// This error case is handled in rustc_typeck::collect.
1766+
}
1767+
None => {
1768+
// Default case (compiler) when arg isn't defined.
1769+
if used_compiler_span.is_none() {
1770+
used_compiler_span = Some(attr.span);
1771+
}
1772+
}
1773+
}
1774+
}
1775+
if let (Some(linker_span), Some(compiler_span)) = (used_linker_span, used_compiler_span) {
1776+
let spans = vec![linker_span, compiler_span];
1777+
self.tcx
1778+
.sess
1779+
.struct_span_err(
1780+
spans,
1781+
"`used(compiler)` and `used(linker)` can't be used together",
1782+
)
1783+
.emit();
17501784
}
17511785
}
17521786

compiler/rustc_typeck/src/collect.rs

+1
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
// ignore-tidy-filelength
12
//! "Collection" is the process of determining the type and other external
23
//! details of each item in Rust. Collection is specifically concerned
34
//! with *inter-procedural* things -- for example, for a function

src/test/codegen/used_with_arg.rs

+2-4
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,10 @@
1-
// compile-flags: -O
2-
31
#![crate_type = "lib"]
42
#![feature(used_with_arg)]
53

6-
// CHECK: @llvm.used = appending global [1 x i8*]
4+
// CHECK: @llvm.used = appending global [1 x i8*]{{.*}}USED_LINKER
75
#[used(linker)]
86
static mut USED_LINKER: [usize; 1] = [0];
97

10-
// CHECK-NEXT: @llvm.compiler.used = appending global [1 x i8*]
8+
// CHECK-NEXT: @llvm.compiler.used = appending global [1 x i8*]{{.*}}USED_COMPILER
119
#[used(compiler)]
1210
static mut USED_COMPILER: [usize; 1] = [0];

src/test/ui/used_with_arg.rs

+19
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
#![feature(used_with_arg)]
2+
3+
#[used(linker)]
4+
static mut USED_LINKER: [usize; 1] = [0];
5+
6+
#[used(compiler)]
7+
static mut USED_COMPILER: [usize; 1] = [0];
8+
9+
#[used(compiler)] //~ ERROR `used(compiler)` and `used(linker)` can't be used together
10+
#[used(linker)]
11+
static mut USED_COMPILER_LINKER2: [usize; 1] = [0];
12+
13+
#[used(compiler)] //~ ERROR `used(compiler)` and `used(linker)` can't be used together
14+
#[used(linker)]
15+
#[used(compiler)]
16+
#[used(linker)]
17+
static mut USED_COMPILER_LINKER3: [usize; 1] = [0];
18+
19+
fn main() {}

src/test/ui/used_with_arg.stderr

+18
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
error: `used(compiler)` and `used(linker)` can't be used together
2+
--> $DIR/used_with_arg.rs:9:1
3+
|
4+
LL | #[used(compiler)]
5+
| ^^^^^^^^^^^^^^^^^
6+
LL | #[used(linker)]
7+
| ^^^^^^^^^^^^^^^
8+
9+
error: `used(compiler)` and `used(linker)` can't be used together
10+
--> $DIR/used_with_arg.rs:13:1
11+
|
12+
LL | #[used(compiler)]
13+
| ^^^^^^^^^^^^^^^^^
14+
LL | #[used(linker)]
15+
| ^^^^^^^^^^^^^^^
16+
17+
error: aborting due to 2 previous errors
18+

src/test/ui/used_with_multi_args.rs

+6
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
#![feature(used_with_arg)]
2+
3+
#[used(compiler, linker)] //~ expected `used`, `used(compiler)` or `used(linker)`
4+
static mut USED_COMPILER_LINKER: [usize; 1] = [0];
5+
6+
fn main() {}
+8
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
error: expected `used`, `used(compiler)` or `used(linker)`
2+
--> $DIR/used_with_multi_args.rs:3:1
3+
|
4+
LL | #[used(compiler, linker)]
5+
| ^^^^^^^^^^^^^^^^^^^^^^^^^
6+
7+
error: aborting due to previous error
8+

0 commit comments

Comments
 (0)