openvm_continuations/prover/deferral/hook/
mod.rs1use std::sync::Arc;
2
3use eyre::Result;
4use openvm_recursion_circuit::system::{AggregationSubCircuit, VerifierConfig, VerifierTraceGen};
5use openvm_stark_backend::{
6 keygen::types::{MultiStarkProvingKey, MultiStarkVerifyingKey},
7 proof::Proof,
8 prover::{
9 CommittedTraceData, DeviceDataTransporter, DeviceMultiStarkProvingKey, ProverBackend,
10 ProverDevice,
11 },
12 EngineDeviceCtx, StarkEngine, SystemParams,
13};
14use openvm_stark_sdk::config::baby_bear_poseidon2::{Digest, EF, F};
15use p3_field::{Field, PrimeField32};
16use tracing::instrument;
17
18use crate::{
19 circuit::{
20 deferral::hook::{DeferralHookCircuit, DeferralHookTraceGen, DeferralIoCommit},
21 Circuit,
22 },
23 prover::trace_heights_tracing_info,
24 CommitBytes, VkCommitBytes, SC,
25};
26
27mod trace;
28
29pub struct DeferralHookProver<
30 PB: ProverBackend<Val = F, Challenge = EF, Commitment = Digest>,
31 S: AggregationSubCircuit,
32 T,
33> {
34 pk: Arc<MultiStarkProvingKey<SC>>,
35 d_pk: DeviceMultiStarkProvingKey<PB>,
36 vk: Arc<MultiStarkVerifyingKey<SC>>,
37
38 agg_node_tracegen: T,
39
40 child_vk: Arc<MultiStarkVerifyingKey<SC>>,
41 child_vk_pcs_data: CommittedTraceData<PB>,
42 circuit: Arc<DeferralHookCircuit<S>>,
43}
44
45impl<PB, S, T> DeferralHookProver<PB, S, T>
46where
47 PB: ProverBackend<Val = F, Challenge = EF, Commitment = Digest>,
48 S: AggregationSubCircuit,
49 PB::Matrix: Clone,
50{
51 #[instrument(name = "total_proof", skip_all)]
52 pub fn prove<E: StarkEngine<SC = SC, PB = PB>>(
53 &self,
54 proof: Proof<SC>,
55 leaf_children: Vec<DeferralIoCommit<F>>,
56 ) -> Result<Proof<SC>>
57 where
58 S: VerifierTraceGen<PB, SC, EngineDeviceCtx<E>>,
59 T: DeferralHookTraceGen<PB, EngineDeviceCtx<E>>,
60 {
61 let engine = E::new(self.pk.params.clone());
62 let proving_ctx =
63 self.generate_proving_ctx(proof, leaf_children, engine.device().device_ctx());
64 if tracing::enabled!(tracing::Level::DEBUG) {
65 trace_heights_tracing_info::<_, SC>(&proving_ctx.per_trace, &self.circuit.airs());
66 }
67 #[cfg(debug_assertions)]
68 if crate::prover::debug_checks_enabled() {
69 crate::prover::debug_constraints(&self.circuit, &proving_ctx, &engine);
70 }
71 let proof = engine.prove(&self.d_pk, proving_ctx)?;
72 #[cfg(debug_assertions)]
73 if crate::prover::debug_checks_enabled() {
74 engine.verify(&self.vk, &proof)?;
75 }
76 Ok(proof)
77 }
78 pub fn new<E: StarkEngine<SC = SC, PB = PB>>(
79 child_vk: Arc<MultiStarkVerifyingKey<SC>>,
80 internal_recursive_cached_commit: CommitBytes,
81 system_params: SystemParams,
82 ) -> Self
83 where
84 S: VerifierTraceGen<PB, SC, EngineDeviceCtx<E>>,
85 T: DeferralHookTraceGen<PB, EngineDeviceCtx<E>>,
86 PB::Val: Field + PrimeField32,
87 PB::Matrix: Clone,
88 PB::Commitment: Into<CommitBytes>,
89 {
90 let verifier_circuit = S::new(
91 child_vk.clone(),
92 VerifierConfig {
93 continuations_enabled: true,
94 ..Default::default()
95 },
96 );
97 let engine = E::new(system_params);
98 let child_vk_pcs_data = verifier_circuit.commit_child_vk(&engine, &child_vk);
99 let internal_recursive_vk_commit = VkCommitBytes {
100 cached_commit: internal_recursive_cached_commit,
101 vk_pre_hash: child_vk.pre_hash.into(),
102 };
103 let circuit = Arc::new(DeferralHookCircuit::new(
104 Arc::new(verifier_circuit),
105 internal_recursive_vk_commit,
106 ));
107 let (pk, vk) = engine.keygen(&circuit.airs());
108 let d_pk = engine.device().transport_pk_to_device(&pk);
109
110 Self {
111 pk: Arc::new(pk),
112 d_pk,
113 vk: Arc::new(vk),
114 agg_node_tracegen: T::new(),
115 child_vk,
116 child_vk_pcs_data,
117 circuit,
118 }
119 }
120
121 pub fn from_pk<E: StarkEngine<SC = SC, PB = PB>>(
122 child_vk: Arc<MultiStarkVerifyingKey<SC>>,
123 internal_recursive_cached_commit: CommitBytes,
124 pk: Arc<MultiStarkProvingKey<SC>>,
125 ) -> Self
126 where
127 S: VerifierTraceGen<PB, SC, EngineDeviceCtx<E>>,
128 T: DeferralHookTraceGen<PB, EngineDeviceCtx<E>>,
129 PB::Val: Field + PrimeField32,
130 PB::Matrix: Clone,
131 PB::Commitment: Into<CommitBytes>,
132 {
133 let verifier_circuit = S::new(
134 child_vk.clone(),
135 VerifierConfig {
136 continuations_enabled: true,
137 ..Default::default()
138 },
139 );
140 let engine = E::new(pk.params.clone());
141 let child_vk_pcs_data = verifier_circuit.commit_child_vk(&engine, &child_vk);
142 let internal_recursive_vk_commit = VkCommitBytes {
143 cached_commit: internal_recursive_cached_commit,
144 vk_pre_hash: child_vk.pre_hash.into(),
145 };
146 let circuit = Arc::new(DeferralHookCircuit::new(
147 Arc::new(verifier_circuit),
148 internal_recursive_vk_commit,
149 ));
150 let vk = Arc::new(pk.get_vk());
151 let d_pk = engine.device().transport_pk_to_device(pk.as_ref());
152 Self {
153 pk,
154 d_pk,
155 vk,
156 agg_node_tracegen: T::new(),
157 child_vk,
158 child_vk_pcs_data,
159 circuit,
160 }
161 }
162
163 pub fn get_circuit(&self) -> Arc<DeferralHookCircuit<S>> {
164 self.circuit.clone()
165 }
166
167 pub fn get_pk(&self) -> Arc<MultiStarkProvingKey<SC>> {
168 self.pk.clone()
169 }
170
171 pub fn get_vk(&self) -> Arc<MultiStarkVerifyingKey<SC>> {
172 self.vk.clone()
173 }
174
175 pub fn get_cached_commit(&self) -> <PB as ProverBackend>::Commitment {
176 self.child_vk_pcs_data.commitment
177 }
178}