|
|
|
@ -1,9 +1,10 @@ |
|
|
|
|
import re |
|
|
|
|
import logging |
|
|
|
|
|
|
|
|
|
from typing import List |
|
|
|
|
from typing import List, Set, Dict, Union, Optional, Callable, Type, Sequence |
|
|
|
|
|
|
|
|
|
from slither.core.compilation_unit import SlitherCompilationUnit |
|
|
|
|
from slither.core.variables import Variable |
|
|
|
|
from slither.slithir.operations import ( |
|
|
|
|
Send, |
|
|
|
|
Transfer, |
|
|
|
@ -14,7 +15,7 @@ from slither.slithir.operations import ( |
|
|
|
|
InternalDynamicCall, |
|
|
|
|
Operation, |
|
|
|
|
) |
|
|
|
|
from slither.core.declarations import Modifier |
|
|
|
|
from slither.core.declarations import Modifier, Event |
|
|
|
|
from slither.core.solidity_types import UserDefinedType, MappingType |
|
|
|
|
from slither.core.declarations import Enum, Contract, Structure, Function |
|
|
|
|
from slither.core.solidity_types.elementary_type import ElementaryTypeName |
|
|
|
@ -29,7 +30,7 @@ logger = logging.getLogger("Slither.Format") |
|
|
|
|
# pylint: disable=anomalous-backslash-in-string |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def custom_format(compilation_unit: SlitherCompilationUnit, result): |
|
|
|
|
def custom_format(compilation_unit: SlitherCompilationUnit, result: Dict) -> None: |
|
|
|
|
elements = result["elements"] |
|
|
|
|
for element in elements: |
|
|
|
|
target = element["additional_fields"]["target"] |
|
|
|
@ -129,24 +130,24 @@ SOLIDITY_KEYWORDS += [ |
|
|
|
|
SOLIDITY_KEYWORDS += ElementaryTypeName |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def _name_already_use(slither, name): |
|
|
|
|
def _name_already_use(slither: SlitherCompilationUnit, name: str) -> bool: |
|
|
|
|
# Do not convert to a name used somewhere else |
|
|
|
|
if not KEY in slither.context: |
|
|
|
|
all_names = set() |
|
|
|
|
all_names: Set[str] = set() |
|
|
|
|
for contract in slither.contracts_derived: |
|
|
|
|
all_names = all_names.union({st.name for st in contract.structures}) |
|
|
|
|
all_names = all_names.union({f.name for f in contract.functions_and_modifiers}) |
|
|
|
|
all_names = all_names.union({e.name for e in contract.enums}) |
|
|
|
|
all_names = all_names.union({s.name for s in contract.state_variables}) |
|
|
|
|
all_names = all_names.union({s.name for s in contract.state_variables if s.name}) |
|
|
|
|
|
|
|
|
|
for function in contract.functions: |
|
|
|
|
all_names = all_names.union({v.name for v in function.variables}) |
|
|
|
|
all_names = all_names.union({v.name for v in function.variables if v.name}) |
|
|
|
|
|
|
|
|
|
slither.context[KEY] = all_names |
|
|
|
|
return name in slither.context[KEY] |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def _convert_CapWords(original_name, slither): |
|
|
|
|
def _convert_CapWords(original_name: str, slither: SlitherCompilationUnit) -> str: |
|
|
|
|
name = original_name.capitalize() |
|
|
|
|
|
|
|
|
|
while "_" in name: |
|
|
|
@ -162,10 +163,13 @@ def _convert_CapWords(original_name, slither): |
|
|
|
|
return name |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def _convert_mixedCase(original_name, compilation_unit: SlitherCompilationUnit): |
|
|
|
|
name = original_name |
|
|
|
|
if isinstance(name, bytes): |
|
|
|
|
name = name.decode("utf8") |
|
|
|
|
def _convert_mixedCase( |
|
|
|
|
original_name: Union[str, bytes], compilation_unit: SlitherCompilationUnit |
|
|
|
|
) -> str: |
|
|
|
|
if isinstance(original_name, bytes): |
|
|
|
|
name = original_name.decode("utf8") |
|
|
|
|
else: |
|
|
|
|
name = original_name |
|
|
|
|
|
|
|
|
|
while "_" in name: |
|
|
|
|
offset = name.find("_") |
|
|
|
@ -174,13 +178,15 @@ def _convert_mixedCase(original_name, compilation_unit: SlitherCompilationUnit): |
|
|
|
|
|
|
|
|
|
name = name[0].lower() + name[1:] |
|
|
|
|
if _name_already_use(compilation_unit, name): |
|
|
|
|
raise FormatImpossible(f"{original_name} cannot be converted to {name} (already used)") |
|
|
|
|
raise FormatImpossible(f"{original_name} cannot be converted to {name} (already used)") # type: ignore |
|
|
|
|
if name in SOLIDITY_KEYWORDS: |
|
|
|
|
raise FormatImpossible(f"{original_name} cannot be converted to {name} (Solidity keyword)") |
|
|
|
|
raise FormatImpossible(f"{original_name} cannot be converted to {name} (Solidity keyword)") # type: ignore |
|
|
|
|
return name |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def _convert_UPPER_CASE_WITH_UNDERSCORES(name, compilation_unit: SlitherCompilationUnit): |
|
|
|
|
def _convert_UPPER_CASE_WITH_UNDERSCORES( |
|
|
|
|
name: str, compilation_unit: SlitherCompilationUnit |
|
|
|
|
) -> str: |
|
|
|
|
if _name_already_use(compilation_unit, name.upper()): |
|
|
|
|
raise FormatImpossible(f"{name} cannot be converted to {name.upper()} (already used)") |
|
|
|
|
if name.upper() in SOLIDITY_KEYWORDS: |
|
|
|
@ -188,7 +194,10 @@ def _convert_UPPER_CASE_WITH_UNDERSCORES(name, compilation_unit: SlitherCompilat |
|
|
|
|
return name.upper() |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
conventions = { |
|
|
|
|
TARGET_TYPE = Union[Contract, Variable, Function] |
|
|
|
|
CONVENTION_F_TYPE = Callable[[str, SlitherCompilationUnit], str] |
|
|
|
|
|
|
|
|
|
conventions: Dict[str, CONVENTION_F_TYPE] = { |
|
|
|
|
"CapWords": _convert_CapWords, |
|
|
|
|
"mixedCase": _convert_mixedCase, |
|
|
|
|
"UPPER_CASE_WITH_UNDERSCORES": _convert_UPPER_CASE_WITH_UNDERSCORES, |
|
|
|
@ -203,7 +212,9 @@ conventions = { |
|
|
|
|
################################################################################### |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def _get_from_contract(compilation_unit: SlitherCompilationUnit, element, name, getter): |
|
|
|
|
def _get_from_contract( |
|
|
|
|
compilation_unit: SlitherCompilationUnit, element: Dict, name: str, getter: str |
|
|
|
|
) -> TARGET_TYPE: |
|
|
|
|
scope = compilation_unit.get_scope(element["source_mapping"]["filename_absolute"]) |
|
|
|
|
contract_name = element["type_specific_fields"]["parent"]["name"] |
|
|
|
|
contract = scope.get_contract_from_name(contract_name) |
|
|
|
@ -218,9 +229,13 @@ def _get_from_contract(compilation_unit: SlitherCompilationUnit, element, name, |
|
|
|
|
################################################################################### |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def _patch(compilation_unit: SlitherCompilationUnit, result, element, _target): |
|
|
|
|
def _patch( |
|
|
|
|
compilation_unit: SlitherCompilationUnit, result: Dict, element: Dict, _target: str |
|
|
|
|
) -> None: |
|
|
|
|
scope = compilation_unit.get_scope(element["source_mapping"]["filename_absolute"]) |
|
|
|
|
|
|
|
|
|
target: Optional[TARGET_TYPE] = None |
|
|
|
|
|
|
|
|
|
if _target == "contract": |
|
|
|
|
target = scope.get_contract_from_name(element["name"]) |
|
|
|
|
|
|
|
|
@ -257,7 +272,9 @@ def _patch(compilation_unit: SlitherCompilationUnit, result, element, _target): |
|
|
|
|
] |
|
|
|
|
param_name = element["name"] |
|
|
|
|
contract = scope.get_contract_from_name(contract_name) |
|
|
|
|
assert contract |
|
|
|
|
function = contract.get_function_from_full_name(function_sig) |
|
|
|
|
assert function |
|
|
|
|
target = function.get_local_variable_from_name(param_name) |
|
|
|
|
|
|
|
|
|
elif _target in ["variable", "variable_constant"]: |
|
|
|
@ -271,7 +288,9 @@ def _patch(compilation_unit: SlitherCompilationUnit, result, element, _target): |
|
|
|
|
] |
|
|
|
|
var_name = element["name"] |
|
|
|
|
contract = scope.get_contract_from_name(contract_name) |
|
|
|
|
assert contract |
|
|
|
|
function = contract.get_function_from_full_name(function_sig) |
|
|
|
|
assert function |
|
|
|
|
target = function.get_local_variable_from_name(var_name) |
|
|
|
|
# State variable |
|
|
|
|
else: |
|
|
|
@ -287,6 +306,7 @@ def _patch(compilation_unit: SlitherCompilationUnit, result, element, _target): |
|
|
|
|
else: |
|
|
|
|
raise FormatError("Unknown naming convention! " + _target) |
|
|
|
|
|
|
|
|
|
assert target |
|
|
|
|
_explore( |
|
|
|
|
compilation_unit, result, target, conventions[element["additional_fields"]["convention"]] |
|
|
|
|
) |
|
|
|
@ -310,7 +330,7 @@ RE_MAPPING = ( |
|
|
|
|
) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def _is_var_declaration(slither, filename, start): |
|
|
|
|
def _is_var_declaration(slither: SlitherCompilationUnit, filename: str, start: int) -> bool: |
|
|
|
|
""" |
|
|
|
|
Detect usage of 'var ' for Solidity < 0.5 |
|
|
|
|
:param slither: |
|
|
|
@ -319,12 +339,19 @@ def _is_var_declaration(slither, filename, start): |
|
|
|
|
:return: |
|
|
|
|
""" |
|
|
|
|
v = "var " |
|
|
|
|
return slither.source_code[filename][start : start + len(v)] == v |
|
|
|
|
return slither.core.source_code[filename][start : start + len(v)] == v |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def _explore_type( # pylint: disable=too-many-arguments,too-many-locals,too-many-branches |
|
|
|
|
slither, result, target, convert, custom_type, filename_source_code, start, end |
|
|
|
|
): |
|
|
|
|
slither: SlitherCompilationUnit, |
|
|
|
|
result: Dict, |
|
|
|
|
target: TARGET_TYPE, |
|
|
|
|
convert: CONVENTION_F_TYPE, |
|
|
|
|
custom_type: Optional[Union[Type, List[Type]]], |
|
|
|
|
filename_source_code: str, |
|
|
|
|
start: int, |
|
|
|
|
end: int, |
|
|
|
|
) -> None: |
|
|
|
|
if isinstance(custom_type, UserDefinedType): |
|
|
|
|
# Patch type based on contract/enum |
|
|
|
|
if isinstance(custom_type.type, (Enum, Contract)): |
|
|
|
@ -358,7 +385,7 @@ def _explore_type( # pylint: disable=too-many-arguments,too-many-locals,too-man |
|
|
|
|
# Structure contain a list of elements, that might need patching |
|
|
|
|
# .elems return a list of VariableStructure |
|
|
|
|
_explore_variables_declaration( |
|
|
|
|
slither, custom_type.type.elems.values(), result, target, convert |
|
|
|
|
slither, list(custom_type.type.elems.values()), result, target, convert |
|
|
|
|
) |
|
|
|
|
|
|
|
|
|
if isinstance(custom_type, MappingType): |
|
|
|
@ -377,7 +404,7 @@ def _explore_type( # pylint: disable=too-many-arguments,too-many-locals,too-man |
|
|
|
|
|
|
|
|
|
full_txt_start = start |
|
|
|
|
full_txt_end = end |
|
|
|
|
full_txt = slither.source_code[filename_source_code].encode("utf8")[ |
|
|
|
|
full_txt = slither.core.source_code[filename_source_code].encode("utf8")[ |
|
|
|
|
full_txt_start:full_txt_end |
|
|
|
|
] |
|
|
|
|
re_match = re.match(RE_MAPPING, full_txt) |
|
|
|
@ -417,14 +444,19 @@ def _explore_type( # pylint: disable=too-many-arguments,too-many-locals,too-man |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def _explore_variables_declaration( # pylint: disable=too-many-arguments,too-many-locals,too-many-nested-blocks |
|
|
|
|
slither, variables, result, target, convert, patch_comment=False |
|
|
|
|
): |
|
|
|
|
slither: SlitherCompilationUnit, |
|
|
|
|
variables: Sequence[Variable], |
|
|
|
|
result: Dict, |
|
|
|
|
target: TARGET_TYPE, |
|
|
|
|
convert: CONVENTION_F_TYPE, |
|
|
|
|
patch_comment: bool = False, |
|
|
|
|
) -> None: |
|
|
|
|
for variable in variables: |
|
|
|
|
# First explore the type of the variable |
|
|
|
|
filename_source_code = variable.source_mapping.filename.absolute |
|
|
|
|
full_txt_start = variable.source_mapping.start |
|
|
|
|
full_txt_end = full_txt_start + variable.source_mapping.length |
|
|
|
|
full_txt = slither.source_code[filename_source_code].encode("utf8")[ |
|
|
|
|
full_txt = slither.core.source_code[filename_source_code].encode("utf8")[ |
|
|
|
|
full_txt_start:full_txt_end |
|
|
|
|
] |
|
|
|
|
|
|
|
|
@ -442,6 +474,8 @@ def _explore_variables_declaration( # pylint: disable=too-many-arguments,too-ma |
|
|
|
|
# If the variable is the target |
|
|
|
|
if variable == target: |
|
|
|
|
old_str = variable.name |
|
|
|
|
if old_str is None: |
|
|
|
|
old_str = "" |
|
|
|
|
new_str = convert(old_str, slither) |
|
|
|
|
|
|
|
|
|
loc_start = full_txt_start + full_txt.find(old_str.encode("utf8")) |
|
|
|
@ -458,10 +492,10 @@ def _explore_variables_declaration( # pylint: disable=too-many-arguments,too-ma |
|
|
|
|
idx = len(func.parameters) - func.parameters.index(variable) + 1 |
|
|
|
|
first_line = end_line - idx - 2 |
|
|
|
|
|
|
|
|
|
potential_comments = slither.source_code[filename_source_code].encode( |
|
|
|
|
potential_comments_ = slither.core.source_code[filename_source_code].encode( |
|
|
|
|
"utf8" |
|
|
|
|
) |
|
|
|
|
potential_comments = potential_comments.splitlines(keepends=True)[ |
|
|
|
|
potential_comments = potential_comments_.splitlines(keepends=True)[ |
|
|
|
|
first_line : end_line - 1 |
|
|
|
|
] |
|
|
|
|
|
|
|
|
@ -491,10 +525,16 @@ def _explore_variables_declaration( # pylint: disable=too-many-arguments,too-ma |
|
|
|
|
idx_beginning += len(line) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def _explore_structures_declaration(slither, structures, result, target, convert): |
|
|
|
|
def _explore_structures_declaration( |
|
|
|
|
slither: SlitherCompilationUnit, |
|
|
|
|
structures: Sequence[Structure], |
|
|
|
|
result: Dict, |
|
|
|
|
target: TARGET_TYPE, |
|
|
|
|
convert: CONVENTION_F_TYPE, |
|
|
|
|
) -> None: |
|
|
|
|
for st in structures: |
|
|
|
|
# Explore the variable declared within the structure (VariableStructure) |
|
|
|
|
_explore_variables_declaration(slither, st.elems.values(), result, target, convert) |
|
|
|
|
_explore_variables_declaration(slither, list(st.elems.values()), result, target, convert) |
|
|
|
|
|
|
|
|
|
# If the structure is the target |
|
|
|
|
if st == target: |
|
|
|
@ -504,7 +544,7 @@ def _explore_structures_declaration(slither, structures, result, target, convert |
|
|
|
|
filename_source_code = st.source_mapping.filename.absolute |
|
|
|
|
full_txt_start = st.source_mapping.start |
|
|
|
|
full_txt_end = full_txt_start + st.source_mapping.length |
|
|
|
|
full_txt = slither.source_code[filename_source_code].encode("utf8")[ |
|
|
|
|
full_txt = slither.core.source_code[filename_source_code].encode("utf8")[ |
|
|
|
|
full_txt_start:full_txt_end |
|
|
|
|
] |
|
|
|
|
|
|
|
|
@ -517,7 +557,13 @@ def _explore_structures_declaration(slither, structures, result, target, convert |
|
|
|
|
create_patch(result, filename_source_code, loc_start, loc_end, old_str, new_str) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def _explore_events_declaration(slither, events, result, target, convert): |
|
|
|
|
def _explore_events_declaration( |
|
|
|
|
slither: SlitherCompilationUnit, |
|
|
|
|
events: Sequence[Event], |
|
|
|
|
result: Dict, |
|
|
|
|
target: TARGET_TYPE, |
|
|
|
|
convert: CONVENTION_F_TYPE, |
|
|
|
|
) -> None: |
|
|
|
|
for event in events: |
|
|
|
|
# Explore the parameters |
|
|
|
|
_explore_variables_declaration(slither, event.elems, result, target, convert) |
|
|
|
@ -535,7 +581,7 @@ def _explore_events_declaration(slither, events, result, target, convert): |
|
|
|
|
create_patch(result, filename_source_code, loc_start, loc_end, old_str, new_str) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def get_ir_variables(ir): |
|
|
|
|
def get_ir_variables(ir: Operation) -> List[Union[Variable, Function]]: |
|
|
|
|
all_vars = ir.read |
|
|
|
|
|
|
|
|
|
if isinstance(ir, (InternalCall, InternalDynamicCall, HighLevelCall)): |
|
|
|
@ -553,9 +599,15 @@ def get_ir_variables(ir): |
|
|
|
|
return [v for v in all_vars if v] |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def _explore_irs(slither, irs: List[Operation], result, target, convert): |
|
|
|
|
def _explore_irs( |
|
|
|
|
slither: SlitherCompilationUnit, |
|
|
|
|
irs: List[Operation], |
|
|
|
|
result: Dict, |
|
|
|
|
target: TARGET_TYPE, |
|
|
|
|
convert: CONVENTION_F_TYPE, |
|
|
|
|
) -> None: |
|
|
|
|
# pylint: disable=too-many-locals |
|
|
|
|
if irs is None: |
|
|
|
|
if not irs: |
|
|
|
|
return |
|
|
|
|
for ir in irs: |
|
|
|
|
for v in get_ir_variables(ir): |
|
|
|
@ -568,7 +620,7 @@ def _explore_irs(slither, irs: List[Operation], result, target, convert): |
|
|
|
|
filename_source_code = source_mapping.filename.absolute |
|
|
|
|
full_txt_start = source_mapping.start |
|
|
|
|
full_txt_end = full_txt_start + source_mapping.length |
|
|
|
|
full_txt = slither.source_code[filename_source_code].encode("utf8")[ |
|
|
|
|
full_txt = slither.core.source_code[filename_source_code].encode("utf8")[ |
|
|
|
|
full_txt_start:full_txt_end |
|
|
|
|
] |
|
|
|
|
|
|
|
|
@ -600,7 +652,13 @@ def _explore_irs(slither, irs: List[Operation], result, target, convert): |
|
|
|
|
) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def _explore_functions(slither, functions, result, target, convert): |
|
|
|
|
def _explore_functions( |
|
|
|
|
slither: SlitherCompilationUnit, |
|
|
|
|
functions: List[Function], |
|
|
|
|
result: Dict, |
|
|
|
|
target: TARGET_TYPE, |
|
|
|
|
convert: CONVENTION_F_TYPE, |
|
|
|
|
) -> None: |
|
|
|
|
for function in functions: |
|
|
|
|
_explore_variables_declaration(slither, function.variables, result, target, convert, True) |
|
|
|
|
_explore_irs(slither, function.all_slithir_operations(), result, target, convert) |
|
|
|
@ -612,7 +670,7 @@ def _explore_functions(slither, functions, result, target, convert): |
|
|
|
|
filename_source_code = function.source_mapping.filename.absolute |
|
|
|
|
full_txt_start = function.source_mapping.start |
|
|
|
|
full_txt_end = full_txt_start + function.source_mapping.length |
|
|
|
|
full_txt = slither.source_code[filename_source_code].encode("utf8")[ |
|
|
|
|
full_txt = slither.core.source_code[filename_source_code].encode("utf8")[ |
|
|
|
|
full_txt_start:full_txt_end |
|
|
|
|
] |
|
|
|
|
|
|
|
|
@ -628,7 +686,13 @@ def _explore_functions(slither, functions, result, target, convert): |
|
|
|
|
create_patch(result, filename_source_code, loc_start, loc_end, old_str, new_str) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def _explore_enums(slither, enums, result, target, convert): |
|
|
|
|
def _explore_enums( |
|
|
|
|
slither: SlitherCompilationUnit, |
|
|
|
|
enums: Sequence[Enum], |
|
|
|
|
result: Dict, |
|
|
|
|
target: TARGET_TYPE, |
|
|
|
|
convert: CONVENTION_F_TYPE, |
|
|
|
|
) -> None: |
|
|
|
|
for enum in enums: |
|
|
|
|
if enum == target: |
|
|
|
|
old_str = enum.name |
|
|
|
@ -637,7 +701,7 @@ def _explore_enums(slither, enums, result, target, convert): |
|
|
|
|
filename_source_code = enum.source_mapping.filename.absolute |
|
|
|
|
full_txt_start = enum.source_mapping.start |
|
|
|
|
full_txt_end = full_txt_start + enum.source_mapping.length |
|
|
|
|
full_txt = slither.source_code[filename_source_code].encode("utf8")[ |
|
|
|
|
full_txt = slither.core.source_code[filename_source_code].encode("utf8")[ |
|
|
|
|
full_txt_start:full_txt_end |
|
|
|
|
] |
|
|
|
|
|
|
|
|
@ -650,7 +714,13 @@ def _explore_enums(slither, enums, result, target, convert): |
|
|
|
|
create_patch(result, filename_source_code, loc_start, loc_end, old_str, new_str) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def _explore_contract(slither, contract, result, target, convert): |
|
|
|
|
def _explore_contract( |
|
|
|
|
slither: SlitherCompilationUnit, |
|
|
|
|
contract: Contract, |
|
|
|
|
result: Dict, |
|
|
|
|
target: TARGET_TYPE, |
|
|
|
|
convert: CONVENTION_F_TYPE, |
|
|
|
|
) -> None: |
|
|
|
|
_explore_variables_declaration(slither, contract.state_variables, result, target, convert) |
|
|
|
|
_explore_structures_declaration(slither, contract.structures, result, target, convert) |
|
|
|
|
_explore_functions(slither, contract.functions_and_modifiers, result, target, convert) |
|
|
|
@ -660,7 +730,7 @@ def _explore_contract(slither, contract, result, target, convert): |
|
|
|
|
filename_source_code = contract.source_mapping.filename.absolute |
|
|
|
|
full_txt_start = contract.source_mapping.start |
|
|
|
|
full_txt_end = full_txt_start + contract.source_mapping.length |
|
|
|
|
full_txt = slither.source_code[filename_source_code].encode("utf8")[ |
|
|
|
|
full_txt = slither.core.source_code[filename_source_code].encode("utf8")[ |
|
|
|
|
full_txt_start:full_txt_end |
|
|
|
|
] |
|
|
|
|
|
|
|
|
@ -677,7 +747,12 @@ def _explore_contract(slither, contract, result, target, convert): |
|
|
|
|
create_patch(result, filename_source_code, loc_start, loc_end, old_str, new_str) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def _explore(compilation_unit: SlitherCompilationUnit, result, target, convert): |
|
|
|
|
def _explore( |
|
|
|
|
compilation_unit: SlitherCompilationUnit, |
|
|
|
|
result: Dict, |
|
|
|
|
target: TARGET_TYPE, |
|
|
|
|
convert: CONVENTION_F_TYPE, |
|
|
|
|
) -> None: |
|
|
|
|
for contract in compilation_unit.contracts_derived: |
|
|
|
|
_explore_contract(compilation_unit, contract, result, target, convert) |
|
|
|
|
|
|
|
|
|