# Callback and refund gas griefing

Outbound calls or refunds to user-controlled addresses with unbounded gas that revert or block callers

_Area: Smart contract access control and control flow. Seen in 3 disclosed reports; latest 2024-05-22. Updated 2026-10-25._

## How it works
A contract makes an outbound call to an address the attacker controls — a token callback, a refund, or a return-data copy — and forwards all or unbounded gas. The recipient's code can burn that gas, return a huge data chunk, or revert. Because the caller's transaction shares one gas budget, the griefed call either reverts the whole operation or leaves too little gas for the remaining work (the 63/64 rule). The broken assumption is that the recipient is passive or benign; in fact it controls execution mid-transaction.

## Where it shows up
- `safeTransferFrom`/`safeTransfer` to user-supplied addresses, invoking `onERC721Received`/`onERC1155Received` [E1](https://bugbountylibrary.com/r/c4%3A2024-03-revert-lend%3AM-02.md)
- ETH refunds or withdrawals to `order.account` or similar user addresses with no gas cap [E3](https://bugbountylibrary.com/r/sherlock%3A2024-05-elfi-protocol%3AM-12.md)
- Batched loops that catch external-call reverts but still copy return/revert data [E2](https://bugbountylibrary.com/r/sherlock%3A2024-05-pooltogether%3AM-19.md)
- State cleanup (config removal, order close) placed after the outbound call, so a revert leaves it re-triggerable [E1](https://bugbountylibrary.com/r/c4%3A2024-03-revert-lend%3AM-02.md)
- Keeper/bot flows that pay gas to push value to users

## How to review
For every outbound call to a user-controlled address, check the invariant: the recipient cannot consume more gas than the caller budgets, and cannot prevent the caller's remaining work. Concretely: is gas capped (capped-gas `call`, pull-payment, or `ExcessivelySafeCall`)? Is return/revert data bounded? Is `address.code.length` checked before sending ETH? Is state cleanup done before the external call so griefing cannot recur? [E1](https://bugbountylibrary.com/r/c4%3A2024-03-revert-lend%3AM-02.md)[E2](https://bugbountylibrary.com/r/sherlock%3A2024-05-pooltogether%3AM-19.md)[E3](https://bugbountylibrary.com/r/sherlock%3A2024-05-elfi-protocol%3AM-12.md)

## Variants seen
- Malicious ERC721 receiver callback burns all gas and reverts, and cleanup runs only after transfer, so griefing repeats [E1](https://bugbountylibrary.com/r/c4%3A2024-03-revert-lend%3AM-02.md)
- Huge return/revert data chunk exhausts gas, leaving too little for remaining batched claims [E2](https://bugbountylibrary.com/r/sherlock%3A2024-05-pooltogether%3AM-19.md)
- Unlimited-gas ETH refund to a reverting or gas-hungry fallback blocks order cancellation [E3](https://bugbountylibrary.com/r/sherlock%3A2024-05-elfi-protocol%3AM-12.md)

## Impact and severity
Medium in the evidence. Effects: protocol-paid gas drained repeatedly [E1](https://bugbountylibrary.com/r/c4%3A2024-03-revert-lend%3AM-02.md), legitimate claimers blocked while attacker replays to collect fees [E2](https://bugbountylibrary.com/r/sherlock%3A2024-05-pooltogether%3AM-19.md), keepers blocked from executing or cancelling orders [E3](https://bugbountylibrary.com/r/sherlock%3A2024-05-elfi-protocol%3AM-12.md). Severity rises when the griefed path is a shared keeper/bot flow or a batch that others depend on, and when cleanup ordering lets the attack recur indefinitely [E1](https://bugbountylibrary.com/r/c4%3A2024-03-revert-lend%3AM-02.md).

## Evidence
- E1: https://bugbountylibrary.com/r/c4%3A2024-03-revert-lend%3AM-02.md
- E2: https://bugbountylibrary.com/r/sherlock%3A2024-05-pooltogether%3AM-19.md
- E3: https://bugbountylibrary.com/r/sherlock%3A2024-05-elfi-protocol%3AM-12.md
