@aztec/prover-client 3.0.0-nightly.20250916 → 3.0.0-nightly.20250918
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/dest/block-factory/light.d.ts +5 -3
- package/dest/block-factory/light.d.ts.map +1 -1
- package/dest/block-factory/light.js +16 -9
- package/dest/mocks/fixtures.d.ts +3 -1
- package/dest/mocks/fixtures.d.ts.map +1 -1
- package/dest/mocks/fixtures.js +19 -2
- package/dest/mocks/test_context.d.ts +30 -9
- package/dest/mocks/test_context.d.ts.map +1 -1
- package/dest/mocks/test_context.js +68 -15
- package/dest/orchestrator/block-building-helpers.d.ts +16 -14
- package/dest/orchestrator/block-building-helpers.d.ts.map +1 -1
- package/dest/orchestrator/block-building-helpers.js +69 -66
- package/dest/orchestrator/block-proving-state.d.ts +53 -46
- package/dest/orchestrator/block-proving-state.d.ts.map +1 -1
- package/dest/orchestrator/block-proving-state.js +209 -172
- package/dest/orchestrator/checkpoint-proving-state.d.ts +62 -0
- package/dest/orchestrator/checkpoint-proving-state.d.ts.map +1 -0
- package/dest/orchestrator/checkpoint-proving-state.js +208 -0
- package/dest/orchestrator/epoch-proving-state.d.ts +32 -25
- package/dest/orchestrator/epoch-proving-state.d.ts.map +1 -1
- package/dest/orchestrator/epoch-proving-state.js +132 -81
- package/dest/orchestrator/orchestrator.d.ts +25 -24
- package/dest/orchestrator/orchestrator.d.ts.map +1 -1
- package/dest/orchestrator/orchestrator.js +318 -190
- package/dest/prover-client/server-epoch-prover.d.ts +8 -7
- package/dest/prover-client/server-epoch-prover.d.ts.map +1 -1
- package/dest/prover-client/server-epoch-prover.js +7 -7
- package/dest/proving_broker/broker_prover_facade.d.ts +12 -7
- package/dest/proving_broker/broker_prover_facade.d.ts.map +1 -1
- package/dest/proving_broker/broker_prover_facade.js +30 -15
- package/dest/proving_broker/proving_broker.d.ts.map +1 -1
- package/dest/proving_broker/proving_broker.js +18 -7
- package/dest/proving_broker/proving_job_controller.d.ts.map +1 -1
- package/dest/proving_broker/proving_job_controller.js +26 -6
- package/dest/test/mock_prover.d.ts +12 -7
- package/dest/test/mock_prover.d.ts.map +1 -1
- package/dest/test/mock_prover.js +25 -10
- package/package.json +15 -15
- package/src/block-factory/light.ts +33 -9
- package/src/mocks/fixtures.ts +25 -7
- package/src/mocks/test_context.ts +113 -21
- package/src/orchestrator/block-building-helpers.ts +107 -93
- package/src/orchestrator/block-proving-state.ts +225 -212
- package/src/orchestrator/checkpoint-proving-state.ts +294 -0
- package/src/orchestrator/epoch-proving-state.ts +169 -121
- package/src/orchestrator/orchestrator.ts +466 -247
- package/src/prover-client/server-epoch-prover.ts +30 -16
- package/src/proving_broker/broker_prover_facade.ts +145 -71
- package/src/proving_broker/proving_broker.ts +24 -6
- package/src/proving_broker/proving_job_controller.ts +26 -6
- package/src/test/mock_prover.ts +105 -28
|
@@ -1,122 +1,123 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import type { SpongeBlob } from '@aztec/blob-lib';
|
|
2
2
|
import {
|
|
3
3
|
type ARCHIVE_HEIGHT,
|
|
4
|
-
BLOBS_PER_BLOCK,
|
|
5
|
-
FIELDS_PER_BLOB,
|
|
6
4
|
type L1_TO_L2_MSG_SUBTREE_SIBLING_PATH_LENGTH,
|
|
5
|
+
NESTED_RECURSIVE_PROOF_LENGTH,
|
|
7
6
|
type NESTED_RECURSIVE_ROLLUP_HONK_PROOF_LENGTH,
|
|
8
7
|
NUM_BASE_PARITY_PER_ROOT_PARITY,
|
|
9
8
|
type RECURSIVE_PROOF_LENGTH,
|
|
10
9
|
} from '@aztec/constants';
|
|
11
|
-
import {
|
|
12
|
-
import { BLS12Point, Fr } from '@aztec/foundation/fields';
|
|
10
|
+
import { Fr } from '@aztec/foundation/fields';
|
|
13
11
|
import type { Tuple } from '@aztec/foundation/serialize';
|
|
14
12
|
import { type TreeNodeLocation, UnbalancedTreeStore } from '@aztec/foundation/trees';
|
|
15
|
-
import { getVKIndex, getVKSiblingPath
|
|
16
|
-
import {
|
|
17
|
-
import type { EthAddress, L2Block } from '@aztec/stdlib/block';
|
|
13
|
+
import { getVKIndex, getVKSiblingPath } from '@aztec/noir-protocol-circuits-types/vk-tree';
|
|
14
|
+
import { getBlockBlobFields } from '@aztec/stdlib/block';
|
|
18
15
|
import type { PublicInputsAndRecursiveProof } from '@aztec/stdlib/interfaces/server';
|
|
19
16
|
import { type ParityPublicInputs, RootParityInput, RootParityInputs } from '@aztec/stdlib/parity';
|
|
20
17
|
import {
|
|
21
18
|
type BaseOrMergeRollupPublicInputs,
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
19
|
+
BlockRollupPublicInputs,
|
|
20
|
+
BlockRootEmptyTxFirstRollupPrivateInputs,
|
|
21
|
+
BlockRootFirstRollupPrivateInputs,
|
|
22
|
+
BlockRootRollupPrivateInputs,
|
|
23
|
+
BlockRootSingleTxFirstRollupPrivateInputs,
|
|
24
|
+
BlockRootSingleTxRollupPrivateInputs,
|
|
25
|
+
CheckpointConstantData,
|
|
29
26
|
MergeRollupInputs,
|
|
30
|
-
PaddingBlockRootRollupInputs,
|
|
31
27
|
PreviousRollupData,
|
|
32
|
-
|
|
28
|
+
type RollupProofData,
|
|
33
29
|
} from '@aztec/stdlib/rollup';
|
|
34
30
|
import type { CircuitName } from '@aztec/stdlib/stats';
|
|
35
|
-
import { AppendOnlyTreeSnapshot
|
|
36
|
-
import { type BlockHeader,
|
|
31
|
+
import { AppendOnlyTreeSnapshot } from '@aztec/stdlib/trees';
|
|
32
|
+
import { type BlockHeader, GlobalVariables } from '@aztec/stdlib/tx';
|
|
33
|
+
import type { UInt64 } from '@aztec/stdlib/types';
|
|
37
34
|
import { VkData } from '@aztec/stdlib/vks';
|
|
38
35
|
|
|
39
|
-
import {
|
|
40
|
-
|
|
41
|
-
buildBlobHints,
|
|
42
|
-
buildHeaderFromCircuitOutputs,
|
|
43
|
-
getEmptyBlockBlobsHash,
|
|
44
|
-
} from './block-building-helpers.js';
|
|
45
|
-
import type { EpochProvingState } from './epoch-proving-state.js';
|
|
36
|
+
import { buildHeaderFromCircuitOutputs, toProofData } from './block-building-helpers.js';
|
|
37
|
+
import type { CheckpointProvingState } from './checkpoint-proving-state.js';
|
|
46
38
|
import type { TxProvingState } from './tx-proving-state.js';
|
|
47
39
|
|
|
48
|
-
export type
|
|
40
|
+
export type ProofState<T, PROOF_LENGTH extends number> = {
|
|
41
|
+
provingOutput?: PublicInputsAndRecursiveProof<T, PROOF_LENGTH>;
|
|
42
|
+
isProving?: boolean;
|
|
43
|
+
};
|
|
49
44
|
|
|
50
45
|
/**
|
|
51
46
|
* The current state of the proving schedule for a given block. Managed by ProvingState.
|
|
52
47
|
* Contains the raw inputs and intermediate state to generate every constituent proof in the tree.
|
|
53
48
|
*/
|
|
54
49
|
export class BlockProvingState {
|
|
55
|
-
private
|
|
56
|
-
|
|
50
|
+
private baseOrMergeProofs: UnbalancedTreeStore<
|
|
51
|
+
ProofState<BaseOrMergeRollupPublicInputs, typeof NESTED_RECURSIVE_ROLLUP_HONK_PROOF_LENGTH>
|
|
57
52
|
> = new UnbalancedTreeStore(0);
|
|
58
|
-
private
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
53
|
+
private baseParityProofs: (ProofState<ParityPublicInputs, typeof NESTED_RECURSIVE_PROOF_LENGTH> | undefined)[] =
|
|
54
|
+
Array.from({
|
|
55
|
+
length: NUM_BASE_PARITY_PER_ROOT_PARITY,
|
|
56
|
+
}).map(_ => undefined);
|
|
57
|
+
private rootParityProof: ProofState<ParityPublicInputs, typeof NESTED_RECURSIVE_PROOF_LENGTH> | undefined;
|
|
58
|
+
private blockRootProof:
|
|
59
|
+
| ProofState<BlockRollupPublicInputs, typeof NESTED_RECURSIVE_ROLLUP_HONK_PROOF_LENGTH>
|
|
62
60
|
| undefined;
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
public spongeBlobState: SpongeBlob | undefined;
|
|
66
|
-
public startBlobAccumulator: BatchedBlobAccumulator | undefined;
|
|
67
|
-
public endBlobAccumulator: BatchedBlobAccumulator | undefined;
|
|
68
|
-
public blobsHash: Fr | undefined;
|
|
69
|
-
public totalNumTxs: number;
|
|
61
|
+
private builtBlockHeader: BlockHeader | undefined;
|
|
62
|
+
private endSpongeBlob: SpongeBlob | undefined;
|
|
70
63
|
private txs: TxProvingState[] = [];
|
|
71
|
-
|
|
64
|
+
private isFirstBlock: boolean;
|
|
65
|
+
private error: string | undefined;
|
|
72
66
|
|
|
73
67
|
constructor(
|
|
74
68
|
public readonly index: number,
|
|
75
|
-
public readonly
|
|
76
|
-
public readonly
|
|
77
|
-
|
|
78
|
-
private readonly
|
|
79
|
-
public readonly
|
|
80
|
-
private readonly lastArchiveSnapshot: AppendOnlyTreeSnapshot,
|
|
69
|
+
public readonly blockNumber: number,
|
|
70
|
+
public readonly totalNumTxs: number,
|
|
71
|
+
private readonly constants: CheckpointConstantData,
|
|
72
|
+
private readonly timestamp: UInt64,
|
|
73
|
+
public readonly lastArchiveTreeSnapshot: AppendOnlyTreeSnapshot,
|
|
81
74
|
private readonly lastArchiveSiblingPath: Tuple<Fr, typeof ARCHIVE_HEIGHT>,
|
|
82
|
-
private readonly
|
|
83
|
-
private readonly
|
|
84
|
-
|
|
85
|
-
private readonly
|
|
75
|
+
private readonly lastL1ToL2MessageTreeSnapshot: AppendOnlyTreeSnapshot,
|
|
76
|
+
private readonly lastL1ToL2MessageSubtreeSiblingPath: Tuple<Fr, typeof L1_TO_L2_MSG_SUBTREE_SIBLING_PATH_LENGTH>,
|
|
77
|
+
public readonly newL1ToL2MessageTreeSnapshot: AppendOnlyTreeSnapshot,
|
|
78
|
+
private readonly headerOfLastBlockInPreviousCheckpoint: BlockHeader,
|
|
79
|
+
private readonly startSpongeBlob: SpongeBlob,
|
|
80
|
+
public parentCheckpoint: CheckpointProvingState,
|
|
86
81
|
) {
|
|
87
|
-
this.
|
|
88
|
-
this.
|
|
89
|
-
|
|
90
|
-
this.startBlobAccumulator = BatchedBlobAccumulator.newWithChallenges(parentEpoch.finalBlobBatchingChallenges);
|
|
82
|
+
this.isFirstBlock = index === 0;
|
|
83
|
+
if (!totalNumTxs && !this.isFirstBlock) {
|
|
84
|
+
throw new Error(`Cannot create a block with 0 txs, unless it's the first block.`);
|
|
91
85
|
}
|
|
92
|
-
}
|
|
93
86
|
|
|
94
|
-
|
|
95
|
-
return this.globalVariables.blockNumber;
|
|
87
|
+
this.baseOrMergeProofs = new UnbalancedTreeStore(totalNumTxs);
|
|
96
88
|
}
|
|
97
89
|
|
|
98
|
-
public
|
|
99
|
-
|
|
100
|
-
throw new Error(`Block ${this.blockNumber} already initalised.`);
|
|
101
|
-
}
|
|
102
|
-
|
|
103
|
-
this.baseOrMergeProvingOutputs = new UnbalancedTreeStore(numTxs);
|
|
104
|
-
// Initialize the sponge which will eventually absorb all tx effects to be added to the blob.
|
|
105
|
-
// Like l1 to l2 messages, we need to know beforehand how many effects will be absorbed.
|
|
106
|
-
this.spongeBlobState = SpongeBlob.init(numBlobFields);
|
|
107
|
-
this.totalNumTxs = numTxs;
|
|
90
|
+
public get epochNumber(): number {
|
|
91
|
+
return this.parentCheckpoint.epochNumber;
|
|
108
92
|
}
|
|
109
93
|
|
|
110
94
|
// Adds a transaction to the proving state, returns it's index
|
|
111
95
|
public addNewTx(tx: TxProvingState) {
|
|
112
|
-
if (!this.
|
|
113
|
-
throw new Error(`
|
|
96
|
+
if (!this.isAcceptingTxs()) {
|
|
97
|
+
throw new Error(`Cannot add more txs to block ${this.blockNumber}.`);
|
|
114
98
|
}
|
|
115
99
|
const txIndex = this.txs.length;
|
|
116
100
|
this.txs[txIndex] = tx;
|
|
117
101
|
return txIndex;
|
|
118
102
|
}
|
|
119
103
|
|
|
104
|
+
public isAcceptingTxs() {
|
|
105
|
+
return this.txs.length < this.totalNumTxs;
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
public getProcessedTxs() {
|
|
109
|
+
return this.txs.map(t => t.processedTx);
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
public tryStartProvingBase(txIndex: number) {
|
|
113
|
+
if (this.baseOrMergeProofs.getLeaf(txIndex)?.isProving) {
|
|
114
|
+
return false;
|
|
115
|
+
} else {
|
|
116
|
+
this.baseOrMergeProofs.setLeaf(txIndex, { isProving: true });
|
|
117
|
+
return true;
|
|
118
|
+
}
|
|
119
|
+
}
|
|
120
|
+
|
|
120
121
|
public setBaseRollupProof(
|
|
121
122
|
txIndex: number,
|
|
122
123
|
provingOutput: PublicInputsAndRecursiveProof<
|
|
@@ -124,7 +125,16 @@ export class BlockProvingState {
|
|
|
124
125
|
typeof NESTED_RECURSIVE_ROLLUP_HONK_PROOF_LENGTH
|
|
125
126
|
>,
|
|
126
127
|
): TreeNodeLocation {
|
|
127
|
-
return this.
|
|
128
|
+
return this.baseOrMergeProofs.setLeaf(txIndex, { provingOutput });
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
public tryStartProvingMerge(location: TreeNodeLocation) {
|
|
132
|
+
if (this.baseOrMergeProofs.getNode(location)?.isProving) {
|
|
133
|
+
return false;
|
|
134
|
+
} else {
|
|
135
|
+
this.baseOrMergeProofs.setNode(location, { isProving: true });
|
|
136
|
+
return true;
|
|
137
|
+
}
|
|
128
138
|
}
|
|
129
139
|
|
|
130
140
|
public setMergeRollupProof(
|
|
@@ -134,7 +144,16 @@ export class BlockProvingState {
|
|
|
134
144
|
typeof NESTED_RECURSIVE_ROLLUP_HONK_PROOF_LENGTH
|
|
135
145
|
>,
|
|
136
146
|
) {
|
|
137
|
-
this.
|
|
147
|
+
this.baseOrMergeProofs.setNode(location, { provingOutput });
|
|
148
|
+
}
|
|
149
|
+
|
|
150
|
+
public tryStartProvingBaseParity(index: number) {
|
|
151
|
+
if (this.baseParityProofs[index]?.isProving) {
|
|
152
|
+
return false;
|
|
153
|
+
} else {
|
|
154
|
+
this.baseParityProofs[index] = { isProving: true };
|
|
155
|
+
return true;
|
|
156
|
+
}
|
|
138
157
|
}
|
|
139
158
|
|
|
140
159
|
// Stores a set of root parity inputs at the given index
|
|
@@ -144,141 +163,178 @@ export class BlockProvingState {
|
|
|
144
163
|
`Unable to set a base parity proofs at index ${index}. Expected at most ${NUM_BASE_PARITY_PER_ROOT_PARITY} proofs.`,
|
|
145
164
|
);
|
|
146
165
|
}
|
|
147
|
-
this.
|
|
166
|
+
this.baseParityProofs[index] = { provingOutput };
|
|
167
|
+
}
|
|
168
|
+
|
|
169
|
+
public tryStartProvingRootParity() {
|
|
170
|
+
if (this.rootParityProof?.isProving) {
|
|
171
|
+
return false;
|
|
172
|
+
} else {
|
|
173
|
+
this.rootParityProof = { isProving: true };
|
|
174
|
+
return true;
|
|
175
|
+
}
|
|
148
176
|
}
|
|
149
177
|
|
|
150
178
|
public setRootParityProof(provingOutput: PublicInputsAndRecursiveProof<ParityPublicInputs>) {
|
|
151
|
-
this.
|
|
179
|
+
this.rootParityProof = { provingOutput };
|
|
180
|
+
}
|
|
181
|
+
|
|
182
|
+
public tryStartProvingBlockRoot() {
|
|
183
|
+
if (this.blockRootProof?.isProving) {
|
|
184
|
+
return false;
|
|
185
|
+
} else {
|
|
186
|
+
this.blockRootProof = { isProving: true };
|
|
187
|
+
return true;
|
|
188
|
+
}
|
|
152
189
|
}
|
|
153
190
|
|
|
154
191
|
public setBlockRootRollupProof(
|
|
155
192
|
provingOutput: PublicInputsAndRecursiveProof<
|
|
156
|
-
|
|
193
|
+
BlockRollupPublicInputs,
|
|
157
194
|
typeof NESTED_RECURSIVE_ROLLUP_HONK_PROOF_LENGTH
|
|
158
195
|
>,
|
|
159
|
-
) {
|
|
160
|
-
this.
|
|
196
|
+
): TreeNodeLocation {
|
|
197
|
+
this.blockRootProof = { provingOutput };
|
|
198
|
+
return this.parentCheckpoint.setBlockRootRollupProof(this.index, provingOutput);
|
|
161
199
|
}
|
|
162
200
|
|
|
163
|
-
public
|
|
164
|
-
this.
|
|
201
|
+
public getBlockRootRollupOutput() {
|
|
202
|
+
return this.blockRootProof?.provingOutput?.inputs;
|
|
165
203
|
}
|
|
166
204
|
|
|
167
|
-
public
|
|
168
|
-
this.
|
|
205
|
+
public setBuiltBlockHeader(blockHeader: BlockHeader) {
|
|
206
|
+
this.builtBlockHeader = blockHeader;
|
|
169
207
|
}
|
|
170
208
|
|
|
171
|
-
public
|
|
172
|
-
this.
|
|
209
|
+
public getBuiltBlockHeader() {
|
|
210
|
+
return this.builtBlockHeader;
|
|
173
211
|
}
|
|
174
212
|
|
|
175
|
-
public
|
|
176
|
-
if (
|
|
177
|
-
|
|
178
|
-
return;
|
|
213
|
+
public getGlobalVariables() {
|
|
214
|
+
if (this.txs.length) {
|
|
215
|
+
return this.txs[0].processedTx.globalVariables;
|
|
179
216
|
}
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
217
|
+
|
|
218
|
+
const constants = this.constants;
|
|
219
|
+
return GlobalVariables.from({
|
|
220
|
+
chainId: constants.chainId,
|
|
221
|
+
version: constants.version,
|
|
222
|
+
blockNumber: this.blockNumber,
|
|
223
|
+
slotNumber: constants.slotNumber,
|
|
224
|
+
timestamp: this.timestamp,
|
|
225
|
+
coinbase: constants.coinbase,
|
|
226
|
+
feeRecipient: constants.feeRecipient,
|
|
227
|
+
gasFees: constants.gasFees,
|
|
228
|
+
});
|
|
185
229
|
}
|
|
186
230
|
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
return this.txs;
|
|
231
|
+
public getStartSpongeBlob() {
|
|
232
|
+
return this.startSpongeBlob;
|
|
190
233
|
}
|
|
191
234
|
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
235
|
+
public setEndSpongeBlob(endSpongeBlob: SpongeBlob) {
|
|
236
|
+
this.endSpongeBlob = endSpongeBlob;
|
|
237
|
+
}
|
|
238
|
+
|
|
239
|
+
public getEndSpongeBlob() {
|
|
240
|
+
return this.endSpongeBlob;
|
|
241
|
+
}
|
|
242
|
+
|
|
243
|
+
public getBlockBlobFields() {
|
|
244
|
+
return getBlockBlobFields(this.txs.map(t => t.processedTx.txEffect));
|
|
195
245
|
}
|
|
196
246
|
|
|
197
247
|
public getParentLocation(location: TreeNodeLocation) {
|
|
198
|
-
return this.
|
|
248
|
+
return this.baseOrMergeProofs.getParentLocation(location);
|
|
199
249
|
}
|
|
200
250
|
|
|
201
251
|
public getMergeRollupInputs(mergeLocation: TreeNodeLocation) {
|
|
202
|
-
const [left, right] = this.
|
|
252
|
+
const [left, right] = this.baseOrMergeProofs.getChildren(mergeLocation).map(c => c?.provingOutput);
|
|
203
253
|
if (!left || !right) {
|
|
204
|
-
throw new Error('At
|
|
254
|
+
throw new Error('At least one child is not ready for the merge rollup.');
|
|
205
255
|
}
|
|
206
256
|
|
|
207
257
|
return new MergeRollupInputs([this.#getPreviousRollupData(left), this.#getPreviousRollupData(right)]);
|
|
208
258
|
}
|
|
209
259
|
|
|
210
|
-
public
|
|
211
|
-
|
|
212
|
-
|
|
260
|
+
public getBlockRootRollupTypeAndInputs() {
|
|
261
|
+
const provingOutputs = this.#getChildProvingOutputsForBlockRoot();
|
|
262
|
+
if (!provingOutputs.every(p => !!p)) {
|
|
263
|
+
throw new Error('At least one child is not ready for the block root rollup.');
|
|
213
264
|
}
|
|
214
265
|
|
|
215
|
-
const
|
|
216
|
-
const nonEmptyProofs = proofs.filter(p => !!p);
|
|
217
|
-
if (proofs.length !== nonEmptyProofs.length) {
|
|
218
|
-
throw new Error('At lease one child is not ready for the block root.');
|
|
219
|
-
}
|
|
266
|
+
const previousRollups = provingOutputs.map(p => toProofData(p));
|
|
220
267
|
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
const constants = BlockConstantData.from({
|
|
225
|
-
lastArchive: this.lastArchiveSnapshot,
|
|
226
|
-
newL1ToL2: this.l1ToL2MessageTreeSnapshotAfterInsertion,
|
|
227
|
-
globalVariables: this.globalVariables,
|
|
228
|
-
vkTreeRoot: getVKTreeRoot(),
|
|
229
|
-
protocolContractTreeRoot,
|
|
230
|
-
});
|
|
231
|
-
|
|
232
|
-
this.blobsHash = await getEmptyBlockBlobsHash();
|
|
268
|
+
if (this.isFirstBlock) {
|
|
269
|
+
return this.#getFirstBlockRootRollupTypeAndInputs(previousRollups);
|
|
270
|
+
}
|
|
233
271
|
|
|
272
|
+
const [leftRollup, rightRollup] = previousRollups;
|
|
273
|
+
if (!rightRollup) {
|
|
234
274
|
return {
|
|
235
|
-
rollupType: '
|
|
236
|
-
inputs:
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
275
|
+
rollupType: 'block-root-single-tx-rollup' satisfies CircuitName,
|
|
276
|
+
inputs: new BlockRootSingleTxRollupPrivateInputs(leftRollup, this.lastArchiveSiblingPath),
|
|
277
|
+
};
|
|
278
|
+
} else {
|
|
279
|
+
return {
|
|
280
|
+
rollupType: 'block-root-rollup' satisfies CircuitName,
|
|
281
|
+
inputs: new BlockRootRollupPrivateInputs([leftRollup, rightRollup], this.lastArchiveSiblingPath),
|
|
240
282
|
};
|
|
241
283
|
}
|
|
284
|
+
}
|
|
242
285
|
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
286
|
+
#getFirstBlockRootRollupTypeAndInputs([leftRollup, rightRollup]: RollupProofData<BaseOrMergeRollupPublicInputs>[]) {
|
|
287
|
+
if (!this.rootParityProof?.provingOutput) {
|
|
288
|
+
throw new Error('Root parity is not ready.');
|
|
289
|
+
}
|
|
290
|
+
const l1ToL2Roots = toProofData(this.rootParityProof.provingOutput);
|
|
246
291
|
|
|
247
|
-
if (
|
|
292
|
+
if (!leftRollup) {
|
|
248
293
|
return {
|
|
249
|
-
rollupType: '
|
|
250
|
-
inputs: new
|
|
294
|
+
rollupType: 'block-root-empty-tx-first-rollup' satisfies CircuitName,
|
|
295
|
+
inputs: new BlockRootEmptyTxFirstRollupPrivateInputs(
|
|
296
|
+
l1ToL2Roots,
|
|
297
|
+
this.lastArchiveTreeSnapshot,
|
|
298
|
+
this.headerOfLastBlockInPreviousCheckpoint.state,
|
|
299
|
+
this.constants,
|
|
300
|
+
this.startSpongeBlob,
|
|
301
|
+
this.timestamp,
|
|
302
|
+
this.lastL1ToL2MessageSubtreeSiblingPath,
|
|
303
|
+
this.lastArchiveSiblingPath,
|
|
304
|
+
),
|
|
305
|
+
};
|
|
306
|
+
} else if (!rightRollup) {
|
|
307
|
+
return {
|
|
308
|
+
rollupType: 'block-root-single-tx-first-rollup' satisfies CircuitName,
|
|
309
|
+
inputs: new BlockRootSingleTxFirstRollupPrivateInputs(
|
|
310
|
+
l1ToL2Roots,
|
|
311
|
+
leftRollup,
|
|
312
|
+
this.lastL1ToL2MessageTreeSnapshot,
|
|
313
|
+
this.lastL1ToL2MessageSubtreeSiblingPath,
|
|
314
|
+
this.lastArchiveSiblingPath,
|
|
315
|
+
),
|
|
251
316
|
};
|
|
252
317
|
} else {
|
|
253
318
|
return {
|
|
254
|
-
rollupType: 'block-root-rollup' satisfies CircuitName,
|
|
255
|
-
inputs: new
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
319
|
+
rollupType: 'block-root-first-rollup' satisfies CircuitName,
|
|
320
|
+
inputs: new BlockRootFirstRollupPrivateInputs(
|
|
321
|
+
l1ToL2Roots,
|
|
322
|
+
[leftRollup, rightRollup],
|
|
323
|
+
this.lastL1ToL2MessageTreeSnapshot,
|
|
324
|
+
this.lastL1ToL2MessageSubtreeSiblingPath,
|
|
325
|
+
this.lastArchiveSiblingPath,
|
|
259
326
|
),
|
|
260
327
|
};
|
|
261
328
|
}
|
|
262
329
|
}
|
|
263
330
|
|
|
264
|
-
public getPaddingBlockRootInputs() {
|
|
265
|
-
const constants = EpochConstantData.from({
|
|
266
|
-
vkTreeRoot: getVKTreeRoot(),
|
|
267
|
-
protocolContractTreeRoot,
|
|
268
|
-
proverId: this.proverId.toField(),
|
|
269
|
-
});
|
|
270
|
-
|
|
271
|
-
return PaddingBlockRootRollupInputs.from({
|
|
272
|
-
constants,
|
|
273
|
-
});
|
|
274
|
-
}
|
|
275
|
-
|
|
276
331
|
public getRootParityInputs() {
|
|
277
|
-
|
|
332
|
+
const baseParityProvingOutputs = this.baseParityProofs.filter(p => !!p?.provingOutput).map(p => p!.provingOutput!);
|
|
333
|
+
if (baseParityProvingOutputs.length !== this.baseParityProofs.length) {
|
|
278
334
|
throw new Error('At lease one base parity is not ready.');
|
|
279
335
|
}
|
|
280
336
|
|
|
281
|
-
const children =
|
|
337
|
+
const children = baseParityProvingOutputs.map(p => this.#getRootParityData(p));
|
|
282
338
|
return new RootParityInputs(
|
|
283
339
|
children as Tuple<RootParityInput<typeof RECURSIVE_PROOF_LENGTH>, typeof NUM_BASE_PARITY_PER_ROOT_PARITY>,
|
|
284
340
|
);
|
|
@@ -290,89 +346,46 @@ export class BlockProvingState {
|
|
|
290
346
|
}
|
|
291
347
|
|
|
292
348
|
public async buildHeaderFromProvingOutputs() {
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
? []
|
|
296
|
-
: await Promise.all(this.#getChildProofsForBlockRoot().map(p => this.#getPreviousRollupData(p!)));
|
|
297
|
-
|
|
298
|
-
let endPartialState = this.previousBlockHeader.state.partial;
|
|
299
|
-
if (this.totalNumTxs !== 0) {
|
|
300
|
-
const previousRollupData = this.#getChildProofsForBlockRoot();
|
|
301
|
-
const lastRollup = previousRollupData[previousRollupData.length - 1];
|
|
302
|
-
if (!lastRollup) {
|
|
303
|
-
throw new Error('End state of the block is not available. Last rollup is not ready yet.');
|
|
304
|
-
}
|
|
305
|
-
endPartialState = lastRollup.inputs.end;
|
|
349
|
+
if (!this.blockRootProof?.provingOutput) {
|
|
350
|
+
throw new Error('Block root rollup is not ready.');
|
|
306
351
|
}
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
return buildHeaderFromCircuitOutputs(
|
|
310
|
-
previousRollupData.map(d => d.baseOrMergeRollupPublicInputs),
|
|
311
|
-
this.rootParityProvingOutput!.inputs,
|
|
312
|
-
this.blockRootProvingOutput!.inputs,
|
|
313
|
-
this.blobsHash!,
|
|
314
|
-
endState,
|
|
315
|
-
);
|
|
352
|
+
|
|
353
|
+
return await buildHeaderFromCircuitOutputs(this.blockRootProof.provingOutput.inputs);
|
|
316
354
|
}
|
|
317
355
|
|
|
318
356
|
public isReadyForMergeRollup(location: TreeNodeLocation) {
|
|
319
|
-
return this.
|
|
357
|
+
return !!this.baseOrMergeProofs.getSibling(location)?.provingOutput;
|
|
320
358
|
}
|
|
321
359
|
|
|
322
360
|
// Returns true if we have sufficient inputs to execute the block root rollup
|
|
323
361
|
public isReadyForBlockRootRollup() {
|
|
324
|
-
const childProofs = this.#
|
|
325
|
-
return (
|
|
326
|
-
this.block !== undefined &&
|
|
327
|
-
this.rootParityProvingOutput !== undefined &&
|
|
328
|
-
this.endBlobAccumulator !== undefined &&
|
|
329
|
-
childProofs.every(p => !!p)
|
|
330
|
-
);
|
|
362
|
+
const childProofs = this.#getChildProvingOutputsForBlockRoot();
|
|
363
|
+
return (!this.isFirstBlock || !!this.rootParityProof?.provingOutput) && childProofs.every(p => !!p);
|
|
331
364
|
}
|
|
332
365
|
|
|
333
366
|
// Returns true if we have sufficient root parity inputs to execute the root parity circuit
|
|
334
367
|
public isReadyForRootParity() {
|
|
335
|
-
return this.
|
|
368
|
+
return this.baseParityProofs.every(p => !!p?.provingOutput);
|
|
336
369
|
}
|
|
337
370
|
|
|
338
371
|
public isComplete() {
|
|
339
|
-
return !!this.
|
|
372
|
+
return !!this.blockRootProof;
|
|
340
373
|
}
|
|
341
374
|
|
|
342
|
-
// Returns whether the proving state is still valid
|
|
343
375
|
public verifyState() {
|
|
344
|
-
return this.
|
|
376
|
+
return this.parentCheckpoint.verifyState();
|
|
345
377
|
}
|
|
346
378
|
|
|
347
|
-
public
|
|
348
|
-
this.error
|
|
349
|
-
this.parentEpoch.reject(reason);
|
|
350
|
-
}
|
|
351
|
-
|
|
352
|
-
#getBlockRootRollupData() {
|
|
353
|
-
return BlockRootRollupData.from({
|
|
354
|
-
l1ToL2Roots: this.#getRootParityData(this.rootParityProvingOutput!),
|
|
355
|
-
l1ToL2MessageSubtreeSiblingPath: this.l1ToL2MessageSubtreeSiblingPath,
|
|
356
|
-
previousArchiveSiblingPath: this.lastArchiveSiblingPath,
|
|
357
|
-
newArchiveSiblingPath: this.newArchiveSiblingPath,
|
|
358
|
-
previousBlockHeader: this.previousBlockHeader,
|
|
359
|
-
startBlobAccumulator: BlobAccumulatorPublicInputs.fromBatchedBlobAccumulator(this.startBlobAccumulator!),
|
|
360
|
-
finalBlobChallenges: this.startBlobAccumulator!.finalBlobChallenges,
|
|
361
|
-
proverId: this.proverId.toField(),
|
|
362
|
-
});
|
|
379
|
+
public getError() {
|
|
380
|
+
return this.error;
|
|
363
381
|
}
|
|
364
382
|
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
return BlockRootRollupBlobData.from({
|
|
369
|
-
blobFields: padArrayEnd(blobFields, Fr.ZERO, FIELDS_PER_BLOB * BLOBS_PER_BLOCK),
|
|
370
|
-
blobCommitments: padArrayEnd(blobCommitments, BLS12Point.ZERO, BLOBS_PER_BLOCK),
|
|
371
|
-
blobsHash,
|
|
372
|
-
});
|
|
383
|
+
public reject(reason: string) {
|
|
384
|
+
this.error = reason;
|
|
385
|
+
this.parentCheckpoint.reject(reason);
|
|
373
386
|
}
|
|
374
387
|
|
|
375
|
-
#
|
|
388
|
+
#getChildProvingOutputsForBlockRoot() {
|
|
376
389
|
if (this.totalNumTxs === 0) {
|
|
377
390
|
return [];
|
|
378
391
|
}
|
|
@@ -380,8 +393,8 @@ export class BlockProvingState {
|
|
|
380
393
|
const rootLocation = { level: 0, index: 0 };
|
|
381
394
|
// If there's only 1 tx, its base rollup proof will be stored at the root.
|
|
382
395
|
return this.totalNumTxs === 1
|
|
383
|
-
? [this.
|
|
384
|
-
: this.
|
|
396
|
+
? [this.baseOrMergeProofs.getNode(rootLocation)?.provingOutput]
|
|
397
|
+
: this.baseOrMergeProofs.getChildren(rootLocation).map(c => c?.provingOutput);
|
|
385
398
|
}
|
|
386
399
|
|
|
387
400
|
#getPreviousRollupData({
|