summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--binaryninjaapi.h10
-rw-r--r--binaryninjacore.h7
-rw-r--r--function.cpp15
-rw-r--r--highlevelil.cpp20
-rw-r--r--highlevelilinstruction.cpp15
-rw-r--r--highlevelilinstruction.h12
-rw-r--r--python/highlevelil.py53
-rw-r--r--ui/flowgraphwidget.h1
-rw-r--r--ui/linearview.h1
-rw-r--r--ui/theme.h1
10 files changed, 123 insertions, 12 deletions
diff --git a/binaryninjaapi.h b/binaryninjaapi.h
index 7a864b58..af68eafd 100644
--- a/binaryninjaapi.h
+++ b/binaryninjaapi.h
@@ -3144,6 +3144,9 @@ __attribute__ ((format (printf, 1, 2)))
Ref<FlowGraph> GetUnresolvedStackAdjustmentGraph();
void RequestDebugReport(const std::string& name);
+
+ std::string GetGotoLabelName(uint64_t labelId);
+ void SetGotoLabelName(uint64_t labelId, const std::string& name);
};
class AdvancedFunctionAnalysisDataRequestor
@@ -4070,8 +4073,8 @@ __attribute__ ((format (printf, 1, 2)))
ExprId Jump(ExprId dest, const ILSourceLocation& loc = ILSourceLocation());
ExprId Return(const std::vector<ExprId>& sources, const ILSourceLocation& loc = ILSourceLocation());
ExprId NoReturn(const ILSourceLocation& loc = ILSourceLocation());
- ExprId Goto(size_t target, const ILSourceLocation& loc = ILSourceLocation());
- ExprId Label(size_t target, const ILSourceLocation& loc = ILSourceLocation());
+ ExprId Goto(uint64_t target, const ILSourceLocation& loc = ILSourceLocation());
+ ExprId Label(uint64_t target, const ILSourceLocation& loc = ILSourceLocation());
ExprId VarDeclare(const Variable& var, const ILSourceLocation& loc = ILSourceLocation());
ExprId VarInit(size_t size, const Variable& dest, ExprId src,
const ILSourceLocation& loc = ILSourceLocation());
@@ -4280,6 +4283,9 @@ __attribute__ ((format (printf, 1, 2)))
void VisitAllExprs(const std::function<bool(const HighLevelILInstruction& expr)>& func);
Ref<FlowGraph> CreateFunctionGraph(DisassemblySettings* settings = nullptr);
+
+ size_t GetExprIndexForLabel(uint64_t label);
+ std::set<size_t> GetUsesForLabel(uint64_t label);
};
class FunctionRecognizer
diff --git a/binaryninjacore.h b/binaryninjacore.h
index 0632b62d..b1a615f5 100644
--- a/binaryninjacore.h
+++ b/binaryninjacore.h
@@ -254,6 +254,7 @@ extern "C"
StructOffsetToken = 25,
StructOffsetByteValueToken = 26,
StructureHexDumpTextToken = 27,
+ GotoLabelToken = 28,
// The following are output by the analysis system automatically, these should
// not be used directly by the architecture plugins
CodeSymbolToken = 64,
@@ -3106,6 +3107,9 @@ __attribute__ ((format (printf, 1, 2)))
BINARYNINJACOREAPI BNFunctionAnalysisSkipOverride BNGetFunctionAnalysisSkipOverride(BNFunction* func);
BINARYNINJACOREAPI void BNSetFunctionAnalysisSkipOverride(BNFunction* func, BNFunctionAnalysisSkipOverride skip);
+ BINARYNINJACOREAPI char* BNGetGotoLabelName(BNFunction* func, uint64_t labelId);
+ BINARYNINJACOREAPI void BNSetUserGotoLabelName(BNFunction* func, uint64_t labelId, const char* name);
+
BINARYNINJACOREAPI BNAnalysisParameters BNGetParametersForAnalysis(BNBinaryView* view);
BINARYNINJACOREAPI void BNSetParametersForAnalysis(BNBinaryView* view, BNAnalysisParameters params);
BINARYNINJACOREAPI uint64_t BNGetMaxFunctionSizeForAnalysis(BNBinaryView* view);
@@ -3808,6 +3812,9 @@ __attribute__ ((format (printf, 1, 2)))
BINARYNINJACOREAPI size_t BNGetHighLevelILSSAMemoryVersionAtILInstruction(BNHighLevelILFunction* func,
size_t instr);
+ BINARYNINJACOREAPI size_t BNGetHighLevelILExprIndexForLabel(BNHighLevelILFunction* func, uint64_t label);
+ BINARYNINJACOREAPI size_t* BNGetHighLevelILUsesForLabel(BNHighLevelILFunction* func, uint64_t label, size_t* count);
+
// Type Libraries
BINARYNINJACOREAPI BNTypeLibrary* BNNewTypeLibrary(BNArchitecture* arch, const char* name);
BINARYNINJACOREAPI BNTypeLibrary* BNNewTypeLibraryReference(BNTypeLibrary* lib);
diff --git a/function.cpp b/function.cpp
index 304a59e2..e4e8af17 100644
--- a/function.cpp
+++ b/function.cpp
@@ -1718,6 +1718,21 @@ void Function::RequestDebugReport(const string& name)
}
+string Function::GetGotoLabelName(uint64_t labelId)
+{
+ char* name = BNGetGotoLabelName(m_object, labelId);
+ string result = name;
+ BNFreeString(name);
+ return result;
+}
+
+
+void Function::SetGotoLabelName(uint64_t labelId, const std::string& name)
+{
+ BNSetUserGotoLabelName(m_object, labelId, name.c_str());
+}
+
+
AdvancedFunctionAnalysisDataRequestor::AdvancedFunctionAnalysisDataRequestor(Function* func): m_func(func)
{
if (m_func)
diff --git a/highlevelil.cpp b/highlevelil.cpp
index f97b11d3..264af7c3 100644
--- a/highlevelil.cpp
+++ b/highlevelil.cpp
@@ -460,3 +460,23 @@ Ref<FlowGraph> HighLevelILFunction::CreateFunctionGraph(DisassemblySettings* set
BNFlowGraph* graph = BNCreateHighLevelILFunctionGraph(m_object, settings ? settings->GetObject() : nullptr);
return new CoreFlowGraph(graph);
}
+
+
+size_t HighLevelILFunction::GetExprIndexForLabel(uint64_t label)
+{
+ return BNGetHighLevelILExprIndexForLabel(m_object, label);
+}
+
+
+set<size_t> HighLevelILFunction::GetUsesForLabel(uint64_t label)
+{
+ size_t count;
+ size_t* uses = BNGetHighLevelILUsesForLabel(m_object, label, &count);
+
+ set<size_t> result;
+ for (size_t i = 0; i < count; i++)
+ result.insert(uses[i]);
+
+ BNFreeILInstructionList(uses);
+ return result;
+}
diff --git a/highlevelilinstruction.cpp b/highlevelilinstruction.cpp
index b5c3e7ed..88f833e0 100644
--- a/highlevelilinstruction.cpp
+++ b/highlevelilinstruction.cpp
@@ -793,6 +793,13 @@ void HighLevelILInstructionBase::UpdateRawOperand(size_t operandIndex, ExprId va
}
+void HighLevelILInstructionBase::UpdateRawOperandAsInteger(size_t operandIndex, uint64_t value)
+{
+ operands[operandIndex] = value;
+ function->UpdateInstructionOperand(exprIndex, operandIndex, value);
+}
+
+
void HighLevelILInstructionBase::UpdateRawOperandAsExprList(size_t operandIndex, const vector<HighLevelILInstruction>& exprs)
{
vector<ExprId> exprIndexList;
@@ -2208,11 +2215,11 @@ uint32_t HighLevelILInstruction::GetIntrinsic() const
}
-size_t HighLevelILInstruction::GetTarget() const
+uint64_t HighLevelILInstruction::GetTarget() const
{
size_t operandIndex;
if (GetOperandIndexForUsage(TargetHighLevelOperandUsage, operandIndex))
- return GetRawOperandAsIndex(operandIndex);
+ return GetRawOperandAsInteger(operandIndex);
throw HighLevelILInstructionAccessException();
}
@@ -2410,13 +2417,13 @@ ExprId HighLevelILFunction::NoReturn(const ILSourceLocation& loc)
}
-ExprId HighLevelILFunction::Goto(size_t target, const ILSourceLocation& loc)
+ExprId HighLevelILFunction::Goto(uint64_t target, const ILSourceLocation& loc)
{
return AddExprWithLocation(HLIL_GOTO, loc, 0, target);
}
-ExprId HighLevelILFunction::Label(size_t target, const ILSourceLocation& loc)
+ExprId HighLevelILFunction::Label(uint64_t target, const ILSourceLocation& loc)
{
return AddExprWithLocation(HLIL_LABEL, loc, 0, target);
}
diff --git a/highlevelilinstruction.h b/highlevelilinstruction.h
index aa872e67..fd140e24 100644
--- a/highlevelilinstruction.h
+++ b/highlevelilinstruction.h
@@ -298,6 +298,7 @@ namespace BinaryNinja
HighLevelILIndexList GetRawOperandAsIndexList(size_t operand) const;
void UpdateRawOperand(size_t operandIndex, ExprId value);
+ void UpdateRawOperandAsInteger(size_t operandIndex, uint64_t value);
void UpdateRawOperandAsSSAVariableList(size_t operandIndex, const std::vector<SSAVariable>& vars);
void UpdateRawOperandAsExprList(size_t operandIndex, const std::vector<HighLevelILInstruction>& exprs);
void UpdateRawOperandAsExprList(size_t operandIndex, const std::vector<size_t>& exprs);
@@ -411,7 +412,7 @@ namespace BinaryNinja
template <BNHighLevelILOperation N> int64_t GetConstant() const { return As<N>().GetConstant(); }
template <BNHighLevelILOperation N> int64_t GetVector() const { return As<N>().GetVector(); }
template <BNHighLevelILOperation N> uint32_t GetIntrinsic() const { return As<N>().GetIntrinsic(); }
- template <BNHighLevelILOperation N> size_t GetTarget() const { return As<N>().GetTarget(); }
+ template <BNHighLevelILOperation N> uint64_t GetTarget() const { return As<N>().GetTarget(); }
template <BNHighLevelILOperation N> HighLevelILInstructionList GetParameterExprs() const { return As<N>().GetParameterExprs(); }
template <BNHighLevelILOperation N> HighLevelILInstructionList GetSourceExprs() const { return As<N>().GetSourceExprs(); }
template <BNHighLevelILOperation N> HighLevelILInstructionList GetDestExprs() const { return As<N>().GetDestExprs(); }
@@ -438,6 +439,7 @@ namespace BinaryNinja
template <BNHighLevelILOperation N> void SetSourceSSAVariables(const std::vector<SSAVariable>& vars) { As<N>().SetSourceSSAVariables(vars); }
template <BNHighLevelILOperation N> void SetSourceMemoryVersion(size_t version) { return As<N>().SetSourceMemoryVersion(version); }
template <BNHighLevelILOperation N> void SetDestMemoryVersion(size_t version) { return As<N>().SetDestMemoryVersion(version); }
+ template <BNHighLevelILOperation N> void SetTarget(uint64_t target) { As<N>().SetTarget(target); }
bool GetOperandIndexForUsage(HighLevelILOperandUsage usage, size_t& operandIndex) const;
@@ -468,7 +470,7 @@ namespace BinaryNinja
int64_t GetConstant() const;
int64_t GetVector() const;
uint32_t GetIntrinsic() const;
- size_t GetTarget() const;
+ uint64_t GetTarget() const;
HighLevelILInstructionList GetParameterExprs() const;
HighLevelILInstructionList GetSourceExprs() const;
HighLevelILInstructionList GetDestExprs() const;
@@ -624,11 +626,13 @@ namespace BinaryNinja
};
template <> struct HighLevelILInstructionAccessor<HLIL_GOTO>: public HighLevelILInstructionBase
{
- size_t GetTarget() const { return GetRawOperandAsIndex(0); }
+ uint64_t GetTarget() const { return GetRawOperandAsInteger(0); }
+ void SetTarget(uint64_t target) { UpdateRawOperandAsInteger(0, target); }
};
template <> struct HighLevelILInstructionAccessor<HLIL_LABEL>: public HighLevelILInstructionBase
{
- size_t GetTarget() const { return GetRawOperandAsIndex(0); }
+ uint64_t GetTarget() const { return GetRawOperandAsInteger(0); }
+ void SetTarget(uint64_t target) { UpdateRawOperandAsInteger(0, target); }
};
template <> struct HighLevelILInstructionAccessor<HLIL_RET>: public HighLevelILInstructionBase
diff --git a/python/highlevelil.py b/python/highlevelil.py
index 6565253d..5cf94b34 100644
--- a/python/highlevelil.py
+++ b/python/highlevelil.py
@@ -72,6 +72,38 @@ class HighLevelILOperationAndSize(object):
self._size = value
+class GotoLabel(object):
+ def __init__(self, function, id):
+ self._function = function
+ self._id = id
+
+ @property
+ def label_id(self):
+ return self._id
+
+ @property
+ def name(self):
+ return core.BNGetGotoLabelName(self._function.source_function.handle, self._id)
+
+ @name.setter
+ def name(self, value):
+ core.BNSetUserGotoLabelName(self._function.source_function.handle, self._id, value)
+
+ @property
+ def definition(self):
+ return self._function.get_label(self._id)
+
+ @property
+ def uses(self):
+ return self._function.get_label_uses(self._id)
+
+ def __str__(self):
+ return self.name
+
+ def __repr__(self):
+ return "<label: %s>" % self.name
+
+
class HighLevelILInstruction(object):
"""
``class HighLevelILInstruction`` High Level Intermediate Language Instructions form an abstract syntax tree of
@@ -95,8 +127,8 @@ class HighLevelILInstruction(object):
HighLevelILOperation.HLIL_JUMP: [("dest", "expr")],
HighLevelILOperation.HLIL_RET: [("src", "expr_list")],
HighLevelILOperation.HLIL_NORET: [],
- HighLevelILOperation.HLIL_GOTO: [("target", "int")],
- HighLevelILOperation.HLIL_LABEL: [("target", "int")],
+ HighLevelILOperation.HLIL_GOTO: [("target", "label")],
+ HighLevelILOperation.HLIL_LABEL: [("target", "label")],
HighLevelILOperation.HLIL_VAR_DECLARE: [("var", "var")],
HighLevelILOperation.HLIL_VAR_INIT: [("dest", "var"), ("src", "expr")],
HighLevelILOperation.HLIL_VAR_INIT_SSA: [("dest", "var_ssa"), ("src", "expr")],
@@ -271,6 +303,8 @@ class HighLevelILInstruction(object):
value = instr.operands[i]
if (value & (1 << 63)) != 0:
value = None
+ elif operand_type == "label":
+ value = GotoLabel(self.function, instr.operands[i])
self._operands.append(value)
self.__dict__[name] = value
i += 1
@@ -877,6 +911,21 @@ class HighLevelILFunction(object):
return None
return result
+ def get_label(self, label_idx):
+ result = core.BNGetHighLevelILExprIndexForLabel(self.handle, label_idx)
+ if result >= core.BNGetHighLevelILExprCount(self.handle):
+ return None
+ return HighLevelILInstruction(self, result)
+
+ def get_label_uses(self, label_idx):
+ count = ctypes.c_ulonglong()
+ uses = core.BNGetHighLevelILUsesForLabel(self.handle, label_idx, count)
+ result = []
+ for i in range(0, count.value):
+ result.append(HighLevelILInstruction(self, uses[i]))
+ core.BNFreeILInstructionList(uses)
+ return result
+
class HighLevelILBasicBlock(basicblock.BasicBlock):
def __init__(self, view, handle, owner):
diff --git a/ui/flowgraphwidget.h b/ui/flowgraphwidget.h
index dc358871..e90bcdc5 100644
--- a/ui/flowgraphwidget.h
+++ b/ui/flowgraphwidget.h
@@ -155,6 +155,7 @@ protected:
void bindActions();
void navigateToAddress(uint64_t addr);
+ void navigateToGotoLabel(uint64_t label);
void setGraphInternal(FlowGraphRef graph, FlowGraphHistoryEntry* entry, bool useAddr, uint64_t addr, bool notify,
bool recenterWithPreviousGraph);
diff --git a/ui/linearview.h b/ui/linearview.h
index 46addd4f..2c9c5fcc 100644
--- a/ui/linearview.h
+++ b/ui/linearview.h
@@ -144,6 +144,7 @@ class BINARYNINJAUIAPI LinearView: public QAbstractScrollArea, public View, publ
void updateCache();
void refreshAtCurrentLocation();
bool navigateToAddress(uint64_t addr, bool center, bool updateHighlight, bool navByRef = false);
+ bool navigateToGotoLabel(uint64_t label);
void scrollLines(int count);
diff --git a/ui/theme.h b/ui/theme.h
index 462e38ed..0199b060 100644
--- a/ui/theme.h
+++ b/ui/theme.h
@@ -69,6 +69,7 @@ enum ThemeColor
UncertainColor,
NameSpaceColor,
NameSpaceSeparatorColor,
+ GotoLabelColor,
// Script console colors
ScriptConsoleOutputColor,