Benchmarks
Real measurements of Cefrium against the three other ways to put web content in an Android app -- the system WebView, Mozilla GeckoView, and Chrome Custom Tabs. Honest numbers, the same page on every engine, with the harness and scripts published so you can reproduce them.
Method
- Same page on every engine: each engine loads the identical
URL (
cefrium.com/modern-web/) in a minimal, matched harness app (one view, nothing else), so the only variable is the engine. - RAM = PSS from
adb shell dumpsys meminfo(the App Summary: Java / Native / Graphics / Code / Total), median of 6 samples after the page settles. PSS is the right cross-process metric. - Cross-architecture caveat: PSS sums every process, so a multi-process engine (Cefrium) reads heavier than a single-process one even at equal real cost. That multi-process overhead is exactly what buys the crash-recovery shown in the stability matrix below -- the number and the resilience are the same trade-off, stated honestly rather than hidden.
- Two real devices: a TABWEE W90 (Android 16, shares one renderer) and a Redmi Note 13 Pro 5G / HyperOS (Android 16, process-per-browser) -- deliberately different process models.
- Custom Tabs renders in a separate Chrome process, so its RAM
is measured on
com.android.chrome(the same Chromium 149 Cefrium pins). It is not embeddable, so most capabilities are N/A. - Engines: Cefrium 0.5.2 (Chromium 149), system WebView, GeckoView 132, Chrome 149, Tauri 2.11.2 (release build, wraps the system WebView).
RAM, same page (lower is lighter)
| Engine | W90 (PSS MB) | Redmi / HyperOS (PSS MB) | Embeddable | Own engine | OSR |
|---|---|---|---|---|---|
| System WebView | 119 | 144 | Yes | No (OS WebView) | No |
| Tauri 2.11 | 138 | 173 | No (app framework) | No (OS WebView) | No |
| GeckoView 132 | 180 | 206 | Yes | Yes (Gecko) | No |
| Custom Tabs (Chrome) | 178 | 224 | No | -- | No |
| Cefrium 0.5.2 | 242 | 263 | Yes | Yes (Chromium) | Yes |
Median PSS (6 samples), modern-web page, both devices, zero crashes during sampling. Cefrium is the heaviest; it is also the only embeddable Chromium with off-screen rendering. The W90 shares one renderer (~1-2 processes); the Redmi runs process-per-browser (3-4) -- which is why its numbers are higher across the board.
Tauri on Android ships no engine of its own: it renders in the device's system WebView -- the same engine and version as the System WebView row above. Its extra RAM over that row (~+19 MB W90, ~+29 MB Redmi) is the Rust/wry native runtime, measured on a release build (Tauri 2.11.2). It is an app framework, not a view you embed in an existing native app, and like any WebView it has no off-screen-rendering path.
Alternatives without a standard Android embedding path
Two engines often raised as lighter alternatives have no measured row here, for an honest reason rather than an omission:
- Ultralight is the real low-RAM contender, and we would have published its number even if it beat Cefrium -- but as of June 2026 its official site lists only Windows, macOS, Linux, Xbox and PlayStation as supported platforms; Android is not among them, so there is no standard embedding path to measure. For the record: Ultralight is a custom WebKit fork (not Chromium), does not implement WebGL or WebRTC and treats HTML5 video/audio as experimental, and is dual-licensed (partial LGPL source plus a paid commercial license). On a page it could render, it would very likely use less RAM than Cefrium -- at the cost of web-platform coverage.
- Servo (0.1.0, 2026) builds an Android shell and is actively
developing its
libservoembedding API, but has no production-stable, standard third-party Android embedding path yet, so it is not in the measured table.
Cefrium flagships & samples (per-app RAM)
RAM of the actual Cefrium apps loading their own content, for reference (PSS MB):
| App | W90 | Redmi / HyperOS |
|---|---|---|
| modern-web showcase | 281 | -- |
| java-sample (browser) | 278 | 317 |
| Compose browser | 269 | -- |
| Exam app | 260 | 308 |
| Kiosk POS | 228 | 230 |
| Kiosk automotive | 224 | 241 |
The dominant component is the engine binary (libcef.so,
~50-140 MB) -- memory-mapped from the file (shared, reclaimable under pressure),
not runtime heap growth. Java heap stays small (7-20 MB).
Crash stability (OEM matrix)
Launch-cycle the same app N times and count app crashes, renderer-level crash events, and out-of-memory / lowmemorykiller kills. A single launch hides intermittent OEM behavior; HyperOS in particular is aggressive.
| Device | Launches | App crashes | Renderer events | LMK kills |
|---|---|---|---|---|
| TABWEE W90 | 10 | 0 (0%) | 0 | 0 |
| Redmi / HyperOS | 10 | 0 (0%) | 3 (30%) | 2 |
Memory is bounded, not leaking
A long-lived embedder opens and closes many pages. The risk is that each closed page leaks its renderer. We drive a 30-navigation loop through a pool that keeps at most 2 browsers alive (each new page evicts the least-recently-used one) and read the engine's exact counters afterwards.
| Device | Navigations | Browsers closed | Live browsers | Render frames | Verdict |
|---|---|---|---|---|---|
| TABWEE W90 | 30 | 29 | 2 | 2 | bounded |
| Redmi / HyperOS | 30 | 29 | 2 | 2 | bounded |
Renderers die gracefully (your app does not)
On aggressive OEM skins the system can kill a background renderer to reclaim memory.
Cefrium surfaces that to the app through a public onRenderProcessTerminated
callback, so the embedder can show a reload affordance instead of a blank page. We
validated it end-to-end: kill the live renderer, the callback fires with an out-of-memory
status, the app stays up. (This needed an engine fix -- the upstream handler only mapped
desktop termination reasons and silently dropped Android's low-memory-kill status.)
Off-screen rendering (the capability the others lack)
Cefrium can render a page to a raw pixel buffer in your process
(OnPaint) -- for screenshots, PDF, headless capture, custom
compositing, or surfaces no View can reach. System WebView,
GeckoView and Custom Tabs expose no pixel-buffer / off-screen
API at all -- a category Cefrium owns outright.
Measured off-screen cold first-paint (loadUrl -> first content
frame): ~1.7-2.0 s (Redmi 1690 ms, W90 2012 ms; cold start --
includes spawning the engine and the renderer). The other three engines have no
number here because they cannot render off-screen at all.

Verified on device: Cefrium rendering a page into a raw BGRA buffer
via OnPaint and drawing it into an ordinary Android ImageView
(no SurfaceView, no WebView) -- the on-screen stats show the
first frame and its non-white pixel count. The other three engines cannot do this.
Reproduce it yourself (traceability)
The whole harness is open in the
cefrium-sample repo under
benchmark-suite/: the external profiler, the matched per-engine apps
(Cefrium / WebView / GeckoView / Custom Tabs), the crash matrix, and every result
CSV. One CSV schema across all engines, so head-to-head and per-release trends are
plain diffs.
# RAM, any installed app, any engine, into results/<ver>/<device>-<engine>.csv
benchmark-suite/profile.sh -s <serial> -p com.cefrium.bench.cef -l modern-web -e cefrium
benchmark-suite/profile.sh -s <serial> -p com.cefrium.bench.webview -l modern-web -e webview
# Readable per-app table from a result CSV
benchmark-suite/summarize.sh results/0.5.2/w90-cefrium.csv
# OEM crash matrix: N launch cycles, crash rate + tombstones/ANR/LMK
benchmark-suite/crash-matrix.sh -s <serial> -p com.cefrium.bench.cef -n 20
Measured on Cefrium 0.5.2 (Chromium 149.0.7827). Numbers are PSS medians and will shift with the page, the device, and the Chromium version; the scripts are the source of truth, not these snapshots.