@aztec/pxe 5.0.0-rc.1 → 5.0.0-rc.2

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 (218) hide show
  1. package/dest/block_synchronizer/block_stream_source.d.ts +5 -5
  2. package/dest/block_synchronizer/block_stream_source.d.ts.map +1 -1
  3. package/dest/block_synchronizer/block_stream_source.js +4 -29
  4. package/dest/block_synchronizer/block_synchronizer.d.ts +13 -11
  5. package/dest/block_synchronizer/block_synchronizer.d.ts.map +1 -1
  6. package/dest/block_synchronizer/block_synchronizer.js +43 -15
  7. package/dest/config/index.d.ts +2 -1
  8. package/dest/config/index.d.ts.map +1 -1
  9. package/dest/config/index.js +1 -0
  10. package/dest/contract_function_simulator/contract_function_simulator.d.ts +11 -16
  11. package/dest/contract_function_simulator/contract_function_simulator.d.ts.map +1 -1
  12. package/dest/contract_function_simulator/contract_function_simulator.js +22 -18
  13. package/dest/contract_function_simulator/index.d.ts +15 -9
  14. package/dest/contract_function_simulator/index.d.ts.map +1 -1
  15. package/dest/contract_function_simulator/index.js +3 -7
  16. package/dest/contract_function_simulator/noir-structs/bounded_vec.d.ts +8 -27
  17. package/dest/contract_function_simulator/noir-structs/bounded_vec.d.ts.map +1 -1
  18. package/dest/contract_function_simulator/noir-structs/bounded_vec.js +8 -23
  19. package/dest/contract_function_simulator/noir-structs/contract_class_log_data.d.ts +9 -0
  20. package/dest/contract_function_simulator/noir-structs/contract_class_log_data.d.ts.map +1 -0
  21. package/dest/contract_function_simulator/noir-structs/contract_class_log_data.js +1 -0
  22. package/dest/contract_function_simulator/noir-structs/embedded_curve_point.d.ts +7 -0
  23. package/dest/contract_function_simulator/noir-structs/embedded_curve_point.d.ts.map +1 -0
  24. package/dest/contract_function_simulator/noir-structs/embedded_curve_point.js +1 -0
  25. package/dest/contract_function_simulator/noir-structs/event_validation_request.js +1 -1
  26. package/dest/contract_function_simulator/noir-structs/fact.d.ts +16 -0
  27. package/dest/contract_function_simulator/noir-structs/fact.d.ts.map +1 -0
  28. package/dest/contract_function_simulator/noir-structs/fact.js +6 -0
  29. package/dest/contract_function_simulator/noir-structs/fact_collection.d.ts +27 -0
  30. package/dest/contract_function_simulator/noir-structs/fact_collection.d.ts.map +1 -0
  31. package/dest/contract_function_simulator/noir-structs/fact_collection.js +29 -0
  32. package/dest/contract_function_simulator/noir-structs/log_retrieval_request.d.ts +11 -12
  33. package/dest/contract_function_simulator/noir-structs/log_retrieval_request.d.ts.map +1 -1
  34. package/dest/contract_function_simulator/noir-structs/log_retrieval_request.js +6 -49
  35. package/dest/contract_function_simulator/noir-structs/log_retrieval_response.d.ts +4 -8
  36. package/dest/contract_function_simulator/noir-structs/log_retrieval_response.d.ts.map +1 -1
  37. package/dest/contract_function_simulator/noir-structs/log_retrieval_response.js +1 -60
  38. package/dest/contract_function_simulator/noir-structs/note_validation_request.js +2 -2
  39. package/dest/contract_function_simulator/noir-structs/option.d.ts +9 -11
  40. package/dest/contract_function_simulator/noir-structs/option.d.ts.map +1 -1
  41. package/dest/contract_function_simulator/noir-structs/option.js +18 -13
  42. package/dest/contract_function_simulator/noir-structs/origin_block.d.ts +11 -0
  43. package/dest/contract_function_simulator/noir-structs/origin_block.d.ts.map +1 -0
  44. package/dest/contract_function_simulator/noir-structs/origin_block.js +5 -0
  45. package/dest/contract_function_simulator/noir-structs/provided_secret.d.ts +5 -8
  46. package/dest/contract_function_simulator/noir-structs/provided_secret.d.ts.map +1 -1
  47. package/dest/contract_function_simulator/noir-structs/provided_secret.js +1 -14
  48. package/dest/contract_function_simulator/noir-structs/resolved_tagging_strategy.d.ts +21 -0
  49. package/dest/contract_function_simulator/noir-structs/resolved_tagging_strategy.d.ts.map +1 -0
  50. package/dest/contract_function_simulator/noir-structs/resolved_tagging_strategy.js +33 -0
  51. package/dest/contract_function_simulator/noir-structs/resolved_tx.d.ts +21 -0
  52. package/dest/contract_function_simulator/noir-structs/resolved_tx.d.ts.map +1 -0
  53. package/dest/contract_function_simulator/noir-structs/resolved_tx.js +50 -0
  54. package/dest/contract_function_simulator/noir-structs/tx_effect_data.d.ts +14 -0
  55. package/dest/contract_function_simulator/noir-structs/tx_effect_data.d.ts.map +1 -0
  56. package/dest/contract_function_simulator/noir-structs/tx_effect_data.js +5 -0
  57. package/dest/contract_function_simulator/noir-structs/utility_context.d.ts +6 -11
  58. package/dest/contract_function_simulator/noir-structs/utility_context.d.ts.map +1 -1
  59. package/dest/contract_function_simulator/noir-structs/utility_context.js +1 -20
  60. package/dest/contract_function_simulator/oracle/message_load_oracle_inputs.d.ts +3 -14
  61. package/dest/contract_function_simulator/oracle/message_load_oracle_inputs.d.ts.map +1 -1
  62. package/dest/contract_function_simulator/oracle/message_load_oracle_inputs.js +1 -24
  63. package/dest/contract_function_simulator/oracle/oracle_registry.d.ts +81 -6
  64. package/dest/contract_function_simulator/oracle/oracle_registry.d.ts.map +1 -1
  65. package/dest/contract_function_simulator/oracle/oracle_registry.js +128 -9
  66. package/dest/contract_function_simulator/oracle/oracle_type_mappings.d.ts +80 -36
  67. package/dest/contract_function_simulator/oracle/oracle_type_mappings.d.ts.map +1 -1
  68. package/dest/contract_function_simulator/oracle/oracle_type_mappings.js +926 -264
  69. package/dest/contract_function_simulator/oracle/private_execution_oracle.d.ts +13 -8
  70. package/dest/contract_function_simulator/oracle/private_execution_oracle.d.ts.map +1 -1
  71. package/dest/contract_function_simulator/oracle/private_execution_oracle.js +80 -11
  72. package/dest/contract_function_simulator/oracle/utility_execution_oracle.d.ts +46 -20
  73. package/dest/contract_function_simulator/oracle/utility_execution_oracle.d.ts.map +1 -1
  74. package/dest/contract_function_simulator/oracle/utility_execution_oracle.js +119 -55
  75. package/dest/contract_sync/helpers.d.ts +7 -6
  76. package/dest/contract_sync/helpers.d.ts.map +1 -1
  77. package/dest/contract_sync/helpers.js +11 -16
  78. package/dest/entrypoints/client/bundle/utils.d.ts +1 -1
  79. package/dest/entrypoints/client/bundle/utils.d.ts.map +1 -1
  80. package/dest/entrypoints/client/bundle/utils.js +1 -0
  81. package/dest/entrypoints/client/lazy/utils.d.ts +1 -1
  82. package/dest/entrypoints/client/lazy/utils.d.ts.map +1 -1
  83. package/dest/entrypoints/client/lazy/utils.js +1 -0
  84. package/dest/entrypoints/pxe_creation_options.d.ts +8 -2
  85. package/dest/entrypoints/pxe_creation_options.d.ts.map +1 -1
  86. package/dest/entrypoints/server/index.d.ts +1 -2
  87. package/dest/entrypoints/server/index.d.ts.map +1 -1
  88. package/dest/entrypoints/server/index.js +0 -1
  89. package/dest/entrypoints/server/utils.d.ts +1 -1
  90. package/dest/entrypoints/server/utils.d.ts.map +1 -1
  91. package/dest/entrypoints/server/utils.js +3 -1
  92. package/dest/error_enriching.js +1 -1
  93. package/dest/hooks/execution_hooks.d.ts +16 -7
  94. package/dest/hooks/execution_hooks.d.ts.map +1 -1
  95. package/dest/hooks/execution_hooks.js +3 -3
  96. package/dest/hooks/index.d.ts +3 -3
  97. package/dest/hooks/index.d.ts.map +1 -1
  98. package/dest/hooks/resolve_tagging_secret_strategy.d.ts +41 -0
  99. package/dest/hooks/resolve_tagging_secret_strategy.d.ts.map +1 -0
  100. package/dest/hooks/resolve_tagging_secret_strategy.js +3 -0
  101. package/dest/logs/log_service.d.ts +6 -6
  102. package/dest/logs/log_service.d.ts.map +1 -1
  103. package/dest/logs/log_service.js +62 -28
  104. package/dest/messages/tx_resolver_service.d.ts +17 -0
  105. package/dest/messages/tx_resolver_service.d.ts.map +1 -0
  106. package/dest/messages/{message_context_service.js → tx_resolver_service.js} +8 -8
  107. package/dest/oracle_version.d.ts +2 -2
  108. package/dest/oracle_version.js +2 -2
  109. package/dest/private_kernel/hints/test_utils.js +1 -1
  110. package/dest/pxe.d.ts +46 -19
  111. package/dest/pxe.d.ts.map +1 -1
  112. package/dest/pxe.js +104 -52
  113. package/dest/storage/allowed_scopes.d.ts +6 -0
  114. package/dest/storage/allowed_scopes.d.ts.map +1 -0
  115. package/dest/storage/allowed_scopes.js +7 -0
  116. package/dest/storage/backwards_compatibility_tests/schema_tests.d.ts +1 -1
  117. package/dest/storage/backwards_compatibility_tests/schema_tests.d.ts.map +1 -1
  118. package/dest/storage/backwards_compatibility_tests/schema_tests.js +86 -33
  119. package/dest/storage/capsule_store/capsule_service.d.ts +1 -1
  120. package/dest/storage/capsule_store/capsule_service.d.ts.map +1 -1
  121. package/dest/storage/capsule_store/capsule_service.js +6 -9
  122. package/dest/storage/contract_store/contract_store.js +2 -2
  123. package/dest/storage/fact_store/fact_service.d.ts +20 -0
  124. package/dest/storage/fact_store/fact_service.d.ts.map +1 -0
  125. package/dest/storage/fact_store/fact_service.js +30 -0
  126. package/dest/storage/fact_store/fact_store.d.ts +95 -0
  127. package/dest/storage/fact_store/fact_store.d.ts.map +1 -0
  128. package/dest/storage/fact_store/fact_store.js +408 -0
  129. package/dest/storage/fact_store/fact_store_keys.d.ts +34 -0
  130. package/dest/storage/fact_store/fact_store_keys.d.ts.map +1 -0
  131. package/dest/storage/fact_store/fact_store_keys.js +50 -0
  132. package/dest/storage/fact_store/index.d.ts +5 -0
  133. package/dest/storage/fact_store/index.d.ts.map +1 -0
  134. package/dest/storage/fact_store/index.js +3 -0
  135. package/dest/storage/fact_store/stored_fact.d.ts +32 -0
  136. package/dest/storage/fact_store/stored_fact.d.ts.map +1 -0
  137. package/dest/storage/fact_store/stored_fact.js +64 -0
  138. package/dest/storage/index.d.ts +2 -1
  139. package/dest/storage/index.d.ts.map +1 -1
  140. package/dest/storage/index.js +1 -0
  141. package/dest/storage/metadata.d.ts +1 -1
  142. package/dest/storage/metadata.js +1 -1
  143. package/dest/storage/open_pxe_stores.d.ts +5 -3
  144. package/dest/storage/open_pxe_stores.d.ts.map +1 -1
  145. package/dest/storage/open_pxe_stores.js +5 -3
  146. package/dest/storage/tagging_store/index.d.ts +2 -2
  147. package/dest/storage/tagging_store/index.d.ts.map +1 -1
  148. package/dest/storage/tagging_store/index.js +1 -1
  149. package/dest/storage/tagging_store/tagging_secret_sources_store.d.ts +40 -0
  150. package/dest/storage/tagging_store/tagging_secret_sources_store.d.ts.map +1 -0
  151. package/dest/storage/tagging_store/tagging_secret_sources_store.js +92 -0
  152. package/package.json +17 -17
  153. package/src/block_synchronizer/block_stream_source.ts +6 -45
  154. package/src/block_synchronizer/block_synchronizer.ts +56 -23
  155. package/src/config/index.ts +1 -0
  156. package/src/contract_function_simulator/contract_function_simulator.ts +32 -31
  157. package/src/contract_function_simulator/index.ts +17 -8
  158. package/src/contract_function_simulator/noir-structs/bounded_vec.ts +12 -24
  159. package/src/contract_function_simulator/noir-structs/contract_class_log_data.ts +9 -0
  160. package/src/contract_function_simulator/noir-structs/embedded_curve_point.ts +4 -0
  161. package/src/contract_function_simulator/noir-structs/event_validation_request.ts +1 -1
  162. package/src/contract_function_simulator/noir-structs/fact.ts +13 -0
  163. package/src/contract_function_simulator/noir-structs/fact_collection.ts +59 -0
  164. package/src/contract_function_simulator/noir-structs/log_retrieval_request.ts +20 -46
  165. package/src/contract_function_simulator/noir-structs/log_retrieval_response.ts +7 -60
  166. package/src/contract_function_simulator/noir-structs/note_validation_request.ts +2 -2
  167. package/src/contract_function_simulator/noir-structs/option.ts +17 -11
  168. package/src/contract_function_simulator/noir-structs/origin_block.ts +8 -0
  169. package/src/contract_function_simulator/noir-structs/provided_secret.ts +3 -14
  170. package/src/contract_function_simulator/noir-structs/resolved_tagging_strategy.ts +45 -0
  171. package/src/contract_function_simulator/noir-structs/resolved_tx.ts +53 -0
  172. package/src/contract_function_simulator/noir-structs/tx_effect_data.ts +15 -0
  173. package/src/contract_function_simulator/noir-structs/utility_context.ts +5 -17
  174. package/src/contract_function_simulator/oracle/message_load_oracle_inputs.ts +6 -21
  175. package/src/contract_function_simulator/oracle/oracle_registry.ts +87 -79
  176. package/src/contract_function_simulator/oracle/oracle_type_mappings.ts +641 -247
  177. package/src/contract_function_simulator/oracle/private_execution_oracle.ts +94 -14
  178. package/src/contract_function_simulator/oracle/utility_execution_oracle.ts +206 -66
  179. package/src/contract_sync/helpers.ts +11 -18
  180. package/src/entrypoints/client/bundle/utils.ts +1 -0
  181. package/src/entrypoints/client/lazy/utils.ts +1 -0
  182. package/src/entrypoints/pxe_creation_options.ts +7 -1
  183. package/src/entrypoints/server/index.ts +0 -1
  184. package/src/entrypoints/server/utils.ts +3 -1
  185. package/src/error_enriching.ts +1 -1
  186. package/src/hooks/execution_hooks.ts +17 -8
  187. package/src/hooks/index.ts +6 -2
  188. package/src/hooks/resolve_tagging_secret_strategy.ts +46 -0
  189. package/src/logs/log_service.ts +71 -37
  190. package/src/messages/{message_context_service.ts → tx_resolver_service.ts} +16 -9
  191. package/src/oracle_version.ts +2 -2
  192. package/src/private_kernel/hints/test_utils.ts +1 -1
  193. package/src/pxe.ts +150 -54
  194. package/src/storage/allowed_scopes.ts +14 -0
  195. package/src/storage/backwards_compatibility_tests/__snapshots__/FactStore.json +40 -0
  196. package/src/storage/backwards_compatibility_tests/__snapshots__/L2TipsKVStore.json +1 -1
  197. package/src/storage/backwards_compatibility_tests/__snapshots__/TaggingSecretSourcesStore.json +30 -0
  198. package/src/storage/backwards_compatibility_tests/__snapshots__/opened_stores.json +21 -5
  199. package/src/storage/backwards_compatibility_tests/schema_tests.ts +88 -33
  200. package/src/storage/capsule_store/capsule_service.ts +8 -13
  201. package/src/storage/contract_store/contract_store.ts +2 -2
  202. package/src/storage/fact_store/fact_service.ts +45 -0
  203. package/src/storage/fact_store/fact_store.ts +487 -0
  204. package/src/storage/fact_store/fact_store_keys.ts +75 -0
  205. package/src/storage/fact_store/index.ts +4 -0
  206. package/src/storage/fact_store/stored_fact.ts +80 -0
  207. package/src/storage/index.ts +1 -0
  208. package/src/storage/metadata.ts +1 -1
  209. package/src/storage/open_pxe_stores.ts +6 -3
  210. package/src/storage/tagging_store/index.ts +1 -1
  211. package/src/storage/tagging_store/tagging_secret_sources_store.ts +117 -0
  212. package/dest/messages/message_context_service.d.ts +0 -17
  213. package/dest/messages/message_context_service.d.ts.map +0 -1
  214. package/dest/storage/tagging_store/sender_address_book_store.d.ts +0 -14
  215. package/dest/storage/tagging_store/sender_address_book_store.d.ts.map +0 -1
  216. package/dest/storage/tagging_store/sender_address_book_store.js +0 -36
  217. package/src/storage/backwards_compatibility_tests/__snapshots__/SenderAddressBookStore.json +0 -16
  218. package/src/storage/tagging_store/sender_address_book_store.ts +0 -48
