Rollup merge of #132156 - estebank:closure-return, r=Nadrieril,compiler-errors
When encountering unexpected closure return type, point at return type/expression ``` error[E0271]: expected `{closure@fallback-closure-wrap.rs:18:40}` to be a closure that returns `()`, but it returns `!` --> $DIR/fallback-closure-wrap.rs:19:9 | LL | let error = Closure::wrap(Box::new(move || { | ------- LL | panic!("Can't connect to server."); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected `()`, found `!` | = note: expected unit type `()` found type `!` = note: required for the cast from `Box<{closure@$DIR/fallback-closure-wrap.rs:18:40: 18:47}>` to `Box<dyn FnMut()>` ``` ``` error[E0271]: expected `{closure@dont-ice-for-type-mismatch-in-closure-in-async.rs:6:10}` to be a closure that returns `bool`, but it returns `Option<()>` --> $DIR/dont-ice-for-type-mismatch-in-closure-in-async.rs:6:16 | LL | call(|| -> Option<()> { | ---- ------^^^^^^^^^^ | | | | | expected `bool`, found `Option<()>` | required by a bound introduced by this call | = note: expected type `bool` found enum `Option<()>` note: required by a bound in `call` --> $DIR/dont-ice-for-type-mismatch-in-closure-in-async.rs:3:25 | LL | fn call(_: impl Fn() -> bool) {} | ^^^^ required by this bound in `call` ``` ``` error[E0271]: expected `{closure@f670.rs:28:13}` to be a closure that returns `Result<(), _>`, but it returns `!` --> f670.rs:28:20 | 28 | let c = |e| -> ! { | -------^ | | | expected `Result<(), _>`, found `!` ... 32 | f().or_else(c); | ------- required by a bound introduced by this call -Ztrack-diagnostics: created at compiler/rustc_trait_selection/src/error_reporting/traits/fulfillment_errors.rs:1433:28 | = note: expected enum `Result<(), _>` found type `!` note: required by a bound in `Result::<T, E>::or_else` --> /home/gh-estebank/rust/library/core/src/result.rs:1406:39 | 1406 | pub fn or_else<F, O: FnOnce(E) -> Result<T, F>>(self, op: O) -> Result<T, F> { | ^^^^^^^^^^^^ required by this bound in `Result::<T, E>::or_else` ``` CC #111539.
This commit is contained in:
commit
ae9dbf169f
13 changed files with 189 additions and 65 deletions
|
@ -653,6 +653,7 @@ pub(super) fn collect_return_position_impl_trait_in_trait_tys<'tcx>(
|
||||||
}))),
|
}))),
|
||||||
terr,
|
terr,
|
||||||
false,
|
false,
|
||||||
|
None,
|
||||||
);
|
);
|
||||||
return Err(diag.emit());
|
return Err(diag.emit());
|
||||||
}
|
}
|
||||||
|
@ -1070,6 +1071,7 @@ fn report_trait_method_mismatch<'tcx>(
|
||||||
}))),
|
}))),
|
||||||
terr,
|
terr,
|
||||||
false,
|
false,
|
||||||
|
None,
|
||||||
);
|
);
|
||||||
|
|
||||||
diag.emit()
|
diag.emit()
|
||||||
|
@ -1862,6 +1864,7 @@ fn compare_const_predicate_entailment<'tcx>(
|
||||||
}))),
|
}))),
|
||||||
terr,
|
terr,
|
||||||
false,
|
false,
|
||||||
|
None,
|
||||||
);
|
);
|
||||||
return Err(diag.emit());
|
return Err(diag.emit());
|
||||||
};
|
};
|
||||||
|
|
|
@ -649,6 +649,7 @@ pub fn check_function_signature<'tcx>(
|
||||||
}))),
|
}))),
|
||||||
err,
|
err,
|
||||||
false,
|
false,
|
||||||
|
None,
|
||||||
);
|
);
|
||||||
return Err(diag.emit());
|
return Err(diag.emit());
|
||||||
}
|
}
|
||||||
|
|
|
@ -1147,6 +1147,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
||||||
Some(self.param_env.and(trace.values)),
|
Some(self.param_env.and(trace.values)),
|
||||||
e,
|
e,
|
||||||
true,
|
true,
|
||||||
|
None,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -2471,6 +2471,7 @@ impl<'tcx> CheckAttrVisitor<'tcx> {
|
||||||
}))),
|
}))),
|
||||||
terr,
|
terr,
|
||||||
false,
|
false,
|
||||||
|
None,
|
||||||
);
|
);
|
||||||
diag.emit();
|
diag.emit();
|
||||||
self.abort.set(true);
|
self.abort.set(true);
|
||||||
|
|
|
@ -1392,9 +1392,13 @@ impl<'a, 'tcx> TypeErrCtxt<'a, 'tcx> {
|
||||||
mut values: Option<ty::ParamEnvAnd<'tcx, ValuePairs<'tcx>>>,
|
mut values: Option<ty::ParamEnvAnd<'tcx, ValuePairs<'tcx>>>,
|
||||||
terr: TypeError<'tcx>,
|
terr: TypeError<'tcx>,
|
||||||
prefer_label: bool,
|
prefer_label: bool,
|
||||||
|
override_span: Option<Span>,
|
||||||
) {
|
) {
|
||||||
let span = cause.span;
|
// We use `override_span` when we want the error to point at a `Span` other than
|
||||||
|
// `cause.span`. This is used in E0271, when a closure is passed in where the return type
|
||||||
|
// isn't what was expected. We want to point at the closure's return type (or expression),
|
||||||
|
// instead of the expression where the closure is passed as call argument.
|
||||||
|
let span = override_span.unwrap_or(cause.span);
|
||||||
// For some types of errors, expected-found does not make
|
// For some types of errors, expected-found does not make
|
||||||
// sense, so just ignore the values we were given.
|
// sense, so just ignore the values we were given.
|
||||||
if let TypeError::CyclicTy(_) = terr {
|
if let TypeError::CyclicTy(_) = terr {
|
||||||
|
@ -2057,6 +2061,7 @@ impl<'a, 'tcx> TypeErrCtxt<'a, 'tcx> {
|
||||||
Some(param_env.and(trace.values)),
|
Some(param_env.and(trace.values)),
|
||||||
terr,
|
terr,
|
||||||
false,
|
false,
|
||||||
|
None,
|
||||||
);
|
);
|
||||||
diag
|
diag
|
||||||
}
|
}
|
||||||
|
|
|
@ -708,6 +708,7 @@ impl<'a, 'tcx> TypeErrCtxt<'a, 'tcx> {
|
||||||
None,
|
None,
|
||||||
TypeError::Sorts(ty::error::ExpectedFound::new(expected_ty, ct_ty)),
|
TypeError::Sorts(ty::error::ExpectedFound::new(expected_ty, ct_ty)),
|
||||||
false,
|
false,
|
||||||
|
None,
|
||||||
);
|
);
|
||||||
diag
|
diag
|
||||||
}
|
}
|
||||||
|
@ -931,14 +932,9 @@ impl<'a, 'tcx> TypeErrCtxt<'a, 'tcx> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
let hir_id = self.tcx.local_def_id_to_hir_id(obligation.cause.body_id);
|
let hir_id = self.tcx.local_def_id_to_hir_id(obligation.cause.body_id);
|
||||||
let body_id = match self.tcx.hir_node(hir_id) {
|
let Some(body_id) = self.tcx.hir_node(hir_id).body_id() else { return false };
|
||||||
hir::Node::Item(hir::Item {
|
let ControlFlow::Break(expr) =
|
||||||
kind: hir::ItemKind::Fn { body: body_id, .. }, ..
|
(FindMethodSubexprOfTry { search_span: span }).visit_body(self.tcx.hir().body(body_id))
|
||||||
}) => body_id,
|
|
||||||
_ => return false,
|
|
||||||
};
|
|
||||||
let ControlFlow::Break(expr) = (FindMethodSubexprOfTry { search_span: span })
|
|
||||||
.visit_body(self.tcx.hir().body(*body_id))
|
|
||||||
else {
|
else {
|
||||||
return false;
|
return false;
|
||||||
};
|
};
|
||||||
|
@ -1385,9 +1381,14 @@ impl<'a, 'tcx> TypeErrCtxt<'a, 'tcx> {
|
||||||
_ => (None, error.err),
|
_ => (None, error.err),
|
||||||
};
|
};
|
||||||
|
|
||||||
let msg = values
|
let (msg, span, closure_span) = values
|
||||||
.and_then(|(predicate, normalized_term, expected_term)| {
|
.and_then(|(predicate, normalized_term, expected_term)| {
|
||||||
self.maybe_detailed_projection_msg(predicate, normalized_term, expected_term)
|
self.maybe_detailed_projection_msg(
|
||||||
|
obligation.cause.span,
|
||||||
|
predicate,
|
||||||
|
normalized_term,
|
||||||
|
expected_term,
|
||||||
|
)
|
||||||
})
|
})
|
||||||
.unwrap_or_else(|| {
|
.unwrap_or_else(|| {
|
||||||
let mut cx = FmtPrinter::new_with_limit(
|
let mut cx = FmtPrinter::new_with_limit(
|
||||||
|
@ -1395,12 +1396,39 @@ impl<'a, 'tcx> TypeErrCtxt<'a, 'tcx> {
|
||||||
Namespace::TypeNS,
|
Namespace::TypeNS,
|
||||||
rustc_session::Limit(10),
|
rustc_session::Limit(10),
|
||||||
);
|
);
|
||||||
|
(
|
||||||
with_forced_trimmed_paths!(format!("type mismatch resolving `{}`", {
|
with_forced_trimmed_paths!(format!("type mismatch resolving `{}`", {
|
||||||
self.resolve_vars_if_possible(predicate).print(&mut cx).unwrap();
|
self.resolve_vars_if_possible(predicate).print(&mut cx).unwrap();
|
||||||
cx.into_buffer()
|
cx.into_buffer()
|
||||||
}))
|
})),
|
||||||
|
obligation.cause.span,
|
||||||
|
None,
|
||||||
|
)
|
||||||
});
|
});
|
||||||
let mut diag = struct_span_code_err!(self.dcx(), obligation.cause.span, E0271, "{msg}");
|
let mut diag = struct_span_code_err!(self.dcx(), span, E0271, "{msg}");
|
||||||
|
if let Some(span) = closure_span {
|
||||||
|
// Mark the closure decl so that it is seen even if we are pointing at the return
|
||||||
|
// type or expression.
|
||||||
|
//
|
||||||
|
// error[E0271]: expected `{closure@foo.rs:41:16}` to be a closure that returns
|
||||||
|
// `Unit3`, but it returns `Unit4`
|
||||||
|
// --> $DIR/foo.rs:43:17
|
||||||
|
// |
|
||||||
|
// LL | let v = Unit2.m(
|
||||||
|
// | - required by a bound introduced by this call
|
||||||
|
// ...
|
||||||
|
// LL | f: |x| {
|
||||||
|
// | --- /* this span */
|
||||||
|
// LL | drop(x);
|
||||||
|
// LL | Unit4
|
||||||
|
// | ^^^^^ expected `Unit3`, found `Unit4`
|
||||||
|
// |
|
||||||
|
diag.span_label(span, "this closure");
|
||||||
|
if !span.overlaps(obligation.cause.span) {
|
||||||
|
// Point at the binding corresponding to the closure where it is used.
|
||||||
|
diag.span_label(obligation.cause.span, "closure used here");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
let secondary_span = (|| {
|
let secondary_span = (|| {
|
||||||
let ty::PredicateKind::Clause(ty::ClauseKind::Projection(proj)) =
|
let ty::PredicateKind::Clause(ty::ClauseKind::Projection(proj)) =
|
||||||
|
@ -1471,6 +1499,7 @@ impl<'a, 'tcx> TypeErrCtxt<'a, 'tcx> {
|
||||||
}),
|
}),
|
||||||
err,
|
err,
|
||||||
false,
|
false,
|
||||||
|
Some(span),
|
||||||
);
|
);
|
||||||
self.note_obligation_cause(&mut diag, obligation);
|
self.note_obligation_cause(&mut diag, obligation);
|
||||||
diag.emit()
|
diag.emit()
|
||||||
|
@ -1479,34 +1508,66 @@ impl<'a, 'tcx> TypeErrCtxt<'a, 'tcx> {
|
||||||
|
|
||||||
fn maybe_detailed_projection_msg(
|
fn maybe_detailed_projection_msg(
|
||||||
&self,
|
&self,
|
||||||
|
mut span: Span,
|
||||||
projection_term: ty::AliasTerm<'tcx>,
|
projection_term: ty::AliasTerm<'tcx>,
|
||||||
normalized_ty: ty::Term<'tcx>,
|
normalized_ty: ty::Term<'tcx>,
|
||||||
expected_ty: ty::Term<'tcx>,
|
expected_ty: ty::Term<'tcx>,
|
||||||
) -> Option<String> {
|
) -> Option<(String, Span, Option<Span>)> {
|
||||||
let trait_def_id = projection_term.trait_def_id(self.tcx);
|
let trait_def_id = projection_term.trait_def_id(self.tcx);
|
||||||
let self_ty = projection_term.self_ty();
|
let self_ty = projection_term.self_ty();
|
||||||
|
|
||||||
with_forced_trimmed_paths! {
|
with_forced_trimmed_paths! {
|
||||||
if self.tcx.is_lang_item(projection_term.def_id, LangItem::FnOnceOutput) {
|
if self.tcx.is_lang_item(projection_term.def_id, LangItem::FnOnceOutput) {
|
||||||
let fn_kind = self_ty.prefix_string(self.tcx);
|
let fn_kind = self_ty.prefix_string(self.tcx);
|
||||||
|
let (span, closure_span) = if let ty::Closure(def_id, _) = self_ty.kind() {
|
||||||
|
let def_span = self.tcx.def_span(def_id);
|
||||||
|
if let Some(local_def_id) = def_id.as_local()
|
||||||
|
&& let node = self.tcx.hir_node_by_def_id(local_def_id)
|
||||||
|
&& let Some(fn_decl) = node.fn_decl()
|
||||||
|
&& let Some(id) = node.body_id()
|
||||||
|
{
|
||||||
|
span = match fn_decl.output {
|
||||||
|
hir::FnRetTy::Return(ty) => ty.span,
|
||||||
|
hir::FnRetTy::DefaultReturn(_) => {
|
||||||
|
let body = self.tcx.hir().body(id);
|
||||||
|
match body.value.kind {
|
||||||
|
hir::ExprKind::Block(
|
||||||
|
hir::Block { expr: Some(expr), .. },
|
||||||
|
_,
|
||||||
|
) => expr.span,
|
||||||
|
hir::ExprKind::Block(
|
||||||
|
hir::Block {
|
||||||
|
expr: None, stmts: [.., last], ..
|
||||||
|
},
|
||||||
|
_,
|
||||||
|
) => last.span,
|
||||||
|
_ => body.value.span,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
(span, Some(def_span))
|
||||||
|
} else {
|
||||||
|
(span, None)
|
||||||
|
};
|
||||||
let item = match self_ty.kind() {
|
let item = match self_ty.kind() {
|
||||||
ty::FnDef(def, _) => self.tcx.item_name(*def).to_string(),
|
ty::FnDef(def, _) => self.tcx.item_name(*def).to_string(),
|
||||||
_ => self_ty.to_string(),
|
_ => self_ty.to_string(),
|
||||||
};
|
};
|
||||||
Some(format!(
|
Some((format!(
|
||||||
"expected `{item}` to be a {fn_kind} that returns `{expected_ty}`, but it \
|
"expected `{item}` to be a {fn_kind} that returns `{expected_ty}`, but it \
|
||||||
returns `{normalized_ty}`",
|
returns `{normalized_ty}`",
|
||||||
))
|
), span, closure_span))
|
||||||
} else if self.tcx.is_lang_item(trait_def_id, LangItem::Future) {
|
} else if self.tcx.is_lang_item(trait_def_id, LangItem::Future) {
|
||||||
Some(format!(
|
Some((format!(
|
||||||
"expected `{self_ty}` to be a future that resolves to `{expected_ty}`, but it \
|
"expected `{self_ty}` to be a future that resolves to `{expected_ty}`, but it \
|
||||||
resolves to `{normalized_ty}`"
|
resolves to `{normalized_ty}`"
|
||||||
))
|
), span, None))
|
||||||
} else if Some(trait_def_id) == self.tcx.get_diagnostic_item(sym::Iterator) {
|
} else if Some(trait_def_id) == self.tcx.get_diagnostic_item(sym::Iterator) {
|
||||||
Some(format!(
|
Some((format!(
|
||||||
"expected `{self_ty}` to be an iterator that yields `{expected_ty}`, but it \
|
"expected `{self_ty}` to be an iterator that yields `{expected_ty}`, but it \
|
||||||
yields `{normalized_ty}`"
|
yields `{normalized_ty}`"
|
||||||
))
|
), span, None))
|
||||||
} else {
|
} else {
|
||||||
None
|
None
|
||||||
}
|
}
|
||||||
|
|
|
@ -21,18 +21,14 @@ LL | true
|
||||||
found type `bool`
|
found type `bool`
|
||||||
|
|
||||||
error[E0271]: expected `{closure@dont-ice-for-type-mismatch-in-closure-in-async.rs:6:10}` to be a closure that returns `bool`, but it returns `Option<()>`
|
error[E0271]: expected `{closure@dont-ice-for-type-mismatch-in-closure-in-async.rs:6:10}` to be a closure that returns `bool`, but it returns `Option<()>`
|
||||||
--> $DIR/dont-ice-for-type-mismatch-in-closure-in-async.rs:6:10
|
--> $DIR/dont-ice-for-type-mismatch-in-closure-in-async.rs:6:16
|
||||||
|
|
|
|
||||||
LL | call(|| -> Option<()> {
|
LL | call(|| -> Option<()> {
|
||||||
| _____----_^
|
| ---- ------^^^^^^^^^^
|
||||||
| | |
|
| | | |
|
||||||
| | required by a bound introduced by this call
|
| | | expected `bool`, found `Option<()>`
|
||||||
LL | |
|
| | this closure
|
||||||
LL | | if true {
|
| required by a bound introduced by this call
|
||||||
LL | | false
|
|
||||||
... |
|
|
||||||
LL | | })
|
|
||||||
| |_____^ expected `bool`, found `Option<()>`
|
|
||||||
|
|
|
|
||||||
= note: expected type `bool`
|
= note: expected type `bool`
|
||||||
found enum `Option<()>`
|
found enum `Option<()>`
|
||||||
|
|
25
tests/ui/closures/return-type-doesnt-match-bound.rs
Normal file
25
tests/ui/closures/return-type-doesnt-match-bound.rs
Normal file
|
@ -0,0 +1,25 @@
|
||||||
|
use std::error::Error;
|
||||||
|
use std::process::exit;
|
||||||
|
|
||||||
|
fn foo<F>(f: F) -> ()
|
||||||
|
where
|
||||||
|
F: FnOnce() -> Result<(), Box<dyn Error>>,
|
||||||
|
{
|
||||||
|
f().or_else(|e| -> ! { //~ ERROR to be a closure that returns
|
||||||
|
eprintln!("{:?}", e);
|
||||||
|
exit(1)
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
fn bar<F>(f: F) -> ()
|
||||||
|
where
|
||||||
|
F: FnOnce() -> Result<(), Box<dyn Error>>,
|
||||||
|
{
|
||||||
|
let c = |e| -> ! { //~ ERROR to be a closure that returns
|
||||||
|
eprintln!("{:?}", e);
|
||||||
|
exit(1)
|
||||||
|
};
|
||||||
|
f().or_else(c);
|
||||||
|
}
|
||||||
|
|
||||||
|
fn main() {}
|
37
tests/ui/closures/return-type-doesnt-match-bound.stderr
Normal file
37
tests/ui/closures/return-type-doesnt-match-bound.stderr
Normal file
|
@ -0,0 +1,37 @@
|
||||||
|
error[E0271]: expected `{closure@return-type-doesnt-match-bound.rs:8:17}` to be a closure that returns `Result<(), _>`, but it returns `!`
|
||||||
|
--> $DIR/return-type-doesnt-match-bound.rs:8:24
|
||||||
|
|
|
||||||
|
LL | f().or_else(|e| -> ! {
|
||||||
|
| ------- -------^
|
||||||
|
| | | |
|
||||||
|
| | | expected `Result<(), _>`, found `!`
|
||||||
|
| | this closure
|
||||||
|
| required by a bound introduced by this call
|
||||||
|
|
|
||||||
|
= note: expected enum `Result<(), _>`
|
||||||
|
found type `!`
|
||||||
|
note: required by a bound in `Result::<T, E>::or_else`
|
||||||
|
--> $SRC_DIR/core/src/result.rs:LL:COL
|
||||||
|
|
||||||
|
error[E0271]: expected `{closure@return-type-doesnt-match-bound.rs:18:13}` to be a closure that returns `Result<(), _>`, but it returns `!`
|
||||||
|
--> $DIR/return-type-doesnt-match-bound.rs:18:20
|
||||||
|
|
|
||||||
|
LL | let c = |e| -> ! {
|
||||||
|
| -------^
|
||||||
|
| | |
|
||||||
|
| | expected `Result<(), _>`, found `!`
|
||||||
|
| this closure
|
||||||
|
...
|
||||||
|
LL | f().or_else(c);
|
||||||
|
| ------- - closure used here
|
||||||
|
| |
|
||||||
|
| required by a bound introduced by this call
|
||||||
|
|
|
||||||
|
= note: expected enum `Result<(), _>`
|
||||||
|
found type `!`
|
||||||
|
note: required by a bound in `Result::<T, E>::or_else`
|
||||||
|
--> $SRC_DIR/core/src/result.rs:LL:COL
|
||||||
|
|
||||||
|
error: aborting due to 2 previous errors
|
||||||
|
|
||||||
|
For more information about this error, try `rustc --explain E0271`.
|
|
@ -36,12 +36,10 @@ trait Ty<'a> {
|
||||||
|
|
||||||
fn main() {
|
fn main() {
|
||||||
let v = Unit2.m(
|
let v = Unit2.m(
|
||||||
L {
|
L { //~ ERROR type mismatch
|
||||||
//~^ ERROR to be a closure that returns `Unit3`, but it returns `Unit4`
|
|
||||||
//~| ERROR type mismatch
|
|
||||||
f: |x| {
|
f: |x| {
|
||||||
drop(x);
|
drop(x);
|
||||||
Unit4
|
Unit4 //~ ERROR to be a closure that returns `Unit3`, but it returns `Unit4`
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|
|
@ -1,16 +1,15 @@
|
||||||
error[E0271]: type mismatch resolving `<L<{closure@issue-62203-hrtb-ice.rs:42:16}> as T0<'r, (&u8,)>>::O == <_ as Ty<'r>>::V`
|
error[E0271]: type mismatch resolving `<L<{closure@issue-62203-hrtb-ice.rs:40:16}> as T0<'r, (&u8,)>>::O == <_ as Ty<'r>>::V`
|
||||||
--> $DIR/issue-62203-hrtb-ice.rs:39:9
|
--> $DIR/issue-62203-hrtb-ice.rs:39:9
|
||||||
|
|
|
|
||||||
LL | let v = Unit2.m(
|
LL | let v = Unit2.m(
|
||||||
| - required by a bound introduced by this call
|
| - required by a bound introduced by this call
|
||||||
LL | / L {
|
LL | / L {
|
||||||
LL | |
|
|
||||||
LL | |
|
|
||||||
LL | | f: |x| {
|
LL | | f: |x| {
|
||||||
... |
|
LL | | drop(x);
|
||||||
|
LL | | Unit4
|
||||||
LL | | },
|
LL | | },
|
||||||
LL | | },
|
LL | | },
|
||||||
| |_________^ type mismatch resolving `<L<{closure@issue-62203-hrtb-ice.rs:42:16}> as T0<'r, (&u8,)>>::O == <_ as Ty<'r>>::V`
|
| |_________^ type mismatch resolving `<L<{closure@issue-62203-hrtb-ice.rs:40:16}> as T0<'r, (&u8,)>>::O == <_ as Ty<'r>>::V`
|
||||||
|
|
|
|
||||||
note: expected this to be `<_ as Ty<'_>>::V`
|
note: expected this to be `<_ as Ty<'_>>::V`
|
||||||
--> $DIR/issue-62203-hrtb-ice.rs:21:14
|
--> $DIR/issue-62203-hrtb-ice.rs:21:14
|
||||||
|
@ -30,21 +29,19 @@ LL | where
|
||||||
LL | F: for<'r> T0<'r, (<Self as Ty<'r>>::V,), O = <B as Ty<'r>>::V>,
|
LL | F: for<'r> T0<'r, (<Self as Ty<'r>>::V,), O = <B as Ty<'r>>::V>,
|
||||||
| ^^^^^^^^^^^^^^^^^^^^ required by this bound in `T1::m`
|
| ^^^^^^^^^^^^^^^^^^^^ required by this bound in `T1::m`
|
||||||
|
|
||||||
error[E0271]: expected `{closure@issue-62203-hrtb-ice.rs:42:16}` to be a closure that returns `Unit3`, but it returns `Unit4`
|
error[E0271]: expected `{closure@issue-62203-hrtb-ice.rs:40:16}` to be a closure that returns `Unit3`, but it returns `Unit4`
|
||||||
--> $DIR/issue-62203-hrtb-ice.rs:39:9
|
--> $DIR/issue-62203-hrtb-ice.rs:42:17
|
||||||
|
|
|
|
||||||
LL | let v = Unit2.m(
|
LL | let v = Unit2.m(
|
||||||
| - required by a bound introduced by this call
|
| - required by a bound introduced by this call
|
||||||
LL | / L {
|
LL | L {
|
||||||
LL | |
|
LL | f: |x| {
|
||||||
LL | |
|
| --- this closure
|
||||||
LL | | f: |x| {
|
LL | drop(x);
|
||||||
... |
|
LL | Unit4
|
||||||
LL | | },
|
| ^^^^^ expected `Unit3`, found `Unit4`
|
||||||
LL | | },
|
|
||||||
| |_________^ expected `Unit3`, found `Unit4`
|
|
||||||
|
|
|
|
||||||
note: required for `L<{closure@$DIR/issue-62203-hrtb-ice.rs:42:16: 42:19}>` to implement `for<'r> T0<'r, (&'r u8,)>`
|
note: required for `L<{closure@$DIR/issue-62203-hrtb-ice.rs:40:16: 40:19}>` to implement `for<'r> T0<'r, (&'r u8,)>`
|
||||||
--> $DIR/issue-62203-hrtb-ice.rs:17:16
|
--> $DIR/issue-62203-hrtb-ice.rs:17:16
|
||||||
|
|
|
|
||||||
LL | impl<'a, A, T> T0<'a, A> for L<T>
|
LL | impl<'a, A, T> T0<'a, A> for L<T>
|
||||||
|
|
|
@ -1,16 +1,15 @@
|
||||||
error[E0271]: expected `{closure@fallback-closure-wrap.rs:18:40}` to be a closure that returns `()`, but it returns `!`
|
error[E0271]: expected `{closure@fallback-closure-wrap.rs:18:40}` to be a closure that returns `()`, but it returns `!`
|
||||||
--> $DIR/fallback-closure-wrap.rs:18:31
|
--> $DIR/fallback-closure-wrap.rs:19:9
|
||||||
|
|
|
|
||||||
LL | let error = Closure::wrap(Box::new(move || {
|
LL | let error = Closure::wrap(Box::new(move || {
|
||||||
| _______________________________^
|
| ------- this closure
|
||||||
LL | |
|
LL | panic!("Can't connect to server.");
|
||||||
LL | | panic!("Can't connect to server.");
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected `()`, found `!`
|
||||||
LL | | }) as Box<dyn FnMut()>);
|
|
||||||
| |______^ expected `()`, found `!`
|
|
||||||
|
|
|
|
||||||
= note: expected unit type `()`
|
= note: expected unit type `()`
|
||||||
found type `!`
|
found type `!`
|
||||||
= note: required for the cast from `Box<{closure@$DIR/fallback-closure-wrap.rs:18:40: 18:47}>` to `Box<dyn FnMut()>`
|
= note: required for the cast from `Box<{closure@$DIR/fallback-closure-wrap.rs:18:40: 18:47}>` to `Box<dyn FnMut()>`
|
||||||
|
= note: this error originates in the macro `panic` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||||
|
|
||||||
error: aborting due to 1 previous error
|
error: aborting due to 1 previous error
|
||||||
|
|
||||||
|
|
|
@ -16,8 +16,8 @@ use std::marker::PhantomData;
|
||||||
|
|
||||||
fn main() {
|
fn main() {
|
||||||
let error = Closure::wrap(Box::new(move || {
|
let error = Closure::wrap(Box::new(move || {
|
||||||
//[fallback]~^ to be a closure that returns `()`, but it returns `!`
|
|
||||||
panic!("Can't connect to server.");
|
panic!("Can't connect to server.");
|
||||||
|
//[fallback]~^ to be a closure that returns `()`, but it returns `!`
|
||||||
}) as Box<dyn FnMut()>);
|
}) as Box<dyn FnMut()>);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue