@sig-net/midnight 0.12.0 → 0.14.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -11,7 +11,9 @@
11
11
  import { lookupSignetRequestAt } from "./signature-requests-state-reader.js";
12
12
  import { readSignetContractLedgerFromState, signetMapEntryKey, } from "./signet-contract-state-reader.js";
13
13
  import { recoverSignatureResponseSigner } from "./signature-response-verification.js";
14
+ import { verifyRespondBidirectionalSignature, } from "./ecdsa-attestation.js";
14
15
  import { signBidirectionalEventToSignedEvmTransaction, signBidirectionalEventToUnsignedEvmTransaction, } from "./signet-evtype2tx-requests.js";
16
+ import { requestIdBytes, } from "./signet-requests.js";
15
17
  /**
16
18
  * Reader over one requester contract / signet contract pair.
17
19
  * Construct once per pair and reuse: fetched request records are cached (they
@@ -181,10 +183,11 @@ export class SignetRequestResponseReader {
181
183
  /**
182
184
  * Fetch every respond-bidirectional response posted for `requestId`, in
183
185
  * post (count) order. UNVERIFIED: the signet contract stores posts without
184
- * checking them, so any entry may be garbage. Verify each candidate before
185
- * trusting it (in-circuit at claim time, or off-chain via the compiled
186
- * `pureCircuits.verifyRespondBidirectionalEvent` against the MPC derived
187
- * key you expect). An empty array simply means none posted yet: poll again.
186
+ * checking them, so any entry may be garbage. Each post carries a signature
187
+ * and nothing else, so verifying it against the MPC response key you expect
188
+ * is the only way to pick the genuine one: in-circuit at claim time, or off
189
+ * chain with {@link verifyRespondBidirectionalSignature} over the output you
190
+ * fetched. An empty array simply means none posted yet: poll again.
188
191
  *
189
192
  * @param requestId - The request id whose responses to enumerate.
190
193
  * @returns The posted records, index = count, empty when none yet.
@@ -206,5 +209,32 @@ export class SignetRequestResponseReader {
206
209
  }
207
210
  return responses;
208
211
  }
212
+ /**
213
+ * Fetch the respond-bidirectional posts for `requestId` and return the
214
+ * first (lowest count) one whose signature verifies over
215
+ * `serializedOutput` against `mpcResponseKey`: the off-chain twin of the
216
+ * check the client contract runs in-circuit, and the only way to pick a
217
+ * genuine post out of an unauthenticated log now that posts carry nothing
218
+ * but a signature.
219
+ *
220
+ * The output must be the exact unpadded bytes the attestation commits to
221
+ * (the packed respond payload, recomputed from the execution output the
222
+ * client fetched), so a post that verifies here is the post that proves at
223
+ * claim time.
224
+ *
225
+ * @param requestId - The request id to fetch a verified attestation for.
226
+ * @param serializedOutput - The serialised execution output the attestation
227
+ * must commit to, exact unpadded bytes.
228
+ * @param mpcResponseKey - The MPC response key the requesting contract
229
+ * pinned at deploy (see `deriveMidnightResponseKey`).
230
+ * @returns The first verifying post, or `undefined` when none has been
231
+ * posted yet (poll again) or none attests this output.
232
+ * @throws Error when the signet contract has no state, or its counter
233
+ * disagrees with the log (inconsistent ledger).
234
+ */
235
+ async getVerifiedRespondBidirectionalEvent(requestId, serializedOutput, mpcResponseKey) {
236
+ const events = await this.getRespondBidirectionalEvents(requestId);
237
+ return events.find((event) => verifyRespondBidirectionalSignature(requestIdBytes(requestId), serializedOutput, event, mpcResponseKey));
238
+ }
209
239
  }
210
240
  //# sourceMappingURL=signet-request-response-reader.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"signet-request-response-reader.js","sourceRoot":"","sources":["../src/signet-request-response-reader.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"signet-request-response-reader.js","sourceRoot":"","sources":["../src/signet-request-response-reader.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@sig-net/midnight",
