EIP-7877 - Enhanced RETURN opcodes

Created 2025-01-31
Status Stagnant
Category Core
Type Standards Track
Authors
Requires

Abstract

This EIP specifies a series of new RETURN opcodes which allow the user to specify which data location to return from instead of defaulting to returning from memory.

Motivation

With the introduction of transient storage, many smart contracts have begun to store data using the new transient opcodes to optimize for gas usage, whereby a callback involves returning the data previously stored transiently. However, the current RETURN opcode only allows for returning sequential bytes in memory. This requires developers to incur additional gas overhead by manually writing data from transient storage to memory before returning, incuring both an additional memory expansion and opcode cost from complicated for-loops. Similar inefficiencies already occur when attempting to return data already placed in storage. This EIP attempts to rectify this by allowing developers to optimize their code by deciding where to return data from directly, instead of requiring the intermediate step of first copying the data to memory.

Specification

This EIP introduces 3 new opcodes as well as renaming/aliasing an existing one.

SRETURN (0xf6)
TRETURN (0xf7)
RRETURN (0xf8)

RETURN -> MRETURN (0xf3)

The MRETURN opcode is a rename of RETURN, whereby sequential bytes in memory are returned. It will operate exactly as it currenty does as of the Cancun hard-fork, and its gas cost will remain the same.

RRETURN operates similar to MRETURN. It pops two items off the stack: offset (starting byte index into the current call’s RETURNDATA buffer) and length (number of bytes to return). It returns the slice RETURNDATA[offset : offset + length). Bounds and error semantics are identical to RETURNDATACOPY per EIP-211: if offset + length > RETURNDATASIZE, execution fails; zero-length reads at bounds are allowed.

SRETURN and TRETURN operate similarly, except on storage and transient storage respectively. Each pops two items off the stack: slot (starting storage slot index) and length (byte length to return). Bytes are produced by serializing consecutive slots starting at slot in ascending order (slot, slot + 1, …). Each slot is serialized as its 32 raw bytes exactly as if the 256-bit word were written to memory via MSTORE (i.e., big-endian 32-byte representation). The returned byte stream is the first length bytes of this concatenation. If length is not a multiple of 32, the final slot contributes only the first length % 32 bytes of its 32-byte image. If length == 0, zero bytes are returned. Reads of uninitialized storage/transient slots yield 32 zero bytes each.

The cost for these opcodes should be similar to the cost of accessing data now.

SRETURN = (number_of_cold_slots) * 2100 + (numer_of_warm_slots * 100)
TRETURN = number_of_slots * 100

RRETURN = cost of RETURNDATACOPY without memory_expansion cost

minimum_word_size = (size + 31) / 32

static_gas = 3
dynamic_gas = 3 * minimum_word_size

overall = static_gas + dynamic_gas

Rationale

Allowing for more targeted return opcodes allows for saving gas at all levels of smart contract optimization by eliminating the intermediate steps of first writing any data to memory before returning. In events where this data may be large, this can result in significant gas savings. These opcodes can be built into the Solidity compiler directly so that all contracts can take advantage of them. Similarly, by making return more explicit it allows for better static analysis by avoiding messy memory allocations.

There is precedent for these changes.

EIP-3855: Introducing PUSH0 opcode to optimize away alternative methods of pushing 0 onto the stack.

EIP-6: Renaming SUICIDE to SELFDESTRUCT without changing functionality.

Backwards Compatibility

There are no backwards compatibility concerns, as MRETURN will utilize the same gas cost and opcode as RETURN does now. Due to EOF, it is suggested that these changes be activated in future EVM version once EOF has been fully implemented.

Security Considerations

There are no security considerations as it is fully backwards compatible, and reduces potential attack space through simplified bytecode.

Copyright

Copyright and related rights waived via CC0.