| 
									
										
										
										
											2015-07-07 02:54:22 +02:00
										 |  |  | // Copyright 2014 The go-ethereum Authors | 
					
						
							| 
									
										
										
										
											2015-07-22 18:48:40 +02:00
										 |  |  | // This file is part of the go-ethereum library. | 
					
						
							| 
									
										
										
										
											2015-07-07 02:54:22 +02:00
										 |  |  | // | 
					
						
							| 
									
										
										
										
											2015-07-23 18:35:11 +02:00
										 |  |  | // The go-ethereum library is free software: you can redistribute it and/or modify | 
					
						
							| 
									
										
										
										
											2015-07-07 02:54:22 +02:00
										 |  |  | // it under the terms of the GNU Lesser General Public License as published by | 
					
						
							|  |  |  | // the Free Software Foundation, either version 3 of the License, or | 
					
						
							|  |  |  | // (at your option) any later version. | 
					
						
							|  |  |  | // | 
					
						
							| 
									
										
										
										
											2015-07-22 18:48:40 +02:00
										 |  |  | // The go-ethereum library is distributed in the hope that it will be useful, | 
					
						
							| 
									
										
										
										
											2015-07-07 02:54:22 +02:00
										 |  |  | // but WITHOUT ANY WARRANTY; without even the implied warranty of | 
					
						
							| 
									
										
										
										
											2015-07-22 18:48:40 +02:00
										 |  |  | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | 
					
						
							| 
									
										
										
										
											2015-07-07 02:54:22 +02:00
										 |  |  | // GNU Lesser General Public License for more details. | 
					
						
							|  |  |  | // | 
					
						
							|  |  |  | // You should have received a copy of the GNU Lesser General Public License | 
					
						
							| 
									
										
										
										
											2015-07-22 18:48:40 +02:00
										 |  |  | // along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>. | 
					
						
							| 
									
										
										
										
											2015-07-07 02:54:22 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-07-07 05:08:16 +02:00
										 |  |  | // Package state provides a caching layer atop the Ethereum state trie. | 
					
						
							| 
									
										
										
										
											2014-10-31 14:43:14 +01:00
										 |  |  | package state | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  | import ( | 
					
						
							| 
									
										
										
										
											2014-07-30 00:31:15 +02:00
										 |  |  | 	"math/big" | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-03-16 11:27:38 +01:00
										 |  |  | 	"github.com/ethereum/go-ethereum/common" | 
					
						
							| 
									
										
										
										
											2015-08-30 10:19:10 +02:00
										 |  |  | 	"github.com/ethereum/go-ethereum/core/vm" | 
					
						
							| 
									
										
										
										
											2015-09-14 09:35:57 +02:00
										 |  |  | 	"github.com/ethereum/go-ethereum/ethdb" | 
					
						
							| 
									
										
										
										
											2014-10-31 12:56:05 +01:00
										 |  |  | 	"github.com/ethereum/go-ethereum/logger" | 
					
						
							| 
									
										
										
										
											2015-04-04 12:40:11 +02:00
										 |  |  | 	"github.com/ethereum/go-ethereum/logger/glog" | 
					
						
							| 
									
										
										
										
											2015-01-08 11:47:04 +01:00
										 |  |  | 	"github.com/ethereum/go-ethereum/trie" | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | ) | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-10-05 13:01:34 +02:00
										 |  |  | // The starting nonce determines the default nonce when new accounts are being | 
					
						
							|  |  |  | // created. | 
					
						
							|  |  |  | var StartingNonce uint64 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-12-04 11:40:20 +01:00
										 |  |  | // StateDBs within the ethereum protocol are used to store anything | 
					
						
							|  |  |  | // within the merkle trie. StateDBs take care of caching and storing | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | // nested states. It's the general query interface to retrieve: | 
					
						
							|  |  |  | // * Contracts | 
					
						
							|  |  |  | // * Accounts | 
					
						
							| 
									
										
										
										
											2014-12-04 11:40:20 +01:00
										 |  |  | type StateDB struct { | 
					
						
							| 
									
										
										
										
											2015-09-14 09:35:57 +02:00
										 |  |  | 	db   ethdb.Database | 
					
						
							| 
									
										
										
										
											2015-03-03 12:25:44 +01:00
										 |  |  | 	trie *trie.SecureTrie | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  | 	stateObjects map[string]*StateObject | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-06-17 10:20:33 +02:00
										 |  |  | 	refund *big.Int | 
					
						
							| 
									
										
										
										
											2014-10-30 13:32:50 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-04-08 17:14:58 +02:00
										 |  |  | 	thash, bhash common.Hash | 
					
						
							|  |  |  | 	txIndex      int | 
					
						
							| 
									
										
										
										
											2015-08-30 10:19:10 +02:00
										 |  |  | 	logs         map[common.Hash]vm.Logs | 
					
						
							| 
									
										
										
										
											2015-07-29 14:16:36 +02:00
										 |  |  | 	logSize      uint | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | // Create a new state from a given trie | 
					
						
							| 
									
										
										
										
											2015-09-14 09:35:57 +02:00
										 |  |  | func New(root common.Hash, db ethdb.Database) *StateDB { | 
					
						
							| 
									
										
										
										
											2015-07-06 01:19:48 +02:00
										 |  |  | 	tr, err := trie.NewSecure(root, db) | 
					
						
							|  |  |  | 	if err != nil { | 
					
						
							|  |  |  | 		// TODO: bubble this up | 
					
						
							|  |  |  | 		tr, _ = trie.NewSecure(common.Hash{}, db) | 
					
						
							|  |  |  | 		glog.Errorf("can't create state trie with root %x: %v", root[:], err) | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 	return &StateDB{ | 
					
						
							|  |  |  | 		db:           db, | 
					
						
							|  |  |  | 		trie:         tr, | 
					
						
							|  |  |  | 		stateObjects: make(map[string]*StateObject), | 
					
						
							|  |  |  | 		refund:       new(big.Int), | 
					
						
							| 
									
										
										
										
											2015-08-30 10:19:10 +02:00
										 |  |  | 		logs:         make(map[common.Hash]vm.Logs), | 
					
						
							| 
									
										
										
										
											2015-07-06 01:19:48 +02:00
										 |  |  | 	} | 
					
						
							| 
									
										
										
										
											2015-03-19 10:57:02 +01:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-04-08 17:14:58 +02:00
										 |  |  | func (self *StateDB) StartRecord(thash, bhash common.Hash, ti int) { | 
					
						
							|  |  |  | 	self.thash = thash | 
					
						
							|  |  |  | 	self.bhash = bhash | 
					
						
							|  |  |  | 	self.txIndex = ti | 
					
						
							| 
									
										
										
										
											2014-10-30 13:32:50 +01:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-08-30 10:19:10 +02:00
										 |  |  | func (self *StateDB) AddLog(log *vm.Log) { | 
					
						
							| 
									
										
										
										
											2015-04-08 17:14:58 +02:00
										 |  |  | 	log.TxHash = self.thash | 
					
						
							|  |  |  | 	log.BlockHash = self.bhash | 
					
						
							|  |  |  | 	log.TxIndex = uint(self.txIndex) | 
					
						
							| 
									
										
										
										
											2015-07-29 14:16:36 +02:00
										 |  |  | 	log.Index = self.logSize | 
					
						
							| 
									
										
										
										
											2015-04-08 17:14:58 +02:00
										 |  |  | 	self.logs[self.thash] = append(self.logs[self.thash], log) | 
					
						
							| 
									
										
										
										
											2015-07-29 14:16:36 +02:00
										 |  |  | 	self.logSize++ | 
					
						
							| 
									
										
										
										
											2015-04-08 17:14:58 +02:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-08-30 10:19:10 +02:00
										 |  |  | func (self *StateDB) GetLogs(hash common.Hash) vm.Logs { | 
					
						
							| 
									
										
										
										
											2015-04-08 17:14:58 +02:00
										 |  |  | 	return self.logs[hash] | 
					
						
							| 
									
										
										
										
											2014-10-30 13:32:50 +01:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-08-30 10:19:10 +02:00
										 |  |  | func (self *StateDB) Logs() vm.Logs { | 
					
						
							|  |  |  | 	var logs vm.Logs | 
					
						
							| 
									
										
										
										
											2015-04-08 17:14:58 +02:00
										 |  |  | 	for _, lgs := range self.logs { | 
					
						
							|  |  |  | 		logs = append(logs, lgs...) | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 	return logs | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-08-30 10:19:10 +02:00
										 |  |  | func (self *StateDB) AddRefund(gas *big.Int) { | 
					
						
							| 
									
										
										
										
											2015-06-17 10:20:33 +02:00
										 |  |  | 	self.refund.Add(self.refund, gas) | 
					
						
							| 
									
										
										
										
											2015-02-11 23:46:45 +01:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-04-08 20:47:32 +02:00
										 |  |  | func (self *StateDB) HasAccount(addr common.Address) bool { | 
					
						
							|  |  |  | 	return self.GetStateObject(addr) != nil | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-08-30 10:19:10 +02:00
										 |  |  | func (self *StateDB) Exist(addr common.Address) bool { | 
					
						
							|  |  |  | 	return self.GetStateObject(addr) != nil | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | func (self *StateDB) GetAccount(addr common.Address) vm.Account { | 
					
						
							|  |  |  | 	return self.GetStateObject(addr) | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | // Retrieve the balance from the given address or 0 if object not found | 
					
						
							| 
									
										
										
										
											2015-03-16 11:59:52 +01:00
										 |  |  | func (self *StateDB) GetBalance(addr common.Address) *big.Int { | 
					
						
							| 
									
										
										
										
											2015-03-12 19:41:56 +01:00
										 |  |  | 	stateObject := self.GetStateObject(addr) | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 	if stateObject != nil { | 
					
						
							| 
									
										
										
										
											2014-10-22 15:22:21 +02:00
										 |  |  | 		return stateObject.balance | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-03-16 11:27:38 +01:00
										 |  |  | 	return common.Big0 | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-03-16 11:59:52 +01:00
										 |  |  | func (self *StateDB) GetNonce(addr common.Address) uint64 { | 
					
						
							| 
									
										
										
										
											2015-03-12 19:41:56 +01:00
										 |  |  | 	stateObject := self.GetStateObject(addr) | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 	if stateObject != nil { | 
					
						
							| 
									
										
										
										
											2015-02-20 14:19:34 +01:00
										 |  |  | 		return stateObject.nonce | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	return 0 | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-03-16 11:59:52 +01:00
										 |  |  | func (self *StateDB) GetCode(addr common.Address) []byte { | 
					
						
							| 
									
										
										
										
											2015-03-12 19:41:56 +01:00
										 |  |  | 	stateObject := self.GetStateObject(addr) | 
					
						
							| 
									
										
										
										
											2014-10-16 13:38:21 +02:00
										 |  |  | 	if stateObject != nil { | 
					
						
							| 
									
										
										
										
											2015-02-20 14:19:34 +01:00
										 |  |  | 		return stateObject.code | 
					
						
							| 
									
										
										
										
											2014-10-16 13:38:21 +02:00
										 |  |  | 	} | 
					
						
							| 
									
										
										
										
											2015-02-19 22:33:22 +01:00
										 |  |  | 
 | 
					
						
							|  |  |  | 	return nil | 
					
						
							| 
									
										
										
										
											2014-10-16 13:38:21 +02:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-06-17 11:24:40 +02:00
										 |  |  | func (self *StateDB) GetState(a common.Address, b common.Hash) common.Hash { | 
					
						
							| 
									
										
										
										
											2015-03-12 19:41:56 +01:00
										 |  |  | 	stateObject := self.GetStateObject(a) | 
					
						
							| 
									
										
										
										
											2014-09-08 00:50:04 +02:00
										 |  |  | 	if stateObject != nil { | 
					
						
							| 
									
										
										
										
											2015-06-17 11:24:40 +02:00
										 |  |  | 		return stateObject.GetState(b) | 
					
						
							| 
									
										
										
										
											2014-09-08 00:50:04 +02:00
										 |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-06-17 11:24:40 +02:00
										 |  |  | 	return common.Hash{} | 
					
						
							| 
									
										
										
										
											2014-09-08 00:50:04 +02:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-04-01 10:53:32 +02:00
										 |  |  | func (self *StateDB) IsDeleted(addr common.Address) bool { | 
					
						
							| 
									
										
										
										
											2015-03-12 19:41:56 +01:00
										 |  |  | 	stateObject := self.GetStateObject(addr) | 
					
						
							| 
									
										
										
										
											2015-04-01 10:53:32 +02:00
										 |  |  | 	if stateObject != nil { | 
					
						
							|  |  |  | 		return stateObject.remove | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 	return false | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | /* | 
					
						
							|  |  |  |  * SETTERS | 
					
						
							|  |  |  |  */ | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | func (self *StateDB) AddBalance(addr common.Address, amount *big.Int) { | 
					
						
							|  |  |  | 	stateObject := self.GetOrNewStateObject(addr) | 
					
						
							|  |  |  | 	if stateObject != nil { | 
					
						
							|  |  |  | 		stateObject.AddBalance(amount) | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | func (self *StateDB) SetNonce(addr common.Address, nonce uint64) { | 
					
						
							|  |  |  | 	stateObject := self.GetOrNewStateObject(addr) | 
					
						
							| 
									
										
										
										
											2014-12-20 02:21:13 +01:00
										 |  |  | 	if stateObject != nil { | 
					
						
							| 
									
										
										
										
											2015-02-20 14:19:34 +01:00
										 |  |  | 		stateObject.SetNonce(nonce) | 
					
						
							| 
									
										
										
										
											2014-12-20 02:21:13 +01:00
										 |  |  | 	} | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-03-16 11:59:52 +01:00
										 |  |  | func (self *StateDB) SetCode(addr common.Address, code []byte) { | 
					
						
							| 
									
										
										
										
											2015-04-01 10:53:32 +02:00
										 |  |  | 	stateObject := self.GetOrNewStateObject(addr) | 
					
						
							| 
									
										
										
										
											2014-10-15 17:12:26 +02:00
										 |  |  | 	if stateObject != nil { | 
					
						
							| 
									
										
										
										
											2015-02-19 22:33:22 +01:00
										 |  |  | 		stateObject.SetCode(code) | 
					
						
							| 
									
										
										
										
											2014-10-15 17:12:26 +02:00
										 |  |  | 	} | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-06-17 11:24:40 +02:00
										 |  |  | func (self *StateDB) SetState(addr common.Address, key common.Hash, value common.Hash) { | 
					
						
							| 
									
										
										
										
											2015-04-01 10:53:32 +02:00
										 |  |  | 	stateObject := self.GetOrNewStateObject(addr) | 
					
						
							| 
									
										
										
										
											2014-10-16 13:38:21 +02:00
										 |  |  | 	if stateObject != nil { | 
					
						
							| 
									
										
										
										
											2015-06-17 11:24:40 +02:00
										 |  |  | 		stateObject.SetState(key, value) | 
					
						
							| 
									
										
										
										
											2014-10-16 13:38:21 +02:00
										 |  |  | 	} | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-03-16 11:59:52 +01:00
										 |  |  | func (self *StateDB) Delete(addr common.Address) bool { | 
					
						
							| 
									
										
										
										
											2015-03-12 19:41:56 +01:00
										 |  |  | 	stateObject := self.GetStateObject(addr) | 
					
						
							| 
									
										
										
										
											2014-10-16 13:38:21 +02:00
										 |  |  | 	if stateObject != nil { | 
					
						
							|  |  |  | 		stateObject.MarkForDeletion() | 
					
						
							| 
									
										
										
										
											2015-03-09 11:28:35 +01:00
										 |  |  | 		stateObject.balance = new(big.Int) | 
					
						
							| 
									
										
										
										
											2014-10-16 13:38:21 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  | 		return true | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	return false | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | // | 
					
						
							|  |  |  | // Setting, updating & deleting state object methods | 
					
						
							|  |  |  | // | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | // Update the given state object and apply it to state trie | 
					
						
							| 
									
										
										
										
											2014-12-04 11:40:20 +01:00
										 |  |  | func (self *StateDB) UpdateStateObject(stateObject *StateObject) { | 
					
						
							| 
									
										
										
										
											2015-03-16 11:59:52 +01:00
										 |  |  | 	//addr := stateObject.Address() | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-09-15 15:42:12 +02:00
										 |  |  | 	if len(stateObject.CodeHash()) > 0 { | 
					
						
							| 
									
										
										
										
											2015-02-20 14:19:34 +01:00
										 |  |  | 		self.db.Put(stateObject.CodeHash(), stateObject.code) | 
					
						
							| 
									
										
										
										
											2014-09-15 15:42:12 +02:00
										 |  |  | 	} | 
					
						
							| 
									
										
										
										
											2015-03-16 17:09:08 +01:00
										 |  |  | 	addr := stateObject.Address() | 
					
						
							|  |  |  | 	self.trie.Update(addr[:], stateObject.RlpEncode()) | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | // Delete the given state object and delete it from the state trie | 
					
						
							| 
									
										
										
										
											2014-12-04 11:40:20 +01:00
										 |  |  | func (self *StateDB) DeleteStateObject(stateObject *StateObject) { | 
					
						
							| 
									
										
										
										
											2015-08-20 18:22:50 +02:00
										 |  |  | 	stateObject.deleted = true | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-03-16 17:09:08 +01:00
										 |  |  | 	addr := stateObject.Address() | 
					
						
							|  |  |  | 	self.trie.Delete(addr[:]) | 
					
						
							| 
									
										
										
										
											2015-08-18 14:14:45 +02:00
										 |  |  | 	//delete(self.stateObjects, addr.Str()) | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | // Retrieve a state object given my the address. Nil if not found | 
					
						
							| 
									
										
										
										
											2015-08-20 18:22:50 +02:00
										 |  |  | func (self *StateDB) GetStateObject(addr common.Address) (stateObject *StateObject) { | 
					
						
							|  |  |  | 	stateObject = self.stateObjects[addr.Str()] | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 	if stateObject != nil { | 
					
						
							| 
									
										
										
										
											2015-08-20 18:22:50 +02:00
										 |  |  | 		if stateObject.deleted { | 
					
						
							|  |  |  | 			stateObject = nil | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 		return stateObject | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-03-16 17:09:08 +01:00
										 |  |  | 	data := self.trie.Get(addr[:]) | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 	if len(data) == 0 { | 
					
						
							|  |  |  | 		return nil | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-01-07 13:17:48 +01:00
										 |  |  | 	stateObject = NewStateObjectFromBytes(addr, []byte(data), self.db) | 
					
						
							| 
									
										
										
										
											2014-10-15 00:40:41 +02:00
										 |  |  | 	self.SetStateObject(stateObject) | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  | 	return stateObject | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-12-04 11:40:20 +01:00
										 |  |  | func (self *StateDB) SetStateObject(object *StateObject) { | 
					
						
							| 
									
										
										
										
											2015-03-16 11:59:52 +01:00
										 |  |  | 	self.stateObjects[object.Address().Str()] = object | 
					
						
							| 
									
										
										
										
											2014-10-15 00:40:41 +02:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | // Retrieve a state object or create a new state object if nil | 
					
						
							| 
									
										
										
										
											2015-03-16 11:59:52 +01:00
										 |  |  | func (self *StateDB) GetOrNewStateObject(addr common.Address) *StateObject { | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 	stateObject := self.GetStateObject(addr) | 
					
						
							| 
									
										
										
										
											2015-08-20 18:22:50 +02:00
										 |  |  | 	if stateObject == nil || stateObject.deleted { | 
					
						
							| 
									
										
										
										
											2015-08-30 10:19:10 +02:00
										 |  |  | 		stateObject = self.CreateStateObject(addr) | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	return stateObject | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-04-01 10:53:32 +02:00
										 |  |  | // NewStateObject create a state object whether it exist in the trie or not | 
					
						
							|  |  |  | func (self *StateDB) newStateObject(addr common.Address) *StateObject { | 
					
						
							| 
									
										
										
										
											2015-04-04 13:24:01 +02:00
										 |  |  | 	if glog.V(logger.Core) { | 
					
						
							| 
									
										
										
										
											2015-04-03 17:09:01 +02:00
										 |  |  | 		glog.Infof("(+) %x\n", addr) | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-01-07 13:17:48 +01:00
										 |  |  | 	stateObject := NewStateObject(addr, self.db) | 
					
						
							| 
									
										
										
										
											2015-10-05 13:01:34 +02:00
										 |  |  | 	stateObject.SetNonce(StartingNonce) | 
					
						
							| 
									
										
										
										
											2015-03-16 17:09:08 +01:00
										 |  |  | 	self.stateObjects[addr.Str()] = stateObject | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  | 	return stateObject | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-04-01 10:53:32 +02:00
										 |  |  | // Creates creates a new state object and takes ownership. This is different from "NewStateObject" | 
					
						
							| 
									
										
										
										
											2015-08-30 10:19:10 +02:00
										 |  |  | func (self *StateDB) CreateStateObject(addr common.Address) *StateObject { | 
					
						
							| 
									
										
										
										
											2015-04-01 10:53:32 +02:00
										 |  |  | 	// Get previous (if any) | 
					
						
							|  |  |  | 	so := self.GetStateObject(addr) | 
					
						
							|  |  |  | 	// Create a new one | 
					
						
							|  |  |  | 	newSo := self.newStateObject(addr) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	// If it existed set the balance to the new account | 
					
						
							|  |  |  | 	if so != nil { | 
					
						
							|  |  |  | 		newSo.balance = so.balance | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	return newSo | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-08-30 10:19:10 +02:00
										 |  |  | func (self *StateDB) CreateAccount(addr common.Address) vm.Account { | 
					
						
							|  |  |  | 	return self.CreateStateObject(addr) | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | // | 
					
						
							|  |  |  | // Setting, copying of the state methods | 
					
						
							|  |  |  | // | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-12-04 11:40:20 +01:00
										 |  |  | func (self *StateDB) Copy() *StateDB { | 
					
						
							| 
									
										
										
										
											2015-03-16 23:48:18 +01:00
										 |  |  | 	state := New(common.Hash{}, self.db) | 
					
						
							| 
									
										
										
										
											2015-06-17 13:39:19 +02:00
										 |  |  | 	state.trie = self.trie | 
					
						
							| 
									
										
										
										
											2015-02-11 23:46:45 +01:00
										 |  |  | 	for k, stateObject := range self.stateObjects { | 
					
						
							|  |  |  | 		state.stateObjects[k] = stateObject.Copy() | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2014-10-30 13:32:50 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-06-17 10:20:33 +02:00
										 |  |  | 	state.refund.Set(self.refund) | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-04-08 17:14:58 +02:00
										 |  |  | 	for hash, logs := range self.logs { | 
					
						
							| 
									
										
										
										
											2015-08-30 10:19:10 +02:00
										 |  |  | 		state.logs[hash] = make(vm.Logs, len(logs)) | 
					
						
							| 
									
										
										
										
											2015-04-08 17:14:58 +02:00
										 |  |  | 		copy(state.logs[hash], logs) | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2015-07-29 14:16:36 +02:00
										 |  |  | 	state.logSize = self.logSize | 
					
						
							| 
									
										
										
										
											2015-02-11 23:46:45 +01:00
										 |  |  | 
 | 
					
						
							|  |  |  | 	return state | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-12-04 11:40:20 +01:00
										 |  |  | func (self *StateDB) Set(state *StateDB) { | 
					
						
							| 
									
										
										
										
											2014-12-23 18:35:36 +01:00
										 |  |  | 	self.trie = state.trie | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 	self.stateObjects = state.stateObjects | 
					
						
							| 
									
										
										
										
											2015-02-03 06:56:19 -08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-10-28 13:22:04 +01:00
										 |  |  | 	self.refund = state.refund | 
					
						
							| 
									
										
										
										
											2014-10-30 13:32:50 +01:00
										 |  |  | 	self.logs = state.logs | 
					
						
							| 
									
										
										
										
											2015-07-29 14:16:36 +02:00
										 |  |  | 	self.logSize = state.logSize | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-08-30 10:19:10 +02:00
										 |  |  | func (self *StateDB) GetRefund() *big.Int { | 
					
						
							|  |  |  | 	return self.refund | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-08-18 14:14:45 +02:00
										 |  |  | // IntermediateRoot computes the current root hash of the state trie. | 
					
						
							|  |  |  | // It is called in between transactions to get the root hash that | 
					
						
							|  |  |  | // goes into transaction receipts. | 
					
						
							|  |  |  | func (s *StateDB) IntermediateRoot() common.Hash { | 
					
						
							|  |  |  | 	s.refund = new(big.Int) | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 	for _, stateObject := range s.stateObjects { | 
					
						
							| 
									
										
										
										
											2015-02-19 22:33:22 +01:00
										 |  |  | 		if stateObject.dirty { | 
					
						
							|  |  |  | 			if stateObject.remove { | 
					
						
							| 
									
										
										
										
											2015-08-18 14:14:45 +02:00
										 |  |  | 				s.DeleteStateObject(stateObject) | 
					
						
							| 
									
										
										
										
											2015-02-19 22:33:22 +01:00
										 |  |  | 			} else { | 
					
						
							| 
									
										
										
										
											2015-06-17 13:27:51 +02:00
										 |  |  | 				stateObject.Update() | 
					
						
							| 
									
										
										
										
											2015-08-18 14:14:45 +02:00
										 |  |  | 				s.UpdateStateObject(stateObject) | 
					
						
							| 
									
										
										
										
											2015-02-19 22:33:22 +01:00
										 |  |  | 			} | 
					
						
							|  |  |  | 			stateObject.dirty = false | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 		} | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2015-08-18 14:14:45 +02:00
										 |  |  | 	return s.trie.Hash() | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-08-18 14:14:45 +02:00
										 |  |  | // Commit commits all state changes to the database. | 
					
						
							|  |  |  | func (s *StateDB) Commit() (root common.Hash, err error) { | 
					
						
							|  |  |  | 	return s.commit(s.db) | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | // CommitBatch commits all state changes to a write batch but does not | 
					
						
							|  |  |  | // execute the batch. It is used to validate state changes against | 
					
						
							|  |  |  | // the root hash stored in a block. | 
					
						
							|  |  |  | func (s *StateDB) CommitBatch() (root common.Hash, batch ethdb.Batch) { | 
					
						
							|  |  |  | 	batch = s.db.NewBatch() | 
					
						
							|  |  |  | 	root, _ = s.commit(batch) | 
					
						
							|  |  |  | 	return root, batch | 
					
						
							|  |  |  | } | 
					
						
							| 
									
										
										
										
											2015-06-30 23:49:34 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-08-18 14:14:45 +02:00
										 |  |  | func (s *StateDB) commit(db trie.DatabaseWriter) (common.Hash, error) { | 
					
						
							|  |  |  | 	s.refund = new(big.Int) | 
					
						
							| 
									
										
										
										
											2015-06-30 23:49:34 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-08-18 14:14:45 +02:00
										 |  |  | 	for _, stateObject := range s.stateObjects { | 
					
						
							| 
									
										
										
										
											2015-06-30 23:49:34 +02:00
										 |  |  | 		if stateObject.remove { | 
					
						
							| 
									
										
										
										
											2015-08-18 14:14:45 +02:00
										 |  |  | 			// If the object has been removed, don't bother syncing it | 
					
						
							|  |  |  | 			// and just mark it for deletion in the trie. | 
					
						
							|  |  |  | 			s.DeleteStateObject(stateObject) | 
					
						
							| 
									
										
										
										
											2015-06-30 23:49:34 +02:00
										 |  |  | 		} else { | 
					
						
							| 
									
										
										
										
											2015-08-18 14:14:45 +02:00
										 |  |  | 			// Write any storage changes in the state object to its trie. | 
					
						
							| 
									
										
										
										
											2015-06-30 23:49:34 +02:00
										 |  |  | 			stateObject.Update() | 
					
						
							| 
									
										
										
										
											2015-08-18 14:14:45 +02:00
										 |  |  | 			// Commit the trie of the object to the batch. | 
					
						
							|  |  |  | 			// This updates the trie root internally, so | 
					
						
							|  |  |  | 			// getting the root hash of the storage trie | 
					
						
							|  |  |  | 			// through UpdateStateObject is fast. | 
					
						
							|  |  |  | 			if _, err := stateObject.trie.CommitTo(db); err != nil { | 
					
						
							|  |  |  | 				return common.Hash{}, err | 
					
						
							|  |  |  | 			} | 
					
						
							|  |  |  | 			// Update the object in the account trie. | 
					
						
							|  |  |  | 			s.UpdateStateObject(stateObject) | 
					
						
							| 
									
										
										
										
											2015-06-30 23:49:34 +02:00
										 |  |  | 		} | 
					
						
							|  |  |  | 		stateObject.dirty = false | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2015-08-18 14:14:45 +02:00
										 |  |  | 	return s.trie.CommitTo(db) | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | func (self *StateDB) Refunds() *big.Int { | 
					
						
							|  |  |  | 	return self.refund | 
					
						
							| 
									
										
										
										
											2015-06-30 23:49:34 +02:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-08-11 16:23:38 +02:00
										 |  |  | // Debug stuff | 
					
						
							| 
									
										
										
										
											2014-12-04 11:40:20 +01:00
										 |  |  | func (self *StateDB) CreateOutputForDiff() { | 
					
						
							| 
									
										
										
										
											2014-08-11 16:23:38 +02:00
										 |  |  | 	for _, stateObject := range self.stateObjects { | 
					
						
							|  |  |  | 		stateObject.CreateOutputForDiff() | 
					
						
							| 
									
										
										
										
											2014-07-22 11:54:48 +02:00
										 |  |  | 	} | 
					
						
							|  |  |  | } |