diff --git a/compiler/rustc_hir_typeck/src/callee.rs b/compiler/rustc_hir_typeck/src/callee.rs index b60d053957a9b..c718a2ef0a0d1 100644 --- a/compiler/rustc_hir_typeck/src/callee.rs +++ b/compiler/rustc_hir_typeck/src/callee.rs @@ -7,6 +7,7 @@ use rustc_hir::def::{self, CtorKind, Namespace, Res}; use rustc_hir::def_id::DefId; use rustc_hir::{self as hir, HirId, LangItem}; use rustc_hir_analysis::autoderef::Autoderef; +use rustc_hir_analysis::hir_ty_lowering::IsMethodCall; use rustc_infer::infer::BoundRegionConversionTime; use rustc_infer::traits::{Obligation, ObligationCause, ObligationCauseCode}; use rustc_middle::ty::adjustment::{ @@ -573,6 +574,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { self.check_argument_types( call_expr.span, call_expr, + IsMethodCall::No, fn_sig.inputs(), fn_sig.output(), expected, @@ -883,6 +885,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { self.check_argument_types( call_expr.span, call_expr, + IsMethodCall::No, fn_sig.inputs(), fn_sig.output(), expected, @@ -962,6 +965,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { self.check_argument_types( call_expr.span, call_expr, + IsMethodCall::Yes, &method.sig.inputs()[1..], method.sig.output(), expected, diff --git a/compiler/rustc_hir_typeck/src/expr.rs b/compiler/rustc_hir_typeck/src/expr.rs index 9f3ff0b2d03c2..bf9a458d570fc 100644 --- a/compiler/rustc_hir_typeck/src/expr.rs +++ b/compiler/rustc_hir_typeck/src/expr.rs @@ -21,7 +21,7 @@ use rustc_hir::def_id::DefId; use rustc_hir::lang_items::LangItem; use rustc_hir::{ExprKind, HirId, QPath, find_attr, is_range_literal}; use rustc_hir_analysis::NoVariantNamed; -use rustc_hir_analysis::hir_ty_lowering::HirTyLowerer as _; +use rustc_hir_analysis::hir_ty_lowering::{HirTyLowerer as _, IsMethodCall}; use rustc_infer::infer::{self, DefineOpaqueTypes, InferOk, RegionVariableOrigin}; use rustc_infer::traits::query::NoSolution; use rustc_middle::ty::adjustment::{Adjust, Adjustment, AllowTwoPhase}; @@ -1494,6 +1494,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { self.check_argument_types( segment.ident.span, expr, + IsMethodCall::Yes, &method.sig.inputs()[1..], method.sig.output(), expected, @@ -1516,6 +1517,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { self.check_argument_types( segment.ident.span, expr, + IsMethodCall::Yes, &err_inputs, err_output, NoExpectation, diff --git a/compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs b/compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs index c07cbfae256dd..a892f075ba76a 100644 --- a/compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs +++ b/compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs @@ -10,7 +10,7 @@ use rustc_hir::def_id::DefId; use rustc_hir::intravisit::Visitor; use rustc_hir::{Expr, ExprKind, HirId, LangItem, Node, QPath, is_range_literal}; use rustc_hir_analysis::check::potentially_plural_count; -use rustc_hir_analysis::hir_ty_lowering::{HirTyLowerer, PermitVariants}; +use rustc_hir_analysis::hir_ty_lowering::{HirTyLowerer, IsMethodCall, PermitVariants}; use rustc_index::IndexVec; use rustc_infer::infer::{BoundRegionConversionTime, DefineOpaqueTypes, InferOk, TypeTrace}; use rustc_middle::ty::adjustment::AllowTwoPhase; @@ -195,6 +195,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { call_span: Span, // Expression of the call site call_expr: &'tcx hir::Expr<'tcx>, + is_method: IsMethodCall, // Types (as defined in the *signature* of the target function) formal_input_tys: &[Ty<'tcx>], formal_output: Ty<'tcx>, @@ -206,7 +207,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { c_variadic: bool, // Whether the arguments have been bundled in a tuple (ex: closures) tuple_arguments: TupleArgumentsFlag, - // The DefId for the function being called, for better error messages + // The DefId for the function being called, for callee bound checks and + // better error messages fn_def_id: Option, ) { let tcx = self.tcx; @@ -305,12 +307,104 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { }) .ok() }) - .unwrap_or_default(); + .unwrap_or_default() + .and_then(|expected_input_tys: Vec>| { + // Check the well-formedness of expected input tys, as using ill-formed + // expectation may cause type inference errors. + let well_formed = self.probe(|_| { + let ocx = ObligationCtxt::new(self); + for &ty in &expected_input_tys { + ocx.register_obligation(traits::Obligation::new( + self.tcx, + self.misc(call_span), + self.param_env, + ty::ClauseKind::WellFormed(ty.into()), + )); + } + ocx.try_evaluate_obligations().is_empty() + }); + well_formed.then_some(expected_input_tys) + }); let mut err_code = E0061; + let mut expected_meets_callee_bounds = Vec::with_capacity(formal_input_tys.len()); + expected_meets_callee_bounds.resize(formal_input_tys.len(), true); + + // Check whether the expected inputs satisfy the callee's where bounds. + // This is skipped for the old solver: attempting trait solving there can + // trigger an overflow, which is a fatal error in the old solver but is + // treated as mere ambiguity by the next solver. + if self.next_trait_solver() + && let Some(expected_input_tys) = &expected_input_tys + && let Some(fn_def_id) = fn_def_id + // We don't need to check bounds for closures as they are already in the current + // body's param env. + && self.tcx.def_kind(fn_def_id) != DefKind::Closure + { + self.probe(|_| { + let new_args = self.fresh_args_for_item(call_span, fn_def_id); + let fn_sig = self.tcx.fn_sig(fn_def_id).instantiate(self.tcx, new_args); + let fn_sig = self.instantiate_binder_with_fresh_vars( + call_span, + BoundRegionConversionTime::FnCall, + fn_sig, + ); + let ocx = ObligationCtxt::new(self); + let origin = self.misc(call_span); + let fn_sig = ocx.normalize(&origin, self.param_env, fn_sig); + + let bound_input_tys = fn_sig.inputs(); + let bound_input_tys = if is_method == IsMethodCall::Yes { + &bound_input_tys[1..] + } else { + &bound_input_tys[..] + }; + + let fn_bounds = self.tcx.predicates_of(fn_def_id).instantiate(self.tcx, new_args); + let fn_bounds = traits::predicates_for_generics( + |_, sp| self.misc(sp), + self.param_env, + fn_bounds, + ); + ocx.register_obligations(fn_bounds); + + // perf: We reuse this by cloning rather than repeating the above lines + let preds = ocx.into_pending_obligations(); + + assert_eq!(bound_input_tys.len(), formal_input_tys.len(),); + for idx in 0..formal_input_tys.len() { + let meets_bounds = self + .probe(|_| { + let ocx = ObligationCtxt::new(self); + ocx.register_obligations(preds.clone()); + ocx.eq( + &origin, + self.param_env, + bound_input_tys[idx], + expected_input_tys[idx], + )?; + if ocx.try_evaluate_obligations().is_empty() { + Ok(()) + } else { + Err(TypeError::Mismatch) + } + }) + .is_ok(); + expected_meets_callee_bounds[idx] = meets_bounds; + } + }); + } + // If the arguments should be wrapped in a tuple (ex: closures), unwrap them here let (formal_input_tys, expected_input_tys) = if tuple_arguments == TupleArguments { + // Since the expected inputs are unpacked from a single tuple, + // each input meets the callee bounds if and only if the tuple does. + expected_meets_callee_bounds.resize( + provided_args.len(), + expected_meets_callee_bounds.first().copied().unwrap_or(true), + ); + let tuple_type = self.structurally_resolve_type(call_span, formal_input_tys[0]); match tuple_type.kind() { // We expected a tuple and got a tuple @@ -373,7 +467,15 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { // We're on the happy path here, so we'll do a more involved check and write back types // To check compatibility, we'll do 3 things: // 1. Unify the provided argument with the expected type - let expectation = Expectation::rvalue_hint(self, expected_input_ty); + let expectation = if expected_meets_callee_bounds[idx] { + Expectation::rvalue_hint(self, expected_input_ty) + } else { + // If the expected input does not satisfy the callee's bounds, we must + // weaken the expectation; otherwise, coercing to a type that violates + // those bounds would result in a type mismatch. + // See https://github.com/rust-lang/rust/issues/149379. + Expectation::ExpectRvalueLikeUnsized(expected_input_ty) + }; let checked_ty = self.check_expr_with_expectation(provided_arg, expectation); diff --git a/tests/ui/coercion/fudge-inference/expectated-input-not-satisfying-fn-bounds-issue-149881.current.stderr b/tests/ui/coercion/fudge-inference/expectated-input-not-satisfying-fn-bounds-issue-149881.current.stderr new file mode 100644 index 0000000000000..75b430d891807 --- /dev/null +++ b/tests/ui/coercion/fudge-inference/expectated-input-not-satisfying-fn-bounds-issue-149881.current.stderr @@ -0,0 +1,22 @@ +error[E0277]: the size for values of type `[{integer}]` cannot be known at compilation time + --> $DIR/expectated-input-not-satisfying-fn-bounds-issue-149881.rs:16:24 + | +LL | <[_]>::into_vec(id(Box::new([0, 1, 2]))); + | -- ^^^^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time + | | + | required by a bound introduced by this call + | + = help: the trait `Sized` is not implemented for `[{integer}]` +note: required by an implicit `Sized` bound in `id` + --> $DIR/expectated-input-not-satisfying-fn-bounds-issue-149881.rs:11:7 + | +LL | fn id(x: Box) -> Box { + | ^ required by the implicit `Sized` requirement on this type parameter in `id` +help: consider relaxing the implicit `Sized` restriction + | +LL | fn id(x: Box) -> Box { + | ++++++++ + +error: aborting due to 1 previous error + +For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/coercion/fudge-inference/expectated-input-not-satisfying-fn-bounds-issue-149881.rs b/tests/ui/coercion/fudge-inference/expectated-input-not-satisfying-fn-bounds-issue-149881.rs new file mode 100644 index 0000000000000..1df450659c5a5 --- /dev/null +++ b/tests/ui/coercion/fudge-inference/expectated-input-not-satisfying-fn-bounds-issue-149881.rs @@ -0,0 +1,18 @@ +//@ revisions: current next +//@ ignore-compare-mode-next-solver (explicit revisions) +//@[next] compile-flags: -Znext-solver +//@[next] check-pass + +// FIXME(#149379): This should pass, but fails due to fudged expactation +// types which are potentially not well-formed or for whom the function +// where-bounds don't actually hold. And this results in weird bugs when +// later treating these expectations as if they were actually correct.. + +fn id(x: Box) -> Box { + x +} + +fn main() { + <[_]>::into_vec(id(Box::new([0, 1, 2]))); + //[current]~^ ERROR: the size for values of type `[{integer}]` cannot be known at compilation time +} diff --git a/tests/ui/coercion/fudge-inference/expectated-input-not-satisfying-fn-bounds-issue-89299.current.stderr b/tests/ui/coercion/fudge-inference/expectated-input-not-satisfying-fn-bounds-issue-89299.current.stderr new file mode 100644 index 0000000000000..3267bfc6cf900 --- /dev/null +++ b/tests/ui/coercion/fudge-inference/expectated-input-not-satisfying-fn-bounds-issue-89299.current.stderr @@ -0,0 +1,16 @@ +error[E0277]: `dyn Trait + Send` cannot be unpinned + --> $DIR/expectated-input-not-satisfying-fn-bounds-issue-89299.rs:21:27 + | +LL | let _x = Foo(Pin::new(&mut a)); + | -------- ^^^^^^ the trait `Unpin` is not implemented for `dyn Trait + Send` + | | + | required by a bound introduced by this call + | + = note: consider using the `pin!` macro + consider using `Box::pin` if you need to access the pinned value outside of the current scope +note: required by a bound in `Pin::::new` + --> $SRC_DIR/core/src/pin.rs:LL:COL + +error: aborting due to 1 previous error + +For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/coercion/fudge-inference/expectated-input-not-satisfying-fn-bounds-issue-89299.rs b/tests/ui/coercion/fudge-inference/expectated-input-not-satisfying-fn-bounds-issue-89299.rs new file mode 100644 index 0000000000000..a746cac238478 --- /dev/null +++ b/tests/ui/coercion/fudge-inference/expectated-input-not-satisfying-fn-bounds-issue-89299.rs @@ -0,0 +1,23 @@ +//@ revisions: current next +//@ ignore-compare-mode-next-solver (explicit revisions) +//@[next] compile-flags: -Znext-solver +//@[next] check-pass + +// FIXME(#149379): This should pass, but fails due to fudged expactation +// types which are potentially not well-formed or for whom the function +// where-bounds don't actually hold. And this results in weird bugs when +// later treating these expectations as if they were actually correct.. + +use std::pin::Pin; + +trait Trait {} + +impl Trait for i32 {} + +struct Foo<'a>(Pin<&'a mut (dyn Trait + Send)>); + +fn main() { + let mut a = 1; + let _x = Foo(Pin::new(&mut a)); + //[current]~^ ERROR: `dyn Trait + Send` cannot be unpinned +} diff --git a/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-1.current.stderr b/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-1.current.stderr deleted file mode 100644 index 426e0fe9e0d92..0000000000000 --- a/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-1.current.stderr +++ /dev/null @@ -1,32 +0,0 @@ -error[E0308]: mismatched types - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-1.rs:16:33 - | -LL | let _: Box = foo(((), ())); - | ^^ expected trait object, found `()` - | - = note: expected trait object `dyn Send` - found unit type `()` - -error[E0277]: the size for values of type `dyn Send` cannot be known at compilation time - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-1.rs:16:32 - | -LL | let _: Box = foo(((), ())); - | --- ^^^^^^^^ doesn't have a size known at compile-time - | | - | required by a bound introduced by this call - | - = help: the trait `Sized` is not implemented for `dyn Send` -note: required by an implicit `Sized` bound in `foo` - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-1.rs:10:8 - | -LL | fn foo(x: (T, ())) -> Box { - | ^ required by the implicit `Sized` requirement on this type parameter in `foo` -help: consider relaxing the implicit `Sized` restriction - | -LL | fn foo(x: (T, ())) -> Box { - | ++++++++ - -error: aborting due to 2 previous errors - -Some errors have detailed explanations: E0277, E0308. -For more information about an error, try `rustc --explain E0277`. diff --git a/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-1.next.stderr b/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-1.next.stderr deleted file mode 100644 index 426e0fe9e0d92..0000000000000 --- a/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-1.next.stderr +++ /dev/null @@ -1,32 +0,0 @@ -error[E0308]: mismatched types - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-1.rs:16:33 - | -LL | let _: Box = foo(((), ())); - | ^^ expected trait object, found `()` - | - = note: expected trait object `dyn Send` - found unit type `()` - -error[E0277]: the size for values of type `dyn Send` cannot be known at compilation time - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-1.rs:16:32 - | -LL | let _: Box = foo(((), ())); - | --- ^^^^^^^^ doesn't have a size known at compile-time - | | - | required by a bound introduced by this call - | - = help: the trait `Sized` is not implemented for `dyn Send` -note: required by an implicit `Sized` bound in `foo` - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-1.rs:10:8 - | -LL | fn foo(x: (T, ())) -> Box { - | ^ required by the implicit `Sized` requirement on this type parameter in `foo` -help: consider relaxing the implicit `Sized` restriction - | -LL | fn foo(x: (T, ())) -> Box { - | ++++++++ - -error: aborting due to 2 previous errors - -Some errors have detailed explanations: E0277, E0308. -For more information about an error, try `rustc --explain E0277`. diff --git a/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-1.rs b/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-1.rs index 070baf77783de..634e4b2d47924 100644 --- a/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-1.rs +++ b/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-1.rs @@ -1,11 +1,9 @@ //@ revisions: current next //@ ignore-compare-mode-next-solver (explicit revisions) //@[next] compile-flags: -Znext-solver +//@ check-pass -// FIXME(#149379): This should pass, but fails due to fudged expactation -// types which are potentially not well-formed or for whom the function -// where-bounds don't actually hold. And this results in weird bugs when -// later treating these expectations as if they were actually correct.. +// A regression test for https://github.com/rust-lang/rust/issues/149379. fn foo(x: (T, ())) -> Box { Box::new(x.0) @@ -14,6 +12,4 @@ fn foo(x: (T, ())) -> Box { fn main() { // Uses expectation as its struct tail is sized, resulting in `(dyn Send, ())` let _: Box = foo(((), ())); - //~^ ERROR mismatched types - //~| ERROR the size for values of type `dyn Send` cannot be known at compilation time } diff --git a/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-2.current.stderr b/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-2.current.stderr index 5bf77eb843a02..8900918e35065 100644 --- a/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-2.current.stderr +++ b/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-2.current.stderr @@ -1,5 +1,5 @@ error[E0277]: the size for values of type `dyn Send` cannot be known at compilation time - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-2.rs:15:38 + --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-2.rs:16:38 | LL | let _: Box = sized_box(Box::new(1)); | --------- ^^^^^^^^^^^ doesn't have a size known at compile-time @@ -8,7 +8,7 @@ LL | let _: Box = sized_box(Box::new(1)); | = help: the trait `Sized` is not implemented for `dyn Send` note: required by an implicit `Sized` bound in `sized_box` - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-2.rs:10:14 + --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-2.rs:11:14 | LL | fn sized_box(x: Box) -> Box { | ^ required by the implicit `Sized` requirement on this type parameter in `sized_box` diff --git a/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-2.next.stderr b/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-2.next.stderr deleted file mode 100644 index 5bf77eb843a02..0000000000000 --- a/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-2.next.stderr +++ /dev/null @@ -1,22 +0,0 @@ -error[E0277]: the size for values of type `dyn Send` cannot be known at compilation time - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-2.rs:15:38 - | -LL | let _: Box = sized_box(Box::new(1)); - | --------- ^^^^^^^^^^^ doesn't have a size known at compile-time - | | - | required by a bound introduced by this call - | - = help: the trait `Sized` is not implemented for `dyn Send` -note: required by an implicit `Sized` bound in `sized_box` - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-2.rs:10:14 - | -LL | fn sized_box(x: Box) -> Box { - | ^ required by the implicit `Sized` requirement on this type parameter in `sized_box` -help: consider relaxing the implicit `Sized` restriction - | -LL | fn sized_box(x: Box) -> Box { - | ++++++++ - -error: aborting due to 1 previous error - -For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-2.rs b/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-2.rs index 521d0338329e1..6df611e11d55d 100644 --- a/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-2.rs +++ b/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-2.rs @@ -1,6 +1,7 @@ //@ revisions: current next //@ ignore-compare-mode-next-solver (explicit revisions) //@[next] compile-flags: -Znext-solver +//@[next] check-pass // FIXME(#149379): This should pass, but fails due to fudged expactation // types which are potentially not well-formed or for whom the function @@ -13,5 +14,5 @@ fn sized_box(x: Box) -> Box { fn main() { let _: Box = sized_box(Box::new(1)); - //~^ ERROR the size for values of type `dyn Send` cannot be known at compilation time + //[current]~^ ERROR the size for values of type `dyn Send` cannot be known at compilation time } diff --git a/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.current.stderr b/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.current.stderr index abeee7fe68a1e..e39ff585ff95a 100644 --- a/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.current.stderr +++ b/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.current.stderr @@ -1,72 +1,5 @@ -error[E0277]: the size for values of type `dyn Send` cannot be known at compilation time - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:32:55 - | -LL | let _: Box = field_to_box1(Foo { field: 1, tail: () }); - | ^ doesn't have a size known at compile-time - | - = help: the trait `Sized` is not implemented for `dyn Send` -note: required by an implicit `Sized` bound in `Foo` - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:10:12 - | -LL | struct Foo { - | ^ required by the implicit `Sized` requirement on this type parameter in `Foo` -help: you could relax the implicit `Sized` bound on `T` if it were used through indirection like `&T` or `Box` - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:10:12 - | -LL | struct Foo { - | ^ this could be changed to `T: ?Sized`... -LL | field: T, - | - ...if indirection were used here: `Box` - -error[E0308]: mismatched types - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:32:55 - | -LL | let _: Box = field_to_box1(Foo { field: 1, tail: () }); - | ^ expected trait object, found integer - | - = note: expected trait object `dyn Send` - found type `{integer}` - -error[E0277]: the size for values of type `dyn Send` cannot be known at compilation time - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:32:42 - | -LL | let _: Box = field_to_box1(Foo { field: 1, tail: () }); - | ------------- ^^^^^^^^^^^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time - | | - | required by a bound introduced by this call - | - = help: the trait `Sized` is not implemented for `dyn Send` -note: required by an implicit `Sized` bound in `field_to_box1` - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:19:18 - | -LL | fn field_to_box1(x: Foo) -> Box { - | ^ required by the implicit `Sized` requirement on this type parameter in `field_to_box1` -help: consider relaxing the implicit `Sized` restriction - | -LL | fn field_to_box1(x: Foo) -> Box { - | ++++++++ - -error[E0277]: the size for values of type `dyn Send` cannot be known at compilation time - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:36:38 - | -LL | let _: &dyn Send = field_to_box2(&Bar { field: 1 }); - | ------------- ^^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time - | | - | required by a bound introduced by this call - | - = help: the trait `Sized` is not implemented for `dyn Send` -note: required by an implicit `Sized` bound in `field_to_box2` - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:23:18 - | -LL | fn field_to_box2(x: &Bar) -> &T { - | ^ required by the implicit `Sized` requirement on this type parameter in `field_to_box2` -help: consider relaxing the implicit `Sized` restriction - | -LL | fn field_to_box2(x: &Bar) -> &T { - | ++++++++ - error[E0308]: mismatched types - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:38:38 + --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:35:38 | LL | let _: &dyn Send = field_to_box3(&(1,)); | ------------- ^^^^^ expected `&(dyn Send,)`, found `&({integer},)` @@ -76,12 +9,11 @@ LL | let _: &dyn Send = field_to_box3(&(1,)); = note: expected reference `&(dyn Send,)` found reference `&({integer},)` note: function defined here - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:27:4 + --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:28:4 | LL | fn field_to_box3(x: &(T,)) -> &T { | ^^^^^^^^^^^^^ -------- -error: aborting due to 5 previous errors +error: aborting due to 1 previous error -Some errors have detailed explanations: E0277, E0308. -For more information about an error, try `rustc --explain E0277`. +For more information about this error, try `rustc --explain E0308`. diff --git a/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.next.stderr b/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.next.stderr deleted file mode 100644 index abeee7fe68a1e..0000000000000 --- a/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.next.stderr +++ /dev/null @@ -1,87 +0,0 @@ -error[E0277]: the size for values of type `dyn Send` cannot be known at compilation time - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:32:55 - | -LL | let _: Box = field_to_box1(Foo { field: 1, tail: () }); - | ^ doesn't have a size known at compile-time - | - = help: the trait `Sized` is not implemented for `dyn Send` -note: required by an implicit `Sized` bound in `Foo` - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:10:12 - | -LL | struct Foo { - | ^ required by the implicit `Sized` requirement on this type parameter in `Foo` -help: you could relax the implicit `Sized` bound on `T` if it were used through indirection like `&T` or `Box` - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:10:12 - | -LL | struct Foo { - | ^ this could be changed to `T: ?Sized`... -LL | field: T, - | - ...if indirection were used here: `Box` - -error[E0308]: mismatched types - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:32:55 - | -LL | let _: Box = field_to_box1(Foo { field: 1, tail: () }); - | ^ expected trait object, found integer - | - = note: expected trait object `dyn Send` - found type `{integer}` - -error[E0277]: the size for values of type `dyn Send` cannot be known at compilation time - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:32:42 - | -LL | let _: Box = field_to_box1(Foo { field: 1, tail: () }); - | ------------- ^^^^^^^^^^^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time - | | - | required by a bound introduced by this call - | - = help: the trait `Sized` is not implemented for `dyn Send` -note: required by an implicit `Sized` bound in `field_to_box1` - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:19:18 - | -LL | fn field_to_box1(x: Foo) -> Box { - | ^ required by the implicit `Sized` requirement on this type parameter in `field_to_box1` -help: consider relaxing the implicit `Sized` restriction - | -LL | fn field_to_box1(x: Foo) -> Box { - | ++++++++ - -error[E0277]: the size for values of type `dyn Send` cannot be known at compilation time - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:36:38 - | -LL | let _: &dyn Send = field_to_box2(&Bar { field: 1 }); - | ------------- ^^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time - | | - | required by a bound introduced by this call - | - = help: the trait `Sized` is not implemented for `dyn Send` -note: required by an implicit `Sized` bound in `field_to_box2` - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:23:18 - | -LL | fn field_to_box2(x: &Bar) -> &T { - | ^ required by the implicit `Sized` requirement on this type parameter in `field_to_box2` -help: consider relaxing the implicit `Sized` restriction - | -LL | fn field_to_box2(x: &Bar) -> &T { - | ++++++++ - -error[E0308]: mismatched types - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:38:38 - | -LL | let _: &dyn Send = field_to_box3(&(1,)); - | ------------- ^^^^^ expected `&(dyn Send,)`, found `&({integer},)` - | | - | arguments to this function are incorrect - | - = note: expected reference `&(dyn Send,)` - found reference `&({integer},)` -note: function defined here - --> $DIR/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs:27:4 - | -LL | fn field_to_box3(x: &(T,)) -> &T { - | ^^^^^^^^^^^^^ -------- - -error: aborting due to 5 previous errors - -Some errors have detailed explanations: E0277, E0308. -For more information about an error, try `rustc --explain E0277`. diff --git a/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs b/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs index 7df7878d6d594..a9894b41f86e9 100644 --- a/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs +++ b/tests/ui/coercion/fudge-inference/fn-ret-trait-object-propagated-to-inputs-issue-149379-3.rs @@ -1,6 +1,7 @@ //@ revisions: current next //@ ignore-compare-mode-next-solver (explicit revisions) //@[next] compile-flags: -Znext-solver +//@[next] check-pass // FIXME(#149379): This should pass, but fails due to fudged expactation // types which are potentially not well-formed or for whom the function @@ -30,11 +31,7 @@ fn field_to_box3(x: &(T,)) -> &T { fn main() { let _: Box = field_to_box1(Foo { field: 1, tail: () }); - //~^ ERROR the size for values of type `dyn Send` cannot be known at compilation time - //~| ERROR the size for values of type `dyn Send` cannot be known at compilation time - //~| ERROR mismatched types let _: &dyn Send = field_to_box2(&Bar { field: 1 }); - //~^ ERROR the size for values of type `dyn Send` cannot be known at compilation time let _: &dyn Send = field_to_box3(&(1,)); - //~^ ERROR mismatched types + //[current]~^ ERROR mismatched types }