The Ethereum Virtual Machine (EVM) operates on a gas metering system, where every computational step consumes a predefined amount of gas. However, the protocol includes a gas refund mechanism that returns a portion of spent gas to the transaction sender upon completing certain state-clearing operations. This is not a direct reduction in gas used during execution but a post-execution credit applied to the total gas cost. The primary purpose is to incentivize good blockchain citizenship by rewarding users who help reduce the global state size, which improves network performance for everyone.
How to Manage EVM Gas Refund Behavior
Introduction to EVM Gas Refunds
Learn how the Ethereum Virtual Machine (EVM) refunds gas for specific operations, a critical mechanism for optimizing smart contract execution costs.
Two main operations trigger gas refunds: destroying a smart contract via SELFDESTRUCT (now SELFDESTRUCT in post-EIP-6780 contexts) and setting a storage slot's value to zero from a non-zero state. As of the London upgrade and EIP-3529, the maximum total refund per transaction is capped at 20% of the gas consumed (gas used before the refund). The refund amounts are: destroying a contract refunds 24,000 gas, and clearing a storage slot refunds 4,800 gas (reduced from 15,000 pre-EIP-3529). These refunds are applied after execution, reducing the final gas fee paid.
Understanding this behavior is crucial for gas optimization. A common pattern is the "gas refund token transfer," where a contract encourages users to zero out their balance, making the final transaction cheaper. However, developers must design carefully. Because refunds are capped, complex logic aiming for large refunds may become inefficient if the 20% cap is hit. Furthermore, since EIP-6780, SELFDESTRUCT only refunds gas if the contract is in the same transaction it was created in, significantly limiting its use for routine refunds.
To manage refund behavior effectively, smart contract code should explicitly handle state clearance. For example, when writing a function that allows users to withdraw tokens, setting their internal balance to zero after the transfer will trigger a refund. Here's a simplified code snippet illustrating the pattern:
solidityfunction withdraw() external { uint256 amount = balances[msg.sender]; require(amount > 0, "No balance"); // Clear storage slot FIRST to maximize refund eligibility balances[msg.sender] = 0; // Then perform the external call (bool success, ) = msg.sender.call{value: amount}(""); require(success, "Transfer failed"); }
Note that the storage is cleared before the external call for security (following checks-effects-interactions) and to ensure the refundable operation is recorded.
When estimating transaction costs, tools like eth_estimateGas typically return the net gas cost after refunds. However, for precise budgeting, remember that the refund does not affect the intrinsic gas or the gas available for execution (gaslimit - gasused). The refund is purely a financial reimbursement. Always test gas usage and refunds on a testnet like Sepolia using trace-level RPC methods (debug_traceTransaction) to see the detailed breakdown of gas consumption and refund credits before deploying optimization strategies to mainnet.
How to Manage EVM Gas Refund Behavior
Understanding gas refunds is essential for optimizing smart contract costs and preventing security vulnerabilities in Ethereum and other EVM-compatible chains.
The Ethereum Virtual Machine (EVM) includes a gas refund mechanism designed to incentivize state cleanup. When a smart contract operation frees up storage (e.g., by setting a storage slot from a non-zero to a zero value), the transaction receives a gas refund. This refund is credited at the end of execution, but it cannot exceed the gas used multiplied by the maximum refund quotient, which is 5 in post-London networks (i.e., max refund is gas_used / 5). This mechanism is critical for protocols that manage dynamic state, such as NFT marketplaces or complex DeFi contracts.
Managing refunds requires understanding two key opcodes: SSTORE and SELFDESTRUCT. An SSTORE that clears a storage slot (writing 0x00) currently grants a 4,800 gas refund. The SELFDESTRUCT opcode, which deletes a contract, refunds 24,000 gas. However, the EIP-3529 update significantly reduced these refunds and removed refunds for certain opcodes to mitigate gas token abuse and network spam. Developers must write contracts with post-EIP-3529 refund logic in mind to avoid unexpected gas costs.
A common pitfall is assuming refunds reduce the upfront gasLimit. They do not. Refunds are applied after execution, meaning users must still provide enough gas to cover the initial, higher cost of state-clearing operations. If a transaction runs out of gas before completion, no refund is issued. This makes accurate gas estimation vital. Tools like Hardhat and Foundry allow you to simulate transactions and inspect refund amounts using eth_call or trace functions to fine-tune your contract's gas profile.
To leverage refunds effectively, structure state changes to maximize cleared slots in a single transaction. For example, in a batch operation that deletes multiple user entries, group all SSTORE clearing operations together. Be cautious of reentrancy risks; a malicious contract could intercept execution after a refund-triggering operation but before the refund is finalized. Always follow the checks-effects-interactions pattern. Furthermore, since EIP-3529, the refund cap prevents single transactions from excessively reducing block space costs, making optimization more about efficient state management than gaming the system.
For security, audit refund logic to prevent gas griefing attacks. An attacker could call a function that triggers a large refund in your contract, but design the call path to consume all the refunded gas, potentially leaving the core transaction underfunded. Explicitly document any refund-heavy functions. When estimating gas for users, consider using the eth_estimateGas RPC call with a buffer, or implement a helper view function that calculates net cost after refunds for common operations, improving user experience.
How EVM Gas Refunds Work
EVM gas refunds are a mechanism to incentivize efficient state management by returning a portion of the gas spent for clearing storage. Understanding this behavior is crucial for writing cost-effective smart contracts.
The Ethereum Virtual Machine (EVM) provides gas refunds to encourage developers to clean up blockchain state. When a smart contract operation frees up storage—such as setting a storage slot's value from a non-zero to a zero—the transaction receives a refund. This refund is not applied mid-execution but is subtracted from the total gas cost at the end. The current maximum refund is 24,000 gas per cleared storage slot, a reduction from the original 15,000 gas refund and 20,000 gas cost established in EIP-3529.
Refunds primarily apply to two opcodes: SSTORE (when setting a slot to zero) and SELFDESTRUCT. The refund is tracked in a counter separate from the remaining gas. Crucially, a transaction can only receive a refund up to half of the total gas used in the transaction's execution. This 50% cap, introduced in EIP-3529, prevents gas token abuse and mitigates block size volatility. Therefore, even if you clear many storage slots, your refund cannot exceed (gas_used_before_refund) / 2.
To manage this behavior effectively, structure your contract logic to batch state-clearing operations. For example, a contract managing user balances should consolidate cleanup in a single function call rather than across multiple transactions to maximize the refund relative to the gas spent. Be aware that internal calls and loops affect the gas-used calculation. The refund is processed after the top-level execution ends, so gas estimates during simulation must account for this final deduction.
Here is a simplified code example demonstrating a refund. The cleanUp function sets a storage variable to zero, triggering a refund.
soliditycontract RefundExample { uint256 public data; // Occupies a storage slot function setData(uint256 _data) external { data = _data; // Costs ~20,000 gas if slot was zero } function cleanUp() external { // If data is non-zero, this SSTORE opcode triggers a refund data = 0; // Refunds 24,000 gas (capped at 50% of total gas used) } }
The net cost of the cleanUp transaction will be its execution gas minus the subsequent refund, subject to the cap.
When designing upgrades or migration functions, leverage refunds for gas efficiency. A pattern for deleting a contract via selfdestruct (which grants a 24,000 gas refund) or clearing arrays and mappings can significantly reduce net costs for users. However, always test gas usage with tools like Hardhat's gasReporter or Ethereum Tracer to verify refund application, as virtual machines like the Arbitrum Nitro stack handle refunds differently. Properly managed, gas refunds are a powerful tool for optimizing end-user transaction fees.
Refundable Operations and Values
Gas refund behavior for common EVM operations before and after the London hard fork (EIP-3529).
| Operation | Pre-EIP-3529 Refund | Post-EIP-3529 Refund | Max Refundable Gas |
|---|---|---|---|
SSTORE: Set non-zero to zero | 15000 | 4800 | 20000 |
SSTORE: Set non-zero to non-zero | 0 | 0 | |
SSTORE: Set zero to non-zero | -20000 | ||
SELFDESTRUCT | 24000 | 0 | 24000 |
Contract Creation (CREATE/CREATE2) | 24000 | 0 | 24000 |
Maximum Refund Quotient | 2 | 5 | |
Maximum Refund per Transaction | 50% of gas used | 20% of gas used |
Impact of EIP-3529 on Refunds
EIP-3529 fundamentally changed how gas refunds work in the EVM, reducing the maximum refund and removing refunds for key opcodes to mitigate network spam and stabilize gas prices.
Before EIP-3529, the Ethereum Virtual Machine (EVM) allowed a maximum gas refund of 50% of the transaction's gas used. This refund was triggered by specific state-clearing operations, primarily the SELFDESTRUCT opcode (24,000 gas refund) and the SSTORE opcode when clearing storage (15,000 gas refund). This system was exploited in gas token protocols like GST2 and CHI, where users could "mint" tokens by writing to storage when gas was cheap and later "burn" them to get a refund when gas was expensive, effectively allowing them to lock in low gas prices.
EIP-3529, implemented in the London Hard Fork (August 2021), introduced critical changes to curb this behavior and its negative externalities. The maximum refund was reduced from 50% to 20% of the transaction's gas used. More significantly, it removed the gas refund for the SELFDESTRUCT opcode entirely and reduced the refund for clearing storage via SSTORE from 15,000 to 4,800 gas. These changes were designed to disincentivize the creation of network spam through refund manipulation and to make gas price prediction more stable for users and block builders.
For smart contract developers, this means strategies that relied on heavy refunds are no longer viable. Code patterns that used SELFDESTRUCT for contract cleanup or gas token mechanics must be redesigned. The effective cost of clearing storage is now significantly higher. When writing contracts, you must account for the real, non-refundable cost of operations like SSTORE(_key, 0). This change encourages more efficient state management and reduces the incentive to bloat the chain state with temporary data just to harvest refunds later.
To manage EVM gas refund behavior post-EIP-3529, audit your contracts for deprecated patterns. Replace any logic dependent on SELFDESTRUCT refunds. For storage, consider using transient storage (EIP-1153) for short-lived data or more efficient data structures like mappings instead of arrays that require clearing. When estimating transaction costs, remember the 20% cap and the new, lower refund values. Tools like Ethers.js's estimateGas and Hardhat will account for these rules, but understanding them is crucial for manual optimization and gas golfing.
The broader impact of EIP-3529 has been positive for network health. It reduced the volatility in block gas limits caused by refund-heavy transactions, leading to more predictable block sizes and base fees. While it made some gas optimization tricks obsolete, it aligned economic incentives with the actual cost of state growth on the network. Developers must now focus on genuine state efficiency rather than financial engineering through the refund mechanism, leading to more sustainable smart contract design long-term.
Calculating and Anticipating Refunds
EVM gas refunds are a critical, often misunderstood mechanism for optimizing transaction costs. This guide explains how refunds are calculated, when they are applied, and how to anticipate them in your smart contract logic.
The Ethereum Virtual Machine (EVM) implements a gas refund system to incentivize state cleanup. When a smart contract operation frees up storage (like setting a storage slot from a non-zero to a zero value), it does not receive an immediate gas rebate. Instead, a refund counter is incremented. The two primary actions that generate refunds are: SSTORE (setting a storage slot to zero, 15,000 gas refund) and SELFDESTRUCT (destroying a contract, 24,000 gas refund). It's crucial to understand that these refunds are only applied after the transaction's execution completes, offsetting the total gas cost, not the cost of the individual opcode.
The total refund is capped at 50% of the gas used in execution. This is a critical security and economic rule. A transaction that uses 100,000 gas in execution can receive a maximum refund of 50,000 gas, making the final cost to the user 50,000 gas. This cap prevents scenarios where a transaction could generate more refunds than it consumes, which would allow for spam or other protocol abuses. The refund is applied to the gas used for computation and memory (intrinsic gas is not refundable).
To anticipate refunds in your code, you must track state changes. For example, consider a function that clears a user's balance in a mapping: balances[user] = 0. This SSTORE will queue a 15,000 gas refund. If your function performs multiple such clears, the refunds accumulate. However, complex logic with conditional paths makes manual calculation difficult. Developers often use tools like Hardhat's gasReporter or test their transactions in a forked environment (e.g., using Foundry's forge test --gas-report) to see the net gas cost after refunds.
A common optimization pattern is gas token contracts like GST2 or CHI. These tokens work by creating storage slots when gas is cheap (minting) and destroying that storage (burning) in a later transaction when gas is expensive, claiming the SSTORE refund to subsidize the costly operation. While effective, their use has declined post-EIP-3529, which reduced the SSTORE refund from 15,000 to 4,800 gas and removed refunds for SELFDESTRUCT, making the economic model less attractive.
When writing or auditing contracts, always verify that logic depending on refunds accounts for the 50% cap. A function that queues 80,000 gas in refunds but only spends 100,000 gas on execution will not refund the full 80,000. The net cost will be 100,000 - 50,000 = 50,000 gas. For the most accurate and up-to-date refund opcode values, always refer to the official Ethereum Execution Layer Specifications.
Solidity Patterns for Gas Refunds
A guide to understanding and leveraging the EVM's gas refund mechanism to reduce transaction costs for users.
The Ethereum Virtual Machine (EVM) includes a gas refund mechanism designed to incentivize good state hygiene. When a smart contract operation clears storage (sets a non-zero value to zero), the EVM grants a partial refund of the gas used in the transaction. The current refund is 24,000 gas per cleared storage slot, a significant portion of the original 20,000 gas cost for an SSTORE from non-zero to zero. This system encourages developers to write contracts that clean up after themselves, ultimately reducing the overall state bloat of the blockchain.
To claim a refund, you must trigger a storage-clearing operation. The most common pattern is using the selfdestruct opcode, which deletes the contract and refunds 24,000 gas, or manually zeroing out storage variables. However, there are critical limitations. The total refund granted per transaction is capped at a maximum of 20% of the total gas consumed (gas used before the refund is applied). Any refund amount exceeding this cap is forfeited. Furthermore, the refund is only processed after the transaction completes execution; it cannot be used to pay for gas during the transaction itself.
A practical application is in token burning or contract migration. When a user burns tokens, the contract reduces their balance from a non-zero value to zero, generating a refund. Sophisticated patterns involve batching multiple storage clears in a single transaction to maximize the refund up to the 20% cap. For example, a contract facilitating account abstraction might clean up temporary storage slots used during a multi-step process. It's crucial to audit these patterns, as incorrect logic can lead to reentrancy vulnerabilities if state is cleared before external calls.
Developers should be aware of the EIP-3529 changes implemented in the London hard fork. This update reduced the refund for SELFDESTRUCT from 24,000 to 0 gas and lowered the maximum refund cap from 50% to 20% of gas used. Code written before this change may have different gas economics. Always test gas consumption and refunds using tools like Hardhat's gasReporter or by examining transaction receipts in a local fork to understand the net cost for end-users.
While optimizing for refunds, prioritize security and clarity over minor gas savings. Avoid complex refund-maximizing logic that obscures contract behavior. The primary benefit often goes to the transaction submitter (the "msg.sender"), not the contract itself. Documenting refund behavior in your contract's NatSpec comments is essential for other developers interacting with your code. For most applications, writing clear, efficient state management will naturally yield refund benefits without requiring specialized patterns.
EVM Gas Refund Strategy Comparison
Comparison of common methods for handling gas refunds in smart contracts, from basic to advanced.
| Strategy Feature | Basic Refund | Pull-Payment Refund | Gas Station Network (GSN) |
|---|---|---|---|
User Pays Gas | |||
Contract Pays Gas | |||
Refund Gas to User | |||
Refund Security Risk | High (reentrancy) | Low (pull pattern) | None (pre-paid) |
Implementation Complexity | Low | Medium | High |
Typical Use Case | Simple internal refunds | Public bounty/refund | Mass adoption dApps |
Avg. Gas Overhead | ~21k gas | ~45k gas | ~100k+ gas (relay) |
Requires Upfront Deposit |
How to Manage EVM Gas Refund Behavior
Gas refunds are a nuanced EVM mechanism that can reduce transaction costs but introduce significant risks if misunderstood.
The Ethereum Virtual Machine (EVM) provides a gas refund mechanism to incentivize state cleanup. When a smart contract operation clears storage (like setting a storage slot from a non-zero to a zero value), the EVM grants a refund of up to 48,000 gas per cleared slot. This refund is applied at the end of transaction execution, after the total gas cost is calculated. The maximum total refund is capped at 50% of the gas used in the transaction. This design aims to compensate users for the long-term benefit of reducing the blockchain's state size.
A common mistake is assuming refunds reduce the upfront gasLimit. They do not. You must still provide enough gas to cover the entire execution path, including the high-cost SSTORE operations that enable the refund. If your gasLimit is too low, the transaction will revert before the refund is applied. For example, a function that uses 100,000 gas and triggers a 20,000 gas refund still requires a gasLimit of at least 100,000. The refund merely reduces the final gas charged, not the initial requirement.
The most significant risk involves the refund counter. Refunds are not applied immediately but accumulated in a counter. Malicious contracts can exploit this by calling into other contracts mid-execution. An attacker's fallback function could perform a state-clearing operation, collect a large refund, and then cause the calling transaction to revert. The original caller still pays for all gas used, but the attacker pockets the refunded ETH. This was a vector in several historical exploits.
To manage refunds safely, audit any contract you interact with for unexpected SELFDESTRUCT opcodes or storage-clearing logic in fallback functions. When writing contracts, avoid making external calls after performing operations that generate refunds. Structure your functions so that state cleanup and refund-triggering actions occur at the very end, after all critical logic and external interactions are complete. This limits the attack surface for refund manipulation.
For developers, tools like the Hardhat console and Tenderly simulations can help estimate net gas costs including refunds. Always test gas usage in a forked mainnet environment to get accurate refund behavior. Remember that EIP-3529, implemented in the London hard fork, reduced certain refund amounts (like for SELFDESTRUCT) and enforced the 50% cap to mitigate these risks, but the fundamental behavioral quirks remain.
Tools and Resources
Tools, specifications, and practices for understanding and managing EVM gas refund behavior after EIP-3529. These resources focus on accurate gas modeling, safer contract design, and realistic testing across modern Ethereum networks.
Solidity Storage Patterns Without Refund Assumptions
Post-EIP-3529, storage write minimization matters more than storage cleanup. Modern Solidity design focuses on reducing SSTORE operations rather than clearing slots.
Recommended patterns:
- Use packed storage structs to reduce slot usage
- Prefer immutable and constant variables for configuration
- Collapse multiple flags into a single
uint256bitmap - Avoid temporary mappings or arrays meant to be deleted later
Anti-patterns to remove:
- Clearing mappings in loops for refunds
- Using
SELFDESTRUCTto "discount" deployment costs - Re-initializing storage-heavy state machines
These practices lower gas deterministically and behave consistently across Ethereum mainnet, rollups, and future forks.
Frequently Asked Questions
Gas refunds are a complex and often misunderstood part of EVM execution. This FAQ addresses common developer questions about how refunds work, their limitations, and best practices for managing them.
EVM gas refunds are a mechanism that returns a portion of the gas paid for a transaction when certain storage-clearing operations are performed. The primary purpose is to incentivize cleaning up the blockchain state by deleting storage slots or self-destructing contracts.
Key refund operations:
SSTOREthat changes a non-zero storage value to zero: 15,000 gas refund.SELFDESTRUCT: 24,000 gas refund (or 0 post-EIP-6780).
Refunds are not credited during execution. They are calculated at the end of the transaction and applied to the final gas cost, up to a maximum of 50% of the gas used. This means you cannot use refunds to pay for subsequent opcodes in the same transaction.
Conclusion and Next Steps
Effectively managing gas refunds in the EVM requires understanding their specific mechanics, limitations, and the strategic trade-offs involved in their use.
Gas refunds are a nuanced feature of the EVM designed to incentivize state cleanup. The primary mechanisms are the SSTORE refund for clearing storage slots and the SELFDESTRUCT refund for deleting contracts. While they can reduce the net gas cost of a transaction, they are capped at 20% of the transaction's total gas used, and refunds are processed after execution. This means you must have enough gas upfront to pay for the entire operation, including the initial high-cost SSTORE write, before receiving the partial refund. Refunds are not applied to the gas used for CALL operations or intrinsic costs.
For developers, the most common application is optimizing contract deployments and upgrades. By using patterns like the EIP-2535 Diamond Standard or deploying via a factory that SELFDESTRUCTs a temporary contract, you can leverage refunds to lower deployment costs. However, you must carefully audit the gas flow. A transaction that attempts to claim a refund larger than the 20% cap will only receive the maximum allowable amount, potentially making an optimization strategy uneconomical. Always test gas usage with tools like eth_estimateGas and Hardhat's console.log for gas tracking.
Looking forward, the role of gas refunds is evolving. EIP-3529, implemented in the London hard fork, reduced SSTORE and eliminated SELFDESTRUCT refunds to mitigate certain attack vectors and state bloat. Developers should be aware that the refund mechanism is a tool for specific scenarios, not a general gas-saving technique. For broader optimization, focus on efficient data structures, minimizing on-chain operations, and using gas-efficient patterns like packed storage variables and external call batching. The Ethereum Yellow Paper and EIP documentation remain the definitive sources for the latest specifications.
To implement these concepts, start by instrumenting your contracts. Use Foundry's forge snapshot --gas or a gasleft() diff pattern in your tests to measure the impact of state-clearing operations. Review popular, gas-optimized contracts like those from OpenZeppelin or the Solmate library to see refund-aware patterns in practice. Remember that the most significant gas savings often come from architectural decisions—reducing the frequency and scope of state changes—rather than relying on refunds alone.