← All posts

How we measure coverage

Every report we ship carries two numbers: a risk score and a coverage score. They answer different questions and are complementary. The risk score rates what we found. The coverage score estimates how much of your attack surface we were able to look at and assess.

An attack surface is never fully mapped up front, so coverage is always an estimate: how much of the in-scope surface we think we managed to look at and assess. It can only speak to what you put in scope; anything outside the agreed boundary is never measured. That is a different, weaker claim than confidence, which would mean we believe we know every vulnerability you have. No test can honestly promise that, so we only give the coverage estimate.

Background radiation

Any host with a public IP is under constant, untargeted attack. Mass scanners sweep the whole address space, bots fire known exploits at whatever answers, and credential-stuffing tools grind through leaked passwords around the clock. None of it is aimed at you specifically. It is the weather. We call it background radiation, and it is where most breaches actually start.

Coverage is framed against that baseline. A high coverage score means we have looked at the surface that background radiation and a motivated attacker would realistically reach, and can say what holds and what doesn't. A low one means large parts of your exposure are still an open question. The number is deliberately a feel for probability, because exploitation is a probability.

The OWASP risk score

The risk score uses the OWASP Risk Rating Methodology, because it is transparent and defensible: every score decomposes into factors you can argue with. It is worth understanding here for a second reason: it explains why the coverage number behaves as it does. The shape is simple:

Risk = Likelihood × Impact

Each side is the average of a set of factors, every factor scored from 0 to 9. Likelihood comes from two groups:

Impact comes from two more:

Average the factors in each half to get a Likelihood value and an Impact value, map each to Low (0 to under 3), Medium (3 to under 6), or High (6 to 9), and read the overall severity off the matrix below: High likelihood against High impact is Critical, Low against Low is a note, and everything else falls in between. Because the inputs are explicit, when we call something Critical you can see exactly which factors drove it and disagree on the merits if you think we scored one wrong.

OWASP overall risk severity
Impact ↓ / Likelihood → Low Medium High
High Medium High Critical
Medium Low Medium High
Low Note Low Medium

Likelihood is half of that score, and it folds in how easy a bug is to discover and to exploit. A high-impact vulnerability that is very hard to find and to trigger scores lower than an easy one, because a real attacker is less likely to ever reach it. So the surface a breadth-first pass covers, the high / medium likelihood surface, is exactly where most of your risk concentrates.

Why coverage caps at 80% and 99%

We run engagements in two passes, and each pass earns a different ceiling on the coverage we can claim.

The first pass is typically agentic-enabled. Humans or scope-bound agents sweep the attack surface in breadth, enumerate assets, and surface the high-likelihood issues fast. This is the pass that matches, and then goes past, what background radiation would find. Completing it earns up to 80% coverage. That ceiling is deliberate, and it follows from the risk model above: what a breadth pass leaves behind is the low-likelihood surface, the deep business logic and multi-step chains that take real complexity to reach. A bug hiding there can still be high-impact, but its low likelihood keeps its risk contribution, and the odds it turns out critical, small.

The second pass is human and in-depth. A reviewer goes deep on what the first pass surfaced and works exactly that low-likelihood, high-complexity surface automation can't judge. Completing it takes you up to 99% coverage.

That 99% depends on us actually knowing your attack surface. If in-scope shadow infra exists — servers, subdomains, cloud accounts, or forgotten test deployments that fall within the agreed scope but were never told to us or discovered during the first pass — we cannot assess what we do not know is there, and the ceiling drops with it. Reaching 99% coverage takes an accurate, complete asset inventory from you going in, not just our two passes.

We stop at 99% and never claim 100%. Your software sits on a supply chain we don't fully audit: the libraries, runtimes, and operating systems underneath it, and their dependencies in turn. We test them for known n-day exploits, but auditing that code in full is out of scope, so the surface never fully closes. A score that claims 100% is lying, and the last percent is the honesty margin.

If you want to see your own number, and the risk score that comes with it, request an engagement.