@@ -1,23 +1,22 @@
1
- import { BLOCK_HEADER_LENGTH, KEY_VALIDATION_REQUEST_LENGTH, MAX_CONTRACT_CLASS_LOGS_PER_TX, MAX_L2_TO_L1_MSGS_PER_TX, MAX_NOTE_HASHES_PER_TX, MAX_NULLIFIERS_PER_TX, MAX_PRIVATE_LOGS_PER_TX, MAX_TOTAL_PUBLIC_DATA_UPDATE_REQUESTS_PER_TX } from '@aztec/constants';
1
+ import { CONTRACT_CLASS_LOG_SIZE_IN_FIELDS, FLAT_PUBLIC_LOGS_PAYLOAD_LENGTH, L1_TO_L2_MSG_TREE_HEIGHT, MAX_CONTRACT_CLASS_LOGS_PER_TX, MAX_L2_TO_L1_MSGS_PER_TX, MAX_NOTE_HASHES_PER_TX, MAX_NULLIFIERS_PER_TX, MAX_PRIVATE_LOGS_PER_TX, MAX_TOTAL_PUBLIC_DATA_UPDATE_REQUESTS_PER_TX, NULLIFIER_TREE_HEIGHT, PRIVATE_LOG_CIPHERTEXT_LEN, PRIVATE_LOG_SIZE_IN_FIELDS, PUBLIC_DATA_TREE_HEIGHT } from '@aztec/constants';
2
2
  import { BlockNumber } from '@aztec/foundation/branded-types';
