@aztec/simulator 0.42.0 → 0.44.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (191) hide show
  1. package/dest/acvm/oracle/oracle.d.ts +5 -2
  2. package/dest/acvm/oracle/oracle.d.ts.map +1 -1
  3. package/dest/acvm/oracle/oracle.js +25 -8
  4. package/dest/acvm/oracle/typed_oracle.d.ts +7 -4
  5. package/dest/acvm/oracle/typed_oracle.d.ts.map +1 -1
  6. package/dest/acvm/oracle/typed_oracle.js +14 -5
  7. package/dest/avm/avm_execution_environment.d.ts +2 -0
  8. package/dest/avm/avm_execution_environment.d.ts.map +1 -1
  9. package/dest/avm/avm_execution_environment.js +9 -4
  10. package/dest/avm/avm_gas.d.ts.map +1 -1
  11. package/dest/avm/avm_gas.js +3 -1
  12. package/dest/avm/avm_memory_types.d.ts.map +1 -1
  13. package/dest/avm/avm_memory_types.js +2 -4
  14. package/dest/avm/avm_simulator.d.ts.map +1 -1
  15. package/dest/avm/avm_simulator.js +2 -3
  16. package/dest/avm/fixtures/index.d.ts +10 -3
  17. package/dest/avm/fixtures/index.d.ts.map +1 -1
  18. package/dest/avm/fixtures/index.js +9 -11
  19. package/dest/avm/journal/journal.d.ts +57 -66
  20. package/dest/avm/journal/journal.d.ts.map +1 -1
  21. package/dest/avm/journal/journal.js +97 -131
  22. package/dest/avm/journal/nullifiers.d.ts +21 -8
  23. package/dest/avm/journal/nullifiers.d.ts.map +1 -1
  24. package/dest/avm/journal/nullifiers.js +26 -8
  25. package/dest/avm/journal/public_storage.d.ts +4 -0
  26. package/dest/avm/journal/public_storage.d.ts.map +1 -1
  27. package/dest/avm/journal/public_storage.js +10 -1
  28. package/dest/avm/opcodes/accrued_substate.d.ts +2 -2
  29. package/dest/avm/opcodes/accrued_substate.d.ts.map +1 -1
  30. package/dest/avm/opcodes/accrued_substate.js +39 -24
  31. package/dest/avm/opcodes/arithmetic.d.ts.map +1 -1
  32. package/dest/avm/opcodes/arithmetic.js +12 -9
  33. package/dest/avm/opcodes/bitwise.d.ts.map +1 -1
  34. package/dest/avm/opcodes/bitwise.js +11 -8
  35. package/dest/avm/opcodes/comparators.d.ts.map +1 -1
  36. package/dest/avm/opcodes/comparators.js +7 -5
  37. package/dest/avm/opcodes/contract.d.ts.map +1 -1
  38. package/dest/avm/opcodes/contract.js +20 -24
  39. package/dest/avm/opcodes/control_flow.d.ts.map +1 -1
  40. package/dest/avm/opcodes/control_flow.js +4 -2
  41. package/dest/avm/opcodes/ec_add.d.ts +19 -0
  42. package/dest/avm/opcodes/ec_add.d.ts.map +1 -0
  43. package/dest/avm/opcodes/ec_add.js +78 -0
  44. package/dest/avm/opcodes/external_calls.d.ts.map +1 -1
  45. package/dest/avm/opcodes/external_calls.js +19 -29
  46. package/dest/avm/opcodes/hashing.d.ts.map +1 -1
  47. package/dest/avm/opcodes/hashing.js +10 -2
  48. package/dest/avm/opcodes/instruction_impl.d.ts.map +1 -1
  49. package/dest/avm/opcodes/instruction_impl.js +4 -2
  50. package/dest/avm/opcodes/memory.d.ts +1 -1
  51. package/dest/avm/opcodes/memory.d.ts.map +1 -1
  52. package/dest/avm/opcodes/memory.js +14 -12
  53. package/dest/avm/opcodes/multi_scalar_mul.d.ts +16 -0
  54. package/dest/avm/opcodes/multi_scalar_mul.d.ts.map +1 -0
  55. package/dest/avm/opcodes/multi_scalar_mul.js +95 -0
  56. package/dest/avm/opcodes/storage.d.ts +1 -1
  57. package/dest/avm/opcodes/storage.d.ts.map +1 -1
  58. package/dest/avm/opcodes/storage.js +11 -8
  59. package/dest/avm/serialization/bytecode_serialization.d.ts.map +1 -1
  60. package/dest/avm/serialization/bytecode_serialization.js +5 -1
  61. package/dest/avm/serialization/instruction_serialization.d.ts +3 -1
  62. package/dest/avm/serialization/instruction_serialization.d.ts.map +1 -1
  63. package/dest/avm/serialization/instruction_serialization.js +4 -2
  64. package/dest/avm/test_utils.d.ts +14 -0
  65. package/dest/avm/test_utils.d.ts.map +1 -0
  66. package/dest/avm/test_utils.js +36 -0
  67. package/dest/client/client_execution_context.d.ts +17 -5
  68. package/dest/client/client_execution_context.d.ts.map +1 -1
  69. package/dest/client/client_execution_context.js +32 -18
  70. package/dest/client/execution_note_cache.d.ts.map +1 -1
  71. package/dest/client/execution_note_cache.js +1 -1
  72. package/dest/client/execution_result.d.ts +2 -1
  73. package/dest/client/execution_result.d.ts.map +1 -1
  74. package/dest/client/execution_result.js +1 -1
  75. package/dest/client/index.d.ts +2 -0
  76. package/dest/client/index.d.ts.map +1 -1
  77. package/dest/client/index.js +3 -1
  78. package/dest/client/simulator.d.ts +4 -3
  79. package/dest/client/simulator.d.ts.map +1 -1
  80. package/dest/client/simulator.js +17 -9
  81. package/dest/client/view_data_oracle.d.ts +2 -0
  82. package/dest/client/view_data_oracle.d.ts.map +1 -1
  83. package/dest/client/view_data_oracle.js +7 -1
  84. package/dest/mocks/fixtures.d.ts.map +1 -1
  85. package/dest/mocks/fixtures.js +3 -2
  86. package/dest/public/abstract_phase_manager.d.ts +11 -11
  87. package/dest/public/abstract_phase_manager.d.ts.map +1 -1
  88. package/dest/public/abstract_phase_manager.js +84 -59
  89. package/dest/public/app_logic_phase_manager.d.ts +3 -3
  90. package/dest/public/app_logic_phase_manager.d.ts.map +1 -1
  91. package/dest/public/app_logic_phase_manager.js +4 -3
  92. package/dest/public/db_interfaces.d.ts +1 -0
  93. package/dest/public/db_interfaces.d.ts.map +1 -1
  94. package/dest/public/execution.d.ts +28 -40
  95. package/dest/public/execution.d.ts.map +1 -1
  96. package/dest/public/execution.js +1 -51
  97. package/dest/public/executor.d.ts +9 -4
  98. package/dest/public/executor.d.ts.map +1 -1
  99. package/dest/public/executor.js +38 -27
  100. package/dest/public/hints_builder.d.ts +1 -1
  101. package/dest/public/index.d.ts +6 -6
  102. package/dest/public/index.d.ts.map +1 -1
  103. package/dest/public/index.js +7 -7
  104. package/dest/public/phase_manager_factory.d.ts +3 -3
  105. package/dest/public/phase_manager_factory.d.ts.map +1 -1
  106. package/dest/public/phase_manager_factory.js +5 -5
  107. package/dest/public/public_db_sources.d.ts +3 -1
  108. package/dest/public/public_db_sources.d.ts.map +1 -1
  109. package/dest/public/public_db_sources.js +54 -8
  110. package/dest/public/public_processor.d.ts +5 -2
  111. package/dest/public/public_processor.d.ts.map +1 -1
  112. package/dest/public/public_processor.js +143 -125
  113. package/dest/public/setup_phase_manager.d.ts +3 -3
  114. package/dest/public/setup_phase_manager.d.ts.map +1 -1
  115. package/dest/public/setup_phase_manager.js +3 -3
  116. package/dest/public/side_effect_trace.d.ts +86 -0
  117. package/dest/public/side_effect_trace.d.ts.map +1 -0
  118. package/dest/public/side_effect_trace.js +222 -0
  119. package/dest/public/side_effect_trace_interface.d.ts +36 -0
  120. package/dest/public/side_effect_trace_interface.d.ts.map +1 -0
  121. package/dest/public/side_effect_trace_interface.js +2 -0
  122. package/dest/public/tail_phase_manager.d.ts +3 -3
  123. package/dest/public/tail_phase_manager.d.ts.map +1 -1
  124. package/dest/public/tail_phase_manager.js +3 -3
  125. package/dest/public/teardown_phase_manager.d.ts +3 -3
  126. package/dest/public/teardown_phase_manager.d.ts.map +1 -1
  127. package/dest/public/teardown_phase_manager.js +4 -3
  128. package/dest/public/transitional_adaptors.d.ts +2 -6
  129. package/dest/public/transitional_adaptors.d.ts.map +1 -1
  130. package/dest/public/transitional_adaptors.js +1 -43
  131. package/package.json +18 -9
  132. package/src/acvm/oracle/oracle.ts +46 -9
  133. package/src/acvm/oracle/typed_oracle.ts +37 -7
  134. package/src/avm/avm_execution_environment.ts +10 -3
  135. package/src/avm/avm_gas.ts +2 -0
  136. package/src/avm/avm_memory_types.ts +1 -3
  137. package/src/avm/avm_simulator.ts +2 -3
  138. package/src/avm/fixtures/index.ts +19 -14
  139. package/src/avm/journal/journal.ts +127 -231
  140. package/src/avm/journal/nullifiers.ts +30 -13
  141. package/src/avm/journal/public_storage.ts +10 -0
  142. package/src/avm/opcodes/accrued_substate.ts +60 -23
  143. package/src/avm/opcodes/arithmetic.ts +17 -8
  144. package/src/avm/opcodes/bitwise.ts +13 -8
  145. package/src/avm/opcodes/comparators.ts +9 -4
  146. package/src/avm/opcodes/contract.ts +22 -26
  147. package/src/avm/opcodes/control_flow.ts +3 -1
  148. package/src/avm/opcodes/ec_add.ts +92 -0
  149. package/src/avm/opcodes/external_calls.ts +20 -36
  150. package/src/avm/opcodes/hashing.ts +11 -1
  151. package/src/avm/opcodes/instruction_impl.ts +4 -1
  152. package/src/avm/opcodes/memory.ts +18 -11
  153. package/src/avm/opcodes/multi_scalar_mul.ts +114 -0
  154. package/src/avm/opcodes/storage.ts +10 -10
  155. package/src/avm/serialization/bytecode_serialization.ts +4 -0
  156. package/src/avm/serialization/instruction_serialization.ts +2 -0
  157. package/src/avm/test_utils.ts +53 -0
  158. package/src/client/client_execution_context.ts +55 -21
  159. package/src/client/execution_note_cache.ts +0 -1
  160. package/src/client/execution_result.ts +2 -1
  161. package/src/client/index.ts +2 -0
  162. package/src/client/simulator.ts +26 -10
  163. package/src/client/view_data_oracle.ts +8 -0
  164. package/src/mocks/fixtures.ts +2 -1
  165. package/src/public/abstract_phase_manager.ts +99 -70
  166. package/src/public/app_logic_phase_manager.ts +3 -2
  167. package/src/public/db_interfaces.ts +2 -0
  168. package/src/public/execution.ts +35 -94
  169. package/src/public/executor.ts +56 -40
  170. package/src/public/index.ts +6 -12
  171. package/src/public/phase_manager_factory.ts +6 -6
  172. package/src/public/public_db_sources.ts +62 -7
  173. package/src/public/public_processor.ts +15 -9
  174. package/src/public/setup_phase_manager.ts +2 -2
  175. package/src/public/side_effect_trace.ts +323 -0
  176. package/src/public/side_effect_trace_interface.ts +41 -0
  177. package/src/public/tail_phase_manager.ts +2 -2
  178. package/src/public/teardown_phase_manager.ts +3 -2
  179. package/src/public/transitional_adaptors.ts +2 -60
  180. package/dest/avm/journal/trace.d.ts +0 -33
  181. package/dest/avm/journal/trace.d.ts.map +0 -1
  182. package/dest/avm/journal/trace.js +0 -151
  183. package/dest/avm/journal/trace_types.d.ts +0 -51
  184. package/dest/avm/journal/trace_types.d.ts.map +0 -1
  185. package/dest/avm/journal/trace_types.js +0 -6
  186. package/dest/public/utils.d.ts +0 -8
  187. package/dest/public/utils.d.ts.map +0 -1
  188. package/dest/public/utils.js +0 -38
  189. package/src/avm/journal/trace.ts +0 -184
  190. package/src/avm/journal/trace_types.ts +0 -88
  191. package/src/public/utils.ts +0 -39