3
- "version": "0.12.0",
3
+ "version": "0.14.0",
4
4
  "repository": {
5
5
  "type": "git",
6
6
  "url": "https://github.com/sig-net/midnight-integration",
@@ -40,7 +40,7 @@
40
40
  "@midnight-ntwrk/compact-runtime": "0.18.0-rc.1",
41
41
  "@midnight-ntwrk/midnight-js-types": "5.0.0-beta.4",
42
42
  "@noble/curves": "^2.2.0",
43
- "@sig-net/midnight-serde": "^0.12.0",
43
+ "@sig-net/midnight-serde": "^0.14.0",
44
44
  "ethers": "^6.17.0"
45
45
  },
46
46
  "devDependencies": {
@@ -7,8 +7,8 @@
7
7
  // - client contract(s): contracts on the Midnight blockchain that integrate with the Signet Distributed MPC
8
8
  // to execute arbitrary transactions on foreign blockchains.
9
9
  // - Signet singleton: a single contract on the Midnight blockchain holding the Signet registry for transaction
10
- // signature requests and responses, as well as the signed output of transactions executed
11
- // on foreign blockchains.
10
+ // signature requests and responses, as well as signed attestations of transactions executed
11
+ // on foreign blockchains (the execution outputs themselves travel off chain).
12
12
  //
13
13
  // Usage:
14
14
  // // Import this module at the start of a contract (resolved through node_modules via COMPACT_PATH):
@@ -29,12 +29,12 @@
29
29
  // (via SignetSigner interface) to notify the MPC of a SignBidirectionalEvent.
30
30
  // - SignatureRespondedEvent: Counterpart to SignBidirectionalEvent containing MPC generated signature requested by a SignBidirectionalEvent.
31
31
  // Posted by MPC back to Signet singleton for clients to extract to build a signed transaction.
32
- // - RespondBidirectionalEvent: Attestation of a transaction executed on a foreign blockchain: the attestation
33
- // digest of the request id and serialised output (see calculateSignetAttestationDigest)
34
- // plus the MPC's ECDSA signature over that digest, signed with the MPC's RESPONSE
35
- // key for the requesting contract: the key derived from the client contract's
36
- // address + the fixed path "midnight response key". The output itself travels
37
- // off chain. Posted by MPC back to Signet singleton for clients to extract,
32
+ // - RespondBidirectionalEvent: Attestation of a transaction executed on a foreign blockchain: the MPC's ECDSA
33
+ // signature over the attestation digest of the request id and serialised output
34
+ // (see calculateSignetAttestationDigest), signed with the MPC's RESPONSE key for
35
+ // the requesting contract: the key derived from the client contract's address +
36
+ // the fixed path "midnight response key". Both the digest and the output itself
37
+ // travel off chain. Posted by MPC back to Signet singleton for clients to extract,
38
38
  // verify (see verifyRespondBidirectionalEvent) and deliver back to the client
39
39
  // contract.
40
40
  //
@@ -50,6 +50,10 @@
50
50
  // verifies the posted SignatureRespondedEvent and broadcasts txn to destination chain.
51
51
  // 4. MPC observes txn execution on destination chain, posts a RespondBidirectionalEvent
52
52
  // attestation to the central Signet contract, and the client polls it by RequestId.
53
+ // The client recovers the execution output itself off chain (for EVM: the mined
54
+ // call's return data via debug_traceTransaction, also served by the fakenet
55
+ // responder's /responses/{requestId} helper API) and hands output plus attestation
56
+ // to its verify circuit. See "Output recovery" in this package's README.
53
57
  //
54
58
  // Read more:
55
59
  // - For full integration examples (such as an ERC20 cross chain vault example) see
@@ -254,30 +258,30 @@ module Signet {
254
258
  signature: Signature;
255
259
  }
256
260
 
257
- // Attestation of a transaction executed on a foreign blockchain: the 32-byte
258
- // attestation digest of the request id and serialised output (see
259
- // calculateSignetAttestationDigest) plus the MPC's ECDSA (secp256k1) signature
260
- // over that digest, signed with the MPC's RESPONSE key for the requesting contract:
261
- // mpcResponseKey = f(mpcRootKey[keyVersion], sender, "midnight response key")
262
- // i.e. the same derivation as request-signing keys but with the FIXED
263
- // respond-bidirectional path, so it is per-client-contract yet independent of any
264
- // request's own path (mirrors the MPC's per-chain "<chain> response key" convention).
265
- // The execution output itself is unbounded, so it travels off chain. Posted by MPC
266
- // back to Signet singleton for clients to extract, verify and deliver back to the
267
- // client contract. Clients fetch the full output off chain, recompute the digest
268
- // and verify via verifyRespondBidirectionalEvent. The singleton stores posts
269
- // UNVERIFIED: client contracts must verify the signature themselves against their
270
- // MPC response key.
261
+ // RespondBidirectionalEvent is the final step of the Sig Network Sign Bidirectional flow.
262
+ // It holds an MPC ECDSA signature of an attestation digest verifying foreign chain execution output.
263
+ //
264
+ // The attestation digest is a keccak256 hash of the request id concatenated with the serialised foreign
265
+ // transaction execution output:
266
+ // attestationDigest = keccak256(requestId + serialisedOutput)
267
+ //
268
+ // The signature is the ECDSA secp256k1 signature over the attestation digest by the MPC with the
269
+ // client contract's MPC response key:
270
+ // signature = signSECP256k1(mpcResponseKey, attestationDigest)
271
+ //
272
+ // Where the MPC response key is a per-client-contract key derived using the same derivation function
273
+ // as request signing keys, with the path set to the fixed "midnight response key":
274
+ // mpcResponseKey = f(mpcRootKey[keyVersion], sender, "midnight response key")
275
+ //
276
+ // Storage & Verification:
277
+ // The execution output is of variable size, so it travels off chain, and the digest
278
+ // over it is recomputed rather than stored. The client fetches the output, recomputes
279
+ // the attestation digest and verifies the signature in-circuit via
280
+ // verifyRespondBidirectionalEvent against its derived MPC response key. The signature
281
+ // is the ONLY thing that distinguishes a genuine post from garbage: the Signet
282
+ // singleton is an unauthenticated log and stores every post unverified.
271
283
  export struct RespondBidirectionalEvent {
272
- // The attestation digest the signature signs: keccak256 of the request id
273
- // concatenated with the serialised output (see calculateSignetAttestationDigest).
274
- // A checkpoint for off-chain readers: match a fetched output against the
275
- // attestation (and check the signature) without any other inputs.
276
- // verifyRespondBidirectionalEvent binds it to the actual output bytes in-circuit.
277
- attestationDigest: Bytes<32>;
278
-
279
- // The MPC's ECDSA signature over attestationDigest above. The verify
280
- // circuit's r is this signature's bigR.x mod the curve order.
284
+ // The MPC's ECDSA signature over the attestation digest.
281
285
  signature: Signature;
282
286
  }
283
287
 
@@ -288,20 +292,13 @@ module Signet {
288
292
  requestId: RequestId;
289
293
  };
290
294
 
291
- // The 32-byte attestation digest the MPC ECDSA-signs to attest a remote execution:
292
- // keccak256 over the request id concatenated with the serialised output, exactly
293
- // the MPC's respond-bidirectional construction (hash(request_id || serialized_output):
294
- // one flat concatenation, one hash). The output is hashed AS GIVEN, at its exact
295
- // width: no padding and no length binding. The width is a generic parameter, fixed
296
- // by each client contract from its own respond serialisation schema. The digest
297
- // commits to the output byte-for-byte: the keccak preimage of the
298
- // [RequestId, Bytes<N>] pair is the raw concatenated bytes.
299
- // secp256k1EcdsaVerify interprets the digest as a BIG-ENDIAN integer reduced mod
300
- // the curve order (RFC 6979 convention). ONE implementation for everyone: client
301
- // contracts call this in-circuit. The compiler cannot export a size-generic circuit
302
- // top-level, so off-chain code uses the TS twin (calculateSignetAttestationDigest
303
- // in ecdsa-attestation.ts), pinned byte-for-byte against the fixed-width
304
- // instantiations circuits.compact exports as test oracles.
295
+ // Calculates the 32-byte attestation digest for a remote execution output:
296
+ // attestationDigest = keccak256(requestId + serializedOutput)
297
+ //
298
+ // Inputs are concatenated raw with no padding or length prefixes. The output digest is
299
+ // interpreted as a big-endian integer during ECDSA signature verification.
300
+ //
301
+ // Note: Off-chain code should use the matching TypeScript twin in `ecdsa-attestation.ts`.
305
302
  export pure circuit calculateSignetAttestationDigest<#serializedOutputLength>(
306
303
  requestId: RequestId,
307
304
  serializedOutput: Bytes<serializedOutputLength>,
@@ -320,23 +317,21 @@ module Signet {
320
317
  v[7], v[6], v[5], v[4], v[3], v[2], v[1], v[0]];
321
318
  }
322
319
 
323
- // Verify a RespondBidirectionalEvent against the serialised output it attests and
324
- // a secp256k1 public key: the event's digest checkpoint must equal the recomputed
325
- // attestation digest of (requestId, serializedOutput), and the event's ECDSA
326
- // signature must sign that digest. This is the check client contracts run before
327
- // accepting a response (the Signet singleton stores posts unverified). Pass the
328
- // contract's MPC RESPONSE key (derived off-chain from the contract's address + the
329
- // fixed path "midnight response key", typically hash-pinned in the contract's
330
- // ledger at deploy time). The caller supplies serializedOutput at its exact
331
- // unpadded width, per calculateSignetAttestationDigest.
320
+ // Verifies a RespondBidirectionalEvent against its execution output and MPC response key.
332
321
  //
333
- // Takes the event as stored: the caller hands over the record it read, and the
334
- // big-endian-to-little-endian re-encoding happens here, in one place for every
335
- // integrator.
322
+ // Verification steps:
323
+ // 1. Recompute digest: digest = keccak256(requestId + serializedOutput)
324
+ // 2. Verify signature: secp256k1EcdsaVerify(digest, signature, mpcResponseKey) == true
336
325
  //
337
- // ECDSA's r is bigR.x reduced mod the curve order. bigR.x is taken as-is: it is
338
- // already below the order for all but a ~2^-128 fraction of signatures, and one
339
- // that is not simply fails to verify.
326
+ // The caller supplies serializedOutput at its exact unpadded width, per
327
+ // calculateSignetAttestationDigest, and hands over the event record as stored: the
328
+ // big-endian-to-little-endian re-encoding of the signature scalars happens here, in one
329
+ // place for every integrator. ECDSA's r is bigR.x reduced mod the curve order; bigR.x is
330
+ // taken as-is, as it is already below the order for all but a ~2^-128 fraction of
331
+ // signatures, and one that is not simply fails to verify.
332
+ //
333
+ // Note: Client contracts must run this check before consuming outputs, as the Signet
334
+ // singleton stores responses unverified.
340
335
  export pure circuit verifyRespondBidirectionalEvent<#serializedOutputLength>(
341
336
  requestId: RequestId,
342
337
  serializedOutput: Bytes<serializedOutputLength>,
@@ -347,10 +342,8 @@ module Signet {
347
342
  requestId,
348
343
  serializedOutput,
349
344
  );
350
- // Two consts rather than one `&&` expression: compactc 0.33 ICEs when the
351
- // secp256k1EcdsaVerify call (its scalar casts) sits inside a subexpression.
352
- const checkpointMatches = digest == respondBidirectionalEvent.attestationDigest;
353
- const signatureValid = secp256k1EcdsaVerify(
345
+
346
+ return secp256k1EcdsaVerify(
354
347
  digest,
355
348
  Secp256k1EcdsaSignature {
356
349
  r: reverseBytes32(respondBidirectionalEvent.signature.bigR.x) as Secp256k1Scalar,
@@ -358,7 +351,6 @@ module Signet {
358
351
  },
359
352
  mpcResponseKey
360
353
  );
361
- return checkpointMatches && signatureValid;
362
354
  }
363
355
 
364
356
  // Hash a secp256k1 public key exactly as client contracts pin it at deploy time