VM execution fixes

Refactoring caused executing issues
This commit is contained in:
obscuren 2014-09-15 22:11:05 +02:00
parent 33a0dec8a1
commit 399256b384
7 changed files with 57 additions and 51 deletions

View File

@ -148,6 +148,9 @@ func AddTestNetFunds(block *Block) {
} }
func (bc *BlockChain) setLastBlock() { func (bc *BlockChain) setLastBlock() {
// Prep genesis
AddTestNetFunds(bc.genesisBlock)
data, _ := ethutil.Config.Db.Get([]byte("LastBlock")) data, _ := ethutil.Config.Db.Get([]byte("LastBlock"))
if len(data) != 0 { if len(data) != 0 {
block := NewBlockFromBytes(data) block := NewBlockFromBytes(data)
@ -155,12 +158,7 @@ func (bc *BlockChain) setLastBlock() {
bc.LastBlockHash = block.Hash() bc.LastBlockHash = block.Hash()
bc.LastBlockNumber = block.Number.Uint64() bc.LastBlockNumber = block.Number.Uint64()
if bc.LastBlockNumber == 0 {
bc.genesisBlock = block
}
} else { } else {
AddTestNetFunds(bc.genesisBlock)
bc.genesisBlock.state.Trie.Sync() bc.genesisBlock.state.Trie.Sync()
// Prepare the genesis block // Prepare the genesis block
bc.Add(bc.genesisBlock) bc.Add(bc.genesisBlock)

View File

@ -5,6 +5,7 @@ import (
"container/list" "container/list"
"fmt" "fmt"
"math/big" "math/big"
"os"
"sync" "sync"
"time" "time"
@ -154,6 +155,10 @@ done:
if i < len(block.Receipts()) { if i < len(block.Receipts()) {
original := block.Receipts()[i] original := block.Receipts()[i]
if !original.Cmp(receipt) { if !original.Cmp(receipt) {
if ethutil.Config.Diff {
os.Exit(1)
}
return nil, nil, nil, fmt.Errorf("err diff #%d (r) %v ~ %x <=> (c) %v ~ %x (%x)\n", i+1, original.CumulativeGasUsed, original.PostState[0:4], receipt.CumulativeGasUsed, receipt.PostState[0:4], receipt.Tx.Hash()) return nil, nil, nil, fmt.Errorf("err diff #%d (r) %v ~ %x <=> (c) %v ~ %x (%x)\n", i+1, original.CumulativeGasUsed, original.PostState[0:4], receipt.CumulativeGasUsed, receipt.PostState[0:4], receipt.Tx.Hash())
} }
} }
@ -307,14 +312,16 @@ func (sm *StateManager) ValidateBlock(block *Block) error {
// Check each uncle's previous hash. In order for it to be valid // Check each uncle's previous hash. In order for it to be valid
// is if it has the same block hash as the current // is if it has the same block hash as the current
previousBlock := sm.bc.GetBlock(block.PrevHash) parent := sm.bc.GetBlock(block.PrevHash)
/*
for _, uncle := range block.Uncles { for _, uncle := range block.Uncles {
if bytes.Compare(uncle.PrevHash, previousBlock.PrevHash) != 0 { if bytes.Compare(uncle.PrevHash,parent.PrevHash) != 0 {
return ValidationError("Mismatch uncle's previous hash. Expected %x, got %x", previousBlock.PrevHash, uncle.PrevHash) return ValidationError("Mismatch uncle's previous hash. Expected %x, got %x",parent.PrevHash, uncle.PrevHash)
} }
} }
*/
diff := block.Time - previousBlock.Time diff := block.Time - parent.Time
if diff < 0 { if diff < 0 {
return ValidationError("Block timestamp less then prev block %v (%v - %v)", diff, block.Time, sm.bc.CurrentBlock.Time) return ValidationError("Block timestamp less then prev block %v (%v - %v)", diff, block.Time, sm.bc.CurrentBlock.Time)
} }

View File

@ -23,7 +23,8 @@ import (
const ( const (
seedTextFileUri string = "http://www.ethereum.org/servers.poc3.txt" seedTextFileUri string = "http://www.ethereum.org/servers.poc3.txt"
seedNodeAddress = "54.76.56.74:30303" //seedNodeAddress = "54.76.56.74:30303"
seedNodeAddress = "localhost:30303"
) )
var ethlogger = ethlog.NewLogger("SERV") var ethlogger = ethlog.NewLogger("SERV")

View File

@ -65,13 +65,13 @@ func (st *Stack) Peekn() (*big.Int, *big.Int) {
} }
func (st *Stack) Swapn(n int) (*big.Int, *big.Int) { func (st *Stack) Swapn(n int) (*big.Int, *big.Int) {
st.data[n], st.data[0] = st.data[0], st.data[n] st.data[len(st.data)-n], st.data[len(st.data)-1] = st.data[len(st.data)-1], st.data[len(st.data)-n]
return st.data[n], st.data[0] return st.data[len(st.data)-n], st.data[len(st.data)-1]
} }
func (st *Stack) Dupn(n int) *big.Int { func (st *Stack) Dupn(n int) *big.Int {
st.Push(st.data[n]) st.Push(st.data[len(st.data)-n])
return st.Peek() return st.Peek()
} }

View File

@ -63,7 +63,7 @@ func New(env Environment) *Vm {
lt = LogTyDiff lt = LogTyDiff
} }
return &Vm{env: env, logTy: lt, Recoverable: true, queue: list.New()} return &Vm{env: env, logTy: lt, Recoverable: false, queue: list.New()}
} }
func calcMemSize(off, l *big.Int) *big.Int { func calcMemSize(off, l *big.Int) *big.Int {
@ -132,7 +132,6 @@ func (self *Vm) RunClosure(closure *Closure) (ret []byte, err error) {
// XXX Leave this Println intact. Don't change this to the log system. // XXX Leave this Println intact. Don't change this to the log system.
// Used for creating diffs between implementations // Used for creating diffs between implementations
if self.logTy == LogTyDiff { if self.logTy == LogTyDiff {
/*
switch op { switch op {
case STOP, RETURN, SUICIDE: case STOP, RETURN, SUICIDE:
closure.object.EachStorage(func(key string, value *ethutil.Value) { closure.object.EachStorage(func(key string, value *ethutil.Value) {
@ -140,7 +139,6 @@ func (self *Vm) RunClosure(closure *Closure) (ret []byte, err error) {
fmt.Printf("%x %x\n", new(big.Int).SetBytes([]byte(key)).Bytes(), value.Bytes()) fmt.Printf("%x %x\n", new(big.Int).SetBytes([]byte(key)).Bytes(), value.Bytes())
}) })
} }
*/
b := pc.Bytes() b := pc.Bytes()
if len(b) == 0 { if len(b) == 0 {
@ -230,13 +228,15 @@ func (self *Vm) RunClosure(closure *Closure) (ret []byte, err error) {
} }
if newMemSize.Cmp(ethutil.Big0) > 0 { if newMemSize.Cmp(ethutil.Big0) > 0 {
//newMemSize = (newMemSize + 31) / 32 * 32 newMemSize.Add(newMemSize, u256(31))
newMemSize = newMemSize.Add(newMemSize, u256(31)).Div(newMemSize, u256(32)).Mul(newMemSize, u256(32)) newMemSize.Div(newMemSize, u256(32))
//if newMemSize > uint64(mem.Len()) { newMemSize.Mul(newMemSize, u256(32))
if newMemSize.Cmp(u256(int64(mem.Len()))) > 0 { if newMemSize.Cmp(u256(int64(mem.Len()))) > 0 {
newMemSize = newMemSize.Sub(newMemSize, u256(int64(mem.Len()))) memGasUsage := new(big.Int).Sub(newMemSize, u256(int64(mem.Len())))
memGasUsage := newMemSize.Mul(GasMemory, newMemSize).Div(newMemSize, u256(32)) memGasUsage.Mul(GasMemory, memGasUsage)
//m := GasMemory.Uint64() * (newMemSize - uint64(mem.Len())) / 32 memGasUsage.Div(memGasUsage, u256(32))
addStepGasUsage(memGasUsage) addStepGasUsage(memGasUsage)
} }
} }
@ -669,12 +669,12 @@ func (self *Vm) RunClosure(closure *Closure) (ret []byte, err error) {
require(1) require(1)
stack.Pop() stack.Pop()
case DUP1, DUP2, DUP3, DUP4, DUP5, DUP6, DUP7, DUP8, DUP9, DUP10, DUP11, DUP12, DUP13, DUP14, DUP15, DUP16: case DUP1, DUP2, DUP3, DUP4, DUP5, DUP6, DUP7, DUP8, DUP9, DUP10, DUP11, DUP12, DUP13, DUP14, DUP15, DUP16:
n := int(op - DUP1) n := int(op - DUP1 + 1)
stack.Dupn(n) stack.Dupn(n)
self.Printf(" => [%d] 0x%x", n, stack.Peek().Bytes()) self.Printf(" => [%d] 0x%x", n, stack.Peek().Bytes())
case SWAP1, SWAP2, SWAP3, SWAP4, SWAP5, SWAP6, SWAP7, SWAP8, SWAP9, SWAP10, SWAP11, SWAP12, SWAP13, SWAP14, SWAP15, SWAP16: case SWAP1, SWAP2, SWAP3, SWAP4, SWAP5, SWAP6, SWAP7, SWAP8, SWAP9, SWAP10, SWAP11, SWAP12, SWAP13, SWAP14, SWAP15, SWAP16:
n := int(op - SWAP1) n := int(op - SWAP1 + 2)
x, y := stack.Swapn(n) x, y := stack.Swapn(n)
self.Printf(" => [%d] %x [0] %x", n, x.Bytes(), y.Bytes()) self.Printf(" => [%d] %x [0] %x", n, x.Bytes(), y.Bytes())
@ -694,12 +694,12 @@ func (self *Vm) RunClosure(closure *Closure) (ret []byte, err error) {
self.Printf(" => 0x%x", val) self.Printf(" => 0x%x", val)
case MSTORE8: case MSTORE8:
require(2) require(2)
val, mStart := stack.Popn() off := stack.Pop()
//base.And(val, new(big.Int).SetInt64(0xff)) val := stack.Pop()
//mem.Set(mStart.Int64(), 32, ethutil.BigToBytes(base, 256))
mem.store[mStart.Int64()] = byte(val.Int64() & 0xff)
self.Printf(" => 0x%x", val) mem.store[off.Int64()] = byte(val.Int64() & 0xff)
self.Printf(" => [%v] 0x%x", off, val)
case SLOAD: case SLOAD:
require(1) require(1)
loc := stack.Pop() loc := stack.Pop()
@ -955,6 +955,7 @@ func (self *Message) Addr() []byte {
} }
func (self *Message) Exec(codeAddr []byte, caller ClosureRef) (ret []byte, err error) { func (self *Message) Exec(codeAddr []byte, caller ClosureRef) (ret []byte, err error) {
fmt.Printf("%x %x\n", codeAddr[0:4], self.address[0:4])
queue := self.vm.queue queue := self.vm.queue
self.vm.queue = list.New() self.vm.queue = list.New()
@ -990,7 +991,7 @@ func (self *Message) Exec(codeAddr []byte, caller ClosureRef) (ret []byte, err e
code := self.vm.env.State().GetCode(codeAddr) code := self.vm.env.State().GetCode(codeAddr)
// Create a new callable closure // Create a new callable closure
c := NewClosure(msg, caller, object, code, self.gas, self.price) c := NewClosure(msg, caller, stateObject, code, self.gas, self.price)
// Executer the closure and get the return value (if any) // Executer the closure and get the return value (if any)
ret, _, err = c.Call(self.vm, self.input) ret, _, err = c.Call(self.vm, self.input)

View File

@ -282,8 +282,10 @@ func ReadMessages(conn net.Conn) (msgs []*Msg, err error) {
var buff []byte var buff []byte
var totalBytes int var totalBytes int
for { for {
// This is a bit of a cheat actually to make buffering extremely fast.
defer recover()
// Give buffering some time // Give buffering some time
conn.SetReadDeadline(time.Now().Add(500 * time.Millisecond)) conn.SetReadDeadline(time.Now().Add(5 * time.Millisecond))
// Create a new temporarily buffer // Create a new temporarily buffer
b := make([]byte, 1440) b := make([]byte, 1440)
// Wait for a message from this peer // Wait for a message from this peer

15
peer.go
View File

@ -497,18 +497,16 @@ func (p *Peer) HandleInbound() {
p.lastBlockReceived = time.Now() p.lastBlockReceived = time.Now()
} }
var err error
blockPool.CheckLinkAndProcess(func(block *ethchain.Block) { blockPool.CheckLinkAndProcess(func(block *ethchain.Block) {
err := p.ethereum.StateManager().Process(block, false) err = p.ethereum.StateManager().Process(block, false)
if err != nil {
peerlogger.Infoln(err)
}
}) })
/* if err != nil {
if !linked { peerlogger.Infoln(err)
} else {
p.FetchBlocks() p.FetchBlocks()
} }
*/
} }
} }
} }
@ -529,11 +527,10 @@ func (self *Peer) FetchHashes() {
blockPool := self.ethereum.blockPool blockPool := self.ethereum.blockPool
if self.td.Cmp(blockPool.td) >= 0 { if self.td.Cmp(blockPool.td) >= 0 {
peerlogger.Debugf("Requesting hashes from %x\n", self.lastReceivedHash)
blockPool.td = self.td blockPool.td = self.td
if !blockPool.HasLatestHash() { if !blockPool.HasLatestHash() {
self.QueueMessage(ethwire.NewMessage(ethwire.MsgGetBlockHashesTy, []interface{}{self.lastReceivedHash, uint32(200)})) self.QueueMessage(ethwire.NewMessage(ethwire.MsgGetBlockHashesTy, []interface{}{self.lastReceivedHash, uint32(256)}))
} }
} }
} }