@@ -1,5 +1,5 @@
1
1
  import type { AvmContext } from '../avm_context.js';
2
- import { Uint8 } from '../avm_memory_types.js';
2
+ import { TypeTag, Uint8 } from '../avm_memory_types.js';
3
3
  import { InstructionExecutionError, StaticCallAlterationError } from '../errors.js';
4
4
  import { NullifierCollisionError } from '../journal/nullifiers.js';
5
5
  import { Opcode, OperandType } from '../serialization/instruction_serialization.js';
@@ -31,17 +31,22 @@ export class NoteHashExists extends Instruction {
31
31
  const memoryOperations = { reads: 2, writes: 1, indirect: this.indirect };
32
32
  const memory = context.machineState.memory.track(this.type);
33
33
  context.machineState.consumeGas(this.gasCost(memoryOperations));
34
+ const [noteHashOffset, leafIndexOffset, existsOffset] = Addressing.fromWire(this.indirect).resolve(
35
+ [this.noteHashOffset, this.leafIndexOffset, this.existsOffset],
36
+ memory,
37
+ );
38
+ memory.checkTags(TypeTag.FIELD, noteHashOffset, leafIndexOffset);
34
39
 
35
40
  // Note that this instruction accepts any type in memory, and converts to Field.
36
- const noteHash = memory.get(this.noteHashOffset).toFr();
37
- const leafIndex = memory.get(this.leafIndexOffset).toFr();
41
+ const noteHash = memory.get(noteHashOffset).toFr();
42
+ const leafIndex = memory.get(leafIndexOffset).toFr();
38
43
 
39
44
  const exists = await context.persistableState.checkNoteHashExists(
40
45
  context.environment.storageAddress,
41
46
  noteHash,
42
47
  leafIndex,
43
48
  );
44
- memory.set(this.existsOffset, exists ? new Uint8(1) : new Uint8(0));
49
+ memory.set(existsOffset, exists ? new Uint8(1) : new Uint8(0));
45
50
 
46
51
  memory.assert(memoryOperations);
47
52
  context.machineState.incrementPc();
@@ -63,11 +68,14 @@ export class EmitNoteHash extends Instruction {
63
68
  const memory = context.machineState.memory.track(this.type);
64
69
  context.machineState.consumeGas(this.gasCost(memoryOperations));
65
70
 
71
+ const [noteHashOffset] = Addressing.fromWire(this.indirect).resolve([this.noteHashOffset], memory);
72
+ memory.checkTag(TypeTag.FIELD, noteHashOffset);
73
+
66
74
  if (context.environment.isStaticCall) {
67
75
  throw new StaticCallAlterationError();
68
76
  }
69
77
 
70
- const noteHash = memory.get(this.noteHashOffset).toFr();
78
+ const noteHash = memory.get(noteHashOffset).toFr();
71
79
  context.persistableState.writeNoteHash(context.environment.storageAddress, noteHash);
72
80
 
73
81
  memory.assert(memoryOperations);
@@ -101,11 +109,17 @@ export class NullifierExists extends Instruction {
101
109
  const memory = context.machineState.memory.track(this.type);
102
110
  context.machineState.consumeGas(this.gasCost(memoryOperations));
103
111
 
104
- const nullifier = memory.get(this.nullifierOffset).toFr();
105
- const address = memory.get(this.addressOffset).toFr();
112
+ const [nullifierOffset, addressOffset, existsOffset] = Addressing.fromWire(this.indirect).resolve(
113
+ [this.nullifierOffset, this.addressOffset, this.existsOffset],
114
+ memory,
115
+ );
116
+ memory.checkTags(TypeTag.FIELD, nullifierOffset, addressOffset);
117
+
118
+ const nullifier = memory.get(nullifierOffset).toFr();
119
+ const address = memory.get(addressOffset).toFr();
106
120
  const exists = await context.persistableState.checkNullifierExists(address, nullifier);
107
121
 
108
- memory.set(this.existsOffset, exists ? new Uint8(1) : new Uint8(0));
122
+ memory.set(existsOffset, exists ? new Uint8(1) : new Uint8(0));
109
123
 
110
124
  memory.assert(memoryOperations);
111
125
  context.machineState.incrementPc();
@@ -131,7 +145,10 @@ export class EmitNullifier extends Instruction {
131
145
  const memory = context.machineState.memory.track(this.type);
132
146
  context.machineState.consumeGas(this.gasCost(memoryOperations));
133
147
 
134
- const nullifier = memory.get(this.nullifierOffset).toFr();
148
+ const [nullifierOffset] = Addressing.fromWire(this.indirect).resolve([this.nullifierOffset], memory);
149
+ memory.checkTag(TypeTag.FIELD, nullifierOffset);
150
+
151
+ const nullifier = memory.get(nullifierOffset).toFr();
135
152
  try {
136
153
  await context.persistableState.writeNullifier(context.environment.storageAddress, nullifier);
137
154
  } catch (e) {
@@ -176,10 +193,20 @@ export class L1ToL2MessageExists extends Instruction {
176
193
  const memory = context.machineState.memory.track(this.type);
177
194
  context.machineState.consumeGas(this.gasCost(memoryOperations));
178
195
 
179
- const msgHash = memory.get(this.msgHashOffset).toFr();
180
- const msgLeafIndex = memory.get(this.msgLeafIndexOffset).toFr();
181
- const exists = await context.persistableState.checkL1ToL2MessageExists(msgHash, msgLeafIndex);
182
- memory.set(this.existsOffset, exists ? new Uint8(1) : new Uint8(0));
196
+ const [msgHashOffset, msgLeafIndexOffset, existsOffset] = Addressing.fromWire(this.indirect).resolve(
197
+ [this.msgHashOffset, this.msgLeafIndexOffset, this.existsOffset],
198
+ memory,
199
+ );
200
+ memory.checkTags(TypeTag.FIELD, msgHashOffset, msgLeafIndexOffset);
201
+
202
+ const msgHash = memory.get(msgHashOffset).toFr();
203
+ const msgLeafIndex = memory.get(msgLeafIndexOffset).toFr();
204
+ const exists = await context.persistableState.checkL1ToL2MessageExists(
205
+ context.environment.address,
206
+ msgHash,
207
+ msgLeafIndex,
208
+ );
209
+ memory.set(existsOffset, exists ? new Uint8(1) : new Uint8(0));
183
210
 
184
211
  memory.assert(memoryOperations);
185
212
  context.machineState.incrementPc();
@@ -202,7 +229,7 @@ export class EmitUnencryptedLog extends Instruction {
202
229
  private indirect: number,
203
230
  private eventSelectorOffset: number,
204
231
  private logOffset: number,
205
- private logSize: number,
232
+ private logSizeOffset: number,
206
233
  ) {
207
234
  super();
208
235
  }
@@ -212,19 +239,24 @@ export class EmitUnencryptedLog extends Instruction {
212
239
  throw new StaticCallAlterationError();
213
240
  }
214
241
 
215
- const memoryOperations = { reads: 1 + this.logSize, indirect: this.indirect };
216
242
  const memory = context.machineState.memory.track(this.type);
217
- context.machineState.consumeGas(this.gasCost(memoryOperations));
218
243
 
219
- const [eventSelectorOffset, logOffset] = Addressing.fromWire(this.indirect).resolve(
220
- [this.eventSelectorOffset, this.logOffset],
244
+ const [eventSelectorOffset, logOffset, logSizeOffset] = Addressing.fromWire(this.indirect).resolve(
245
+ [this.eventSelectorOffset, this.logOffset, this.logSizeOffset],
221
246
  memory,
222
247
  );
248
+ memory.checkTag(TypeTag.FIELD, eventSelectorOffset);
249
+ memory.checkTag(TypeTag.UINT32, logSizeOffset);
250
+ const logSize = memory.get(logSizeOffset).toNumber();
251
+ memory.checkTagsRange(TypeTag.FIELD, logOffset, logSize);
223
252
 
224
253
  const contractAddress = context.environment.address;
225
254
  const event = memory.get(eventSelectorOffset).toFr();
226
- const log = memory.getSlice(logOffset, this.logSize).map(f => f.toFr());
227
- context.persistableState.writeLog(contractAddress, event, log);
255
+
256
+ const memoryOperations = { reads: 2 + logSize, indirect: this.indirect };
257
+ context.machineState.consumeGas(this.gasCost(memoryOperations));
258
+ const log = memory.getSlice(logOffset, logSize).map(f => f.toFr());
259
+ context.persistableState.writeUnencryptedLog(contractAddress, event, log);
228
260
 
229
261
  memory.assert(memoryOperations);
230
262
  context.machineState.incrementPc();
@@ -250,9 +282,14 @@ export class SendL2ToL1Message extends Instruction {
250
282
  const memory = context.machineState.memory.track(this.type);
251
283
  context.machineState.consumeGas(this.gasCost(memoryOperations));
252
284
 
253
- const recipient = memory.get(this.recipientOffset).toFr();
254
- const content = memory.get(this.contentOffset).toFr();
255
- context.persistableState.writeL1Message(recipient, content);
285
+ const [recipientOffset, contentOffset] = Addressing.fromWire(this.indirect).resolve(
286
+ [this.recipientOffset, this.contentOffset],
287
+ memory,
288
+ );
289
+
290
+ const recipient = memory.get(recipientOffset).toFr();
291
+ const content = memory.get(contentOffset).toFr();
292
+ context.persistableState.writeL2ToL1Message(recipient, content);
256
293
 
257
294
  memory.assert(memoryOperations);
258
295
  context.machineState.incrementPc();
@@ -1,6 +1,7 @@
1
1
  import type { AvmContext } from '../avm_context.js';
2
2
  import { type Field, type MemoryValue, TypeTag } from '../avm_memory_types.js';
3
3
  import { Opcode, OperandType } from '../serialization/instruction_serialization.js';
4
+ import { Addressing } from './addressing_mode.js';
4
5
  import { Instruction } from './instruction.js';
5
6
  import { ThreeOperandInstruction } from './instruction_impl.js';
6
7
 
@@ -10,13 +11,17 @@ export abstract class ThreeOperandArithmeticInstruction extends ThreeOperandInst
10
11
  const memory = context.machineState.memory.track(this.type);
11
12
  context.machineState.consumeGas(this.gasCost(memoryOperations));
12
13
 
13
- memory.checkTags(this.inTag, this.aOffset, this.bOffset);
14
+ const [aOffset, bOffset, dstOffset] = Addressing.fromWire(this.indirect).resolve(
15
+ [this.aOffset, this.bOffset, this.dstOffset],
16
+ memory,
17
+ );
18
+ memory.checkTags(this.inTag, aOffset, bOffset);
14
19
 
15
- const a = memory.get(this.aOffset);
16
- const b = memory.get(this.bOffset);
20
+ const a = memory.get(aOffset);
21
+ const b = memory.get(bOffset);
17
22
 
18
23
  const dest = this.compute(a, b);
19
- memory.set(this.dstOffset, dest);
24
+ memory.set(dstOffset, dest);
20
25
 
21
26
  memory.assert(memoryOperations);
22
27
  context.machineState.incrementPc();
@@ -83,13 +88,17 @@ export class FieldDiv extends Instruction {
83
88
  const memory = context.machineState.memory.track(this.type);
84
89
  context.machineState.consumeGas(this.gasCost(memoryOperations));
85
90
 
86
- memory.checkTags(TypeTag.FIELD, this.aOffset, this.bOffset);
91
+ const [aOffset, bOffset, dstOffset] = Addressing.fromWire(this.indirect).resolve(
92
+ [this.aOffset, this.bOffset, this.dstOffset],
93
+ memory,
94
+ );
95
+ memory.checkTags(TypeTag.FIELD, aOffset, bOffset);
87
96
 
88
- const a = memory.getAs<Field>(this.aOffset);
89
- const b = memory.getAs<Field>(this.bOffset);
97
+ const a = memory.getAs<Field>(aOffset);
98
+ const b = memory.getAs<Field>(bOffset);
90
99
 
91
100
  const dest = a.fdiv(b);
92
- memory.set(this.dstOffset, dest);
101
+ memory.set(dstOffset, dest);
93
102
 
94
103
  memory.assert(memoryOperations);
95
104
  context.machineState.incrementPc();
@@ -1,6 +1,7 @@
1
1
  import type { AvmContext } from '../avm_context.js';
2
2
  import { type IntegralValue, type TaggedMemoryInterface, TypeTag } from '../avm_memory_types.js';
3
3
  import { Opcode } from '../serialization/instruction_serialization.js';
4
+ import { Addressing } from './addressing_mode.js';
4
5
  import { ThreeOperandInstruction, TwoOperandInstruction } from './instruction_impl.js';
5
6
 
6
7
  abstract class ThreeOperandBitwiseInstruction extends ThreeOperandInstruction {
@@ -9,13 +10,17 @@ abstract class ThreeOperandBitwiseInstruction extends ThreeOperandInstruction {
9
10
  const memory = context.machineState.memory.track(this.type);
10
11
  context.machineState.consumeGas(this.gasCost(memoryOperations));
11
12
 
12
- this.checkTags(memory, this.inTag, this.aOffset, this.bOffset);
13
+ const [aOffset, bOffset, dstOffset] = Addressing.fromWire(this.indirect).resolve(
14
+ [this.aOffset, this.bOffset, this.dstOffset],
15
+ memory,
16
+ );
17
+ this.checkTags(memory, this.inTag, aOffset, bOffset);
13
18
 
14
- const a = memory.getAs<IntegralValue>(this.aOffset);
15
- const b = memory.getAs<IntegralValue>(this.bOffset);
19
+ const a = memory.getAs<IntegralValue>(aOffset);
20
+ const b = memory.getAs<IntegralValue>(bOffset);
16
21
 
17
22
  const res = this.compute(a, b);
18
- memory.set(this.dstOffset, res);
23
+ memory.set(dstOffset, res);
19
24
 
20
25
  memory.assert(memoryOperations);
21
26
  context.machineState.incrementPc();
@@ -93,12 +98,12 @@ export class Not extends TwoOperandInstruction {
93
98
  const memory = context.machineState.memory.track(this.type);
94
99
  context.machineState.consumeGas(this.gasCost(memoryOperations));
95
100
 
96
- memory.checkTags(this.inTag, this.aOffset);
97
-
98
- const a = memory.getAs<IntegralValue>(this.aOffset);
101
+ const [aOffset, dstOffset] = Addressing.fromWire(this.indirect).resolve([this.aOffset, this.dstOffset], memory);
102
+ memory.checkTags(this.inTag, aOffset);
103
+ const a = memory.getAs<IntegralValue>(aOffset);
99
104
 
100
105
  const res = a.not();
101
- memory.set(this.dstOffset, res);
106
+ memory.set(dstOffset, res);
102
107
 
103
108
  memory.assert(memoryOperations);
104
109
  context.machineState.incrementPc();
@@ -1,6 +1,7 @@
1
1
  import type { AvmContext } from '../avm_context.js';
2
2
  import { type MemoryValue, Uint8 } from '../avm_memory_types.js';
3
3
  import { Opcode } from '../serialization/instruction_serialization.js';
4
+ import { Addressing } from './addressing_mode.js';
4
5
  import { ThreeOperandInstruction } from './instruction_impl.js';
5
6
 
6
7
  abstract class ComparatorInstruction extends ThreeOperandInstruction {
@@ -9,13 +10,17 @@ abstract class ComparatorInstruction extends ThreeOperandInstruction {
9
10
  const memory = context.machineState.memory.track(this.type);
10
11
  context.machineState.consumeGas(this.gasCost(memoryOperations));
11
12
 
12
- memory.checkTags(this.inTag, this.aOffset, this.bOffset);
13
+ const [aOffset, bOffset, dstOffset] = Addressing.fromWire(this.indirect).resolve(
14
+ [this.aOffset, this.bOffset, this.dstOffset],
15
+ memory,
16
+ );
17
+ memory.checkTags(this.inTag, aOffset, bOffset);
13
18
 
14
- const a = memory.get(this.aOffset);
15
- const b = memory.get(this.bOffset);
19
+ const a = memory.get(aOffset);
20
+ const b = memory.get(bOffset);
16
21
 
17
22
  const dest = new Uint8(this.compare(a, b) ? 1 : 0);
18
- memory.set(this.dstOffset, dest);
23
+ memory.set(dstOffset, dest);
19
24
 
20
25
  memory.assert(memoryOperations);
21
26
  context.machineState.incrementPc();
@@ -1,7 +1,7 @@
1
- import { AztecAddress, Fr } from '@aztec/circuits.js';
1
+ import { Fr } from '@aztec/circuits.js';
2
2
 
3
3
  import type { AvmContext } from '../avm_context.js';
4
- import { Field } from '../avm_memory_types.js';
4
+ import { Field, TypeTag } from '../avm_memory_types.js';
5
5
  import { Opcode, OperandType } from '../serialization/instruction_serialization.js';
6
6
  import { Addressing } from './addressing_mode.js';
7
7
  import { Instruction } from './instruction.js';
@@ -22,35 +22,31 @@ export class GetContractInstance extends Instruction {
22
22
  }
23
23
 
24
24
  async execute(context: AvmContext): Promise<void> {
25
+ const memoryOperations = { reads: 1, writes: 6, indirect: this.indirect };
26
+ const memory = context.machineState.memory.track(this.type);
27
+ context.machineState.consumeGas(this.gasCost(memoryOperations));
28
+
25
29
  const [addressOffset, dstOffset] = Addressing.fromWire(this.indirect).resolve(
26
30
  [this.addressOffset, this.dstOffset],
27
- context.machineState.memory,
31
+ memory,
28
32
  );
33
+ memory.checkTag(TypeTag.FIELD, addressOffset);
34
+
35
+ const address = memory.get(addressOffset).toFr();
36
+ const instance = await context.persistableState.getContractInstance(address);
37
+
38
+ const data = [
39
+ new Fr(instance.exists),
40
+ instance.salt,
41
+ instance.deployer.toField(),
42
+ instance.contractClassId,
43
+ instance.initializationHash,
44
+ instance.publicKeysHash,
45
+ ].map(f => new Field(f));
29
46
 
30
- const address = AztecAddress.fromField(context.machineState.memory.get(addressOffset).toFr());
31
- const instance = await context.persistableState.hostStorage.contractsDb.getContractInstance(address);
32
-
33
- const data =
34
- instance === undefined
35
- ? [
36
- new Field(0), // not found
37
- new Field(0),
38
- new Field(0),
39
- new Field(0),
40
- new Field(0),
41
- new Field(0),
42
- ]
43
- : [
44
- new Fr(1), // found
45
- instance.salt,
46
- instance.deployer.toField(),
47
- instance.contractClassId,
48
- instance.initializationHash,
49
- instance.publicKeysHash,
50
- ].map(f => new Field(f));
51
-
52
- context.machineState.memory.setSlice(dstOffset, data);
47
+ memory.setSlice(dstOffset, data);
53
48
 
49
+ memory.assert(memoryOperations);
54
50
  context.machineState.incrementPc();
55
51
  }
56
52
  }
@@ -2,6 +2,7 @@ import type { AvmContext } from '../avm_context.js';
2
2
  import { type IntegralValue } from '../avm_memory_types.js';
3
3
  import { InstructionExecutionError } from '../errors.js';
4
4
  import { Opcode, OperandType } from '../serialization/instruction_serialization.js';
5
+ import { Addressing } from './addressing_mode.js';
5
6
  import { Instruction } from './instruction.js';
6
7
 
7
8
  export class Jump extends Instruction {
@@ -44,7 +45,8 @@ export class JumpI extends Instruction {
44
45
  const memory = context.machineState.memory.track(this.type);
45
46
  context.machineState.consumeGas(this.gasCost(memoryOperations));
46
47
 
47
- const condition = memory.getAs<IntegralValue>(this.condOffset);
48
+ const [condOffset] = Addressing.fromWire(this.indirect).resolve([this.condOffset], memory);
49
+ const condition = memory.getAs<IntegralValue>(condOffset);
48
50
 
49
51
  // TODO: reconsider this casting
50
52
  if (condition.toBigInt() == 0n) {
@@ -0,0 +1,92 @@
1
+ import { Grumpkin } from '@aztec/circuits.js/barretenberg';
2
+ import { Point } from '@aztec/foundation/fields';
3
+
4
+ import { type AvmContext } from '../avm_context.js';
5
+ import { Field } from '../avm_memory_types.js';
6
+ import { Opcode, OperandType } from '../serialization/instruction_serialization.js';
7
+ import { Addressing } from './addressing_mode.js';
8
+ import { Instruction } from './instruction.js';
9
+
10
+ export class EcAdd extends Instruction {
11
+ static type: string = 'ECADD';
12
+ static readonly opcode = Opcode.ECADD;
13
+
14
+ // Informs (de)serialization. See Instruction.deserialize.
15
+ static readonly wireFormat: OperandType[] = [
16
+ OperandType.UINT8, // reserved
17
+ OperandType.UINT8, // indirect
18
+ OperandType.UINT32, // p1X
19
+ OperandType.UINT32, // p1Y
20
+ OperandType.UINT32, // p1IsInfinite
21
+ OperandType.UINT32, // p2X
22
+ OperandType.UINT32, // p2Y
23
+ OperandType.UINT32, // p2IsInfinite
24
+ OperandType.UINT32, // dst
25
+ ];
26
+
27
+ constructor(
28
+ private indirect: number,
29
+ private p1XOffset: number,
30
+ private p1YOffset: number,
31
+ private p1IsInfiniteOffset: number,
32
+ private p2XOffset: number,
33
+ private p2YOffset: number,
34
+ private p2IsInfiniteOffset: number,
35
+ private dstOffset: number,
36
+ ) {
37
+ super();
38
+ }
39
+
40
+ public async execute(context: AvmContext): Promise<void> {
41
+ const memoryOperations = { reads: 6, writes: 3, indirect: this.indirect };
42
+ const memory = context.machineState.memory.track(this.type);
43
+ context.machineState.consumeGas(this.gasCost(memoryOperations));
44
+
45
+ const [p1XOffset, p1YOffset, p1IsInfiniteOffset, p2XOffset, p2YOffset, p2IsInfiniteOffset, dstOffset] =
46
+ Addressing.fromWire(this.indirect).resolve(
47
+ [
48
+ this.p1XOffset,
49
+ this.p1YOffset,
50
+ this.p1IsInfiniteOffset,
51
+ this.p2XOffset,
52
+ this.p2YOffset,
53
+ this.p2IsInfiniteOffset,
54
+ this.dstOffset,
55
+ ],
56
+ memory,
57
+ );
58
+
59
+ const p1X = memory.get(p1XOffset);
60
+ const p1Y = memory.get(p1YOffset);
61
+ const p1IsInfinite = memory.get(p1IsInfiniteOffset).toNumber() === 1;
62
+ const p1 = new Point(p1X.toFr(), p1Y.toFr());
63
+ if (!p1.isOnGrumpkin()) {
64
+ throw new Error(`Point1 is not on the curve`);
65
+ }
66
+
67
+ const p2X = memory.get(p2XOffset);
68
+ const p2Y = memory.get(p2YOffset);
69
+ // unused. Point doesn't store this information
70
+ const p2IsInfinite = memory.get(p2IsInfiniteOffset).toNumber() === 1;
71
+ const p2 = new Point(p2X.toFr(), p2Y.toFr());
72
+ if (!p2.isOnGrumpkin()) {
73
+ throw new Error(`Point1 is not on the curve`);
74
+ }
75
+
76
+ const grumpkin = new Grumpkin();
77
+ let dest = grumpkin.add(p1, p2);
78
+ // Temporary,
79
+ if (p1IsInfinite) {
80
+ dest = p2;
81
+ } else if (p2IsInfinite) {
82
+ dest = p1;
83
+ }
84
+ memory.set(dstOffset, new Field(dest.x));
85
+ memory.set(dstOffset + 1, new Field(dest.y));
86
+ // Check representation of infinity for grumpkin
87
+ memory.set(dstOffset + 2, new Field(dest.equals(Point.ZERO) ? 1 : 0));
88
+
89
+ memory.assert(memoryOperations);
90
+ context.machineState.incrementPc();
91
+ }
92
+ }
@@ -1,10 +1,9 @@
1
1
  import { FunctionSelector, Gas } from '@aztec/circuits.js';
2
2
  import { padArrayEnd } from '@aztec/foundation/collection';
3
3
 
4
- import { convertAvmResultsToPxResult, createPublicExecution } from '../../public/transitional_adaptors.js';
5
4
  import type { AvmContext } from '../avm_context.js';
6
5
  import { gasLeftToGas } from '../avm_gas.js';
7
- import { Field, Uint8 } from '../avm_memory_types.js';
6
+ import { Field, TypeTag, Uint8 } from '../avm_memory_types.js';
8
7
  import { type AvmContractCallResults } from '../avm_message_call_result.js';
9
8
  import { AvmSimulator } from '../avm_simulator.js';
10
9
  import { RethrownError } from '../errors.js';
@@ -24,7 +23,6 @@ abstract class ExternalCall extends Instruction {
24
23
  OperandType.UINT32,
25
24
  OperandType.UINT32,
26
25
  OperandType.UINT32,
27
- /* temporary function selector */
28
26
  OperandType.UINT32,
29
27
  ];
30
28
 
@@ -37,8 +35,8 @@ abstract class ExternalCall extends Instruction {
37
35
  private retOffset: number,
38
36
  private retSize: number,
39
37
  private successOffset: number,
40
- // Function selector is temporary since eventually public contract bytecode will be one blob
41
- // containing all functions, and function selector will become an application-level mechanism
38
+ // NOTE: Function selector is likely temporary since eventually public contract bytecode will be one
39
+ // blob containing all functions, and function selector will become an application-level mechanism
42
40
  // (e.g. first few bytes of calldata + compiler-generated jump table)
43
41
  private functionSelectorOffset: number,
44
42
  ) {
@@ -53,9 +51,15 @@ abstract class ExternalCall extends Instruction {
53
51
  [this.gasOffset, this.addrOffset, this.argsOffset, this.argsSizeOffset, this.retOffset, this.successOffset],
54
52
  memory,
55
53
  );
54
+ memory.checkTags(TypeTag.FIELD, gasOffset, gasOffset + 1);
55
+ memory.checkTag(TypeTag.FIELD, addrOffset);
56
+ memory.checkTag(TypeTag.UINT32, argsSizeOffset);
57
+ memory.checkTag(TypeTag.FIELD, this.functionSelectorOffset);
56
58
 
57
- const callAddress = memory.getAs<Field>(addrOffset);
58
59
  const calldataSize = memory.get(argsSizeOffset).toNumber();
60
+ memory.checkTagsRange(TypeTag.FIELD, argsOffset, calldataSize);
61
+
62
+ const callAddress = memory.getAs<Field>(addrOffset);
59
63
  const calldata = memory.getSlice(argsOffset, calldataSize).map(f => f.toFr());
60
64
  const functionSelector = memory.getAs<Field>(this.functionSelectorOffset).toFr();
61
65
  // If we are already in a static call, we propagate the environment.
@@ -75,7 +79,6 @@ abstract class ExternalCall extends Instruction {
75
79
  const allocatedGas = { l2Gas: allocatedL2Gas, daGas: allocatedDaGas };
76
80
  context.machineState.consumeGas(allocatedGas);
77
81
 
78
- // TRANSITIONAL: This should be removed once the kernel handles and entire enqueued call per circuit
79
82
  const nestedContext = context.createNestedContractCallContext(
80
83
  callAddress.toFr(),
81
84
  calldata,
@@ -83,32 +86,9 @@ abstract class ExternalCall extends Instruction {
83
86
  callType,
84
87
  FunctionSelector.fromField(functionSelector),
85
88
  );
86
- const startSideEffectCounter = nestedContext.persistableState.trace.accessCounter;
87
89
 
88
- const oldStyleExecution = createPublicExecution(startSideEffectCounter, nestedContext.environment, calldata);
89
90
  const simulator = new AvmSimulator(nestedContext);
90
91
  const nestedCallResults: AvmContractCallResults = await simulator.execute();
91
- const pxResults = convertAvmResultsToPxResult(
92
- nestedCallResults,
93
- startSideEffectCounter,
94
- oldStyleExecution,
95
- Gas.from(allocatedGas),
96
- nestedContext,
97
- simulator.getBytecode(),
98
- );
99
- // store the old PublicExecutionResult object to maintain a recursive data structure for the old kernel
100
- context.persistableState.transitionalExecutionResult.nestedExecutions.push(pxResults);
101
- // END TRANSITIONAL
102
-
103
- // const nestedContext = context.createNestedContractCallContext(
104
- // callAddress.toFr(),
105
- // calldata,
106
- // allocatedGas,
107
- // this.type,
108
- // FunctionSelector.fromField(functionSelector),
109
- // );
110
- // const nestedCallResults: AvmContractCallResults = await new AvmSimulator(nestedContext).execute();
111
-
112
92
  const success = !nestedCallResults.reverted;
113
93
 
114
94
  // TRANSITIONAL: We rethrow here so that the MESSAGE gets propagated.
@@ -137,12 +117,16 @@ abstract class ExternalCall extends Instruction {
137
117
  // Refund unused gas
138
118
  context.machineState.refundGas(gasLeftToGas(nestedContext.machineState));
139
119
 
140
- // TODO: Should we merge the changes from a nested call in the case of a STATIC call?
141
- if (success) {
142
- context.persistableState.acceptNestedCallState(nestedContext.persistableState);
143
- } else {
144
- context.persistableState.rejectNestedCallState(nestedContext.persistableState);
145
- }
120
+ // Accept the nested call's state and trace the nested call
121
+ await context.persistableState.processNestedCall(
122
+ /*nestedState=*/ nestedContext.persistableState,
123
+ /*success=*/ success,
124
+ /*nestedEnvironment=*/ nestedContext.environment,
125
+ /*startGasLeft=*/ Gas.from(allocatedGas),
126
+ /*endGasLeft=*/ Gas.from(nestedContext.machineState.gasLeft),
127
+ /*bytecode=*/ simulator.getBytecode()!,
128
+ /*avmCallResults=*/ nestedCallResults,
129
+ );
146
130
 
147
131
  memory.assert(memoryOperations);
148
132
  context.machineState.incrementPc();
@@ -1,7 +1,7 @@
1
1
  import { keccak256, pedersenHash, poseidon2Permutation, sha256 } from '@aztec/foundation/crypto';
2
2
 
3
3
  import { type AvmContext } from '../avm_context.js';
4
- import { Field, Uint8 } from '../avm_memory_types.js';
4
+ import { Field, TypeTag, Uint8 } from '../avm_memory_types.js';
5
5
  import { Opcode, OperandType } from '../serialization/instruction_serialization.js';
6
6
  import { Addressing } from './addressing_mode.js';
7
7
  import { Instruction } from './instruction.js';
@@ -32,6 +32,7 @@ export class Poseidon2 extends Instruction {
32
32
  [this.inputStateOffset, this.outputStateOffset],
33
33
  memory,
34
34
  );
35
+ memory.checkTagsRange(TypeTag.FIELD, inputOffset, Poseidon2.stateSize);
35
36
 
36
37
  const inputState = memory.getSlice(inputOffset, Poseidon2.stateSize);
37
38
  const outputState = poseidon2Permutation(inputState);
@@ -74,10 +75,13 @@ export class Keccak extends Instruction {
74
75
  [this.dstOffset, this.messageOffset, this.messageSizeOffset],
75
76
  memory,
76
77
  );
78
+ memory.checkTag(TypeTag.UINT32, messageSizeOffset);
77
79
  const messageSize = memory.get(messageSizeOffset).toNumber();
78
80
  const memoryOperations = { reads: messageSize + 1, writes: 32, indirect: this.indirect };
79
81
  context.machineState.consumeGas(this.gasCost(memoryOperations));
80
82
 
83
+ memory.checkTagsRange(TypeTag.UINT8, messageOffset, messageSize);
84
+
81
85
  const messageData = Buffer.concat(memory.getSlice(messageOffset, messageSize).map(word => word.toBuffer()));
82
86
  const hashBuffer = keccak256(messageData);
83
87
 
@@ -119,9 +123,11 @@ export class Sha256 extends Instruction {
119
123
  [this.dstOffset, this.messageOffset, this.messageSizeOffset],
120
124
  memory,
121
125
  );
126
+ memory.checkTag(TypeTag.UINT32, messageSizeOffset);
122
127
  const messageSize = memory.get(messageSizeOffset).toNumber();
123
128
  const memoryOperations = { reads: messageSize + 1, writes: 32, indirect: this.indirect };
124
129
  context.machineState.consumeGas(this.gasCost(memoryOperations));
130
+ memory.checkTagsRange(TypeTag.UINT8, messageOffset, messageSize);
125
131
 
126
132
  const messageData = Buffer.concat(memory.getSlice(messageOffset, messageSize).map(word => word.toBuffer()));
127
133
  const hashBuffer = sha256(messageData);
@@ -168,12 +174,16 @@ export class Pedersen extends Instruction {
168
174
 
169
175
  // We hash a set of field elements
170
176
  const genIndex = Number(memory.get(genIndexOffset).toBigInt());
177
+ memory.checkTag(TypeTag.UINT32, genIndexOffset);
171
178
  const messageSize = Number(memory.get(messageSizeOffset).toBigInt());
179
+ memory.checkTag(TypeTag.UINT32, messageSizeOffset);
172
180
  const hashData = memory.getSlice(messageOffset, messageSize);
173
181
 
174
182
  const memoryOperations = { reads: messageSize + 2, writes: 1, indirect: this.indirect };
175
183
  context.machineState.consumeGas(this.gasCost(memoryOperations));
176
184
 
185
+ memory.checkTagsRange(TypeTag.FIELD, messageOffset, messageSize);
186
+
177
187
  // No domain sep for now
178
188
  const hash = pedersenHash(hashData, genIndex);
179
189
  memory.set(dstOffset, new Field(hash));
@@ -1,6 +1,7 @@
1
1
  import { type AvmContext } from '../avm_context.js';
2
2
  import { type MemoryValue } from '../avm_memory_types.js';
3
3
  import { OperandType } from '../serialization/instruction_serialization.js';
4
+ import { Addressing } from './addressing_mode.js';
4
5
  import { Instruction } from './instruction.js';
5
6
 
6
7
  /** Wire format that informs deserialization for instructions with two operands. */
@@ -72,7 +73,9 @@ export abstract class GetterInstruction extends Instruction {
72
73
  const memory = context.machineState.memory.track(this.type);
73
74
  context.machineState.consumeGas(this.gasCost(memoryOperations));
74
75
 
75
- memory.set(this.dstOffset, this.getValue(context));
76
+ const [dstOffset] = Addressing.fromWire(this.indirect).resolve([this.dstOffset], memory);
77
+
78
+ memory.set(dstOffset, this.getValue(context));
76
79
 
77
80
  memory.assert(memoryOperations);
78
81
  context.machineState.incrementPc();