Skip to content

bug: eth_getLogs OOM — limit check runs after full block log materialization #1033

@Aboudjem

Description

@Aboudjem

Bug Description

In rpc/namespaces/ethereum/eth/filters/filters.go, the Logs() function checks the log limit only AFTER calling blockLogs():

filtered, err := f.blockLogs(blockRes, bloom)
// ... error handling ...
if len(logs)+len(filtered) > logLimit {
    return nil, fmt.Errorf("query returned more than %d results", logLimit)
}

blockLogs() materializes ALL matching logs from a single block into memory before the limit is checked.

Reproduction

  1. Deploy a cosmos/evm chain with a public RPC endpoint
  2. Have a block with many log-emitting transactions (e.g., 100k+ event logs)
  3. Call eth_getLogs with a filter matching that block
  4. The RPC node allocates all logs into memory before checking the limit
  5. Node runs out of memory and crashes

Impact

Any public RPC endpoint running cosmos/evm is vulnerable to OOM crash via a single eth_getLogs call. An attacker only needs to know a log-heavy block number.

Proposed Fix

Add an early guard checking len(logs) >= logLimit BEFORE calling blockLogs() for each block iteration:

if logLimit > 0 && len(logs) >= logLimit {
    break
}

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions