# Han (weihan) - Update 12 & 13 ## Development Updates __________.__ .__ .__ __ .__ .__ .___ .___ \__ ___| |__ ____ ____ | | ____ ______ | |__ _____ _____/ |_ | |__ _____ ______ | | _____ ____ __| _/____ __| _/ | | | | \_/ __ \ _/ __ \| | _/ __ \\____ \| | \\__ \ / \ __\ | | \\__ \ / ___/ | | \__ \ / \ / __ _/ __ \ / __ | | | | Y \ ___/ \ ___/| |_\ ___/| |_> | Y \/ __ \| | | | | Y \/ __ \_\___ \ | |__/ __ \| | / /_/ \ ___// /_/ | |____| |___| /\___ \___ |____/\___ | __/|___| (____ |___| |__| |___| (____ /_____/ |____(____ |___| \____ |\___ \____ | |__| All of the components have been built already. Also managed to get a local private Verkle testnet running with the Clique consensus. I'm testing out the state expiry functionality by simulating the hard forks and sending revive transactions. The PoC isn't fully done yet as there are still some bugs here and there, but it's close to being done. Check out my development branch for Verkle Tree [here](https://github.com/weiihann/go-verkle/tree/state-expiry-dev). Check out my development branch for Geth [here](https://github.com/weiihann/go-ethereum/tree/state-expiry-dev). Check out my local Verkle testnet setup [here](https://github.com/weiihann/verkle-state-expiry). ## Code Notes ### Integration of all components On a high level overview, the current block that is being processed has to propagate the state epoch information all the way to the trie node and refresh the access information of the key-value pairs. The following diagram shows the block importing process from the time a block is being received and processed (based on the Geth codebase): ![](https://hackmd.io/_uploads/SJk_Y2q-p.png) When the `Blockchain` object receives a block, or it's creating a block, it initializes the underlying state database object (i.e. `stateDb`) with the epoch based on the predefined configuration logic. ``` func NewWithStateEpoch(config *params.ChainConfig, TargetBlock *big.Int, root common.Hash, db Database, snaps *snapshot.Tree) (*StateDB, error) { TargetEpoch := types.GetStateEpoch(config, TargetBlock) stateDB, err := newStateDB(root, db, snaps, TargetEpoch) if err != nil { return nil, err } stateDB.TargetBlock = TargetBlock if err != nil { return nil, err } return stateDB, nil } ``` There are only 2 opcodes that stores persistent state data: 1) `SLOAD` and 2) `SSTORE`. The following diagram shows the flow from how the `SSTORE` opcode is being executed with a key-value pair (`SLOAD` is similar): ![](https://hackmd.io/_uploads/HkCEC35Wa.png) The crucial part is at the `stateObject.GetCommittedState` part. It will first attempt to retrieve a value given a key by loading it from local cache. If it's not found, then it will load from snapshot layers. If it's not found again, it will load from the trie persisted in the disk. During this retrieval process, if the query accesses an expired value (as determined by the state epoch metadata in the leaf node), then an error is returned, all the way back to the EVM layer. Thus, a transaction's execution is reverted. ## State Storage Analysis I've been running a full node to collect KV's data for about a month now. It has synced up to ~14M blocks (about January 2022). It's estimated to sync up until ~16M blocks right before the Devconnect's session. It's unfortunate that I can't generate and present the most updated analysis, but I'll still write a complete article once the data collection process is finished. ## Next week's Action Items - Complete the PoC - Complete the logic to insert MPT to the VKT with KV's block number