Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
28 changes: 16 additions & 12 deletions arch/msp430/src/lift.rs
Original file line number Diff line number Diff line change
Expand Up @@ -172,12 +172,14 @@ pub(crate) fn lift_instruction(inst: &Instruction, addr: u64, il: &LowLevelILMut
let src = il.const_int(size, 1);
let dest = lift_source_operand(inst.source(), size, il);
let op = match inst.operand_width() {
Some(OperandWidth::Byte) => {
il.zx(2, il.rrc(size, dest, src).with_flag_write(FlagWrite::All))
}
Some(OperandWidth::Word) | None => {
il.rrc(size, dest, src).with_flag_write(FlagWrite::All)
}
Some(OperandWidth::Byte) => il.zx(
2,
il.rrc(size, dest, src, il.flag(Flag::C))
.with_flag_write(FlagWrite::All),
),
Some(OperandWidth::Word) | None => il
.rrc(size, dest, src, il.flag(Flag::C))
.with_flag_write(FlagWrite::All),
};
one_operand!(inst.source(), il, op);
}
Expand Down Expand Up @@ -580,12 +582,14 @@ pub(crate) fn lift_instruction(inst: &Instruction, addr: u64, il: &LowLevelILMut
let src = il.const_int(size, 1);
let dest = lift_source_operand(&inst.destination().unwrap(), size, il);
let op = match inst.operand_width() {
Some(OperandWidth::Byte) => {
il.zx(2, il.rlc(size, dest, src).with_flag_write(FlagWrite::All))
}
Some(OperandWidth::Word) | None => {
il.rlc(size, dest, src).with_flag_write(FlagWrite::All)
}
Some(OperandWidth::Byte) => il.zx(
2,
il.rlc(size, dest, src, il.flag(Flag::C))
.with_flag_write(FlagWrite::All),
),
Some(OperandWidth::Word) | None => il
.rlc(size, dest, src, il.flag(Flag::C))
.with_flag_write(FlagWrite::All),
};
emulated!(inst, il, op);
}
Expand Down
77 changes: 68 additions & 9 deletions highlevelilinstruction.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -93,7 +93,8 @@ static constexpr std::array s_operandTypeForUsage = {
OperandUsageType{SourceSSAVariablesHighLevelOperandUsage, SSAVariableListHighLevelOperand},
OperandUsageType{SourceMemoryVersionHighLevelOperandUsage, IndexHighLevelOperand},
OperandUsageType{SourceMemoryVersionsHighLevelOperandUsage, IndexListHighLevelOperand},
OperandUsageType{DestMemoryVersionHighLevelOperandUsage, IndexHighLevelOperand}
OperandUsageType{DestMemoryVersionHighLevelOperandUsage, IndexHighLevelOperand},
OperandUsageType{ConstraintHighLevelOperandUsage, ConstraintHighLevelOperand}
};

