github.com/waltonchain/waltonchain_gwtc_src@v1.1.4-0.20201225072101-8a298c95a819/core/state/journal.go (about)

     1  // Copyright 2016 The go-ethereum Authors
     2  // This file is part of the go-ethereum library.
     3  //
     4  // The go-wtc library is free software: you can redistribute it and/or modify
     5  // it under the terms of the GNU Lesser General Public License as published by
     6  // the Free Software Foundation, either version 3 of the License, or
     7  // (at your option) any later version.
     8  //
     9  // The go-wtc library is distributed in the hope that it will be useful,
    10  // but WITHOUT ANY WARRANTY; without even the implied warranty of
    11  // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
    12  // GNU Lesser General Public License for more details.
    13  //
    14  // You should have received a copy of the GNU Lesser General Public License
    15  // along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>.
    16  
    17  package state
    18  
    19  import (
    20  	"math/big"
    21  
    22  	"github.com/wtc/go-wtc/common"
    23  )
    24  
    25  type journalEntry interface {
    26  	undo(*StateDB)
    27  }
    28  
    29  type journal []journalEntry
    30  
    31  type (
    32  	// Changes to the account trie.
    33  	createObjectChange struct {
    34  		account *common.Address
    35  	}
    36  	resetObjectChange struct {
    37  		prev *stateObject
    38  	}
    39  	suicideChange struct {
    40  		account     *common.Address
    41  		prev        bool // whether account had already suicided
    42  		prevbalance *big.Int
    43  		prevcoinage *big.Int
    44  		//prevfublocknum *big.Int
    45  		prevfublocktime *big.Int
    46  	}
    47  
    48  	// Changes to individual accounts.
    49  	balanceChange struct {
    50  		account *common.Address
    51  		prev    *big.Int
    52  	}
    53  	coinageChange struct {
    54  		account *common.Address
    55  		prev    *big.Int
    56  	}
    57  	fublockChange struct {
    58  		account *common.Address
    59  		//prevnum *big.Int
    60  		prevtime *big.Int
    61  	}
    62  	nonceChange struct {
    63  		account *common.Address
    64  		prev    uint64
    65  	}
    66  	storageChange struct {
    67  		account       *common.Address
    68  		key, prevalue common.Hash
    69  	}
    70  	codeChange struct {
    71  		account            *common.Address
    72  		prevcode, prevhash []byte
    73  	}
    74  
    75  	// Changes to other state values.
    76  	refundChange struct {
    77  		prev *big.Int
    78  	}
    79  	addLogChange struct {
    80  		txhash common.Hash
    81  	}
    82  	addPreimageChange struct {
    83  		hash common.Hash
    84  	}
    85  	touchChange struct {
    86  		account   *common.Address
    87  		prev      bool
    88  		prevDirty bool
    89  	}
    90  )
    91  
    92  func (ch createObjectChange) undo(s *StateDB) {
    93  	delete(s.stateObjects, *ch.account)
    94  	delete(s.stateObjectsDirty, *ch.account)
    95  }
    96  
    97  func (ch resetObjectChange) undo(s *StateDB) {
    98  	s.setStateObject(ch.prev)
    99  }
   100  
   101  func (ch suicideChange) undo(s *StateDB) {
   102  	obj := s.getStateObject(*ch.account)
   103  	if obj != nil {
   104  		obj.suicided = ch.prev
   105  		obj.setBalance(ch.prevbalance)
   106  		obj.setCoinAge(ch.prevcoinage)
   107  		obj.setFUBlock(ch.prevfublocktime)
   108  	}
   109  }
   110  
   111  var ripemd = common.HexToAddress("0000000000000000000000000000000000000003")
   112  
   113  func (ch touchChange) undo(s *StateDB) {
   114  	if !ch.prev && *ch.account != ripemd {
   115  		s.getStateObject(*ch.account).touched = ch.prev
   116  		if !ch.prevDirty {
   117  			delete(s.stateObjectsDirty, *ch.account)
   118  		}
   119  	}
   120  }
   121  
   122  func (ch balanceChange) undo(s *StateDB) {
   123  	s.getStateObject(*ch.account).setBalance(ch.prev)
   124  }
   125  
   126  func (ch coinageChange) undo(s *StateDB) {
   127  	s.getStateObject(*ch.account).setCoinAge(ch.prev)
   128  }
   129  
   130  func (ch fublockChange) undo(s *StateDB) {
   131  	s.getStateObject(*ch.account).setFUBlock(ch.prevtime)
   132  }
   133  
   134  func (ch nonceChange) undo(s *StateDB) {
   135  	s.getStateObject(*ch.account).setNonce(ch.prev)
   136  }
   137  
   138  func (ch codeChange) undo(s *StateDB) {
   139  	s.getStateObject(*ch.account).setCode(common.BytesToHash(ch.prevhash), ch.prevcode)
   140  }
   141  
   142  func (ch storageChange) undo(s *StateDB) {
   143  	s.getStateObject(*ch.account).setState(ch.key, ch.prevalue)
   144  }
   145  
   146  func (ch refundChange) undo(s *StateDB) {
   147  	s.refund = ch.prev
   148  }
   149  
   150  func (ch addLogChange) undo(s *StateDB) {
   151  	logs := s.logs[ch.txhash]
   152  	if len(logs) == 1 {
   153  		delete(s.logs, ch.txhash)
   154  	} else {
   155  		s.logs[ch.txhash] = logs[:len(logs)-1]
   156  	}
   157  	s.logSize--
   158  }
   159  
   160  func (ch addPreimageChange) undo(s *StateDB) {
   161  	delete(s.preimages, ch.hash)
   162  }