Skip to content

Commit cd7839e

Browse files
feat: Add blanket implementations for remote and perf traits + NativeHost remote support (#81)
This commit adds blanket implementations and native host remote proving support: 1. `ZkVmRemoteHost`: Automatically implemented for any type that implements both `ZkVmHost` and `ZkVmRemoteProver`. Eliminates manual implementations. 2. `ZkVmRemoteProgram`: Automatically implemented for any type implementing `ZkVmProgram`. All programs get remote proving without explicit impls. 3. `ZkVmProgramPerf`: Automatically implemented for any type implementing `ZkVmProgram`. All programs get perf reporting without explicit impls. 4. **NativeHost now implements `ZkVmRemoteProver`**: Executes proofs synchronously and hex-encodes them in the "proof ID". Combined with blanket impl #1, `NativeHost` automatically gets `ZkVmRemoteHost`! These changes eliminate all wrapper boilerplate while maintaining type safety.
1 parent 8af6b93 commit cd7839e

File tree

11 files changed

+79
-13
lines changed

11 files changed

+79
-13
lines changed

Cargo.lock

Lines changed: 2 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

adapters/native/Cargo.toml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,8 @@ rustdoc.all = "warn"
1515
[dependencies]
1616
zkaleido.workspace = true
1717

18+
async-trait.workspace = true
1819
bincode.workspace = true
1920
borsh.workspace = true
21+
hex.workspace = true
2022
serde.workspace = true

adapters/native/src/host.rs

Lines changed: 53 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,11 @@
11
use std::{env, fmt, sync::Arc};
22

3+
use async_trait::async_trait;
34
use zkaleido::{
45
Proof, ProofMetadata, ProofReceipt, ProofReceiptWithMetadata, ProofType, PublicValues,
56
VerifyingKey, VerifyingKeyCommitment, ZkVm, ZkVmError, ZkVmExecutor, ZkVmHost,
6-
ZkVmOutputExtractor, ZkVmProver, ZkVmResult, ZkVmTypedVerifier, ZkVmVkProvider,
7+
ZkVmOutputExtractor, ZkVmProver, ZkVmRemoteProver, ZkVmResult, ZkVmTypedVerifier,
8+
ZkVmVkProvider,
79
};
810

911
use crate::{env::NativeMachine, input::NativeMachineInputBuilder, proof::NativeProofReceipt};
@@ -97,3 +99,53 @@ impl fmt::Debug for NativeHost {
9799
write!(f, "native")
98100
}
99101
}
102+
103+
/// Implementation of `ZkVmRemoteProver` for `NativeHost`.
104+
///
105+
/// Since `NativeHost` executes proofs synchronously, this implementation:
106+
/// - Runs the proof immediately in `start_proving`
107+
/// - Serializes the result and hex-encodes it as the "proof ID"
108+
/// - Deserializes and returns the proof in `get_proof_if_ready_inner`
109+
///
110+
/// Combined with the blanket impl `impl<T: ZkVmHost + ZkVmRemoteProver> ZkVmRemoteHost for T`,
111+
/// this automatically gives `NativeHost` the `ZkVmRemoteHost` trait, allowing it to work
112+
/// seamlessly with async/remote proving interfaces.
113+
#[async_trait(?Send)]
114+
impl ZkVmRemoteProver for NativeHost {
115+
async fn start_proving<'a>(
116+
&self,
117+
input: <Self::Input<'a> as zkaleido::ZkVmInputBuilder<'a>>::Input,
118+
proof_type: ProofType,
119+
) -> ZkVmResult<String> {
120+
// Execute proof synchronously
121+
let proof_receipt = self.prove(input, proof_type)?;
122+
123+
// Serialize using bincode
124+
let serialized = bincode::serialize(&proof_receipt)
125+
.map_err(|e| ZkVmError::InvalidProofReceipt(e.into()))?;
126+
127+
// Encode as hex to use as "proof ID"
128+
Ok(hex::encode(serialized))
129+
}
130+
131+
async fn get_proof_if_ready_inner(
132+
&self,
133+
id: String,
134+
) -> ZkVmResult<Option<Self::ZkVmProofReceipt>> {
135+
// Decode the hex-encoded proof
136+
let decoded = hex::decode(&id).map_err(|_| {
137+
ZkVmError::InvalidProofReceipt(
138+
std::io::Error::new(std::io::ErrorKind::InvalidData, "Invalid hex encoding").into(),
139+
)
140+
})?;
141+
142+
// Deserialize the ProofReceiptWithMetadata
143+
let proof: ProofReceiptWithMetadata =
144+
bincode::deserialize(&decoded).map_err(|e| ZkVmError::InvalidProofReceipt(e.into()))?;
145+
146+
// Convert to NativeProofReceipt
147+
let native_receipt = proof.try_into().map_err(ZkVmError::InvalidProofReceipt)?;
148+
149+
Ok(Some(native_receipt))
150+
}
151+
}

