summaryrefslogtreecommitdiff
path: root/python
diff options
context:
space:
mode:
authorRusty Wagner <rusty.wagner@gmail.com>2022-08-16 20:49:02 -0400
committerRusty Wagner <rusty.wagner@gmail.com>2022-09-01 23:13:43 -0400
commit40bdfac7b71dd1cbe9223b82518053f80268e2a8 (patch)
treee53fc5710bb6e6844c1f09e967b715db0aac4444 /python
parent2f6ebaa0042f6a02b9fcbf49b742fc25887bfdb4 (diff)
Splitting of variables
Diffstat (limited to 'python')
-rw-r--r--python/function.py44
-rw-r--r--python/mediumlevelil.py16
2 files changed, 60 insertions, 0 deletions
diff --git a/python/function.py b/python/function.py
index 06a9beb5..93ed8b49 100644
--- a/python/function.py
+++ b/python/function.py
@@ -1397,6 +1397,21 @@ class Function:
core.BNFreeMergedVariableList(data, count.value)
return result
+ @property
+ def split_vars(self) -> List['variable.Variable']:
+ """
+ Set of variables that have been split with ``split_var``. These variables correspond
+ to those unique to each definition site and are obtained by using
+ ``MediumLevelILInstruction.get_split_var_for_definition`` at the definitions.
+ """
+ count = ctypes.c_ulonglong()
+ data = core.BNGetSplitVariables(self.handle, count)
+ result = []
+ for i in range(count.value):
+ result.append(Variable.from_BNVariable(self, data[i]))
+ core.BNFreeVariableList(data)
+ return result
+
def mark_recent_use(self) -> None:
core.BNMarkFunctionAsRecentlyUsed(self.handle)
@@ -3374,6 +3389,35 @@ class Function:
source_list[i].storage = sources[i].storage
core.BNUnmergeVariables(self.handle, target.to_BNVariable(), source_list, len(sources))
+ def split_var(self, var: 'variable.Variable') -> None:
+ """
+ ``split_var`` splits a varible at the definition site. The given ``var`` must be the
+ variable unique to the definition and should be obtained by using
+ ``MediumLevelILInstruction.get_split_var_for_definition`` at the definition site.
+
+ This function is not meant to split variables that have been previously merged. Use
+ ``unmerge_vars`` to split previously merged variables.
+
+ .. warning:: Binary Ninja automatically splits all variables that the analysis determines \
+ to be safely splittable. Splitting a variable manually with ``split_var`` can cause \
+ IL and decompilation to be incorrect. There are some patterns where variables can be safely \
+ split semantically but analysis cannot determine that it is safe. This function is provided \
+ to allow variable splitting to be performed in these cases by plugins or by the user.
+
+ :param Variable var: variable to split
+ """
+ core.BNSplitVariable(self.handle, var.to_BNVariable())
+
+ def unsplit_var(self, var: 'variable.Variable') -> None:
+ """
+ ``unsplit_var`` undoes varible splitting performed with ``split_var``. The given ``var``
+ must be the variable unique to the definition and should be obtained by using
+ ``MediumLevelILInstruction.get_split_var_for_definition`` at the definition site.
+
+ :param Variable var: variable to unsplit
+ """
+ core.BNUnsplitVariable(self.handle, var.to_BNVariable())
+
class AdvancedFunctionAnalysisDataRequestor:
def __init__(self, func: 'Function' = None):
diff --git a/python/mediumlevelil.py b/python/mediumlevelil.py
index 06298e6e..47e7e2e1 100644
--- a/python/mediumlevelil.py
+++ b/python/mediumlevelil.py
@@ -730,6 +730,22 @@ class MediumLevelILInstruction(BaseILInstruction):
core.BNGetMediumLevelILBranchDependence(self.function.handle, self.instr_index, branch_instr)
)
+ def get_split_var_for_definition(self, var: variable.Variable) -> variable.Variable:
+ """
+ Gets the unique variable for a definition instruction. This unique variable can be passed
+ to ``Function.split_var`` to split a variable at a definition. The given ``var`` is the
+ assigned variable to query.
+
+ :param Variable var: variable to query
+ :rtype: Variable
+ """
+ return variable.Variable(
+ self.function.source_function, var.source_type,
+ core.BNGetDefaultIndexForMediumLevelILVariableDefinition(
+ self.function.handle, var.to_BNVariable(), self.instr_index
+ ), var.storage
+ )
+
@property
def operation(self) -> MediumLevelILOperation:
return self.instr.operation