diff --git a/clippy_lints/src/lib.rs b/clippy_lints/src/lib.rs index cb223ce9d..d8bfb8453 100644 --- a/clippy_lints/src/lib.rs +++ b/clippy_lints/src/lib.rs @@ -932,12 +932,12 @@ pub fn register_plugins(store: &mut rustc_lint::LintStore, sess: &Session, conf: store.register_late_pass(|_| Box::new(from_raw_with_void_ptr::FromRawWithVoidPtr)); store.register_late_pass(|_| Box::new(suspicious_xor_used_as_pow::ConfusingXorAndPow)); store.register_late_pass(move |_| Box::new(manual_is_ascii_check::ManualIsAsciiCheck::new(msrv()))); - let semicolon_inside_block_if_multiline = conf.semicolon_inside_block_if_multiline; - let semicolon_outside_block_if_singleline = conf.semicolon_outside_block_if_singleline; + let semicolon_inside_block_ignore_singleline = conf.semicolon_inside_block_ignore_singleline; + let semicolon_outside_block_ignore_multiline = conf.semicolon_outside_block_ignore_multiline; store.register_late_pass(move |_| { Box::new(semicolon_block::SemicolonBlock::new( - semicolon_inside_block_if_multiline, - semicolon_outside_block_if_singleline, + semicolon_inside_block_ignore_singleline, + semicolon_outside_block_ignore_multiline, )) }); store.register_late_pass(|_| Box::new(fn_null_check::FnNullCheck)); diff --git a/clippy_lints/src/semicolon_block.rs b/clippy_lints/src/semicolon_block.rs index c1c0325b7..419d7991f 100644 --- a/clippy_lints/src/semicolon_block.rs +++ b/clippy_lints/src/semicolon_block.rs @@ -68,17 +68,73 @@ impl_lint_pass!(SemicolonBlock => [SEMICOLON_INSIDE_BLOCK, SEMICOLON_OUTSIDE_BLO #[derive(Copy, Clone)] pub struct SemicolonBlock { - semicolon_inside_block_if_multiline: bool, - semicolon_outside_block_if_singleline: bool, + semicolon_inside_block_ignore_singleline: bool, + semicolon_outside_block_ignore_multiline: bool, } impl SemicolonBlock { - pub fn new(semicolon_inside_block_if_multiline: bool, semicolon_outside_block_if_singleline: bool) -> Self { + pub fn new(semicolon_inside_block_ignore_singleline: bool, semicolon_outside_block_ignore_multiline: bool) -> Self { Self { - semicolon_inside_block_if_multiline, - semicolon_outside_block_if_singleline, + semicolon_inside_block_ignore_singleline, + semicolon_outside_block_ignore_multiline, } } + + fn semicolon_inside_block(self, cx: &LateContext<'_>, block: &Block<'_>, tail: &Expr<'_>, semi_span: Span) { + let insert_span = tail.span.source_callsite().shrink_to_hi(); + let remove_span = semi_span.with_lo(block.span.hi()); + + if self.semicolon_inside_block_ignore_singleline && get_line(cx, remove_span) == get_line(cx, insert_span) { + return; + } + + span_lint_and_then( + cx, + SEMICOLON_INSIDE_BLOCK, + semi_span, + "consider moving the `;` inside the block for consistent formatting", + |diag| { + multispan_sugg_with_applicability( + diag, + "put the `;` here", + Applicability::MachineApplicable, + [(remove_span, String::new()), (insert_span, ";".to_owned())], + ); + }, + ); + } + + fn semicolon_outside_block( + self, + cx: &LateContext<'_>, + block: &Block<'_>, + tail_stmt_expr: &Expr<'_>, + semi_span: Span, + ) { + let insert_span = block.span.with_lo(block.span.hi()); + // account for macro calls + let semi_span = cx.sess().source_map().stmt_span(semi_span, block.span); + let remove_span = semi_span.with_lo(tail_stmt_expr.span.source_callsite().hi()); + + if self.semicolon_outside_block_ignore_multiline && get_line(cx, remove_span) != get_line(cx, insert_span) { + return; + } + + span_lint_and_then( + cx, + SEMICOLON_OUTSIDE_BLOCK, + block.span, + "consider moving the `;` outside the block for consistent formatting", + |diag| { + multispan_sugg_with_applicability( + diag, + "put the `;` here", + Applicability::MachineApplicable, + [(remove_span, String::new()), (insert_span, ";".to_owned())], + ); + }, + ); + } } impl LateLintPass<'_> for SemicolonBlock { @@ -98,81 +154,19 @@ impl LateLintPass<'_> for SemicolonBlock { span, .. } = stmt else { return }; - semicolon_outside_block(self, cx, block, expr, span); + self.semicolon_outside_block(cx, block, expr, span); }, StmtKind::Semi(Expr { kind: ExprKind::Block(block @ Block { expr: Some(tail), .. }, _), .. }) if !block.span.from_expansion() => { - semicolon_inside_block(self, cx, block, tail, stmt.span); + self.semicolon_inside_block(cx, block, tail, stmt.span); }, _ => (), } } } -fn semicolon_inside_block( - conf: &mut SemicolonBlock, - cx: &LateContext<'_>, - block: &Block<'_>, - tail: &Expr<'_>, - semi_span: Span, -) { - let insert_span = tail.span.source_callsite().shrink_to_hi(); - let remove_span = semi_span.with_lo(block.span.hi()); - - if conf.semicolon_inside_block_if_multiline && get_line(cx, remove_span) == get_line(cx, insert_span) { - return; - } - - span_lint_and_then( - cx, - SEMICOLON_INSIDE_BLOCK, - semi_span, - "consider moving the `;` inside the block for consistent formatting", - |diag| { - multispan_sugg_with_applicability( - diag, - "put the `;` here", - Applicability::MachineApplicable, - [(remove_span, String::new()), (insert_span, ";".to_owned())], - ); - }, - ); -} - -fn semicolon_outside_block( - conf: &mut SemicolonBlock, - cx: &LateContext<'_>, - block: &Block<'_>, - tail_stmt_expr: &Expr<'_>, - semi_span: Span, -) { - let insert_span = block.span.with_lo(block.span.hi()); - // account for macro calls - let semi_span = cx.sess().source_map().stmt_span(semi_span, block.span); - let remove_span = semi_span.with_lo(tail_stmt_expr.span.source_callsite().hi()); - - if conf.semicolon_outside_block_if_singleline && get_line(cx, remove_span) != get_line(cx, insert_span) { - return; - } - - span_lint_and_then( - cx, - SEMICOLON_OUTSIDE_BLOCK, - block.span, - "consider moving the `;` outside the block for consistent formatting", - |diag| { - multispan_sugg_with_applicability( - diag, - "put the `;` here", - Applicability::MachineApplicable, - [(remove_span, String::new()), (insert_span, ";".to_owned())], - ); - }, - ); -} - fn get_line(cx: &LateContext<'_>, span: Span) -> Option { if let Ok(line) = cx.sess().source_map().lookup_line(span.lo()) { return Some(line.line); diff --git a/clippy_lints/src/utils/conf.rs b/clippy_lints/src/utils/conf.rs index 939f6cd5f..18a6e2a4a 100644 --- a/clippy_lints/src/utils/conf.rs +++ b/clippy_lints/src/utils/conf.rs @@ -280,11 +280,11 @@ define_Conf! { /// Lint: SEMICOLON_INSIDE_BLOCK. /// /// Whether to lint only if it's multiline. - (semicolon_inside_block_if_multiline: bool = false), + (semicolon_inside_block_ignore_singleline: bool = false), /// Lint: SEMICOLON_OUTSIDE_BLOCK. /// /// Whether to lint only if it's singleline. - (semicolon_outside_block_if_singleline: bool = false), + (semicolon_outside_block_ignore_multiline: bool = false), /// Lint: DOC_MARKDOWN. /// /// The list of words this lint should not consider as identifiers needing ticks. The value diff --git a/tests/ui-toml/semicolon_block/clippy.toml b/tests/ui-toml/semicolon_block/clippy.toml index cc3bc8cae..4d03e88de 100644 --- a/tests/ui-toml/semicolon_block/clippy.toml +++ b/tests/ui-toml/semicolon_block/clippy.toml @@ -1,2 +1,2 @@ -semicolon-inside-block-if-multiline = true -semicolon-outside-block-if-singleline = true +semicolon-inside-block-ignore-singleline = true +semicolon-outside-block-ignore-multiline = true diff --git a/tests/ui-toml/toml_unknown_key/conf_unknown_key.stderr b/tests/ui-toml/toml_unknown_key/conf_unknown_key.stderr index c49c90879..1e0d7499c 100644 --- a/tests/ui-toml/toml_unknown_key/conf_unknown_key.stderr +++ b/tests/ui-toml/toml_unknown_key/conf_unknown_key.stderr @@ -37,8 +37,8 @@ error: error reading Clippy's configuration file `$DIR/clippy.toml`: unknown fie missing-docs-in-crate-items msrv pass-by-value-size-limit - semicolon-inside-block-if-multiline - semicolon-outside-block-if-singleline + semicolon-inside-block-ignore-singleline + semicolon-outside-block-ignore-multiline single-char-binding-names-threshold standard-macro-braces suppress-restriction-lint-in-const