aboutsummaryrefslogtreecommitdiffstats
path: root/ptrie
diff options
context:
space:
mode:
Diffstat (limited to 'ptrie')
-rw-r--r--ptrie/fullnode.go7
-rw-r--r--ptrie/trie.go25
-rw-r--r--ptrie/trie_test.go2
3 files changed, 27 insertions, 7 deletions
diff --git a/ptrie/fullnode.go b/ptrie/fullnode.go
index 7a7f7d22d..d6b0745ec 100644
--- a/ptrie/fullnode.go
+++ b/ptrie/fullnode.go
@@ -1,5 +1,7 @@
package ptrie
+import "fmt"
+
type FullNode struct {
trie *Trie
nodes [17]Node
@@ -56,6 +58,11 @@ func (self *FullNode) RlpData() interface{} {
}
func (self *FullNode) set(k byte, value Node) {
+ if _, ok := value.(*ValueNode); ok && k != 16 {
+ fmt.Println(value, k)
+ panic(":(")
+ }
+
self.nodes[int(k)] = value
}
diff --git a/ptrie/trie.go b/ptrie/trie.go
index 9fe9ea52a..d8135f36c 100644
--- a/ptrie/trie.go
+++ b/ptrie/trie.go
@@ -19,7 +19,7 @@ func ParanoiaCheck(t1 *Trie, backend Backend) (bool, *Trie) {
t2.Update(it.Key, it.Value)
}
- return bytes.Compare(t2.Hash(), t1.Hash()) == 0, t2
+ return bytes.Equal(t2.Hash(), t1.Hash()), t2
}
type Trie struct {
@@ -49,14 +49,17 @@ func (self *Trie) Iterator() *Iterator {
return NewIterator(self)
}
+func (self *Trie) Copy() *Trie {
+ return New(self.roothash, self.cache.backend)
+}
+
// Legacy support
func (self *Trie) Root() []byte { return self.Hash() }
func (self *Trie) Hash() []byte {
var hash []byte
if self.root != nil {
- //hash = self.root.Hash().([]byte)
t := self.root.Hash()
- if byts, ok := t.([]byte); ok {
+ if byts, ok := t.([]byte); ok && len(byts) > 0 {
hash = byts
} else {
hash = crypto.Sha3(ethutil.Encode(self.root.RlpData()))
@@ -73,6 +76,9 @@ func (self *Trie) Hash() []byte {
return hash
}
func (self *Trie) Commit() {
+ self.mu.Lock()
+ defer self.mu.Unlock()
+
// Hash first
self.Hash()
@@ -81,10 +87,15 @@ func (self *Trie) Commit() {
// Reset should only be called if the trie has been hashed
func (self *Trie) Reset() {
+ self.mu.Lock()
+ defer self.mu.Unlock()
+
self.cache.Reset()
- revision := self.revisions.Remove(self.revisions.Back()).([]byte)
- self.roothash = revision
+ if self.revisions.Len() > 0 {
+ revision := self.revisions.Remove(self.revisions.Back()).([]byte)
+ self.roothash = revision
+ }
value := ethutil.NewValueFromBytes(self.cache.Get(self.roothash))
self.root = self.mknode(value)
}
@@ -173,7 +184,7 @@ func (self *Trie) insert(node Node, key []byte, value Node) Node {
return cpy
default:
- panic("Invalid node")
+ panic(fmt.Sprintf("%T: invalid node: %v", node, node))
}
}
@@ -274,6 +285,8 @@ func (self *Trie) delete(node Node, key []byte) Node {
func (self *Trie) mknode(value *ethutil.Value) Node {
l := value.Len()
switch l {
+ case 0:
+ return nil
case 2:
return NewShortNode(self, trie.CompactDecode(string(value.Get(0).Bytes())), self.mknode(value.Get(1)))
case 17:
diff --git a/ptrie/trie_test.go b/ptrie/trie_test.go
index 5b1c64140..63a8ed36e 100644
--- a/ptrie/trie_test.go
+++ b/ptrie/trie_test.go
@@ -141,7 +141,7 @@ func TestReplication(t *testing.T) {
trie2 := New(trie.roothash, trie.cache.backend)
if string(trie2.GetString("horse")) != "stallion" {
- t.Error("expected to have harse => stallion")
+ t.Error("expected to have horse => stallion")
}
hash := trie2.Hash()