Skip to content
This repository was archived by the owner on May 28, 2025. It is now read-only.

Commit 0209485

Browse files
committed
Auto merge of rust-lang#100966 - compiler-errors:revert-remove-deferred-sized-checks, r=pnkfelix
Revert "Remove deferred sized checks" cc: rust-lang#100652 (comment) I'm okay with reverting this for now, and I will look into the diagnostic regressions. This reverts commit 33212bf. r? `@pnkfelix` ---- EDIT: This _also_ fixes rust-lang#101066, a regression in method selection logic/coercion(?) due to the early registering of a `Sized` bound.
2 parents 8c6ce6b + eda91d9 commit 0209485

File tree

18 files changed

+247
-35
lines changed

18 files changed

+247
-35
lines changed

compiler/rustc_typeck/src/check/expr.rs

Lines changed: 5 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -560,17 +560,16 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
560560
// We just want to check sizedness, so instead of introducing
561561
// placeholder lifetimes with probing, we just replace higher lifetimes
562562
// with fresh vars.
563-
let arg_span = args.get(i).map(|a| a.span);
564-
let span = arg_span.unwrap_or(expr.span);
563+
let span = args.get(i).map(|a| a.span).unwrap_or(expr.span);
565564
let input = self.replace_bound_vars_with_fresh_vars(
566565
span,
567566
infer::LateBoundRegionConversionTime::FnCall,
568567
fn_sig.input(i),
569568
);
570-
self.require_type_is_sized(
571-
self.normalize_associated_types_in(span, input),
569+
self.require_type_is_sized_deferred(
570+
input,
572571
span,
573-
traits::SizedArgumentType(arg_span),
572+
traits::SizedArgumentType(None),
574573
);
575574
}
576575
}
@@ -585,11 +584,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
585584
infer::LateBoundRegionConversionTime::FnCall,
586585
fn_sig.output(),
587586
);
588-
self.require_type_is_sized(
589-
self.normalize_associated_types_in(expr.span, output),
590-
expr.span,
591-
traits::SizedReturnType,
592-
);
587+
self.require_type_is_sized_deferred(output, expr.span, traits::SizedReturnType);
593588
}
594589

595590
// We always require that the type provided as the value for

compiler/rustc_typeck/src/check/fn_ctxt/_impl.rs

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -439,6 +439,17 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
439439
}
440440
}
441441

