Beispiel #1
0
class _Account(rlp.Serializable):
    fields = [
        ("nonce", big_endian_int),
        ("balance", big_endian_int),
        ("storage", trie_root),
        ("code_hash", hash32),
        ("full_shard_id", BigEndianInt(4)),
    ]
Beispiel #2
0
class _Account(rlp.Serializable):
    fields = [
        ('nonce', big_endian_int),
        ('balance', big_endian_int),
        ('storage', trie_root),
        ('code_hash', hash32),
        ('full_shard_id', BigEndianInt(4)),
    ]
Beispiel #3
0
class _Account(rlp.Serializable):
    fields = [
        ("nonce", big_endian_int),
        ("token_balances", binary),
        ("storage", trie_root),
        ("code_hash", hash32),
        ("full_shard_key", BigEndianInt(4)),
        ("optional", binary),
    ]
Beispiel #4
0
class Account(rlp.Serializable):

    fields = [
        ('nonce', big_endian_int),
        ('balance', big_endian_int),
        ('storage', trie_root),
        ('code_hash', hash32),
        ('full_shard_id', BigEndianInt(4)),
    ]

    def __init__(self,
                 nonce,
                 balance,
                 storage,
                 code_hash,
                 full_shard_id,
                 env,
                 address,
                 db=None):
        self.db = env.db if db is None else db
        assert isinstance(db, Db)
        self.env = env
        self.address = address
        super(Account, self).__init__(nonce, balance, storage, code_hash,
                                      full_shard_id)
        self.storage_cache = {}
        self.storage_trie = SecureTrie(Trie(self.db))
        self.storage_trie.root_hash = self.storage
        self.touched = False
        self.existent_at_start = True
        self._mutable = True
        self.deleted = False

    def commit(self):
        for k, v in self.storage_cache.items():
            if v:
                self.storage_trie.update(utils.encode_int32(k), rlp.encode(v))
            else:
                self.storage_trie.delete(utils.encode_int32(k))
        self.storage_cache = {}
        self.storage = self.storage_trie.root_hash

    @property
    def code(self):
        return self.db[self.code_hash]

    @code.setter
    def code(self, value):
        self.code_hash = utils.sha3(value)
        # Technically a db storage leak, but doesn't really matter; the only
        # thing that fails to get garbage collected is when code disappears due
        # to a suicide
        self.db.put(self.code_hash, value)

    def get_storage_data(self, key):
        if key not in self.storage_cache:
            v = self.storage_trie.get(utils.encode_int32(key))
            self.storage_cache[key] = utils.big_endian_to_int(
                rlp.decode(v) if v else b'')
        return self.storage_cache[key]

    def set_storage_data(self, key, value):
        self.storage_cache[key] = value

    @classmethod
    def blank_account(cls,
                      env,
                      address,
                      full_shard_id,
                      initial_nonce=0,
                      db=None):
        if db is None:
            db = env.db
        db.put(BLANK_HASH, b'')
        o = cls(initial_nonce,
                0,
                trie.BLANK_ROOT,
                BLANK_HASH,
                full_shard_id,
                env,
                address,
                db=db)
        o.existent_at_start = False
        return o

    def is_blank(self):
        return self.nonce == 0 and self.balance == 0 and self.code_hash == BLANK_HASH

    @property
    def exists(self):
        if self.is_blank():
            return self.touched or (self.existent_at_start
                                    and not self.deleted)
        return True

    def to_dict(self):
        odict = self.storage_trie.to_dict()
        for k, v in self.storage_cache.items():
            odict[utils.encode_int(k)] = rlp.encode(utils.encode_int(v))
        return {
            'balance': str(self.balance),
            'nonce': str(self.nonce),
            'code': '0x' + encode_hex(self.code),
            'storage': {
                '0x' + encode_hex(key.lstrip(b'\x00') or b'\x00'):
                '0x' + encode_hex(rlp.decode(val))
                for key, val in odict.items()
            }
        }