fn trans_trait_callee<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
                                  opaque_fn_ty: Ty<'tcx>,
                                  vtable_index: usize,
                                  self_expr: &hir::Expr,
                                  arg_cleanup_scope: cleanup::ScopeId)
                                  -> Callee<'blk, 'tcx> {
    let _icx = push_ctxt("meth::trans_trait_callee");
    let mut bcx = bcx;

    // Translate self_datum and take ownership of the value by
    // converting to an rvalue.
    let self_datum = unpack_datum!(
        bcx, expr::trans(bcx, self_expr));

    let llval = if bcx.fcx.type_needs_drop(self_datum.ty) {
        let self_datum = unpack_datum!(
            bcx, self_datum.to_rvalue_datum(bcx, "trait_callee"));

        // Convert to by-ref since `trans_trait_callee_from_llval` wants it
        // that way.
        let self_datum = unpack_datum!(
            bcx, self_datum.to_ref_datum(bcx));

        // Arrange cleanup in case something should go wrong before the
        // actual call occurs.
        self_datum.add_clean(bcx.fcx, arg_cleanup_scope)
    } else {
        // We don't have to do anything about cleanups for &Trait and &mut Trait.
        assert!(self_datum.kind.is_by_ref());
        self_datum.val
    };

    let llself = Load(bcx, expr::get_dataptr(bcx, llval));
    let llvtable = Load(bcx, expr::get_meta(bcx, llval));
    trans_trait_callee_from_llval(bcx, opaque_fn_ty, vtable_index, llself, llvtable)
}
/// Create a method callee where the method is coming from a trait object (e.g., Box<Trait> type).
/// In this case, we must pull the fn pointer out of the vtable that is packaged up with the
/// object. Objects are represented as a pair, so we first evaluate the self expression and then
/// extract the self data and vtable out of the pair.
Create a method callee where the method is coming from a trait object .
In this case, we must pull the fn pointer out of the vtable that is packaged up with the
object. Objects are represented as a pair, so we first evaluate the self expression and then
extract the self data and vtable out of the pair.
Create a method callee where the method is coming from a trait object . In this case we must pull the fn pointer out of the vtable that is packaged up with the object . Objects are represented as a pair so we first evaluate the self expression and then extract the self data and vtable out of the pair .
fn trans_trait_callee<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
                                  opaque_fn_ty: Ty<'tcx>,
                                  vtable_index: usize,
                                  self_expr: &hir::Expr,
                                  arg_cleanup_scope: cleanup::ScopeId)
                                  -> Callee<'blk, 'tcx> {
    let _icx = push_ctxt("meth::trans_trait_callee");
    let mut bcx = bcx;
    // Translate self_datum and take ownership of the value by
    // converting to an rvalue.
    let self_datum = unpack_datum!(
        bcx, expr::trans(bcx, self_expr));
    let llval = if bcx.fcx.type_needs_drop(self_datum.ty) {
        let self_datum = unpack_datum!(
            bcx, self_datum.to_rvalue_datum(bcx, "trait_callee"));
        // Convert to by-ref since `trans_trait_callee_from_llval` wants it
        // that way.
        let self_datum = unpack_datum!(
            bcx, self_datum.to_ref_datum(bcx));
        // Arrange cleanup in case something should go wrong before the
        // actual call occurs.
        self_datum.add_clean(bcx.fcx, arg_cleanup_scope)
    } else {
        // We don't have to do anything about cleanups for &Trait and &mut Trait.
        assert!(self_datum.kind.is_by_ref());
        self_datum.val
    };
    let llself = Load(bcx, expr::get_dataptr(bcx, llval));
    let llvtable = Load(bcx, expr::get_meta(bcx, llval));
    trans_trait_callee_from_llval(bcx, opaque_fn_ty, vtable_index, llself, llvtable)
}
fn trans_trait_callee < ' blk , ' tcx > ( bcx : Block < ' blk , ' tcx > , opaque_fn_ty : Ty < ' tcx > , vtable_index : usize , self_expr : & hir :: Expr , arg_cleanup_scope : cleanup :: ScopeId ) -> Callee < ' blk , ' tcx > { let _icx = push_ctxt ( " " ) ; let mut bcx = bcx ; // Translate self_datum and take ownership of the value by // converting to an rvalue. let self_datum = unpack_datum ! ( bcx expr trans ( bcx self_expr ) ) ; let llval = if bcx . fcx . type_needs_drop ( self_datum . ty ) { let self_datum = unpack_datum ! ( bcx self_datum to_rvalue_datum ( bcx " " ) ) ; // Convert to by-ref since `trans_trait_callee_from_llval` wants it // that way. let self_datum = unpack_datum ! ( bcx self_datum to_ref_datum ( bcx ) ) ; // Arrange cleanup in case something should go wrong before the // actual call occurs. self_datum . add_clean ( bcx . fcx , arg_cleanup_scope ) } else { // We don't have to do anything about cleanups for &Trait and &mut Trait. assert ! ( self_datum kind is_by_ref ( ) ) ; self_datum . val } ; let llself = Load ( bcx , expr :: get_dataptr ( bcx , llval ) ) ; let llvtable = Load ( bcx , expr :: get_meta ( bcx , llval ) ) ; trans_trait_callee_from_llval ( bcx , opaque_fn_ty , vtable_index , llself , llvtable ) }
Create a method callee where the method is coming from a trait object (e.g., Box<Trait> type).
Create a method callee where the method is coming from a trait object ( e . g . Box<Trait > type ) .
bcx
Block<'blk, 'tcx>
opaque_fn_ty
Ty<'tcx>
vtable_index
usize
self_expr
&hir::Expr
arg_cleanup_scope
cleanup::ScopeId
bcx
Block<'blk, 'tcx>
opaque_fn_ty
Ty<'tcx>
vtable_index
usize
self_expr
&hir::Expr
arg_cleanup_scope
cleanup::ScopeId