diff --git a/src/librustc_trans/common.rs b/src/librustc_trans/common.rs index eb6ea8fa94b0a..419267cb269c9 100644 --- a/src/librustc_trans/common.rs +++ b/src/librustc_trans/common.rs @@ -45,37 +45,30 @@ use rustc_i128::u128; pub use context::{CrateContext, SharedCrateContext}; pub fn type_is_fat_ptr<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>, ty: Ty<'tcx>) -> bool { - match ty.sty { - ty::TyRawPtr(ty::TypeAndMut{ty, ..}) | - ty::TyRef(_, ty::TypeAndMut{ty, ..}) | - ty::TyBox(ty) => { - !ccx.shared().type_is_sized(ty) - } - _ => { - false - } + if let Layout::FatPointer { .. } = *ccx.layout_of(ty) { + true + } else { + false } } pub fn type_is_immediate<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>, ty: Ty<'tcx>) -> bool { - use machine::llsize_of_alloc; - use type_of::sizing_type_of; - - let simple = ty.is_scalar() || - ty.is_unique() || ty.is_region_ptr() || - ty.is_simd(); - if simple && !type_is_fat_ptr(ccx, ty) { - return true; - } - if !ccx.shared().type_is_sized(ty) { - return false; - } - match ty.sty { - ty::TyAdt(..) | ty::TyTuple(..) | ty::TyArray(..) | ty::TyClosure(..) => { - let llty = sizing_type_of(ccx, ty); - llsize_of_alloc(ccx, llty) <= llsize_of_alloc(ccx, ccx.int_type()) + let layout = ccx.layout_of(ty); + match *layout { + Layout::CEnum { .. } | + Layout::Scalar { .. } | + Layout::Vector { .. } => true, + + Layout::FatPointer { .. } => false, + + Layout::Array { .. } | + Layout::Univariant { .. } | + Layout::General { .. } | + Layout::UntaggedUnion { .. } | + Layout::RawNullablePointer { .. } | + Layout::StructWrappedNullablePointer { .. } => { + !layout.is_unsized() && layout.size(&ccx.tcx().data_layout).bytes() == 0 } - _ => type_is_zero_size(ccx, ty) } } diff --git a/src/librustc_trans/mir/rvalue.rs b/src/librustc_trans/mir/rvalue.rs index 67fb8cf576d62..1b97a8d010cfe 100644 --- a/src/librustc_trans/mir/rvalue.rs +++ b/src/librustc_trans/mir/rvalue.rs @@ -260,22 +260,9 @@ impl<'a, 'tcx> MirContext<'a, 'tcx> { let r_t_out = CastTy::from_ty(cast_ty).expect("bad output type for cast"); let ll_t_in = type_of::immediate_type_of(bcx.ccx, operand.ty); let ll_t_out = type_of::immediate_type_of(bcx.ccx, cast_ty); - let (llval, signed) = if let CastTy::Int(IntTy::CEnum) = r_t_in { - let l = bcx.ccx.layout_of(operand.ty); - let discr = match operand.val { - OperandValue::Immediate(llval) => llval, - OperandValue::Ref(llptr) => { - adt::trans_get_discr(&bcx, operand.ty, llptr, None, true) - } - OperandValue::Pair(..) => bug!("Unexpected Pair operand") - }; - let (signed, min, max) = match l { - &Layout::CEnum { signed, min, max, .. } => { - (signed, min, max) - } - _ => bug!("CEnum {:?} is not an enum", operand) - }; - + let llval = operand.immediate(); + let l = bcx.ccx.layout_of(operand.ty); + let signed = if let Layout::CEnum { signed, min, max, .. } = *l { if max > min { // We want `table[e as usize]` to not // have bound checks, and this is the most @@ -283,14 +270,14 @@ impl<'a, 'tcx> MirContext<'a, 'tcx> { base::call_assume(&bcx, bcx.icmp( llvm::IntULE, - discr, - C_integral(common::val_ty(discr), max, false) - )) + llval, + C_integral(common::val_ty(llval), max, false) + )); } - (discr, signed) + signed } else { - (operand.immediate(), operand.ty.is_signed()) + operand.ty.is_signed() }; let newval = match (r_t_in, r_t_out) {