examples/fibonacci-composition/src/program.rs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -41,5 +41,3 @@ impl ZkVmProgram for FibCompositionProgram {
4141
H::extract_serde_public_output(public_values)
4242
}
4343
}
44-
45-
impl ZkVmProgramPerf for FibCompositionProgram {}

examples/fibonacci/src/program.rs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -31,8 +31,6 @@ impl ZkVmProgram for FibProgram {
3131
}
3232
}
3333

34-
impl ZkVmProgramPerf for FibProgram {}
35-
3634
#[cfg(test)]
3735
pub mod tests {
3836
use std::sync::Arc;

examples/groth16-verify-risc0/src/program.rs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -33,8 +33,6 @@ impl ZkVmProgram for Risc0Groth16VerifyProgram {
3333
}
3434
}
3535

36-
impl ZkVmProgramPerf for Risc0Groth16VerifyProgram {}
37-
3836
#[cfg(test)]
3937
mod tests {
4038
use std::sync::Arc;

examples/groth16-verify-sp1/src/program.rs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -33,8 +33,6 @@ impl ZkVmProgram for SP1Groth16VerifyProgram {
3333
}
3434
}
3535

36-
impl ZkVmProgramPerf for SP1Groth16VerifyProgram {}
37-
3836
#[cfg(test)]
3937
mod tests {
4038
use std::sync::Arc;

examples/schnorr-sig-verify/src/program.rs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -37,8 +37,6 @@ impl ZkVmProgram for SchnorrSigProgram {
3737
}
3838
}
3939

40-
impl ZkVmProgramPerf for SchnorrSigProgram {}
41-
4240
#[cfg(test)]
4341
mod tests {
4442
use std::sync::Arc;

examples/sha2-chain/src/program.rs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -31,8 +31,6 @@ impl ZkVmProgram for ShaChainProgram {
3131
}
3232
}
3333

34-
impl ZkVmProgramPerf for ShaChainProgram {}
35-
3634
#[cfg(test)]
3735
mod tests {
3836
use std::sync::Arc;

zkaleido/src/host.rs

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,3 +35,10 @@ pub trait ZkVmHostPerf: ZkVmHost {
3535

3636
/// A trait implemented by the host of a zkVM program with support for remote proving operations.
3737
pub trait ZkVmRemoteHost: ZkVmHost + ZkVmRemoteProver {}
38+
39+
/// Blanket implementation of `ZkVmRemoteHost` for any type that implements both
40+
/// `ZkVmHost` and `ZkVmRemoteProver`.
41+
///
42+
/// This allows any host that provides the necessary trait implementations to automatically
43+
/// satisfy the `ZkVmRemoteHost` trait without requiring explicit implementations.
44+
impl<T> ZkVmRemoteHost for T where T: ZkVmHost + ZkVmRemoteProver {}

0 commit comments

Comments
 (0)