From 0d16dcfce11ef524f34f8179352d2dc701808cfc Mon Sep 17 00:00:00 2001 From: bjorn3 Date: Sun, 3 Feb 2019 13:29:04 +0100 Subject: [PATCH] Don't try to store func_addr for FnDef in trans_const_value This would crash, because the place provides 0 bytes of space for FnDef --- src/base.rs | 12 ++++++++++-- src/constant.rs | 11 +++++------ 2 files changed, 15 insertions(+), 8 deletions(-) diff --git a/src/base.rs b/src/base.rs index 0d130bb8a1b8..ef96b89f7995 100644 --- a/src/base.rs +++ b/src/base.rs @@ -474,9 +474,17 @@ fn trans_stmt<'a, 'tcx: 'a>( lval.write_cvalue(fx, CValue::ByVal(res, layout)); } Rvalue::Cast(CastKind::ReifyFnPointer, operand, ty) => { - let operand = trans_operand(fx, operand); let layout = fx.layout_of(ty); - lval.write_cvalue(fx, operand.unchecked_cast_to(layout)); + match fx.monomorphize(&operand.ty(&fx.mir.local_decls, fx.tcx)).sty { + ty::FnDef(def_id, substs) => { + let func_ref = fx.get_function_ref( + Instance::resolve(fx.tcx, ParamEnv::reveal_all(), def_id, substs).unwrap(), + ); + let func_addr = fx.bcx.ins().func_addr(fx.pointer_type, func_ref); + lval.write_cvalue(fx, CValue::ByVal(func_addr, layout)); + } + _ => bug!("Trying to ReifyFnPointer on non FnDef {:?}", ty), + } } Rvalue::Cast(CastKind::UnsafeFnPointer, operand, ty) => { let operand = trans_operand(fx, operand); diff --git a/src/constant.rs b/src/constant.rs index 6411e3d8563b..1af5a2868819 100644 --- a/src/constant.rs +++ b/src/constant.rs @@ -110,12 +110,11 @@ fn trans_const_value<'a, 'tcx: 'a>( let bits = const_.val.try_to_bits(layout.size).unwrap(); CValue::const_val(fx, ty, bits as i128 as i64) } - ty::FnDef(def_id, substs) => { - let func_ref = fx.get_function_ref( - Instance::resolve(fx.tcx, ParamEnv::reveal_all(), def_id, substs).unwrap(), - ); - let func_addr = fx.bcx.ins().func_addr(fx.pointer_type, func_ref); - CValue::ByVal(func_addr, layout) + ty::FnDef(_def_id, _substs) => { + CValue::ByRef( + fx.bcx.ins().iconst(fx.pointer_type, 0), + layout + ) } _ => trans_const_place(fx, const_).to_cvalue(fx), }