diff options
| author | Michael Krasnitski <michael.krasnitski@gmail.com> | 2024-02-08 19:50:49 -0500 |
|---|---|---|
| committer | Kyle Martin <krm504@nyu.edu> | 2024-03-18 17:46:37 -0400 |
| commit | 970fe84875e2d6eed918f5bdc9ff689ef37b05ce (patch) | |
| tree | 31fe9d82a623693c92c5c1fc7d05daf69fad3da3 /rust/src/mlil/instruction.rs | |
| parent | f535df40f978d221547b45650b75aa1089e197ce (diff) | |
Make `OperandIter` generic over its function IL
Diffstat (limited to 'rust/src/mlil/instruction.rs')
| -rw-r--r-- | rust/src/mlil/instruction.rs | 123 |
1 files changed, 91 insertions, 32 deletions
diff --git a/rust/src/mlil/instruction.rs b/rust/src/mlil/instruction.rs index 7b182010..a25a0859 100644 --- a/rust/src/mlil/instruction.rs +++ b/rust/src/mlil/instruction.rs @@ -1,8 +1,13 @@ +use binaryninjacore_sys::BNFromVariableIdentifier; use binaryninjacore_sys::BNGetMediumLevelILByIndex; +use binaryninjacore_sys::BNMediumLevelILInstruction; use binaryninjacore_sys::BNMediumLevelILOperation; +use crate::operand_iter::OperandIter; use crate::rc::Ref; -use crate::types::{ConstantData, ILIntrinsic, RegisterValue, RegisterValueType}; +use crate::types::{ + ConstantData, ILIntrinsic, RegisterValue, RegisterValueType, SSAVariable, Variable, +}; use super::lift::*; use super::operation::*; @@ -773,8 +778,8 @@ impl MediumLevelILInstruction { }), JumpTo(op) => Lifted::JumpTo(LiftedJumpTo { dest: self.lift_operand(op.dest), - targets: OperandIter::new(&self.function, op.first_operand, op.num_operands) - .as_pairs() + targets: OperandIter::new(&*self.function, op.first_operand, op.num_operands) + .pairs() .collect(), }), Goto(op) => Lifted::Goto(op), @@ -812,13 +817,13 @@ impl MediumLevelILInstruction { }), VarPhi(op) => Lifted::VarPhi(LiftedVarPhi { dest: op.dest, - src: OperandIter::new(&self.function, op.first_operand, op.num_operands) - .as_ssa_vars() + src: OperandIter::new(&*self.function, op.first_operand, op.num_operands) + .ssa_vars() .collect(), }), MemPhi(op) => Lifted::MemPhi(LiftedMemPhi { dest_memory: op.dest_memory, - src_memory: OperandIter::new(&self.function, op.first_operand, op.num_operands) + src_memory: OperandIter::new(&*self.function, op.first_operand, op.num_operands) .collect(), }), VarSplit(op) => Lifted::VarSplit(op), @@ -889,31 +894,31 @@ impl MediumLevelILInstruction { Tailcall(op) => Lifted::Tailcall(self.lift_call(op)), Intrinsic(op) => Lifted::Intrinsic(LiftedIntrinsic { - output: OperandIter::new(&self.function, op.first_output, op.num_outputs) - .as_vars() + output: OperandIter::new(&*self.function, op.first_output, op.num_outputs) + .vars() .collect(), intrinsic: ILIntrinsic::new(self.function.get_function().arch(), op.intrinsic), - params: OperandIter::new(&self.function, op.first_param, op.num_params) - .as_exprs() + params: OperandIter::new(&*self.function, op.first_param, op.num_params) + .exprs() .map(|expr| expr.lift()) .collect(), }), Syscall(op) => Lifted::Syscall(LiftedSyscallCall { - output: OperandIter::new(&self.function, op.first_output, op.num_outputs) - .as_vars() + output: OperandIter::new(&*self.function, op.first_output, op.num_outputs) + .vars() .collect(), - params: OperandIter::new(&self.function, op.first_param, op.num_params) - .as_exprs() + params: OperandIter::new(&*self.function, op.first_param, op.num_params) + .exprs() .map(|expr| expr.lift()) .collect(), }), IntrinsicSsa(op) => Lifted::IntrinsicSsa(LiftedIntrinsicSsa { - output: OperandIter::new(&self.function, op.first_output, op.num_outputs) - .as_ssa_vars() + output: OperandIter::new(&*self.function, op.first_output, op.num_outputs) + .ssa_vars() .collect(), intrinsic: ILIntrinsic::new(self.function.get_function().arch(), op.intrinsic), - params: OperandIter::new(&self.function, op.first_param, op.num_params) - .as_exprs() + params: OperandIter::new(&*self.function, op.first_param, op.num_params) + .exprs() .map(|expr| expr.lift()) .collect(), }), @@ -926,8 +931,8 @@ impl MediumLevelILInstruction { SyscallSsa(op) => Lifted::SyscallSsa(LiftedSyscallSsa { output: get_call_output_ssa(&self.function, op.output).collect(), - params: OperandIter::new(&self.function, op.first_param, op.num_params) - .as_exprs() + params: OperandIter::new(&*self.function, op.first_param, op.num_params) + .exprs() .map(|expr| expr.lift()) .collect(), src_memory: op.src_memory, @@ -983,20 +988,20 @@ impl MediumLevelILInstruction { src_memory: op.src_memory, }), Ret(op) => Lifted::Ret(LiftedRet { - src: OperandIter::new(&self.function, op.first_operand, op.num_operands) - .as_exprs() + src: OperandIter::new(&*self.function, op.first_operand, op.num_operands) + .exprs() .map(|expr| expr.lift()) .collect(), }), SeparateParamList(op) => Lifted::SeparateParamList(LiftedSeparateParamList { - params: OperandIter::new(&self.function, op.first_param, op.num_params) - .as_exprs() + params: OperandIter::new(&*self.function, op.first_param, op.num_params) + .exprs() .map(|expr| expr.lift()) .collect(), }), SharedParamSlot(op) => Lifted::SharedParamSlot(LiftedSharedParamSlot { - params: OperandIter::new(&self.function, op.first_param, op.num_params) - .as_exprs() + params: OperandIter::new(&*self.function, op.first_param, op.num_params) + .exprs() .map(|expr| expr.lift()) .collect(), }), @@ -1045,12 +1050,12 @@ impl MediumLevelILInstruction { fn lift_call(&self, op: Call) -> LiftedCall { LiftedCall { - output: OperandIter::new(&self.function, op.first_output, op.num_outputs) - .as_vars() + output: OperandIter::new(&*self.function, op.first_output, op.num_outputs) + .vars() .collect(), dest: self.lift_operand(op.dest), - params: OperandIter::new(&self.function, op.first_param, op.num_params) - .as_exprs() + params: OperandIter::new(&*self.function, op.first_param, op.num_params) + .exprs() .map(|expr| expr.lift()) .collect(), } @@ -1071,8 +1076,8 @@ impl MediumLevelILInstruction { LiftedCallSsa { output: get_call_output_ssa(&self.function, op.output).collect(), dest: self.lift_operand(op.dest), - params: OperandIter::new(&self.function, op.first_param, op.num_params) - .as_exprs() + params: OperandIter::new(&*self.function, op.first_param, op.num_params) + .exprs() .map(|expr| expr.lift()) .collect(), src_memory: op.src_memory, @@ -1090,3 +1095,57 @@ impl MediumLevelILInstruction { } } } + +fn get_float(value: u64, size: usize) -> f64 { + match size { + 4 => f32::from_bits(value as u32) as f64, + 8 => f64::from_bits(value), + // TODO how to handle this value? + size => todo!("float size {}", size), + } +} + +fn get_raw_operation(function: &MediumLevelILFunction, idx: usize) -> BNMediumLevelILInstruction { + unsafe { BNGetMediumLevelILByIndex(function.handle, idx) } +} + +fn get_var(id: u64) -> Variable { + unsafe { Variable::from_raw(BNFromVariableIdentifier(id)) } +} + +fn get_var_ssa(id: u64, version: usize) -> SSAVariable { + SSAVariable::new(get_var(id), version) +} + +fn get_call_output(function: &MediumLevelILFunction, idx: usize) -> impl Iterator<Item = Variable> { + let op = get_raw_operation(function, idx); + assert_eq!(op.operation, BNMediumLevelILOperation::MLIL_CALL_OUTPUT); + OperandIter::new(function, op.operands[1] as usize, op.operands[0] as usize).vars() +} + +fn get_call_params( + function: &MediumLevelILFunction, + idx: usize, +) -> impl Iterator<Item = MediumLevelILInstruction> { + let op = get_raw_operation(function, idx); + assert_eq!(op.operation, BNMediumLevelILOperation::MLIL_CALL_PARAM); + OperandIter::new(function, op.operands[1] as usize, op.operands[0] as usize).exprs() +} + +fn get_call_output_ssa( + function: &MediumLevelILFunction, + idx: usize, +) -> impl Iterator<Item = SSAVariable> { + let op = get_raw_operation(function, idx); + assert_eq!(op.operation, BNMediumLevelILOperation::MLIL_CALL_OUTPUT_SSA); + OperandIter::new(function, op.operands[2] as usize, op.operands[1] as usize).ssa_vars() +} + +fn get_call_params_ssa( + function: &MediumLevelILFunction, + idx: usize, +) -> impl Iterator<Item = MediumLevelILInstruction> { + let op = get_raw_operation(function, idx); + assert_eq!(op.operation, BNMediumLevelILOperation::MLIL_CALL_PARAM_SSA); + OperandIter::new(function, op.operands[2] as usize, op.operands[1] as usize).exprs() +} |
