Skip to content

Commit 2f6cb5f

Browse files
committed
Add lint for excess trailing semicolons
1 parent 71415ef commit 2f6cb5f

File tree

2 files changed

+55
-0
lines changed

2 files changed

+55
-0
lines changed

src/librustc_lint/lib.rs

+3
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ extern crate rustc;
2424

2525
mod error_codes;
2626
mod nonstandard_style;
27+
mod redundant_semicolon;
2728
pub mod builtin;
2829
mod types;
2930
mod unused;
@@ -55,6 +56,7 @@ use session::Session;
5556
use lint::LintId;
5657
use lint::FutureIncompatibleInfo;
5758

59+
use redundant_semicolon::*;
5860
use nonstandard_style::*;
5961
use builtin::*;
6062
use types::*;
@@ -98,6 +100,7 @@ macro_rules! early_lint_passes {
98100
WhileTrue: WhileTrue,
99101
NonAsciiIdents: NonAsciiIdents,
100102
IncompleteFeatures: IncompleteFeatures,
103+
RedundantSemicolon: RedundantSemicolon,
101104
]);
102105
)
103106
}
+52
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
use crate::lint::{EarlyLintPass, LintPass, EarlyContext, LintArray, LintContext};
2+
use syntax::ast::{Stmt, StmtKind, ExprKind};
3+
use syntax::errors::Applicability;
4+
5+
declare_lint! {
6+
pub REDUNDANT_SEMICOLON,
7+
Warn,
8+
"detects unnecessary trailing semicolons"
9+
}
10+
11+
declare_lint_pass!(RedundantSemicolon => [REDUNDANT_SEMICOLON]);
12+
13+
impl EarlyLintPass for RedundantSemicolon {
14+
fn check_stmt(&mut self, cx: &EarlyContext<'_>, stmt: &Stmt) {
15+
if let StmtKind::Semi(expr) = &stmt.node {
16+
if let ExprKind::Tup(ref v) = &expr.node {
17+
if v.is_empty() {
18+
// Strings of excess semicolons are encoded as empty tuple expressions
19+
// during the parsing stage, so we check for empty tuple expressions
20+
// which span only semicolons
21+
if let Ok(source_str) = cx.sess().source_map().span_to_snippet(stmt.span) {
22+
if source_str.chars().all(|c| c == ';') {
23+
let multiple = (stmt.span.hi() - stmt.span.lo()).0 > 1;
24+
let msg = if multiple {
25+
"unnecessary trailing semicolons"
26+
} else {
27+
"unnecessary trailing semicolon"
28+
};
29+
let mut err = cx.struct_span_lint(
30+
REDUNDANT_SEMICOLON,
31+
stmt.span,
32+
&msg
33+
);
34+
let suggest_msg = if multiple {
35+
"remove these semicolons"
36+
} else {
37+
"remove this semicolon"
38+
};
39+
err.span_suggestion(
40+
stmt.span,
41+
&suggest_msg,
42+
String::new(),
43+
Applicability::MaybeIncorrect
44+
);
45+
err.emit();
46+
}
47+
}
48+
}
49+
}
50+
}
51+
}
52+
}

0 commit comments

Comments
 (0)