Skip to content

Commit

Permalink
Do not consider using a semicolon inside of a different-crate macro
Browse files Browse the repository at this point in the history
Fixes #81943
  • Loading branch information
notriddle committed Feb 23, 2021
1 parent 0196107 commit de6f1b8
Show file tree
Hide file tree
Showing 5 changed files with 83 additions and 2 deletions.
8 changes: 7 additions & 1 deletion compiler/rustc_typeck/src/check/coercion.rs
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@ use rustc_hir as hir;
use rustc_hir::def_id::DefId;
use rustc_infer::infer::type_variable::{TypeVariableOrigin, TypeVariableOriginKind};
use rustc_infer::infer::{Coercion, InferOk, InferResult};
use rustc_middle::lint::in_external_macro;
use rustc_middle::ty::adjustment::{
Adjust, Adjustment, AllowTwoPhase, AutoBorrow, AutoBorrowMutability, PointerCast,
};
Expand Down Expand Up @@ -1448,7 +1449,12 @@ impl<'tcx, 'exprs, E: AsCoercionSite> CoerceMany<'tcx, 'exprs, E> {
expected.is_unit(),
pointing_at_return_type,
) {
if cond_expr.span.desugaring_kind().is_none() {
// If the block is from an external macro, then do not suggest
// adding a semicolon, because there's nowhere to put it.
// See issue #81943.
if cond_expr.span.desugaring_kind().is_none()
&& !in_external_macro(fcx.tcx.sess, cond_expr.span)
{
err.span_label(cond_expr.span, "expected this to be `()`");
if expr.can_have_side_effects() {
fcx.suggest_semicolon_at_end(cond_expr.span, &mut err);
Expand Down
6 changes: 5 additions & 1 deletion compiler/rustc_typeck/src/check/fn_ctxt/suggestions.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ use rustc_hir::def::{CtorOf, DefKind};
use rustc_hir::lang_items::LangItem;
use rustc_hir::{ExprKind, ItemKind, Node};
use rustc_infer::infer;
use rustc_middle::lint::in_external_macro;
use rustc_middle::ty::{self, Ty};
use rustc_span::symbol::kw;

Expand Down Expand Up @@ -44,7 +45,10 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
blk_id: hir::HirId,
) -> bool {
let expr = expr.peel_drop_temps();
if expr.can_have_side_effects() {
// If the expression is from an external macro, then do not suggest
// adding a semicolon, because there's nowhere to put it.
// See issue #81943.
if expr.can_have_side_effects() && !in_external_macro(self.tcx.sess, cause_span) {
self.suggest_missing_semicolon(err, expr, expected, cause_span);
}
let mut pointing_at_return_type = false;
Expand Down
7 changes: 7 additions & 0 deletions src/test/ui/typeck/auxiliary/issue-81943-lib.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
pub fn g(t: i32) -> i32 { t }
// This function imitates `dbg!` so that future changes
// to its macro definition won't make this test a dud.
#[macro_export]
macro_rules! d {
($e:expr) => { match $e { x => { $crate::g(x) } } }
}
13 changes: 13 additions & 0 deletions src/test/ui/typeck/issue-81943.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
// aux-build:issue-81943-lib.rs
extern crate issue_81943_lib as lib;

fn f<F: Fn(i32)>(f: F) { f(0); }
fn g(t: i32) -> i32 { t }
fn main() {
f(|x| lib::d!(x)); //~ERROR
f(|x| match x { tmp => { g(tmp) } }); //~ERROR
macro_rules! d {
($e:expr) => { match $e { x => { g(x) } } } //~ERROR
}
f(|x| d!(x));
}
51 changes: 51 additions & 0 deletions src/test/ui/typeck/issue-81943.stderr
Original file line number Diff line number Diff line change
@@ -0,0 +1,51 @@
error[E0308]: mismatched types
--> $DIR/issue-81943.rs:7:9
|
LL | f(|x| lib::d!(x));
| ^^^^^^^^^^ expected `()`, found `i32`
|
= note: this error originates in a macro (in Nightly builds, run with -Z macro-backtrace for more info)

error[E0308]: mismatched types
--> $DIR/issue-81943.rs:8:28
|
LL | f(|x| match x { tmp => { g(tmp) } });
| -------------------^^^^^^----
| | |
| | expected `()`, found `i32`
| expected this to be `()`
|
help: consider using a semicolon here
|
LL | f(|x| match x { tmp => { g(tmp); } });
| ^
help: consider using a semicolon here
|
LL | f(|x| match x { tmp => { g(tmp) } };);
| ^

error[E0308]: mismatched types
--> $DIR/issue-81943.rs:10:38
|
LL | ($e:expr) => { match $e { x => { g(x) } } }
| ------------------^^^^----
| | |
| | expected `()`, found `i32`
| expected this to be `()`
LL | }
LL | f(|x| d!(x));
| ----- in this macro invocation
|
= note: this error originates in a macro (in Nightly builds, run with -Z macro-backtrace for more info)
help: consider using a semicolon here
|
LL | ($e:expr) => { match $e { x => { g(x); } } }
| ^
help: consider using a semicolon here
|
LL | ($e:expr) => { match $e { x => { g(x) } }; }
| ^

error: aborting due to 3 previous errors

For more information about this error, try `rustc --explain E0308`.

0 comments on commit de6f1b8

Please sign in to comment.