interpret/cast: make more matches on FloatTy properly exhaustive · rust-lang/rust@86e88fc (original) (raw)
`@@ -182,13 +182,14 @@ impl<'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> {
`
182
182
`) -> InterpResult<'tcx, ImmTy<'tcx, M::Provenance>> {
`
183
183
`use rustc_type_ir::TyKind::*;
`
184
184
``
185
``
`-
let val = match src.layout.ty.kind() {
`
186
``
`-
// Floating point
`
187
``
`-
Float(FloatTy::F32) => self.cast_from_float(src.to_scalar().to_f32()?, cast_to.ty),
`
188
``
`-
Float(FloatTy::F64) => self.cast_from_float(src.to_scalar().to_f64()?, cast_to.ty),
`
189
``
`-
_ => {
`
190
``
`-
bug!("Can't cast 'Float' type into {}", cast_to.ty);
`
191
``
`-
}
`
``
185
`+
let Float(fty) = src.layout.ty.kind() else {
`
``
186
`+
bug!("FloatToFloat/FloatToInt cast: source type {} is not a float type", src.layout.ty)
`
``
187
`+
};
`
``
188
`+
let val = match fty {
`
``
189
`+
FloatTy::F16 => unimplemented!("f16_f128"),
`
``
190
`+
FloatTy::F32 => self.cast_from_float(src.to_scalar().to_f32()?, cast_to.ty),
`
``
191
`+
FloatTy::F64 => self.cast_from_float(src.to_scalar().to_f64()?, cast_to.ty),
`
``
192
`+
FloatTy::F128 => unimplemented!("f16_f128"),
`
192
193
`};
`
193
194
`Ok(ImmTy::from_scalar(val, cast_to))
`
194
195
`}
`
`@@ -275,6 +276,7 @@ impl<'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> {
`
275
276
`trace!("cast_from_scalar: {}, {} -> {}", v, src_layout.ty, cast_ty);
`
276
277
``
277
278
`Ok(match *cast_ty.kind() {
`
``
279
`+
// int -> int
`
278
280
`Int() | Uint() => {
`
279
281
`let size = match *cast_ty.kind() {
`
280
282
`Int(t) => Integer::from_int_ty(self, t).size(),
`
`@@ -285,15 +287,26 @@ impl<'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> {
`
285
287
`Scalar::from_uint(v, size)
`
286
288
`}
`
287
289
``
288
``
`-
Float(FloatTy::F32) if signed => Scalar::from_f32(Single::from_i128(v as i128).value),
`
289
``
`-
Float(FloatTy::F64) if signed => Scalar::from_f64(Double::from_i128(v as i128).value),
`
290
``
`-
Float(FloatTy::F32) => Scalar::from_f32(Single::from_u128(v).value),
`
291
``
`-
Float(FloatTy::F64) => Scalar::from_f64(Double::from_u128(v).value),
`
292
``
-
293
``
`-
Char => {
`
294
``
`` -
// u8
to char
cast
``
295
``
`-
Scalar::from_u32(u8::try_from(v).unwrap().into())
`
``
290
`+
// signed int -> float
`
``
291
`+
Float(fty) if signed => {
`
``
292
`+
let v = v as i128;
`
``
293
`+
match fty {
`
``
294
`+
FloatTy::F16 => unimplemented!("f16_f128"),
`
``
295
`+
FloatTy::F32 => Scalar::from_f32(Single::from_i128(v).value),
`
``
296
`+
FloatTy::F64 => Scalar::from_f64(Double::from_i128(v).value),
`
``
297
`+
FloatTy::F128 => unimplemented!("f16_f128"),
`
``
298
`+
}
`
296
299
`}
`
``
300
`+
// unsiged int -> float
`
``
301
`+
Float(fty) => match fty {
`
``
302
`+
FloatTy::F16 => unimplemented!("f16_f128"),
`
``
303
`+
FloatTy::F32 => Scalar::from_f32(Single::from_u128(v).value),
`
``
304
`+
FloatTy::F64 => Scalar::from_f64(Double::from_u128(v).value),
`
``
305
`+
FloatTy::F128 => unimplemented!("f16_f128"),
`
``
306
`+
},
`
``
307
+
``
308
`+
// u8 -> char
`
``
309
`+
Char => Scalar::from_u32(u8::try_from(v).unwrap().into()),
`
297
310
``
298
311
`// Casts to bool are not permitted by rustc, no need to handle them here.
`
299
312
` _ => span_bug!(self.cur_span(), "invalid int to {} cast", cast_ty),
`
`@@ -339,14 +352,13 @@ impl<'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> {
`
339
352
`let v = f.to_i128(size.bits_usize()).value;
`
340
353
`Scalar::from_int(v, size)
`
341
354
`}
`
342
``
`-
// float -> f32
`
343
``
`-
Float(FloatTy::F32) => {
`
344
``
`-
Scalar::from_f32(adjust_nan(self, f, f.convert(&mut false).value))
`
345
``
`-
}
`
346
``
`-
// float -> f64
`
347
``
`-
Float(FloatTy::F64) => {
`
348
``
`-
Scalar::from_f64(adjust_nan(self, f, f.convert(&mut false).value))
`
349
``
`-
}
`
``
355
`+
// float -> float
`
``
356
`+
Float(fty) => match fty {
`
``
357
`+
FloatTy::F16 => unimplemented!("f16_f128"),
`
``
358
`+
FloatTy::F32 => Scalar::from_f32(adjust_nan(self, f, f.convert(&mut false).value)),
`
``
359
`+
FloatTy::F64 => Scalar::from_f64(adjust_nan(self, f, f.convert(&mut false).value)),
`
``
360
`+
FloatTy::F128 => unimplemented!("f16_f128"),
`
``
361
`+
},
`
350
362
`// That's it.
`
351
363
` _ => span_bug!(self.cur_span(), "invalid float to {} cast", dest_ty),
`
352
364
`}
`