From e4a6ee3d7f8a3876387f837f6fec6822bd97951e Mon Sep 17 00:00:00 2001 From: obscuren Date: Sun, 16 Feb 2014 20:32:56 +0100 Subject: Added dirty tracking on the cache --- ethutil/trie.go | 17 +++++++++++++++-- ethutil/trie_test.go | 20 ++++++++++++++++++++ 2 files changed, 35 insertions(+), 2 deletions(-) diff --git a/ethutil/trie.go b/ethutil/trie.go index 0a3f73136..7140a1b36 100644 --- a/ethutil/trie.go +++ b/ethutil/trie.go @@ -20,8 +20,9 @@ func (n *Node) Copy() *Node { } type Cache struct { - nodes map[string]*Node - db Database + nodes map[string]*Node + db Database + IsDirty bool } func NewCache(db Database) *Cache { @@ -36,6 +37,7 @@ func (cache *Cache) Put(v interface{}) interface{} { sha := Sha3Bin(enc) cache.nodes[string(sha)] = NewNode(sha, value, true) + cache.IsDirty = true return sha } @@ -60,12 +62,18 @@ func (cache *Cache) Get(key []byte) *Value { } func (cache *Cache) Commit() { + // Don't try to commit if it isn't dirty + if !cache.IsDirty { + return + } + for key, node := range cache.nodes { if node.Dirty { cache.db.Put([]byte(key), node.Value.Encode()) node.Dirty = false } } + cache.IsDirty = false // If the nodes grows beyond the 200 entries we simple empty it // FIXME come up with something better @@ -80,6 +88,7 @@ func (cache *Cache) Undo() { delete(cache.nodes, key) } } + cache.IsDirty = false } // A (modified) Radix Trie implementation. The Trie implements @@ -103,6 +112,10 @@ func (t *Trie) Sync() { t.cache.Commit() } +func (t *Trie) Undo() { + t.cache.Undo() +} + /* * Public (query) interface functions */ diff --git a/ethutil/trie_test.go b/ethutil/trie_test.go index 94414b82e..fa60c8cfc 100644 --- a/ethutil/trie_test.go +++ b/ethutil/trie_test.go @@ -45,6 +45,26 @@ func TestTrieSync(t *testing.T) { } } +func TestTrieDirtyTracking(t *testing.T) { + _, trie := New() + trie.Update("dog", LONG_WORD) + if !trie.cache.IsDirty { + t.Error("Expected trie to be dirty") + } + + trie.Sync() + if trie.cache.IsDirty { + t.Error("Expected trie not to be dirty") + } + + trie.Update("test", LONG_WORD) + trie.cache.Undo() + if trie.cache.IsDirty { + t.Error("Expected trie not to be dirty") + } + +} + func TestTrieReset(t *testing.T) { _, trie := New() -- cgit