diff --git a/evm/src/cpu/kernel/asm/basic_macros.asm b/evm/src/cpu/kernel/asm/basic_macros.asm index 7bf001b4..854e0a1a 100644 --- a/evm/src/cpu/kernel/asm/basic_macros.asm +++ b/evm/src/cpu/kernel/asm/basic_macros.asm @@ -26,6 +26,24 @@ %endrep %endmacro +%macro pop5 + %rep 5 + pop + %endrep +%endmacro + +%macro pop6 + %rep 6 + pop + %endrep +%endmacro + +%macro pop7 + %rep 7 + pop + %endrep +%endmacro + %macro add_const(c) // stack: input, ... PUSH $c diff --git a/evm/src/cpu/kernel/asm/memory.asm b/evm/src/cpu/kernel/asm/memory.asm index e3af9954..0bf0fbd1 100644 --- a/evm/src/cpu/kernel/asm/memory.asm +++ b/evm/src/cpu/kernel/asm/memory.asm @@ -1,4 +1,4 @@ -// Load a byte from the given segment of the current context's memory space. +// Load a value from the given segment of the current context's memory space. // Note that main memory values are one byte each, but in general memory values // can be 256 bits. This macro deals with a single address (unlike MLOAD), so // if it is used with main memory, it will load a single byte. @@ -12,7 +12,7 @@ // stack: value %endmacro -// Store a byte to the given segment of the current context's memory space. +// Store a value to the given segment of the current context's memory space. // Note that main memory values are one byte each, but in general memory values // can be 256 bits. This macro deals with a single address (unlike MSTORE), so // if it is used with main memory, it will store a single byte. @@ -25,3 +25,55 @@ MSTORE_GENERAL // stack: (empty) %endmacro + +// Copies `count` values from +// SRC = (src_ctx, src_segment, src_addr) +// to +// DST = (dst_ctx, dst_segment, dst_addr). +// These tuple definitions are used for brevity in the stack comments below. +global memcpy: + JUMPDEST + // stack: DST, SRC, count, retdest + DUP7 + // stack: count, DST, SRC, count, retdest + ISZERO + // stack: count == 0, DST, SRC, count, retdest + %jumpi memcpy_finish + // stack: DST, SRC, count, retdest + + // Copy the next value. + DUP6 + DUP6 + DUP6 + // stack: SRC, DST, SRC, count, retdest + MLOAD_GENERAL + // stack: value, DST, SRC, count, retdest + DUP4 + DUP4 + DUP4 + // stack: DST, value, DST, SRC, count, retdest + MSTORE_GENERAL + // stack: DST, SRC, count, retdest + + // Increment dst_addr. + SWAP2 + %add_const(1) + SWAP2 + // Increment src_addr. + SWAP5 + %add_const(1) + SWAP5 + // Decrement count. + SWAP6 + %sub_const(1) + SWAP6 + + // Recurse! + JUMP memcpy + +memcpy_finish: + JUMPDEST + // stack: DST, SRC, count, retdest + %pop7 + // stack: retdest + JUMP