3
3
  import { padArrayEnd } from '@aztec/foundation/collection';
4
4
  import { Fr } from '@aztec/foundation/curves/bn254';
5
- import { Point } from '@aztec/foundation/curves/grumpkin';
5
+ import { EthAddress } from '@aztec/foundation/eth-address';
6
+ import { FieldReader } from '@aztec/foundation/serialize';
6
7
  import { fromUintArray } from '@aztec/simulator/client';
7
8
  import { FunctionSelector, NoteSelector } from '@aztec/stdlib/abi';
8
- import { PublicDataWrite } from '@aztec/stdlib/avm';
9
9
  import { AztecAddress } from '@aztec/stdlib/aztec-address';
10
10
  import { BlockHash } from '@aztec/stdlib/block';
11
- import { KeyValidationRequest } from '@aztec/stdlib/kernel';
12
- import { ContractClassLog, ContractClassLogFields, FlatPublicLogs, PrivateLog, Tag, appTaggingSecretKindFromDeliveryMode } from '@aztec/stdlib/logs';
13
- import { BlockHeader, TxHash } from '@aztec/stdlib/tx';
11
+ import { Tag, appTaggingSecretKindFromDeliveryMode } from '@aztec/stdlib/logs';
12
+ import { TxHash } from '@aztec/stdlib/tx';
14
13
  import { BoundedVec } from '../noir-structs/bounded_vec.js';
15
14
  import { EphemeralArray } from '../noir-structs/ephemeral_array.js';
16
15
  import { EventValidationRequest } from '../noir-structs/event_validation_request.js';
17
- import { LogRetrievalRequest } from '../noir-structs/log_retrieval_request.js';
16
+ import { logSourceFromField } from '../noir-structs/log_retrieval_request.js';
18
17
  import { NoteValidationRequest } from '../noir-structs/note_validation_request.js';
19
18
  import { Option } from '../noir-structs/option.js';
20
- import { ProvidedSecret } from '../noir-structs/provided_secret.js';
19
+ import { resolvedTaggingStrategyFromFields, resolvedTaggingStrategyToFields } from '../noir-structs/resolved_tagging_strategy.js';
21
20
  import { packAsHintedNote } from './note_packing_utils.js';
22
21
  /**
23
22
  * Asserts that every reader was fully consumed by a deserialization, throwing on leftover fields.
@@ -36,9 +35,11 @@ export const FIELD = {
36
35
  ]
37
36
  },
38
37
  deserialization: {
39
- fn: ([reader])=>reader.readField(),
40
- slots: 1
41
- }
38
+ fn: ([reader])=>reader.readField()
39
+ },
40
+ shape: [
41
+ 'scalar'
42
+ ]
42
43
  };
43
44
  export const BOOL = {
44
45
  serialization: {
@@ -47,9 +48,11 @@ export const BOOL = {
47
48
  ]
48
49
  },
49
50
  deserialization: {
50
- fn: ([reader])=>!reader.readField().isZero(),
51
- slots: 1
52
- }
51
+ fn: ([reader])=>!reader.readField().isZero()
52
+ },
53
+ shape: [
54
+ 'scalar'
55
+ ]
53
56
  };
54
57
  export const U32 = {
55
58
  serialization: {
@@ -64,9 +67,11 @@ export const U32 = {
64
67
  throw new Error(`U32 overflow: value ${value} exceeds u32 max (${0xffffffffn})`);
65
68
  }
66
69
  return Number(value);
67
- },
68
- slots: 1
69
- }
70
+ }
71
+ },
72
+ shape: [
73
+ 'scalar'
74
+ ]
70
75
  };
71
76
  export const BLOCK_NUMBER = {
72
77
  serialization: {
@@ -75,9 +80,11 @@ export const BLOCK_NUMBER = {
75
80
  ]
76
81
  },
77
82
  deserialization: {
78
- fn: ([reader])=>BlockNumber(reader.readField().toNumber()),
79
- slots: 1
80
- }
83
+ fn: ([reader])=>BlockNumber(reader.readField().toNumber())
84
+ },
85
+ shape: [
86
+ 'scalar'
87
+ ]
81
88
  };
82
89
  /** A u8 byte: serializes to a single Fr; deserializes from a single Fr to a number in [0, 255]. */ export const BYTE = {
83
90
  serialization: {
@@ -92,16 +99,30 @@ export const BLOCK_NUMBER = {
92
99
  throw new Error(`BYTE overflow: value ${value} exceeds u8 max (255)`);
93
100
  }
94
101
  return Number(value);
95
- },
96
- slots: 1
97
- }
102
+ }
103
+ },
104
+ shape: [
105
+ 'scalar'
106
+ ]
98
107
  };
99
108
  // Noir passes `MessageDelivery` onchain variants here.
100
109
  export const DELIVERY_MODE = {
101
110
  deserialization: {
102
- fn: (readers)=>appTaggingSecretKindFromDeliveryMode(BYTE.deserialization.fn(readers)),
103
- slots: BYTE.deserialization.slots
104
- }
111
+ fn: (readers)=>appTaggingSecretKindFromDeliveryMode(BYTE.deserialization.fn(readers))
112
+ },
113
+ shape: BYTE.shape
114
+ };
115
+ export const RESOLVED_TAGGING_STRATEGY = {
116
+ serialization: {
117
+ fn: (resolved)=>resolvedTaggingStrategyToFields(resolved)
118
+ },
119
+ deserialization: {
120
+ fn: ([kindReader, secretReader])=>resolvedTaggingStrategyFromFields(kindReader.readField().toNumber(), secretReader.readField())
121
+ },
122
+ shape: [
123
+ 'scalar',
124
+ 'scalar'
125
+ ]
105
126
  };
106
127
  export const BIGINT = {
107
128
  serialization: {
@@ -110,9 +131,11 @@ export const BIGINT = {
110
131
  ]
111
132
  },
112
133
  deserialization: {
113
- fn: ([reader])=>reader.readField().toBigInt(),
114
- slots: 1
115
- }
134
+ fn: ([reader])=>reader.readField().toBigInt()
135
+ },
136
+ shape: [
137
+ 'scalar'
138
+ ]
116
139
  };
117
140
  /** Reads every field in the slot as a UTF-8 character code. */ export const STR = {
118
141
  serialization: {
@@ -127,9 +150,11 @@ export const BIGINT = {
127
150
  chars.push(String.fromCharCode(reader.readField().toNumber()));
128
151
  }
129
152
  return chars.join('');
130
- },
131
- slots: 1
132
- }
153
+ }
154
+ },
155
+ shape: [
156
+ 'variable'
157
+ ]
133
158
  };
134
159
  export const AZTEC_ADDRESS = {
135
160
  serialization: {
@@ -138,9 +163,11 @@ export const AZTEC_ADDRESS = {
138
163
  ]
139
164
  },
140
165
  deserialization: {
141
- fn: ([reader])=>AztecAddress.fromField(reader.readField()),
142
- slots: 1
143
- }
166
+ fn: ([reader])=>AztecAddress.fromFieldUnsafe(reader.readField())
167
+ },
168
+ shape: [
169
+ 'scalar'
170
+ ]
144
171
  };
145
172
  export const BLOCK_HASH = {
146
173
  serialization: {
@@ -149,9 +176,11 @@ export const BLOCK_HASH = {
149
176
  ]
150
177
  },
151
178
  deserialization: {
152
- fn: ([reader])=>new BlockHash(reader.readField()),
153
- slots: 1
154
- }
179
+ fn: ([reader])=>new BlockHash(reader.readField())
180
+ },
181
+ shape: [
182
+ 'scalar'
183
+ ]
155
184
  };
156
185
  export const FUNCTION_SELECTOR = {
157
186
  serialization: {
@@ -160,9 +189,11 @@ export const FUNCTION_SELECTOR = {
160
189
  ]
161
190
  },
162
191
  deserialization: {
163
- fn: ([reader])=>FunctionSelector.fromField(reader.readField()),
164
- slots: 1
165
- }
192
+ fn: ([reader])=>FunctionSelector.fromField(reader.readField())
193
+ },
194
+ shape: [
195
+ 'scalar'
196
+ ]
166
197
  };
167
198
  export const NOTE_SELECTOR = {
168
199
  serialization: {
@@ -171,9 +202,11 @@ export const NOTE_SELECTOR = {
171
202
  ]
172
203
  },
173
204
  deserialization: {
174
- fn: ([reader])=>NoteSelector.fromField(reader.readField()),
175
- slots: 1
176
- }
205
+ fn: ([reader])=>NoteSelector.fromField(reader.readField())
206
+ },
207
+ shape: [
208
+ 'scalar'
209
+ ]
177
210
  };
