github.com/amazechain/amc@v0.1.3/modules/ethdb/olddb/reader.go (about)

     1  package olddb
     2  
     3  import (
     4  	"bytes"
     5  	"github.com/amazechain/amc/common/account"
     6  	"github.com/amazechain/amc/common/crypto"
     7  	"github.com/amazechain/amc/common/types"
     8  	"github.com/amazechain/amc/modules"
     9  	"unsafe"
    10  
    11  	"github.com/ledgerwatch/erigon-lib/kv"
    12  )
    13  
    14  type StateReader struct {
    15  	accHistoryC, storageHistoryC kv.Cursor
    16  	accChangesC, storageChangesC kv.CursorDupSort
    17  	blockNr                      uint64
    18  	readCodeF                    func(types.Hash) ([]byte, error)
    19  	data                         map[string][]byte
    20  	codes                        map[types.Hash][]byte
    21  	db                           kv.Getter
    22  }
    23  
    24  func NewStateReader(data map[string][]byte, codes map[types.Hash][]byte, db kv.Getter, blockNr uint64) *StateReader {
    25  	return &StateReader{
    26  		codes:   codes,
    27  		data:    data,
    28  		blockNr: blockNr,
    29  		db:      db,
    30  	}
    31  }
    32  
    33  func (dbr *StateReader) SetBlockNumber(blockNr uint64) {
    34  	dbr.blockNr = blockNr
    35  }
    36  
    37  func (dbr *StateReader) SetReadCodeF(readCodeF func(types.Hash) ([]byte, error)) {
    38  	dbr.readCodeF = readCodeF
    39  }
    40  
    41  func (dbr *StateReader) GetOne(bucket string, key []byte) ([]byte, error) {
    42  	if len(bucket) == 0 {
    43  		return nil, nil
    44  	}
    45  	b, err := dbr.db.GetOne(bucket, key[:])
    46  	if err == nil && len(b) > 0 {
    47  		return b, err
    48  	}
    49  	v, ok := dbr.data[*(*string)(unsafe.Pointer(&key))]
    50  	if !ok {
    51  		return nil, nil
    52  	}
    53  	return v, nil
    54  }
    55  
    56  func (r *StateReader) ReadAccountData(address types.Address) (*account.StateAccount, error) {
    57  	v, err := r.db.GetOne(modules.Account, address[:])
    58  	if err == nil && len(v) > 0 {
    59  		var acc account.StateAccount
    60  		if err := acc.DecodeForStorage(v); err != nil {
    61  			return nil, err
    62  		}
    63  		return &acc, nil
    64  	}
    65  	b := address.Bytes()
    66  	v, ok := r.data[*(*string)(unsafe.Pointer(&b))]
    67  	if !ok {
    68  		return nil, nil
    69  	}
    70  	if ok && len(v) > 0 {
    71  		var acc account.StateAccount
    72  		if err := acc.DecodeForStorage(v); err != nil {
    73  			return nil, err
    74  		}
    75  		return &acc, nil
    76  	}
    77  	return nil, nil
    78  }
    79  
    80  func (r *StateReader) ReadAccountStorage(address types.Address, incarnation uint16, key *types.Hash) ([]byte, error) {
    81  	compositeKey := modules.PlainGenerateCompositeStorageKey(address.Bytes(), incarnation, key.Bytes())
    82  	v, err := r.db.GetOne(modules.Storage, compositeKey)
    83  	if err == nil && len(v) > 0 {
    84  		return v, nil
    85  	}
    86  	vv, ok := r.data[*(*string)(unsafe.Pointer(&compositeKey))]
    87  	if !ok {
    88  		return nil, nil
    89  	}
    90  	return vv, nil
    91  }
    92  
    93  func (r *StateReader) ReadAccountCode(address types.Address, incarnation uint16, codeHash types.Hash) ([]byte, error) {
    94  	if bytes.Equal(codeHash[:], crypto.Keccak256(nil)) {
    95  		return nil, nil
    96  	}
    97  	if r.readCodeF != nil {
    98  		return r.readCodeF(codeHash)
    99  	}
   100  	return r.codes[codeHash], nil
   101  }
   102  
   103  func (r *StateReader) ReadAccountCodeSize(address types.Address, incarnation uint16, codeHash types.Hash) (int, error) {
   104  	code, err := r.ReadAccountCode(address, incarnation, codeHash)
   105  	if err != nil {
   106  		return 0, err
   107  	}
   108  	return len(code), nil
   109  }
   110  
   111  func (r *StateReader) ReadAccountIncarnation(address types.Address) (uint16, error) {
   112  	return 0, nil
   113  }