blob: fd27e30a67f3b8a3dbb120c2443aadd27d069b4a [file] [log] [blame] [edit]
use super::{Attribute, SHOULD_PANIC_WITHOUT_EXPECT};
use clippy_utils::diagnostics::span_lint_and_sugg;
use rustc_ast::token::{Token, TokenKind};
use rustc_ast::tokenstream::TokenTree;
use rustc_ast::{AttrArgs, AttrKind};
use rustc_errors::Applicability;
use rustc_lint::EarlyContext;
use rustc_span::sym;
pub(super) fn check(cx: &EarlyContext<'_>, attr: &Attribute) {
if let AttrKind::Normal(normal_attr) = &attr.kind {
if let AttrArgs::Eq { .. } = &normal_attr.item.args {
// `#[should_panic = ".."]` found, good
return;
}
if let AttrArgs::Delimited(args) = &normal_attr.item.args
&& let mut tt_iter = args.tokens.iter()
&& let Some(TokenTree::Token(
Token {
kind: TokenKind::Ident(sym::expected, _),
..
},
_,
)) = tt_iter.next()
&& let Some(TokenTree::Token(
Token {
kind: TokenKind::Eq, ..
},
_,
)) = tt_iter.next()
&& let Some(TokenTree::Token(
Token {
kind: TokenKind::Literal(_),
..
},
_,
)) = tt_iter.next()
{
// `#[should_panic(expected = "..")]` found, good
return;
}
span_lint_and_sugg(
cx,
SHOULD_PANIC_WITHOUT_EXPECT,
attr.span,
"#[should_panic] attribute without a reason",
"consider specifying the expected panic",
"#[should_panic(expected = /* panic message */)]".into(),
Applicability::HasPlaceholders,
);
}
}