Add InstructionData::imm_value()

This commit is contained in:
Andrew Brown
2020-10-01 09:50:07 -07:00
parent 6f6f79ef2b
commit 3a2025fdc7
2 changed files with 52 additions and 1 deletions

View File

@@ -1,6 +1,6 @@
//! This module gives users to instantiate values that Cranelift understands. These values are used, //! This module gives users to instantiate values that Cranelift understands. These values are used,
//! for example, during interpretation and for wrapping immediates. //! for example, during interpretation and for wrapping immediates.
use crate::ir::immediates::{Ieee32, Ieee64, Imm64}; use crate::ir::immediates::{Ieee32, Ieee64, Imm64, Offset32};
use crate::ir::{types, ConstantData, Type}; use crate::ir::{types, ConstantData, Type};
use core::convert::TryInto; use core::convert::TryInto;
use core::fmt::{self, Display, Formatter}; use core::fmt::{self, Display, Formatter};
@@ -100,6 +100,21 @@ build_conversion_impl!(i64, I64, I64);
build_conversion_impl!(f32, F32, F32); build_conversion_impl!(f32, F32, F32);
build_conversion_impl!(f64, F64, F64); build_conversion_impl!(f64, F64, F64);
build_conversion_impl!([u8; 16], V128, I8X16); build_conversion_impl!([u8; 16], V128, I8X16);
impl From<Ieee64> for DataValue {
fn from(f: Ieee64) -> Self {
DataValue::from(f64::from_bits(f.bits()))
}
}
impl From<Ieee32> for DataValue {
fn from(f: Ieee32) -> Self {
DataValue::from(f32::from_bits(f.bits()))
}
}
impl From<Offset32> for DataValue {
fn from(o: Offset32) -> Self {
DataValue::from(Into::<i32>::into(o))
}
}
impl Display for DataValue { impl Display for DataValue {
fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result { fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {

View File

@@ -17,6 +17,7 @@ use crate::ir::{self, trapcode::TrapCode, types, Block, FuncRef, JumpTable, SigR
use crate::isa; use crate::isa;
use crate::bitset::BitSet; use crate::bitset::BitSet;
use crate::data_value::DataValue;
use crate::entity; use crate::entity;
use ir::condcodes::{FloatCC, IntCC}; use ir::condcodes::{FloatCC, IntCC};
@@ -284,6 +285,41 @@ impl InstructionData {
} }
} }
/// Return the value of an immediate if the instruction has one or `None` otherwise. Only
/// immediate values are considered, not global values, constant handles, condition codes, etc.
pub fn imm_value(&self) -> Option<DataValue> {
match self {
&InstructionData::UnaryBool { imm, .. } => Some(DataValue::from(imm)),
// 8-bit.
&InstructionData::BinaryImm8 { imm, .. }
| &InstructionData::BranchTableEntry { imm, .. } => Some(DataValue::from(imm as i8)), // Note the switch from unsigned to signed.
// 32-bit
&InstructionData::UnaryIeee32 { imm, .. } => Some(DataValue::from(imm)),
&InstructionData::HeapAddr { imm, .. } => {
let imm: u32 = imm.into();
Some(DataValue::from(imm as i32)) // Note the switch from unsigned to signed.
}
&InstructionData::Load { offset, .. }
| &InstructionData::LoadComplex { offset, .. }
| &InstructionData::Store { offset, .. }
| &InstructionData::StoreComplex { offset, .. }
| &InstructionData::StackLoad { offset, .. }
| &InstructionData::StackStore { offset, .. }
| &InstructionData::TableAddr { offset, .. } => Some(DataValue::from(offset)),
// 64-bit.
&InstructionData::UnaryImm { imm, .. }
| &InstructionData::BinaryImm64 { imm, .. }
| &InstructionData::IntCompareImm { imm, .. } => Some(DataValue::from(imm.bits())),
&InstructionData::UnaryIeee64 { imm, .. } => Some(DataValue::from(imm)),
// 128-bit; though these immediates are present logically in the IR they are not
// included in the `InstructionData` for memory-size reasons. This case, returning
// `None`, is left here to alert users of this method that they should retrieve the
// value using the `DataFlowGraph`.
&InstructionData::Shuffle { mask: _, .. } => None,
_ => None,
}
}
/// If this is a trapping instruction, get its trap code. Otherwise, return /// If this is a trapping instruction, get its trap code. Otherwise, return
/// `None`. /// `None`.
pub fn trap_code(&self) -> Option<TrapCode> { pub fn trap_code(&self) -> Option<TrapCode> {