static_assert(std::is_sorted(s_operandTypeForUsage.begin(), s_operandTypeForUsage.end()),
Expand Down Expand Up @@ -159,7 +160,7 @@ static constexpr std::array s_instructionOperandUsage = {
OperandUsage{HLIL_ASSIGN, {DestExprHighLevelOperandUsage, SourceExprHighLevelOperandUsage}},
OperandUsage{HLIL_ASSIGN_UNPACK, {DestExprsHighLevelOperandUsage, SourceExprHighLevelOperandUsage}},
OperandUsage{HLIL_FORCE_VER, {DestVariableHighLevelOperandUsage, VariableHighLevelOperandUsage}},
OperandUsage{HLIL_ASSERT, {VariableHighLevelOperandUsage, ConstantHighLevelOperandUsage}},
OperandUsage{HLIL_ASSERT, {VariableHighLevelOperandUsage, ConstraintHighLevelOperandUsage}},
OperandUsage{HLIL_VAR, {VariableHighLevelOperandUsage}},
OperandUsage{HLIL_STRUCT_FIELD, {SourceExprHighLevelOperandUsage, OffsetHighLevelOperandUsage, MemberIndexHighLevelOperandUsage}},
OperandUsage{HLIL_ARRAY_INDEX, {SourceExprHighLevelOperandUsage, IndexExprHighLevelOperandUsage}},
Expand Down Expand Up @@ -260,7 +261,7 @@ static constexpr std::array s_instructionOperandUsage = {
OperandUsage{HLIL_ASSIGN_MEM_SSA, {DestExprHighLevelOperandUsage, DestMemoryVersionHighLevelOperandUsage, SourceExprHighLevelOperandUsage, SourceMemoryVersionHighLevelOperandUsage}},
OperandUsage{HLIL_ASSIGN_UNPACK_MEM_SSA, {DestExprsHighLevelOperandUsage, DestMemoryVersionHighLevelOperandUsage, SourceExprHighLevelOperandUsage, SourceMemoryVersionHighLevelOperandUsage}},
OperandUsage{HLIL_FORCE_VER_SSA, {DestSSAVariableHighLevelOperandUsage, SSAVariableHighLevelOperandUsage}},
OperandUsage{HLIL_ASSERT_SSA, {SSAVariableHighLevelOperandUsage, ConstantHighLevelOperandUsage}},
OperandUsage{HLIL_ASSERT_SSA, {SSAVariableHighLevelOperandUsage, ConstraintHighLevelOperandUsage}},
OperandUsage{HLIL_VAR_SSA, {SSAVariableHighLevelOperandUsage}},
OperandUsage{HLIL_VAR_SSA_PARTIAL, {SSAVariableHighLevelOperandUsage, PartialSSAVariableSourceHighLevelOperandUsage}},
OperandUsage{HLIL_ARRAY_INDEX_SSA, {SourceExprHighLevelOperandUsage, SourceMemoryVersionHighLevelOperandUsage, IndexExprHighLevelOperandUsage}},
Expand Down Expand Up @@ -632,6 +633,8 @@ SSAVariable HighLevelILOperand::GetSSAVariable() const
{
if (m_type != SSAVariableHighLevelOperand)
throw HighLevelILInstructionAccessException();
if (m_usage == PartialSSAVariableSourceHighLevelOperandUsage)
return m_instr.GetRawOperandAsPartialSSAVariableSource(m_operandIndex - 2);
return m_instr.GetRawOperandAsSSAVariable(m_operandIndex);
}

Expand Down Expand Up @@ -1798,11 +1801,11 @@ bool HighLevelILInstruction::operator<(const HighLevelILInstruction& other) cons
return true;
if (other.GetConditionPhiExpr<HLIL_WHILE_SSA>() < GetConditionPhiExpr<HLIL_WHILE_SSA>())
return false;
if (GetConditionExpr<HLIL_WHILE>() < other.GetConditionExpr<HLIL_WHILE>())
if (GetConditionExpr<HLIL_WHILE_SSA>() < other.GetConditionExpr<HLIL_WHILE_SSA>())
return true;
if (other.GetConditionExpr<HLIL_WHILE>() < GetConditionExpr<HLIL_WHILE>())
if (other.GetConditionExpr<HLIL_WHILE_SSA>() < GetConditionExpr<HLIL_WHILE_SSA>())
return false;
return GetLoopExpr<HLIL_WHILE>() < other.GetLoopExpr<HLIL_WHILE>();
return GetLoopExpr<HLIL_WHILE_SSA>() < other.GetLoopExpr<HLIL_WHILE_SSA>();
case HLIL_DO_WHILE:
if (GetLoopExpr<HLIL_DO_WHILE>() < other.GetLoopExpr<HLIL_DO_WHILE>())
return true;
Expand Down Expand Up @@ -1913,6 +1916,46 @@ bool HighLevelILInstruction::operator<(const HighLevelILInstruction& other) cons
if (other.GetSourceExpr<HLIL_ASSIGN_UNPACK>() < GetSourceExpr<HLIL_ASSIGN_UNPACK>())
return false;
return CompareExprList(GetDestExprs<HLIL_ASSIGN_UNPACK>(), other.GetDestExprs<HLIL_ASSIGN_UNPACK>());
case HLIL_FORCE_VER:
if (size < other.size)
return true;
if (size > other.size)
return false;
if (GetDestVariable<HLIL_FORCE_VER>() < other.GetDestVariable<HLIL_FORCE_VER>())
return true;
if (other.GetDestVariable<HLIL_FORCE_VER>() < GetDestVariable<HLIL_FORCE_VER>())
return false;
return GetVariable<HLIL_FORCE_VER>() < other.GetVariable<HLIL_FORCE_VER>();
case HLIL_FORCE_VER_SSA:
if (size < other.size)
return true;
if (size > other.size)
return false;
if (GetDestSSAVariable<HLIL_FORCE_VER_SSA>() < other.GetDestSSAVariable<HLIL_FORCE_VER_SSA>())
return true;
if (other.GetDestSSAVariable<HLIL_FORCE_VER_SSA>() < GetDestSSAVariable<HLIL_FORCE_VER_SSA>())
return false;
return GetSSAVariable<HLIL_FORCE_VER_SSA>() < other.GetSSAVariable<HLIL_FORCE_VER_SSA>();
case HLIL_ASSERT:
if (size < other.size)
return true;
if (size > other.size)
return false;
if (GetVariable<HLIL_ASSERT>() < other.GetVariable<HLIL_ASSERT>())
return true;
if (other.GetVariable<HLIL_ASSERT>() < GetVariable<HLIL_ASSERT>())
return false;
return GetRawOperandAsInteger(1) < other.GetRawOperandAsInteger(1);
case HLIL_ASSERT_SSA:
if (size < other.size)
return true;
if (size > other.size)
return false;
if (GetSSAVariable<HLIL_ASSERT_SSA>() < other.GetSSAVariable<HLIL_ASSERT_SSA>())
return true;
if (other.GetSSAVariable<HLIL_ASSERT_SSA>() < GetSSAVariable<HLIL_ASSERT_SSA>())
return false;
return GetRawOperandAsInteger(2) < other.GetRawOperandAsInteger(2);
case HLIL_ASSIGN_MEM_SSA:
if (size < other.size)
return true;
Expand Down Expand Up @@ -2225,12 +2268,29 @@ bool HighLevelILInstruction::operator<(const HighLevelILInstruction& other) cons
if (other.AsTwoOperandWithCarry().GetRightExpr() < AsTwoOperandWithCarry().GetRightExpr())
return false;
return AsTwoOperandWithCarry().GetCarryExpr() < other.AsTwoOperandWithCarry().GetCarryExpr();
case HLIL_CONST:
case HLIL_CONST_DATA:
if (GetRawOperandAsInteger(0) < other.GetRawOperandAsInteger(0))
return true;
if (other.GetRawOperandAsInteger(0) < GetRawOperandAsInteger(0))
return false;
return GetRawOperandAsInteger(1) < other.GetRawOperandAsInteger(1);
case HLIL_CONST:
case HLIL_CONST_PTR:
case HLIL_FLOAT_CONST:
case HLIL_IMPORT:
return AsConstant().GetConstant() < other.AsConstant().GetConstant();
case HLIL_UNIMPL:
return As<HLIL_UNIMPL>().IsUnknown() < other.As<HLIL_UNIMPL>().IsUnknown();
case HLIL_UNIMPL_MEM:
if (size < other.size)
return true;
if (size > other.size)
return false;
if (GetSourceExpr<HLIL_UNIMPL_MEM>() < other.GetSourceExpr<HLIL_UNIMPL_MEM>())
return true;
if (other.GetSourceExpr<HLIL_UNIMPL_MEM>() < GetSourceExpr<HLIL_UNIMPL_MEM>())
return false;
return As<HLIL_UNIMPL_MEM>().IsUnknown() < other.As<HLIL_UNIMPL_MEM>().IsUnknown();
case HLIL_DEREF:
case HLIL_NEG:
case HLIL_NOT:
Expand All @@ -2245,7 +2305,6 @@ bool HighLevelILInstruction::operator<(const HighLevelILInstruction& other) cons
case HLIL_ZX:
case HLIL_LOW_PART:
case HLIL_BOOL_TO_INT:
case HLIL_UNIMPL_MEM:
case HLIL_FSQRT:
case HLIL_FNEG:
case HLIL_FABS:
Expand Down Expand Up @@ -2396,7 +2455,7 @@ SSAVariable HighLevelILInstruction::GetSourceSSAVariable() const
size_t operandIndex;
if (GetOperandIndexForUsage(PartialSSAVariableSourceHighLevelOperandUsage, operandIndex))
return GetRawOperandAsPartialSSAVariableSource(operandIndex - 2);
throw MediumLevelILInstructionAccessException();
throw HighLevelILInstructionAccessException();
}


Expand Down
6 changes: 4 additions & 2 deletions highlevelilinstruction.h
Original file line number Diff line number Diff line change
Expand Up @@ -76,7 +76,8 @@ namespace BinaryNinja
SSAVariableHighLevelOperand,
ExprListHighLevelOperand,
SSAVariableListHighLevelOperand,
IndexListHighLevelOperand
IndexListHighLevelOperand,
ConstraintHighLevelOperand
};

/*!
Expand Down Expand Up @@ -122,7 +123,8 @@ namespace BinaryNinja
SourceSSAVariablesHighLevelOperandUsage,
SourceMemoryVersionHighLevelOperandUsage,
SourceMemoryVersionsHighLevelOperandUsage,
DestMemoryVersionHighLevelOperandUsage
DestMemoryVersionHighLevelOperandUsage,
ConstraintHighLevelOperandUsage
};
} // namespace BinaryNinjaCore

Expand Down
33 changes: 29 additions & 4 deletions lowlevelilinstruction.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -188,6 +188,14 @@ using OperandUsage = detail::ILInstructionOperandUsage<LowLevelILOperationTraits
static_assert(sizeof(OperandUsage) == 14);


template <size_t N>
static constexpr OperandUsage WithOperandIndices(OperandUsage usage, const uint8_t (&indices)[N])
{
std::copy(indices, indices + N, usage.indices);
return usage;
}


static constexpr std::array s_instructionOperandUsage = {
OperandUsage{LLIL_NOP},
OperandUsage{LLIL_SET_REG, {DestRegisterLowLevelOperandUsage, SourceExprLowLevelOperandUsage}},
Expand Down Expand Up @@ -305,8 +313,8 @@ static constexpr std::array s_instructionOperandUsage = {
OperandUsage{LLIL_REG_STACK_DEST_SSA},
OperandUsage{LLIL_REG_SSA, {SourceSSARegisterLowLevelOperandUsage}},
OperandUsage{LLIL_REG_SSA_PARTIAL, {SourceSSARegisterLowLevelOperandUsage, PartialRegisterLowLevelOperandUsage}},
OperandUsage{LLIL_REG_SPLIT_SSA, {HighSSARegisterLowLevelOperandUsage, LowSSARegisterLowLevelOperandUsage}},
OperandUsage{LLIL_REG_STACK_REL_SSA, {SourceSSARegisterStackLowLevelOperandUsage, TopSSARegisterLowLevelOperandUsage, SourceExprLowLevelOperandUsage}},
WithOperandIndices(OperandUsage{LLIL_REG_SPLIT_SSA, {HighSSARegisterLowLevelOperandUsage, LowSSARegisterLowLevelOperandUsage}}, {0, 2}),
OperandUsage{LLIL_REG_STACK_REL_SSA, {SourceSSARegisterStackLowLevelOperandUsage, SourceExprLowLevelOperandUsage, TopSSARegisterLowLevelOperandUsage}},
OperandUsage{LLIL_REG_STACK_ABS_SSA, {SourceSSARegisterStackLowLevelOperandUsage, SourceRegisterLowLevelOperandUsage}},
OperandUsage{LLIL_REG_STACK_FREE_REL_SSA, {DestSSARegisterStackLowLevelOperandUsage, PartialSSARegisterStackSourceLowLevelOperandUsage, DestExprLowLevelOperandUsage, TopSSARegisterLowLevelOperandUsage}},
OperandUsage{LLIL_REG_STACK_FREE_ABS_SSA, {DestSSARegisterStackLowLevelOperandUsage, PartialSSARegisterStackSourceLowLevelOperandUsage, DestRegisterLowLevelOperandUsage}},
Expand All @@ -329,7 +337,7 @@ static constexpr std::array s_instructionOperandUsage = {
OperandUsage{LLIL_INTRINSIC_SSA, {OutputSSARegisterOrFlagListLowLevelOperandUsage, IntrinsicLowLevelOperandUsage, ParameterExprsLowLevelOperandUsage}},
OperandUsage{LLIL_MEMORY_INTRINSIC_SSA, {OutputMemoryIntrinsicLowLevelOperandUsage, OutputMemoryVersionLowLevelOperandUsage, IntrinsicLowLevelOperandUsage, ParameterExprsLowLevelOperandUsage, SourceMemoryVersionLowLevelOperandUsage}},
OperandUsage{LLIL_REG_PHI, {DestSSARegisterLowLevelOperandUsage, SourceSSARegistersLowLevelOperandUsage}},
OperandUsage{LLIL_REG_STACK_PHI, {DestSSARegisterStackLowLevelOperandUsage, SourceSSARegisterStacksLowLevelOperandUsage}},
WithOperandIndices(OperandUsage{LLIL_REG_STACK_PHI, {DestSSARegisterStackLowLevelOperandUsage, SourceSSARegisterStacksLowLevelOperandUsage}}, {0, 2}),
OperandUsage{LLIL_FLAG_PHI, {DestSSAFlagLowLevelOperandUsage, SourceSSAFlagsLowLevelOperandUsage}},
OperandUsage{LLIL_MEM_PHI, {DestMemoryVersionLowLevelOperandUsage, SourceMemoryVersionsLowLevelOperandUsage}},
OperandUsage{LLIL_BSWAP, {SourceExprLowLevelOperandUsage}},
Expand Down Expand Up @@ -1243,6 +1251,9 @@ SSARegister LowLevelILOperand::GetSSARegister() const
{
if (m_type != SSARegisterLowLevelOperand)
throw LowLevelILInstructionAccessException();
if (((m_usage == HighSSARegisterLowLevelOperandUsage) || (m_usage == LowSSARegisterLowLevelOperandUsage))
&& (m_instr.operation == LLIL_REG_SPLIT_SSA))
return m_instr.GetRawOperandAsSSARegister(m_operandIndex);
if ((m_usage == HighSSARegisterLowLevelOperandUsage) || (m_usage == LowSSARegisterLowLevelOperandUsage)
|| (m_usage == StackSSARegisterLowLevelOperandUsage) || (m_usage == TopSSARegisterLowLevelOperandUsage))
return m_instr.GetRawOperandAsExpr(m_operandIndex).GetRawOperandAsSSARegister(0);
Expand All @@ -1254,7 +1265,7 @@ SSARegisterStack LowLevelILOperand::GetSSARegisterStack() const
{
if (m_type != SSARegisterStackLowLevelOperand)
throw LowLevelILInstructionAccessException();
if (m_usage == DestSSARegisterStackLowLevelOperandUsage)
if ((m_usage == DestSSARegisterStackLowLevelOperandUsage) && (m_instr.operation != LLIL_REG_STACK_PHI))
return m_instr.GetRawOperandAsExpr(m_operandIndex).GetRawOperandAsSSARegisterStack(0);
if (m_usage == PartialSSARegisterStackSourceLowLevelOperandUsage)
return m_instr.GetRawOperandAsExpr(m_operandIndex).GetRawOperandAsPartialSSARegisterStackSource(0);
Expand Down Expand Up @@ -1290,6 +1301,8 @@ LowLevelILInstructionList LowLevelILOperand::GetExprList() const
{
if (m_type != ExprListLowLevelOperand)
throw LowLevelILInstructionAccessException();
if (m_operandIndex == 0)
return m_instr.GetRawOperandAsExprList(0);
return m_instr.GetRawOperandAsExpr(m_operandIndex).GetRawOperandAsExprList(0);
}

Expand Down Expand Up @@ -2585,7 +2598,11 @@ SSARegisterStack LowLevelILInstruction::GetDestSSARegisterStack() const
{
size_t operandIndex;
if (GetOperandIndexForUsage(DestSSARegisterStackLowLevelOperandUsage, operandIndex))
{
if (operation == LLIL_REG_STACK_PHI)
return GetRawOperandAsSSARegisterStack(operandIndex);
return GetRawOperandAsExpr(operandIndex).GetRawOperandAsSSARegisterStack(0);
}
throw LowLevelILInstructionAccessException();
}

Expand Down Expand Up @@ -2693,7 +2710,11 @@ SSARegister LowLevelILInstruction::GetHighSSARegister() const
{
size_t operandIndex;
if (GetOperandIndexForUsage(HighSSARegisterLowLevelOperandUsage, operandIndex))
{
if (operation == LLIL_REG_SPLIT_SSA)
return GetRawOperandAsSSARegister(operandIndex);
return GetRawOperandAsExpr(operandIndex).GetRawOperandAsSSARegister(0);
}
throw LowLevelILInstructionAccessException();
}

Expand All @@ -2711,7 +2732,11 @@ SSARegister LowLevelILInstruction::GetLowSSARegister() const
{
size_t operandIndex;
if (GetOperandIndexForUsage(LowSSARegisterLowLevelOperandUsage, operandIndex))
{
if (operation == LLIL_REG_SPLIT_SSA)
return GetRawOperandAsSSARegister(operandIndex);
return GetRawOperandAsExpr(operandIndex).GetRawOperandAsSSARegister(0);
}
throw LowLevelILInstructionAccessException();
}

Expand Down
Loading
Loading