# Snarkifying `process_block_header()` (Risc0)
## TLDR
- I'm now able to pass a `BeaconState` and a `BeaconBlock` into risc0 zkVM to perform `BeaconState::process_block_header()` within the guest VM.
- The program was able to prove this specific operation in 15 minutes. 15 minutes per a subset transition function is far from ideal
- Out of the 3 operations: 1) reading the state, 2) reading the block, 3) processing the block header, reading the state took over 92.5% of the cycle count. Loading the state into the guest VM seems to be the biggest bottleneck.
- Still not able to output the result into the receipt journal.
- See the work at https://github.com/ReamLabs/consenzero/pull/1/
## Details
- Thanks to @junsong's headwork on [`process_*` skeleton](https://github.com/ReamLabs/ream/pull/42) and Varun's [`process_block_header()` implementation](https://github.com/ReamLabs/ream/pull/54), I'm now able to drop this into risc0 zkVM with only slight hacking, i.e. removing `ssz_types::serde_utils::quoted_u64_var_list::deserialize()` from the `BeaconState`
- I benchmarked 3 points in the guest program. This is the result which is consistent across multiple runs.
```
read_pre_state: 47791528
read_block: 49553
process_block_header: 3809599
```
Clearly loading the state took most (92.5%) of the cycle count.
- I also confirmed by benchmarking from the host
- Removing all guest VM code -> The proving time was instant
- Removing all but passing in just the block -> The proving time was also instant
- Removing all but passing in just the state -> The proving time went up to ~10 minutes
- From my limited understanding, right now I guess these are the 3 possible directions?
1. Trim down the beam chain state
2. Split the prove into multiple subjects so they can be parallelized, then recursively proved
3. Optimize the zkVM
## Next
- Make the program output the post-state into the receipt journal
- Explore optimizations