Workaround for missing #[rustc_args_required_const(..)] support

cc #666
This commit is contained in:
bjorn3 2019-08-16 16:04:50 +02:00
parent 6bf47ad0d4
commit 2558bf2f6b
3 changed files with 33 additions and 10 deletions

View File

@ -75,6 +75,9 @@ unsafe fn test_simd() {
test_mm_cvtepi8_epi16();
test_mm_cvtsi128_si64();
// FIXME(#666) implement `#[rustc_arg_required_const(..)]` support
//test_mm_extract_epi8();
let mask1 = _mm_movemask_epi8(dbg!(_mm_setr_epi8(255u8 as i8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0)));
assert_eq!(mask1, 1);
}
@ -194,6 +197,19 @@ unsafe fn test_mm_cvtepi8_epi16() {
assert_eq_m128i(r, e);
}
#[target_feature(enable = "sse4.1")]
unsafe fn test_mm_extract_epi8() {
#[rustfmt::skip]
let a = _mm_setr_epi8(
-1, 1, 2, 3, 4, 5, 6, 7,
8, 9, 10, 11, 12, 13, 14, 15
);
let r1 = _mm_extract_epi8(a, 0);
let r2 = _mm_extract_epi8(a, 19);
assert_eq!(r1, 0xFF);
assert_eq!(r2, 3);
}
#[derive(PartialEq)]
enum LoopState {
Continue(()),

View File

@ -439,22 +439,19 @@ impl<'mir, 'tcx> Machine<'mir, 'tcx> for TransPlaceInterpreter {
pub fn mir_operand_get_const_val<'tcx>(
fx: &FunctionCx<'_, 'tcx, impl Backend>,
operand: &Operand<'tcx>,
) -> Result<&'tcx Const<'tcx>, String> {
) -> Option<&'tcx Const<'tcx>> {
let place = match operand {
Operand::Copy(place) => place,
Operand::Constant(const_) => return Ok(force_eval_const(fx, const_.literal)),
_ => return Err(format!("{:?}", operand)),
Operand::Copy(place) | Operand::Move(place) => place,
Operand::Constant(const_) => return Some(force_eval_const(fx, const_.literal)),
};
assert!(place.projection.is_none());
let static_ = match &place.base {
PlaceBase::Static(static_) => {
static_
}
PlaceBase::Local(_) => return Err("local".to_string()),
PlaceBase::Static(static_) => static_,
PlaceBase::Local(_) => return None,
};
Ok(match &static_.kind {
Some(match &static_.kind {
StaticKind::Static(_) => unimplemented!(),
StaticKind::Promoted(promoted) => {
fx.tcx.const_eval(ParamEnv::reveal_all().and(GlobalId {

View File

@ -951,7 +951,17 @@ pub fn codegen_intrinsic_call<'a, 'tcx: 'a>(
};
simd_extract, (c v, o idx) {
let idx_const = crate::constant::mir_operand_get_const_val(fx, idx).expect("simd_extract* idx not const");
let idx_const = if let Some(idx_const) = crate::constant::mir_operand_get_const_val(fx, idx) {
idx_const
} else {
fx.tcx.sess.span_warn(
fx.mir.span,
"`#[rustc_arg_required_const(..)]` is not yet supported. Calling this function will panic.",
);
crate::trap::trap_panic(fx, "`#[rustc_arg_required_const(..)]` is not yet supported.");
return;
};
let idx = idx_const.val.try_to_bits(Size::from_bytes(4 /* u32*/)).expect(&format!("kind not scalar: {:?}", idx_const));
let (_lane_type, lane_count) = lane_type_and_count(fx, v.layout(), intrinsic);
if idx >= lane_count.into() {