Skip to content

Commit c49fc91

Browse files
authoredFeb 7, 2025
Rollup merge of #135179 - compiler-errors:arbitrary-self-types-object, r=BoxyUwU
Make sure to use `Receiver` trait when extracting object method candidate In method confirmation, the `extract_existential_trait_ref` function re-extracts the object type by derefing until it reaches an object. If we're assembling methods via the `Receiver` trait, make sure we re-do our work also using the receiver trait. Fixes #135155 cc ``@adetaylor``
2 parents 64e06c0 + 999695b commit c49fc91

File tree

2 files changed

+44
-3
lines changed

2 files changed

+44
-3
lines changed
 

‎compiler/rustc_hir_typeck/src/method/confirm.rs

+11-3
Original file line numberDiff line numberDiff line change
@@ -347,9 +347,17 @@ impl<'a, 'tcx> ConfirmContext<'a, 'tcx> {
347347
// yield an object-type (e.g., `&Object` or `Box<Object>`
348348
// etc).
349349

350-
// FIXME: this feels, like, super dubious
351-
self.fcx
352-
.autoderef(self.span, self_ty)
350+
let mut autoderef = self.fcx.autoderef(self.span, self_ty);
351+
352+
// We don't need to gate this behind arbitrary self types
353+
// per se, but it does make things a bit more gated.
354+
if self.tcx.features().arbitrary_self_types()
355+
|| self.tcx.features().arbitrary_self_types_pointers()
356+
{
357+
autoderef = autoderef.use_receiver_trait();
358+
}
359+
360+
autoderef
353361
.include_raw_pointers()
354362
.find_map(|(ty, _)| match ty.kind() {
355363
ty::Dynamic(data, ..) => Some(closure(
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
//@ check-pass
2+
3+
#![feature(derive_coerce_pointee)]
4+
#![feature(arbitrary_self_types)]
5+
6+
use std::marker::CoercePointee;
7+
use std::ops::Receiver;
8+
9+
// `CoercePointee` isn't needed here, it's just a simpler
10+
// (and more conceptual) way of deriving `DispatchFromDyn`.
11+
// You could think of `MyDispatcher` as a smart pointer
12+
// that just doesn't deref to its target type.
13+
#[derive(CoercePointee)]
14+
#[repr(transparent)]
15+
struct MyDispatcher<T: ?Sized>(*const T);
16+
17+
impl<T: ?Sized> Receiver for MyDispatcher<T> {
18+
type Target = T;
19+
}
20+
struct Test;
21+
22+
trait Trait {
23+
fn test(self: MyDispatcher<Self>);
24+
}
25+
26+
impl Trait for Test {
27+
fn test(self: MyDispatcher<Self>) {
28+
todo!()
29+
}
30+
}
31+
fn main() {
32+
MyDispatcher::<dyn Trait>(core::ptr::null_mut::<Test>()).test();
33+
}

0 commit comments

Comments
 (0)
Please sign in to comment.