Private eth_getBalance · Ethereum mainnet · CANS 2026

The chain is public. Only your RPC query needs hiding.

Private eth_getBalance looks up any Ethereum balance without the server learning which address you asked about. Built on RisePIR, a new incremental keyword PIR scheme. It serves over 200 million mainnet accounts, answers in under a second, and meets NIST Category 1 security.

Research prototype · the live instance runs during demos and on request.

A ribbon of database scales, mostly pale, with a few solid-orange scales showing the block just patched
≈433 accounts change per block
patched in place · 5.6 ms
204,714,034accounts served
0.69 sper private query
5.6 msto absorb a block
noneaddresses sent to the server

Measured on the live deployment, 2026-09-03.

01 · Patched in place

Ethereum changes every 12 seconds. RisePIR keeps up by patching, not rebuilding.

Fast private lookups need a preprocessed hint of the whole database. In earlier keyword PIR, changing one account meant rebuilding it. RisePIR's d-ary Segmented Cuckoo Filter turns each change into a sparse, position-predictable patch — so a block's changes land in milliseconds.

One block's changes, two ways · measured 2026-09-03, 16 threads
block N block N+1 block N+2 0 s 12 s 24 s 36 s
Patch in place — 5.6 ms
0.05% of the block
Full rebuild — 29.2 s
longer than two blocks — it can never catch up
5,200×
cheaper than a rebuild
≈433
accounts changed per block
≈10.8 kB
communication per block
“A scheme that rebuilds on every change cannot keep pace with the chain.” — RisePIR paper, §9
02 · How a private lookup works

Encrypted here. Computed blind. Decoded here.

01

Download the hint, once

Your browser fetches a 553.8 MB preprocessed hint. It is identical for every visitor, so holding it says nothing about you.

02

Ask in ciphertext

The address is encrypted in your browser into a ≈435 kB LWE query. The server computes over every one of its 204.7 million accounts, so it cannot tell which one you meant.

03

Stay current, block by block

Each finalized block's changes arrive as ≈10.8 kB of public data that every client downloads in full, so your answer is corrected to the latest finalized block without re-downloading the hint.

The address stays here

Your browser

Builds the LWE query locally.

query · ≈435 kB ciphertext →
← response · ≈434 kB ciphertext

PIR server

Computes over the entire database · sees ciphertext only.

← finalized blocks

Ethereum mainnet

Followed at finalized, ≈13 min behind the head.

03 · Under the hood

One component changed. Everything else stays fast.

A grid of buckets in two segments; a few highlighted orange as the ones a mutation touches
segment 0segment 1

d-ary Segmented Cuckoo Filter

Each address maps to exactly one bucket per segment, so every segment is a self-contained PIR database — and an insert, update or delete touches only a few predictable cells.

Never a wrong answer

An error is acceptable. A silently wrong balance is not. Every failure path refuses rather than guesses.

The address never leaves your browser

The client is WebAssembly running on your machine. The address is not hashed, not truncated, not encrypted for the server — it is not sent.

Finalized, never reorged

Answers are as of the latest finalized block, about 13 minutes behind the head, so an answer cannot be quietly invalidated.

Checked against the chain

300 of 300 live answers matched an independent provider byte for byte (2026-09-03).

Two variants, one construction

RisePIR-S over SimplePIR runs this deployment; RisePIR-F runs over FrodoPIR.

Read the paper →
04 · Measured, not estimated

The live deployment, in numbers

One binary, one host, one 3.1-hour window on 2026-09-03: 300 private queries and 959 blocks.

204,714,034accounts served (complete nonzero-balance set)
0.69 sprivate query, end to end (0.61 s is the server's product)
5.6 msper-block patch (5.573 ms mean · 4.783 ms p50)
553.8 MBone-time hint
435 kBquery on the wire (response: 434 kB)
23.62 GBserver database
≈10.8 kBcommunication per block
≈13 minfreshness lag (latest finalized block, by design)

Measured on 2026-09-03 on a GCP c3d-highmem-16 (AMD EPYC 9B14, Zen 4, 16 threads); client an AWS r7a.xlarge over the public internet. Source: docs/deployment-numbers.md in the repository.

05 · Try it

Look up a real balance. Watch what leaves your browser.

Type any address.

The hint downloads once.

A receipt shows exactly what crossed the wire.

The live instance is not always on — it runs during demos and on request.

Screenshot of demo.risepir.org at a mobile viewport width: a completed private balance lookup of the Ethereum beacon deposit contract, and the receipt's "Addresses transmitted: none" row.
Captured from demo.risepir.org on 2026-09-24 (UTC): a private lookup of the beacon deposit contract, as of finalized block 26,049,113. The receipt shows no address was transmitted.
Screenshot of demo.risepir.org at desktop width: the same lookup, with the decoded balance and the full receipt of everything that crossed the wire, including the highlighted "Addresses transmitted: none" row.
The same lookup at desktop width, captured 2026-09-24 (UTC): the decoded balance beside the full receipt of what crossed the wire.
Screenshot of demo.risepir.org during the first-visit one-time setup: the hint download in progress, and the receipt panel before any lookup has run.
A first visit, captured 2026-09-24 (UTC): the one-time hint download in progress, before any lookup.
06 · Trust

What this does not protect

The guarantee is specific: the operator cannot learn which account you asked about. Everything it does not cover is stated here, up front — not in fine print.

Who is choosing your client

demo.risepir.org serves both the page and the WebAssembly, so PIR holds only if that origin is honest.

  • Same-origin delivery plus a connect-src 'self' CSP constrain a tampered page, not a dishonest origin.
  • The wasm's only host import is a random-bytes source.
  • The wasm and CLI share source — run risepir-rpc client --pir-url … yourself to remove the question.

What the cryptography does not hide

It hides which account, not that, when, how often or from where you asked; the server sees your IP address and timing like any web server — use Tor if that matters.

Freshness

Answers are as of the latest finalized block, about 13 minutes behind a block explorer — deliberately, because finalized blocks do not reorganise.

This page is not the PIR origin

risepir.org is static, carries no cryptographic client, and makes no PIR queries — it sits outside the trust boundary above. It is hosted on Cloudflare Pages, so Cloudflare terminates TLS for it and injects its own analytics script (cloudflareinsights.com) at the edge — not in this page's source, and not something it asks for. demo.risepir.org is served directly, with no proxy in the path that delivers the cryptographic client.

The operator is assumed honest-but-curious: it follows the protocol and cannot learn your address, but a dishonest operator could serve a wrong balance — see the threat model.
07 · Paper & code

Read the paper. Run the code.

Paper

Incremental Keyword Private Information Retrieval from d-ary Segmented Cuckoo Filters

Bao Ninh · CANS 2026 — International Conference on Cryptology and Network Security
“…the first preprocessing keyword private information retrieval (PIR) scheme that absorbs insert, update, and delete on its key-value store at a cost proportional to the number of mutations alone.”

Accepted at CANS 2026. Full version on IACR ePrint 2026/2082.

Code

github.com/orochi-network/private-eth-getbalance

Apache-2.0

Rust workspace: PIR server and verified store, WebAssembly and CLI clients, mainnet feed, JSON-RPC front end, conformance harness.

Open the live demo →