Tweak stability attribute diagnostic output
This commit is contained in:
parent
4cb089bb54
commit
19806e4514
5 changed files with 55 additions and 39 deletions
|
@ -176,7 +176,7 @@ pub fn find_stability(
|
||||||
sess: &Session,
|
sess: &Session,
|
||||||
attrs: &[Attribute],
|
attrs: &[Attribute],
|
||||||
item_sp: Span,
|
item_sp: Span,
|
||||||
) -> (Option<Stability>, Option<ConstStability>) {
|
) -> (Option<(Stability, Span)>, Option<(ConstStability, Span)>) {
|
||||||
find_stability_generic(sess, attrs.iter(), item_sp)
|
find_stability_generic(sess, attrs.iter(), item_sp)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -184,15 +184,16 @@ fn find_stability_generic<'a, I>(
|
||||||
sess: &Session,
|
sess: &Session,
|
||||||
attrs_iter: I,
|
attrs_iter: I,
|
||||||
item_sp: Span,
|
item_sp: Span,
|
||||||
) -> (Option<Stability>, Option<ConstStability>)
|
) -> (Option<(Stability, Span)>, Option<(ConstStability, Span)>)
|
||||||
where
|
where
|
||||||
I: Iterator<Item = &'a Attribute>,
|
I: Iterator<Item = &'a Attribute>,
|
||||||
{
|
{
|
||||||
use StabilityLevel::*;
|
use StabilityLevel::*;
|
||||||
|
|
||||||
let mut stab: Option<Stability> = None;
|
let mut stab: Option<(Stability, Span)> = None;
|
||||||
let mut const_stab: Option<ConstStability> = None;
|
let mut const_stab: Option<(ConstStability, Span)> = None;
|
||||||
let mut promotable = false;
|
let mut promotable = false;
|
||||||
|
|
||||||
let diagnostic = &sess.parse_sess.span_diagnostic;
|
let diagnostic = &sess.parse_sess.span_diagnostic;
|
||||||
|
|
||||||
'outer: for attr in attrs_iter {
|
'outer: for attr in attrs_iter {
|
||||||
|
@ -356,10 +357,12 @@ where
|
||||||
}
|
}
|
||||||
let level = Unstable { reason, issue: issue_num, is_soft };
|
let level = Unstable { reason, issue: issue_num, is_soft };
|
||||||
if sym::unstable == meta_name {
|
if sym::unstable == meta_name {
|
||||||
stab = Some(Stability { level, feature });
|
stab = Some((Stability { level, feature }, attr.span));
|
||||||
} else {
|
} else {
|
||||||
const_stab =
|
const_stab = Some((
|
||||||
Some(ConstStability { level, feature, promotable: false });
|
ConstStability { level, feature, promotable: false },
|
||||||
|
attr.span,
|
||||||
|
));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
(None, _, _) => {
|
(None, _, _) => {
|
||||||
|
@ -432,10 +435,12 @@ where
|
||||||
(Some(feature), Some(since)) => {
|
(Some(feature), Some(since)) => {
|
||||||
let level = Stable { since };
|
let level = Stable { since };
|
||||||
if sym::stable == meta_name {
|
if sym::stable == meta_name {
|
||||||
stab = Some(Stability { level, feature });
|
stab = Some((Stability { level, feature }, attr.span));
|
||||||
} else {
|
} else {
|
||||||
const_stab =
|
const_stab = Some((
|
||||||
Some(ConstStability { level, feature, promotable: false });
|
ConstStability { level, feature, promotable: false },
|
||||||
|
attr.span,
|
||||||
|
));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
(None, _) => {
|
(None, _) => {
|
||||||
|
@ -455,7 +460,7 @@ where
|
||||||
|
|
||||||
// Merge the const-unstable info into the stability info
|
// Merge the const-unstable info into the stability info
|
||||||
if promotable {
|
if promotable {
|
||||||
if let Some(ref mut stab) = const_stab {
|
if let Some((ref mut stab, _)) = const_stab {
|
||||||
stab.promotable = promotable;
|
stab.promotable = promotable;
|
||||||
} else {
|
} else {
|
||||||
struct_span_err!(
|
struct_span_err!(
|
||||||
|
|
|
@ -770,10 +770,13 @@ impl SyntaxExtension {
|
||||||
.find_by_name(attrs, sym::rustc_builtin_macro)
|
.find_by_name(attrs, sym::rustc_builtin_macro)
|
||||||
.map(|a| a.value_str().unwrap_or(name));
|
.map(|a| a.value_str().unwrap_or(name));
|
||||||
let (stability, const_stability) = attr::find_stability(&sess, attrs, span);
|
let (stability, const_stability) = attr::find_stability(&sess, attrs, span);
|
||||||
if const_stability.is_some() {
|
if let Some((_, sp)) = const_stability {
|
||||||
sess.parse_sess
|
sess.parse_sess
|
||||||
.span_diagnostic
|
.span_diagnostic
|
||||||
.span_err(span, "macros cannot have const stability attributes");
|
.struct_span_err(sp, "macros cannot have const stability attributes")
|
||||||
|
.span_label(sp, "invalid stability attribute")
|
||||||
|
.span_label(span, "in this macro")
|
||||||
|
.emit();
|
||||||
}
|
}
|
||||||
|
|
||||||
SyntaxExtension {
|
SyntaxExtension {
|
||||||
|
@ -782,7 +785,7 @@ impl SyntaxExtension {
|
||||||
allow_internal_unstable,
|
allow_internal_unstable,
|
||||||
allow_internal_unsafe: sess.contains_name(attrs, sym::allow_internal_unsafe),
|
allow_internal_unsafe: sess.contains_name(attrs, sym::allow_internal_unsafe),
|
||||||
local_inner_macros,
|
local_inner_macros,
|
||||||
stability,
|
stability: stability.map(|(s, _)| s),
|
||||||
deprecation: attr::find_deprecation(&sess, attrs).map(|(d, _)| d),
|
deprecation: attr::find_deprecation(&sess, attrs).map(|(d, _)| d),
|
||||||
helper_attrs,
|
helper_attrs,
|
||||||
edition,
|
edition,
|
||||||
|
|
|
@ -163,7 +163,7 @@ impl<'a, 'tcx> Annotator<'a, 'tcx> {
|
||||||
|
|
||||||
let (stab, const_stab) = attr::find_stability(&self.tcx.sess, attrs, item_sp);
|
let (stab, const_stab) = attr::find_stability(&self.tcx.sess, attrs, item_sp);
|
||||||
|
|
||||||
let const_stab = const_stab.map(|const_stab| {
|
let const_stab = const_stab.map(|(const_stab, _)| {
|
||||||
let const_stab = self.tcx.intern_const_stability(const_stab);
|
let const_stab = self.tcx.intern_const_stability(const_stab);
|
||||||
self.index.const_stab_map.insert(hir_id, const_stab);
|
self.index.const_stab_map.insert(hir_id, const_stab);
|
||||||
const_stab
|
const_stab
|
||||||
|
@ -193,12 +193,15 @@ impl<'a, 'tcx> Annotator<'a, 'tcx> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
let stab = stab.map(|stab| {
|
let stab = stab.map(|(stab, span)| {
|
||||||
// Error if prohibited, or can't inherit anything from a container.
|
// Error if prohibited, or can't inherit anything from a container.
|
||||||
if kind == AnnotationKind::Prohibited
|
if kind == AnnotationKind::Prohibited
|
||||||
|| (kind == AnnotationKind::Container && stab.level.is_stable() && is_deprecated)
|
|| (kind == AnnotationKind::Container && stab.level.is_stable() && is_deprecated)
|
||||||
{
|
{
|
||||||
self.tcx.sess.span_err(item_sp, "this stability annotation is useless");
|
self.tcx.sess.struct_span_err(span,"this stability annotation is useless")
|
||||||
|
.span_label(span, "useless stability annotation")
|
||||||
|
.span_label(item_sp, "the stability attribute annotates this item")
|
||||||
|
.emit();
|
||||||
}
|
}
|
||||||
|
|
||||||
debug!("annotate: found {:?}", stab);
|
debug!("annotate: found {:?}", stab);
|
||||||
|
@ -215,16 +218,19 @@ impl<'a, 'tcx> Annotator<'a, 'tcx> {
|
||||||
{
|
{
|
||||||
match stab_v.parse::<u64>() {
|
match stab_v.parse::<u64>() {
|
||||||
Err(_) => {
|
Err(_) => {
|
||||||
self.tcx.sess.span_err(item_sp, "invalid stability version found");
|
self.tcx.sess.struct_span_err(span, "invalid stability version found")
|
||||||
|
.span_label(span, "invalid stability version")
|
||||||
|
.span_label(item_sp, "the stability attribute annotates this item")
|
||||||
|
.emit();
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
Ok(stab_vp) => match dep_v.parse::<u64>() {
|
Ok(stab_vp) => match dep_v.parse::<u64>() {
|
||||||
Ok(dep_vp) => match dep_vp.cmp(&stab_vp) {
|
Ok(dep_vp) => match dep_vp.cmp(&stab_vp) {
|
||||||
Ordering::Less => {
|
Ordering::Less => {
|
||||||
self.tcx.sess.span_err(
|
self.tcx.sess.struct_span_err(span, "an API can't be stabilized after it is deprecated")
|
||||||
item_sp,
|
.span_label(span, "invalid version")
|
||||||
"an API can't be stabilized after it is deprecated",
|
.span_label(item_sp, "the stability attribute annotates this item")
|
||||||
);
|
.emit();
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
Ordering::Equal => continue,
|
Ordering::Equal => continue,
|
||||||
|
@ -232,9 +238,10 @@ impl<'a, 'tcx> Annotator<'a, 'tcx> {
|
||||||
},
|
},
|
||||||
Err(_) => {
|
Err(_) => {
|
||||||
if dep_v != "TBD" {
|
if dep_v != "TBD" {
|
||||||
self.tcx
|
self.tcx.sess.struct_span_err(span, "invalid deprecation version found")
|
||||||
.sess
|
.span_label(span, "invalid deprecation version")
|
||||||
.span_err(item_sp, "invalid deprecation version found");
|
.span_label(item_sp, "the stability attribute annotates this item")
|
||||||
|
.emit();
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -756,18 +763,13 @@ impl Visitor<'tcx> for Checker<'tcx> {
|
||||||
// error if all involved types and traits are stable, because
|
// error if all involved types and traits are stable, because
|
||||||
// it will have no effect.
|
// it will have no effect.
|
||||||
// See: https://github.com/rust-lang/rust/issues/55436
|
// See: https://github.com/rust-lang/rust/issues/55436
|
||||||
if let (Some(Stability { level: attr::Unstable { .. }, .. }), _) =
|
if let (Some((Stability { level: attr::Unstable { .. }, .. }, span)), _) =
|
||||||
attr::find_stability(&self.tcx.sess, &item.attrs, item.span)
|
attr::find_stability(&self.tcx.sess, &item.attrs, item.span)
|
||||||
{
|
{
|
||||||
let mut c = CheckTraitImplStable { tcx: self.tcx, fully_stable: true };
|
let mut c = CheckTraitImplStable { tcx: self.tcx, fully_stable: true };
|
||||||
c.visit_ty(self_ty);
|
c.visit_ty(self_ty);
|
||||||
c.visit_trait_ref(t);
|
c.visit_trait_ref(t);
|
||||||
if c.fully_stable {
|
if c.fully_stable {
|
||||||
let span = item
|
|
||||||
.attrs
|
|
||||||
.iter()
|
|
||||||
.find(|a| a.has_name(sym::unstable))
|
|
||||||
.map_or(item.span, |a| a.span);
|
|
||||||
self.tcx.struct_span_lint_hir(
|
self.tcx.struct_span_lint_hir(
|
||||||
INEFFECTIVE_UNSTABLE_TRAIT_IMPL,
|
INEFFECTIVE_UNSTABLE_TRAIT_IMPL,
|
||||||
item.hir_id,
|
item.hir_id,
|
||||||
|
|
|
@ -57,16 +57,16 @@ fn multiple2() { }
|
||||||
#[stable(feature = "a", since = "b")] //~ ERROR multiple stability levels [E0544]
|
#[stable(feature = "a", since = "b")] //~ ERROR multiple stability levels [E0544]
|
||||||
fn multiple3() { }
|
fn multiple3() { }
|
||||||
|
|
||||||
#[stable(feature = "a", since = "b")]
|
#[stable(feature = "a", since = "b")] //~ ERROR invalid stability version found
|
||||||
#[rustc_deprecated(since = "b", reason = "text")]
|
#[rustc_deprecated(since = "b", reason = "text")]
|
||||||
#[rustc_deprecated(since = "b", reason = "text")] //~ ERROR multiple deprecated attributes
|
#[rustc_deprecated(since = "b", reason = "text")] //~ ERROR multiple deprecated attributes
|
||||||
#[rustc_const_unstable(feature = "c", issue = "none")]
|
#[rustc_const_unstable(feature = "c", issue = "none")]
|
||||||
#[rustc_const_unstable(feature = "d", issue = "none")] //~ ERROR multiple stability levels
|
#[rustc_const_unstable(feature = "d", issue = "none")] //~ ERROR multiple stability levels
|
||||||
pub const fn multiple4() { } //~ ERROR invalid stability version found
|
pub const fn multiple4() { }
|
||||||
|
|
||||||
#[stable(feature = "a", since = "1.0.0")]
|
#[stable(feature = "a", since = "1.0.0")] //~ ERROR invalid deprecation version found
|
||||||
#[rustc_deprecated(since = "invalid", reason = "text")]
|
#[rustc_deprecated(since = "invalid", reason = "text")]
|
||||||
fn invalid_deprecation_version() {} //~ ERROR invalid deprecation version found
|
fn invalid_deprecation_version() {}
|
||||||
|
|
||||||
#[rustc_deprecated(since = "a", reason = "text")]
|
#[rustc_deprecated(since = "a", reason = "text")]
|
||||||
fn deprecated_without_unstable_or_stable() { }
|
fn deprecated_without_unstable_or_stable() { }
|
||||||
|
|
|
@ -97,16 +97,22 @@ LL | #[rustc_const_unstable(feature = "d", issue = "none")]
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||||
|
|
||||||
error: invalid stability version found
|
error: invalid stability version found
|
||||||
--> $DIR/stability-attribute-sanity.rs:65:1
|
--> $DIR/stability-attribute-sanity.rs:60:1
|
||||||
|
|
|
|
||||||
|
LL | #[stable(feature = "a", since = "b")]
|
||||||
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ invalid stability version
|
||||||
|
...
|
||||||
LL | pub const fn multiple4() { }
|
LL | pub const fn multiple4() { }
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
| ---------------------------- the stability attribute annotates this item
|
||||||
|
|
||||||
error: invalid deprecation version found
|
error: invalid deprecation version found
|
||||||
--> $DIR/stability-attribute-sanity.rs:69:1
|
--> $DIR/stability-attribute-sanity.rs:67:1
|
||||||
|
|
|
|
||||||
|
LL | #[stable(feature = "a", since = "1.0.0")]
|
||||||
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ invalid deprecation version
|
||||||
|
LL | #[rustc_deprecated(since = "invalid", reason = "text")]
|
||||||
LL | fn invalid_deprecation_version() {}
|
LL | fn invalid_deprecation_version() {}
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
| ----------------------------------- the stability attribute annotates this item
|
||||||
|
|
||||||
error[E0549]: rustc_deprecated attribute must be paired with either stable or unstable attribute
|
error[E0549]: rustc_deprecated attribute must be paired with either stable or unstable attribute
|
||||||
--> $DIR/stability-attribute-sanity.rs:71:1
|
--> $DIR/stability-attribute-sanity.rs:71:1
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue