@sig-net/midnight 0.10.0 → 0.12.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.
- package/README.md +17 -17
- package/dist/abi-serde.d.ts +89 -0
- package/dist/abi-serde.d.ts.map +1 -0
- package/dist/abi-serde.js +393 -0
- package/dist/abi-serde.js.map +1 -0
- package/dist/constants.d.ts +23 -14
- package/dist/constants.d.ts.map +1 -1
- package/dist/constants.js +28 -20
- package/dist/constants.js.map +1 -1
- package/dist/ecdsa-attestation.d.ts +81 -9
- package/dist/ecdsa-attestation.d.ts.map +1 -1
- package/dist/ecdsa-attestation.js +137 -18
- package/dist/ecdsa-attestation.js.map +1 -1
- package/dist/epsilon-derivation.d.ts +8 -8
- package/dist/epsilon-derivation.d.ts.map +1 -1
- package/dist/epsilon-derivation.js +16 -18
- package/dist/epsilon-derivation.js.map +1 -1
- package/dist/index.d.ts +1 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1 -0
- package/dist/index.js.map +1 -1
- package/dist/managed/compiler/contract-info.json +180 -104
- package/dist/managed/compiler/contract-manifest.json +8 -8
- package/dist/managed/contract/index.d.ts +38 -24
- package/dist/managed/contract/index.js +363 -154
- package/dist/managed/contract/index.js.map +1 -1
- package/dist/signature-requests-state-reader.d.ts +15 -15
- package/dist/signature-requests-state-reader.d.ts.map +1 -1
- package/dist/signature-requests-state-reader.js +51 -34
- package/dist/signature-requests-state-reader.js.map +1 -1
- package/dist/signature-response-verification.d.ts +2 -2
- package/dist/signature-response-verification.js +8 -8
- package/dist/signature-response-verification.js.map +1 -1
- package/dist/signet-contract-state-reader.d.ts +74 -58
- package/dist/signet-contract-state-reader.d.ts.map +1 -1
- package/dist/signet-contract-state-reader.js +76 -58
- package/dist/signet-contract-state-reader.js.map +1 -1
- package/dist/signet-evtype2tx-requests.d.ts +62 -59
- package/dist/signet-evtype2tx-requests.d.ts.map +1 -1
- package/dist/signet-evtype2tx-requests.js +58 -90
- package/dist/signet-evtype2tx-requests.js.map +1 -1
- package/dist/signet-request-response-reader.d.ts +26 -26
- package/dist/signet-request-response-reader.d.ts.map +1 -1
- package/dist/signet-request-response-reader.js +37 -37
- package/dist/signet-request-response-reader.js.map +1 -1
- package/dist/signet-requests.d.ts +30 -30
- package/dist/signet-requests.d.ts.map +1 -1
- package/dist/signet-requests.js +29 -30
- package/dist/signet-requests.js.map +1 -1
- package/package.json +3 -2
- package/src/Signet.compact +137 -88
- package/src/circuits.compact +45 -2
package/src/Signet.compact
CHANGED
|
@@ -29,13 +29,14 @@
|
|
|
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:
|
|
33
|
-
//
|
|
34
|
-
// MPC's
|
|
35
|
-
//
|
|
36
|
-
//
|
|
37
|
-
//
|
|
38
|
-
// to the client
|
|
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,
|
|
38
|
+
// verify (see verifyRespondBidirectionalEvent) and deliver back to the client
|
|
39
|
+
// contract.
|
|
39
40
|
//
|
|
40
41
|
// These key types are best understood within the sign bidirectional flow that they enable:
|
|
41
42
|
// 1. Client contract stores a SignBidirectionalEvent in a SignBidirectionalEventMap its own ledger
|
|
@@ -48,7 +49,7 @@
|
|
|
48
49
|
// 3. Client polls the Signet singleton contract SignatureRespondedEventMap for the signature by RequestId,
|
|
49
50
|
// verifies the posted SignatureRespondedEvent and broadcasts txn to destination chain.
|
|
50
51
|
// 4. MPC observes txn execution on destination chain, posts a RespondBidirectionalEvent
|
|
51
|
-
// attestation to the central Signet contract
|
|
52
|
+
// attestation to the central Signet contract, and the client polls it by RequestId.
|
|
52
53
|
//
|
|
53
54
|
// Read more:
|
|
54
55
|
// - For full integration examples (such as an ERC20 cross chain vault example) see
|
|
@@ -121,7 +122,7 @@ module Signet {
|
|
|
121
122
|
// TxParamType indicates which transaction-param decomposition a request
|
|
122
123
|
// contains so an off-chain consumer (e.g. the MPC) knows how to re-assemble it.
|
|
123
124
|
export enum TxParamType {
|
|
124
|
-
evmType2, //
|
|
125
|
+
evmType2, // EvmType2TxParams: an EIP-1559 EVM transaction (envelope + calldata)
|
|
125
126
|
reserved, // Reserved for future use. Exists to keep enum >= 2 (proof server bug).
|
|
126
127
|
}
|
|
127
128
|
|
|
@@ -166,14 +167,16 @@ module Signet {
|
|
|
166
167
|
// (see calculateRequestId).
|
|
167
168
|
export new type RequestId = Bytes<32>;
|
|
168
169
|
|
|
169
|
-
//
|
|
170
|
-
//
|
|
171
|
-
//
|
|
172
|
-
//
|
|
170
|
+
// keccak256 of the whole record, so the id commits to every field including sender
|
|
171
|
+
// (which scopes ids per contract). No domain-separation tag, deliberately.
|
|
172
|
+
//
|
|
173
|
+
// Hashes the field-aligned binary representation (each field re-padded to its declared
|
|
174
|
+
// width), so off-chain consumers must reproduce that layout exactly. Type argument is
|
|
175
|
+
// the INPUT type, the return is always Bytes<32>.
|
|
173
176
|
export pure circuit calculateRequestId<TxParams, #LenOutputDeserialization, #LenRespondSerialization>(
|
|
174
177
|
request: SignBidirectionalEvent<TxParams, LenOutputDeserialization, LenRespondSerialization>
|
|
175
178
|
): RequestId {
|
|
176
|
-
return
|
|
179
|
+
return keccak256<SignBidirectionalEvent<TxParams, LenOutputDeserialization, LenRespondSerialization>>(request) as RequestId;
|
|
177
180
|
}
|
|
178
181
|
|
|
179
182
|
// ---- Client Contract: SignBidirectionalEvent Map ---------------------------------------------------
|
|
@@ -190,7 +193,7 @@ module Signet {
|
|
|
190
193
|
// Signet singleton to notify the MPC of a SignBidirectionalEvent.
|
|
191
194
|
export contract SignetSigner {
|
|
192
195
|
// Called by client contracts to notify the MPC of a SignBidirectionalEvent.
|
|
193
|
-
circuit
|
|
196
|
+
circuit signBidirectional(
|
|
194
197
|
// Canonical id of the SignBidirectionalEvent (calculate with calculateRequestId).
|
|
195
198
|
requestId: RequestId,
|
|
196
199
|
// Versioned notification of the SignBidirectionalEvent
|
|
@@ -221,46 +224,61 @@ module Signet {
|
|
|
221
224
|
};
|
|
222
225
|
}
|
|
223
226
|
|
|
227
|
+
// A curve point in affine coordinates, SEC1 big-endian. Field-for-field the
|
|
228
|
+
// AffinePoint of the sig-net EVM and Solana signer contracts.
|
|
229
|
+
export struct AffinePoint {
|
|
230
|
+
x: Bytes<32>;
|
|
231
|
+
y: Bytes<32>;
|
|
232
|
+
}
|
|
233
|
+
|
|
234
|
+
// The MPC's canonical ECDSA signature: bigR the full nonce point (so consumers
|
|
235
|
+
// never decompress), s big-endian, recoveryId the parity of R.y (0 or 1).
|
|
236
|
+
// Deliberately identical to the Signature struct every other sig-net signer
|
|
237
|
+
// contract exposes (EVM ChainSignatures.sol, the Solana signet program) and to
|
|
238
|
+
// the MPC's own Signature { big_r, s, recovery_id }: one vocabulary across
|
|
239
|
+
// chains. The scheme is fixed by the request's own MPCSignatureAlgorithm.
|
|
240
|
+
//
|
|
241
|
+
// Stored bytes are BIG-endian throughout, the canonical SEC1 order. The scalar
|
|
242
|
+
// casts read little-endian, so verifyRespondBidirectionalEvent reverses on the
|
|
243
|
+
// way in, keeping the stored record canonical.
|
|
244
|
+
export struct Signature {
|
|
245
|
+
bigR: AffinePoint;
|
|
246
|
+
s: Bytes<32>;
|
|
247
|
+
recoveryId: Uint<8>;
|
|
248
|
+
}
|
|
249
|
+
|
|
224
250
|
// Counterpart to SignBidirectionalEvent containing MPC generated signature requested by a SignBidirectionalEvent.
|
|
225
251
|
// Posted by MPC back to Signet singleton for clients to extract to build a signed transaction.
|
|
226
252
|
export struct SignatureRespondedEvent {
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
s: Bytes<32>; // signature s
|
|
230
|
-
recoveryId: Uint<8>; // parity of R.y for public-key recovery
|
|
253
|
+
// The requested signature over the transaction the request describes.
|
|
254
|
+
signature: Signature;
|
|
231
255
|
}
|
|
232
256
|
|
|
233
|
-
//
|
|
234
|
-
//
|
|
235
|
-
//
|
|
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:
|
|
236
261
|
// mpcResponseKey = f(mpcRootKey[keyVersion], sender, "midnight response key")
|
|
237
262
|
// i.e. the same derivation as request-signing keys but with the FIXED
|
|
238
263
|
// respond-bidirectional path, so it is per-client-contract yet independent of any
|
|
239
264
|
// request's own path (mirrors the MPC's per-chain "<chain> response key" convention).
|
|
240
|
-
//
|
|
241
|
-
// back to
|
|
242
|
-
//
|
|
243
|
-
// verifyRespondBidirectionalEvent.
|
|
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.
|
|
244
271
|
export struct RespondBidirectionalEvent {
|
|
245
|
-
//
|
|
246
|
-
//
|
|
247
|
-
//
|
|
248
|
-
//
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
// `Secp256k1Scalar as Bytes<32>` cast produces). Stored as bytes because
|
|
256
|
-
// Secp256k1Scalar values cannot live in ledger state (compiler limitation).
|
|
257
|
-
// r is the MPC signature's big_r.x reduced mod the curve order.
|
|
258
|
-
r: Bytes<32>;
|
|
259
|
-
s: Bytes<32>;
|
|
260
|
-
|
|
261
|
-
// Recovery id (parity of R.y), for off-chain public key recovery only.
|
|
262
|
-
// Unused in-circuit: verification takes the public key as an explicit input.
|
|
263
|
-
recoveryId: Uint<8>;
|
|
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.
|
|
281
|
+
signature: Signature;
|
|
264
282
|
}
|
|
265
283
|
|
|
266
284
|
// SignetMapKey used to locate SignBidirectionalEventNotifications, SignatureRespondedEvent and
|
|
@@ -270,48 +288,77 @@ module Signet {
|
|
|
270
288
|
requestId: RequestId;
|
|
271
289
|
};
|
|
272
290
|
|
|
273
|
-
// The 32-byte digest the MPC ECDSA-signs to attest a remote execution:
|
|
274
|
-
//
|
|
275
|
-
//
|
|
276
|
-
//
|
|
277
|
-
//
|
|
278
|
-
//
|
|
279
|
-
//
|
|
280
|
-
|
|
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.
|
|
305
|
+
export pure circuit calculateSignetAttestationDigest<#serializedOutputLength>(
|
|
281
306
|
requestId: RequestId,
|
|
282
|
-
serializedOutput: Bytes<
|
|
283
|
-
outputLen: Uint<8>
|
|
307
|
+
serializedOutput: Bytes<serializedOutputLength>,
|
|
284
308
|
): Bytes<32> {
|
|
285
|
-
|
|
286
|
-
persistentHash<Bytes<128>>(serializedOutput),
|
|
287
|
-
outputLen as Field as Bytes<32>
|
|
288
|
-
]);
|
|
289
|
-
return persistentHash<Vector<2, Bytes<32>>>([requestId as Bytes<32>, outHash]);
|
|
309
|
+
return keccak256<[RequestId, Bytes<serializedOutputLength>]>([requestId, serializedOutput]);
|
|
290
310
|
}
|
|
291
311
|
|
|
292
|
-
//
|
|
293
|
-
//
|
|
294
|
-
//
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
312
|
+
// Same Bytes -> Vector<Uint<8>> idiom numericAbiWord uses. Pulls in a byte-decomposition
|
|
313
|
+
// lookup table, a fixed cost the calling circuit pays once and shares with any other
|
|
314
|
+
// byte-level work it does, so reverse at the boundary and never per element.
|
|
315
|
+
pure circuit reverseBytes32(b: Bytes<32>): Bytes<32> {
|
|
316
|
+
const v = b as Vector<32, Uint<8>>;
|
|
317
|
+
return Bytes[v[31], v[30], v[29], v[28], v[27], v[26], v[25], v[24],
|
|
318
|
+
v[23], v[22], v[21], v[20], v[19], v[18], v[17], v[16],
|
|
319
|
+
v[15], v[14], v[13], v[12], v[11], v[10], v[9], v[8],
|
|
320
|
+
v[7], v[6], v[5], v[4], v[3], v[2], v[1], v[0]];
|
|
321
|
+
}
|
|
322
|
+
|
|
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.
|
|
332
|
+
//
|
|
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.
|
|
336
|
+
//
|
|
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.
|
|
340
|
+
export pure circuit verifyRespondBidirectionalEvent<#serializedOutputLength>(
|
|
299
341
|
requestId: RequestId,
|
|
342
|
+
serializedOutput: Bytes<serializedOutputLength>,
|
|
300
343
|
respondBidirectionalEvent: RespondBidirectionalEvent,
|
|
301
344
|
mpcResponseKey: Secp256k1Point
|
|
302
345
|
): Boolean {
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
346
|
+
const digest = calculateSignetAttestationDigest<serializedOutputLength>(
|
|
347
|
+
requestId,
|
|
348
|
+
serializedOutput,
|
|
349
|
+
);
|
|
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(
|
|
354
|
+
digest,
|
|
309
355
|
Secp256k1EcdsaSignature {
|
|
310
|
-
r: respondBidirectionalEvent.
|
|
311
|
-
s: respondBidirectionalEvent.s as Secp256k1Scalar,
|
|
356
|
+
r: reverseBytes32(respondBidirectionalEvent.signature.bigR.x) as Secp256k1Scalar,
|
|
357
|
+
s: reverseBytes32(respondBidirectionalEvent.signature.s) as Secp256k1Scalar,
|
|
312
358
|
},
|
|
313
359
|
mpcResponseKey
|
|
314
360
|
);
|
|
361
|
+
return checkpointMatches && signatureValid;
|
|
315
362
|
}
|
|
316
363
|
|
|
317
364
|
// Hash a secp256k1 public key exactly as client contracts pin it at deploy time
|
|
@@ -325,35 +372,37 @@ module Signet {
|
|
|
325
372
|
|
|
326
373
|
// The EVM transaction to be signed, decomposed into typed fields
|
|
327
374
|
// (EIP-1559 / type-2: https://eips.ethereum.org/EIPS/eip-1559).
|
|
328
|
-
// Decomposed
|
|
329
|
-
//
|
|
330
|
-
//
|
|
331
|
-
// serialized_transaction instead; the decomposition follows its Canton
|
|
375
|
+
// Decomposed so the requesting contract can enforce invariants field by
|
|
376
|
+
// field, and the MPC re-assembles and RLP-encodes off-chain. (The MPC's chain-agnostic primitive carries an opaque
|
|
377
|
+
// serialized_transaction instead, and the decomposition follows its Canton
|
|
332
378
|
// adapter's EvmType2TransactionParams.)
|
|
333
379
|
//
|
|
334
380
|
// Compact has no runtime-dynamic sizes, so every variable-length EVM tx
|
|
335
381
|
// part follows one scheme: a compile-time CAPACITY (a generic size
|
|
336
382
|
// parameter each requesting contract fixes as its throttle) plus a runtime
|
|
337
383
|
// count that says how many leading slots are real. Off-chain consumers use
|
|
338
|
-
// the counts
|
|
384
|
+
// the counts. Unused capacity is hashed as part of the record (zero-fill by
|
|
339
385
|
// convention) but never reaches the assembled transaction.
|
|
340
|
-
|
|
341
|
-
|
|
386
|
+
// Canonical EIP-1559 payload order, which is the RLP order the MPC re-assembles into.
|
|
387
|
+
// Each count sits directly before the slot it bounds. This order is also the
|
|
388
|
+
// request-id hash order, so it is part of the wire contract.
|
|
389
|
+
export struct EvmType2TxParams<#maxCalldataWords, #maxAccessListEntries, #maxStorageKeysPerEntry> {
|
|
342
390
|
chainId: Uint<64>; // EVM chain id (also expressed in caip2Id)
|
|
343
391
|
nonce: Uint<64>; // account nonce of the derived sender
|
|
344
|
-
gasLimit: Uint<64>; // gas ceiling for the call
|
|
345
|
-
maxFeePerGas: Uint<128>; // wei
|
|
346
392
|
maxPriorityFeePerGas: Uint<128>; // wei
|
|
393
|
+
maxFeePerGas: Uint<128>; // wei
|
|
394
|
+
gasLimit: Uint<64>; // gas ceiling for the call
|
|
395
|
+
to: Bytes<20>; // call target (e.g. the ERC20 contract)
|
|
347
396
|
value: Uint<128>; // ETH sent with the call, in wei
|
|
397
|
+
calldata: Maybe<EvmCalldata<maxCalldataWords>>; // none = plain ETH transfer ("0x" data)
|
|
348
398
|
accessListEntryCount: Uint<8>; // how many leading accessList entries are real
|
|
349
|
-
accessList: Vector<maxAccessListEntries,
|
|
350
|
-
calldata: Maybe<EVMCalldata<maxCalldataWords>>; // none = plain ETH transfer ("0x" data)
|
|
399
|
+
accessList: Vector<maxAccessListEntries, EvmAccessListEntry<maxStorageKeysPerEntry>>;
|
|
351
400
|
}
|
|
352
401
|
|
|
353
402
|
// One EIP-2930 access-list entry (https://eips.ethereum.org/EIPS/eip-2930):
|
|
354
403
|
// an address plus the storage keys the transaction pre-declares. Keys are
|
|
355
404
|
// raw 32-byte values, copied verbatim into the RLP encoding.
|
|
356
|
-
export struct
|
|
405
|
+
export struct EvmAccessListEntry<#maxStorageKeys> {
|
|
357
406
|
address: Bytes<20>;
|
|
358
407
|
storageKeyCount: Uint<8>; // how many leading storageKeys are real
|
|
359
408
|
storageKeys: Vector<maxStorageKeys, Bytes<32>>;
|
|
@@ -365,7 +414,7 @@ module Signet {
|
|
|
365
414
|
// the MPC signs a transaction composed of exactly these words. See the
|
|
366
415
|
// ABI Calldata Word Construction Utilities below for help constructing
|
|
367
416
|
// canonical ABI words for common types.
|
|
368
|
-
export struct
|
|
417
|
+
export struct EvmCalldata<#maxWords> {
|
|
369
418
|
selector: Bytes<4>; // the literal first 4 calldata bytes
|
|
370
419
|
noWords: Uint<16>; // No. of used words in the words list
|
|
371
420
|
words: Vector<maxWords, Bytes<32>>; // canonical ABI words (big-endian)
|
package/src/circuits.compact
CHANGED
|
@@ -12,8 +12,6 @@ import CompactStandardLibrary;
|
|
|
12
12
|
import "./Signet";
|
|
13
13
|
|
|
14
14
|
export {
|
|
15
|
-
signetAttestationDigest,
|
|
16
|
-
verifyRespondBidirectionalEvent,
|
|
17
15
|
signetKeyHash,
|
|
18
16
|
constructSignBidirectionalEventNotificationV1,
|
|
19
17
|
evmAddressAbiWord,
|
|
@@ -22,3 +20,48 @@ export {
|
|
|
22
20
|
abiWordToUint128,
|
|
23
21
|
abiWordToBool
|
|
24
22
|
};
|
|
23
|
+
|
|
24
|
+
// ---- Fixed-width attestation oracles (tests only) --------------------------
|
|
25
|
+
// calculateSignetAttestationDigest and verifyRespondBidirectionalEvent are
|
|
26
|
+
// size-generic, so they cannot appear in the export list above. These
|
|
27
|
+
// fixed-width instantiations exist SOLELY to pin the off-chain TS twin
|
|
28
|
+
// (calculateSignetAttestationDigest in ecdsa-attestation.ts) byte-for-byte
|
|
29
|
+
// against the compiled circuits: 1 is the smallest packed output (a lone
|
|
30
|
+
// bool), 32 one ABI word, 100 a deliberately non-word-aligned width.
|
|
31
|
+
// Off-chain code must use the TS twin; client contracts instantiate the
|
|
32
|
+
// generic circuits at the width their own respond schema implies.
|
|
33
|
+
|
|
34
|
+
export pure circuit calculateSignetAttestationDigest1(
|
|
35
|
+
requestId: RequestId,
|
|
36
|
+
serializedOutput: Bytes<1>
|
|
37
|
+
): Bytes<32> {
|
|
38
|
+
return calculateSignetAttestationDigest<1>(requestId, serializedOutput);
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
export pure circuit calculateSignetAttestationDigest32(
|
|
42
|
+
requestId: RequestId,
|
|
43
|
+
serializedOutput: Bytes<32>
|
|
44
|
+
): Bytes<32> {
|
|
45
|
+
return calculateSignetAttestationDigest<32>(requestId, serializedOutput);
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
export pure circuit calculateSignetAttestationDigest100(
|
|
49
|
+
requestId: RequestId,
|
|
50
|
+
serializedOutput: Bytes<100>
|
|
51
|
+
): Bytes<32> {
|
|
52
|
+
return calculateSignetAttestationDigest<100>(requestId, serializedOutput);
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
export pure circuit verifyRespondBidirectionalEvent32(
|
|
56
|
+
requestId: RequestId,
|
|
57
|
+
serializedOutput: Bytes<32>,
|
|
58
|
+
respondBidirectionalEvent: RespondBidirectionalEvent,
|
|
59
|
+
mpcResponseKey: Secp256k1Point
|
|
60
|
+
): Boolean {
|
|
61
|
+
return verifyRespondBidirectionalEvent<32>(
|
|
62
|
+
requestId,
|
|
63
|
+
serializedOutput,
|
|
64
|
+
respondBidirectionalEvent,
|
|
65
|
+
mpcResponseKey
|
|
66
|
+
);
|
|
67
|
+
}
|