178
211
  export const TX_HASH = {
179
212
  serialization: {
@@ -182,147 +215,465 @@ export const TX_HASH = {
182
215
  ]
183
216
  },
184
217
  deserialization: {
185
- fn: ([reader])=>TxHash.fromField(reader.readField()),
186
- slots: 1
187
- }
218
+ fn: ([reader])=>TxHash.fromField(reader.readField())
219
+ },
220
+ shape: [
221
+ 'scalar'
222
+ ]
188
223
  };
189
- export const TAG = {
224
+ const TAG = {
190
225
  serialization: {
191
226
  fn: (v)=>[
192
227
  v.value
193
228
  ]
194
229
  },
195
230
  deserialization: {
196
- fn: ([reader])=>new Tag(reader.readField()),
197
- slots: 1
198
- }
231
+ fn: ([reader])=>new Tag(reader.readField())
232
+ },
233
+ shape: [
234
+ 'scalar'
235
+ ]
199
236
  };
200
- export const POINT = {
201
- serialization: {
202
- fn: (p)=>[
203
- p.toFields()
204
- ]
237
+ export const POINT = STRUCT([
238
+ {
239
+ name: 'x',
240
+ type: FIELD
205
241
  },
206
- deserialization: {
207
- fn: ([reader])=>Point.fromFields([
208
- reader.readField(),
209
- reader.readField()
210
- ]),
211
- slots: 1
242
+ {
243
+ name: 'y',
244
+ type: FIELD
212
245
  }
213
- };
214
- // ─── Struct Type Mappings ────────────────────────────────────────────────────
215
- export const BLOCK_HEADER = {
246
+ ]);
247
+ const LOG_SOURCE = {
216
248
  serialization: {
217
- fn: (v)=>v.toFields()
249
+ fn: (v)=>[
250
+ new Fr(v)
251
+ ]
218
252
  },
219
253
  deserialization: {
220
- fn: ([reader])=>BlockHeader.fromFields(reader.readFieldArray(BLOCK_HEADER_LENGTH)),
221
- slots: 1
222
- }
254
+ fn: ([reader])=>logSourceFromField(reader.readField())
255
+ },
256
+ shape: [
257
+ 'scalar'
258
+ ]
223
259
  };
224
- export const KEY_VALIDATION_REQUEST = {
260
+ export const ETH_ADDRESS = {
225
261
  serialization: {
226
- fn: (v)=>v.toFields()
262
+ fn: (v)=>[
263
+ v.toField()
264
+ ]
227
265
  },
228
266
  deserialization: {
229
- fn: ([reader])=>KeyValidationRequest.fromFields(reader.readFieldArray(KEY_VALIDATION_REQUEST_LENGTH)),
230
- slots: 1
231
- }
267
+ fn: ([reader])=>EthAddress.fromField(reader.readField())
268
+ },
269
+ shape: [
270
+ 'scalar'
271
+ ]
232
272
  };
233
- export const CONTRACT_INSTANCE = {
273
+ const SLOT_NUMBER = {
234
274
  serialization: {
235
275
  fn: (v)=>[
236
- v.salt,
237
- v.deployer.toField(),
238
- v.currentContractClassId,
239
- v.initializationHash,
240
- v.immutablesHash,
241
- ...v.publicKeys.toFields()
276
+ new Fr(v)
242
277
  ]
243
- }
278
+ },
279
+ shape: [
280
+ 'scalar'
281
+ ]
244
282
  };
245
- export const NULLIFIER_MEMBERSHIP_WITNESS = {
246
- serialization: {
247
- fn: (w)=>w.toNoirRepresentation().map((slot)=>Array.isArray(slot) ? slot.map((s)=>Fr.fromString(s)) : Fr.fromString(slot))
283
+ const APPEND_ONLY_TREE_SNAPSHOT = STRUCT([
284
+ {
285
+ name: 'root',
286
+ type: FIELD
287
+ },
288
+ {
289
+ name: 'nextAvailableLeafIndex',
290
+ type: U32
248
291
  }
249
- };
250
- export const PUBLIC_DATA_WITNESS = {
251
- serialization: {
252
- fn: (w)=>w.toNoirRepresentation().map((slot)=>Array.isArray(slot) ? slot.map((s)=>Fr.fromString(s)) : Fr.fromString(slot))
292
+ ]);
293
+ const PARTIAL_STATE_REFERENCE = STRUCT([
294
+ {
295
+ name: 'noteHashTree',
296
+ type: APPEND_ONLY_TREE_SNAPSHOT
297
+ },
298
+ {
299
+ name: 'nullifierTree',
300
+ type: APPEND_ONLY_TREE_SNAPSHOT
301
+ },
302
+ {
303
+ name: 'publicDataTree',
304
+ type: APPEND_ONLY_TREE_SNAPSHOT
253
305
  }
254
- };
255
- export const MESSAGE_LOAD_ORACLE_INPUTS = {
256
- serialization: {
257
- fn: (m)=>m.toNoirRepresentation().map((slot)=>Array.isArray(slot) ? slot.map((s)=>Fr.fromString(s)) : Fr.fromString(slot))
306
+ ]);
307
+ const STATE_REFERENCE = STRUCT([
308
+ {
309
+ name: 'l1ToL2MessageTree',
310
+ type: APPEND_ONLY_TREE_SNAPSHOT
311
+ },
312
+ {
313
+ name: 'partial',
314
+ type: PARTIAL_STATE_REFERENCE
258
315
  }
259
- };
260
- export const UTILITY_CONTEXT = {
261
- serialization: {
262
- fn: (ctx)=>[
263
- ...ctx.blockHeader.toFields(),
264
- ctx.contractAddress.toField()
265
- ]
316
+ ]);
317
+ const GAS_FEES = STRUCT([
318
+ {
319
+ name: 'feePerDaGas',
320
+ type: BIGINT
321
+ },
322
+ {
323
+ name: 'feePerL2Gas',
324
+ type: BIGINT
266
325
  }
267
- };
268
- export const CALL_PRIVATE_RESULT = {
269
- serialization: {
270
- fn: (v)=>[
271
- [
272
- v.endSideEffectCounter,
273
- v.returnsHash
274
- ]
275
- ]
326
+ ]);
327
+ const GLOBAL_VARIABLES = STRUCT([
328
+ {
329
+ name: 'chainId',
330
+ type: FIELD
331
+ },
332
+ {
333
+ name: 'version',
334
+ type: FIELD
335
+ },
336
+ {
337
+ name: 'blockNumber',
338
+ type: BLOCK_NUMBER
339
+ },
340
+ {
341
+ name: 'slotNumber',
342
+ type: SLOT_NUMBER
343
+ },
344
+ {
345
+ name: 'timestamp',
346
+ type: BIGINT
347
+ },
348
+ {
349
+ name: 'coinbase',
350
+ type: ETH_ADDRESS
351
+ },
352
+ {
353
+ name: 'feeRecipient',
354
+ type: AZTEC_ADDRESS
355
+ },
356
+ {
357
+ name: 'gasFees',
358
+ type: GAS_FEES
276
359
  }
277
- };
278
- export const PUBLIC_KEYS_AND_PARTIAL_ADDRESS = {
360
+ ]);
361
+ export const BLOCK_HEADER = STRUCT([
362
+ {
363
+ name: 'lastArchive',
364
+ type: APPEND_ONLY_TREE_SNAPSHOT
365
+ },
366
+ {
367
+ name: 'state',
368
+ type: STATE_REFERENCE
369
+ },
370
+ {
371
+ name: 'spongeBlobHash',
372
+ type: FIELD
373
+ },
374
+ {
375
+ name: 'globalVariables',
376
+ type: GLOBAL_VARIABLES
377
+ },
378
+ {
379
+ name: 'totalFees',
380
+ type: FIELD
381
+ },
382
+ {
383
+ name: 'totalManaUsed',
384
+ type: FIELD
385
+ }
386
+ ]);
387
+ export const KEY_VALIDATION_REQUEST = STRUCT([
388
+ {
389
+ name: 'pkMHash',
390
+ type: FIELD
391
+ },
392
+ {
393
+ name: 'skApp',
394
+ type: FIELD
395
+ }
396
+ ]);
397
+ const PUBLIC_KEYS = STRUCT([
398
+ {
399
+ name: 'npkMHash',
400
+ type: FIELD
401
+ },
402
+ {
403
+ name: 'ivpkM',
404
+ type: POINT
405
+ },
406
+ {
407
+ name: 'ovpkMHash',
408
+ type: FIELD
409
+ },
410
+ {
411
+ name: 'tpkMHash',
412
+ type: FIELD
413
+ },
414
+ {
415
+ name: 'mspkMHash',
416
+ type: FIELD
417
+ },
418
+ {
419
+ name: 'fbpkMHash',
420
+ type: FIELD
421
+ }
422
+ ]);
423
+ export const CONTRACT_INSTANCE = STRUCT([
424
+ {
425
+ name: 'salt',
426
+ type: FIELD
427
+ },
428
+ {
429
+ name: 'deployer',
430
+ type: AZTEC_ADDRESS
431
+ },
432
+ // Note that the nr side of this struct does not contain the current class, only original
433
+ {
434
+ name: 'originalContractClassId',
435
+ type: FIELD
436
+ },
437
+ {
438
+ name: 'initializationHash',
439
+ type: FIELD
440
+ },
441
+ {
442
+ name: 'immutablesHash',
443
+ type: FIELD
444
+ },
445
+ {
446
+ name: 'publicKeys',
447
+ type: PUBLIC_KEYS
448
+ }
449
+ ]);
450
+ const NULLIFIER_LEAF = STRUCT([
451
+ {
452
+ name: 'nullifier',
453
+ type: FIELD
454
+ }
455
+ ]);
456
+ const NULLIFIER_LEAF_PREIMAGE = STRUCT([
457
+ {
458
+ name: 'leaf',
459
+ type: NULLIFIER_LEAF
460
+ },
461
+ {
462
+ name: 'nextKey',
463
+ type: FIELD
464
+ },
465
+ {
466
+ name: 'nextIndex',
467
+ type: BIGINT
468
+ }
469
+ ]);
470
+ export const NULLIFIER_MEMBERSHIP_WITNESS = STRUCT([
471
+ {
472
+ name: 'leafPreimage',
473
+ type: NULLIFIER_LEAF_PREIMAGE
474
+ },
475
+ {
476
+ name: 'index',
477
+ type: BIGINT
478
+ },
479
+ {
480
+ name: 'siblingPath',
481
+ type: SIBLING_PATH(NULLIFIER_TREE_HEIGHT)
482
+ }
483
+ ]);
484
+ const PUBLIC_DATA_LEAF = STRUCT([
485
+ {
486
+ name: 'slot',
487
+ type: FIELD
488
+ },
489
+ {
490
+ name: 'value',
491
+ type: FIELD
492
+ }
493
+ ]);
494
+ const PUBLIC_DATA_LEAF_PREIMAGE = STRUCT([
495
+ {
496
+ name: 'leaf',
497
+ type: PUBLIC_DATA_LEAF
498
+ },
499
+ {
500
+ name: 'nextKey',
501
+ type: FIELD
502
+ },
503
+ {
504
+ name: 'nextIndex',
505
+ type: BIGINT
506
+ }
507
+ ]);
508
+ export const PUBLIC_DATA_WITNESS = STRUCT([
509
+ {
510
+ name: 'index',
511
+ type: BIGINT
512
+ },
513
+ {
514
+ name: 'leafPreimage',
515
+ type: PUBLIC_DATA_LEAF_PREIMAGE
516
+ },
517
+ {
518
+ name: 'siblingPath',
519
+ type: SIBLING_PATH(PUBLIC_DATA_TREE_HEIGHT)
520
+ }
521
+ ]);
522
+ export const MESSAGE_LOAD_ORACLE_INPUTS = STRUCT([
523
+ {
524
+ name: 'index',
525
+ type: BIGINT
526
+ },
527
+ {
528
+ name: 'siblingPath',
529
+ type: SIBLING_PATH(L1_TO_L2_MSG_TREE_HEIGHT)
530
+ }
531
+ ]);
532
+ export const UTILITY_CONTEXT = STRUCT([
533
+ {
534
+ name: 'blockHeader',
535
+ type: BLOCK_HEADER
536
+ },
537
+ {
538
+ name: 'contractAddress',
539
+ type: AZTEC_ADDRESS
540
+ },
541
+ {
542
+ name: 'msgSender',
543
+ type: AZTEC_ADDRESS
544
+ }
545
+ ]);
546
+ export const CALL_PRIVATE_RESULT = STRUCT([
547
+ {
548
+ name: 'endSideEffectCounter',
549
+ type: FIELD
550
+ },
551
+ {
552
+ name: 'returnsHash',
553
+ type: FIELD
554
+ }
555
+ ]);
556
+ export const PUBLIC_KEYS_AND_PARTIAL_ADDRESS = STRUCT([
557
+ {
558
+ name: 'publicKeys',
559
+ type: PUBLIC_KEYS
560
+ },
561
+ {
562
+ name: 'partialAddress',
563
+ type: FIELD
564
+ }
565
+ ]);
566
+ export const CONTRACT_CLASS_LOG = STRUCT([
567
+ {
568
+ name: 'contractAddress',
569
+ type: AZTEC_ADDRESS
570
+ },
571
+ {
572
+ name: 'fields',
573
+ type: FIXED_ARRAY(FIELD, CONTRACT_CLASS_LOG_SIZE_IN_FIELDS)
574
+ },
575
+ {
576
+ name: 'emittedLength',
577
+ type: U32
578
+ }
579
+ ]);
580
+ const REVERT_CODE = {
279
581
  serialization: {
280
- fn: (v)=>[
281
- [
282
- ...v.publicKeys.toFields(),
283
- v.partialAddress
284
- ]
582
+ fn: (rc)=>[
583
+ rc.toField()
285
584
  ]
286
- }
585
+ },
586
+ shape: [
587
+ 'scalar'
588
+ ]
287
589
  };
288
- export const CONTRACT_CLASS_LOG_INPUT = {
289
- deserialization: {
290
- fn: ([addrReader, fieldsReader, lengthReader])=>{
291
- const addr = AztecAddress.fromField(addrReader.readField());
292
- const fields = new ContractClassLogFields([
293
- ...fieldsReader.readFieldArray(fieldsReader.remainingFields())
294
- ]);
295
- const length = lengthReader.readField().toNumber();
296
- return new ContractClassLog(addr, fields, length);
297
- },
298
- // ContractClassLog input occupies 3 ACVM slots: [contractAddress], [message fields...], [length].
299
- slots: 3
590
+ const PUBLIC_DATA_WRITE = STRUCT([
591
+ {
592
+ name: 'leafSlot',
593
+ type: FIELD
594
+ },
595
+ {
596
+ name: 'value',
597
+ type: FIELD
300
598
  }
301
- };
302
- export const TX_EFFECT = {
303
- serialization: {
304
- fn: (effect)=>{
305
- const flatPublicLogs = FlatPublicLogs.fromLogs(effect.publicLogs);
306
- return [
307
- effect.revertCode.toField(),
308
- effect.txHash.hash,
309
- effect.transactionFee,
310
- padArrayEnd(effect.noteHashes, Fr.ZERO, MAX_NOTE_HASHES_PER_TX),
311
- padArrayEnd(effect.nullifiers, Fr.ZERO, MAX_NULLIFIERS_PER_TX),
312
- padArrayEnd(effect.l2ToL1Msgs, Fr.ZERO, MAX_L2_TO_L1_MSGS_PER_TX),
313
- padArrayEnd(effect.publicDataWrites, PublicDataWrite.empty(), MAX_TOTAL_PUBLIC_DATA_UPDATE_REQUESTS_PER_TX).flatMap((w)=>w.toFields()),
314
- padArrayEnd(effect.privateLogs, PrivateLog.empty(), MAX_PRIVATE_LOGS_PER_TX).flatMap((l)=>l.toFields()),
315
- new Fr(flatPublicLogs.length),
316
- flatPublicLogs.payload,
317
- padArrayEnd(effect.contractClassLogs, ContractClassLog.empty(), MAX_CONTRACT_CLASS_LOGS_PER_TX).flatMap((l)=>[
318
- ...l.fields.toFields(),
319
- new Fr(l.emittedLength),
320
- l.contractAddress.toField()
321
- ])
322
- ];
323
- }
599
+ ]);
600
+ const PRIVATE_LOG = STRUCT([
601
+ {
602
+ name: 'fields',
603
+ type: FIXED_ARRAY(FIELD, PRIVATE_LOG_SIZE_IN_FIELDS)
604
+ },
605
+ {
606
+ name: 'emittedLength',
607
+ type: U32
324
608
  }
325
- };
609
+ ]);
610
+ const FLAT_PUBLIC_LOGS = STRUCT([
611
+ {
612
+ name: 'length',
613
+ type: U32
614
+ },
615
+ {
616
+ name: 'payload',
617
+ type: FIXED_ARRAY(FIELD, FLAT_PUBLIC_LOGS_PAYLOAD_LENGTH)
618
+ }
619
+ ]);
620
+ const CONTRACT_CLASS_LOG_ENTRY = STRUCT([
621
+ {
622
+ name: 'fields',
623
+ type: FIXED_ARRAY(FIELD, CONTRACT_CLASS_LOG_SIZE_IN_FIELDS)
624
+ },
625
+ {
626
+ name: 'emittedLength',
627
+ type: U32
628
+ },
629
+ {
630
+ name: 'contractAddress',
631
+ type: AZTEC_ADDRESS
632
+ }
633
+ ]);
634
+ const CONTRACT_CLASS_LOGS = FIXED_ARRAY(CONTRACT_CLASS_LOG_ENTRY, MAX_CONTRACT_CLASS_LOGS_PER_TX);
635
+ export const TX_EFFECT = STRUCT([
636
+ {
637
+ name: 'revertCode',
638
+ type: REVERT_CODE
639
+ },
640
+ {
641
+ name: 'txHash',
642
+ type: TX_HASH
643
+ },
644
+ {
645
+ name: 'transactionFee',
646
+ type: FIELD
647
+ },
648
+ {
649
+ name: 'noteHashes',
650
+ type: FIXED_ARRAY(FIELD, MAX_NOTE_HASHES_PER_TX)
651
+ },
652
+ {
653
+ name: 'nullifiers',
654
+ type: FIXED_ARRAY(FIELD, MAX_NULLIFIERS_PER_TX)
655
+ },
656
+ {
657
+ name: 'l2ToL1Msgs',
658
+ type: FIXED_ARRAY(FIELD, MAX_L2_TO_L1_MSGS_PER_TX)
659
+ },
660
+ {
661
+ name: 'publicDataWrites',
662
+ type: FIXED_ARRAY(PUBLIC_DATA_WRITE, MAX_TOTAL_PUBLIC_DATA_UPDATE_REQUESTS_PER_TX)
663
+ },
664
+ {
665
+ name: 'privateLogs',
666
+ type: FIXED_ARRAY(PRIVATE_LOG, MAX_PRIVATE_LOGS_PER_TX)
667
+ },
668
+ {
669
+ name: 'publicLogs',
670
+ type: FLAT_PUBLIC_LOGS
671
+ },
672
+ {
673
+ name: 'contractClassLogs',
674
+ type: CONTRACT_CLASS_LOGS
675
+ }
676
+ ]);
326
677
  export const NOTE = {
327
678
  serialization: {
328
679
  fn: (noteData)=>packAsHintedNote({
@@ -334,90 +685,244 @@ export const NOTE = {
334
685
  isPending: noteData.isPending,
335
686
  note: noteData.note
336
687
  })
337
- }
338
- };
339
- export const PENDING_TAGGED_LOG = {
340
- serialization: {
341
- fn: (log)=>[
342
- log.toFields()
343
- ]
344
- }
688
+ },
689
+ // A packed note is the note's (variable-count) field items followed by 6 metadata scalars, emitted as one field
690
+ // output per element. Its length depends on the note, so it is described as a single variable-width run.
691
+ shape: [
692
+ 'variable'
693
+ ]
345
694
  };
346
695
  export const NOTE_VALIDATION_REQUEST = {
347
696
  deserialization: {
348
- fn: ([reader])=>NoteValidationRequest.fromFields(reader),
349
- slots: 1
350
- }
697
+ fn: ([reader])=>NoteValidationRequest.fromFields(reader)
698
+ },
699
+ shape: [
700
+ 'variable'
701
+ ]
351
702
  };
352
703
  export const EVENT_VALIDATION_REQUEST = {
353
704
  deserialization: {
354
- fn: ([reader])=>EventValidationRequest.fromFields(reader),
355
- slots: 1
705
+ fn: ([reader])=>EventValidationRequest.fromFields(reader)
706
+ },
707
+ shape: [
708
+ 'variable'
709
+ ]
710
+ };
711
+ export const LOG_RETRIEVAL_REQUEST = STRUCT([
712
+ {
713
+ name: 'contractAddress',
714
+ type: AZTEC_ADDRESS
715
+ },
716
+ {
717
+ name: 'tag',
718
+ type: TAG
719
+ },
720
+ {
721
+ name: 'source',
722
+ type: LOG_SOURCE
723
+ },
724
+ {
725
+ name: 'fromBlock',
726
+ type: OPTION(BLOCK_NUMBER)
727
+ },
728
+ {
729
+ name: 'toBlock',
730
+ type: OPTION(BLOCK_NUMBER)
731
+ }
732
+ ]);
733
+ export const LOG_RETRIEVAL_RESPONSE = STRUCT([
734
+ {
735
+ name: 'logPayload',
736
+ type: FIXED_BOUNDED_VEC(FIELD, PRIVATE_LOG_CIPHERTEXT_LEN)
737
+ },
738
+ {
739
+ name: 'txHash',
740
+ type: TX_HASH
741
+ },
742
+ {
743
+ name: 'uniqueNoteHashesInTx',
744
+ type: FIXED_BOUNDED_VEC(FIELD, MAX_NOTE_HASHES_PER_TX)
745
+ },
746
+ {
747
+ name: 'firstNullifierInTx',
748
+ type: FIELD
749
+ }
750
+ ]);
751
+ export const MESSAGE_CONTEXT = STRUCT([
752
+ {
753
+ name: 'txHash',
754
+ type: TX_HASH
755
+ },
756
+ {
757
+ name: 'uniqueNoteHashesInTx',
758
+ type: FIXED_BOUNDED_VEC(FIELD, MAX_NOTE_HASHES_PER_TX)
759
+ },
760
+ {
761
+ name: 'firstNullifierInTx',
762
+ type: FIELD
356
763
  }
764
+ ]);
765
+ export const PENDING_TAGGED_LOG = STRUCT([
766
+ {
767
+ name: 'log',
768
+ type: FIXED_BOUNDED_VEC(FIELD, PRIVATE_LOG_SIZE_IN_FIELDS)
769
+ },
770
+ {
771
+ name: 'context',
772
+ type: MESSAGE_CONTEXT
773
+ }
774
+ ]);
775
+ // `ResolvedTx.toFields()` packs the whole struct into a single slot: txHash, the uniqueNoteHashesInTx BoundedVec
776
+ // (MAX_NOTE_HASHES_PER_TX storage fields + length), firstNullifierInTx, blockNumber and blockHash.
777
+ export const RESOLVED_TX = {
778
+ serialization: {
779
+ fn: (resolved)=>[
780
+ resolved.toFields()
781
+ ]
782
+ },
783
+ shape: [
784
+ {
785
+ len: MAX_NOTE_HASHES_PER_TX + 5
786
+ }
787
+ ]
357
788
  };
358
- export const LOG_RETRIEVAL_REQUEST = {
789
+ export const ORIGIN_BLOCK = {
359
790
  serialization: {
360
- fn: (req)=>[
361
- req.toFields()
791
+ fn: (ob)=>[
792
+ new Fr(ob.blockNumber),
793
+ ob.blockHash
362
794
  ]
363
795
  },
364
796
  deserialization: {
365
- fn: ([reader])=>LogRetrievalRequest.fromFields(reader),
366
- slots: 1
367
- }
797
+ fn: ([blockNumberReader, blockHashReader])=>({
798
+ blockNumber: blockNumberReader.readField().toNumber(),
799
+ blockHash: blockHashReader.readField()
800
+ })
801
+ },
802
+ shape: [
803
+ 'scalar',
804
+ 'scalar'
805
+ ]
368
806
  };
369
- export const LOG_RETRIEVAL_RESPONSE = {
807
+ // `facts` and `payload` each materialize to a single service-slot id, so a Fact occupies: factTypeId, the payload
808
+ // array slot, and `OPTION(ORIGIN_BLOCK)` (its discriminant plus ORIGIN_BLOCK's two slots).
809
+ export const FACT = {
370
810
  serialization: {
371
- fn: (resp)=>[
372
- resp.toFields()
811
+ fn: (f)=>[
812
+ f.factTypeId,
813
+ f.payload.materializeSlot((v)=>FIELD.serialization.fn(v).flat()),
814
+ ...OPTION(ORIGIN_BLOCK).serialization.fn(f.originBlock)
373
815
  ]
374
- }
816
+ },
817
+ shape: [
818
+ 'scalar',
819
+ 'scalar',
820
+ 'scalar',
821
+ 'scalar',
822
+ 'scalar'
823
+ ]
375
824
  };
376
- export const MESSAGE_CONTEXT = {
825
+ export const FACT_COLLECTION = {
377
826
  serialization: {
378
- fn: (mc)=>[
379
- mc.toFields()
827
+ fn: (c)=>[
828
+ c.contractAddress.toField(),
829
+ c.scope.toField(),
830
+ c.factCollectionTypeId,
831
+ c.factCollectionId,
832
+ c.facts.materializeSlot((v)=>FACT.serialization.fn(v).flat())
380
833
  ]
381
- }
834
+ },
835
+ shape: [
836
+ 'scalar',
837
+ 'scalar',
838
+ 'scalar',
839
+ 'scalar',
840
+ 'scalar'
841
+ ]
382
842
  };
383
843
  export const PROVIDED_SECRET = {
384
844
  deserialization: {
385
- fn: ([reader])=>ProvidedSecret.fromFields(reader),
386
- slots: 1
387
- }
845
+ fn: ([reader])=>({
846
+ secret: reader.readField(),
847
+ mode: appTaggingSecretKindFromDeliveryMode(BYTE.deserialization.fn([
848
+ reader
849
+ ]))
850
+ })
851
+ },
852
+ shape: [
853
+ {
854
+ len: 2
855
+ }
856
+ ]
388
857
  };
389
858
  // ─── Combinator Type Mappings ────────────────────────────────────────────────
390
- /** `_height` is unused at runtime but lets TypeScript infer the exact `N` for `MembershipWitness<N>`. */ export function MEMBERSHIP_WITNESS(_height) {
859
+ function SIBLING_PATH(height) {
391
860
  return {
392
861
  serialization: {
393
- fn: (witness)=>[
394
- new Fr(witness.leafIndex),
395
- [
396
- ...witness.siblingPath
397
- ]
862
+ fn: (sp)=>[
863
+ sp.toFields()
398
864
  ]
865
+ },
866
+ shape: [
867
+ {
868
+ len: height
869
+ }
870
+ ]
871
+ };
872
+ }
873
+ export function MEMBERSHIP_WITNESS(height) {
874
+ return STRUCT([
875
+ {
876
+ name: 'leafIndex',
877
+ type: BIGINT
878
+ },
879
+ {
880
+ name: 'siblingPath',
881
+ type: FIXED_ARRAY(FIELD, height)
399
882
  }
883
+ ]);
884
+ }
885
+ export function ARRAY(inner) {
886
+ return {
887
+ kind: 'array',
888
+ inner,
889
+ serialization: inner.serialization ? {
890
+ fn: (values)=>[
891
+ packElements(inner, values)
892
+ ]
893
+ } : undefined,
894
+ deserialization: inner.deserialization ? {
895
+ // The whole slot is the array, so read as many elements as its fields hold.
896
+ fn: ([reader])=>unpackElements(inner, reader, reader.remainingFields() / fieldWidth(inner.shape))
897
+ } : undefined,
898
+ // One slot of variable length (all elements flattened into it).
899
+ shape: [
900
+ {
901
+ lenFrom: (size)=>size.length * fieldWidth(inner.shape)
902
+ }
903
+ ]
400
904
  };
401
905
  }
402
- export function ARRAY(element) {
906
+ /**
907
+ * Noir's fixed-length array `[T; maxLength]` in one slot: serializes `values` (each flattened via `element`)
908
+ * zero-padded to exactly `maxLength * elementWidth` fields, and deserializes all `maxLength` elements back. An absent
909
+ * element is the zero encoding, so the padding is derived from the shape.
910
+ */ function FIXED_ARRAY(element, maxLength) {
911
+ const elementWidth = fieldWidth(element.shape);
403
912
  return {
404
913
  serialization: element.serialization ? {
405
914
  fn: (values)=>[
406
- values.flatMap((v)=>element.serialization.fn(v).flat())
915
+ padArrayEnd(packElements(element, values), Fr.ZERO, maxLength * elementWidth)
407
916
  ]
408
917
  } : undefined,
409
918
  deserialization: element.deserialization ? {
410
- fn: ([reader])=>{
411
- const result = [];
412
- while(!reader.isFinished()){
413
- result.push(element.deserialization.fn([
414
- reader
415
- ]));
416
- }
417
- return result;
418
- },
419
- slots: 1
420
- } : undefined
919
+ fn: ([reader])=>unpackElements(element, reader, maxLength)
920
+ } : undefined,
921
+ shape: [
922
+ {
923
+ len: maxLength * elementWidth
924
+ }
925
+ ]
421
926
  };
422
927
  }
423
928
  /**
@@ -432,92 +937,128 @@ export function ARRAY(element) {
432
937
  * slot 0: [Fr(0x41), Fr(0x42), Fr(0), Fr(0)] // data padded to maxLength
433
938
  * slot 1: Fr(2) // actual length
434
939
  * ```
435
- */ export function BOUNDED_VEC(element) {
940
+ */ export function BOUNDED_VEC(inner) {
436
941
  return {
437
- serialization: element.serialization ? {
942
+ kind: 'bounded-vec',
943
+ inner,
944
+ serialization: inner.serialization ? {
438
945
  fn: (bv)=>{
439
946
  if (bv.data.length > bv.maxLength) {
440
947
  throw new Error(`Got ${bv.data.length} items, but maxLength is ${bv.maxLength}`);
441
948
  }
442
- const flat = bv.data.flatMap((item)=>element.serialization.fn(item).flat());
949
+ // Fixed-width elements take their width from the shape (consistent with deserialization); only a
950
+ // variable-width element (e.g. a packed note) falls back to the runtime `elementSize` the value carries.
951
+ const elementWidth = tryFieldWidth(inner.shape) ?? bv.elementSize;
952
+ const flat = padArrayEnd(packElements(inner, bv.data), Fr.ZERO, bv.maxLength * elementWidth);
443
953
  return [
444
- padArrayEnd(flat, Fr.ZERO, bv.maxLength * bv.elementSize),
954
+ flat,
445
955
  new Fr(bv.data.length)
446
956
  ];
447
957
  }
448
958
  } : undefined,
449
- deserialization: element.deserialization ? {
959
+ deserialization: inner.deserialization ? {
450
960
  fn: ([storageReader, lengthReader])=>{
451
- const maxLength = storageReader.remainingFields();
961
+ // slot 0 is the padded storage, slot 1 the actual length. Parse only the first `length` elements out of
962
+ // storage, then drain the trailing zero-padding so the storage reader is fully consumed.
963
+ const maxLength = storageReader.remainingFields() / fieldWidth(inner.shape);
452
964
  const length = lengthReader.readField().toNumber();
453
- const elements = [];
454
- for(let i = 0; i < length; i++){
455
- elements.push(element.deserialization.fn([
456
- storageReader
457
- ]));
458
- }
459
- // Drain the trailing zero-padding (maxLength - length unused element slots) so the storage reader is
460
- // fully consumed.
965
+ const elements = unpackElements(inner, storageReader, length);
461
966
  storageReader.skip(storageReader.remainingFields());
462
967
  return BoundedVec.from({
463
968
  data: elements,
464
969
  maxLength
465
970
  });
971
+ }
972
+ } : undefined,
973
+ // slot 0: variable-length storage; slot 1: the length scalar.
974
+ shape: [
975
+ {
976
+ lenFrom: (size)=>size.maxLength * fieldWidth(inner.shape)
466
977
  },
467
- slots: 2
468
- } : undefined
978
+ 'scalar'
979
+ ]
980
+ };
981
+ }
982
+ /**
983
+ * Noir's `BoundedVec<T, MaxLen>` in its padded form (one fixed-width slot): `maxLength * elementWidth` storage fields
984
+ * (zero-padded) followed by the actual length, with no length prefix, so the width is statically known. Serialize-only.
985
+ * Throws if the input exceeds `maxLength`.
986
+ */ function FIXED_BOUNDED_VEC(element, maxLength) {
987
+ const width = fieldWidth(element.shape);
988
+ return {
989
+ serialization: element.serialization ? {
990
+ fn: (values)=>{
991
+ if (values.length > maxLength) {
992
+ throw new Error(`Got ${values.length} items, but maxLength is ${maxLength}`);
993
+ }
994
+ const flat = padArrayEnd(packElements(element, values), Fr.ZERO, maxLength * width);
995
+ return [
996
+ [
997
+ ...flat,
998
+ new Fr(values.length)
999
+ ]
1000
+ ];
1001
+ }
1002
+ } : undefined,
1003
+ shape: [
1004
+ {
1005
+ len: maxLength * width + 1
1006
+ }
1007
+ ]
469
1008
  };
470
1009
  }
471
1010
  /**
472
- * Wraps an inner TypeMapping in Noir-style `Option<T>`. Adds a discriminant slot and uses the handler-provided
473
- * `Option.none(shape)` template to produce a correctly-sized zero-filled output for the None case.
1011
+ * Wraps an inner TypeMapping in Noir-style `Option<T>`, adding a leading discriminant slot.
474
1012
  *
475
- * @example Serializing `Option.some(AztecAddress.fromField(Fr(42)))` with `OPTION(AZTEC_ADDRESS)`:
1013
+ * For the `None` case, the inner's slots must still be present on the wire as zero-padding (so `Some` and `None` have
1014
+ * identical size). That padding is derived entirely from `inner.shape`.
1015
+ *
1016
+ * @example Serializing `Option.some(AztecAddress.fromFieldUnsafe(Fr(42)))` with `OPTION(AZTEC_ADDRESS)`:
476
1017
  * ```
477
1018
  * slot 0: Fr(1) // discriminant: Some
478
1019
  * slot 1: Fr(42) // inner value
479
1020
  * ```
480
1021
  *
481
- * @example Serializing `Option.empty(AztecAddress.ZERO)` with `OPTION(AZTEC_ADDRESS)`:
1022
+ * @example Serializing `Option.none()` with `OPTION(AZTEC_ADDRESS)`:
482
1023
  * ```
483
1024
  * slot 0: Fr(0) // discriminant: None
484
- * slot 1: Fr(0) // zero-filled using shape
1025
+ * slot 1: Fr(0) // zero-filled from AZTEC_ADDRESS.shape
485
1026
  * ```
486
1027
  */ export function OPTION(inner) {
487
1028
  return {
1029
+ kind: 'option',
1030
+ inner,
488
1031
  serialization: inner.serialization ? {
489
- fn: (opt)=>{
490
- if (opt.isSome()) {
491
- return [
492
- Fr.ONE,
493
- ...inner.serialization.fn(opt.value)
494
- ];
495
- }
496
- if (opt.template === undefined) {
497
- throw new Error('Cannot serialize Option.empty() without an emptyTemplate — provide one via Option.empty(emptyTemplate)');
498
- }
499
- const zeroSlots = inner.serialization.fn(opt.template).map((s)=>Array.isArray(s) ? Array(s.length).fill(Fr.ZERO) : Fr.ZERO);
500
- return [
1032
+ fn: (opt)=>opt.isSome() ? [
1033
+ Fr.ONE,
1034
+ ...inner.serialization.fn(opt.value)
1035
+ ] : [
501
1036
  Fr.ZERO,
502
- ...zeroSlots
503
- ];
504
- }
1037
+ ...zeroSlotsFromShape(inner.shape, opt.size)
1038
+ ]
505
1039
  } : undefined,
506
1040
  deserialization: inner.deserialization ? {
507
1041
  fn: ([discriminant, ...innerReaders])=>{
508
1042
  if (discriminant.readField().isZero()) {
509
- // None still carries zero-filled inner slots on the wire; drain them so the inner readers are fully
510
- // consumed.
1043
+ // None still carries the inner's zero-padded slots; consume them without parsing, since an inner that
1044
+ // validates its fields would reject the zeros.
511
1045
  innerReaders.forEach((reader)=>reader.skip(reader.remainingFields()));
512
- return Option.none(undefined);
1046
+ return Option.none();
513
1047
  }
514
1048
  return Option.some(inner.deserialization.fn(innerReaders));
515
- },
516
- slots: inner.deserialization.slots + 1
517
- } : undefined
1049
+ }
1050
+ } : undefined,
1051
+ // A leading discriminant slot followed by the inner's slots.
1052
+ shape: [
1053
+ 'scalar',
1054
+ ...inner.shape
1055
+ ]
518
1056
  };
519
1057
  }
520
- /** A packed uint buffer (e.g. `[u8; N]` in Noir): 1 slot of packed uint values ↔ `Buffer`. */ export function BUFFER(bitSize) {
1058
+ /**
1059
+ * A fixed packed uint buffer (Noir `[u8; length]` at `bitSize` 8): one slot of `length` packed uint values ↔ `Buffer`.
1060
+ * `length` is the field count, which equals the byte count at `bitSize` 8.
1061
+ */ export function BUFFER(bitSize, length) {
521
1062
  return {
522
1063
  serialization: {
523
1064
  fn: (buf)=>[
@@ -525,36 +1066,157 @@ export function ARRAY(element) {
525
1066
  ]
526
1067
  },
527
1068
  deserialization: {
528
- fn: ([reader])=>{
529
- const fields = reader.readFieldArray(reader.remainingFields()).map((f)=>f.toString());
530
- return fromUintArray(fields, bitSize);
531
- },
532
- slots: 1
533
- }
1069
+ fn: ([reader])=>fromUintArray(reader.readFieldArray(length).map((f)=>f.toString()), bitSize)
1070
+ },
1071
+ shape: [
1072
+ {
1073
+ len: length
1074
+ }
1075
+ ]
534
1076
  };
535
1077
  }
536
1078
  export function EPHEMERAL_ARRAY(element) {
537
- // An EphemeralArray param is a single slot; the per-param assert covers that slot but never sees the
538
- // per-row readers materialized in readAll(). Assert full consumption per row here.
1079
+ // EphemeralArray.readAll hands each row's flat fields in as a single reader; reconstruct the element's per-slot
1080
+ // readers from its shape, deserialize, and assert the row was fully consumed so a row with trailing fields is
1081
+ // rejected.
539
1082
  const rowElement = element.deserialization ? {
540
1083
  deserialization: {
541
- fn: (readers)=>{
542
- const value = element.deserialization.fn(readers);
543
- assertReadersConsumed(readers);
544
- return value;
545
- },
546
- slots: element.deserialization.slots
547
- }
1084
+ fn: ([rowReader])=>deserializeElement(element, rowReader.readFieldArray(rowReader.remainingFields()))
1085
+ },
1086
+ // `fn` reads the whole row from one reader, so this is one variable-width slot, not the element's multi-slot
1087
+ // shape.
1088
+ shape: [
1089
+ 'variable'
1090
+ ]
548
1091
  } : undefined;
549
1092
  return {
550
1093
  serialization: element.serialization ? {
551
1094
  fn: (ea)=>[
552
- ea.materializeSlot((v)=>element.serialization.fn(v).flat())
1095
+ ea.materializeSlot((v)=>serializeElement(element, v))
553
1096
  ]
554
1097
  } : undefined,
555
1098
  deserialization: rowElement ? {
556
- fn: ([reader])=>EphemeralArray.fromSlot(reader.readField(), rowElement),
557
- slots: 1
558
- } : undefined
1099
+ fn: ([reader])=>EphemeralArray.fromSlot(reader.readField(), rowElement)
1100
+ } : undefined,
1101
+ // A single slot carrying the array's service-slot id.
1102
+ shape: [
1103
+ 'scalar'
1104
+ ]
1105
+ };
1106
+ }
1107
+ /**
1108
+ * A Noir struct: its `shape` and (de)serialization are the concatenation of its fields', so callers never hand-write a
1109
+ * `shape`. `T` is the struct's TS value type and must match the field layout — serialization reads each field by name
1110
+ * off the value, deserialization returns the decoded bag as `T`; convert in the handler, not here, when `T` differs.
1111
+ */ function STRUCT(fields) {
1112
+ return {
1113
+ serialization: fields.every((f)=>f.type.serialization) ? {
1114
+ fn: (value)=>{
1115
+ const props = value;
1116
+ return fields.flatMap((f)=>f.type.serialization.fn(props[f.name]));
1117
+ }
1118
+ } : undefined,
1119
+ deserialization: fields.every((f)=>f.type.deserialization) ? {
1120
+ fn: (readers)=>{
1121
+ const props = {};
1122
+ let slot = 0;
1123
+ for (const f of fields){
1124
+ const slotCount = f.type.shape.length;
1125
+ props[f.name] = f.type.deserialization.fn(readers.slice(slot, slot + slotCount));
1126
+ slot += slotCount;
1127
+ }
1128
+ return props;
1129
+ }
1130
+ } : undefined,
1131
+ shape: fields.flatMap((f)=>f.type.shape)
559
1132
  };
560
1133
  }
1134
+ /** Number of InputSlots a deserializable type spans, derived from its {@link TypeMapping.shape}. */ export function slotsOf(mapping) {
1135
+ return mapping.shape.length;
1136
+ }
1137
+ /** Number of fields a fully-static shape occupies, or `undefined` if any slot is variable-width. */ function tryFieldWidth(shape) {
1138
+ let total = 0;
1139
+ for (const slot of shape){
1140
+ if (slot === 'scalar') {
1141
+ total += 1;
1142
+ } else if (typeof slot === 'object' && 'len' in slot) {
1143
+ total += slot.len;
1144
+ } else {
1145
+ return undefined;
1146
+ }
1147
+ }
1148
+ return total;
1149
+ }
1150
+ /** Number of fields a fully-static shape occupies. Throws on a variable-width shape, whose field count isn't known. */ function fieldWidth(shape) {
1151
+ const width = tryFieldWidth(shape);
1152
+ if (width === undefined) {
1153
+ throw new Error('Cannot compute a fixed field width for a variable-width shape');
1154
+ }
1155
+ return width;
1156
+ }
1157
+ /** Reconstructs a value's per-slot readers from a flat run of fields, using its shape (inverse of slot-flattening). */ function splitByShape(fields, shape) {
1158
+ const readers = [];
1159
+ let cursor = 0;
1160
+ shape.forEach((slot, i)=>{
1161
+ if (slot === 'scalar' || typeof slot === 'object' && 'len' in slot) {
1162
+ const width = slot === 'scalar' ? 1 : slot.len;
1163
+ if (cursor + width > fields.length) {
1164
+ throw new Error(`Not enough fields to reconstruct shape: needed ${width}, had ${fields.length - cursor}`);
1165
+ }
1166
+ readers.push(new FieldReader(fields.slice(cursor, cursor + width)));
1167
+ cursor += width;
1168
+ } else {
1169
+ // A variable slot (sized or not) takes whatever remains, so it must be last.
1170
+ if (i !== shape.length - 1) {
1171
+ throw new Error('A variable-width slot must be last to be reconstructed from a flat field array');
1172
+ }
1173
+ readers.push(new FieldReader(fields.slice(cursor)));
1174
+ cursor = fields.length;
1175
+ }
1176
+ });
1177
+ if (cursor !== fields.length) {
1178
+ throw new Error(`Malformed flattened value: ${fields.length - cursor} unexpected trailing field(s)`);
1179
+ }
1180
+ return readers;
1181
+ }
1182
+ /** Serializes one element to its flat fields. Element must be serializable. */ function serializeElement(element, value) {
1183
+ return element.serialization.fn(value).flat();
1184
+ }
1185
+ /**
1186
+ * Deserializes one element from its exact flat fields, reconstructing its per-slot readers from its shape and asserting
1187
+ * they are fully consumed (so trailing fields are rejected). Element must be deserializable.
1188
+ */ function deserializeElement(element, fields) {
1189
+ const readers = splitByShape(fields, element.shape);
1190
+ const value = element.deserialization.fn(readers);
1191
+ assertReadersConsumed(readers);
1192
+ return value;
1193
+ }
1194
+ /** Flattens `values` into one contiguous run of fields by serializing each element. Element must be serializable. */ function packElements(element, values) {
1195
+ return values.flatMap((v)=>serializeElement(element, v));
1196
+ }
1197
+ /**
1198
+ * Reads `count` fixed-width elements out of a packed run (the inverse of {@link packElements}). Element must be
1199
+ * deserializable.
1200
+ */ function unpackElements(element, reader, count) {
1201
+ const elementWidth = fieldWidth(element.shape);
1202
+ return Array.from({
1203
+ length: count
1204
+ }, ()=>deserializeElement(element, reader.readFieldArray(elementWidth)));
1205
+ }
1206
+ /** Builds the zero-filled slots for a `None`, matching a `Some`'s wire shape (variable slots sized from `size`). */ function zeroSlotsFromShape(shape, size) {
1207
+ return shape.map((slot)=>{
1208
+ if (slot === 'scalar') {
1209
+ return Fr.ZERO;
1210
+ }
1211
+ if (slot === 'variable') {
1212
+ throw new Error('Cannot zero-fill an unsized variable-width slot');
1213
+ }
1214
+ if ('len' in slot) {
1215
+ return Array(slot.len).fill(Fr.ZERO);
1216
+ }
1217
+ if (size === undefined) {
1218
+ throw new Error('Serializing Option.none() over a variable-size inner needs a size, e.g. Option.none({ length: n })');
1219
+ }
1220
+ return Array(slot.lenFrom(size)).fill(Fr.ZERO);
1221
+ });
1222
+ }