Skip to content

Commit 4f36e96

Browse files
committed
feat: stateless proving with Moongate
1 parent 287a2c5 commit 4f36e96

File tree

4 files changed

+59
-1
lines changed

4 files changed

+59
-1
lines changed

crates/cuda/proto/api.proto

+1
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ service ProverService {
66
rpc Setup(SetupRequest) returns (SetupResponse) {}
77
rpc Ready(ReadyRequest) returns (ReadyResponse) {}
88
rpc ProveCore(ProveCoreRequest) returns (ProveCoreResponse) {}
9+
rpc ProveCoreStateless(ProveCoreRequest) returns (ProveCoreResponse) {}
910
rpc Compress(CompressRequest) returns (CompressResponse) {}
1011
rpc Shrink(ShrinkRequest) returns (ShrinkResponse) {}
1112
rpc Wrap(WrapRequest) returns (WrapResponse) {}

crates/cuda/src/lib.rs

+29
Original file line numberDiff line numberDiff line change
@@ -76,6 +76,19 @@ pub struct ProveCoreRequestPayload {
7676
pub stdin: SP1Stdin,
7777
}
7878

79+
/// The payload for the [sp1_prover::SP1Prover::stateless_prove_core] method.
80+
///
81+
/// We use this object to serialize and deserialize the payload from the client to the server.
82+
/// The ELF is included in the payload to allow to build the program and the pk on the Moongate
83+
/// server
84+
#[derive(Serialize, Deserialize)]
85+
pub struct StatelessProveCoreRequestPayload {
86+
/// The input stream.
87+
pub stdin: SP1Stdin,
88+
/// The ELF.
89+
pub elf: Vec<u8>,
90+
}
91+
7992
/// The payload for the [sp1_prover::SP1Prover::compress] method.
8093
///
8194
/// We use this object to serialize and deserialize the payload from the client to the server.
@@ -259,6 +272,22 @@ impl SP1CudaProver {
259272
Ok(proof)
260273
}
261274

275+
/// Executes the [sp1_prover::SP1Prover::prove_core] method inside the container.
276+
///
277+
/// You will need at least 24GB of VRAM to run this method.
278+
pub fn prove_core_stateless(
279+
&self,
280+
elf: Vec<u8>,
281+
stdin: &SP1Stdin,
282+
) -> Result<SP1CoreProof, SP1CoreProverError> {
283+
let payload = StatelessProveCoreRequestPayload { elf, stdin: stdin.clone() };
284+
let request =
285+
crate::proto::api::ProveCoreRequest { data: bincode::serialize(&payload).unwrap() };
286+
let response = block_on(async { self.client.prove_core_stateless(request).await }).unwrap();
287+
let proof: SP1CoreProof = bincode::deserialize(&response.result).unwrap();
288+
Ok(proof)
289+
}
290+
262291
/// Executes the [sp1_prover::SP1Prover::compress] method inside the container.
263292
///
264293
/// You will need at least 24GB of VRAM to run this method.

crates/cuda/src/proto/api.rs

+28
Original file line numberDiff line numberDiff line change
@@ -87,6 +87,11 @@ pub trait ProverService {
8787
ctx: twirp::Context,
8888
req: ProveCoreRequest,
8989
) -> Result<ProveCoreResponse, twirp::TwirpErrorResponse>;
90+
async fn prove_core_stateless(
91+
&self,
92+
ctx: twirp::Context,
93+
req: ProveCoreRequest,
94+
) -> Result<ProveCoreResponse, twirp::TwirpErrorResponse>;
9095
async fn compress(
9196
&self,
9297
ctx: twirp::Context,
@@ -129,6 +134,13 @@ where
129134
) -> Result<ProveCoreResponse, twirp::TwirpErrorResponse> {
130135
T::prove_core(&*self, ctx, req).await
131136
}
137+
async fn prove_core_stateless(
138+
&self,
139+
ctx: twirp::Context,
140+
req: ProveCoreRequest,
141+
) -> Result<ProveCoreResponse, twirp::TwirpErrorResponse> {
142+
T::prove_core_stateless(&*self, ctx, req).await
143+
}
132144
async fn compress(
133145
&self,
134146
ctx: twirp::Context,
@@ -174,6 +186,12 @@ where
174186
api.prove_core(ctx, req).await
175187
},
176188
)
189+
.route(
190+
"/ProveCoreStateless",
191+
|api: T, ctx: twirp::Context, req: ProveCoreRequest| async move {
192+
api.prove_core_stateless(ctx, req).await
193+
},
194+
)
177195
.route(
178196
"/Compress",
179197
|api: T, ctx: twirp::Context, req: CompressRequest| async move {
@@ -208,6 +226,10 @@ pub trait ProverServiceClient: Send + Sync + std::fmt::Debug {
208226
&self,
209227
req: ProveCoreRequest,
210228
) -> Result<ProveCoreResponse, twirp::ClientError>;
229+
async fn prove_core_stateless(
230+
&self,
231+
req: ProveCoreRequest,
232+
) -> Result<ProveCoreResponse, twirp::ClientError>;
211233
async fn compress(
212234
&self,
213235
req: CompressRequest,
@@ -238,6 +260,12 @@ impl ProverServiceClient for twirp::client::Client {
238260
) -> Result<ProveCoreResponse, twirp::ClientError> {
239261
self.request("api.ProverService/ProveCore", req).await
240262
}
263+
async fn prove_core_stateless(
264+
&self,
265+
req: ProveCoreRequest,
266+
) -> Result<ProveCoreResponse, twirp::ClientError> {
267+
self.request("api.ProverService/ProveCoreStateless", req).await
268+
}
241269
async fn compress(
242270
&self,
243271
req: CompressRequest,

crates/sdk/src/cuda/mod.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -96,7 +96,7 @@ impl Prover<CpuProverComponents> for CudaProver {
9696
kind: SP1ProofMode,
9797
) -> Result<SP1ProofWithPublicValues> {
9898
// Generate the core proof.
99-
let proof = self.cuda_prover.prove_core(stdin)?;
99+
let proof = self.cuda_prover.prove_core_stateless(pk.elf.clone(), stdin)?;
100100
if kind == SP1ProofMode::Core {
101101
return Ok(SP1ProofWithPublicValues::new(
102102
SP1Proof::Core(proof.proof.0),

0 commit comments

Comments
 (0)