Skip to content

Commit 3d8ef7a

Browse files
authored
Rollup merge of rust-lang#140713 - compiler-errors:check_ref_cast, r=lcnr
Structurally resolve in `check_ref_cast` in new solver Fixes rust-lang/trait-system-refactor-initiative#203 r? lcnr
2 parents 8984d65 + 636a138 commit 3d8ef7a

File tree

2 files changed

+29
-8
lines changed

2 files changed

+29
-8
lines changed

compiler/rustc_hir_typeck/src/cast.rs

+7-8
Original file line numberDiff line numberDiff line change
@@ -1051,20 +1051,19 @@ impl<'a, 'tcx> CastCheck<'tcx> {
10511051
fn check_ref_cast(
10521052
&self,
10531053
fcx: &FnCtxt<'a, 'tcx>,
1054-
m_expr: ty::TypeAndMut<'tcx>,
1055-
m_cast: ty::TypeAndMut<'tcx>,
1054+
mut m_expr: ty::TypeAndMut<'tcx>,
1055+
mut m_cast: ty::TypeAndMut<'tcx>,
10561056
) -> Result<CastKind, CastError<'tcx>> {
10571057
// array-ptr-cast: allow mut-to-mut, mut-to-const, const-to-const
1058+
m_expr.ty = fcx.try_structurally_resolve_type(self.expr_span, m_expr.ty);
1059+
m_cast.ty = fcx.try_structurally_resolve_type(self.cast_span, m_cast.ty);
1060+
10581061
if m_expr.mutbl >= m_cast.mutbl
10591062
&& let ty::Array(ety, _) = m_expr.ty.kind()
10601063
&& fcx.can_eq(fcx.param_env, *ety, m_cast.ty)
10611064
{
1062-
// Due to the limitations of LLVM global constants,
1063-
// region pointers end up pointing at copies of
1064-
// vector elements instead of the original values.
1065-
// To allow raw pointers to work correctly, we
1066-
// need to special-case obtaining a raw pointer
1067-
// from a region pointer to a vector.
1065+
// Due to historical reasons we allow directly casting references of
1066+
// arrays into raw pointers of their element type.
10681067

10691068
// Coerce to a raw pointer so that we generate RawPtr in MIR.
10701069
let array_ptr_type = Ty::new_ptr(fcx.tcx, m_expr.ty, m_expr.mutbl);
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
//@ check-pass
2+
//@ revisions: current next
3+
//@ ignore-compare-mode-next-solver (explicit revisions)
4+
//@[next] compile-flags: -Znext-solver
5+
6+
// Regression test for <https://github.com/rust-lang/trait-system-refactor-initiative/issues/203>.
7+
// Test that we structually normalize in the hacky `&[T; N] -> *const T` in cast.
8+
9+
trait Mirror {
10+
type Assoc: ?Sized;
11+
}
12+
impl<T: ?Sized> Mirror for T {
13+
type Assoc = T;
14+
}
15+
16+
struct W<'a>(&'a <[f32; 0] as Mirror>::Assoc);
17+
18+
fn foo(x: W<'_>) -> *const f32 {
19+
x.0 as *const f32
20+
}
21+
22+
fn main() {}

0 commit comments

Comments
 (0)