Skip to content

Commit 4810cf1

Browse files
committed
rustc_mir: don't hardcode InstanceDef::VtableShim behavior to Adjustment::DerefMove.
1 parent 552ea44 commit 4810cf1

File tree

1 file changed

+24
-18
lines changed

1 file changed

+24
-18
lines changed

src/librustc_mir/shim.rs

Lines changed: 24 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@ fn make_shim<'tcx>(tcx: TyCtxt<'tcx>, instance: ty::InstanceDef<'tcx>) -> &'tcx
3535
ty::InstanceDef::VtableShim(def_id) => {
3636
build_call_shim(
3737
tcx,
38-
def_id,
38+
instance,
3939
Adjustment::DerefMove,
4040
CallKind::Direct(def_id),
4141
None,
@@ -60,7 +60,7 @@ fn make_shim<'tcx>(tcx: TyCtxt<'tcx>, instance: ty::InstanceDef<'tcx>) -> &'tcx
6060

6161
build_call_shim(
6262
tcx,
63-
def_id,
63+
instance,
6464
adjustment,
6565
CallKind::Indirect,
6666
Some(arg_tys)
@@ -74,13 +74,13 @@ fn make_shim<'tcx>(tcx: TyCtxt<'tcx>, instance: ty::InstanceDef<'tcx>) -> &'tcx
7474
ty::InstanceDef::ReifyShim(def_id) => {
7575
build_call_shim(
7676
tcx,
77-
def_id,
77+
instance,
7878
Adjustment::Identity,
7979
CallKind::Direct(def_id),
8080
None
8181
)
8282
}
83-
ty::InstanceDef::ClosureOnceShim { call_once } => {
83+
ty::InstanceDef::ClosureOnceShim { call_once: _ } => {
8484
let fn_mut = tcx.lang_items().fn_mut_trait().unwrap();
8585
let call_mut = tcx
8686
.associated_items(fn_mut)
@@ -89,7 +89,7 @@ fn make_shim<'tcx>(tcx: TyCtxt<'tcx>, instance: ty::InstanceDef<'tcx>) -> &'tcx
8989

9090
build_call_shim(
9191
tcx,
92-
call_once,
92+
instance,
9393
Adjustment::RefMut,
9494
CallKind::Direct(call_mut),
9595
None
@@ -697,25 +697,38 @@ impl CloneShimBuilder<'tcx> {
697697
}
698698
}
699699

700-
/// Builds a "call" shim for `def_id`. The shim calls the
700+
/// Builds a "call" shim for `instance`. The shim calls the
701701
/// function specified by `call_kind`, first adjusting its first
702702
/// argument according to `rcvr_adjustment`.
703703
///
704704
/// If `untuple_args` is a vec of types, the second argument of the
705705
/// function will be untupled as these types.
706706
fn build_call_shim<'tcx>(
707707
tcx: TyCtxt<'tcx>,
708-
def_id: DefId,
708+
instance: ty::InstanceDef<'tcx>,
709709
rcvr_adjustment: Adjustment,
710710
call_kind: CallKind,
711711
untuple_args: Option<&[Ty<'tcx>]>,
712712
) -> BodyCache<'tcx> {
713-
debug!("build_call_shim(def_id={:?}, rcvr_adjustment={:?}, \
713+
debug!("build_call_shim(instance={:?}, rcvr_adjustment={:?}, \
714714
call_kind={:?}, untuple_args={:?})",
715-
def_id, rcvr_adjustment, call_kind, untuple_args);
715+
instance, rcvr_adjustment, call_kind, untuple_args);
716716

717+
let def_id = instance.def_id();
717718
let sig = tcx.fn_sig(def_id);
718-
let sig = tcx.erase_late_bound_regions(&sig);
719+
let mut sig = tcx.erase_late_bound_regions(&sig);
720+
721+
// FIXME(eddyb) avoid having this snippet both here and in
722+
// `Instance::fn_sig` (introduce `InstanceDef::fn_sig`?).
723+
if let ty::InstanceDef::VtableShim(..) = instance {
724+
// Modify fn(self, ...) to fn(self: *mut Self, ...)
725+
let mut inputs_and_output = sig.inputs_and_output.to_vec();
726+
let self_arg = &mut inputs_and_output[0];
727+
debug_assert!(tcx.generics_of(def_id).has_self && *self_arg == tcx.types.self_param);
728+
*self_arg = tcx.mk_mut_ptr(*self_arg);
729+
sig.inputs_and_output = tcx.intern_type_list(&inputs_and_output);
730+
}
731+
719732
let span = tcx.def_span(def_id);
720733

721734
debug!("build_call_shim: sig={:?}", sig);
@@ -730,14 +743,7 @@ fn build_call_shim<'tcx>(
730743
let rcvr = match rcvr_adjustment {
731744
Adjustment::Identity => Operand::Move(rcvr_l),
732745
Adjustment::Deref => Operand::Copy(tcx.mk_place_deref(rcvr_l)),
733-
Adjustment::DerefMove => {
734-
// fn(Self, ...) -> fn(*mut Self, ...)
735-
let arg_ty = local_decls[rcvr_arg].ty;
736-
debug_assert!(tcx.generics_of(def_id).has_self && arg_ty == tcx.types.self_param);
737-
local_decls[rcvr_arg].ty = tcx.mk_mut_ptr(arg_ty);
738-
739-
Operand::Move(tcx.mk_place_deref(rcvr_l))
740-
}
746+
Adjustment::DerefMove => Operand::Move(tcx.mk_place_deref(rcvr_l)),
741747
Adjustment::RefMut => {
742748
// let rcvr = &mut rcvr;
743749
let ref_rcvr = local_decls.push(temp_decl(

0 commit comments

Comments
 (0)