|
|
@ -2,6 +2,7 @@ import plyvel |
|
|
|
import binascii |
|
|
|
import binascii |
|
|
|
import rlp |
|
|
|
import rlp |
|
|
|
import hashlib |
|
|
|
import hashlib |
|
|
|
|
|
|
|
import logging |
|
|
|
from ethereum import utils |
|
|
|
from ethereum import utils |
|
|
|
from ethereum.block import BlockHeader, Block |
|
|
|
from ethereum.block import BlockHeader, Block |
|
|
|
from mythril.leveldb.state import State, Account |
|
|
|
from mythril.leveldb.state import State, Account |
|
|
@ -40,27 +41,32 @@ class EthLevelDB(object): |
|
|
|
self.headBlockHeader = None |
|
|
|
self.headBlockHeader = None |
|
|
|
self.headState = None |
|
|
|
self.headState = None |
|
|
|
|
|
|
|
|
|
|
|
def get_contracts(self, search_all): |
|
|
|
def get_contracts(self): |
|
|
|
''' |
|
|
|
''' |
|
|
|
iterate through contracts with non-zero balance by default or all if search_all is set |
|
|
|
iterate through all contracts |
|
|
|
''' |
|
|
|
''' |
|
|
|
for account in self._get_head_state().get_all_accounts(): |
|
|
|
for account in self._get_head_state().get_all_accounts(): |
|
|
|
if account.code is not None and (search_all or account.balance != 0): |
|
|
|
if account.code is not None: |
|
|
|
code = _encode_hex(account.code) |
|
|
|
code = _encode_hex(account.code) |
|
|
|
md5 = hashlib.md5() |
|
|
|
contract = ETHContract(code) |
|
|
|
md5.update(code.encode('UTF-8')) |
|
|
|
|
|
|
|
contract_hash = md5.digest() |
|
|
|
|
|
|
|
contract = ETHContract(code, name=contract_hash.hex()) |
|
|
|
|
|
|
|
yield contract, _encode_hex(account.address), account.balance |
|
|
|
yield contract, _encode_hex(account.address), account.balance |
|
|
|
|
|
|
|
|
|
|
|
def search(self, expression, search_all, callback_func): |
|
|
|
def search(self, expression, callback_func): |
|
|
|
''' |
|
|
|
''' |
|
|
|
searches through non-zero balance contracts |
|
|
|
searches through non-zero balance contracts |
|
|
|
''' |
|
|
|
''' |
|
|
|
for contract, address, balance in self.get_contracts(search_all): |
|
|
|
cnt = 0 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
for contract, address, balance in self.get_contracts(): |
|
|
|
|
|
|
|
|
|
|
|
if contract.matches_expression(expression): |
|
|
|
if contract.matches_expression(expression): |
|
|
|
callback_func(contract.name, contract, [address], [balance]) |
|
|
|
callback_func(contract.name, contract, [address], [balance]) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
cnt += 1 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if not cnt % 1000: |
|
|
|
|
|
|
|
logging.info("Searched %d contracts" % cnt) |
|
|
|
|
|
|
|
|
|
|
|
def eth_getBlockHeaderByNumber(self, number): |
|
|
|
def eth_getBlockHeaderByNumber(self, number): |
|
|
|
''' |
|
|
|
''' |
|
|
|
gets block header by block number |
|
|
|
gets block header by block number |
|
|
|