@aztec/pxe 0.0.1-commit.21ecf947b → 0.0.1-commit.2448fdb

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.
Files changed (224) hide show
  1. package/dest/bin/check_oracle_version.js +4 -4
  2. package/dest/block_synchronizer/block_synchronizer.d.ts +3 -1
  3. package/dest/block_synchronizer/block_synchronizer.d.ts.map +1 -1
  4. package/dest/block_synchronizer/block_synchronizer.js +10 -0
  5. package/dest/config/package_info.js +1 -1
  6. package/dest/contract_function_simulator/contract_function_simulator.d.ts +13 -5
  7. package/dest/contract_function_simulator/contract_function_simulator.d.ts.map +1 -1
  8. package/dest/contract_function_simulator/contract_function_simulator.js +41 -14
  9. package/dest/contract_function_simulator/ephemeral_array_service.d.ts +28 -0
  10. package/dest/contract_function_simulator/ephemeral_array_service.d.ts.map +1 -0
  11. package/dest/contract_function_simulator/ephemeral_array_service.js +78 -0
  12. package/dest/contract_function_simulator/execution_tagging_index_cache.d.ts +7 -7
  13. package/dest/contract_function_simulator/execution_tagging_index_cache.d.ts.map +1 -1
  14. package/dest/contract_function_simulator/execution_tagging_index_cache.js +19 -11
  15. package/dest/contract_function_simulator/index.d.ts +2 -1
  16. package/dest/contract_function_simulator/index.d.ts.map +1 -1
  17. package/dest/contract_function_simulator/index.js +1 -0
  18. package/dest/contract_function_simulator/noir-structs/event_validation_request.d.ts +4 -6
  19. package/dest/contract_function_simulator/noir-structs/event_validation_request.d.ts.map +1 -1
  20. package/dest/contract_function_simulator/noir-structs/event_validation_request.js +8 -10
  21. package/dest/contract_function_simulator/noir-structs/log_retrieval_request.d.ts +1 -1
  22. package/dest/contract_function_simulator/noir-structs/log_retrieval_request.js +1 -1
  23. package/dest/contract_function_simulator/noir-structs/log_retrieval_response.d.ts +2 -2
  24. package/dest/contract_function_simulator/noir-structs/log_retrieval_response.d.ts.map +1 -1
  25. package/dest/contract_function_simulator/noir-structs/log_retrieval_response.js +2 -4
  26. package/dest/contract_function_simulator/noir-structs/note_validation_request.d.ts +4 -7
  27. package/dest/contract_function_simulator/noir-structs/note_validation_request.d.ts.map +1 -1
  28. package/dest/contract_function_simulator/noir-structs/note_validation_request.js +6 -11
  29. package/dest/contract_function_simulator/oracle/interfaces.d.ts +61 -45
  30. package/dest/contract_function_simulator/oracle/interfaces.d.ts.map +1 -1
  31. package/dest/contract_function_simulator/oracle/legacy_oracle_mappings.d.ts +9 -0
  32. package/dest/contract_function_simulator/oracle/legacy_oracle_mappings.d.ts.map +1 -0
  33. package/dest/contract_function_simulator/oracle/legacy_oracle_mappings.js +47 -0
  34. package/dest/contract_function_simulator/oracle/oracle.d.ts +75 -44
  35. package/dest/contract_function_simulator/oracle/oracle.d.ts.map +1 -1
  36. package/dest/contract_function_simulator/oracle/oracle.js +281 -96
  37. package/dest/contract_function_simulator/oracle/private_execution.js +5 -3
  38. package/dest/contract_function_simulator/oracle/private_execution_oracle.d.ts +24 -50
  39. package/dest/contract_function_simulator/oracle/private_execution_oracle.d.ts.map +1 -1
  40. package/dest/contract_function_simulator/oracle/private_execution_oracle.js +55 -85
  41. package/dest/contract_function_simulator/oracle/utility_execution_oracle.d.ts +94 -60
  42. package/dest/contract_function_simulator/oracle/utility_execution_oracle.d.ts.map +1 -1
  43. package/dest/contract_function_simulator/oracle/utility_execution_oracle.js +277 -114
  44. package/dest/contract_function_simulator/pick_notes.d.ts +1 -1
  45. package/dest/contract_function_simulator/pick_notes.d.ts.map +1 -1
  46. package/dest/contract_function_simulator/pick_notes.js +20 -3
  47. package/dest/contract_function_simulator/proxied_contract_data_source.d.ts +1 -1
  48. package/dest/contract_function_simulator/proxied_contract_data_source.d.ts.map +1 -1
  49. package/dest/contract_function_simulator/proxied_contract_data_source.js +3 -0
  50. package/dest/contract_logging.d.ts +27 -0
  51. package/dest/contract_logging.d.ts.map +1 -0
  52. package/dest/contract_logging.js +38 -0
  53. package/dest/contract_sync/contract_sync_service.d.ts +6 -5
  54. package/dest/contract_sync/contract_sync_service.d.ts.map +1 -1
  55. package/dest/contract_sync/contract_sync_service.js +62 -43
  56. package/dest/contract_sync/helpers.d.ts +2 -3
  57. package/dest/contract_sync/helpers.d.ts.map +1 -1
  58. package/dest/contract_sync/helpers.js +7 -2
  59. package/dest/debug/pxe_debug_utils.d.ts +3 -3
  60. package/dest/debug/pxe_debug_utils.d.ts.map +1 -1
  61. package/dest/debug/pxe_debug_utils.js +4 -4
  62. package/dest/entrypoints/client/bundle/index.d.ts +2 -2
  63. package/dest/entrypoints/client/bundle/index.d.ts.map +1 -1
  64. package/dest/entrypoints/client/bundle/index.js +1 -1
  65. package/dest/entrypoints/client/bundle/utils.d.ts +2 -2
  66. package/dest/entrypoints/client/bundle/utils.d.ts.map +1 -1
  67. package/dest/entrypoints/client/bundle/utils.js +2 -2
  68. package/dest/entrypoints/client/lazy/index.d.ts +2 -2
  69. package/dest/entrypoints/client/lazy/index.d.ts.map +1 -1
  70. package/dest/entrypoints/client/lazy/index.js +1 -1
  71. package/dest/entrypoints/client/lazy/utils.d.ts +2 -2
  72. package/dest/entrypoints/client/lazy/utils.d.ts.map +1 -1
  73. package/dest/entrypoints/client/lazy/utils.js +2 -2
  74. package/dest/entrypoints/pxe_creation_options.d.ts +3 -1
  75. package/dest/entrypoints/pxe_creation_options.d.ts.map +1 -1
  76. package/dest/entrypoints/pxe_creation_options.js +3 -1
  77. package/dest/entrypoints/server/index.d.ts +2 -3
  78. package/dest/entrypoints/server/index.d.ts.map +1 -1
  79. package/dest/entrypoints/server/index.js +1 -2
  80. package/dest/entrypoints/server/utils.d.ts +2 -2
  81. package/dest/entrypoints/server/utils.d.ts.map +1 -1
  82. package/dest/entrypoints/server/utils.js +2 -2
  83. package/dest/events/event_service.d.ts +3 -2
  84. package/dest/events/event_service.d.ts.map +1 -1
  85. package/dest/events/event_service.js +16 -4
  86. package/dest/events/private_event_filter_validator.d.ts +3 -2
  87. package/dest/events/private_event_filter_validator.d.ts.map +1 -1
  88. package/dest/events/private_event_filter_validator.js +15 -0
  89. package/dest/logs/log_service.d.ts +7 -8
  90. package/dest/logs/log_service.d.ts.map +1 -1
  91. package/dest/logs/log_service.js +29 -39
  92. package/dest/messages/message_context_service.d.ts +17 -0
  93. package/dest/messages/message_context_service.d.ts.map +1 -0
  94. package/dest/messages/message_context_service.js +36 -0
  95. package/dest/notes/note_service.d.ts +4 -5
  96. package/dest/notes/note_service.d.ts.map +1 -1
  97. package/dest/notes/note_service.js +14 -5
  98. package/dest/notes_filter.d.ts +2 -3
  99. package/dest/notes_filter.d.ts.map +1 -1
  100. package/dest/oracle_version.d.ts +4 -3
  101. package/dest/oracle_version.d.ts.map +1 -1
  102. package/dest/oracle_version.js +20 -10
  103. package/dest/private_kernel/hints/private_kernel_reset_private_inputs_builder.d.ts +4 -3
  104. package/dest/private_kernel/hints/private_kernel_reset_private_inputs_builder.d.ts.map +1 -1
  105. package/dest/private_kernel/hints/private_kernel_reset_private_inputs_builder.js +125 -64
  106. package/dest/private_kernel/hints/test_utils.d.ts +122 -0
  107. package/dest/private_kernel/hints/test_utils.d.ts.map +1 -0
  108. package/dest/private_kernel/hints/test_utils.js +203 -0
  109. package/dest/private_kernel/private_kernel_execution_prover.d.ts +1 -1
  110. package/dest/private_kernel/private_kernel_execution_prover.d.ts.map +1 -1
  111. package/dest/private_kernel/private_kernel_execution_prover.js +17 -12
  112. package/dest/private_kernel/private_kernel_oracle.d.ts +10 -6
  113. package/dest/private_kernel/private_kernel_oracle.d.ts.map +1 -1
  114. package/dest/private_kernel/private_kernel_oracle.js +19 -18
  115. package/dest/pxe.d.ts +15 -12
  116. package/dest/pxe.d.ts.map +1 -1
  117. package/dest/pxe.js +76 -49
  118. package/dest/storage/anchor_block_store/anchor_block_store.js +1 -1
  119. package/dest/storage/capsule_store/capsule_service.d.ts +21 -0
  120. package/dest/storage/capsule_store/capsule_service.d.ts.map +1 -0
  121. package/dest/storage/capsule_store/capsule_service.js +50 -0
  122. package/dest/storage/capsule_store/capsule_store.d.ts +9 -9
  123. package/dest/storage/capsule_store/capsule_store.d.ts.map +1 -1
  124. package/dest/storage/capsule_store/capsule_store.js +36 -28
  125. package/dest/storage/capsule_store/index.d.ts +2 -1
  126. package/dest/storage/capsule_store/index.d.ts.map +1 -1
  127. package/dest/storage/capsule_store/index.js +1 -0
  128. package/dest/storage/contract_store/contract_store.d.ts +42 -15
  129. package/dest/storage/contract_store/contract_store.d.ts.map +1 -1
  130. package/dest/storage/contract_store/contract_store.js +143 -65
  131. package/dest/storage/metadata.d.ts +1 -1
  132. package/dest/storage/metadata.js +1 -1
  133. package/dest/storage/note_store/note_store.d.ts +1 -1
  134. package/dest/storage/note_store/note_store.d.ts.map +1 -1
  135. package/dest/storage/note_store/note_store.js +2 -2
  136. package/dest/storage/private_event_store/private_event_store.d.ts +1 -1
  137. package/dest/storage/private_event_store/private_event_store.d.ts.map +1 -1
  138. package/dest/storage/private_event_store/private_event_store.js +3 -0
  139. package/dest/storage/tagging_store/recipient_tagging_store.d.ts +6 -6
  140. package/dest/storage/tagging_store/recipient_tagging_store.d.ts.map +1 -1
  141. package/dest/storage/tagging_store/sender_tagging_store.d.ts +29 -28
  142. package/dest/storage/tagging_store/sender_tagging_store.d.ts.map +1 -1
  143. package/dest/storage/tagging_store/sender_tagging_store.js +141 -115
  144. package/dest/tagging/index.d.ts +3 -3
  145. package/dest/tagging/index.d.ts.map +1 -1
  146. package/dest/tagging/index.js +1 -1
  147. package/dest/tagging/recipient_sync/load_private_logs_for_sender_recipient_pair.d.ts +4 -5
  148. package/dest/tagging/recipient_sync/load_private_logs_for_sender_recipient_pair.d.ts.map +1 -1
  149. package/dest/tagging/recipient_sync/load_private_logs_for_sender_recipient_pair.js +4 -18
  150. package/dest/tagging/recipient_sync/utils/load_logs_for_range.d.ts +6 -7
  151. package/dest/tagging/recipient_sync/utils/load_logs_for_range.d.ts.map +1 -1
  152. package/dest/tagging/recipient_sync/utils/load_logs_for_range.js +12 -11
  153. package/dest/tagging/sender_sync/sync_sender_tagging_indexes.d.ts +4 -8
  154. package/dest/tagging/sender_sync/sync_sender_tagging_indexes.d.ts.map +1 -1
  155. package/dest/tagging/sender_sync/sync_sender_tagging_indexes.js +13 -7
  156. package/dest/tagging/sender_sync/utils/get_status_change_of_pending.d.ts +4 -3
  157. package/dest/tagging/sender_sync/utils/get_status_change_of_pending.d.ts.map +1 -1
  158. package/dest/tagging/sender_sync/utils/get_status_change_of_pending.js +20 -10
  159. package/dest/tagging/sender_sync/utils/load_and_store_new_tagging_indexes.d.ts +5 -7
  160. package/dest/tagging/sender_sync/utils/load_and_store_new_tagging_indexes.d.ts.map +1 -1
  161. package/dest/tagging/sender_sync/utils/load_and_store_new_tagging_indexes.js +36 -24
  162. package/package.json +16 -16
  163. package/src/bin/check_oracle_version.ts +4 -4
  164. package/src/block_synchronizer/block_synchronizer.ts +12 -0
  165. package/src/config/package_info.ts +1 -1
  166. package/src/contract_function_simulator/contract_function_simulator.ts +63 -28
  167. package/src/contract_function_simulator/ephemeral_array_service.ts +110 -0
  168. package/src/contract_function_simulator/execution_tagging_index_cache.ts +19 -14
  169. package/src/contract_function_simulator/index.ts +1 -0
  170. package/src/contract_function_simulator/noir-structs/event_validation_request.ts +9 -9
  171. package/src/contract_function_simulator/noir-structs/log_retrieval_request.ts +1 -1
  172. package/src/contract_function_simulator/noir-structs/log_retrieval_response.ts +2 -5
  173. package/src/contract_function_simulator/noir-structs/note_validation_request.ts +4 -10
  174. package/src/contract_function_simulator/oracle/interfaces.ts +82 -54
  175. package/src/contract_function_simulator/oracle/legacy_oracle_mappings.ts +104 -0
  176. package/src/contract_function_simulator/oracle/oracle.ts +363 -139
  177. package/src/contract_function_simulator/oracle/private_execution.ts +4 -4
  178. package/src/contract_function_simulator/oracle/private_execution_oracle.ts +67 -106
  179. package/src/contract_function_simulator/oracle/utility_execution_oracle.ts +457 -152
  180. package/src/contract_function_simulator/pick_notes.ts +22 -3
  181. package/src/contract_function_simulator/proxied_contract_data_source.ts +8 -1
  182. package/src/contract_logging.ts +52 -0
  183. package/src/contract_sync/contract_sync_service.ts +99 -75
  184. package/src/contract_sync/helpers.ts +4 -4
  185. package/src/debug/pxe_debug_utils.ts +7 -7
  186. package/src/entrypoints/client/bundle/index.ts +1 -1
  187. package/src/entrypoints/client/bundle/utils.ts +2 -3
  188. package/src/entrypoints/client/lazy/index.ts +1 -1
  189. package/src/entrypoints/client/lazy/utils.ts +2 -3
  190. package/src/entrypoints/pxe_creation_options.ts +7 -0
  191. package/src/entrypoints/server/index.ts +1 -2
  192. package/src/entrypoints/server/utils.ts +2 -3
  193. package/src/events/event_service.ts +17 -4
  194. package/src/events/private_event_filter_validator.ts +21 -1
  195. package/src/logs/log_service.ts +59 -75
  196. package/src/messages/message_context_service.ts +44 -0
  197. package/src/notes/note_service.ts +18 -8
  198. package/src/notes_filter.ts +1 -3
  199. package/src/oracle_version.ts +20 -10
  200. package/src/private_kernel/hints/private_kernel_reset_private_inputs_builder.ts +157 -110
  201. package/src/private_kernel/hints/test_utils.ts +325 -0
  202. package/src/private_kernel/private_kernel_execution_prover.ts +17 -15
  203. package/src/private_kernel/private_kernel_oracle.ts +21 -21
  204. package/src/pxe.ts +109 -61
  205. package/src/storage/anchor_block_store/anchor_block_store.ts +1 -1
  206. package/src/storage/capsule_store/capsule_service.ts +90 -0
  207. package/src/storage/capsule_store/capsule_store.ts +44 -26
  208. package/src/storage/capsule_store/index.ts +1 -0
  209. package/src/storage/contract_store/contract_store.ts +177 -76
  210. package/src/storage/metadata.ts +1 -1
  211. package/src/storage/note_store/note_store.ts +2 -5
  212. package/src/storage/private_event_store/private_event_store.ts +4 -0
  213. package/src/storage/tagging_store/recipient_tagging_store.ts +9 -5
  214. package/src/storage/tagging_store/sender_tagging_store.ts +185 -138
  215. package/src/tagging/index.ts +2 -2
  216. package/src/tagging/recipient_sync/load_private_logs_for_sender_recipient_pair.ts +8 -21
  217. package/src/tagging/recipient_sync/utils/load_logs_for_range.ts +10 -15
  218. package/src/tagging/sender_sync/sync_sender_tagging_indexes.ts +23 -10
  219. package/src/tagging/sender_sync/utils/get_status_change_of_pending.ts +26 -11
  220. package/src/tagging/sender_sync/utils/load_and_store_new_tagging_indexes.ts +27 -26
  221. package/dest/access_scopes.d.ts +0 -9
  222. package/dest/access_scopes.d.ts.map +0 -1
  223. package/dest/access_scopes.js +0 -6
  224. package/src/access_scopes.ts +0 -9
