# `EEVM.StateRoot`
[🔗](https://github.com/mw2000/eevm/blob/v0.1.0/lib/eevm/state_root.ex#L1)

Computes Ethereum storage roots and state roots from the current `EEVM.Database`.

The first state root of a database enumerates the backend through
`c:EEVM.Database.accounts/1` and `c:EEVM.Database.storage_slots/2`, so the
backend must support them. `update/1` keeps the hashed tries in the
database it returns, and every database derived from that one by writes
and `EEVM.Database.commit/1` carries them along with the addresses and
slots written since. The next state root rehashes only those paths, so a
block costs Keccak work in proportion to what it wrote, not to the size of
the state (#203). `EEVM.Block.execute/4` and `EEVM.Block.build/4` use it,
so the databases in their results, committed or not, carry the tries to
the next block.

# `tries`

```elixir
@opaque tries()
```

Hashed tries for some earlier state, and what changed since: for each
address, the slots written, or `:all` when its storage was cleared. Kept
in `EEVM.Database`'s `:tries` field.

# `compute_state_root`

```elixir
@spec compute_state_root(EEVM.Database.t()) :: binary()
```

Returns the world-state trie root of `db`, overlay included.

# `compute_storage_root`

```elixir
@spec compute_storage_root(EEVM.Database.t(), non_neg_integer()) :: binary()
```

Returns the storage trie root of `address`.

# `update`

```elixir
@spec update(EEVM.Database.t()) :: {binary(), EEVM.Database.t()}
```

Returns the world-state trie root of `db`, overlay included, and `db`
with its hashed tries updated, so the next state root of it, or of a
database written or committed from it, rehashes only what changed.

## Example

    iex> alias EEVM.Database
    iex> {_root, db} = EEVM.StateRoot.update(Database.InMemory.new(accounts: %{1 => %{balance: 5}}))
    iex> {:ok, db} = db |> Database.set_balance(2, 7) |> Database.commit()
    iex> {root, _db} = EEVM.StateRoot.update(db)
    iex> fresh = Database.InMemory.new(accounts: %{1 => %{balance: 5}, 2 => %{balance: 7}})
    iex> root == EEVM.StateRoot.compute_state_root(fresh)
    true

---

*Consult [api-reference.md](api-reference.md) for complete listing*
