diff --git a/yarn-project/acir-simulator/src/avm/avm_context.ts b/yarn-project/acir-simulator/src/avm/avm_context.ts index 79e763f79f4..ec3fd17a87a 100644 --- a/yarn-project/acir-simulator/src/avm/avm_context.ts +++ b/yarn-project/acir-simulator/src/avm/avm_context.ts @@ -1,5 +1,4 @@ -import { Fr } from '@aztec/foundation/fields'; - +import { AvmExecutionEnvironment } from './avm_execution_environment.js'; import { AvmMachineState } from './avm_machine_state.js'; import { AvmMessageCallResult } from './avm_message_call_result.js'; import { AvmStateManager } from './avm_state_manager.js'; @@ -13,9 +12,13 @@ import { Instruction } from './opcodes/index.js'; * It stores a state manager */ export class AvmContext { + /** Contains constant variables provided by the kernel */ + private executionEnvironment: AvmExecutionEnvironment; + /** A wrapper that manages mutable state during execution - (caching, fetching) */ private stateManager: AvmStateManager; - constructor(stateManager: AvmStateManager) { + constructor(executionEnvironment: AvmExecutionEnvironment, stateManager: AvmStateManager) { + this.executionEnvironment = executionEnvironment; this.stateManager = stateManager; } @@ -26,17 +29,15 @@ export class AvmContext { * - We interpret the bytecode * - We run the interpreter * - * @param contractAddress - - * @param calldata - */ - public call(contractAddress: Fr, calldata: Fr[]): AvmMessageCallResult { + public call(): AvmMessageCallResult { // NOTE: the following is mocked as getPublicBytecode does not exist yet - // const bytecode = stateManager.journal.hostStorage.contractsDb.getBytecode(contractAddress); + // const bytecode = stateManager.journal.hostStorage.contractsDb.getBytecode(this.executionEnvironment.address); const bytecode = Buffer.from('0x01000100020003'); const instructions: Instruction[] = decodeBytecode(bytecode); - const context = new AvmMachineState(calldata); + const context = new AvmMachineState(this.executionEnvironment); const interpreter = new AvmInterpreter(context, this.stateManager, instructions); return interpreter.run(); diff --git a/yarn-project/acir-simulator/src/avm/avm_execution_environment.ts b/yarn-project/acir-simulator/src/avm/avm_execution_environment.ts new file mode 100644 index 00000000000..495a579feab --- /dev/null +++ b/yarn-project/acir-simulator/src/avm/avm_execution_environment.ts @@ -0,0 +1,39 @@ +import { GlobalVariables } from '@aztec/circuits.js'; +import { AztecAddress } from '@aztec/foundation/aztec-address'; +import { EthAddress } from '@aztec/foundation/eth-address'; +import { Fr } from '@aztec/foundation/fields'; + +/** + * Contains variables that remain constant during AVM execution + * These variables are provided by the public kernel circuit + */ +export class AvmExecutionEnvironment { + constructor( + /** - */ + public readonly address: AztecAddress, + /** - */ + public readonly storageAddress: AztecAddress, + /** - */ + public readonly origin: AztecAddress, + /** - */ + public readonly sender: AztecAddress, + /** - */ + public readonly portal: EthAddress, + /** - */ + public readonly feePerL1Gas: Fr, + /** - */ + public readonly feePerL2Gas: Fr, + /** - */ + public readonly feePerDaGas: Fr, + /** - */ + public readonly contractCallDepth: Fr, + /** - */ + public readonly globals: GlobalVariables, + /** - */ + public readonly isStaticCall: boolean, + /** - */ + public readonly isDelegateCall: boolean, + /** - */ + public readonly calldata: Fr[], + ) {} +} diff --git a/yarn-project/acir-simulator/src/avm/avm_machine_state.ts b/yarn-project/acir-simulator/src/avm/avm_machine_state.ts index bdb9dfcc7c8..dc1ce28aa23 100644 --- a/yarn-project/acir-simulator/src/avm/avm_machine_state.ts +++ b/yarn-project/acir-simulator/src/avm/avm_machine_state.ts @@ -1,13 +1,18 @@ import { Fr } from '@aztec/foundation/fields'; +import { AvmExecutionEnvironment } from './avm_execution_environment.js'; import { TaggedMemory } from './avm_memory_types.js'; /** * Store's data for an Avm execution frame */ export class AvmMachineState { - /** - */ - public readonly calldata: Fr[]; + /** + * Execution environment contains hard coded information that is received from the kernel + * Items like, the block header and global variables fall within this category + */ + public readonly executionEnvironment: AvmExecutionEnvironment; + private returnData: Fr[]; /** - */ @@ -31,10 +36,9 @@ export class AvmMachineState { /** * Create a new avm context - * @param calldata - + * @param executionEnvironment - Machine context that is passed to the avm */ - constructor(calldata: Fr[]) { - this.calldata = calldata; + constructor(executionEnvironment: AvmExecutionEnvironment) { this.returnData = []; this.memory = new TaggedMemory(); this.internalCallStack = []; @@ -43,6 +47,8 @@ export class AvmMachineState { this.callStack = []; this.halted = false; + + this.executionEnvironment = executionEnvironment; } /** diff --git a/yarn-project/acir-simulator/src/avm/avm_state_manager.ts b/yarn-project/acir-simulator/src/avm/avm_state_manager.ts index b5396accc7a..d75c25c72a1 100644 --- a/yarn-project/acir-simulator/src/avm/avm_state_manager.ts +++ b/yarn-project/acir-simulator/src/avm/avm_state_manager.ts @@ -1,4 +1,5 @@ -import { BlockHeader } from '@aztec/circuits.js'; +import { AztecAddress, BlockHeader } from '@aztec/circuits.js'; +import { Fr } from '@aztec/foundation/fields'; import { AvmJournal, HostStorage } from './journal/index.js'; @@ -42,4 +43,23 @@ export class AvmStateManager { const journal = AvmJournal.branchParent(parent.journal); return new AvmStateManager(parent.blockHeader, journal); } + + /** + * Passes storage call to the journal + * @param contractAddress - + * @param slot - + * @param value - + */ + public store(contractAddress: AztecAddress, slot: Fr, value: Fr): void { + this.journal.writeStorage(contractAddress, slot, value); + } + + /** + * Passes storage read from the journal + * @param contractAddress - + * @param slot - + */ + public read(contractAddress: AztecAddress, slot: Fr): Promise { + return this.journal.readStorage(contractAddress, slot); + } } diff --git a/yarn-project/acir-simulator/src/avm/fixtures/index.ts b/yarn-project/acir-simulator/src/avm/fixtures/index.ts index cfab7bc47b8..fb16ebf4ee3 100644 --- a/yarn-project/acir-simulator/src/avm/fixtures/index.ts +++ b/yarn-project/acir-simulator/src/avm/fixtures/index.ts @@ -1 +1,60 @@ // Place large AVM text fixtures in here +import { GlobalVariables } from '@aztec/circuits.js'; +import { AztecAddress } from '@aztec/foundation/aztec-address'; +import { EthAddress } from '@aztec/foundation/eth-address'; +import { Fr } from '@aztec/foundation/fields'; + +import { AvmExecutionEnvironment } from '../avm_execution_environment.js'; + +/** + * An interface that allows to override the default values of the AvmExecutionEnvironment + */ +export interface AvmExecutionEnvironmentOverrides { + /** - */ + address?: AztecAddress; + /** - */ + storageAddress?: AztecAddress; + /** - */ + origin?: AztecAddress; + /** - */ + sender?: AztecAddress; + /** - */ + portal?: EthAddress; + /** - */ + feePerL1Gas?: Fr; + /** - */ + feePerL2Gas?: Fr; + /** - */ + feePerDaGas?: Fr; + /** - */ + contractCallDepth?: Fr; + /** - */ + globals?: GlobalVariables; + /** - */ + isStaticCall?: boolean; + /** - */ + isDelegateCall?: boolean; + /** - */ + calldata?: Fr[]; +} + +/** + * Create an empty instance of the Execution Environment where all values are zero, unless overriden in the overrides object + */ +export function initExecutionEnvironment(overrides?: AvmExecutionEnvironmentOverrides): AvmExecutionEnvironment { + return new AvmExecutionEnvironment( + overrides?.address ?? AztecAddress.zero(), + overrides?.storageAddress ?? AztecAddress.zero(), + overrides?.origin ?? AztecAddress.zero(), + overrides?.sender ?? AztecAddress.zero(), + overrides?.portal ?? EthAddress.ZERO, + overrides?.feePerL1Gas ?? Fr.zero(), + overrides?.feePerL2Gas ?? Fr.zero(), + overrides?.feePerDaGas ?? Fr.zero(), + overrides?.contractCallDepth ?? Fr.zero(), + overrides?.globals ?? GlobalVariables.empty(), + overrides?.isStaticCall ?? false, + overrides?.isDelegateCall ?? false, + overrides?.calldata ?? [], + ); +} diff --git a/yarn-project/acir-simulator/src/avm/index.test.ts b/yarn-project/acir-simulator/src/avm/index.test.ts index 1db8306447a..bb1b15bffe0 100644 --- a/yarn-project/acir-simulator/src/avm/index.test.ts +++ b/yarn-project/acir-simulator/src/avm/index.test.ts @@ -4,6 +4,7 @@ import { mock } from 'jest-mock-extended'; import { AvmMachineState } from './avm_machine_state.js'; import { AvmStateManager } from './avm_state_manager.js'; +import { initExecutionEnvironment } from './fixtures/index.js'; import { AvmInterpreter } from './interpreter/interpreter.js'; import { decodeBytecode } from './opcodes/decode_bytecode.js'; import { encodeToBytecode } from './opcodes/encode_to_bytecode.js'; @@ -28,7 +29,7 @@ describe('avm', () => { const instructions = decodeBytecode(fullBytecode); // Execute instructions - const context = new AvmMachineState(calldata); + const context = new AvmMachineState(initExecutionEnvironment({ calldata })); const interpreter = new AvmInterpreter(context, stateManager, instructions); const avmReturnData = interpreter.run(); diff --git a/yarn-project/acir-simulator/src/avm/interpreter/interpreter.test.ts b/yarn-project/acir-simulator/src/avm/interpreter/interpreter.test.ts index 7f252ec739c..cd6b93d592c 100644 --- a/yarn-project/acir-simulator/src/avm/interpreter/interpreter.test.ts +++ b/yarn-project/acir-simulator/src/avm/interpreter/interpreter.test.ts @@ -1,9 +1,10 @@ import { Fr } from '@aztec/foundation/fields'; -import { mock } from 'jest-mock-extended'; +import { MockProxy, mock } from 'jest-mock-extended'; import { AvmMachineState } from '../avm_machine_state.js'; import { AvmStateManager } from '../avm_state_manager.js'; +import { initExecutionEnvironment } from '../fixtures/index.js'; import { Add } from '../opcodes/arithmetic.js'; import { Jump, Return } from '../opcodes/control_flow.js'; import { Instruction } from '../opcodes/instruction.js'; @@ -11,9 +12,14 @@ import { CalldataCopy } from '../opcodes/memory.js'; import { AvmInterpreter, InvalidProgramCounterError } from './interpreter.js'; describe('interpreter', () => { + let stateManager: MockProxy; + + beforeEach(() => { + stateManager = mock(); + }); + it('Should execute a series of instructions', () => { const calldata: Fr[] = [new Fr(1), new Fr(2)]; - const stateManager = mock(); const instructions: Instruction[] = [ new CalldataCopy(/*cdOffset=*/ 0, /*copySize=*/ 2, /*destOffset=*/ 0), @@ -21,7 +27,7 @@ describe('interpreter', () => { new Return(/*returnOffset=*/ 2, /*copySize=*/ 1), ]; - const context = new AvmMachineState(calldata); + const context = new AvmMachineState(initExecutionEnvironment({ calldata })); const interpreter = new AvmInterpreter(context, stateManager, instructions); const avmReturnData = interpreter.run(); @@ -32,13 +38,12 @@ describe('interpreter', () => { it('Should revert with an invalid jump', () => { const calldata: Fr[] = []; - const stateManager = mock(); const invalidJumpDestination = 22; const instructions: Instruction[] = [new Jump(invalidJumpDestination)]; - const context = new AvmMachineState(calldata); + const context = new AvmMachineState(initExecutionEnvironment({ calldata })); const interpreter = new AvmInterpreter(context, stateManager, instructions); const avmReturnData = interpreter.run(); diff --git a/yarn-project/acir-simulator/src/avm/opcodes/arithmetic.test.ts b/yarn-project/acir-simulator/src/avm/opcodes/arithmetic.test.ts index 51059a38854..9f45eb15ac5 100644 --- a/yarn-project/acir-simulator/src/avm/opcodes/arithmetic.test.ts +++ b/yarn-project/acir-simulator/src/avm/opcodes/arithmetic.test.ts @@ -1,16 +1,17 @@ -import { mock } from 'jest-mock-extended'; +import { MockProxy, mock } from 'jest-mock-extended'; import { AvmMachineState } from '../avm_machine_state.js'; import { Field } from '../avm_memory_types.js'; import { AvmStateManager } from '../avm_state_manager.js'; +import { initExecutionEnvironment } from '../fixtures/index.js'; import { Add, Div, Mul, Sub } from './arithmetic.js'; describe('Arithmetic Instructions', () => { let machineState: AvmMachineState; - let stateManager = mock(); + let stateManager: MockProxy; beforeEach(() => { - machineState = new AvmMachineState([]); + machineState = new AvmMachineState(initExecutionEnvironment()); stateManager = mock(); }); diff --git a/yarn-project/acir-simulator/src/avm/opcodes/bitwise.test.ts b/yarn-project/acir-simulator/src/avm/opcodes/bitwise.test.ts index 6fe969513fa..4221f338972 100644 --- a/yarn-project/acir-simulator/src/avm/opcodes/bitwise.test.ts +++ b/yarn-project/acir-simulator/src/avm/opcodes/bitwise.test.ts @@ -3,6 +3,7 @@ import { mock } from 'jest-mock-extended'; import { AvmMachineState } from '../avm_machine_state.js'; import { TypeTag, Uint16, Uint32 } from '../avm_memory_types.js'; import { AvmStateManager } from '../avm_state_manager.js'; +import { initExecutionEnvironment } from '../fixtures/index.js'; import { And, Not, Or, Shl, Shr, Xor } from './bitwise.js'; describe('Bitwise instructions', () => { @@ -10,7 +11,7 @@ describe('Bitwise instructions', () => { let stateManager = mock(); beforeEach(() => { - machineState = new AvmMachineState([]); + machineState = new AvmMachineState(initExecutionEnvironment()); stateManager = mock(); }); diff --git a/yarn-project/acir-simulator/src/avm/opcodes/control_flow.test.ts b/yarn-project/acir-simulator/src/avm/opcodes/control_flow.test.ts index c30825ba912..f703242cc5a 100644 --- a/yarn-project/acir-simulator/src/avm/opcodes/control_flow.test.ts +++ b/yarn-project/acir-simulator/src/avm/opcodes/control_flow.test.ts @@ -1,8 +1,9 @@ -import { mock } from 'jest-mock-extended'; +import { MockProxy, mock } from 'jest-mock-extended'; import { AvmMachineState } from '../avm_machine_state.js'; import { TypeTag, Uint16 } from '../avm_memory_types.js'; import { AvmStateManager } from '../avm_state_manager.js'; +import { initExecutionEnvironment } from '../fixtures/index.js'; import { Add, Mul, Sub } from './arithmetic.js'; import { And, Not, Or, Shl, Shr, Xor } from './bitwise.js'; import { Eq, Lt, Lte } from './comparators.js'; @@ -11,12 +12,12 @@ import { InstructionExecutionError } from './instruction.js'; import { CMov, CalldataCopy, Cast, Mov, Set } from './memory.js'; describe('Control Flow Opcodes', () => { - let stateManager = mock(); + let stateManager: MockProxy; let machineState: AvmMachineState; beforeEach(() => { stateManager = mock(); - machineState = new AvmMachineState([]); + machineState = new AvmMachineState(initExecutionEnvironment()); }); it('Should implement JUMP', () => { @@ -138,7 +139,7 @@ describe('Control Flow Opcodes', () => { for (const instruction of instructions) { // Use a fresh machine state each run - const innerMachineState = new AvmMachineState([]); + const innerMachineState = new AvmMachineState(initExecutionEnvironment()); innerMachineState.memory.set(0, new Uint16(4n)); innerMachineState.memory.set(1, new Uint16(8n)); innerMachineState.memory.set(2, new Uint16(12n)); diff --git a/yarn-project/acir-simulator/src/avm/opcodes/instruction_set.ts b/yarn-project/acir-simulator/src/avm/opcodes/instruction_set.ts index 664467f887d..3413673f7e6 100644 --- a/yarn-project/acir-simulator/src/avm/opcodes/instruction_set.ts +++ b/yarn-project/acir-simulator/src/avm/opcodes/instruction_set.ts @@ -1,10 +1,11 @@ import { Add, Div, Mul, Sub } from './arithmetic.js'; import { And, Not, Or, Shl, Shr, Xor } from './bitwise.js'; -//import { Eq, Lt, Lte } from './comparators.js'; import { InternalCall, InternalReturn, Jump, JumpI, Return } from './control_flow.js'; import { Instruction } from './instruction.js'; import { CMov, CalldataCopy, Cast, Mov, Set } from './memory.js'; import { Opcode } from './opcodes.js'; +//import { Eq, Lt, Lte } from './comparators.js'; +import { SLoad, SStore } from './storage.js'; /** - */ type InstructionConstructor = new (...args: any[]) => Instruction; @@ -75,8 +76,8 @@ export const INSTRUCTION_SET: Map = ne //// World State //[Opcode.BLOCKHEADERBYNUMBER, Blockheaderbynumber], - //[Opcode.SLOAD, Sload], // Public Storage - //[Opcode.SSTORE, Sstore], // Public Storage + [Opcode.SLOAD, SLoad], // Public Storage + [Opcode.SSTORE, SStore], // Public Storage //[Opcode.READL1TOL2MSG, Readl1tol2msg], // Messages //[Opcode.SENDL2TOL1MSG, Sendl2tol1msg], // Messages //[Opcode.EMITNOTEHASH, Emitnotehash], // Notes & Nullifiers diff --git a/yarn-project/acir-simulator/src/avm/opcodes/memory.test.ts b/yarn-project/acir-simulator/src/avm/opcodes/memory.test.ts index 1c8b49ea678..5c3edb9e379 100644 --- a/yarn-project/acir-simulator/src/avm/opcodes/memory.test.ts +++ b/yarn-project/acir-simulator/src/avm/opcodes/memory.test.ts @@ -5,6 +5,7 @@ import { mock } from 'jest-mock-extended'; import { AvmMachineState } from '../avm_machine_state.js'; import { Field, TypeTag, Uint8, Uint16, Uint32, Uint64, Uint128 } from '../avm_memory_types.js'; import { AvmStateManager } from '../avm_state_manager.js'; +import { initExecutionEnvironment } from '../fixtures/index.js'; import { CMov, CalldataCopy, Cast, Mov, Set } from './memory.js'; describe('Memory instructions', () => { @@ -12,7 +13,7 @@ describe('Memory instructions', () => { let stateManager = mock(); beforeEach(() => { - machineState = new AvmMachineState([]); + machineState = new AvmMachineState(initExecutionEnvironment()); stateManager = mock(); }); @@ -242,7 +243,7 @@ describe('Memory instructions', () => { describe('CALLDATACOPY', () => { it('Writes nothing if size is 0', () => { const calldata = [new Fr(1n), new Fr(2n), new Fr(3n)]; - machineState = new AvmMachineState(calldata); + machineState = new AvmMachineState(initExecutionEnvironment({ calldata })); machineState.memory.set(0, new Uint16(12)); // Some previous data to be overwritten new CalldataCopy(/*cdOffset=*/ 0, /*copySize=*/ 0, /*dstOffset=*/ 0).execute(machineState, stateManager); @@ -253,7 +254,7 @@ describe('Memory instructions', () => { it('Copies all calldata', () => { const calldata = [new Fr(1n), new Fr(2n), new Fr(3n)]; - machineState = new AvmMachineState(calldata); + machineState = new AvmMachineState(initExecutionEnvironment({ calldata })); machineState.memory.set(0, new Uint16(12)); // Some previous data to be overwritten new CalldataCopy(/*cdOffset=*/ 0, /*copySize=*/ 3, /*dstOffset=*/ 0).execute(machineState, stateManager); @@ -264,7 +265,7 @@ describe('Memory instructions', () => { it('Copies slice of calldata', () => { const calldata = [new Fr(1n), new Fr(2n), new Fr(3n)]; - machineState = new AvmMachineState(calldata); + machineState = new AvmMachineState(initExecutionEnvironment({ calldata })); machineState.memory.set(0, new Uint16(12)); // Some previous data to be overwritten new CalldataCopy(/*cdOffset=*/ 1, /*copySize=*/ 2, /*dstOffset=*/ 0).execute(machineState, stateManager); diff --git a/yarn-project/acir-simulator/src/avm/opcodes/memory.ts b/yarn-project/acir-simulator/src/avm/opcodes/memory.ts index cd546a448c6..5645246b962 100644 --- a/yarn-project/acir-simulator/src/avm/opcodes/memory.ts +++ b/yarn-project/acir-simulator/src/avm/opcodes/memory.ts @@ -87,7 +87,7 @@ export class CalldataCopy extends Instruction { } execute(machineState: AvmMachineState, _stateManager: AvmStateManager): void { - const transformedData = machineState.calldata + const transformedData = machineState.executionEnvironment.calldata .slice(this.cdOffset, this.cdOffset + this.copySize) .map(f => new Field(f)); machineState.memory.setSlice(this.dstOffset, transformedData); diff --git a/yarn-project/acir-simulator/src/avm/opcodes/storage.test.ts b/yarn-project/acir-simulator/src/avm/opcodes/storage.test.ts new file mode 100644 index 00000000000..265bf670e20 --- /dev/null +++ b/yarn-project/acir-simulator/src/avm/opcodes/storage.test.ts @@ -0,0 +1,53 @@ +import { AztecAddress } from '@aztec/foundation/aztec-address'; +import { Fr } from '@aztec/foundation/fields'; + +import { MockProxy, mock } from 'jest-mock-extended'; + +import { AvmMachineState } from '../avm_machine_state.js'; +import { AvmStateManager } from '../avm_state_manager.js'; +import { initExecutionEnvironment } from '../fixtures/index.js'; +import { SLoad, SStore } from './storage.js'; + +describe('Storage Instructions', () => { + let stateManager: MockProxy; + let machineState: AvmMachineState; + const address = AztecAddress.random(); + + beforeEach(() => { + stateManager = mock(); + + const executionEnvironment = initExecutionEnvironment({ address, storageAddress: address }); + machineState = new AvmMachineState(executionEnvironment); + }); + + it('Sstore should Write into storage', () => { + const a = new Fr(1n); + const b = new Fr(2n); + + machineState.memory.set(0, a); + machineState.memory.set(1, b); + + new SStore(0, 1).execute(machineState, stateManager); + + expect(stateManager.store).toBeCalledWith(address, a, b); + }); + + it('Sload should Read into storage', async () => { + // Mock response + const expectedResult = new Fr(1n); + stateManager.read.mockReturnValueOnce(Promise.resolve(expectedResult)); + + const a = new Fr(1n); + const b = new Fr(2n); + + machineState.memory.set(0, a); + machineState.memory.set(1, b); + + await new SLoad(0, 1).execute(machineState, stateManager); + + expect(stateManager.read).toBeCalledWith(address, a); + + const actual = machineState.memory.get(1); + expect(actual).toEqual(expectedResult); + }); +}); diff --git a/yarn-project/acir-simulator/src/avm/opcodes/storage.ts b/yarn-project/acir-simulator/src/avm/opcodes/storage.ts new file mode 100644 index 00000000000..3f79594cb31 --- /dev/null +++ b/yarn-project/acir-simulator/src/avm/opcodes/storage.ts @@ -0,0 +1,48 @@ +import { Fr } from '@aztec/foundation/fields'; + +import { AvmMachineState } from '../avm_machine_state.js'; +import { AvmStateManager } from '../avm_state_manager.js'; +import { Instruction } from './instruction.js'; + +/** - */ +export class SStore extends Instruction { + static type: string = 'SSTORE'; + static numberOfOperands = 2; + + constructor(private slotOffset: number, private dataOffset: number) { + super(); + } + + execute(machineState: AvmMachineState, stateManager: AvmStateManager): void { + const slot = machineState.memory.get(this.slotOffset); + const data = machineState.memory.get(this.dataOffset); + + stateManager.store( + machineState.executionEnvironment.storageAddress, + new Fr(slot.toBigInt()), + new Fr(data.toBigInt()), + ); + + this.incrementPc(machineState); + } +} + +/** - */ +export class SLoad extends Instruction { + static type: string = 'SLOAD'; + static numberOfOperands = 2; + + constructor(private slotOffset: number, private destOffset: number) { + super(); + } + + async execute(machineState: AvmMachineState, stateManager: AvmStateManager): Promise { + const slot = machineState.memory.get(this.slotOffset); + + const data = stateManager.read(machineState.executionEnvironment.storageAddress, new Fr(slot.toBigInt())); + + machineState.memory.set(this.destOffset, await data); + + this.incrementPc(machineState); + } +} diff --git a/yellow-paper/docs/public-vm/avm.md b/yellow-paper/docs/public-vm/avm.md index b3417afcb29..60f06218ab6 100644 --- a/yellow-paper/docs/public-vm/avm.md +++ b/yellow-paper/docs/public-vm/avm.md @@ -70,7 +70,7 @@ ExecutionEnvironment { storageAddress: AztecAddress, origin: AztecAddress, sender: AztecAddress, - portal: AztecAddress, + portal: EthAddress, feePerL1Gas: field, feePerL2Gas: field, feePerDaGas: field,