diff --git a/src/librustc/error_codes.rs b/src/librustc/error_codes.rs index cf268078a2c5d..3e35add9616bd 100644 --- a/src/librustc/error_codes.rs +++ b/src/librustc/error_codes.rs @@ -2219,7 +2219,7 @@ rejected in your own crates. "##, E0736: r##" -#[track_caller] and #[naked] cannot be applied to the same function. +`#[track_caller]` and `#[naked]` cannot both be applied to the same function. Erroneous code example: @@ -2237,6 +2237,57 @@ See [RFC 2091] for details on this and other limitations. [RFC 2091]: https://github.com/rust-lang/rfcs/blob/master/text/2091-inline-semantic.md "##, +E0738: r##" +`#[track_caller]` cannot be used in traits yet. This is due to limitations in +the compiler which are likely to be temporary. See [RFC 2091] for details on +this and other restrictions. + +Erroneous example with a trait method implementation: + +```compile_fail,E0738 +#![feature(track_caller)] + +trait Foo { + fn bar(&self); +} + +impl Foo for u64 { + #[track_caller] + fn bar(&self) {} +} +``` + +Erroneous example with a blanket trait method implementation: + +```compile_fail,E0738 +#![feature(track_caller)] + +trait Foo { + #[track_caller] + fn bar(&self) {} + fn baz(&self); +} +``` + +Erroneous example with a trait method declaration: + +```compile_fail,E0738 +#![feature(track_caller)] + +trait Foo { + fn bar(&self) {} + + #[track_caller] + fn baz(&self); +} +``` + +Note that while the compiler may be able to support the attribute in traits in +the future, [RFC 2091] prohibits their implementation without a follow-up RFC. + +[RFC 2091]: https://github.com/rust-lang/rfcs/blob/master/text/2091-inline-semantic.md +"##, + ; // E0006, // merged with E0005 // E0101, // replaced with E0282 diff --git a/src/librustc/hir/check_attr.rs b/src/librustc/hir/check_attr.rs index a175bcafdc4a4..55ac95f4ac4b7 100644 --- a/src/librustc/hir/check_attr.rs +++ b/src/librustc/hir/check_attr.rs @@ -206,27 +206,37 @@ impl CheckAttrVisitor<'tcx> { span: &Span, target: Target, ) -> bool { - if target != Target::Fn { - struct_span_err!( - self.tcx.sess, - *attr_span, - E0739, - "attribute should be applied to function" - ) - .span_label(*span, "not a function") - .emit(); - false - } else if attr::contains_name(attrs, sym::naked) { - struct_span_err!( - self.tcx.sess, - *attr_span, - E0736, - "cannot use `#[track_caller]` with `#[naked]`", - ) - .emit(); - false - } else { - true + match target { + Target::Fn if attr::contains_name(attrs, sym::naked) => { + struct_span_err!( + self.tcx.sess, + *attr_span, + E0736, + "cannot use `#[track_caller]` with `#[naked]`", + ).emit(); + false + } + Target::Fn => true, + Target::Method { .. } => { + struct_span_err!( + self.tcx.sess, + *attr_span, + E0738, + "`#[track_caller]` may not be used on trait methods", + ).emit(); + false + } + _ => { + struct_span_err!( + self.tcx.sess, + *attr_span, + E0739, + "attribute should be applied to function" + ) + .span_label(*span, "not a function") + .emit(); + false + } } } diff --git a/src/librustc/hir/mod.rs b/src/librustc/hir/mod.rs index 19959c11d0950..0edc41e6b4881 100644 --- a/src/librustc/hir/mod.rs +++ b/src/librustc/hir/mod.rs @@ -2756,10 +2756,10 @@ bitflags! { /// `#[used]`: indicates that LLVM can't eliminate this function (but the /// linker can!). const USED = 1 << 9; - /// #[ffi_returns_twice], indicates that an extern function can return + /// `#[ffi_returns_twice]`, indicates that an extern function can return /// multiple times const FFI_RETURNS_TWICE = 1 << 10; - /// #[track_caller]: allow access to the caller location + /// `#[track_caller]`: allow access to the caller location const TRACK_CALLER = 1 << 11; } } diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index 18b103960c745..905655176d1e7 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -172,18 +172,6 @@ pub fn check_trait_item(tcx: TyCtxt<'_>, def_id: DefId) { _ => None }; check_associated_item(tcx, trait_item.hir_id, trait_item.span, method_sig); - - // Prohibits applying `#[track_caller]` to trait decls - for attr in &trait_item.attrs { - if attr.check_name(sym::track_caller) { - struct_span_err!( - tcx.sess, - attr.span, - E0738, - "`#[track_caller]` is not supported in trait declarations." - ).emit(); - } - } } pub fn check_impl_item(tcx: TyCtxt<'_>, def_id: DefId) { @@ -195,29 +183,6 @@ pub fn check_impl_item(tcx: TyCtxt<'_>, def_id: DefId) { _ => None }; - // Prohibits applying `#[track_caller]` to trait impls - if method_sig.is_some() { - let track_caller_attr = impl_item.attrs.iter() - .find(|a| a.check_name(sym::track_caller)); - if let Some(tc_attr) = track_caller_attr { - let parent_hir_id = tcx.hir().get_parent_item(hir_id); - let containing_item = tcx.hir().expect_item(parent_hir_id); - let containing_impl_is_for_trait = match &containing_item.kind { - hir::ItemKind::Impl(_, _, _, _, tr, _, _) => tr.is_some(), - _ => bug!("parent of an ImplItem must be an Impl"), - }; - - if containing_impl_is_for_trait { - struct_span_err!( - tcx.sess, - tc_attr.span, - E0738, - "`#[track_caller]` is not supported in traits yet." - ).emit(); - } - } - } - check_associated_item(tcx, impl_item.hir_id, impl_item.span, method_sig); } diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index 00435d67184a3..026a3d0122d19 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -2640,7 +2640,7 @@ fn codegen_fn_attrs(tcx: TyCtxt<'_>, id: DefId) -> CodegenFnAttrs { tcx.sess, attr.span, E0737, - "rust ABI is required to use `#[track_caller]`" + "Rust ABI is required to use `#[track_caller]`" ).emit(); } codegen_fn_attrs.flags |= CodegenFnAttrFlags::TRACK_CALLER; diff --git a/src/librustc_typeck/error_codes.rs b/src/librustc_typeck/error_codes.rs index 75b508a1bbf0f..8990ee2eaccc6 100644 --- a/src/librustc_typeck/error_codes.rs +++ b/src/librustc_typeck/error_codes.rs @@ -4938,7 +4938,7 @@ and the pin is required to keep it in the same place in memory. "##, E0737: r##" -#[track_caller] requires functions to have the "Rust" ABI for implicitly +`#[track_caller]` requires functions to have the `"Rust"` ABI for implicitly receiving caller location. See [RFC 2091] for details on this and other restrictions. @@ -4954,57 +4954,6 @@ extern "C" fn foo() {} [RFC 2091]: https://github.com/rust-lang/rfcs/blob/master/text/2091-inline-semantic.md "##, -E0738: r##" -#[track_caller] cannot be used in traits yet. This is due to limitations in the -compiler which are likely to be temporary. See [RFC 2091] for details on this -and other restrictions. - -Erroneous example with a trait method implementation: - -```compile_fail,E0738 -#![feature(track_caller)] - -trait Foo { - fn bar(&self); -} - -impl Foo for u64 { - #[track_caller] - fn bar(&self) {} -} -``` - -Erroneous example with a blanket trait method implementation: - -```compile_fail,E0738 -#![feature(track_caller)] - -trait Foo { - #[track_caller] - fn bar(&self) {} - fn baz(&self); -} -``` - -Erroneous example with a trait method declaration: - -```compile_fail,E0738 -#![feature(track_caller)] - -trait Foo { - fn bar(&self) {} - - #[track_caller] - fn baz(&self); -} -``` - -Note that while the compiler may be able to support the attribute in traits in -the future, [RFC 2091] prohibits their implementation without a follow-up RFC. - -[RFC 2091]: https://github.com/rust-lang/rfcs/blob/master/text/2091-inline-semantic.md -"##, - E0741: r##" Only `structural_match` types (that is, types that derive `PartialEq` and `Eq`) may be used as the types of const generic parameters. diff --git a/src/test/ui/rfc-2091-track-caller/error-with-invalid-abi.rs b/src/test/ui/rfc-2091-track-caller/error-with-invalid-abi.rs index 2994f3c06212f..162c6387088e7 100644 --- a/src/test/ui/rfc-2091-track-caller/error-with-invalid-abi.rs +++ b/src/test/ui/rfc-2091-track-caller/error-with-invalid-abi.rs @@ -1,7 +1,6 @@ #![feature(track_caller)] //~ WARN the feature `track_caller` is incomplete -#[track_caller] +#[track_caller] //~ ERROR Rust ABI is required to use `#[track_caller]` extern "C" fn f() {} -//~^^ ERROR rust ABI is required to use `#[track_caller]` fn main() {} diff --git a/src/test/ui/rfc-2091-track-caller/error-with-invalid-abi.stderr b/src/test/ui/rfc-2091-track-caller/error-with-invalid-abi.stderr index a34acf3fc6142..ad89b142f0ec8 100644 --- a/src/test/ui/rfc-2091-track-caller/error-with-invalid-abi.stderr +++ b/src/test/ui/rfc-2091-track-caller/error-with-invalid-abi.stderr @@ -6,7 +6,7 @@ LL | #![feature(track_caller)] | = note: `#[warn(incomplete_features)]` on by default -error[E0737]: rust ABI is required to use `#[track_caller]` +error[E0737]: Rust ABI is required to use `#[track_caller]` --> $DIR/error-with-invalid-abi.rs:3:1 | LL | #[track_caller] diff --git a/src/test/ui/rfc-2091-track-caller/error-with-trait-decl.rs b/src/test/ui/rfc-2091-track-caller/error-with-trait-decl.rs index 1cd45c8cdbc91..4fd768d640a55 100644 --- a/src/test/ui/rfc-2091-track-caller/error-with-trait-decl.rs +++ b/src/test/ui/rfc-2091-track-caller/error-with-trait-decl.rs @@ -1,9 +1,8 @@ #![feature(track_caller)] //~ WARN the feature `track_caller` is incomplete trait Trait { - #[track_caller] + #[track_caller] //~ ERROR: `#[track_caller]` may not be used on trait methods fn unwrap(&self); - //~^^ ERROR: `#[track_caller]` is not supported in trait declarations. } impl Trait for u64 { diff --git a/src/test/ui/rfc-2091-track-caller/error-with-trait-decl.stderr b/src/test/ui/rfc-2091-track-caller/error-with-trait-decl.stderr index fb3732b597083..72ed6f89faa96 100644 --- a/src/test/ui/rfc-2091-track-caller/error-with-trait-decl.stderr +++ b/src/test/ui/rfc-2091-track-caller/error-with-trait-decl.stderr @@ -6,7 +6,7 @@ LL | #![feature(track_caller)] | = note: `#[warn(incomplete_features)]` on by default -error[E0738]: `#[track_caller]` is not supported in trait declarations. +error[E0738]: `#[track_caller]` may not be used on trait methods --> $DIR/error-with-trait-decl.rs:4:5 | LL | #[track_caller] diff --git a/src/test/ui/rfc-2091-track-caller/error-with-trait-default-impl.rs b/src/test/ui/rfc-2091-track-caller/error-with-trait-default-impl.rs index 0f2020d6fb26b..2139ba5de10c3 100644 --- a/src/test/ui/rfc-2091-track-caller/error-with-trait-default-impl.rs +++ b/src/test/ui/rfc-2091-track-caller/error-with-trait-default-impl.rs @@ -1,9 +1,8 @@ #![feature(track_caller)] //~ WARN the feature `track_caller` is incomplete trait Trait { - #[track_caller] + #[track_caller] //~ ERROR: `#[track_caller]` may not be used on trait methods fn unwrap(&self) {} - //~^^ ERROR: `#[track_caller]` is not supported in trait declarations. } fn main() {} diff --git a/src/test/ui/rfc-2091-track-caller/error-with-trait-default-impl.stderr b/src/test/ui/rfc-2091-track-caller/error-with-trait-default-impl.stderr index c212a716c2024..05689c9468bec 100644 --- a/src/test/ui/rfc-2091-track-caller/error-with-trait-default-impl.stderr +++ b/src/test/ui/rfc-2091-track-caller/error-with-trait-default-impl.stderr @@ -6,7 +6,7 @@ LL | #![feature(track_caller)] | = note: `#[warn(incomplete_features)]` on by default -error[E0738]: `#[track_caller]` is not supported in trait declarations. +error[E0738]: `#[track_caller]` may not be used on trait methods --> $DIR/error-with-trait-default-impl.rs:4:5 | LL | #[track_caller] diff --git a/src/test/ui/rfc-2091-track-caller/error-with-trait-fn-impl.rs b/src/test/ui/rfc-2091-track-caller/error-with-trait-fn-impl.rs index 1378ebaa03ffa..9b97df2e4eb33 100644 --- a/src/test/ui/rfc-2091-track-caller/error-with-trait-fn-impl.rs +++ b/src/test/ui/rfc-2091-track-caller/error-with-trait-fn-impl.rs @@ -5,9 +5,8 @@ trait Trait { } impl Trait for u64 { - #[track_caller] + #[track_caller] //~ ERROR: `#[track_caller]` may not be used on trait methods fn unwrap(&self) {} - //~^^ ERROR: `#[track_caller]` is not supported in traits yet. } fn main() {} diff --git a/src/test/ui/rfc-2091-track-caller/error-with-trait-fn-impl.stderr b/src/test/ui/rfc-2091-track-caller/error-with-trait-fn-impl.stderr index 2662fbff7a2c2..9646cb1ac0b08 100644 --- a/src/test/ui/rfc-2091-track-caller/error-with-trait-fn-impl.stderr +++ b/src/test/ui/rfc-2091-track-caller/error-with-trait-fn-impl.stderr @@ -6,7 +6,7 @@ LL | #![feature(track_caller)] | = note: `#[warn(incomplete_features)]` on by default -error[E0738]: `#[track_caller]` is not supported in traits yet. +error[E0738]: `#[track_caller]` may not be used on trait methods --> $DIR/error-with-trait-fn-impl.rs:8:5 | LL | #[track_caller]