github.com/ethereum/go-ethereum@v1.16.1/trie/trie.go (about) 1 // Copyright 2014 The go-ethereum Authors 2 // This file is part of the go-ethereum library. 3 // 4 // The go-ethereum 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-ethereum 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 trie implements Merkle Patricia Tries. 18 package trie 19 20 import ( 21 "bytes" 22 "errors" 23 "fmt" 24 25 "github.com/ethereum/go-ethereum/common" 26 "github.com/ethereum/go-ethereum/core/types" 27 "github.com/ethereum/go-ethereum/log" 28 "github.com/ethereum/go-ethereum/trie/trienode" 29 "github.com/ethereum/go-ethereum/triedb/database" 30 ) 31 32 // Trie represents a Merkle Patricia Trie. Use New to create a trie that operates 33 // on top of a node database. During a commit operation, the trie collects all 34 // modified nodes into a set for return. After committing, the trie becomes 35 // unusable, and callers must recreate it with the new root based on the updated 36 // trie database. 37 // 38 // Trie is not safe for concurrent use. 39 type Trie struct { 40 root node 41 owner common.Hash 42 43 // Flag whether the commit operation is already performed. If so the 44 // trie is not usable(latest states is invisible). 45 committed bool 46 47 // Keep track of the number leaves which have been inserted since the last 48 // hashing operation. This number will not directly map to the number of 49 // actually unhashed nodes. 50 unhashed int 51 52 // uncommitted is the number of updates since last commit. 53 uncommitted int 54 55 // reader is the handler trie can retrieve nodes from. 56 reader *trieReader 57 58 // tracer is the tool to track the trie changes. 59 tracer *tracer 60 } 61 62 // newFlag returns the cache flag value for a newly created node. 63 func (t *Trie) newFlag() nodeFlag { 64 return nodeFlag{dirty: true} 65 } 66 67 // Copy returns a copy of Trie. 68 func (t *Trie) Copy() *Trie { 69 return &Trie{ 70 root: copyNode(t.root), 71 owner: t.owner, 72 committed: t.committed, 73 unhashed: t.unhashed, 74 uncommitted: t.uncommitted, 75 reader: t.reader, 76 tracer: t.tracer.copy(), 77 } 78 } 79 80 // New creates the trie instance with provided trie id and the read-only 81 // database. The state specified by trie id must be available, otherwise 82 // an error will be returned. The trie root specified by trie id can be 83 // zero hash or the sha3 hash of an empty string, then trie is initially 84 // empty, otherwise, the root node must be present in database or returns 85 // a MissingNodeError if not. 86 func New(id *ID, db database.NodeDatabase) (*Trie, error) { 87 reader, err := newTrieReader(id.StateRoot, id.Owner, db) 88 if err != nil { 89 return nil, err 90 } 91 trie := &Trie{ 92 owner: id.Owner, 93 reader: reader, 94 tracer: newTracer(), 95 } 96 if id.Root != (common.Hash{}) && id.Root != types.EmptyRootHash { 97 rootnode, err := trie.resolveAndTrack(id.Root[:], nil) 98 if err != nil { 99 return nil, err 100 } 101 trie.root = rootnode 102 } 103 return trie, nil 104 } 105 106 // NewEmpty is a shortcut to create empty tree. It's mostly used in tests. 107 func NewEmpty(db database.NodeDatabase) *Trie { 108 tr, _ := New(TrieID(types.EmptyRootHash), db) 109 return tr 110 } 111 112 // MustNodeIterator is a wrapper of NodeIterator and will omit any encountered 113 // error but just print out an error message. 114 func (t *Trie) MustNodeIterator(start []byte) NodeIterator { 115 it, err := t.NodeIterator(start) 116 if err != nil { 117 log.Error("Unhandled trie error in Trie.NodeIterator", "err", err) 118 } 119 return it 120 } 121 122 // NodeIterator returns an iterator that returns nodes of the trie. Iteration starts at 123 // the key after the given start key. 124 func (t *Trie) NodeIterator(start []byte) (NodeIterator, error) { 125 // Short circuit if the trie is already committed and not usable. 126 if t.committed { 127 return nil, ErrCommitted 128 } 129 return newNodeIterator(t, start), nil 130 } 131 132 // MustGet is a wrapper of Get and will omit any encountered error but just 133 // print out an error message. 134 func (t *Trie) MustGet(key []byte) []byte { 135 res, err := t.Get(key) 136 if err != nil { 137 log.Error("Unhandled trie error in Trie.Get", "err", err) 138 } 139 return res 140 } 141 142 // Get returns the value for key stored in the trie. 143 // The value bytes must not be modified by the caller. 144 // 145 // If the requested node is not present in trie, no error will be returned. 146 // If the trie is corrupted, a MissingNodeError is returned. 147 func (t *Trie) Get(key []byte) ([]byte, error) { 148 // Short circuit if the trie is already committed and not usable. 149 if t.committed { 150 return nil, ErrCommitted 151 } 152 value, newroot, didResolve, err := t.get(t.root, keybytesToHex(key), 0) 153 if err == nil && didResolve { 154 t.root = newroot 155 } 156 return value, err 157 } 158 159 func (t *Trie) get(origNode node, key []byte, pos int) (value []byte, newnode node, didResolve bool, err error) { 160 switch n := (origNode).(type) { 161 case nil: 162 return nil, nil, false, nil 163 case valueNode: 164 return n, n, false, nil 165 case *shortNode: 166 if !bytes.HasPrefix(key[pos:], n.Key) { 167 // key not found in trie 168 return nil, n, false, nil 169 } 170 value, newnode, didResolve, err = t.get(n.Val, key, pos+len(n.Key)) 171 if err == nil && didResolve { 172 n.Val = newnode 173 } 174 return value, n, didResolve, err 175 case *fullNode: 176 value, newnode, didResolve, err = t.get(n.Children[key[pos]], key, pos+1) 177 if err == nil && didResolve { 178 n.Children[key[pos]] = newnode 179 } 180 return value, n, didResolve, err 181 case hashNode: 182 child, err := t.resolveAndTrack(n, key[:pos]) 183 if err != nil { 184 return nil, n, true, err 185 } 186 value, newnode, _, err := t.get(child, key, pos) 187 return value, newnode, true, err 188 default: 189 panic(fmt.Sprintf("%T: invalid node: %v", origNode, origNode)) 190 } 191 } 192 193 // MustGetNode is a wrapper of GetNode and will omit any encountered error but 194 // just print out an error message. 195 func (t *Trie) MustGetNode(path []byte) ([]byte, int) { 196 item, resolved, err := t.GetNode(path) 197 if err != nil { 198 log.Error("Unhandled trie error in Trie.GetNode", "err", err) 199 } 200 return item, resolved 201 } 202 203 // GetNode retrieves a trie node by compact-encoded path. It is not possible 204 // to use keybyte-encoding as the path might contain odd nibbles. 205 // 206 // If the requested node is not present in trie, no error will be returned. 207 // If the trie is corrupted, a MissingNodeError is returned. 208 func (t *Trie) GetNode(path []byte) ([]byte, int, error) { 209 // Short circuit if the trie is already committed and not usable. 210 if t.committed { 211 return nil, 0, ErrCommitted 212 } 213 item, newroot, resolved, err := t.getNode(t.root, compactToHex(path), 0) 214 if err != nil { 215 return nil, resolved, err 216 } 217 if resolved > 0 { 218 t.root = newroot 219 } 220 return item, resolved, nil 221 } 222 223 func (t *Trie) getNode(origNode node, path []byte, pos int) (item []byte, newnode node, resolved int, err error) { 224 // If non-existent path requested, abort 225 if origNode == nil { 226 return nil, nil, 0, nil 227 } 228 // If we reached the requested path, return the current node 229 if pos >= len(path) { 230 // Although we most probably have the original node expanded, encoding 231 // that into consensus form can be nasty (needs to cascade down) and 232 // time consuming. Instead, just pull the hash up from disk directly. 233 var hash hashNode 234 if node, ok := origNode.(hashNode); ok { 235 hash = node 236 } else { 237 hash, _ = origNode.cache() 238 } 239 if hash == nil { 240 return nil, origNode, 0, errors.New("non-consensus node") 241 } 242 blob, err := t.reader.node(path, common.BytesToHash(hash)) 243 return blob, origNode, 1, err 244 } 245 // Path still needs to be traversed, descend into children 246 switch n := (origNode).(type) { 247 case valueNode: 248 // Path prematurely ended, abort 249 return nil, nil, 0, nil 250 251 case *shortNode: 252 if !bytes.HasPrefix(path[pos:], n.Key) { 253 // Path branches off from short node 254 return nil, n, 0, nil 255 } 256 item, newnode, resolved, err = t.getNode(n.Val, path, pos+len(n.Key)) 257 if err == nil && resolved > 0 { 258 n.Val = newnode 259 } 260 return item, n, resolved, err 261 262 case *fullNode: 263 item, newnode, resolved, err = t.getNode(n.Children[path[pos]], path, pos+1) 264 if err == nil && resolved > 0 { 265 n.Children[path[pos]] = newnode 266 } 267 return item, n, resolved, err 268 269 case hashNode: 270 child, err := t.resolveAndTrack(n, path[:pos]) 271 if err != nil { 272 return nil, n, 1, err 273 } 274 item, newnode, resolved, err := t.getNode(child, path, pos) 275 return item, newnode, resolved + 1, err 276 277 default: 278 panic(fmt.Sprintf("%T: invalid node: %v", origNode, origNode)) 279 } 280 } 281 282 // MustUpdate is a wrapper of Update and will omit any encountered error but 283 // just print out an error message. 284 func (t *Trie) MustUpdate(key, value []byte) { 285 if err := t.Update(key, value); err != nil { 286 log.Error("Unhandled trie error in Trie.Update", "err", err) 287 } 288 } 289 290 // Update associates key with value in the trie. Subsequent calls to 291 // Get will return value. If value has length zero, any existing value 292 // is deleted from the trie and calls to Get will return nil. 293 // 294 // The value bytes must not be modified by the caller while they are 295 // stored in the trie. 296 // 297 // If the requested node is not present in trie, no error will be returned. 298 // If the trie is corrupted, a MissingNodeError is returned. 299 func (t *Trie) Update(key, value []byte) error { 300 // Short circuit if the trie is already committed and not usable. 301 if t.committed { 302 return ErrCommitted 303 } 304 return t.update(key, value) 305 } 306 307 func (t *Trie) update(key, value []byte) error { 308 t.unhashed++ 309 t.uncommitted++ 310 k := keybytesToHex(key) 311 if len(value) != 0 { 312 _, n, err := t.insert(t.root, nil, k, valueNode(value)) 313 if err != nil { 314 return err 315 } 316 t.root = n 317 } else { 318 _, n, err := t.delete(t.root, nil, k) 319 if err != nil { 320 return err 321 } 322 t.root = n 323 } 324 return nil 325 } 326 327 func (t *Trie) insert(n node, prefix, key []byte, value node) (bool, node, error) { 328 if len(key) == 0 { 329 if v, ok := n.(valueNode); ok { 330 return !bytes.Equal(v, value.(valueNode)), value, nil 331 } 332 return true, value, nil 333 } 334 switch n := n.(type) { 335 case *shortNode: 336 matchlen := prefixLen(key, n.Key) 337 // If the whole key matches, keep this short node as is 338 // and only update the value. 339 if matchlen == len(n.Key) { 340 dirty, nn, err := t.insert(n.Val, append(prefix, key[:matchlen]...), key[matchlen:], value) 341 if !dirty || err != nil { 342 return false, n, err 343 } 344 return true, &shortNode{n.Key, nn, t.newFlag()}, nil 345 } 346 // Otherwise branch out at the index where they differ. 347 branch := &fullNode{flags: t.newFlag()} 348 var err error 349 _, branch.Children[n.Key[matchlen]], err = t.insert(nil, append(prefix, n.Key[:matchlen+1]...), n.Key[matchlen+1:], n.Val) 350 if err != nil { 351 return false, nil, err 352 } 353 _, branch.Children[key[matchlen]], err = t.insert(nil, append(prefix, key[:matchlen+1]...), key[matchlen+1:], value) 354 if err != nil { 355 return false, nil, err 356 } 357 // Replace this shortNode with the branch if it occurs at index 0. 358 if matchlen == 0 { 359 return true, branch, nil 360 } 361 // New branch node is created as a child of the original short node. 362 // Track the newly inserted node in the tracer. The node identifier 363 // passed is the path from the root node. 364 t.tracer.onInsert(append(prefix, key[:matchlen]...)) 365 366 // Replace it with a short node leading up to the branch. 367 return true, &shortNode{key[:matchlen], branch, t.newFlag()}, nil 368 369 case *fullNode: 370 dirty, nn, err := t.insert(n.Children[key[0]], append(prefix, key[0]), key[1:], value) 371 if !dirty || err != nil { 372 return false, n, err 373 } 374 n.flags = t.newFlag() 375 n.Children[key[0]] = nn 376 return true, n, nil 377 378 case nil: 379 // New short node is created and track it in the tracer. The node identifier 380 // passed is the path from the root node. Note the valueNode won't be tracked 381 // since it's always embedded in its parent. 382 t.tracer.onInsert(prefix) 383 384 return true, &shortNode{key, value, t.newFlag()}, nil 385 386 case hashNode: 387 // We've hit a part of the trie that isn't loaded yet. Load 388 // the node and insert into it. This leaves all child nodes on 389 // the path to the value in the trie. 390 rn, err := t.resolveAndTrack(n, prefix) 391 if err != nil { 392 return false, nil, err 393 } 394 dirty, nn, err := t.insert(rn, prefix, key, value) 395 if !dirty || err != nil { 396 return false, rn, err 397 } 398 return true, nn, nil 399 400 default: 401 panic(fmt.Sprintf("%T: invalid node: %v", n, n)) 402 } 403 } 404 405 // MustDelete is a wrapper of Delete and will omit any encountered error but 406 // just print out an error message. 407 func (t *Trie) MustDelete(key []byte) { 408 if err := t.Delete(key); err != nil { 409 log.Error("Unhandled trie error in Trie.Delete", "err", err) 410 } 411 } 412 413 // Delete removes any existing value for key from the trie. 414 // 415 // If the requested node is not present in trie, no error will be returned. 416 // If the trie is corrupted, a MissingNodeError is returned. 417 func (t *Trie) Delete(key []byte) error { 418 // Short circuit if the trie is already committed and not usable. 419 if t.committed { 420 return ErrCommitted 421 } 422 t.uncommitted++ 423 t.unhashed++ 424 k := keybytesToHex(key) 425 _, n, err := t.delete(t.root, nil, k) 426 if err != nil { 427 return err 428 } 429 t.root = n 430 return nil 431 } 432 433 // delete returns the new root of the trie with key deleted. 434 // It reduces the trie to minimal form by simplifying 435 // nodes on the way up after deleting recursively. 436 func (t *Trie) delete(n node, prefix, key []byte) (bool, node, error) { 437 switch n := n.(type) { 438 case *shortNode: 439 matchlen := prefixLen(key, n.Key) 440 if matchlen < len(n.Key) { 441 return false, n, nil // don't replace n on mismatch 442 } 443 if matchlen == len(key) { 444 // The matched short node is deleted entirely and track 445 // it in the deletion set. The same the valueNode doesn't 446 // need to be tracked at all since it's always embedded. 447 t.tracer.onDelete(prefix) 448 449 return true, nil, nil // remove n entirely for whole matches 450 } 451 // The key is longer than n.Key. Remove the remaining suffix 452 // from the subtrie. Child can never be nil here since the 453 // subtrie must contain at least two other values with keys 454 // longer than n.Key. 455 dirty, child, err := t.delete(n.Val, append(prefix, key[:len(n.Key)]...), key[len(n.Key):]) 456 if !dirty || err != nil { 457 return false, n, err 458 } 459 switch child := child.(type) { 460 case *shortNode: 461 // The child shortNode is merged into its parent, track 462 // is deleted as well. 463 t.tracer.onDelete(append(prefix, n.Key...)) 464 465 // Deleting from the subtrie reduced it to another 466 // short node. Merge the nodes to avoid creating a 467 // shortNode{..., shortNode{...}}. Use concat (which 468 // always creates a new slice) instead of append to 469 // avoid modifying n.Key since it might be shared with 470 // other nodes. 471 return true, &shortNode{concat(n.Key, child.Key...), child.Val, t.newFlag()}, nil 472 default: 473 return true, &shortNode{n.Key, child, t.newFlag()}, nil 474 } 475 476 case *fullNode: 477 dirty, nn, err := t.delete(n.Children[key[0]], append(prefix, key[0]), key[1:]) 478 if !dirty || err != nil { 479 return false, n, err 480 } 481 n.flags = t.newFlag() 482 n.Children[key[0]] = nn 483 484 // Because n is a full node, it must've contained at least two children 485 // before the delete operation. If the new child value is non-nil, n still 486 // has at least two children after the deletion, and cannot be reduced to 487 // a short node. 488 if nn != nil { 489 return true, n, nil 490 } 491 // Reduction: 492 // Check how many non-nil entries are left after deleting and 493 // reduce the full node to a short node if only one entry is 494 // left. Since n must've contained at least two children 495 // before deletion (otherwise it would not be a full node) n 496 // can never be reduced to nil. 497 // 498 // When the loop is done, pos contains the index of the single 499 // value that is left in n or -2 if n contains at least two 500 // values. 501 pos := -1 502 for i, cld := range &n.Children { 503 if cld != nil { 504 if pos == -1 { 505 pos = i 506 } else { 507 pos = -2 508 break 509 } 510 } 511 } 512 if pos >= 0 { 513 if pos != 16 { 514 // If the remaining entry is a short node, it replaces 515 // n and its key gets the missing nibble tacked to the 516 // front. This avoids creating an invalid 517 // shortNode{..., shortNode{...}}. Since the entry 518 // might not be loaded yet, resolve it just for this 519 // check. 520 cnode, err := t.resolve(n.Children[pos], append(prefix, byte(pos))) 521 if err != nil { 522 return false, nil, err 523 } 524 if cnode, ok := cnode.(*shortNode); ok { 525 // Replace the entire full node with the short node. 526 // Mark the original short node as deleted since the 527 // value is embedded into the parent now. 528 t.tracer.onDelete(append(prefix, byte(pos))) 529 530 k := append([]byte{byte(pos)}, cnode.Key...) 531 return true, &shortNode{k, cnode.Val, t.newFlag()}, nil 532 } 533 } 534 // Otherwise, n is replaced by a one-nibble short node 535 // containing the child. 536 return true, &shortNode{[]byte{byte(pos)}, n.Children[pos], t.newFlag()}, nil 537 } 538 // n still contains at least two values and cannot be reduced. 539 return true, n, nil 540 541 case valueNode: 542 return true, nil, nil 543 544 case nil: 545 return false, nil, nil 546 547 case hashNode: 548 // We've hit a part of the trie that isn't loaded yet. Load 549 // the node and delete from it. This leaves all child nodes on 550 // the path to the value in the trie. 551 rn, err := t.resolveAndTrack(n, prefix) 552 if err != nil { 553 return false, nil, err 554 } 555 dirty, nn, err := t.delete(rn, prefix, key) 556 if !dirty || err != nil { 557 return false, rn, err 558 } 559 return true, nn, nil 560 561 default: 562 panic(fmt.Sprintf("%T: invalid node: %v (%v)", n, n, key)) 563 } 564 } 565 566 func concat(s1 []byte, s2 ...byte) []byte { 567 r := make([]byte, len(s1)+len(s2)) 568 copy(r, s1) 569 copy(r[len(s1):], s2) 570 return r 571 } 572 573 // copyNode deep-copies the supplied node along with its children recursively. 574 func copyNode(n node) node { 575 switch n := (n).(type) { 576 case nil: 577 return nil 578 case valueNode: 579 return valueNode(common.CopyBytes(n)) 580 581 case *shortNode: 582 return &shortNode{ 583 flags: n.flags.copy(), 584 Key: common.CopyBytes(n.Key), 585 Val: copyNode(n.Val), 586 } 587 case *fullNode: 588 var children [17]node 589 for i, cn := range n.Children { 590 children[i] = copyNode(cn) 591 } 592 return &fullNode{ 593 flags: n.flags.copy(), 594 Children: children, 595 } 596 case hashNode: 597 return n 598 default: 599 panic(fmt.Sprintf("%T: unknown node type", n)) 600 } 601 } 602 603 func (t *Trie) resolve(n node, prefix []byte) (node, error) { 604 if n, ok := n.(hashNode); ok { 605 return t.resolveAndTrack(n, prefix) 606 } 607 return n, nil 608 } 609 610 // resolveAndTrack loads node from the underlying store with the given node hash 611 // and path prefix and also tracks the loaded node blob in tracer treated as the 612 // node's original value. The rlp-encoded blob is preferred to be loaded from 613 // database because it's easy to decode node while complex to encode node to blob. 614 func (t *Trie) resolveAndTrack(n hashNode, prefix []byte) (node, error) { 615 blob, err := t.reader.node(prefix, common.BytesToHash(n)) 616 if err != nil { 617 return nil, err 618 } 619 t.tracer.onRead(prefix, blob) 620 621 // The returned node blob won't be changed afterward. No need to 622 // deep-copy the slice. 623 return decodeNodeUnsafe(n, blob) 624 } 625 626 // Hash returns the root hash of the trie. It does not write to the 627 // database and can be used even if the trie doesn't have one. 628 func (t *Trie) Hash() common.Hash { 629 return common.BytesToHash(t.hashRoot().(hashNode)) 630 } 631 632 // Commit collects all dirty nodes in the trie and replaces them with the 633 // corresponding node hash. All collected nodes (including dirty leaves if 634 // collectLeaf is true) will be encapsulated into a nodeset for return. 635 // The returned nodeset can be nil if the trie is clean (nothing to commit). 636 // Once the trie is committed, it's not usable anymore. A new trie must 637 // be created with new root and updated trie database for following usage 638 func (t *Trie) Commit(collectLeaf bool) (common.Hash, *trienode.NodeSet) { 639 defer func() { 640 t.committed = true 641 }() 642 // Trie is empty and can be classified into two types of situations: 643 // (a) The trie was empty and no update happens => return nil 644 // (b) The trie was non-empty and all nodes are dropped => return 645 // the node set includes all deleted nodes 646 if t.root == nil { 647 paths := t.tracer.deletedNodes() 648 if len(paths) == 0 { 649 return types.EmptyRootHash, nil // case (a) 650 } 651 nodes := trienode.NewNodeSet(t.owner) 652 for _, path := range paths { 653 nodes.AddNode([]byte(path), trienode.NewDeleted()) 654 } 655 return types.EmptyRootHash, nodes // case (b) 656 } 657 // Derive the hash for all dirty nodes first. We hold the assumption 658 // in the following procedure that all nodes are hashed. 659 rootHash := t.Hash() 660 661 // Do a quick check if we really need to commit. This can happen e.g. 662 // if we load a trie for reading storage values, but don't write to it. 663 if hashedNode, dirty := t.root.cache(); !dirty { 664 // Replace the root node with the origin hash in order to 665 // ensure all resolved nodes are dropped after the commit. 666 t.root = hashedNode 667 return rootHash, nil 668 } 669 nodes := trienode.NewNodeSet(t.owner) 670 for _, path := range t.tracer.deletedNodes() { 671 nodes.AddNode([]byte(path), trienode.NewDeleted()) 672 } 673 // If the number of changes is below 100, we let one thread handle it 674 t.root = newCommitter(nodes, t.tracer, collectLeaf).Commit(t.root, t.uncommitted > 100) 675 t.uncommitted = 0 676 return rootHash, nodes 677 } 678 679 // hashRoot calculates the root hash of the given trie 680 func (t *Trie) hashRoot() node { 681 if t.root == nil { 682 return hashNode(types.EmptyRootHash.Bytes()) 683 } 684 // If the number of changes is below 100, we let one thread handle it 685 h := newHasher(t.unhashed >= 100) 686 defer func() { 687 returnHasherToPool(h) 688 t.unhashed = 0 689 }() 690 return h.hash(t.root, true) 691 } 692 693 // Witness returns a set containing all trie nodes that have been accessed. 694 func (t *Trie) Witness() map[string]struct{} { 695 if len(t.tracer.accessList) == 0 { 696 return nil 697 } 698 witness := make(map[string]struct{}, len(t.tracer.accessList)) 699 for _, node := range t.tracer.accessList { 700 witness[string(node)] = struct{}{} 701 } 702 return witness 703 } 704 705 // Reset drops the referenced root node and cleans all internal state. 706 func (t *Trie) Reset() { 707 t.root = nil 708 t.owner = common.Hash{} 709 t.unhashed = 0 710 t.uncommitted = 0 711 t.tracer.reset() 712 t.committed = false 713 }