442+
pub fn require_type_is_sized_deferred(
443+
&self,
444+
ty: Ty<'tcx>,
445+
span: Span,
446+
code: traits::ObligationCauseCode<'tcx>,
447+
) {
448+
if !ty.references_error() {
449+
self.deferred_sized_obligations.borrow_mut().push((ty, span, code));
450+
}
451+
}
452+
442453
pub fn register_bound(
443454
&self,
444455
ty: Ty<'tcx>,

compiler/rustc_typeck/src/check/inherited.rs

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,12 @@ pub struct Inherited<'a, 'tcx> {
3838

3939
pub(super) fulfillment_cx: RefCell<Box<dyn TraitEngine<'tcx>>>,
4040

41+
// Some additional `Sized` obligations badly affect type inference.
42+
// These obligations are added in a later stage of typeck.
43+
// Removing these may also cause additional complications, see #101066.
44+
pub(super) deferred_sized_obligations:
45+
RefCell<Vec<(Ty<'tcx>, Span, traits::ObligationCauseCode<'tcx>)>>,
46+
4147
// When we process a call like `c()` where `c` is a closure type,
4248
// we may not have decided yet whether `c` is a `Fn`, `FnMut`, or
4349
// `FnOnce` closure. In that case, we defer full resolution of the
@@ -137,6 +143,7 @@ impl<'a, 'tcx> Inherited<'a, 'tcx> {
137143
infcx,
138144
fulfillment_cx: RefCell::new(<dyn TraitEngine<'_>>::new(tcx)),
139145
locals: RefCell::new(Default::default()),
146+
deferred_sized_obligations: RefCell::new(Vec::new()),
140147
deferred_call_resolutions: RefCell::new(Default::default()),
141148
deferred_cast_checks: RefCell::new(Vec::new()),
142149
deferred_transmute_checks: RefCell::new(Vec::new()),

compiler/rustc_typeck/src/check/mod.rs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -464,6 +464,11 @@ fn typeck_with_fallback<'tcx>(
464464
fcx.resolve_rvalue_scopes(def_id.to_def_id());
465465
fcx.resolve_generator_interiors(def_id.to_def_id());
466466

467+
for (ty, span, code) in fcx.deferred_sized_obligations.borrow_mut().drain(..) {
468+
let ty = fcx.normalize_ty(span, ty);
469+
fcx.require_type_is_sized(ty, span, code);
470+
}
471+
467472
fcx.select_all_obligations_or_error();
468473

469474
if !fcx.infcx.is_tainted_by_errors() {

src/test/incremental/const-generics/hash-tyvid-regression-1.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ where
99
use std::convert::TryFrom;
1010
<[T; N.get()]>::try_from(())
1111
//~^ error: the trait bound
12+
//~| error: the trait bound
1213
//~| error: mismatched types
1314
}
1415

src/test/ui/associated-types/associated-types-path-2.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,12 +29,14 @@ pub fn f1_uint_uint() {
2929
f1(2u32, 4u32);
3030
//~^ ERROR `u32: Foo` is not satisfied
3131
//~| ERROR `u32: Foo` is not satisfied
32+
//~| ERROR `u32: Foo` is not satisfied
3233
}
3334

3435
pub fn f1_uint_int() {
3536
f1(2u32, 4i32);
3637
//~^ ERROR `u32: Foo` is not satisfied
3738
//~| ERROR `u32: Foo` is not satisfied
39+
//~| ERROR `u32: Foo` is not satisfied
3840
}
3941

4042
pub fn f2_int() {

src/test/ui/associated-types/associated-types-path-2.stderr

Lines changed: 20 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,14 @@ note: required by a bound in `f1`
3131
LL | pub fn f1<T: Foo>(a: T, x: T::A) {}
3232
| ^^^ required by this bound in `f1`
3333

34+
error[E0277]: the trait bound `u32: Foo` is not satisfied
35+
--> $DIR/associated-types-path-2.rs:29:5
36+
|
37+
LL | f1(2u32, 4u32);
38+
| ^^^^^^^^^^^^^^ the trait `Foo` is not implemented for `u32`
39+
|
40+
= help: the trait `Foo` is implemented for `i32`
41+
3442
error[E0277]: the trait bound `u32: Foo` is not satisfied
3543
--> $DIR/associated-types-path-2.rs:29:14
3644
|
@@ -40,7 +48,7 @@ LL | f1(2u32, 4u32);
4048
= help: the trait `Foo` is implemented for `i32`
4149

4250
error[E0277]: the trait bound `u32: Foo` is not satisfied
43-
--> $DIR/associated-types-path-2.rs:35:8
51+
--> $DIR/associated-types-path-2.rs:36:8
4452
|
4553
LL | f1(2u32, 4i32);
4654
| -- ^^^^ the trait `Foo` is not implemented for `u32`
@@ -55,15 +63,23 @@ LL | pub fn f1<T: Foo>(a: T, x: T::A) {}
5563
| ^^^ required by this bound in `f1`
5664

5765
error[E0277]: the trait bound `u32: Foo` is not satisfied
58-
--> $DIR/associated-types-path-2.rs:35:14
66+
--> $DIR/associated-types-path-2.rs:36:5
67+
|
68+
LL | f1(2u32, 4i32);
69+
| ^^^^^^^^^^^^^^ the trait `Foo` is not implemented for `u32`
70+
|
71+
= help: the trait `Foo` is implemented for `i32`
72+
73+
error[E0277]: the trait bound `u32: Foo` is not satisfied
74+
--> $DIR/associated-types-path-2.rs:36:14
5975
|
6076
LL | f1(2u32, 4i32);
6177
| ^^^^ the trait `Foo` is not implemented for `u32`
6278
|
6379
= help: the trait `Foo` is implemented for `i32`
6480

6581
error[E0308]: mismatched types
66-
--> $DIR/associated-types-path-2.rs:41:18
82+
--> $DIR/associated-types-path-2.rs:43:18
6783
|
6884
LL | let _: i32 = f2(2i32);
6985
| --- ^^^^^^^^ expected `i32`, found `u32`
@@ -75,7 +91,7 @@ help: you can convert a `u32` to an `i32` and panic if the converted value doesn
7591
LL | let _: i32 = f2(2i32).try_into().unwrap();
7692
| ++++++++++++++++++++
7793

78-
error: aborting due to 6 previous errors
94+
error: aborting due to 8 previous errors
7995

8096
Some errors have detailed explanations: E0277, E0308.
8197
For more information about an error, try `rustc --explain E0277`.

src/test/ui/coercion/issue-101066.rs

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
// check-pass
2+
3+
use std::convert::TryFrom;
4+
5+
pub trait FieldElement {
6+
type Integer: TryFrom<usize, Error = std::num::TryFromIntError>;
7+
8+
fn valid_integer_try_from<N>(i: N) -> Result<Self::Integer, ()>
9+
where
10+
Self::Integer: TryFrom<N>,
11+
{
12+
Self::Integer::try_from(i).map_err(|_| ())
13+
}
14+
}
15+
16+
fn main() {}

src/test/ui/feature-gates/feature-gate-unsized_fn_params.stderr

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -18,11 +18,8 @@ LL | foo(*x);
1818
| ^^ doesn't have a size known at compile-time
1919
|
2020
= help: the trait `Sized` is not implemented for `(dyn Foo + 'static)`
21+
= note: all function arguments must have a statically known size
2122
= help: unsized fn params are gated as an unstable feature
22-
help: function arguments must have a statically known size, borrowed types always have a known size
23-
|
24-
LL | foo(&*x);
25-
| +
2623

2724
error: aborting due to 2 previous errors
2825

src/test/ui/iterators/issue-28098.rs

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,15 @@
11
fn main() {
22
let _ = Iterator::next(&mut ());
33
//~^ ERROR `()` is not an iterator
4+
//~| ERROR `()` is not an iterator
5+
//~| ERROR `()` is not an iterator
46

57
for _ in false {}
68
//~^ ERROR `bool` is not an iterator
79

810
let _ = Iterator::next(&mut ());
911
//~^ ERROR `()` is not an iterator
12+
//~| ERROR `()` is not an iterator
1013

1114
other()
1215
}
@@ -16,9 +19,12 @@ pub fn other() {
1619

1720
let _ = Iterator::next(&mut ());
1821
//~^ ERROR `()` is not an iterator
22+
//~| ERROR `()` is not an iterator
23+
//~| ERROR `()` is not an iterator
1924

2025
let _ = Iterator::next(&mut ());
2126
//~^ ERROR `()` is not an iterator
27+
//~| ERROR `()` is not an iterator
2228

2329
for _ in false {}
2430
//~^ ERROR `bool` is not an iterator

0 commit comments

Comments
 (0)