@@ -203,6 +203,7 @@ export const parseGroth16ProofFromObject = (data: any, publicInputsData?: bigint
203
203
const imageIdBytes = hexStringToBytes ( imageIdHex ) ;
204
204
const journalBytes = hexStringToBytes ( journalHex ) ;
205
205
206
+
206
207
return createGroth16ProofFromRisc0 ( sealBytes , imageIdBytes , journalBytes )
207
208
208
209
} catch ( err ) {
@@ -228,7 +229,7 @@ export const parseGroth16ProofFromObject = (data: any, publicInputsData?: bigint
228
229
try {
229
230
publicInputs = findItemFromKeyPatterns ( data , [ 'public' ] ) ;
230
231
} catch ( err ) {
231
- throw new Error ( `Error: ${ err } ` ) ;
232
+
232
233
}
233
234
}
234
235
const a = tryParseG1PointFromKey ( proof , [ 'a' ] , curveId ) ;
@@ -258,21 +259,26 @@ export const parseGroth16ProofFromObject = (data: any, publicInputsData?: bigint
258
259
export const createGroth16ProofFromRisc0 = ( seal : Uint8Array , imageId : Uint8Array , journalBytes : Uint8Array ,
259
260
controlRoot : bigint = RISC0_CONTROL_ROOT , bn254ControlId : bigint = RISC0_BN254_CONTROL_ID ) : Groth16Proof => {
260
261
262
+
261
263
if ( imageId . length > 32 ) {
262
264
throw new Error ( "imageId must be 32 bytes" )
263
265
}
264
266
265
- const [ constrolRoot0 , controlRoot1 ] = splitDigest ( controlRoot ) ;
267
+ const [ controlRoot0 , controlRoot1 ] = splitDigest ( controlRoot ) ;
266
268
267
269
const proof = seal . slice ( 4 ) ;
268
270
269
271
272
+
270
273
const journal = createHash ( "sha256" ) . update ( journalBytes ) . digest ( ) ;
271
274
272
275
const claimDigest = digestReceiptClaim ( ok ( imageId , journal ) ) ;
273
276
277
+
274
278
const [ claim0 , claim1 ] = splitDigest ( claimDigest ) ;
275
279
280
+
281
+
276
282
const groth16Proof : Groth16Proof = {
277
283
a : {
278
284
x : toBigInt ( proof . slice ( 0 , 32 ) ) ,
@@ -282,7 +288,7 @@ export const createGroth16ProofFromRisc0 = (seal: Uint8Array, imageId: Uint8Arra
282
288
b : {
283
289
x : [
284
290
toBigInt ( proof . slice ( 96 , 128 ) ) ,
285
- toBigInt ( proof . slice ( 64 , 196 ) )
291
+ toBigInt ( proof . slice ( 64 , 96 ) )
286
292
] ,
287
293
y : [
288
294
toBigInt ( proof . slice ( 160 , 192 ) ) ,
@@ -296,7 +302,7 @@ export const createGroth16ProofFromRisc0 = (seal: Uint8Array, imageId: Uint8Arra
296
302
curveId : CurveId . BN254
297
303
} ,
298
304
publicInputs : [
299
- constrolRoot0 ,
305
+ controlRoot0 ,
300
306
controlRoot1 ,
301
307
claim0 ,
302
308
claim1 ,
@@ -311,7 +317,6 @@ export const createGroth16ProofFromRisc0 = (seal: Uint8Array, imageId: Uint8Arra
311
317
312
318
throw new Error ( `Invalid Groth16 proof: ${ groth16Proof } ` ) ;
313
319
314
-
315
320
}
316
321
317
322
@@ -344,19 +349,30 @@ export const checkGroth16VerifyingKey = (vk: Groth16VerifyingKey): boolean => {
344
349
345
350
const digestReceiptClaim = ( receipt : ReceiptClaim ) : Uint8Array => {
346
351
const { tagDigest, input, preStateDigest, postStateDigest, output, exitCode } = receipt ;
352
+
353
+ const systemExitCodeBuffer = Buffer . alloc ( 4 ) ;
354
+ systemExitCodeBuffer . writeUInt32BE ( exitCode . system << 24 ) ;
355
+
356
+ const userExitCodeBuffer = Buffer . alloc ( 4 ) ;
357
+ userExitCodeBuffer . writeUInt32BE ( exitCode . user << 24 ) ;
358
+
359
+ // Create a 2-byte big-endian representation of 4 << 8
360
+ const twoBytes = Buffer . alloc ( 2 ) ;
361
+ twoBytes . writeUInt16BE ( 4 << 8 ) ;
362
+
363
+
347
364
// Concatenating all parts into one Buffer
348
365
const data = Buffer . concat ( [
349
366
tagDigest ! ,
350
367
input ,
351
368
preStateDigest ,
352
369
postStateDigest ,
353
370
output ,
354
- Buffer . alloc ( 4 , exitCode . system << 24 ) , // Encode exitCode.system in 4 bytes, big-endian
355
- Buffer . alloc ( 4 , exitCode . user << 24 ) , // Encode exitCode.user in 4 bytes, big-endian
356
- Buffer . alloc ( 2 , 4 << 8 ) // Add the 4 << 8 equivalent to (4 << 8).to_bytes(2, 'big')
371
+ systemExitCodeBuffer ,
372
+ userExitCodeBuffer ,
373
+ twoBytes
357
374
] ) ;
358
375
359
- // Return the sha256 digest of the combined data
360
376
return createHash ( 'sha256' ) . update ( data ) . digest ( ) ;
361
377
}
362
378
@@ -390,19 +406,22 @@ function ok(imageId: Uint8Array, journalDigest: Uint8Array): ReceiptClaim {
390
406
const digestOutput = ( output : Output ) : Uint8Array => {
391
407
const { journalDigest, assumptionsDigest } = output ;
392
408
409
+
393
410
// Compute the internal tag digest equivalent to hashlib.sha256(b"risc0.Output").digest()
394
411
const tagDigest = createHash ( 'sha256' ) . update ( Buffer . from ( "risc0.Output" ) ) . digest ( ) ;
395
412
396
- // Concatenate all parts into a single Buffer
397
- const data = Buffer . concat ( [
398
- tagDigest ,
399
- journalDigest ,
400
- assumptionsDigest ,
401
- Buffer . alloc ( 2 , 2 << 8 ) // Add the 2 << 8 equivalent to (2 << 8).to_bytes(2, 'big')
413
+ const twoBytes = Buffer . alloc ( 2 ) ;
414
+ twoBytes . writeUInt16BE ( 512 ) ;
415
+
416
+ const combined = Buffer . concat ( [
417
+ tagDigest ,
418
+ Buffer . from ( journalDigest ) ,
419
+ Buffer . from ( assumptionsDigest ) ,
420
+ twoBytes // Append 2 as a 2-byte big-endian integer
402
421
] ) ;
403
422
404
423
// Return the sha256 digest of the combined data
405
- return createHash ( 'sha256' ) . update ( data ) . digest ( ) ;
424
+ return createHash ( 'sha256' ) . update ( combined ) . digest ( ) ;
406
425
}
407
426
408
427
const reverseByteOrderUint256 = ( value : bigint | Uint8Array ) : bigint => {
0 commit comments