summaryrefslogtreecommitdiff
path: root/rust/src/medium_level_il
diff options
context:
space:
mode:
authorMason Reed <mason@vector35.com>2025-05-11 21:00:55 -0400
committerMason Reed <35282038+emesare@users.noreply.github.com>2025-05-12 17:45:24 -0400
commit3b14d1605cf9ea638a0d058911a8c1e233a9f70d (patch)
tree578fde48ea785a21072ba0e2c5c93061e4ba5a72 /rust/src/medium_level_il
parente2fac46543527d27eab2fc77cf19a4f715438857 (diff)
[Rust] Add missing instruction types to MLIL
Diffstat (limited to 'rust/src/medium_level_il')
-rw-r--r--rust/src/medium_level_il/instruction.rs63
-rw-r--r--rust/src/medium_level_il/lift.rs32
-rw-r--r--rust/src/medium_level_il/operation.rs78
3 files changed, 164 insertions, 9 deletions
diff --git a/rust/src/medium_level_il/instruction.rs b/rust/src/medium_level_il/instruction.rs
index 065e28f1..70d69b7f 100644
--- a/rust/src/medium_level_il/instruction.rs
+++ b/rust/src/medium_level_il/instruction.rs
@@ -5,12 +5,12 @@ use crate::architecture::{CoreIntrinsic, FlagId, IntrinsicId, RegisterId};
use crate::basic_block::BasicBlock;
use crate::confidence::Conf;
use crate::disassembly::InstructionTextToken;
-use crate::operand_iter::OperandIter;
use crate::rc::{Array, CoreArrayProvider, CoreArrayProviderInner, Ref};
use crate::types::Type;
use crate::variable::{ConstantData, PossibleValueSet, RegisterValue, SSAVariable, Variable};
use crate::{DataFlowQueryOption, ILBranchDependence};
use binaryninjacore_sys::*;
+use std::collections::BTreeMap;
use std::fmt;
use std::fmt::{Debug, Display, Formatter};
@@ -411,6 +411,24 @@ impl MediumLevelILInstruction {
num_params: op.operands[3] as usize,
first_param: op.operands[4] as usize,
}),
+ MLIL_CALL_OUTPUT => Op::CallOutput(CallOutput {
+ first_output: op.operands[0] as usize,
+ num_outputs: op.operands[1] as usize,
+ }),
+ MLIL_CALL_PARAM => Op::CallParam(CallParam {
+ first_param: op.operands[0] as usize,
+ num_params: op.operands[1] as usize,
+ }),
+ MLIL_CALL_OUTPUT_SSA => Op::CallOutputSsa(CallOutputSsa {
+ dest_memory: op.operands[0],
+ num_outputs: op.operands[1] as usize,
+ first_output: op.operands[2] as usize,
+ }),
+ MLIL_CALL_PARAM_SSA => Op::CallParamSsa(CallParamSsa {
+ src_memory: op.operands[0],
+ num_params: op.operands[1] as usize,
+ first_param: op.operands[2] as usize,
+ }),
MLIL_TAILCALL => Op::Tailcall(Call {
num_outputs: op.operands[0] as usize,
first_output: op.operands[1] as usize,
@@ -438,6 +456,20 @@ impl MediumLevelILInstruction {
num_params: op.operands[3] as usize,
first_param: op.operands[4] as usize,
}),
+ MLIL_MEMORY_INTRINSIC_SSA => Op::MemoryIntrinsicSsa(MemoryIntrinsicSsa {
+ output: op.operands[0] as usize,
+ intrinsic: op.operands[1] as u32,
+ num_params: op.operands[2] as usize,
+ first_param: op.operands[3] as usize,
+ src_memory: op.operands[4],
+ }),
+ MLIL_MEMORY_INTRINSIC_OUTPUT_SSA => {
+ Op::MemoryIntrinsicOutputSsa(MemoryIntrinsicOutputSsa {
+ dest_memory: op.operands[0],
+ first_output: op.operands[1] as usize,
+ num_outputs: op.operands[2] as usize,
+ })
+ }
MLIL_CALL_SSA => Op::CallSsa(CallSsa {
output: op.operands[0] as usize,
dest: op.operands[1] as usize,
@@ -602,14 +634,6 @@ impl MediumLevelILInstruction {
MLIL_TRAP => Op::Trap(Trap {
vector: op.operands[0],
}),
- // translated directly into a list for Expression or Variables
- // TODO MLIL_MEMORY_INTRINSIC_SSA needs to be handled properly
- MLIL_CALL_OUTPUT
- | MLIL_CALL_PARAM
- | MLIL_CALL_PARAM_SSA
- | MLIL_CALL_OUTPUT_SSA
- | MLIL_MEMORY_INTRINSIC_OUTPUT_SSA
- | MLIL_MEMORY_INTRINSIC_SSA => Op::NotYetImplemented,
};
Self {
@@ -847,6 +871,21 @@ impl MediumLevelILInstruction {
Rrc(op) => Lifted::Rrc(self.lift_binary_op_carry(op)),
Call(op) => Lifted::Call(self.lift_call(op)),
+ CallOutput(_op) => Lifted::CallOutput(LiftedCallOutput {
+ output: self.get_var_list(0),
+ }),
+ CallParam(_op) => Lifted::CallParam(LiftedCallParam {
+ params: self.get_expr_list(0).iter().map(|i| i.lift()).collect(),
+ }),
+ CallOutputSsa(op) => Lifted::CallOutputSsa(LiftedCallOutputSsa {
+ dest_memory: op.dest_memory,
+ output: self.get_ssa_var_list(1),
+ }),
+ CallParamSsa(op) => Lifted::CallParamSsa(LiftedCallParamSsa {
+ src_memory: op.src_memory,
+ params: self.get_expr_list(1).iter().map(|i| i.lift()).collect(),
+ }),
+
Tailcall(op) => Lifted::Tailcall(self.lift_call(op)),
Intrinsic(op) => Lifted::Intrinsic(LiftedIntrinsic {
@@ -1672,10 +1711,16 @@ pub enum MediumLevelILInstructionKind {
Rlc(BinaryOpCarry),
Rrc(BinaryOpCarry),
Call(Call),
+ CallOutput(CallOutput),
+ CallParam(CallParam),
+ CallOutputSsa(CallOutputSsa),
+ CallParamSsa(CallParamSsa),
Tailcall(Call),
Syscall(Syscall),
Intrinsic(Intrinsic),
IntrinsicSsa(IntrinsicSsa),
+ MemoryIntrinsicSsa(MemoryIntrinsicSsa),
+ MemoryIntrinsicOutputSsa(MemoryIntrinsicOutputSsa),
CallSsa(CallSsa),
TailcallSsa(CallSsa),
CallUntypedSsa(CallUntypedSsa),
diff --git a/rust/src/medium_level_il/lift.rs b/rust/src/medium_level_il/lift.rs
index f5ee45b3..399bda78 100644
--- a/rust/src/medium_level_il/lift.rs
+++ b/rust/src/medium_level_il/lift.rs
@@ -129,10 +129,16 @@ pub enum MediumLevelILLiftedInstructionKind {
Rlc(LiftedBinaryOpCarry),
Rrc(LiftedBinaryOpCarry),
Call(LiftedCall),
+ CallOutput(LiftedCallOutput),
+ CallParam(LiftedCallParam),
+ CallOutputSsa(LiftedCallOutputSsa),
+ CallParamSsa(LiftedCallParamSsa),
Tailcall(LiftedCall),
Intrinsic(LiftedIntrinsic),
Syscall(LiftedSyscallCall),
IntrinsicSsa(LiftedIntrinsicSsa),
+ MemoryIntrinsicSsa(LiftedMemoryIntrinsicSsa),
+ MemoryIntrinsicOutputSsa(LiftedMemoryIntrinsicOutputSsa),
CallSsa(LiftedCallSsa),
TailcallSsa(LiftedCallSsa),
CallUntypedSsa(LiftedCallUntypedSsa),
@@ -269,10 +275,16 @@ impl MediumLevelILLiftedInstruction {
Rlc(_) => "Rlc",
Rrc(_) => "Rrc",
Call(_) => "Call",
+ CallOutput(_) => "CallOutput",
+ CallParam(_) => "CallParam",
+ CallOutputSsa(_) => "CallOutputSsa",
+ CallParamSsa(_) => "CallParamSsa",
Tailcall(_) => "Tailcall",
Syscall(_) => "Syscall",
Intrinsic(_) => "Intrinsic",
IntrinsicSsa(_) => "IntrinsicSsa",
+ MemoryIntrinsicSsa(_) => "MemoryIntrinsicSsa",
+ MemoryIntrinsicOutputSsa(_) => "MemoryIntrinsicOutputSsa",
CallSsa(_) => "CallSsa",
TailcallSsa(_) => "TailcallSsa",
CallUntypedSsa(_) => "CallUntypedSsa",
@@ -441,6 +453,16 @@ impl MediumLevelILLiftedInstruction {
("dest", Operand::Expr(*op.dest.clone())),
("params", Operand::ExprList(op.params.clone())),
],
+ CallOutput(op) => vec![("output", Operand::VarList(op.output.clone()))],
+ CallParam(op) => vec![("params", Operand::ExprList(op.params.clone()))],
+ CallOutputSsa(op) => vec![
+ ("output", Operand::VarSsaList(op.output.clone())),
+ ("dest_memory", Operand::Int(op.dest_memory)),
+ ],
+ CallParamSsa(op) => vec![
+ ("params", Operand::ExprList(op.params.clone())),
+ ("src_memory", Operand::Int(op.src_memory)),
+ ],
Syscall(op) => vec![
("output", Operand::VarList(op.output.clone())),
("params", Operand::ExprList(op.params.clone())),
@@ -455,6 +477,16 @@ impl MediumLevelILLiftedInstruction {
("intrinsic", Operand::Intrinsic(op.intrinsic)),
("params", Operand::ExprList(op.params.clone())),
],
+ MemoryIntrinsicSsa(op) => vec![
+ ("output", Operand::Expr(*op.output.clone())),
+ ("intrinsic", Operand::Intrinsic(op.intrinsic)),
+ ("params", Operand::ExprList(op.params.clone())),
+ ("src_memory", Operand::Int(op.src_memory)),
+ ],
+ MemoryIntrinsicOutputSsa(op) => vec![
+ ("dest_memory", Operand::Int(op.dest_memory)),
+ ("output", Operand::VarSsaList(op.output.clone())),
+ ],
CallSsa(op) | TailcallSsa(op) => vec![
("output", Operand::VarSsaList(op.output.clone())),
("dest", Operand::Expr(*op.dest.clone())),
diff --git a/rust/src/medium_level_il/operation.rs b/rust/src/medium_level_il/operation.rs
index e11f59c8..e8b70cc6 100644
--- a/rust/src/medium_level_il/operation.rs
+++ b/rust/src/medium_level_il/operation.rs
@@ -329,6 +329,54 @@ pub struct LiftedCall {
pub params: Vec<MediumLevelILLiftedInstruction>,
}
+// CALL_OUTPUT
+#[derive(Debug, Copy, Clone)]
+pub struct CallOutput {
+ pub first_output: usize,
+ pub num_outputs: usize,
+}
+#[derive(Clone, Debug, PartialEq)]
+pub struct LiftedCallOutput {
+ pub output: Vec<Variable>,
+}
+
+// CALL_PARAM_SSA
+#[derive(Debug, Copy, Clone)]
+pub struct CallParam {
+ pub first_param: usize,
+ pub num_params: usize,
+}
+#[derive(Clone, Debug, PartialEq)]
+pub struct LiftedCallParam {
+ pub params: Vec<MediumLevelILLiftedInstruction>,
+}
+
+// CALL_OUTPUT_SSA
+#[derive(Debug, Copy, Clone)]
+pub struct CallOutputSsa {
+ pub dest_memory: u64,
+ pub first_output: usize,
+ pub num_outputs: usize,
+}
+#[derive(Clone, Debug, PartialEq)]
+pub struct LiftedCallOutputSsa {
+ pub dest_memory: u64,
+ pub output: Vec<SSAVariable>,
+}
+
+// CALL_PARAM_SSA
+#[derive(Debug, Copy, Clone)]
+pub struct CallParamSsa {
+ pub src_memory: u64,
+ pub first_param: usize,
+ pub num_params: usize,
+}
+#[derive(Clone, Debug, PartialEq)]
+pub struct LiftedCallParamSsa {
+ pub src_memory: u64,
+ pub params: Vec<MediumLevelILLiftedInstruction>,
+}
+
// SYSCALL
#[derive(Debug, Copy, Clone)]
pub struct Syscall {
@@ -375,6 +423,36 @@ pub struct LiftedIntrinsicSsa {
pub params: Vec<MediumLevelILLiftedInstruction>,
}
+// MEMORY_INTRINSIC_SSA
+#[derive(Debug, Copy, Clone)]
+pub struct MemoryIntrinsicSsa {
+ pub output: usize,
+ pub intrinsic: u32,
+ pub first_param: usize,
+ pub num_params: usize,
+ pub src_memory: u64,
+}
+#[derive(Clone, Debug, PartialEq)]
+pub struct LiftedMemoryIntrinsicSsa {
+ pub output: Box<MediumLevelILLiftedInstruction>,
+ pub intrinsic: CoreIntrinsic,
+ pub params: Vec<MediumLevelILLiftedInstruction>,
+ pub src_memory: u64,
+}
+
+// MEMORY_INTRINSIC_OUTPUT_SSA
+#[derive(Debug, Copy, Clone)]
+pub struct MemoryIntrinsicOutputSsa {
+ pub dest_memory: u64,
+ pub first_output: usize,
+ pub num_outputs: usize,
+}
+#[derive(Clone, Debug, PartialEq)]
+pub struct LiftedMemoryIntrinsicOutputSsa {
+ pub dest_memory: u64,
+ pub output: Vec<SSAVariable>,
+}
+
// CALL_SSA, TAILCALL_SSA
#[derive(Debug, Copy, Clone)]
pub struct CallSsa {