Skip to content
All fingerprint checksRender & GPU

text metrics are not a uniform multiple of the engine's own grid

Check id text-metrics-uniform-scale

What an ordinary browser yields

Either every width lands on the 1/512 grid, or the off-grid widths are not explained by any single common factor. One factor fitting all of them is the thing being looked for.

What a detector infers

This is the sub-pixel grid check asked one question deeper. That check reports THAT widths have left Blink's 1/512-pixel grid; this one asks what SHAPE the deviation has, which turns out to separate the possible causes cleanly. Because the engine quantises advance widths onto the grid, the nearest grid point to a measured width IS the true width — so dividing each measurement by its own recovered grid point yields the factor by which that string was altered. Three causes, three signatures. Per-glyph noise scatters those factors. A different font or font version moves widths from one grid point to another and leaves them ON the grid, so the factors stay at exactly 1. But a single multiplier applied to the number after the text engine has finished returns the SAME factor for every string — for a single "A", for a twenty-character run of the same letter, for mixed alphanumerics — because it never looked at the glyphs at all. Fourteen strings means thirteen independent constraints on one constant, and satisfying all of them to the last representable bit of a double is not something a coincidence does. Measured on a shipping stealth browser: fourteen of fourteen strings off-grid, every ratio agreeing to within one unit in the last place, with the constant redrawn on each launch. The same product's Worker returned widths exactly on the grid, which independently confirms that the recovered grid points were the true values and that only the page's realm was multiplied. The recovery has a deliberate limit: it holds while the scale is small enough that a shifted width stays nearest its own grid point, and a coarser farble scatters the ratios and makes this check report nothing rather than guess.

How to resolve it

The engine emits widths already quantised on the grid, so a factor shared by every string can only have been applied after it finished. This row is deliberately not scored as a contradiction, because a privacy build that farbles canvas text metrics per session produces precisely this shape and that is a legitimate thing to want. If metrics must vary between sites, vary them inside the shaper so the results stay quantised; a scale applied to the returned number is recoverable regardless of how small it is — the factor measured here was under three parts per million and reconstructed exactly. Worth knowing for anyone weighing that severity: stock Brave 150 was measured against this row on both a real HTTPS origin and on localhost and did NOT trip it — it farbles canvas but leaves text metrics alone — so the unscored treatment is a deliberate margin rather than a response to any observed false positive. Chrome 150, Edge 150 and Firefox 151 were measured clean too, the last of them N/A as the Blink-grid gate requires.

What is font fingerprinting?

Read in the wild by

CloakBrowser (measured)

Every one of fourteen strings off the grid by an identical factor, on all three launches measured, with the factor redrawn per session — under three parts per million each time, and therefore invisible to any check that only asks whether a width looks reasonable. The product's Worker returned the exact grid values in the same sessions, so the main thread's numbers were the engine's own output multiplied on the way out.

14/14 strings off-grid on 3/3 launches; factors 0.999997293617128, 1.000002932966041 and 0.999997197243199, each shared across all fourteen strings with a spread of 0 to 2.2e-16 (one ULP). Stock Chrome on the same machine: 0/14 off-grid, every ratio exactly 1, spread exactly 0.

CloakBrowser (measured)

Every attribution traces to a published artifact. See the sources and their limits.

Nearby checks in Render & GPU

See all 32 checks in Render & GPU
Who builds this test

Clearcote is a browser built for fingerprint coherence

It is a Chromium fork, maintained by the same people who wrote this reference. It ships as a compiled browser rather than as a stealth script injected into someone else's — which is a description of how it is built, and is not an argument about how it behaves on this check.

This audit takes no position on how Clearcote scores on Render & GPU checks, on this one, or anywhere else. It has no baseline corpus of other people's fingerprints to rank you against and no vendor scoreboard — nearly every check is self-referential, asking one browser the same question through two independent APIs and reporting whether both answers can be true at once. It runs identically on any browser, including ours. Run it on yours and read the result yourself.

See the other checks in Render & GPU — the family text-metrics-uniform-scale belongs to.