From dabffe3630e1c6cee52142c589df36dec029c67d Mon Sep 17 00:00:00 2001 From: Josselin Date: Thu, 8 Nov 2018 09:07:01 +0100 Subject: [PATCH] API taint changes: - Change taint.state_variables -> all_variables (track also slithIR variables) - Remove taint.calls (include in all_variables) --- .../{state_variables.py => all_variables.py} | 24 ++++++-- slither/analyses/taint/calls.py | 58 ------------------- 2 files changed, 20 insertions(+), 62 deletions(-) rename slither/analyses/taint/{state_variables.py => all_variables.py} (77%) delete mode 100644 slither/analyses/taint/calls.py diff --git a/slither/analyses/taint/state_variables.py b/slither/analyses/taint/all_variables.py similarity index 77% rename from slither/analyses/taint/state_variables.py rename to slither/analyses/taint/all_variables.py index f96853d7d..3f12ce967 100644 --- a/slither/analyses/taint/state_variables.py +++ b/slither/analyses/taint/all_variables.py @@ -10,10 +10,10 @@ from slither.core.declarations.solidity_variables import \ SolidityVariableComposed from slither.core.variables.state_variable import StateVariable from slither.slithir.operations import Index, Member, OperationWithLValue -from slither.slithir.variables import ReferenceVariable, TemporaryVariable +from slither.slithir.variables import ReferenceVariable#, TemporaryVariable from .common import iterate_over_irs -KEY = 'TAINT_STATE_VARIABLES' +KEY = 'TAINT_ALL_VARIABLES' def _transfer_func(ir, read, refs, taints): if isinstance(ir, OperationWithLValue) and any(var_read in taints for var_read in read): @@ -33,7 +33,7 @@ def _visit_node(node, visited): taints = iterate_over_irs(node.irs, _transfer_func, taints) - taints = [v for v in taints if not isinstance(v, (TemporaryVariable, ReferenceVariable))] +# taints = [v for v in taints if not isinstance(v, (TemporaryVariable, ReferenceVariable))] node.function.slither.context[KEY] = list(set(taints)) @@ -59,12 +59,14 @@ def _run_taint(slither, initial_taint): slither.context[KEY] = list(set(slither.context[KEY] + function.parameters)) _visit_node(function.entry_point, []) - slither.context[KEY] = [v for v in prev_taints if isinstance(v, StateVariable)] + slither.context[KEY] = prev_taints # [v for v in prev_taints if isinstance(v, StateVariable)] def run_taint(slither, initial_taint=None): if initial_taint is None: initial_taint = [SolidityVariableComposed('msg.sender')] initial_taint += [SolidityVariableComposed('msg.value')] + initial_taint += [SolidityVariableComposed('msg.data')] + initial_taint += [SolidityVariableComposed('tx.origin')] if KEY not in slither.context: _run_taint(slither, initial_taint) @@ -80,3 +82,17 @@ def get_taint(slither, initial_taint=None): """ run_taint(slither, initial_taint) return slither.context[KEY] + +def is_tainted(slither, variable): + """ + Returns if the variable is tainted by inputs + Args: + slither + variable (Variable) + Returns: + bool + """ + if KEY not in slither.context: + run_taint(slither) + + return variable in slither.context[KEY] diff --git a/slither/analyses/taint/calls.py b/slither/analyses/taint/calls.py deleted file mode 100644 index ac3e08260..000000000 --- a/slither/analyses/taint/calls.py +++ /dev/null @@ -1,58 +0,0 @@ -""" - Compute taint on call - - use taint from state_variable - - call from slithIR with a taint set to yes means its destination is tainted -""" -from slither.analyses.taint.state_variables import get_taint as get_taint_state -from slither.core.declarations import SolidityVariableComposed -from slither.slithir.operations import (HighLevelCall, Index, LowLevelCall, - Member, OperationWithLValue, Send, - Transfer) -from slither.slithir.variables import ReferenceVariable - -from .common import iterate_over_irs - -KEY = 'TAINT_CALL_DESTINATION' - -def _transfer_func(ir, read, refs, taints): - if isinstance(ir, OperationWithLValue) and any(var_read in taints for var_read in read): - taints += [ir.lvalue] - lvalue = ir.lvalue - while isinstance(lvalue, ReferenceVariable): - taints += [refs[lvalue]] - lvalue = refs[lvalue] - if isinstance(ir, (HighLevelCall, LowLevelCall, Transfer, Send)): - if ir.destination in taints: - ir.context[KEY] = True - - return taints - -def _visit_node(node, visited, taints): - if node in visited: - return - - visited += [node] - - taints = iterate_over_irs(node.irs, _transfer_func, taints) - - for son in node.sons: - _visit_node(son, visited, taints) - -def _run_taint(slither, initial_taint): - if KEY in slither.context: - return - for contract in slither.contracts: - for function in contract.functions: - if not function.is_implemented: - continue - _visit_node(function.entry_point, [], initial_taint + function.parameters) - -def run_taint(slither): - initial_taint = get_taint_state(slither) - initial_taint += [SolidityVariableComposed('msg.sender')] - - if KEY not in slither.context: - _run_taint(slither, initial_taint) -