package/src/pxe.ts CHANGED
@@ -18,6 +18,7 @@ import {
18
18
  } from '@aztec/stdlib/abi';
19
19
  import type { AuthWitness } from '@aztec/stdlib/auth-witness';
20
20
  import type { AztecAddress } from '@aztec/stdlib/aztec-address';
21
+ import type { L2TipsProvider } from '@aztec/stdlib/block';
21
22
  import {
22
23
  CompleteAddress,
23
24
  type ContractInstanceWithAddress,
@@ -47,12 +48,11 @@ import {
47
48
  TxProfileResult,
48
49
  TxProvingResult,
49
50
  TxSimulationResult,
50
- UtilitySimulationResult,
51
+ UtilityExecutionResult,
51
52
  } from '@aztec/stdlib/tx';
52
53
 
53
54
  import { inspect } from 'util';
54
55
 
55
- import type { AccessScopes } from './access_scopes.js';
56
56
  import { BlockSynchronizer } from './block_synchronizer/index.js';
57
57
  import type { PXEConfig } from './config/index.js';
58
58
  import { BenchmarkedNodeFactory } from './contract_function_simulator/benchmarked_node.js';
@@ -61,12 +61,14 @@ import {
61
61
  generateSimulatedProvingResult,
62
62
  } from './contract_function_simulator/contract_function_simulator.js';
63
63
  import { ProxiedContractStoreFactory } from './contract_function_simulator/proxied_contract_data_source.js';
64
+ import { displayDebugLogs } from './contract_logging.js';
64
65
  import { ContractSyncService } from './contract_sync/contract_sync_service.js';
65
66
  import { readCurrentClassId } from './contract_sync/helpers.js';
66
67
  import { PXEDebugUtils } from './debug/pxe_debug_utils.js';
67
68
  import { enrichPublicSimulationError, enrichSimulationError } from './error_enriching.js';
68
69
  import { PrivateEventFilterValidator } from './events/private_event_filter_validator.js';
69
70
  import { JobCoordinator } from './job_coordinator/job_coordinator.js';
71
+ import { MessageContextService } from './messages/message_context_service.js';
70
72
  import {
71
73
  PrivateKernelExecutionProver,
72
74
  type PrivateKernelExecutionProverConfig,
@@ -94,7 +96,7 @@ export type ProfileTxOpts = {
94
96
  /** If true, proof generation is skipped during profiling. Defaults to true. */
95
97
  skipProofGeneration?: boolean;
96
98
  /** Addresses whose private state and keys are accessible during private execution. */
97
- scopes: AccessScopes;
99
+ scopes: AztecAddress[];
98
100
  };
99
101
 
100
102
  /** Options for PXE.simulateTx. */
@@ -105,18 +107,20 @@ export type SimulateTxOpts = {
105
107
  skipTxValidation?: boolean;
106
108
  /** If false, fees are enforced. */
107
109
  skipFeeEnforcement?: boolean;
108
- /** State overrides for the simulation, such as contract instances and artifacts. */
110
+ /** If true, kernel logic is emulated in TS for simulation */
111
+ skipKernels?: boolean;
112
+ /** State overrides for the simulation, such as contract instances and artifacts. Requires skipKernels: true */
109
113
  overrides?: SimulationOverrides;
110
114
  /** Addresses whose private state and keys are accessible during private execution */
111
- scopes: AccessScopes;
115
+ scopes: AztecAddress[];
112
116
  };
113
117
 
114
- /** Options for PXE.simulateUtility. */
115
- export type SimulateUtilityOpts = {
118
+ /** Options for PXE.executeUtility. */
119
+ export type ExecuteUtilityOpts = {
116
120
  /** The authentication witnesses required for the function call. */
117
121
  authwits?: AuthWitness[];
118
122
  /** The accounts whose notes we can access in this call */
119
- scopes: AccessScopes;
123
+ scopes: AztecAddress[];
120
124
  };
121
125
 
122
126
  /** Args for PXE.create. */
@@ -156,6 +160,8 @@ export class PXE {
156
160
  private addressStore: AddressStore,
157
161
  private privateEventStore: PrivateEventStore,
158
162
  private contractSyncService: ContractSyncService,
163
+ private messageContextService: MessageContextService,
164
+ private l2TipsStore: L2TipsProvider,
159
165
  private simulator: CircuitSimulator,
160
166
  private proverEnabled: boolean,
161
167
  private proofCreator: PrivateKernelProver,
@@ -211,6 +217,8 @@ export class PXE {
211
217
  noteStore,
212
218
  createLogger('pxe:contract_sync', bindings),
213
219
  );
220
+ const messageContextService = new MessageContextService(node);
221
+
214
222
  const synchronizer = new BlockSynchronizer(
215
223
  node,
216
224
  store,
@@ -251,6 +259,8 @@ export class PXE {
251
259
  addressStore,
252
260
  privateEventStore,
253
261
  contractSyncService,
262
+ messageContextService,
263
+ tipsStore,
254
264
  simulator,
255
265
  proverEnabled,
256
266
  proofCreator,
@@ -264,7 +274,7 @@ export class PXE {
264
274
  debugUtils.setPXEHelpers(
265
275
  pxe.#putInJobQueue.bind(pxe),
266
276
  pxe.#getSimulatorForTx.bind(pxe),
267
- pxe.#simulateUtility.bind(pxe),
277
+ pxe.#executeUtility.bind(pxe),
268
278
  );
269
279
 
270
280
  pxe.jobQueue.start();
@@ -285,6 +295,7 @@ export class PXE {
285
295
  keyStore: this.keyStore,
286
296
  addressStore: this.addressStore,
287
297
  aztecNode: BenchmarkedNodeFactory.create(this.node),
298
+ l2TipsStore: this.l2TipsStore,
288
299
  senderTaggingStore: this.senderTaggingStore,
289
300
  recipientTaggingStore: this.recipientTaggingStore,
290
301
  senderAddressBookStore: this.senderAddressBookStore,
@@ -292,6 +303,7 @@ export class PXE {
292
303
  privateEventStore: this.privateEventStore,
293
304
  simulator: this.simulator,
294
305
  contractSyncService: this.contractSyncService,
306
+ messageContextService: this.messageContextService,
295
307
  });
296
308
  }
297
309
 
@@ -344,9 +356,8 @@ export class PXE {
344
356
  async #registerProtocolContracts() {
345
357
  const registered: Record<string, string> = {};
346
358
  for (const name of protocolContractNames) {
347
- const { address, contractClass, instance, artifact } =
348
- await this.protocolContractsProvider.getProtocolContractArtifact(name);
349
- await this.contractStore.addContractArtifact(contractClass.id, artifact);
359
+ const { address, instance, artifact } = await this.protocolContractsProvider.getProtocolContractArtifact(name);
360
+ await this.contractStore.addContractArtifact(artifact);
350
361
  await this.contractStore.addContractInstance(instance);
351
362
  registered[name] = address.toString();
352
363
  }
@@ -358,7 +369,7 @@ export class PXE {
358
369
  async #executePrivate(
359
370
  contractFunctionSimulator: ContractFunctionSimulator,
360
371
  txRequest: TxExecutionRequest,
361
- scopes: AccessScopes,
372
+ scopes: AztecAddress[],
362
373
  jobId: string,
363
374
  ): Promise<PrivateExecutionResult> {
364
375
  const { origin: contractAddress, functionSelector } = txRequest;
@@ -370,7 +381,7 @@ export class PXE {
370
381
  contractAddress,
371
382
  functionSelector,
372
383
  (privateSyncCall, execScopes) =>
373
- this.#simulateUtility(contractFunctionSimulator, privateSyncCall, [], execScopes, jobId),
384
+ this.#executeUtility(contractFunctionSimulator, privateSyncCall, [], execScopes, jobId),
374
385
  anchorBlockHeader,
375
386
  jobId,
376
387
  scopes,
@@ -394,25 +405,32 @@ export class PXE {
394
405
  }
395
406
 
396
407
  /**
397
- * Simulate a utility function call on the given contract.
408
+ * Execute a utility function call on the given contract.
398
409
  * @param contractFunctionSimulator - The simulator to use for the function call.
399
410
  * @param call - The function call to execute.
400
411
  * @param authWitnesses - Authentication witnesses required for the function call.
401
412
  * @param scopes - Optional array of account addresses whose notes can be accessed in this call. Defaults to all
402
413
  * accounts if not specified.
403
414
  * @param jobId - The job ID for staged writes.
404
- * @returns The simulation result containing the outputs of the utility function.
415
+ * @returns The execution result containing the outputs of the utility function.
405
416
  */
406
- async #simulateUtility(
417
+ async #executeUtility(
407
418
  contractFunctionSimulator: ContractFunctionSimulator,
408
419
  call: FunctionCall,
409
420
  authWitnesses: AuthWitness[] | undefined,
410
- scopes: AccessScopes,
421
+ scopes: AztecAddress[],
411
422
  jobId: string,
412
423
  ) {
413
424
  try {
414
425
  const anchorBlockHeader = await this.anchorBlockStore.getBlockHeader();
415
- return contractFunctionSimulator.runUtility(call, authWitnesses ?? [], anchorBlockHeader, scopes, jobId);
426
+ const { result, offchainEffects } = await contractFunctionSimulator.runUtility(
427
+ call,
428
+ authWitnesses ?? [],
429
+ anchorBlockHeader,
430
+ scopes,
431
+ jobId,
432
+ );
433
+ return { result, offchainEffects };
416
434
  } catch (err) {
417
435
  if (err instanceof SimulationError) {
418
436
  await enrichSimulationError(err, this.contractStore, this.log);
@@ -466,8 +484,7 @@ export class PXE {
466
484
  config: PrivateKernelExecutionProverConfig,
467
485
  ): Promise<PrivateKernelExecutionProofOutput<PrivateKernelTailCircuitPublicInputs>> {
468
486
  const anchorBlockHeader = await this.anchorBlockStore.getBlockHeader();
469
- const anchorBlockHash = await anchorBlockHeader.hash();
470
- const kernelOracle = new PrivateKernelOracle(this.contractStore, this.keyStore, this.node, anchorBlockHash);
487
+ const kernelOracle = new PrivateKernelOracle(this.contractStore, this.keyStore, this.node, anchorBlockHeader);
471
488
  const kernelTraceProver = new PrivateKernelExecutionProver(
472
489
  kernelOracle,
473
490
  proofCreator,
@@ -485,7 +502,9 @@ export class PXE {
485
502
  * @returns The synced block header
486
503
  */
487
504
  public getSyncedBlockHeader(): Promise<BlockHeader> {
488
- return this.anchorBlockStore.getBlockHeader();
505
+ return this.#putInJobQueue(() => {
506
+ return this.anchorBlockStore.getBlockHeader();
507
+ });
489
508
  }
490
509
 
491
510
  /**
@@ -542,6 +561,12 @@ export class PXE {
542
561
  * TODO: It's strange that we return the address here and I (benesjan) think we should drop the return value.
543
562
  */
544
563
  public async registerSender(sender: AztecAddress): Promise<AztecAddress> {
564
+ if (!(await sender.isValid())) {
565
+ throw new Error(
566
+ `Address ${sender} is not valid: it does not correspond to a point on the Grumpkin curve. Cannot register it as a sender.`,
567
+ );
568
+ }
569
+
545
570
  const accounts = await this.keyStore.getAccounts();
546
571
  if (accounts.includes(sender)) {
547
572
  this.log.info(`Sender:\n "${sender.toString()}"\n already registered.`);
@@ -552,6 +577,9 @@ export class PXE {
552
577
 
553
578
  if (wasAdded) {
554
579
  this.log.info(`Added sender:\n ${sender.toString()}`);
580
+ // Wipe the entire sync cache: the new sender's tagged logs could contain notes/events for any contract, so
581
+ // all contracts must re-sync to discover them. Queued to avoid wiping while a job is in flight.
582
+ await this.#putInJobQueue(() => Promise.resolve(this.contractSyncService.wipe()));
555
583
  } else {
556
584
  this.log.info(`Sender:\n "${sender.toString()}"\n already registered.`);
557
585
  }
@@ -601,8 +629,7 @@ export class PXE {
601
629
  * @param artifact - The build artifact for the contract class.
602
630
  */
603
631
  public async registerContractClass(artifact: ContractArtifact): Promise<void> {
604
- const { id: contractClassId } = await getContractClassFromArtifact(artifact);
605
- await this.contractStore.addContractArtifact(contractClassId, artifact);
632
+ const contractClassId = await this.contractStore.addContractArtifact(artifact);
606
633
  this.log.info(`Added contract class ${artifact.name} with id ${contractClassId}`);
607
634
  }
608
635
 
@@ -621,17 +648,17 @@ export class PXE {
621
648
  if (artifact) {
622
649
  // If the user provides an artifact, validate it against the expected class id and register it
623
650
  const contractClass = await getContractClassFromArtifact(artifact);
624
- const contractClassId = contractClass.id;
625
- if (!contractClassId.equals(instance.currentContractClassId)) {
651
+ if (!contractClass.id.equals(instance.currentContractClassId)) {
626
652
  throw new Error(
627
- `Artifact does not match expected class id (computed ${contractClassId} but instance refers to ${instance.currentContractClassId})`,
653
+ `Artifact does not match expected class id (computed ${contractClass.id} but instance refers to ${instance.currentContractClassId})`,
628
654
  );
629
655
  }
630
656
  const computedAddress = await computeContractAddressFromInstance(instance);
631
657
  if (!computedAddress.equals(instance.address)) {
632
658
  throw new Error('Added a contract in which the address does not match the contract instance.');
633
659
  }
634
- await this.contractStore.addContractArtifact(contractClass.id, artifact);
660
+
661
+ await this.contractStore.addContractArtifact(artifact, contractClass);
635
662
 
636
663
  const publicFunctionSignatures = artifact.functions
637
664
  .filter(fn => fn.functionType === FunctionType.PUBLIC)
@@ -680,15 +707,16 @@ export class PXE {
680
707
  throw new Error('Could not update contract to a class different from the current one.');
681
708
  }
682
709
 
683
- await this.contractStore.addContractArtifact(contractClass.id, artifact);
684
-
685
710
  const publicFunctionSignatures = artifact.functions
686
711
  .filter(fn => fn.functionType === FunctionType.PUBLIC)
687
712
  .map(fn => decodeFunctionSignature(fn.name, fn.parameters));
688
713
  await this.node.registerContractFunctionSignatures(publicFunctionSignatures);
689
714
 
690
715
  currentInstance.currentContractClassId = contractClass.id;
691
- await this.contractStore.addContractInstance(currentInstance);
716
+ await Promise.all([
717
+ this.contractStore.addContractArtifact(artifact, contractClass),
718
+ this.contractStore.addContractInstance(currentInstance),
719
+ ]);
692
720
  this.log.info(`Updated contract ${artifact.name} at ${contractAddress.toString()} to class ${contractClass.id}`);
693
721
  });
694
722
  }
@@ -764,17 +792,17 @@ export class PXE {
764
792
  // transaction before this one is included in a block from this PXE, and that transaction contains a log with
765
793
  // a tag derived from the same secret, we would reuse the tag and the transactions would be linked. Hence
766
794
  // storing the tags here prevents linkage of txs sent from the same PXE.
767
- const preTagsUsedInTheTx = privateExecutionResult.entrypoint.preTags;
768
- if (preTagsUsedInTheTx.length > 0) {
795
+ const taggingIndexRangesUsedInTheTx = privateExecutionResult.entrypoint.taggingIndexRanges;
796
+ if (taggingIndexRangesUsedInTheTx.length > 0) {
769
797
  // TODO(benesjan): The following is an expensive operation. Figure out a way to avoid it.
770
798
  const txHash = (await txProvingResult.toTx()).txHash;
771
799
 
772
- await this.senderTaggingStore.storePendingIndexes(preTagsUsedInTheTx, txHash, jobId);
773
- this.log.debug(`Stored used pre-tags as sender for the tx`, {
774
- preTagsUsedInTheTx,
800
+ await this.senderTaggingStore.storePendingIndexes(taggingIndexRangesUsedInTheTx, txHash, jobId);
801
+ this.log.debug(`Stored used tagging index ranges as sender for the tx`, {
802
+ taggingIndexRangesUsedInTheTx,
775
803
  });
776
804
  } else {
777
- this.log.debug(`No pre-tags used in the tx`);
805
+ this.log.debug(`No tagging index ranges used in the tx`);
778
806
  }
779
807
 
780
808
  return txProvingResult;
@@ -881,7 +909,14 @@ export class PXE {
881
909
  */
882
910
  public simulateTx(
883
911
  txRequest: TxExecutionRequest,
884
- { simulatePublic, skipTxValidation = false, skipFeeEnforcement = false, overrides, scopes }: SimulateTxOpts,
912
+ {
913
+ simulatePublic,
914
+ skipTxValidation = false,
915
+ skipFeeEnforcement = false,
916
+ skipKernels = true,
917
+ overrides,
918
+ scopes,
919
+ }: SimulateTxOpts,
885
920
  ): Promise<TxSimulationResult> {
886
921
  // We disable concurrent simulations since those might execute oracles which read and write to the PXE stores (e.g.
887
922
  // to the capsules), and we need to prevent concurrent runs from interfering with one another (e.g. attempting to
@@ -905,17 +940,20 @@ export class PXE {
905
940
  await this.blockStateSynchronizer.sync();
906
941
  const syncTime = syncTimer.ms();
907
942
 
908
- const contractFunctionSimulator = this.#getSimulatorForTx(overrides);
909
- // Temporary: in case there are overrides, we have to skip the kernels or validations
910
- // will fail. Consider handing control to the user/wallet on whether they want to run them
911
- // or not.
912
943
  const overriddenContracts = overrides?.contracts ? new Set(Object.keys(overrides.contracts)) : undefined;
913
944
  const hasOverriddenContracts = overriddenContracts !== undefined && overriddenContracts.size > 0;
914
- const skipKernels = hasOverriddenContracts;
915
945
 
916
- // Set overridden contracts on the sync service so it knows to skip syncing them
946
+ if (hasOverriddenContracts && !skipKernels) {
947
+ throw new Error(
948
+ 'Simulating with overridden contracts is not compatible with kernel execution. Please set skipKernels to true when simulating with overridden contracts.',
949
+ );
950
+ }
951
+ const contractFunctionSimulator = this.#getSimulatorForTx(overrides);
952
+
917
953
  if (hasOverriddenContracts) {
918
- this.contractSyncService.setOverriddenContracts(jobId, overriddenContracts);
954
+ // Overridden contracts don't have a sync function, so calling sync on them would fail.
955
+ // We exclude them so the sync service skips them entirely.
956
+ this.contractSyncService.setExcludedFromSync(jobId, overriddenContracts);
919
957
  }
920
958
 
921
959
  // Execution of private functions only; no proving, and no kernel logic.
@@ -947,6 +985,9 @@ export class PXE {
947
985
  const publicSimulationTimer = new Timer();
948
986
  publicOutput = await this.#simulatePublicCalls(simulatedTx, skipFeeEnforcement);
949
987
  publicSimulationTime = publicSimulationTimer.ms();
988
+ if (publicOutput?.debugLogs?.length) {
989
+ await displayDebugLogs(publicOutput.debugLogs, addr => this.contractStore.getDebugContractName(addr));
990
+ }
950
991
  }
951
992
 
952
993
  let validationTime: number | undefined;
@@ -955,7 +996,8 @@ export class PXE {
955
996
  const validationResult = await this.node.isValidTx(simulatedTx, { isSimulation: true, skipFeeEnforcement });
956
997
  validationTime = validationTimer.ms();
957
998
  if (validationResult.result === 'invalid') {
958
- throw new Error('The simulated transaction is unable to be added to state and is invalid.');
999
+ const reason = validationResult.reason.length > 0 ? ` Reason: ${validationResult.reason.join(', ')}` : '';
1000
+ throw new Error(`The simulated transaction is unable to be added to state and is invalid.${reason}`);
959
1001
  }
960
1002
  }
961
1003
 
@@ -1006,23 +1048,23 @@ export class PXE {
1006
1048
  inspect(txRequest),
1007
1049
  `simulatePublic=${simulatePublic}`,
1008
1050
  `skipTxValidation=${skipTxValidation}`,
1009
- `scopes=${scopes === 'ALL_SCOPES' ? scopes : scopes.map(s => s.toString()).join(', ')}`,
1051
+ `scopes=${scopes.map(s => s.toString()).join(', ')}`,
1010
1052
  );
1011
1053
  }
1012
1054
  });
1013
1055
  }
1014
1056
 
1015
1057
  /**
1016
- * Simulates the execution of a contract utility function.
1058
+ * Executes a contract utility function.
1017
1059
  * @param call - The function call containing the function details, arguments, and target contract address.
1018
1060
  */
1019
- public simulateUtility(
1061
+ public executeUtility(
1020
1062
  call: FunctionCall,
1021
- { authwits, scopes }: SimulateUtilityOpts = { scopes: 'ALL_SCOPES' },
1022
- ): Promise<UtilitySimulationResult> {
1023
- // We disable concurrent simulations since those might execute oracles which read and write to the PXE stores (e.g.
1063
+ { authwits, scopes }: ExecuteUtilityOpts = { scopes: [] },
1064
+ ): Promise<UtilityExecutionResult> {
1065
+ // We disable concurrent executions since those might execute oracles which read and write to the PXE stores (e.g.
1024
1066
  // to the capsules), and we need to prevent concurrent runs from interfering with one another (e.g. attempting to
1025
- // delete the same read value, or reading values that another simulation is currently modifying).
1067
+ // delete the same read value, or reading values that another execution is currently modifying).
1026
1068
  return this.#putInJobQueue(async jobId => {
1027
1069
  try {
1028
1070
  const totalTimer = new Timer();
@@ -1037,13 +1079,13 @@ export class PXE {
1037
1079
  call.to,
1038
1080
  call.selector,
1039
1081
  (privateSyncCall, execScopes) =>
1040
- this.#simulateUtility(contractFunctionSimulator, privateSyncCall, [], execScopes, jobId),
1082
+ this.#executeUtility(contractFunctionSimulator, privateSyncCall, [], execScopes, jobId),
1041
1083
  anchorBlockHeader,
1042
1084
  jobId,
1043
1085
  scopes,
1044
1086
  );
1045
1087
 
1046
- const executionResult = await this.#simulateUtility(
1088
+ const { result: executionResult, offchainEffects } = await this.#executeUtility(
1047
1089
  contractFunctionSimulator,
1048
1090
  call,
1049
1091
  authwits ?? [],
@@ -1064,14 +1106,19 @@ export class PXE {
1064
1106
  };
1065
1107
 
1066
1108
  const simulationStats = contractFunctionSimulator.getStats();
1067
- return { result: executionResult, stats: { timings, nodeRPCCalls: simulationStats.nodeRPCCalls } };
1109
+ return {
1110
+ result: executionResult,
1111
+ offchainEffects,
1112
+ anchorBlockTimestamp: anchorBlockHeader.globalVariables.timestamp,
1113
+ stats: { timings, nodeRPCCalls: simulationStats.nodeRPCCalls },
1114
+ };
1068
1115
  } catch (err: any) {
1069
1116
  const { to, name, args } = call;
1070
1117
  const stringifiedArgs = args.map(arg => arg.toString()).join(', ');
1071
1118
  throw this.#contextualizeError(
1072
1119
  err,
1073
- `simulateUtility ${to}:${name}(${stringifiedArgs})`,
1074
- `scopes=${scopes === 'ALL_SCOPES' ? scopes : scopes.map(s => s.toString()).join(', ')}`,
1120
+ `executeUtility ${to}:${name}(${stringifiedArgs})`,
1121
+ `scopes=${scopes.map(s => s.toString()).join(', ')}`,
1075
1122
  );
1076
1123
  }
1077
1124
  });
@@ -1108,7 +1155,7 @@ export class PXE {
1108
1155
  filter.contractAddress,
1109
1156
  null,
1110
1157
  async (privateSyncCall, execScopes) =>
1111
- await this.#simulateUtility(contractFunctionSimulator, privateSyncCall, [], execScopes, jobId),
1158
+ await this.#executeUtility(contractFunctionSimulator, privateSyncCall, [], execScopes, jobId),
1112
1159
  anchorBlockHeader,
1113
1160
  jobId,
1114
1161
  filter.scopes,
@@ -1128,7 +1175,8 @@ export class PXE {
1128
1175
  /**
1129
1176
  * Stops the PXE's job queue.
1130
1177
  */
1131
- public stop(): Promise<void> {
1132
- return this.jobQueue.end();
1178
+ public async stop(): Promise<void> {
1179
+ await this.jobQueue.end();
1180
+ await this.blockStateSynchronizer.stop();
1133
1181
  }
1134
1182
  }
@@ -23,7 +23,7 @@ export class AnchorBlockStore {
23
23
  }
24
24
 
25
25
  async getBlockHeader(): Promise<BlockHeader> {
26
- const headerBuffer = await this.#synchronizedHeader.getAsync();
26
+ const headerBuffer = await this.#store.transactionAsync(() => this.#synchronizedHeader.getAsync());
27
27
  if (!headerBuffer) {
28
28
  throw new Error(`Trying to get block header with a not-yet-synchronized PXE - this should never happen`);
29
29
  }
@@ -0,0 +1,90 @@
1
+ import type { Fr } from '@aztec/foundation/curves/bn254';
2
+ import { AztecAddress } from '@aztec/stdlib/aztec-address';
3
+ import type { Capsule } from '@aztec/stdlib/tx';
4
+
5
+ import type { CapsuleStore } from './capsule_store.js';
6
+
7
+ /**
8
+ * Wraps a CapsuleStore with scope-based access control. Each operation asserts that the requested scope is in the
9
+ * allowed scopes list before delegating to the underlying store.
10
+ */
11
+ export class CapsuleService {
12
+ constructor(
13
+ private readonly capsuleStore: CapsuleStore,
14
+ private readonly allowedScopes: AztecAddress[],
15
+ ) {}
16
+
17
+ setCapsule(contractAddress: AztecAddress, slot: Fr, capsule: Fr[], jobId: string, scope: AztecAddress) {
18
+ assertAllowedScope(scope, this.allowedScopes);
19
+ this.capsuleStore.setCapsule(contractAddress, slot, capsule, jobId, scope);
20
+ }
21
+
22
+ async getCapsule(
23
+ contractAddress: AztecAddress,
24
+ slot: Fr,
25
+ jobId: string,
26
+ scope: AztecAddress,
27
+ transientCapsules?: Capsule[],
28
+ ): Promise<Fr[] | null> {
29
+ assertAllowedScope(scope, this.allowedScopes);
30
+
31
+ // TODO(#12425): On the following line, the pertinent capsule gets overshadowed by the transient one. Tackle this.
32
+ const maybeTransientCapsule = transientCapsules?.find(
33
+ c =>
34
+ c.contractAddress.equals(contractAddress) &&
35
+ c.storageSlot.equals(slot) &&
36
+ (c.scope ?? AztecAddress.ZERO).equals(scope),
37
+ )?.data;
38
+
39
+ return maybeTransientCapsule ?? (await this.capsuleStore.getCapsule(contractAddress, slot, jobId, scope));
40
+ }
41
+
42
+ deleteCapsule(contractAddress: AztecAddress, slot: Fr, jobId: string, scope: AztecAddress) {
43
+ assertAllowedScope(scope, this.allowedScopes);
44
+ this.capsuleStore.deleteCapsule(contractAddress, slot, jobId, scope);
45
+ }
46
+
47
+ copyCapsule(
48
+ contractAddress: AztecAddress,
49
+ srcSlot: Fr,
50
+ dstSlot: Fr,
51
+ numEntries: number,
52
+ jobId: string,
53
+ scope: AztecAddress,
54
+ ): Promise<void> {
55
+ assertAllowedScope(scope, this.allowedScopes);
56
+ return this.capsuleStore.copyCapsule(contractAddress, srcSlot, dstSlot, numEntries, jobId, scope);
57
+ }
58
+
59
+ appendToCapsuleArray(
60
+ contractAddress: AztecAddress,
61
+ baseSlot: Fr,
62
+ content: Fr[][],
63
+ jobId: string,
64
+ scope: AztecAddress,
65
+ ): Promise<void> {
66
+ assertAllowedScope(scope, this.allowedScopes);
67
+ return this.capsuleStore.appendToCapsuleArray(contractAddress, baseSlot, content, jobId, scope);
68
+ }
69
+
70
+ readCapsuleArray(contractAddress: AztecAddress, baseSlot: Fr, jobId: string, scope: AztecAddress): Promise<Fr[][]> {
71
+ assertAllowedScope(scope, this.allowedScopes);
72
+ return this.capsuleStore.readCapsuleArray(contractAddress, baseSlot, jobId, scope);
73
+ }
74
+
75
+ setCapsuleArray(contractAddress: AztecAddress, baseSlot: Fr, content: Fr[][], jobId: string, scope: AztecAddress) {
76
+ assertAllowedScope(scope, this.allowedScopes);
77
+ return this.capsuleStore.setCapsuleArray(contractAddress, baseSlot, content, jobId, scope);
78
+ }
79
+ }
80
+
81
+ function assertAllowedScope(scope: AztecAddress, allowedScopes: AztecAddress[]) {
82
+ if (scope.equals(AztecAddress.ZERO)) {
83
+ return;
84
+ }
85
+ if (!allowedScopes.some((allowed: AztecAddress) => allowed.equals(scope))) {
86
+ throw new Error(
87
+ `Scope ${scope.toString()} is not in the allowed scopes list: [${allowedScopes.map((s: AztecAddress) => s.toString()).join(', ')}]. See https://docs.aztec.network/errors/10`,
88
+ );
89
+ }
90
+ }