<?xml version="1.0" encoding="UTF-8"?><rss version="2.0" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:atom="http://www.w3.org/2005/Atom"><channel><title>Parag Mali - tag: crypto-agility</title><description>Posts tagged crypto-agility.</description><link>https://paragmali.com/</link><language>en-US</language><lastBuildDate>Sat, 25 Jul 2026 08:57:53 GMT</lastBuildDate><atom:link href="https://paragmali.com/tags/crypto-agility/rss.xml" rel="self" type="application/rss+xml"/><item><title>How the Whole Stack Would Break: SIDH, Correlated Assumptions, and the Cryptography We Are Betting the Next Thirty Years On</title><link>https://paragmali.com/blog/how-the-whole-stack-would-break-sidh-correlated-assumptions-/</link><guid isPermaLink="true">https://paragmali.com/blog/how-the-whole-stack-would-break-sidh-correlated-assumptions-/</guid><description>No post-quantum algorithm is proven hard. The stack&apos;s only real defense is a deliberately uncorrelated portfolio of lattice, code, and hash assumptions.</description><pubDate>Sun, 19 Jul 2026 00:00:00 GMT</pubDate><content:encoded>
The security of the post-quantum stack is not the hardness of any single algorithm -- **none of them is proven hard**. It is a deliberately *uncorrelated* portfolio: lattice (ML-KEM, ML-DSA, Falcon), hash (SLH-DSA), and code (HQC, Classic McEliece), chosen so a break of one family leaves the others standing. Shor was the original correlated failure -- factoring and discrete log fell together because they were one bet -- and the 2022 SIDH/SIKE collapse (classical, about ten minutes, no warning) proved a well-vetted family can still vanish overnight. This capstone maps where the surviving bets are genuinely correlated (the lattice cluster, the Module-LWE pair at its center) and argues that, for a science that can prove nothing hard, diversity is the entire defense.
&lt;h2&gt;1. Nine Teardowns, One Question&lt;/h2&gt;
&lt;p&gt;In late July 2022, a key-exchange scheme that had survived eleven years of public cryptanalysis was broken. Not by a quantum computer. Not gradually. It fell on a single laptop core in about ten minutes, using a theorem from pure mathematics published in 1997 [@castryck-decru-2022]. The scheme was SIKE, the instantiation of SIDH first proposed in 2011 [@jao-defeo-2011], and just three and a half weeks earlier NIST had promoted it to the fourth and final round of its post-quantum standardization effort for continued study [@nist-2022-selection].&lt;/p&gt;
&lt;p&gt;Read the status carefully, because the precise words carry the whole point. SIKE was never a standard. It was a Round-4 &lt;em&gt;alternate candidate&lt;/em&gt;, still under evaluation, key-recovered before any selection was made [@ir-8413]. That makes the collapse worse, not better: this was cryptography failing while under the most intense scrutiny our field knows how to apply.&lt;/p&gt;

Two or more cryptographic primitives that fail together because they secretly depend on the same piece of mathematics. The schemes look independent -- different names, different standards, different teams -- but a single advance takes all of them at once. It is the failure mode a diverse portfolio exists to prevent.
&lt;p&gt;This series has spent nine articles taking post-quantum primitives apart one at a time: how ML-KEM would break, how ML-DSA would break, how each candidate meets its mathematical limit. This final part does what none of the nine could do alone: it steps back and asks whether they fail &lt;em&gt;independently&lt;/em&gt;. Because a stack is not nine separate bets that each has to be strong. It is one system, and its real question is whether two of those bets might secretly be the same bet.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Key idea:&lt;/strong&gt; A cryptosystem is a wager that one math problem is hard. A cryptographic &lt;em&gt;stack&lt;/em&gt; is a portfolio of such wagers -- and the only thing that ultimately matters is whether the wagers are correlated. The stack is secure not because any assumption is proven hard (none is), but only to the degree that a break of one leaves the others standing.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;That is the lens for everything below -- a sentence you will earn by the end.&lt;/p&gt;

A cryptographic stack is a portfolio of bets -- and the only thing that ultimately matters is whether the bets are correlated.
&lt;p&gt;Before we map the stack, one boundary. The break we just described was &lt;em&gt;structural&lt;/em&gt;: an attack on SIDH&apos;s own mathematics, not on a buggy implementation of it.SIDH is not CSIDH. SIDH collapsed classically in 2022; CSIDH is a separate isogeny construction that survives, with its own separately-contested &lt;em&gt;quantum&lt;/em&gt; security -- Kuperberg&apos;s algorithm applies to CSIDH, never to lattices [@kuperberg-2005]. Never let one family&apos;s obituary be read as the other&apos;s. That distinction is the boundary every section below holds to.&lt;/p&gt;

This capstone analyzes only structural cryptanalysis -- attacks on an algorithm&apos;s own mathematics. Side channels, fault and power attacks, implementation bugs, weak randomness, and protocol misuse are real, often easier, and equally capable of sinking a deployment -- but they are a different surface, owned by the sibling track *How It Breaks in Real Life*. One clarification for the quantum question: Shor&apos;s algorithm counts as structural math and is in scope; Grover&apos;s generic search is not a structural break, and it is named once later, then set aside.
&lt;p&gt;The thirty-year story we are about to trace is a spiral, not a line. Three times the field concentrated its security onto one kind of mathematics, and three times a shock forced it to spread out again.&lt;/p&gt;

flowchart LR
  A[&quot;1978 McEliece: the first code-based bet&quot;] --&amp;gt; B[&quot;1994 Shor: two bets share one spine&quot;]
  B --&amp;gt; C[&quot;2005 LWE: the lattice core arrives&quot;]
  C --&amp;gt; D[&quot;2016 NIST competition: five families enter&quot;]
  D --&amp;gt; E[&quot;2022 SIDH collapses, classically&quot;]
  E --&amp;gt; F[&quot;2024 FIPS 203, 204, 205 published&quot;]
  F --&amp;gt; G[&quot;2025 HQC selected as the code hedge&quot;]
&lt;p&gt;To answer whether the &lt;em&gt;new&lt;/em&gt; bets are correlated, we first have to understand the last time they were -- the one moment when a single idea took the entire classical stack at once.&lt;/p&gt;
&lt;h2&gt;2. Shor: The Original Correlated Failure&lt;/h2&gt;
&lt;p&gt;For twenty years the field slept soundly because breaking RSA seemed to say nothing about breaking elliptic-curve cryptography. That comfort was an illusion -- the most important one to understand here, because the entire post-quantum project is an attempt not to fall for it twice.&lt;/p&gt;
&lt;p&gt;The numbers told a reassuring story. The best classical attack on RSA was the general number field sieve, with a sub-exponential running time; the best classical attack on elliptic curves was Pollard&apos;s rho, a square-root method [@gnfs-pollard]. Two problems, two unrelated algorithms, two independent-looking bets. If someone found a faster way to factor, elliptic curves would be untouched, and vice versa. Diversify across both and you were doubly safe -- or so the reasoning went.&lt;/p&gt;

The foundation of all public-key cryptography: security rests on the belief that some specific problem -- factoring a 2048-bit number, recovering a short lattice vector -- is too expensive to solve on average, for anyone, with any known method. The operative word is *belief*. &quot;Nobody has broken it yet&quot; is evidence, not a proof; almost nothing in cryptography is proven hard.
&lt;p&gt;Then, in 1994, Peter Shor showed that both bets were the same bet. His &lt;a href=&quot;https://paragmali.com/blog/how-q-day-breaks-everything-shors-algorithm-and-the-simultan/&quot; rel=&quot;noopener&quot;&gt;polynomial-time quantum algorithm&lt;/a&gt; solved integer factoring &lt;em&gt;and&lt;/em&gt; discrete logarithm, because underneath their different surfaces both are instances of a single mathematical object: the abelian hidden-subgroup problem [@shor-1994]. Find the hidden periodic structure and you have solved the factoring instance, the discrete-log instance, and the elliptic-curve instance alike.&lt;/p&gt;

A general problem about finding hidden periodic structure in a function defined over an abelian (commutative) group. Integer factoring and discrete logarithm are both special cases of it. Shor&apos;s 1994 algorithm solves the abelian HSP in polynomial time on a quantum computer, which is why one result dissolved two problems that looked entirely unrelated.

flowchart TD
  RSA[&quot;RSA: integer factoring&quot;] --&amp;gt; HSP{&quot;Abelian hidden-subgroup problem&quot;}
  ECC[&quot;ECC: discrete logarithm&quot;] --&amp;gt; HSP
  HSP --&amp;gt; SHOR[&quot;Shor, 1994: polynomial-time quantum HSP&quot;]
  SHOR --&amp;gt; Z1[&quot;RSA falls&quot;]
  SHOR --&amp;gt; Z2[&quot;ECC falls&quot;]
&lt;p&gt;This is the template for everything this article fears. Two primitives can each be individually strong -- decades of failed attacks, careful parameter choices, universal deployment -- and still fall together, in one stroke, because their strength was never really two separate things.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Note:&lt;/strong&gt; RSA and elliptic-curve cryptography were never two bets. They were one bet on the abelian hidden-subgroup problem, wearing two costumes. The security question was never &quot;is each algorithm strong?&quot; It was always &quot;do the algorithms secretly share a spine?&quot; Strength is measured per algorithm; &lt;em&gt;failure is measured per assumption&lt;/em&gt;.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;Two honest caveats keep this precise. First, Shor&apos;s algorithm needs a large, fault-tolerant quantum computer that does not yet exist; its threat is future, not present, and it does &lt;em&gt;not&lt;/em&gt; threaten any of the lattice, code, or hash schemes we will meet below.Grover&apos;s algorithm is the other quantum result people cite. It gives only a generic quadratic, $2^{n/2}$, speedup for unstructured search -- effectively halving a symmetric key&apos;s strength, so a 256-bit key still offers about 128 bits against a quantum attacker [@grover-1996]. That is absorbed by larger parameters, not a structural break, and the last we will say of it. Second, the reason Shor matters here is historical, not technical: it is the event that created the field. The looming &quot;Q-Day,&quot; when a quantum computer runs Shor at scale, is precisely &lt;em&gt;the&lt;/em&gt; correlated failure that made everyone go looking for replacements.&lt;/p&gt;
&lt;p&gt;If the lesson of Shor is that independent-looking bets can share a hidden spine, then the obvious first move after 1994 -- just swap RSA and elliptic curves for one quantum-safe algorithm -- walks straight back into the same trap.&lt;/p&gt;
&lt;h2&gt;3. The Naive Swap Rebuilt the Single Point of Failure&lt;/h2&gt;
&lt;p&gt;The first instinct after Shor was the worst one: treat it as a component swap. Rip out RSA and elliptic curves, find one quantum-safe replacement, and declare victory. The instinct is understandable -- engineers replace broken parts every day -- but it is exactly the mistake the correlation lens tells you to avoid.&lt;/p&gt;
&lt;p&gt;The raw material was already on the shelf. The candidate problems with no exploitable abelian-HSP structure had existed for decades: McEliece&apos;s code-based cryptosystem from 1978 [@mceliece-1978], Merkle&apos;s hash-based signatures from 1979 [@merkle-1979], the NTRU lattice system from 1998 [@ntru-1998], and Regev&apos;s Learning With Errors problem from 2005, which would become the workhorse of the entire modern stack [@regev-lwe-2005]. Any of them could resist Shor. The temptation was to pick the most efficient one and standardize it alone.&lt;/p&gt;

A deployed stack whose security, however many algorithms it contains, ultimately rests on a single hard-problem family. Like a field planted with one genetic strain, it can look healthy right up until a single blight -- one mathematical advance -- takes all of it at once.
&lt;p&gt;Here is why a single replacement is not a fix but a relocation of the risk. Shor did not punish RSA for being weak; it punished the &lt;em&gt;stack&lt;/em&gt; for concentrating on one kind of mathematics. Swap in a lone lattice scheme and you have rebuilt precisely that: a monoculture with a new problem underneath, one advance away from total failure. You did not escape the Shor pattern. You reissued it.&lt;/p&gt;
&lt;p&gt;To be honest about the epistemics: no paper proves the theorem &quot;monocultures always fail.&quot; This is a design argument, and its evidence is circumstantial rather than deductive -- the Shor precedent behind us, and, as we will see, the collapses of SIKE and Rainbow still ahead.&lt;/p&gt;
&lt;p&gt;The people who saw it earliest said so in plain terms. Daniel Bernstein and Tanja Lange argued for years that committing to a single system courts a &quot;cryptographic monoculture,&quot; and built NTRU Prime partly as a standing objection to it [@ntruprime-diversity]. That position, once a minority view, is the intellectual seed of everything NIST eventually did.&lt;/p&gt;
&lt;p&gt;Because NIST did not swap. It ran a competition.&lt;/p&gt;

When NIST opened its post-quantum project in 2016, 82 submissions arrived and 69 were accepted into the first round, spread across five mathematical families: lattice, code, hash, multivariate, and isogeny [@ir-8240; @nist-pqc-project]. The breadth was the substance, not the packaging. An open competition across unrelated hard problems is, structurally, a search for a *set* of uncorrelated bets -- even before anyone attached that language to it.
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Note:&lt;/strong&gt; The deepest design lesson of the post-Shor era is counterintuitive: a standardization effort should not try to crown the single best algorithm. It should assemble a diversified set whose members would have to fail for independent reasons. A lone &quot;winner&quot; is a monoculture waiting to happen.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;NIST bet on breadth -- five families, an open process, trust earned by attrition. But breadth on paper is not diversity in fact. A competition can start with five families and still funnel almost all of its real-world weight onto one of them. To see whether that happened, you have to stop reading the roster and start reading the map -- exactly what the survivors ended up standing on.&lt;/p&gt;
&lt;h2&gt;4. The Map of What Rests on What&lt;/h2&gt;
&lt;p&gt;Here is the uncomfortable picture, drawn as a map. Take the standardized and selected post-quantum stack, ignore the marketing names, and color each scheme by the hard problem it actually rests on. Where is the concentration?&lt;/p&gt;

The modern public-key primitive for agreeing on a shared secret. Rather than encrypting a chosen message, the sender *encapsulates* a fresh random key against the recipient&apos;s public key, producing a ciphertext; the recipient decapsulates it to recover the same key. ML-KEM, HQC, and Classic McEliece are all KEMs.
&lt;p&gt;Six schemes carry the weight. ML-KEM (FIPS 203) is a lattice KEM whose security is tied to Module-LWE at modulus q = 3329 [@fips-203]. ML-DSA (FIPS 204) is a lattice signature resting on Module-LWE &lt;em&gt;and&lt;/em&gt; Module-SIS at modulus q = 8380417 [@fips-204]. &lt;a href=&quot;https://paragmali.com/blog/how-falcon-would-break-ntru-lattices-and-the-structure-nobod/&quot; rel=&quot;noopener&quot;&gt;Falcon&lt;/a&gt; (draft FIPS 206) is a lattice signature too, but on the NTRU short-vector problem rather than Module-LWE [@ntru-1998].&lt;/p&gt;
&lt;p&gt;SLH-DSA (FIPS 205) is a signature whose security reduces entirely to the strength of a hash function [@fips-205]. Classic McEliece rests on decoding random binary Goppa codes [@mceliece-1978], and HQC -- selected by NIST in March 2025 -- rests on decoding quasi-cyclic codes [@ir-8545].&lt;/p&gt;

flowchart TD
  subgraph Lattice
    MLKEM[&quot;ML-KEM on Module-LWE&quot;]
    MLDSA[&quot;ML-DSA on Module-LWE plus Module-SIS&quot;]
    FAL[&quot;Falcon on the NTRU lattice&quot;]
  end
  subgraph Hash
    SLH[&quot;SLH-DSA on hash security only&quot;]
  end
  subgraph Code
    HQC[&quot;HQC on quasi-cyclic decoding&quot;]
    MCE[&quot;Classic McEliece on binary-Goppa decoding&quot;]
  end
  MLKEM -.-&amp;gt;|shared Module LWE assumption| MLDSA

The hard problem underneath both ML-KEM and ML-DSA. Informally it is noisy linear algebra over structured (module) lattices: you are shown many linear equations whose right-hand sides have each been nudged by a small random error, and asked to recover the secret. &quot;Module&quot; is the middle setting between fully unstructured LWE (slow but conservative) and fully structured Ring-LWE (fast but more algebraic surface for an attacker to grab).
&lt;p&gt;The map makes one fact impossible to miss: &lt;strong&gt;three of the six schemes stand on lattices.&lt;/strong&gt; That concentration is not an accident. It is the payoff of a twenty-year efficiency arc -- Ajtai&apos;s 1996 worst-case-to-average-case reduction [@ajtai-1996], Regev&apos;s LWE in 2005 [@regev-lwe-2005], Ring-LWE&apos;s dramatic size reductions in 2010 [@ring-lwe-2010], and the Module-LWE middle ground in 2015 [@module-lwe-2015] that Kyber and Dilithium adopted in 2017 to become today&apos;s ML-KEM and ML-DSA [@kyber-2017; @dilithium-2017]. Lattices won the efficiency argument, and that is why they became the core.&lt;/p&gt;
&lt;p&gt;But notice the precise shape of the correlation, because misstating it is the single most common error about this stack. &lt;a href=&quot;https://paragmali.com/blog/two-standards-one-lattice-how-ml-kem-and-ml-dsa-would-break/&quot; rel=&quot;noopener&quot;&gt;ML-KEM and ML-DSA&lt;/a&gt; are the genuinely correlated &lt;em&gt;pair&lt;/em&gt;: both rest on Module-LWE. That does &lt;strong&gt;not&lt;/strong&gt; mean any attack on one instantly breaks the other. They use different parameters -- different moduli (3329 versus 8380417), different module ranks,The rank is roughly how many ring elements stack into the secret vector; a higher rank means a harder instance and a larger key. different noise -- so a &lt;em&gt;parameter-specific&lt;/em&gt; attack need not transfer, and ML-DSA carries an additional Module-SIS assumption that ML-KEM does not [@fips-204].&lt;/p&gt;
&lt;p&gt;What they share is the &lt;em&gt;assumption family&lt;/em&gt;. A generic, structural advance against Module-LWE would reach both at once; a narrow trick tuned to one parameter set might reach neither.Falcon is NTRU, not Module-LWE -- a third and structurally distinct lattice bet, and the least conservative of the three because its NTRU lattices carry extra algebraic structure. It is also the one still unfinished: draft FIPS 206 (FN-DSA) remained unreleased as of this writing [@nist-pqc-project].&lt;/p&gt;
&lt;p&gt;You can turn that observation into a two-line audit. Do not count algorithms; count &lt;em&gt;assumptions&lt;/em&gt;.&lt;/p&gt;
&lt;p&gt;{`
// Map each deployed scheme to the hard problem it truly rests on.
const assumption = {
  &apos;ML-KEM-768&apos;:        &apos;lattice&apos;,
  &apos;ML-DSA-65&apos;:         &apos;lattice&apos;,
  &apos;Falcon-512&apos;:        &apos;lattice&apos;,
  &apos;SLH-DSA-128s&apos;:      &apos;hash&apos;,
  &apos;HQC-128&apos;:           &apos;code&apos;,
  &apos;Classic-McEliece&apos;:  &apos;code&apos;
};&lt;/p&gt;
&lt;p&gt;// A stack is only as diverse as its set of DISTINCT assumptions.
function auditStack(schemes) {
  const families = new Set(schemes.map(function (s) { return assumption[s]; }));
  console.log(&apos;Deployed: &apos; + schemes.join(&apos;, &apos;));
  console.log(&apos;Distinct assumption families: &apos; + Array.from(families).join(&apos;, &apos;));
  if (families.size === 1) {
    console.log(&apos;WARNING: monoculture. One advance against &apos; +
                Array.from(families)[0] + &apos; takes the whole stack.&apos;);
  } else {
    console.log(&apos;OK: a break must cross &apos; + families.size +
                &apos; unrelated families to take everything.&apos;);
  }
}&lt;/p&gt;
&lt;p&gt;auditStack([&apos;ML-KEM-768&apos;, &apos;ML-DSA-65&apos;, &apos;Falcon-512&apos;]);    // looks diverse, is not
auditStack([&apos;ML-KEM-768&apos;, &apos;SLH-DSA-128s&apos;, &apos;HQC-128&apos;]);    // lattice + hash + code
`}&lt;/p&gt;
&lt;p&gt;The first stack has three different algorithm names and one assumption. The second has three names and three assumptions. Only the second is a portfolio.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Key idea:&lt;/strong&gt; The map is the thesis. Every scheme sits in exactly one assumption band -- lattice, hash, or code -- and every break lives in a band too. To take the whole stack down, a single break would have to cross bands, reaching mathematics unrelated to where it started. Diversity is not decoration on top of the security argument. It &lt;em&gt;is&lt;/em&gt; the security argument.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;The map, laid out precisely, and the five generations of thinking that produced it:&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Scheme (standard)&lt;/th&gt;
&lt;th&gt;Role&lt;/th&gt;
&lt;th&gt;Family&lt;/th&gt;
&lt;th&gt;Specific assumption&lt;/th&gt;
&lt;th&gt;Best-known attack&lt;/th&gt;
&lt;th&gt;Representative size&lt;/th&gt;
&lt;th&gt;Correlation group&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;&lt;tr&gt;
&lt;td&gt;ML-KEM (FIPS 203)&lt;/td&gt;
&lt;td&gt;KEM workhorse&lt;/td&gt;
&lt;td&gt;Lattice&lt;/td&gt;
&lt;td&gt;Module-LWE, q = 3329&lt;/td&gt;
&lt;td&gt;Lattice sieving / BKZ [@core-svp]&lt;/td&gt;
&lt;td&gt;~1 KB public key&lt;/td&gt;
&lt;td&gt;Lattice core&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;ML-DSA (FIPS 204)&lt;/td&gt;
&lt;td&gt;Signature workhorse&lt;/td&gt;
&lt;td&gt;Lattice&lt;/td&gt;
&lt;td&gt;Module-LWE + Module-SIS, q = 8380417&lt;/td&gt;
&lt;td&gt;Lattice sieving / BKZ [@core-svp]&lt;/td&gt;
&lt;td&gt;~3 KB signature&lt;/td&gt;
&lt;td&gt;Lattice core (paired)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Falcon (draft FIPS 206)&lt;/td&gt;
&lt;td&gt;Compact signature&lt;/td&gt;
&lt;td&gt;Lattice&lt;/td&gt;
&lt;td&gt;NTRU short vector&lt;/td&gt;
&lt;td&gt;Lattice sieving / BKZ [@core-svp]&lt;/td&gt;
&lt;td&gt;sub-kilobyte signature&lt;/td&gt;
&lt;td&gt;Lattice (distinct)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;SLH-DSA (FIPS 205)&lt;/td&gt;
&lt;td&gt;Conservative signature&lt;/td&gt;
&lt;td&gt;Hash&lt;/td&gt;
&lt;td&gt;Hash preimage / collision resistance&lt;/td&gt;
&lt;td&gt;Generic hash attacks&lt;/td&gt;
&lt;td&gt;several to tens of KB signature&lt;/td&gt;
&lt;td&gt;Hash anchor (uncorrelated)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;HQC (NIST IR 8545)&lt;/td&gt;
&lt;td&gt;KEM hedge&lt;/td&gt;
&lt;td&gt;Code&lt;/td&gt;
&lt;td&gt;Quasi-cyclic syndrome decoding&lt;/td&gt;
&lt;td&gt;Information-set decoding [@bjmm-2012]&lt;/td&gt;
&lt;td&gt;few-KB public key&lt;/td&gt;
&lt;td&gt;Code hedge&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Classic McEliece (ISO-track) [@classic-mceliece-iso]&lt;/td&gt;
&lt;td&gt;KEM deep hedge&lt;/td&gt;
&lt;td&gt;Code&lt;/td&gt;
&lt;td&gt;Binary-Goppa syndrome decoding&lt;/td&gt;
&lt;td&gt;Information-set decoding [@bjmm-2012]&lt;/td&gt;
&lt;td&gt;0.26-1.36 MB public key [@classic-mceliece-site]&lt;/td&gt;
&lt;td&gt;Code hedge&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;&lt;/table&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Generation&lt;/th&gt;
&lt;th&gt;Era&lt;/th&gt;
&lt;th&gt;What we bet on&lt;/th&gt;
&lt;th&gt;How we avoided concentrating&lt;/th&gt;
&lt;th&gt;Why it was superseded&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;&lt;tr&gt;
&lt;td&gt;Number-theoretic monoculture&lt;/td&gt;
&lt;td&gt;pre-1994&lt;/td&gt;
&lt;td&gt;Factoring and discrete log (RSA, ECC)&lt;/td&gt;
&lt;td&gt;We did not -- two problems were believed independent&lt;/td&gt;
&lt;td&gt;Shor: both are one abelian-HSP bet [@shor-1994]&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Naive one-for-one swap&lt;/td&gt;
&lt;td&gt;1994-2016&lt;/td&gt;
&lt;td&gt;A single quantum-safe replacement&lt;/td&gt;
&lt;td&gt;Not at all -- one new problem underneath&lt;/td&gt;
&lt;td&gt;Rebuilds the monoculture Shor punished&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Five-family bake-off&lt;/td&gt;
&lt;td&gt;2016-2022&lt;/td&gt;
&lt;td&gt;An open competition across five families&lt;/td&gt;
&lt;td&gt;Breadth of candidates [@ir-8240]&lt;/td&gt;
&lt;td&gt;Attrition thinned it toward a lattice-heavy core&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Lattice-centric core&lt;/td&gt;
&lt;td&gt;2022-2024&lt;/td&gt;
&lt;td&gt;Module-LWE efficiency (ML-KEM, ML-DSA)&lt;/td&gt;
&lt;td&gt;Partly -- hash-based SLH-DSA retained&lt;/td&gt;
&lt;td&gt;Concentration risk: three lattice schemes&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Diversified portfolio&lt;/td&gt;
&lt;td&gt;2024-2025&lt;/td&gt;
&lt;td&gt;Lattice, hash, and code, explicitly&lt;/td&gt;
&lt;td&gt;Dated policy: SLH-DSA, then HQC [@ir-8545]&lt;/td&gt;
&lt;td&gt;Current -- the correction made explicit&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;&lt;/table&gt;
&lt;p&gt;A map like this is only a worry until a family actually vanishes from it. That is not hypothetical. An entire family that reached NIST&apos;s Round-4 shortlist -- isogenies -- did exactly that, while sitting under the most intense scrutiny the field can muster.&lt;/p&gt;
&lt;h2&gt;5. SIDH: How a Family Vanished in an Afternoon&lt;/h2&gt;
&lt;p&gt;Return to the ten-minute break and look at exactly how it worked, because the mechanism is the warning. A scheme that survived more than a decade did not fall to a new theory, a faster computer, or a lucky guess. It fell to arithmetic that had been sitting in a 1997 journal, waiting.&lt;/p&gt;
&lt;p&gt;SIDH&apos;s hard problem is to find a secret isogeny -- a structured map -- between two supersingular elliptic curves. That problem, taken bare, still looks hard today. But a protocol has to do more than pose a hard problem; it has to let two honest parties reach the same key. To make that possible, SIDH publishes extra data alongside its public key: the images of certain torsion points under the secret isogeny [@jao-defeo-2011]. That auxiliary information is not part of the underlying hard problem. It is a gift the protocol hands the attacker in order to function.&lt;/p&gt;

An isogeny is a structure-preserving map between two elliptic curves. SIDH hides its secret in a specific isogeny and dares attackers to find it. But to let two parties agree on a key, the protocol must also publish the images of certain torsion points under that secret map. Those published images are auxiliary data the bare hard problem never had to reveal -- and they are exactly what the attack fed on.
&lt;p&gt;In late July 2022, Wouter Castryck and Thomas Decru showed how to weaponize that gift. They applied Kani&apos;s reducibility criterion -- a result in arithmetic geometry published in 1997 and essentially unused in cryptography for twenty-five years [@kani-1997] -- to the published torsion-point images. The criterion lets you glue the curves into a higher-dimensional abelian surface and test whether it splits, and from that test recover the secret isogeny. On SIKEp434 it ran in about ten minutes on a single classical core [@castryck-decru-2022].&lt;/p&gt;

sequenceDiagram
  participant P as Protocol
  participant A as Attacker
  P-&amp;gt;&amp;gt;A: Publishes torsion-point images (required to function)
  A-&amp;gt;&amp;gt;A: Apply Kani reducibility criterion from 1997
  A-&amp;gt;&amp;gt;A: Glue curves into an abelian surface, test reducibility
  A-&amp;gt;&amp;gt;P: Recover the secret isogeny (the private key)
  Note over A: About ten minutes, one core, classical, not quantum
&lt;p&gt;It was not a fluke of one parameter set. Within weeks, Damien Robert proved the attack runs in classical &lt;em&gt;polynomial&lt;/em&gt; time from any starting curve, sealing the result as structural rather than patchable [@robert-2022], and Luciano Maino and Chloe Martindale generalized it while carefully bounding it away from neighboring constructions [@maino-martindale-2022].&lt;/p&gt;
&lt;p&gt;Now sit with the three facts that make this the emotional center of the article. It was not Shor and not a quantum computer -- an ordinary laptop did it.The interval is the whole point. SIKE advanced to Round 4 on 5 July 2022 and was broken around 30 July 2022 -- roughly three and a half weeks later [@nist-2022-selection; @castryck-decru-2022]. Years of survival bought time, not safety. It was not gradual erosion -- one paper took the family from &quot;final round&quot; to &quot;dead.&quot; And the vulnerability was structural from birth: SIDH published its own attack surface on day one, and the tool that read it had existed, fully public, since 1997.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Note:&lt;/strong&gt; The attack was &lt;strong&gt;classical&lt;/strong&gt;. It ran on an ordinary core using Kani&apos;s criterion, with no quantum computer anywhere in the story. And SIDH is &lt;strong&gt;not&lt;/strong&gt; CSIDH: this result key-recovered SIDH and SIKE, but does not apply to CSIDH, CSI-FiSh, or SQIsign [@maino-martindale-2022]. Blaming a quantum machine, or extending the collapse to every isogeny scheme, are both wrong.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;Here is the shift. Most of us treat heavy vetting as evidence of durability: if a scheme survives years of expert attack, surely it is safe. SIKE says otherwise. Vetting measures how long a family has resisted the tools people &lt;em&gt;thought to try&lt;/em&gt;. It cannot measure the tool nobody connected yet -- and that tool can already be published, in a field the cryptographers were not reading.&lt;/p&gt;

The mathematics that collapses a quantum-safe family can already exist, fully published, decades before anyone connects it to the target.
&lt;p&gt;If a whole family can vanish like this -- classically, in an afternoon, at the peak of its scrutiny -- then the only rational response is to never bet the stack on one. That is precisely, and deliberately, what NIST built next.&lt;/p&gt;
&lt;h2&gt;6. The Portfolio NIST Actually Built&lt;/h2&gt;
&lt;p&gt;The standardized stack is not a winner. It is a portfolio, and it was designed rather than stumbled into. Read across the three families and you can see the strategy in the shape.&lt;/p&gt;
&lt;p&gt;The lattice pair, ML-KEM and ML-DSA, are the efficient workhorses -- small keys, fast operations, the default choice for general traffic [@fips-203; @fips-204]. Next to them sits the maximally conservative anchor: &lt;a href=&quot;https://paragmali.com/blog/how-slh-dsa-would-break-the-signature-that-can-only-fall-if-/&quot; rel=&quot;noopener&quot;&gt;SLH-DSA&lt;/a&gt;, a signature whose security reduces entirely to the strength of a hash function and shares no algebraic structure with lattices at all [@fips-205]. Its lineage runs straight back to the SPHINCS stateless hash-based signature of 2015 [@sphincs-2015]. If every lattice assumption on the map fell tomorrow, SLH-DSA would not notice.&lt;/p&gt;

The hard problem behind code-based cryptography. Given a random-looking linear code and a corrupted codeword, recover the small error pattern that was added. That recovery is a decoding problem which has resisted efficient solution since the 1970s. HQC and Classic McEliece both rest on variants of it.
&lt;p&gt;The third family is the encryption hedge. Classic McEliece has stood essentially unbroken as a structure for roughly 47 years, the deepest-studied bet on the board [@classic-mceliece-site].McEliece&apos;s conservatism has a price: its public keys run from about 0.26 MB to 1.36 MB depending on parameters [@classic-mceliece-site], roughly two to three orders of magnitude larger than ML-KEM&apos;s. That bandwidth is the price of a structure unbroken for nearly half a century. And in March 2025, NIST added HQC, a newer code-based KEM built on quasi-cyclic codes [@hqc-site], precisely to have a standardized encryption path that does not touch lattices.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Note:&lt;/strong&gt; The clearest proof that diversity is a deliberate strategy and not an accident is the calendar. On 11 March 2025, NIST selected HQC as a second standardized KEM -- explicitly because it rests on codes rather than lattices, so that a future lattice break cannot bring down all post-quantum encryption at once. NIST even documented why it chose HQC over BIKE and why it did not select Classic McEliece [@ir-8545].&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;That selection is the thesis rendered as a signed, dated decision. A monoculture-minded process would have shipped one KEM -- the fastest -- and moved on. NIST shipped a second one on a different hard problem, and said out loud that non-correlation was the reason.&lt;/p&gt;

NIST did not choose HQC because it was the fastest or the smallest. It chose HQC because it is not a lattice.
&lt;p&gt;Here is the whole portfolio as an engineering comparison. The last row -- correlation to the lattice core -- is the one this article cares about most.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Dimension&lt;/th&gt;
&lt;th&gt;Lattice core (ML-KEM / ML-DSA)&lt;/th&gt;
&lt;th&gt;Lattice (Falcon)&lt;/th&gt;
&lt;th&gt;Hash (SLH-DSA)&lt;/th&gt;
&lt;th&gt;Code (HQC)&lt;/th&gt;
&lt;th&gt;Code (McEliece)&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;&lt;tr&gt;
&lt;td&gt;Worst-case structural threat&lt;/td&gt;
&lt;td&gt;Generic Module-LWE advance&lt;/td&gt;
&lt;td&gt;Advance on NTRU lattices&lt;/td&gt;
&lt;td&gt;Break of the underlying hash&lt;/td&gt;
&lt;td&gt;ISD advance on quasi-cyclic codes&lt;/td&gt;
&lt;td&gt;ISD advance on Goppa codes&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Best-known attack cost&lt;/td&gt;
&lt;td&gt;Sieving $2^{0.292\beta}$ [@core-svp]&lt;/td&gt;
&lt;td&gt;Sieving $2^{0.292\beta}$ [@core-svp]&lt;/td&gt;
&lt;td&gt;Generic hash bounds&lt;/td&gt;
&lt;td&gt;ISD $2^{\Theta(n)}$ [@bjmm-2012]&lt;/td&gt;
&lt;td&gt;ISD $2^{\Theta(n)}$ [@bjmm-2012]&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Representative size&lt;/td&gt;
&lt;td&gt;~1 KB pk, ~3 KB sig&lt;/td&gt;
&lt;td&gt;sub-KB signature&lt;/td&gt;
&lt;td&gt;KB-scale signature&lt;/td&gt;
&lt;td&gt;few-KB public key&lt;/td&gt;
&lt;td&gt;0.26-1.36 MB public key [@classic-mceliece-site]&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Performance&lt;/td&gt;
&lt;td&gt;Fast&lt;/td&gt;
&lt;td&gt;Compact, fast verify&lt;/td&gt;
&lt;td&gt;Slower, larger signatures&lt;/td&gt;
&lt;td&gt;Moderate&lt;/td&gt;
&lt;td&gt;Fast operations, very large keys&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Attack-cost verifiability&lt;/td&gt;
&lt;td&gt;Contested margin [@classic-mceliece-site]&lt;/td&gt;
&lt;td&gt;Contested margin&lt;/td&gt;
&lt;td&gt;High (hash-based)&lt;/td&gt;
&lt;td&gt;Machine-checkable&lt;/td&gt;
&lt;td&gt;Machine-checkable, most stable&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Correlation to lattice core&lt;/td&gt;
&lt;td&gt;It is the core&lt;/td&gt;
&lt;td&gt;High (lattice)&lt;/td&gt;
&lt;td&gt;None (hash)&lt;/td&gt;
&lt;td&gt;Low (code)&lt;/td&gt;
&lt;td&gt;Low (code)&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;&lt;/table&gt;
&lt;p&gt;A portfolio on paper only becomes a defense when it is fielded, and this one is. On the wire, the dominant deployment is a &lt;em&gt;hybrid&lt;/em&gt;: a classical key exchange and a lattice KEM run together, most commonly the X25519MLKEM768 group, which pairs X25519 with ML-KEM-768, the two primitives it shares with the general-purpose X-Wing combiner [@xwing-2024].&lt;/p&gt;

Running a classical key exchange (say X25519) and a post-quantum KEM (say ML-KEM) side by side, then combining their two shared secrets through a key-derivation function. The result is secure as long as *either* half is unbroken, so a surprise break of the post-quantum piece does not, on its own, expose the session.
&lt;p&gt;The adoption is real and recent. By early 2024, roughly 2 percent of TLS 1.3 connections to Cloudflare used post-quantum key exchange, with over 99 percent of that traffic driven by Chrome [@cloudflare-pq-2024]. Apple&apos;s iMessage PQ3 and Signal&apos;s PQXDH shipped post-quantum protection into production messaging [@apple-pq3; @signal-pqxdh]. And the NSA&apos;s CNSA 2.0 suite mandates ML-KEM and ML-DSA, plus the stateful hash-based signatures LMS and XMSS for software- and firmware-signing, for national security systems on a timeline running to 2033 [@cnsa-2.0]. The portfolio is not a whiteboard proposal; it is being poured into the foundations of the internet right now.&lt;/p&gt;
&lt;p&gt;A portfolio is only a defense, though, if its bets are genuinely uncorrelated. So the honest question -- the one that separates comfort from security -- is whether these bets are independent. They are not all as independent as the map makes them look.&lt;/p&gt;
&lt;h2&gt;7. Are the Bets Actually Uncorrelated?&lt;/h2&gt;
&lt;p&gt;This is where the map earns its keep. Press on each band and watch how far the crack spreads. There are three verdicts to reach and one uncomfortable caveat that undercuts all of them.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;The lattice cluster is genuinely correlated -- and it is the largest correlated surface on the map.&lt;/strong&gt; A sufficiently general advance against structured lattices, or a real quantum algorithm for Module-LWE, would not stay contained. It would reach ML-KEM and ML-DSA through their shared Module-LWE assumption and very likely Falcon through its NTRU lattices as well.&lt;/p&gt;
&lt;p&gt;The caveats from Section 4 still hold and still matter -- Falcon is NTRU rather than Module-LWE, the parameters differ, and ML-DSA carries an extra Module-SIS route -- so not every lattice result hits all three. But the honest summary is stark: the single most valuable target on the board is &quot;lattices in general,&quot; and three standardized schemes sit behind it.&lt;/p&gt;

flowchart TD
  GEN[&quot;Generic Module-LWE break&quot;] --&amp;gt; MLKEM[&quot;ML-KEM&quot;]
  GEN --&amp;gt; MLDSA[&quot;ML-DSA&quot;]
  LR[&quot;Large lattice-reduction advance&quot;] --&amp;gt; MLKEM
  LR --&amp;gt; MLDSA
  LR --&amp;gt; FAL[&quot;Falcon&quot;]
  ISD[&quot;Information-set decoding advance&quot;] --&amp;gt; HQC[&quot;HQC&quot;]
  ISD --&amp;gt; MCE[&quot;Classic McEliece&quot;]
  HASH[&quot;Hash function break&quot;] --&amp;gt; SLH[&quot;SLH-DSA&quot;]
  NN[&quot;Nearest-neighbor search&quot;] -.-&amp;gt; LR
  NN -.-&amp;gt; ISD
&lt;p&gt;&lt;strong&gt;The code pair is partially correlated.&lt;/strong&gt; HQC and Classic McEliece are both code-based, but they are different structural bets -- quasi-cyclic codes versus binary Goppa codes. They share an attack ruler: improvements to information-set decoding erode both [@bjmm-2012]. But a structure-specific attack, one that exploits the quasi-cyclic shape or the Goppa structure in particular, need not transfer between them. Same family, two different bets inside it.&lt;/p&gt;

The best-known family of attacks against code-based cryptography. ISD guesses a subset of coordinates it hopes are error-free, solves the resulting linear system, and checks whether the implied error is small enough, repeating until it succeeds. Fifty years of refinement have chipped at its exponent without changing its exponential character -- which is exactly why the code margin is considered stable.
&lt;p&gt;&lt;strong&gt;The hash anchor is the least correlated bet on the map, but not perfectly isolated.&lt;/strong&gt; SLH-DSA shares no algebraic structure with lattices or codes at all; its only correlation is to the strength of the &lt;a href=&quot;https://paragmali.com/blog/how-sha-2-and-sha-3-would-break-merkle-damgard-collisions-le/&quot; rel=&quot;noopener&quot;&gt;SHA-2 and SHA-3 families&lt;/a&gt; it is built on. And those carry the largest, most-attacked security margins in all of cryptography. If you wanted the closest thing to an assumption that fails for reasons entirely its own, this is it.The lattice margin, by contrast, is not settled. Concrete-security estimates that NIST itself has published for Kyber-512 have spanned roughly $2^{140}$ to $2^{180}$ gates depending on modeling assumptions [@classic-mceliece-site]; the code margin is comparatively stable and can be checked by attack-cost simulators.&lt;/p&gt;
&lt;p&gt;Now the caveat that keeps this section honest. Lattice sieving and code-based ISD, at their algorithmic cores, both reduce to the same primitive: finding very close vectors in a huge set, a nearest-neighbor search. The best sieving algorithms and the best decoding algorithms have both been sharpened by advances in nearest-neighbor techniques [@core-svp]. So it is &lt;em&gt;conceivable&lt;/em&gt; that one deep breakthrough in nearest-neighbor search could sharpen attacks in both the lattice band and the code band at once -- a meta-correlation the tidy three-color map hides.&lt;/p&gt;
&lt;p&gt;I have to mark that claim precisely, because overstating it would betray the whole argument. No published result demonstrates an attack that transfers between the families, and no reduction is known in either direction. This is an &lt;em&gt;inferred&lt;/em&gt; caution, not a documented failure.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Note:&lt;/strong&gt; &quot;No known reduction between two assumptions&quot; is a statement about today&apos;s literature, not about mathematics. It means nobody has &lt;em&gt;published&lt;/em&gt; a way to turn a break of one into a break of the other. It does not mean no such way exists. Mistaking &quot;we have not found a link&quot; for &quot;there is no link&quot; is exactly the overconfidence that Shor and SIDH punished.&lt;/p&gt;
&lt;/blockquote&gt;

The strongest case for leaning on code-based encryption comes from the anti-monoculture camp around Daniel Bernstein and Tanja Lange [@ntruprime-diversity]. The argument has two parts: lattice concrete-security estimates are contested and have shifted over time, whereas the cost of information-set decoding is stable and can be pinned down by machine-checked attack simulators. The Kyber-512 figures they marshal are NIST&apos;s own [@classic-mceliece-site]. Read them as an interested party making a real point -- not as a neutral referee.
&lt;p&gt;So the encryption diversity is real but not proven, and the lattice concentration is real and only partly hedged. Which raises the deepest question in the article, the one no better algorithm can answer: could we ever &lt;em&gt;prove&lt;/em&gt; two assumptions uncorrelated, even in principle?&lt;/p&gt;
&lt;h2&gt;8. Why You Cannot Prove the Portfolio Uncorrelated&lt;/h2&gt;
&lt;p&gt;Now the bad news that no better algorithm can fix. There are two impossibilities here, and they ascend: the first is well known and merely humbling; the second is specific to this article&apos;s thesis and is, in a strict sense, permanent.&lt;/p&gt;
&lt;p&gt;The first: &lt;strong&gt;nothing in the stack is proven hard.&lt;/strong&gt; Module-LWE, syndrome decoding, and hash security all rest on the same foundation -- &quot;nobody has broken it yet.&quot; The best-known positive result is Regev&apos;s: a &lt;em&gt;quantum&lt;/em&gt; reduction from worst-case lattice problems to average-case LWE [@regev-lwe-2005]. That is genuine, beautiful evidence: if you could solve random LWE instances efficiently, you could solve the worst case of certain lattice problems too. But it is not a hardness proof, because those worst-case problems are themselves only &lt;em&gt;believed&lt;/em&gt; hard.&lt;/p&gt;

A problem is worst-case hard if *some* inputs are hard; it is average-case hard if a *randomly chosen* input is hard. Cryptography needs the second, stronger property, because keys are random. General decoding is NP-complete in the worst case, but that says nothing about the average random instance a code-based scheme actually uses -- which is why &quot;NP-complete&quot; is a weaker comfort here than it first sounds.
&lt;p&gt;It goes deeper than &quot;we have not gotten around to it.&quot; The lattice problems live in a place that makes a proof structurally unavailable.&lt;/p&gt;

The class of problems whose yes-answers and no-answers both have short, checkable certificates. The worst-case lattice problems (approximate GapSVP and GapSIVP) that LWE reduces from sit here [@aharonov-regev-2005]. That location is itself a clue: problems in NP intersect coNP are believed *not* to be NP-complete, so lattice hardness cannot simply be inherited from NP-completeness -- and a real hardness proof would have to settle questions about P, NP, and coNP that have resisted half a century of effort.

Suppose you proved that Module-LWE requires exponential time. You would then have exhibited a problem in NP that is not in P -- which proves P is not equal to NP, the most famous open question in computer science, with a million-dollar prize attached. Every cryptographic hardness assumption is, in this exact sense, a bet on how a Millennium Problem resolves. We build the internet on conjectures because proofs are unavailable, not because anyone is being careless.
&lt;p&gt;The second impossibility is the one this whole article has been circling, and it is worse than the first. Even if, by some miracle, we could prove each assumption individually hard, we still could not prove them &lt;em&gt;uncorrelated&lt;/em&gt;. Uncorrelatedness is a statement about all possible future mathematics: that no single idea, in any field, ever reaches two of these problems at once. You can accumulate evidence for it -- watch two assumptions resist different tools, wielded by different communities, for different lengths of time. You can never close it.&lt;/p&gt;
&lt;p&gt;SIDH is the proof of the danger: the tool that took it was a 1997 theorem nobody had connected to cryptography. There is no theorem that says &quot;and there are no more surprises like that one.&quot;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Key idea:&lt;/strong&gt; You cannot prove the portfolio uncorrelated. You can observe that two assumptions have resisted different tools for different lengths of time, but you can never rule out a single future idea that reaches both -- that is not a gap in today&apos;s knowledge, it is unprovable in principle. Diversity is therefore risk management, not proof. The portfolio is not a solution to the hardness problem; it is the best available discipline in the permanent absence of one.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;This is the moment the comfortable reading breaks. Diversity felt like a solution -- hold different assumptions and relax. It is not a solution. It is a disciplined bet made under permanent uncertainty, chosen precisely because certainty is not on the menu and never will be.&lt;/p&gt;

Diversity is the closest thing to a security proof this science permits -- and it is not a proof at all.
&lt;p&gt;If we can neither prove the bets hard nor prove them independent, the only rational questions left are practical ones: where would a correlated break actually come from, and how much time is on the clock?&lt;/p&gt;
&lt;h2&gt;9. Where the Correlated Break Would Come From&lt;/h2&gt;
&lt;p&gt;If you wanted to take down the whole stack, here is where you would aim. Three of these questions are open mathematics; the fourth is a clock.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;A &quot;Shor for lattices.&quot;&lt;/strong&gt; An efficient quantum algorithm for Module-LWE would be the nightmare scenario: a single result reaching ML-KEM, ML-DSA, and by extension the lattice core all at once -- the correlated break the map warns about. And this is not a thought experiment. In April 2024, Yilei Chen posted a paper claiming exactly such an algorithm.In little more than a week Chen withdrew the claim: a flaw in Step 9, found independently by Hongxun Wu and Thomas Vidick, could not be repaired [@chen-2024; @green-chen-2024]. It must be cited only as retracted, never as a live break [@quantum-insider-chen].&lt;/p&gt;
&lt;p&gt;The algorithm did not survive contact with other experts -- but for a little over a week, serious people believed the lattice core might be gone. That interval is the point. The feared correlated break is unrealized, not impossible, and the field felt exactly how much rides on one assumption.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Shared structure between lattices and codes.&lt;/strong&gt; As Section 7 noted, lattice sieving and code decoding both lean on nearest-neighbor search. Whether that shared tooling hides a deeper connection -- a single advance that erodes both bands -- is genuinely open. No reduction is known, no transfer has been demonstrated, and &quot;no known reduction&quot; is not &quot;no possible link.&quot;&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Whether the signature on-ramp adds real diversity.&lt;/strong&gt; NIST is still recruiting more signature families, and the roster is a live test of the whole thesis.&lt;/p&gt;

NIST is hunting for additional, uncorrelated signature families through an &quot;on-ramp&quot; call [@nist-onramp]. The candidates are telling. SQIsign is an isogeny scheme, the family whose SIDH and SIKE members collapsed in 2022. UOV, MAYO, and SNOVA are multivariate, the family whose flagship Rainbow was key-recovered in a weekend on a laptop [@beullens-rainbow-2022]. FAEST and HAWK bring still other assumptions. The open question is whether adding a *young, lightly vetted* family is durable diversity or just new, unmeasured risk -- because SIDH proved that &quot;vetted for a few years&quot; is not the same as &quot;safe.&quot;
&lt;p&gt;&lt;strong&gt;The clock.&lt;/strong&gt; Everything above would be an academic seminar if the timeline were comfortable. It is not, because of a single idea.&lt;/p&gt;

The attack that makes migration urgent today even though no quantum computer exists yet. An adversary records encrypted traffic now and stores it, waiting for a future quantum computer to decrypt it retroactively. Any secret that must stay confidential for longer than the time-to-quantum is already exposed, no matter how strong today&apos;s key exchange looks.
&lt;p&gt;Michele Mosca turned this into a one-line risk test, $X + Y \geq Z$: if the years your data must stay secret ($X$) plus the years you need to migrate ($Y$) meet or exceed the years until a cryptographically relevant quantum computer ($Z$), your data is already at risk today [@mosca-2015].&lt;/p&gt;
&lt;p&gt;{`&lt;/p&gt;
Mosca&apos;s inequality: if secrecy_life + migration_time &amp;gt;= time_to_quantum,
your data is already exposed to harvest-now-decrypt-later.
&lt;p&gt;def already_exposed(secrecy_life_years, migration_years, years_to_quantum):
    exposure = secrecy_life_years + migration_years
    print(&quot;Secrecy lifetime (X): &quot; + str(secrecy_life_years) + &quot; yr&quot;)
    print(&quot;Migration time  (Y):  &quot; + str(migration_years) + &quot; yr&quot;)
    print(&quot;Time to quantum (Z):  &quot; + str(years_to_quantum) + &quot; yr&quot;)
    if exposure &amp;gt;= years_to_quantum:
        print(&quot;EXPOSED: X + Y exceeds Z by &quot; + str(exposure - years_to_quantum) + &quot; yr. Migrate now.&quot;)
    else:
        print(&quot;Safe for now by &quot; + str(years_to_quantum - exposure) + &quot; yr. Keep watching Z.&quot;)&lt;/p&gt;
A record that must stay secret 15 years, a 5-year migration, quantum in 12 years:
&lt;p&gt;already_exposed(15, 5, 12)
`}&lt;/p&gt;
&lt;p&gt;For many long-lived secrets the inequality already bites, which is why the migration is being written into law rather than left to preference. The alarm is not new -- the NSA signaled it as early as 2015, when it announced plans to move away from its existing Suite B algorithms [@nsa-2015]. It has since hardened into deadlines: CNSA 2.0 sets a 2025-to-2033 timeline for national security systems [@cnsa-2.0], and Executive Order 14412 codifies migration requirements and the &lt;a href=&quot;https://paragmali.com/blog/q-day-has-not-happened-the-incident-already-has-harvest-now-/&quot; rel=&quot;noopener&quot;&gt;harvest-now-decrypt-later&lt;/a&gt; threat directly into federal policy [@eo-14412].&lt;/p&gt;
&lt;p&gt;None of the open questions is settled, and the clock is already running. So the only responsible move is to build a stack today that survives being wrong about any one of them. That turns out to be a concrete engineering task.&lt;/p&gt;
&lt;h2&gt;10. Building an Uncorrelated Stack on Monday&lt;/h2&gt;
&lt;p&gt;Strip away the theory. Here is what to deploy, and the single rule that ties it together: watch the &lt;em&gt;assumption&lt;/em&gt;, not the algorithm name.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Deploy hybrids.&lt;/strong&gt; Run a classical key exchange and a post-quantum KEM together and combine their secrets, so that a break of the post-quantum half is not, by itself, a break of the session. The dominant TLS deployment is the hybrid group X25519MLKEM768; the closely related general-purpose combiner X-Wing [@xwing-2024] is built on the same X25519 and ML-KEM-768 primitives.&lt;/p&gt;

flowchart LR
  X[&quot;X25519 shared secret&quot;] --&amp;gt; KDF[&quot;Combiner / KDF&quot;]
  K[&quot;ML-KEM-768 shared secret&quot;] --&amp;gt; KDF
  KDF --&amp;gt; S[&quot;Session key (secure if either input holds)&quot;]
&lt;p&gt;This is not a hypothetical benefit.The empirical case for hybrids is already written. Cloudflare&apos;s earlier CECPQ2b experiment paired X25519 with the isogeny KEM SIKE, and any traffic recorded then stayed safe when SIKE broke -- the classical half still held [@cloudflare-pq-2024]. A hybrid turned a total break into a non-event. A hybrid is the correlation lens applied to a single connection.&lt;/p&gt;
&lt;p&gt;{`
// A hybrid combines a classical secret and a post-quantum secret.
// The session key is safe as long as EITHER half is still unbroken.
function hybridSafe(classicalBroken, pqBroken) {
  return !(classicalBroken &amp;amp;&amp;amp; pqBroken);
}&lt;/p&gt;
&lt;p&gt;for (const classicalBroken of [false, true]) {
  for (const pqBroken of [false, true]) {
    const verdict = hybridSafe(classicalBroken, pqBroken) ? &apos;SAFE&apos; : &apos;EXPOSED&apos;;
    console.log(&apos;classical broken=&apos; + classicalBroken +
                &apos;, PQ broken=&apos; + pqBroken + &apos;  -&amp;gt;  &apos; + verdict);
  }
}
// Only the final row, where both are broken, prints EXPOSED.
`}&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Refuse a lattice monoculture.&lt;/strong&gt; This is the mistake the whole article exists to prevent.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Note:&lt;/strong&gt; Replacing RSA with ML-KEM, and ECDSA with ML-DSA and Falcon, feels like a thorough migration. In assumption terms it is a lattice monoculture: one good enough advance against structured lattices reaches all of it. &quot;Post-quantum&quot; is not the same thing as &quot;diversified.&quot;&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;Pair the efficient lattice core with a backstop that shares nothing with it: SLH-DSA for signatures you need to trust for decades, and a code-based KEM -- HQC or Classic McEliece -- kept available for encryption. And because the lattice margin is the contested one, prefer the higher-margin parameter sets (ML-KEM-768 or 1024) over the smallest.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Build for replacement.&lt;/strong&gt; No choice here is permanent, so the system must be able to change its mind.&lt;/p&gt;

The engineering property of being able to swap a cryptographic primitive without re-architecting the system around it. If your protocol treats &quot;the KEM&quot; as a replaceable module rather than a hardwired choice, then an assumption that starts to erode can be dropped for another before it fails -- which is the operational form of holding a portfolio.
&lt;p&gt;Put together, the decision guide is short, and every row is chosen by &lt;em&gt;assumption&lt;/em&gt;, not by benchmark:&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Need&lt;/th&gt;
&lt;th&gt;Deploy&lt;/th&gt;
&lt;th&gt;Why&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;&lt;tr&gt;
&lt;td&gt;General key exchange&lt;/td&gt;
&lt;td&gt;ML-KEM-768, hybridized with X25519&lt;/td&gt;
&lt;td&gt;Efficient lattice core plus a classical backstop&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Maximum-conservatism encryption&lt;/td&gt;
&lt;td&gt;Classic McEliece or HQC&lt;/td&gt;
&lt;td&gt;Code assumption, uncorrelated with lattices&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;General signatures&lt;/td&gt;
&lt;td&gt;ML-DSA-65, hybridized&lt;/td&gt;
&lt;td&gt;Efficient lattice signature with a classical hedge&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Firmware and root-of-trust signing&lt;/td&gt;
&lt;td&gt;SLH-DSA&lt;/td&gt;
&lt;td&gt;Hash-only, shares nothing with the rest, longest-lived trust&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Bandwidth-critical signing&lt;/td&gt;
&lt;td&gt;Falcon&lt;/td&gt;
&lt;td&gt;Smallest signatures, at the cost of a third lattice bet&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;&lt;/table&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Note:&lt;/strong&gt; When you audit a stack for diversity, ignore the product names and list the &lt;em&gt;assumptions&lt;/em&gt;. Three lattice schemes with three different names are one bet. A lattice KEM, a hash signature, and a code KEM are three. The name tells you the vendor; the assumption tells you what actually has to break.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;One boundary, named once and handed off: the ways these schemes break &lt;em&gt;in practice&lt;/em&gt; -- &lt;a href=&quot;https://paragmali.com/blog/how-ml-kem-breaks-in-real-life-the-machine-leaked-while-the-/&quot; rel=&quot;noopener&quot;&gt;timing leaks in KEM decapsulation&lt;/a&gt;, the delicate floating-point sampling inside Falcon&apos;s signer, fault and power attacks -- are implementation attacks, a different and equally real surface owned by the sibling track. This section is about the mathematics you choose to deploy, not the code that runs it.&lt;/p&gt;
&lt;p&gt;Every one of these moves is a refusal to concentrate -- the same refusal, at the level of a single deployment, that the whole standardization effort was reaching for. Which brings us back to the thesis, now with all the evidence in.&lt;/p&gt;
&lt;h2&gt;11. Common Misconceptions, Corrected&lt;/h2&gt;
&lt;p&gt;The fastest way to misread everything above is to reach for one of these seven conclusions. Each is a precise trap, and each answer defends the portfolio rather than any single scheme.&lt;/p&gt;


No. Every standardized scheme -- ML-KEM, ML-DSA, SLH-DSA -- currently stands, and HQC has been selected on top of them [@ir-8545]. The argument of this article is not that the stack is weak. It is that the stack&apos;s safety is a *diversified portfolio*, not the proven hardness of any one algorithm, because none of them is proven hard.


No. The 2022 break was entirely *classical*: it applied Kani&apos;s 1997 reducibility criterion to the torsion-point data that SIDH publishes by design, and recovered the key in about ten minutes on a single ordinary core [@castryck-decru-2022; @kani-1997]. No quantum computer was involved. It was not Shor and it was not quantum.


No. SIKE was a Round-4 *alternate candidate* still under evaluation, and it was broken before any selection was made [@ir-8413; @nist-2022-selection]. It was never standardized. The correct lesson is that a late-stage, heavily vetted candidate can fall without warning -- which is worse, not better, than a fringe scheme failing.


A *generic, structural* break of Module-LWE would indeed threaten both -- that is the correlated-pair risk at the center of the map. But they use different parameters (moduli 3329 versus 8380417, different ranks and noise), and ML-DSA additionally rests on Module-SIS, so a *parameter-specific* attack on one need not transfer to the other [@fips-203; @fips-204]. The correlation is at the level of the shared assumption family, not identical instances.


Its security *is* hash security -- that is the design, not a weakness [@fips-205]. And SHA-2 and SHA-3 carry the largest, most-scrutinized security margins in all of cryptography. Reducing entirely to that well-studied foundation, while sharing no algebraic structure with lattices or codes, is exactly why SLH-DSA is the conservative anchor of the portfolio.


Because the trust is not placed in one assumption; it is placed in diversity. Lattice, code, and hash rest on unrelated mathematics developed by different communities, and are unlikely to all fall for the same reason at the same time. A break of one leaves the others standing. That is risk management under permanent uncertainty, which is the most any cryptographic science can offer.


No -- it is HQC. Classic McEliece is standardized on the ISO track [@classic-mceliece-iso] and was not selected in this round; NIST&apos;s IR 8545 explains why it chose HQC over BIKE and why it did not select McEliece [@ir-8545]. Both are code-based, but the newly selected NIST KEM is HQC.

&lt;p&gt;Notice what every answer has in common: not one of them defends a single algorithm. They defend the portfolio.&lt;/p&gt;
&lt;h2&gt;12. The Portfolio Is the Product&lt;/h2&gt;
&lt;p&gt;Put the evidence back together. Shor proved that two bets which looked independent -- factoring and discrete log -- were one bet on the abelian hidden-subgroup problem, and fell together the moment the right machine existed [@shor-1994]. SIDH proved that a family can vanish in an afternoon, classically, with no warning, when a 1997 theorem finally met the auxiliary data the protocol had been publishing all along [@castryck-decru-2022]. And the standardized stack, colored by assumption, clusters onto three families -- lattice, hash, and code -- with a genuinely correlated Module-LWE pair, ML-KEM and ML-DSA, sitting at its efficient center [@fips-203; @fips-204].&lt;/p&gt;
&lt;p&gt;None of those assumptions is proven hard. None ever will be, short of settling questions about P, NP, and coNPP is the class of problems solvable quickly; NP the class whose solutions can be verified quickly. Whether the two are equal is the central unsolved question of computer science. that have resisted fifty years of effort. And even if they were proven hard one at a time, no theorem could certify them uncorrelated, because uncorrelatedness is a promise about mathematics not yet invented. That is the humbling floor under the entire post-quantum project.&lt;/p&gt;
&lt;p&gt;So the security of the stack was never going to be the strength of its strongest algorithm. It is the deliberate, dated refusal to let its bets be correlated: hash-only SLH-DSA standing apart from everything, the March 2025 selection of code-based HQC precisely &lt;em&gt;because&lt;/em&gt; it is not a lattice, and an on-ramp still searching for more uncorrelated bets [@fips-205; @ir-8545]. Diversity here is not a hedge bolted onto the design. It is the design.&lt;/p&gt;
&lt;p&gt;That reframes what we have actually been buying all along. Not a proof. A portfolio.&lt;/p&gt;

We cannot prove the stack secure. But we can, and did, refuse to bet it all on one piece of mathematics.
&lt;p&gt;This is the sentence you were handed in the first section, now earned. We are not betting on a proof. We are betting that lattice, code, and hash will not all fail for the same reason on the same day -- and we have arranged things so that if we are wrong about one, we are not wrong about all three. For a science that can prove nothing hard, that disciplined refusal to concentrate is not a consolation prize. It is the whole defense, and it is the best one available for the thirty years we are wagering on it.&lt;/p&gt;
&lt;p&gt;&amp;lt;StudyGuide slug=&quot;how-the-whole-stack-would-break&quot; keyTerms={[
  { term: &quot;Correlated failure&quot;, definition: &quot;Two or more primitives that fail together because they share hidden mathematics&quot; },
  { term: &quot;Abelian hidden-subgroup problem&quot;, definition: &quot;The structure Shor exploits; factoring and discrete log are both instances&quot; },
  { term: &quot;Module-LWE&quot;, definition: &quot;Noisy linear algebra over module lattices; the shared assumption of ML-KEM and ML-DSA&quot; },
  { term: &quot;Syndrome decoding&quot;, definition: &quot;The code-based hard problem behind HQC and Classic McEliece&quot; },
  { term: &quot;Hybrid key exchange&quot;, definition: &quot;Combine a classical and a post-quantum secret; secure if either half holds&quot; },
  { term: &quot;Crypto-agility&quot;, definition: &quot;The ability to swap a primitive without re-architecting the system&quot; },
  { term: &quot;NP intersect coNP&quot;, definition: &quot;Where lattice problems sit, which implies they are believed not NP-complete&quot; }
]} flashcards={[
  { front: &quot;What was the original correlated failure?&quot;, back: &quot;Shor: factoring and discrete log fell together as one abelian-HSP bet&quot; },
  { front: &quot;How was SIDH broken?&quot;, back: &quot;Classically, via Kani&apos;s 1997 criterion on published torsion images, about ten minutes on one core&quot; },
  { front: &quot;Which schemes are the correlated pair?&quot;, back: &quot;ML-KEM and ML-DSA, both on Module-LWE, with different parameters&quot; },
  { front: &quot;Which scheme shares nothing with the rest?&quot;, back: &quot;SLH-DSA, whose security reduces entirely to hash strength&quot; },
  { front: &quot;What is the code hedge?&quot;, back: &quot;HQC (NIST-selected 2025) and Classic McEliece (ISO-track)&quot; }
]} questions={[
  { q: &quot;Why is a single-family swap still a monoculture?&quot;, a: &quot;It concentrates all security on one hard-problem family, so one advance takes everything -- the mistake Shor punished.&quot; },
  { q: &quot;Why can uncorrelatedness never be proven?&quot;, a: &quot;It is a claim about all future mathematics; you cannot rule out one idea reaching two assumptions at once. SIDH is the cautionary case.&quot; },
  { q: &quot;What does the March 2025 HQC selection demonstrate?&quot;, a: &quot;Diversification as explicit, dated policy: a second KEM chosen because it is code-based, not lattice-based.&quot; }
]} /&amp;gt;&lt;/p&gt;
</content:encoded><category>post-quantum-cryptography</category><category>cryptographic-assumptions</category><category>lattice-cryptography</category><category>sidh-sike</category><category>nist-pqc</category><category>crypto-agility</category><category>correlated-failure</category><category>hybrid-key-exchange</category><author>noreply@paragmali.com (Parag Mali)</author></item><item><title>You Cannot Rotate What You Cannot See: Crypto-Agility and the Cryptographic Bill of Materials</title><link>https://paragmali.com/blog/you-cannot-rotate-what-you-cannot-see-crypto-agility-and-the/</link><guid isPermaLink="true">https://paragmali.com/blog/you-cannot-rotate-what-you-cannot-see-crypto-agility-and-the/</guid><description>The hard part of post-quantum is not the new algorithms -- it is finding the old ones. A field guide to crypto-agility, discovery, and the CycloneDX CBOM.</description><pubDate>Tue, 14 Jul 2026 03:13:06 GMT</pubDate><content:encoded>
Post-quantum migration is two problems wearing one name: being able to ROTATE your cryptography, and being able to SEE where it all lives. The new algorithms are the easy part -- ML-KEM is a `pip install` away and already ships inside Windows. The hard part is finding the old RSA, ECDH, and ECDSA, which is &quot;typically buried deep within components.&quot; Crypto-agility (RFC 7696, 2015) is the design-time discipline for rotating. The Cryptography Bill of Materials (CBOM), upstreamed into CycloneDX v1.6 in April 2024, is the machine-readable substrate for seeing: it models cryptography as a first-class asset with `implements` and `uses` dependencies you can prioritize as a graph. Executive Order 14412 makes the stack binding -- key establishment by 2030, signatures by 2031 -- and directs CISA to define CBOM&apos;s minimum elements. But both halves have a provable ceiling: complete automated discovery is undecidable, and long-lived signatures, trust anchors, and firmware cannot be rotated after the fact. This is the field guide to both verbs, and to why you cannot rotate what you cannot see.
&lt;h2&gt;1. You Cannot Rotate What You Cannot See&lt;/h2&gt;
&lt;p&gt;In November 2022, the White House told every federal civilian agency to do something that sounds almost trivial: make a list. OMB Memorandum M-23-02 directed each agency to produce a &lt;em&gt;prioritized inventory&lt;/em&gt; of the cryptographic systems most vulnerable to a future quantum computer, to submit the first version by May 4, 2023, and to keep it current every year through 2035 [@omb-m2302]. Not to migrate anything yet. Just to write down where the vulnerable cryptography was, and to name a migration lead within thirty days to own the effort [@omb-m2302].&lt;/p&gt;
&lt;p&gt;Agencies discovered they could not do it. They could not reliably answer the question &quot;where does our RSA-2048 actually live?&quot; -- because, as IBM&apos;s own documentation for the Cryptography Bill of Materials puts it, cryptography &quot;is typically buried deep within components that are used to compose and build systems and applications&quot; [@ibm-cbom]. The mandate assumed a list any competent organization could produce. The list turned out to be the hard part.&lt;/p&gt;
&lt;p&gt;Now the deadlines are real. Executive Order 14412, signed June 22, 2026, orders agencies to move their high-value and high-impact systems to post-quantum key establishment by December 31, 2030 and to post-quantum digital signatures by December 31, 2031 [@eo14412]. And here is the asymmetry that reframes the entire migration: &lt;strong&gt;the new algorithm is the easy part.&lt;/strong&gt; NIST finalized the replacements in FIPS 203, 204, and 205 on August 13, 2024 [@fips203].&lt;/p&gt;
&lt;p&gt;ML-KEM, the standardized replacement for the key exchange that Shor&apos;s algorithm dooms, is a &lt;code&gt;pip install&lt;/code&gt; away in Python and already ships inside Windows&apos; SChannel and SymCrypt [@pyca-changelog] [@ms-pqc-windows], as the sibling posts in this series show.The two &quot;migrate to what&quot; endpoints are covered in companion posts: ML-KEM arriving in the default &lt;code&gt;pyca/cryptography&lt;/code&gt; wheels, and ML-KEM plus ML-DSA landing in Windows SChannel and SymCrypt. This article is deliberately the other half -- finding the old cryptography, not adopting the new.&lt;/p&gt;
&lt;p&gt;You can adopt the replacement this afternoon. What you cannot do this afternoon -- or this quarter, or perhaps by the deadline -- is enumerate every place your organization still relies on the cryptography it replaces.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Note:&lt;/strong&gt; FIPS 203, 204, and 205 were finalized in August 2024 [@fips203], and quantum-safe primitives now ship in mainstream libraries and operating systems [@pyca-changelog] [@ms-pqc-windows]. Yet the 2030 and 2031 deadlines are hard [@eo14412]. The binding constraint is not availability. It is visibility -- knowing where the quantum-vulnerable cryptography is.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;Post-quantum migration is really two problems wearing one name. One is being &lt;em&gt;able to change&lt;/em&gt; your cryptography -- the discipline of &lt;strong&gt;crypto-agility&lt;/strong&gt;, which the field has refined since the 1990s and formalized in 2015. The other is &lt;em&gt;knowing where your cryptography is&lt;/em&gt; -- the inventory problem, which almost nobody was forced to take seriously until a mandate arrived with a deadline attached.&lt;/p&gt;
&lt;p&gt;The two-verb diagnostic runs through everything that follows. &lt;strong&gt;ROTATE:&lt;/strong&gt; can a system change its algorithms at all, without being re-architected? &lt;strong&gt;SEE:&lt;/strong&gt; does the organization actually know where its RSA, ECDH, and ECDSA are deployed? The thesis of this field guide is one line: &lt;em&gt;you cannot rotate what you cannot see.&lt;/em&gt;&lt;/p&gt;
&lt;p&gt;Why does the split matter so precisely, and why do the two deadlines differ by a year? Because the threat driving the confidentiality deadline is not a quantum computer that exists today. It is an adversary recording your encrypted traffic today to decrypt it later, once a capable quantum machine is built.&lt;/p&gt;

The threat model in which an adversary records encrypted data today and stores it, intending to decrypt it once a sufficiently capable quantum computer exists. Because captured ciphertext can be broken retroactively, HNDL makes confidentiality and key establishment urgent *now* -- even before any quantum computer is built. It does not threaten digital signatures, which cannot be forged retroactively, which is why Executive Order 14412 dates key establishment (2030) ahead of signatures (2031) [@eo14412].

A quantum computer large and reliable enough to run Shor&apos;s algorithm against deployed RSA and elliptic-curve key sizes. No CRQC is known to exist yet; its uncertain future arrival date is the quantity a migration plan races against, and the term that anchors the prioritization math introduced later in this guide.
&lt;p&gt;The ability to swap an algorithm is the half the field spent thirty years perfecting. Knowing where every algorithm lives is the half it avoided until a deadline made avoidance impossible. To see how the discipline got so lopsided, start where the pain began: with cryptography that could not be changed at all.&lt;/p&gt;
&lt;h2&gt;2. Algorithm Rigidity as Original Sin&lt;/h2&gt;
&lt;p&gt;Long before anyone worried about quantum computers, migrating a single cryptographic algorithm was already agony -- and the reason was structural, not mathematical. The 2030 deadline is a decade-long emergency, not a weekend of &lt;code&gt;pip install&lt;/code&gt; commands, because changing one algorithm has always been so hard that it takes decades.&lt;/p&gt;
&lt;p&gt;Start with why a migration is coming at all. In 1994, Peter Shor showed that a quantum computer could factor large integers and compute discrete logarithms in polynomial time [@shor1994]. That single result put RSA, Diffie-Hellman, elliptic-curve Diffie-Hellman, and ECDSA on notice: the mathematical problems they rely on become tractable to a sufficiently large quantum machine.&lt;/p&gt;
&lt;p&gt;The internals of Shor&apos;s algorithm and the lattice math that replaces these primitives belong to the companion posts in this series. For this guide, one fact is enough: the public-key cryptography holding up most of the internet has a known expiration condition, and the field has known it for three decades.&lt;/p&gt;
&lt;p&gt;Knowing an algorithm will eventually fall is not the same as being able to replace it. The deeper problem is that early protocols baked a single primitive directly into their design. There was no algorithm identifier on the wire, so a peer could not announce which cipher it intended to use, and there was no clean seam at which to substitute a different one.&lt;/p&gt;
&lt;p&gt;RFC 7696, the IETF&apos;s 2015 best-current-practice document on the subject, describes the consequence precisely: without an algorithm identifier, transitioning &quot;from one algorithm to another&quot; requires &quot;the protocol version number or some other major change&quot; [@rfc7696]. Swapping a cipher meant revising the protocol itself.&lt;/p&gt;

The design-time property that, in RFC 7696&apos;s words, &quot;Algorithm agility is achieved when a protocol can easily migrate from one algorithm suite to another more desirable one, over time&quot; [@rfc7696]. In plain terms: the ability to change cryptographic algorithms without re-architecting the systems that depend on them. It is a property you build in before you need it -- and it says nothing about discovering cryptography you have already deployed.
&lt;p&gt;The canonical worked example is slow, symmetric, and instructive. RFC 7696 notes that &quot;the transition from DES to Triple-DES to AES took place over decades, causing a shift in symmetric block cipher strength from 56 bits to 112 bits to 128 bits&quot; [@rfc7696].That 56-to-112-to-128-bit progression over roughly a quarter century is the template the public-key world is now rerunning against RSA and elliptic curves, except compressed into a single mandated decade. The symmetric transition had no hard federal deadline; this one does. Decades, for a change every cryptographer agreed was necessary. And the reason was not that AES was hard to implement. It was that thousands of systems had hardcoded the old cipher with no seam at which to change it.&lt;/p&gt;
&lt;p&gt;This is the original sin, and it compounds. RFC 7696 opens with the blunt observation that &quot;cryptographic algorithms age; they become weaker with time,&quot; so protocol designers &quot;need to assume that advances in computing power or advances in cryptoanalytic techniques will eventually make any algorithm obsolete&quot; [@rfc7696]. If aging is certain and the algorithm is welded in place, then every cryptographic break becomes an estate-wide re-architecture. The field lived this repeatedly: DES and Triple-DES, MD5, RC4, and SHA-1 each had to be ripped out of deployed systems at enormous cost.&lt;/p&gt;
&lt;p&gt;RC4 was so entrenched that removing it required the IETF to publish an entire standard, RFC 7465, whose sole job was to command that &quot;TLS clients and servers never negotiate the use of RC4 cipher suites when they establish connections&quot; [@rfc7465].Adding an algorithm is easy; removing one is so hard that it can take a dedicated standards-body prohibition. RFC 7465 exists only to say &quot;stop using RC4&quot; -- a one-line policy that needed the weight of a published RFC because the cipher was wired into too many implementations to retire quietly [@rfc7465].&lt;/p&gt;

timeline
    title From Shor to a federal deadline
    1994 : Shor&apos;s algorithm dooms RSA, DH, and ECC in theory
    1990s-2001 : DES to Triple-DES to AES over decades
    2015 : RFC 7696 turns agility into a discipline
    2022 : NSM-10 and OMB M-23-02 mandate a prioritized inventory
    2023 : NIST NCCoE SP 1800-38 preliminary draft on discovery
    2024 : CBOM upstreamed into CycloneDX v1.6
    2025 : NIST CSWP 39 restates agility as risk management
    2026 : Executive Order 14412 sets the 2030 and 2031 deadlines
&lt;p&gt;Notice the character of this failure. It is not that the cryptography computed the wrong answer. DES still encrypts; MD5 still hashes. The failure is one of operability: the algorithm runs fine, but the system cannot move off it. That distinction matters, because it means the fix is not a better algorithm. The fix is a better &lt;em&gt;design&lt;/em&gt; -- one that stops welding the primitive in place.&lt;/p&gt;
&lt;p&gt;The obvious such fix is to put a name on the wire and let the peers choose. That fix has a name of its own, cipher-suite negotiation, and for a while it looked like the whole answer. It was not.&lt;/p&gt;
&lt;h2&gt;3. Negotiation and the Spreadsheet&lt;/h2&gt;
&lt;p&gt;Each half of the problem got a first-generation answer. Both were reasonable. Both under-delivered, and in almost the same instructive way. If you can negotiate algorithms at connection time and audit the results into a spreadsheet, what could possibly be left to solve?&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;The rotate half&apos;s first answer was negotiation.&lt;/strong&gt; Instead of welding one cipher into the protocol, carry an identifier for the algorithm -- or for a whole suite of them -- on the wire, back it with an IANA registry of code points, and let the two endpoints agree on the best option they both support. TLS cipher suites, IKE and IPsec transforms, the &lt;a href=&quot;https://paragmali.com/blog/a-perfect-signature-for-a-certificate-that-should-never-have/&quot; rel=&quot;noopener&quot;&gt;X.509&lt;/a&gt; &lt;code&gt;AlgorithmIdentifier&lt;/code&gt;, and the JOSE and COSE object formats all work this way.&lt;/p&gt;
&lt;p&gt;RFC 7696 blesses the approach while carefully bounding its importance: &quot;The inclusion of an algorithm identifier is a minimal step toward cryptographic algorithm agility&quot; [@rfc7696]. Minimal is the operative word.&lt;/p&gt;
&lt;p&gt;Negotiation is necessary, and it is nowhere near sufficient, for three documented reasons. First, negotiation you do not integrity-protect can be turned against you. RFC 7696 warns that an unprotected negotiation &quot;will be subject to a downgrade attack&quot; [@rfc7696], and the field has the scars to prove it. The 2015 Logjam attack &quot;allows a man-in-the-middle attacker to downgrade vulnerable TLS connections to 512-bit export-grade cryptography&quot; [@weakdh], steering two peers who both support strong &lt;a href=&quot;https://paragmali.com/blog/nobody-broke-the-discrete-log-a-field-guide-to-diffie-hellma/&quot; rel=&quot;noopener&quot;&gt;Diffie-Hellman&lt;/a&gt; down to a key size a well-resourced attacker can break [@weakdh-pdf]. FREAK and POODLE are cousins in the same family [@freak] [@poodle].&lt;/p&gt;
&lt;p&gt;Second, negotiation encourages &lt;em&gt;ossification&lt;/em&gt;: because dropping an option can break some peer somewhere, &quot;flawed algorithms are supported for far too long&quot; [@rfc7696] -- which is exactly why retiring RC4 needed its own prohibiting standard [@rfc7465].&lt;/p&gt;
&lt;p&gt;Third, every additional negotiable option is additional attack surface and additional code to get right [@rfc7696].&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Note:&lt;/strong&gt; Being able to negotiate a strong cipher does two things it is easy to conflate with a solved migration, and neither is one. Unprotected negotiation invites downgrade attacks -- Logjam, FREAK, and POODLE all forced peers onto weak-but-supported options [@weakdh] [@freak] [@poodle]. And selecting AES at connection time tells you nothing about &lt;em&gt;where&lt;/em&gt; the weak algorithm still lives. Negotiating AES on one server says nothing about which of your ten thousand other servers still negotiate RC4.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;That last point is the decisive one for this guide. Negotiation lets a system &lt;em&gt;select&lt;/em&gt; among options both peers pre-agreed to support. It gives you no ability to &lt;em&gt;remove&lt;/em&gt; an algorithm across your estate, and -- this is the part everyone misses -- no ability to &lt;em&gt;know where a given algorithm is deployed in the first place&lt;/em&gt;.&lt;/p&gt;
&lt;p&gt;A protocol that can negotiate its way onto AES has told you nothing about the inventory of RC4, RSA-1024, or SHA-1 scattered across your servers, firmware, and stored certificates. Agility at the connection is not visibility across the estate.&lt;/p&gt;
&lt;p&gt;The two negotiation styles are both legitimate and opposite. IPsec and IKEv2 carry a separate identifier for each algorithm; TLS carries one identifier per whole suite. RFC 7696 explicitly blesses both -- &quot;some approaches carry one identifier for each algorithm ... other approaches carry one identifier for a full suite of algorithms&quot; [@rfc7696] -- trading a combinatorial explosion of options against coarser, less flexible suites. There is no single right answer, only a design choice.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;The see half&apos;s first answer was the spreadsheet.&lt;/strong&gt; Manual audits, one-off certificate scans, a cryptography inventory maintained by hand. It is the natural first move, and it fails for reasons that have nothing to do with effort. A spreadsheet does not scale to an estate of thousands of applications and millions of certificates. It is stale the moment it is written, because code ships and certificates rotate daily.&lt;/p&gt;
&lt;p&gt;It is not machine-actionable: you cannot run a query against it, diff it against last quarter, or check it automatically against a 2030 deadline. And it cannot be propagated -- when a vendor updates a library, nothing in your spreadsheet knows. It is a document, not a queryable system.&lt;/p&gt;
&lt;p&gt;The one semi-automated technique in wide use, certificate discovery, is genuinely useful but sees only the public-key infrastructure surface: the certificates, not the code that calls them or the protocols that carry them.&lt;/p&gt;
&lt;p&gt;To name the shape of the answer that eventually arrives, borrow the idea the software supply chain had already converged on.&lt;/p&gt;

A machine-readable inventory of the components inside a piece of software and the dependencies among them, published in a standard format such as CycloneDX or SPDX so that tools -- not people -- can query, diff, and act on it [@owasp-cdx16]. An SBOM is to software components what a later chapter&apos;s Cryptography Bill of Materials is to cryptographic assets: the crypto version is a specialized extension of exactly this idea.
&lt;p&gt;Both first answers failed for the same underlying reason: they treated agility and inventory as afterthoughts to bolt on, rather than disciplines to design for. The difference in what happened next is the whole story of the next section. The rotate half got its discipline first, compressed into a single 2015 document that turned &quot;agility&quot; from a slogan into an engineering checklist. The see half got nothing comparable -- until someone with a deadline &lt;em&gt;made&lt;/em&gt; organizations solve it.&lt;/p&gt;
&lt;h2&gt;4. From Slogan to Discipline, and the Inventory Forced Into the Open&lt;/h2&gt;
&lt;p&gt;This is where the two lineages split, mature on separate tracks, and then -- years later -- get forced back together by a mandate. It also poses the sharpest question in the whole story: if algorithm agility became a real engineering discipline in 2015, why were federal agencies still helpless in front of a simple inventory in 2022?&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;The rotate half got its discipline in a single document.&lt;/strong&gt; In November 2015, Russ Housley published RFC 7696, &quot;Guidelines for Cryptographic Algorithm Agility and Selecting Mandatory-to-Implement Algorithms,&quot; as IETF Best Current Practice 201 [@rfc7696]. It turned a slogan into a checklist. Register your algorithm identifiers. Keep the set of algorithms every implementation must support small, and -- the load-bearing idea -- put that set in a &lt;em&gt;companion&lt;/em&gt; document so it can change &quot;without updating the base protocol specification&quot; [@rfc7696]. Integrity-protect your negotiation so it cannot be downgraded [@rfc7696].&lt;/p&gt;
&lt;p&gt;And heed two cautions that sound paradoxical until you have lived them: section 3.2 is titled &quot;Too Many Choices Can Be Harmful,&quot; and section 3.3 is titled &quot;Picking One True Cipher Suite Can Be Harmful&quot; [@rfc7696]. Too many negotiable options is attack surface; exactly one is a single point of failure with no in-band recovery. The discipline lives in the tension between them.&lt;/p&gt;

The small set of algorithms every conformant implementation of a protocol is required to support, so that any two implementations are guaranteed to share at least one. RFC 7696 recommends keeping the MTI set in a separate companion document precisely so the required algorithms can change &quot;without updating the base protocol specification&quot; when one weakens [@rfc7696] -- agility applied to the requirements themselves.
&lt;p&gt;Here is the limit that makes 2015 insufficient for 2022. RFC 7696 is &lt;em&gt;design-time and forward-looking&lt;/em&gt;. It helps every system you build &lt;em&gt;after&lt;/em&gt; you adopt it, and it says nothing about &lt;em&gt;discovering&lt;/em&gt; the cryptography you already deployed across a legacy estate. An organization can adopt RFC 7696 wholesale for all new development and still be completely unable to answer &quot;where does RSA-2048 live in what we already run?&quot; The discipline hardens the rotate half. It never touched the see half.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;The see half was forced open by a mandate.&lt;/strong&gt; In May 2022, National Security Memorandum 10 set the strategy: inventory the government&apos;s quantum-vulnerable cryptography [@nsm10]. That November, OMB M-23-02 operationalized it, directing every agency to submit a &lt;em&gt;prioritized&lt;/em&gt; cryptographic inventory, to designate a cryptographic inventory and migration lead within thirty days, and to repeat the inventory annually [@omb-m2302]. The order was not &quot;migrate.&quot; It was merely &quot;tell us what you have, worst things first.&quot;&lt;/p&gt;
&lt;p&gt;And it exposed the binding constraint immediately: agencies could not enumerate their own quantum-vulnerable cryptography, because -- as IBM&apos;s CBOM documentation states -- it &quot;is typically buried deep within components that are used to compose and build systems and applications&quot; [@ibm-cbom]. The manual method the mandate inherited did not scale to the estate it was pointed at. This, not any algorithm milestone, is the real turning point of the field: thirty years of perfecting the rotate half had left the see half genuinely unsolved.&lt;/p&gt;

&quot;Cryptography is typically buried deep within components that are used to compose and build systems and applications.&quot; -- IBM CBOM documentation, on why an inventory is the hard part [@ibm-cbom]
&lt;p&gt;&lt;strong&gt;Automation answered the scale problem, and revealed a deeper one.&lt;/strong&gt; CISA responded with a strategy for Automated Cryptography Discovery and Inventory tools, describing their purpose as &quot;the use of ACDI tools to support a FCEB agency in its creation of an inventory of its information systems and assets that contain CRQC-vulnerable cryptography,&quot; where &quot;the inventory tools automate the collection of the cryptographic characteristics required for the inventory&quot; [@cisa-acdi]. NIST&apos;s National Cybersecurity Center of Excellence supplied a reference architecture in the SP 1800-38 practice guide, which remains a preliminary draft rather than a finalized standard [@sp1800-38-guide].&lt;/p&gt;
&lt;p&gt;Automation gave the see half the scale a spreadsheet never had. But it exposed a subtler gap: a scanner emits a &lt;em&gt;pile of tool-specific findings&lt;/em&gt;, not a queryable inventory. &quot;Component X contains AES&quot; carries no distinction between the algorithm family and the specific variant, and no dependency structure connecting the library that implements an algorithm to the application that uses it. Automation delivered scale without a data model.&lt;/p&gt;

CISA&apos;s term for tools that automatically enumerate an organization&apos;s cryptographically relevant, quantum-vulnerable assets across its systems, collecting &quot;the cryptographic characteristics required for the inventory&quot; rather than relying on manual audits [@cisa-acdi]. ACDI supplies the scale a manual inventory lacks -- but on its own it produces findings, not a structured, prioritizable model.
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Key idea:&lt;/strong&gt; Post-quantum migration is two verbs, not one: ROTATE, the design-time discipline of being able to change your cryptography, and SEE, the run-time practice of knowing where it all lives. The field perfected the rotate half over thirty years -- rigidity to negotiation to RFC 7696 -- and only closed the see half under a federal deadline. You cannot rotate what you cannot see.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;The two lineages, and their eventual meeting point, look like this when you draw them on one page.&lt;/p&gt;

flowchart TD
    subgraph ROT[&quot;ROTATE lane -- design-time agility&quot;]
      R1[Hardcoded rigidity] --&amp;gt; R2[Cipher-suite negotiation]
      R2 --&amp;gt; R3[RFC 7696 discipline]
      R3 --&amp;gt; R4[NIST CSWP 39 risk guidance]
    end
    subgraph SEE[&quot;SEE lane -- run-time inventory&quot;]
      G1[Manual spreadsheet] --&amp;gt; G2[Federal mandate NSM-10 and M-23-02]
      G2 --&amp;gt; G3[Automated discovery ACDI]
    end
    R4 --&amp;gt; CBOM[&quot;CycloneDX CBOM, crypto as a first-class asset&quot;]
    G3 --&amp;gt; CBOM
    CBOM --&amp;gt; EO[&quot;Executive Order 14412 makes the stack binding&quot;]
&lt;p&gt;The condensed history of both lanes fits in one table.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Generation&lt;/th&gt;
&lt;th&gt;Era&lt;/th&gt;
&lt;th&gt;Key idea&lt;/th&gt;
&lt;th&gt;Why it was superseded, or its limit&lt;/th&gt;
&lt;th&gt;Status&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;&lt;tr&gt;
&lt;td&gt;1. Hardcoded rigidity&lt;/td&gt;
&lt;td&gt;pre-2000s&lt;/td&gt;
&lt;td&gt;One primitive baked in, no wire identifier&lt;/td&gt;
&lt;td&gt;Every break forced an estate-wide re-architecture&lt;/td&gt;
&lt;td&gt;Obsolete&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;2. Cipher-suite negotiation&lt;/td&gt;
&lt;td&gt;1990s-2010s&lt;/td&gt;
&lt;td&gt;Algorithm or suite identifiers, IANA registry, negotiate&lt;/td&gt;
&lt;td&gt;Downgrade attacks and ossification; selects but cannot see or remove&lt;/td&gt;
&lt;td&gt;Necessary, insufficient&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;3. Agility as discipline (RFC 7696)&lt;/td&gt;
&lt;td&gt;2015&lt;/td&gt;
&lt;td&gt;Registered IDs, MTI in a companion doc, protected negotiation&lt;/td&gt;
&lt;td&gt;Design-time and forward-looking only; blind to deployed crypto&lt;/td&gt;
&lt;td&gt;Current (rotate half)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;4. Manual inventory under mandate&lt;/td&gt;
&lt;td&gt;2022 (NSM-10 / M-23-02)&lt;/td&gt;
&lt;td&gt;Order a prioritized cryptographic inventory&lt;/td&gt;
&lt;td&gt;Spreadsheet does not scale, stale, not machine-actionable&lt;/td&gt;
&lt;td&gt;Superseded by automation&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;5. Automated discovery (ACDI)&lt;/td&gt;
&lt;td&gt;2022-2025&lt;/td&gt;
&lt;td&gt;Tools auto-collect cryptographic characteristics&lt;/td&gt;
&lt;td&gt;A pile of tool-specific findings, no shared data model&lt;/td&gt;
&lt;td&gt;Current (scale)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;6. CBOM substrate&lt;/td&gt;
&lt;td&gt;2024 (CycloneDX 1.6)&lt;/td&gt;
&lt;td&gt;Model crypto as a first-class asset with dependencies&lt;/td&gt;
&lt;td&gt;Only as complete as the scanners that populate it&lt;/td&gt;
&lt;td&gt;Current (see half)&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;&lt;/table&gt;

The deadlines in this article are precise about scope, and it matters. Executive Order 14412 requires *federal agencies* to transition their high-value assets and high-impact systems -- explicitly excluding National Security Systems -- to post-quantum key establishment by December 31, 2030 and to post-quantum digital signatures by December 31, 2031 [@eo14412]. A companion Federal Acquisition Regulation rule pushes covered federal contractors toward compliance by December 31, 2030 [@eo14412]. Critical infrastructure operators are *encouraged*, not mandated. That National Security Systems exclusion is a hand-off, not a gap: NSA&apos;s Commercial National Security Algorithm Suite 2.0 (CNSA 2.0, September 2022) already owns that estate, mandating the same NIST winners -- ML-KEM and ML-DSA -- on its own use-case-staggered schedule, to be complete by 2035 in line with NSM-10, the memorandum that set the whole government-wide posture [@cnsa2] [@nsm10]. The civilian and national-security tracks are two branches of one 2022 origin. And one more distinction worth burning in: EO 14412 (&quot;Securing the Nation Against Advanced Cryptographic Attacks&quot;) is not EO 14413, a separate order about quantum innovation published in the same Federal Register issue [@eo14412]. Do not cite one for the other.
&lt;p&gt;Design-time agility was, by 2024, a solved discipline. Run-time inventory finally had scale, but no shape. The missing piece was never another scanner. It was a way to model cryptography &lt;em&gt;itself&lt;/em&gt; as an asset you could query, prioritize, and pass down a supply chain. That piece arrived on April 9, 2024.&lt;/p&gt;
&lt;h2&gt;5. The Breakthrough: Cryptography as a First-Class Asset&lt;/h2&gt;
&lt;p&gt;The breakthrough was not a better scanner. It was a decision to model cryptography the way the software supply chain already models its components -- as inventoried assets with dependencies you can query. To see why that is a genuine shift and not a rebranding, ask what a raw scan finding is missing. What does &quot;component X contains AES&quot; need to carry before it becomes something you can actually act on?&lt;/p&gt;
&lt;p&gt;On April 9, 2024, that question got an answer with a standard behind it. IBM Research&apos;s Cryptography Bill of Materials was upstreamed into OWASP CycloneDX v1.6 [@owasp-cdx16]. CBOM was carried into the current CycloneDX v1.7 (October 2025), published as the Ecma International standard ECMA-424, which extended the cryptography model further [@cdx-spec-17]. The design choice that matters most is the quietest one: a CBOM is an &lt;em&gt;extension of the same CycloneDX BOM document&lt;/em&gt;, not a separate schema [@ibm-cbom]. Your cryptographic inventory can live in the same file as your software inventory, produced by the same tools, consumed by the same pipelines. CBOM did not invent a parallel supply chain. It taught the existing one to describe cryptography.&lt;/p&gt;
&lt;p&gt;Its design answers four specific ways a raw finding falls short [@ibm-cbom]. First, it models the &lt;em&gt;asset types&lt;/em&gt; that matter -- algorithms, protocols, certificates, and &quot;related crypto material like keys, tokens, secrets or passwords.&quot; Second, it captures the property that makes a finding actionable: the difference between a family and a variant. As the CBOM documentation puts it, &quot;it makes a difference if one knows the algorithm family (e.g. AES) or the specific variant ... (e.g. AES-128-GCM) ... SHA1 vs. HMAC-SHA1 also makes a difference&quot; [@ibm-cbom]. A report of &quot;AES&quot; is not actionable. &quot;AES-128-GCM at file X, line 51&quot; is.&lt;/p&gt;

An extension of the CycloneDX BOM document that models an organization&apos;s cryptographic assets -- algorithms, protocols, certificates, and related key material -- together with their properties and the dependencies among them [@ibm-cbom]. At the field level, a crypto-asset is a component of type `cryptographic-asset` carrying `cryptoProperties` (whose `assetType` is one of algorithm, certificate, protocol, or related-crypto-material) and `evidence.occurrences` recording where it was found [@cdx-cbom-cap] [@cdx-cbom-guide]. It is the first open standard purpose-built to describe cryptography as an inventoried, dependency-aware asset.
&lt;p&gt;The third design goal is the one that turns a list into a graph. CBOM &quot;differentiates between &apos;implements&apos; and &apos;uses&apos; dependencies ... (e.g. TLS 1.3 uses ECDH/secp256r1)&quot; [@ibm-cbom]. A library &lt;em&gt;implements&lt;/em&gt; an algorithm; an application &lt;em&gt;uses&lt;/em&gt; it. That single distinction is the edge type that lets you answer the question the whole migration turns on: which applications transitively depend on a quantum-vulnerable primitive? Fourth and finally, the model applies uniformly across applications, libraries, firmware, and files, so the same representation describes source code, a shipped container, and an embedded device.&lt;/p&gt;

CBOM&apos;s two crypto-asset relationship types. A component *implements* a cryptographic asset when it provides the algorithm (a library implements ECDH/secp256r1); a component *uses* an asset when it consumes it (TLS 1.3 uses ECDH/secp256r1, and an application uses TLS 1.3) [@ibm-cbom]. Distinguishing the two turns a flat inventory into a directed graph -- and makes &quot;which applications are exposed to this weak primitive?&quot; a graph traversal rather than a guess.
&lt;p&gt;Model each crypto-asset with &lt;code&gt;cryptoProperties&lt;/code&gt; and connect them with &lt;code&gt;implements&lt;/code&gt; and &lt;code&gt;uses&lt;/code&gt; edges, and the inventory stops being a list and becomes a directed graph. The CycloneDX capability documentation describes exactly this: the format &quot;enables detailed representation of cryptographic assets within a system,&quot; including &quot;algorithms, keys, certificates, and their relationships to software components&quot; [@cdx-cbom-cap]. On a graph, prioritization is a traversal -- and a traversal over $V$ assets and $E$ dependencies costs $O(V + E)$, cheap enough to run over an entire estate.&lt;/p&gt;

flowchart TD
    APP[&quot;Application (payments-api)&quot;] --&amp;gt;|uses| TLS[&quot;TLS 1.3&quot;]
    TLS --&amp;gt;|uses| ECDH[&quot;ECDH secp256r1, quantum-vulnerable&quot;]
    LIB[&quot;Library (openssl)&quot;] --&amp;gt;|implements| ECDH
    LIB --&amp;gt;|implements| AES[&quot;AES-128-GCM&quot;]
&lt;p&gt;The graph reads directly. The application &lt;code&gt;payments-api&lt;/code&gt; uses TLS 1.3, which uses ECDH over secp256r1 -- a key-exchange primitive Shor&apos;s algorithm defeats. Follow the &lt;code&gt;uses&lt;/code&gt; edges and the exposure is explicit: this application is on the 2030 list. The &lt;code&gt;implements&lt;/code&gt; edges tell you where to fix it: &lt;code&gt;openssl&lt;/code&gt; provides that primitive, so the remediation targets that library. The same two edge types that describe the estate also route the work.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;CBOM concept&lt;/th&gt;
&lt;th&gt;What it captures&lt;/th&gt;
&lt;th&gt;Example&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;&lt;tr&gt;
&lt;td&gt;&lt;code&gt;assetType: algorithm&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;A cryptographic algorithm or primitive&lt;/td&gt;
&lt;td&gt;ML-KEM, RSA-2048, ECDH/secp256r1, AES-128-GCM&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;assetType: certificate&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;An X.509 certificate as an inventoried asset&lt;/td&gt;
&lt;td&gt;A TLS server certificate expiring in 2029&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;assetType: protocol&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;A protocol that consumes cryptography&lt;/td&gt;
&lt;td&gt;TLS 1.3, SSH, IKEv2&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;assetType: related-crypto-material&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;Keys, tokens, secrets, passwords&lt;/td&gt;
&lt;td&gt;A stored private key or API token&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Family vs variant&lt;/td&gt;
&lt;td&gt;The property that makes a finding actionable&lt;/td&gt;
&lt;td&gt;AES vs AES-128-GCM; SHA-1 vs HMAC-SHA1&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;implements&lt;/code&gt; edge&lt;/td&gt;
&lt;td&gt;A library provides an algorithm&lt;/td&gt;
&lt;td&gt;&lt;code&gt;openssl&lt;/code&gt; implements ECDH/secp256r1&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;uses&lt;/code&gt; edge&lt;/td&gt;
&lt;td&gt;An application or protocol consumes an algorithm&lt;/td&gt;
&lt;td&gt;TLS 1.3 uses ECDH/secp256r1&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;evidence.occurrences&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;Where the asset was actually found&lt;/td&gt;
&lt;td&gt;File path and line number&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;&lt;/table&gt;
&lt;p&gt;Here is the traversal made concrete. The snippet below parses a miniature CBOM and walks its &lt;code&gt;uses&lt;/code&gt; edges to flag every application transitively exposed to a quantum-vulnerable primitive.&lt;/p&gt;
&lt;p&gt;{`
// Pedagogical, not production -- use a vetted tool such as CBOMkit.
// A tiny CycloneDX-style CBOM: crypto-assets plus implements/uses edges.
const cbom = {
  components: [
    { ref: &quot;app:payments-api&quot;, type: &quot;application&quot; },
    { ref: &quot;proto:tls-1.3&quot;, type: &quot;cryptographic-asset&quot;, assetType: &quot;protocol&quot; },
    { ref: &quot;alg:ecdh-secp256r1&quot;, type: &quot;cryptographic-asset&quot;, assetType: &quot;algorithm&quot;, quantumVulnerable: true },
    { ref: &quot;alg:aes-128-gcm&quot;, type: &quot;cryptographic-asset&quot;, assetType: &quot;algorithm&quot;, quantumVulnerable: false },
    { ref: &quot;lib:openssl&quot;, type: &quot;library&quot; }
  ],
  dependencies: [
    { ref: &quot;app:payments-api&quot;, dependsOn: [&quot;proto:tls-1.3&quot;], kind: &quot;uses&quot; },
    { ref: &quot;proto:tls-1.3&quot;, dependsOn: [&quot;alg:ecdh-secp256r1&quot;], kind: &quot;uses&quot; },
    { ref: &quot;lib:openssl&quot;, dependsOn: [&quot;alg:ecdh-secp256r1&quot;, &quot;alg:aes-128-gcm&quot;], kind: &quot;implements&quot; }
  ]
};&lt;/p&gt;
&lt;p&gt;// Adjacency map built from the &quot;uses&quot; edges only.
const usesEdges = {};
for (const d of cbom.dependencies) {
  if (d.kind === &quot;uses&quot;) usesEdges[d.ref] = d.dependsOn;
}
const vulnerable = new Set(
  cbom.components.filter(c =&amp;gt; c.quantumVulnerable).map(c =&amp;gt; c.ref)
);&lt;/p&gt;
&lt;p&gt;// Depth-first: does this component transitively use a vulnerable primitive?
function reachesVulnerable(ref, seen) {
  seen = seen || new Set();
  if (seen.has(ref)) return false;
  seen.add(ref);
  for (const next of (usesEdges[ref] || [])) {
    if (vulnerable.has(next) || reachesVulnerable(next, seen)) return true;
  }
  return false;
}&lt;/p&gt;
&lt;p&gt;const apps = cbom.components.filter(c =&amp;gt; c.type === &quot;application&quot;);
for (const app of apps) {
  const verdict = reachesVulnerable(app.ref) ? &quot;EXPOSED&quot; : &quot;clear&quot;;
  console.log(app.ref + &quot;  -&amp;gt;  &quot; + verdict);
}
`}&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Key idea:&lt;/strong&gt; CBOM&apos;s breakthrough is not discovery power -- it is a data model. Model each crypto-asset with the property that makes it actionable (family versus variant) and its &lt;code&gt;implements&lt;/code&gt; and &lt;code&gt;uses&lt;/code&gt; dependencies, and a pile of tool-specific scan findings becomes a prioritizable graph you can query with a single traversal.&lt;/p&gt;
&lt;/blockquote&gt;

&quot;CBOM is the first open standard to describe an organizations&apos; cryptographic assets inventory, and their dependencies.&quot; -- Michael Osborne, CTO, IBM Quantum Safe [@owasp-cdx16]
&lt;p&gt;One caution keeps this honest, and a later section pays it off in full. A CBOM is a data model, not a discovery method. It is only ever as complete as the scanners that populate it [@ibm-cbomkit-blog]. Modeling cryptography as a graph is necessary, and it does not make the cryptography any easier to find.CycloneDX v1.6 shipped Attestations (CDXA) alongside CBOM -- machine-readable &quot;attestations to the veracity and completeness of those claims&quot; [@owasp-cdx16]. That plumbing is what the open problem of &lt;em&gt;completeness attestation&lt;/em&gt;, discussed later, is built on: a way to state not just what you found, but how thoroughly you looked.&lt;/p&gt;
&lt;p&gt;With cryptography finally modeled as a queryable, prioritizable graph, the remaining pieces could be assembled into a real pipeline: discipline at design time, discovery across every surface, roll-up into a CBOM, and prioritization against a deadline. By 2026, that pipeline has a definite shape.&lt;/p&gt;
&lt;h2&gt;6. The Discovery-to-Migration Stack (2026)&lt;/h2&gt;
&lt;p&gt;The state of the art in 2026 is not a product. It is a layered pipeline, and its governing rule is that no single layer is complete. Read from the top, it takes a legacy estate and produces a prioritized, deadline-aware migration plan.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;The design-time layer is crypto-agility as discipline.&lt;/strong&gt; RFC 7696 did not stay an IETF document. In December 2025, NIST published Cybersecurity White Paper 39, &quot;Considerations for Achieving Cryptographic Agility: Strategies and Practices&quot; (updated as CSWP 39-upd1 in June 2026), restating algorithm agility as national risk-management guidance [@cswp39]. The author list closes a thirty-year loop: Russ Housley, who wrote RFC 7696, appears alongside the leaders of NIST&apos;s post-quantum standardization such as Dustin Moody and Lily Chen, and William Newhouse, who leads the NCCoE inventory work [@cswp39].&lt;/p&gt;
&lt;p&gt;The people who standardized the new algorithms, the person who formalized agility, and the person building the inventory practice signed the same page. Agility sits at the top of the stack because it is what makes the eventual swap cheap.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;The discovery layer is five surfaces, and each is blind exactly where another sees clearly.&lt;/strong&gt; This is the heart of the see half, and the reason the outputs must be merged rather than chosen among.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;em&gt;Static source analysis&lt;/em&gt; reads owned source code and reports cryptographic calls with file-and-line precision. CBOMkit-Hyperion and its Sonar Cryptography plugin do this today, generating a CBOM directly from source and covering Java&apos;s JCA and Python&apos;s pyca/cryptography libraries [@sonar-crypto] [@ibm-cbomkit-blog]. It is precise and cheap in continuous integration -- and blind to third-party binaries it cannot see the source of, and to algorithms selected through dynamically constructed names.&lt;/li&gt;
&lt;li&gt;&lt;em&gt;Binary and container analysis&lt;/em&gt; reaches what static analysis cannot: shipped binaries, container images, and firmware. CBOMkit-Theia scans these artifacts [@cbomkit]. It reaches code you did not build -- and is defeated by packing and obfuscation, which can make cryptographic code indistinguishable from anything else.&lt;/li&gt;
&lt;li&gt;&lt;em&gt;Passive network monitoring&lt;/em&gt; observes the algorithms actually negotiated on live links, giving ground-truth on what is really in use. It is blind to data at rest and to systems that are simply idle during the capture window.&lt;/li&gt;
&lt;li&gt;&lt;em&gt;Active probing&lt;/em&gt; connects to listening services and enumerates the algorithms they will agree to negotiate, producing a capability census. It reaches only services that are listening, and says nothing about internal batch jobs or stored data.&lt;/li&gt;
&lt;li&gt;&lt;em&gt;Certificate and key-store analysis&lt;/em&gt; is the most mature surface and feeds the 2031 signature deadline most directly, but it sees only the public-key infrastructure: certificates, keys, and signature algorithms, not the code or protocols around them.&lt;/li&gt;
&lt;/ul&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Note:&lt;/strong&gt; No single surface is complete, so the operational rule is to run several and merge them, then budget a permanent manual-validation pass over the residual. This is not a workaround; it is what CISA&apos;s ACDI strategy and NIST&apos;s SP 1800-38 practice guide prescribe -- a method mix feeding a human-checked inventory, never one tool trusted to see everything [@cisa-acdi] [@sp1800-38-guide].&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;The five surfaces do not rank; they tile. Draw them feeding one merge-and-validate step, and the architecture is clear.&lt;/p&gt;

flowchart TD
    SRC[Static source scan] --&amp;gt; MERGE
    BIN[Binary and container scan] --&amp;gt; MERGE
    NET[Passive network sensor] --&amp;gt; MERGE
    PROBE[Active probing census] --&amp;gt; MERGE
    CERT[Certificate and key-store scan] --&amp;gt; MERGE
    MERGE[Merge and manual validation] --&amp;gt; CBOM[CycloneDX CBOM]
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Discovery surface&lt;/th&gt;
&lt;th&gt;What it sees&lt;/th&gt;
&lt;th&gt;Scaling&lt;/th&gt;
&lt;th&gt;Primary blind spot&lt;/th&gt;
&lt;th&gt;Best suited for&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;&lt;tr&gt;
&lt;td&gt;Static source&lt;/td&gt;
&lt;td&gt;Crypto calls in owned source, with file and line&lt;/td&gt;
&lt;td&gt;High, runs in CI&lt;/td&gt;
&lt;td&gt;Third-party binaries, dynamic names&lt;/td&gt;
&lt;td&gt;Owned codebases&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Binary / container&lt;/td&gt;
&lt;td&gt;Crypto in shipped binaries, containers, firmware&lt;/td&gt;
&lt;td&gt;Medium&lt;/td&gt;
&lt;td&gt;Packing and obfuscation&lt;/td&gt;
&lt;td&gt;Third-party and embedded artifacts&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Passive network&lt;/td&gt;
&lt;td&gt;Algorithms actually negotiated on the wire&lt;/td&gt;
&lt;td&gt;High&lt;/td&gt;
&lt;td&gt;Data at rest, idle systems&lt;/td&gt;
&lt;td&gt;Live ground-truth&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Active probing&lt;/td&gt;
&lt;td&gt;Capabilities of listening services&lt;/td&gt;
&lt;td&gt;Medium&lt;/td&gt;
&lt;td&gt;Non-listening and internal-only services&lt;/td&gt;
&lt;td&gt;External posture census&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Certificate / key-store&lt;/td&gt;
&lt;td&gt;Certificates, keys, signature algorithms&lt;/td&gt;
&lt;td&gt;High&lt;/td&gt;
&lt;td&gt;Anything outside the PKI&lt;/td&gt;
&lt;td&gt;The 2031 signature deadline&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;&lt;/table&gt;
&lt;p&gt;The table names each surface&apos;s blind spot. Understanding &lt;em&gt;why&lt;/em&gt; those blind spots exist -- and why they are not gaps a future release will quietly close -- means looking at how a scanner actually finds cryptography, because on the two hardest surfaces the detection mechanism and the blind spot turn out to be one fact seen from two sides.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Static source analysis lifts a library call to a normalized identity and its OID.&lt;/strong&gt; A source scanner does not understand cryptography; it recognizes calls into catalogued cryptographic-library APIs and resolves each to a canonical algorithm.&lt;/p&gt;
&lt;p&gt;CBOMkit-Hyperion and its Sonar Cryptography plugin walk the parsed syntax tree, spot a call into a known provider API -- Java&apos;s &lt;code&gt;MessageDigest.getInstance(&quot;SHA-256&quot;)&lt;/code&gt;, or a &lt;code&gt;pyca/cryptography&lt;/code&gt; constructor -- and map it to the algorithm, its variant, and its object identifier, the dotted-decimal name the registries use [@sonar-crypto] [@ibm-cbomkit-blog]. &lt;code&gt;SHA-256&lt;/code&gt; normalizes to the OID &lt;code&gt;2.16.840.1.101.3.4.2.1&lt;/code&gt;, in the NIST Computer Security Objects Register arc [@oidref-sha256].The SHA-256 OID &lt;code&gt;2.16.840.1.101.3.4.2.1&lt;/code&gt; is the machine-mergeable identity a static scanner lifts an API call to: two tools that print &quot;SHA-256&quot; and &quot;SHA256&quot; collapse to one crypto-asset the moment both resolve to it [@oidref-sha256].&lt;/p&gt;

A globally unique, dotted-decimal name for an algorithm or other object, assigned under a registration hierarchy. SHA-256 is `2.16.840.1.101.3.4.2.1` in the NIST Computer Security Objects Register arc [@oidref-sha256]. A static scanner resolves a recognized API call to its OID, and because two tools that spell an algorithm differently agree the instant both resolve to the same OID, the OID is the machine-mergeable identity the CBOM roll-up is built on.
&lt;p&gt;The OID is what lets two tools&apos; findings merge into one graph, and it also fixes the surface&apos;s exact reach. Recognition runs against a fixed catalog of call patterns -- a decidable restriction -- so an algorithm name assembled at runtime, a call made through reflection, a language the ruleset does not cover, or a hand-rolled primitive presents no catalogued API to match and is simply never seen. The precision of static analysis and its blindness to dynamic names are the same design decision.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Binary and container analysis recovers a primitive with no symbols at all, from constants and from behavior.&lt;/strong&gt; A stripped artifact still exposes two things a detector can key on. The first is its constants: block ciphers and hashes embed fixed, algorithm-specific tables -- an AES S-box, SHA round-constant tables, DES permutation tables -- and matching those known tables names the primitive with no function symbol present, the structural technique of Gröbert, Willems, and Holz in their 2011 RAID paper [@grobert-raid2011].&lt;/p&gt;
&lt;p&gt;The second is its behavior: where the constants are absent or rewritten, the detector runs the code and tests the output for cryptographic signatures -- high Shannon entropy, and the avalanche effect, in which flipping one input bit flips roughly half the output bits, a property real ciphers have and ordinary arithmetic does not. Later work such as Hill and Bellekens&apos; CryptoKnight names the same problem of recognizing primitives in compiled code [@hill-bellekens].&lt;/p&gt;
&lt;p&gt;This mechanism is exactly why packing is a blind spot rather than a bug to be patched. Packing or white-box obfuscation removes or rewrites the very constant tables the structural matcher depends on, and can make an implementation indistinguishable by construction from non-cryptographic code -- the worst-case form of a limit the section after next proves is fundamental.&lt;/p&gt;
&lt;p&gt;The behavioral fallback then meets a coverage wall: it can only judge the paths it actually executes, so cryptography on an unexecuted branch stays dark. The blind spot is not a defect in the tool; it is the shadow the detection mechanism casts.&lt;/p&gt;

flowchart LR
    subgraph STATIC[&quot;Static source lane&quot;]
      A1[&quot;Recognize catalogued library API call&quot;] --&amp;gt; A2[&quot;Resolve to algorithm and variant&quot;]
      A2 --&amp;gt; A3[&quot;Look up object identifier, the OID&quot;]
    end
    subgraph BINARY[&quot;Binary lane, no symbols&quot;]
      B1[&quot;Match S-box and round-constant tables&quot;] --&amp;gt; B3[&quot;Name the primitive&quot;]
      B2[&quot;Run it, measure entropy and avalanche&quot;] --&amp;gt; B3
    end
    A3 --&amp;gt; OID[&quot;Crypto-asset keyed by OID&quot;]
    B3 --&amp;gt; OID
    OID --&amp;gt; NODE[&quot;Mergeable CBOM node&quot;]
&lt;p&gt;Both lanes converge on the same object: a crypto-asset named by its OID, ready to merge with every other tool&apos;s findings. That shared identity is what makes the next layer possible.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;The substrate layer rolls every surface up into a CycloneDX CBOM&lt;/strong&gt; -- the graph from the previous section, now populated from five directions. (SPDX 3.0 is the parallel choice, and the next section weighs it.)&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;The prioritization layer turns the graph into a ranked queue using Mosca&apos;s inequality.&lt;/strong&gt; You cannot migrate everything at once, so you order the work by exposure.&lt;/p&gt;

A triage rule attributed to Michele Mosca (IACR ePrint 2015/1075): begin migrating a system *now* if $x + y &amp;gt; z$, where $x$ is how long the data must stay confidential, $y$ is how long the migration will take, and $z$ is the time until a cryptographically relevant quantum computer exists [@mosca-eprint]. When the exposure window $x + y$ exceeds the time to a CRQC, harvest-now-decrypt-later already threatens that data, so waiting is a loss [@gri-mosca].
&lt;p&gt;Applied over the CBOM graph, Mosca&apos;s inequality converts an inventory into a sorted migration queue, and it maps cleanly onto the executive order&apos;s split: confidentiality and key establishment, where $x$ can be decades, come due in 2030, while signatures, which cannot be forged retroactively, come due in 2031 [@eo14412]. The decision, per asset, looks like this.&lt;/p&gt;

flowchart TD
    X[Data shelf-life x] --&amp;gt; SUM[&quot;Exposure window x + y&quot;]
    Y[Migration time y] --&amp;gt; SUM
    Z[Time to a CRQC z] --&amp;gt; D
    SUM --&amp;gt; D{&quot;x + y exceeds z?&quot;}
    D --&amp;gt;|yes| NOW[Migrate now, harvest-now-decrypt-later already applies]
    D --&amp;gt;|no| DEFER[Defer, but keep monitoring z]
&lt;p&gt;The same rule expressed as code sorts a real inventory by how little slack it has left.&lt;/p&gt;
&lt;p&gt;{`
// Pedagogical, not production. Mosca&apos;s inequality: migrate now when x + y &amp;gt; z.
const yearsToCRQC = 12; // z: uncertain estimate of time to a capable quantum computer.
const assets = [
  { name: &quot;root-CA-signing&quot;, shelfLifeYears: 20, migrationYears: 3 },
  { name: &quot;payments-TLS&quot;,    shelfLifeYears: 10, migrationYears: 2 },
  { name: &quot;internal-metrics&quot;, shelfLifeYears: 1, migrationYears: 1 },
  { name: &quot;archival-backups&quot;, shelfLifeYears: 25, migrationYears: 4 }
];&lt;/p&gt;
&lt;p&gt;function triage(a) {
  const exposure = a.shelfLifeYears + a.migrationYears; // x + y
  return {
    name: a.name,
    exposure: exposure,
    slack: yearsToCRQC - exposure,          // negative slack means already exposed
    migrateNow: exposure &amp;gt; yearsToCRQC
  };
}&lt;/p&gt;
&lt;p&gt;const ranked = assets.map(triage).sort((p, q) =&amp;gt; p.slack - q.slack);
for (const r of ranked) {
  const flag = r.migrateNow ? &quot;MIGRATE NOW&quot; : &quot;monitor&quot;;
  console.log(r.name + &quot;  exposure=&quot; + r.exposure + &quot;y  slack=&quot; + r.slack + &quot;y  -&amp;gt; &quot; + flag);
}
`}&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;The binding-policy layer is what makes the stack mandatory rather than aspirational.&lt;/strong&gt; CISA&apos;s ACDI strategy defines the automated-discovery goal [@cisa-acdi]; NIST&apos;s SP 1800-38 practice guide, the deliverable of the NCCoE&apos;s Migration to Post-Quantum Cryptography project, supplies the reference architecture, as a preliminary draft [@sp1800-38-guide] [@sp1800-38-project]; and Executive Order 14412 attaches the dates and, within 270 days of signing, directs CISA to publish the &quot;minimum elements for a cryptographic bill of materials&quot; that &quot;enable the automated assessment of the cryptographic assets&quot; [@eo14412]. The policy layer literally names the substrate the rest of the stack produces.&lt;/p&gt;

NIST NCCoE&apos;s &quot;Migration to Post-Quantum Cryptography&quot; practice guide -- whose Volume B is the cryptographic-discovery volume -- is an initial public *preliminary draft*, and its own title page says so [@sp1800-38-guide] [@sp1800-38b-pdf]. Cite it for its discovery reference architecture, which is genuinely useful, but never as a finalized, normative NIST standard. Treating a draft as a final spec is one of the recurring errors in this space.
&lt;p&gt;This stack works, up to a point. &quot;Run every surface and roll it up&quot; quietly assumes the surfaces can, together, see everything. They cannot, and no substrate choice changes that. Before confronting that ceiling, though, there is an honest comparison to make: CBOM is not the only way to inventory cryptography.&lt;/p&gt;
&lt;h2&gt;7. CBOM Is Not the Only Way to Inventory Cryptography&lt;/h2&gt;
&lt;p&gt;A claim that CBOM is &lt;em&gt;the&lt;/em&gt; substrate has to survive its rivals. There are three real axes of competition, and on each, the honest answer is &quot;it depends.&quot; Steelmanning the alternatives is not a detour from the thesis; it is how the thesis earns the word &quot;substrate.&quot;&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;The schema choice: CycloneDX CBOM versus SPDX 3.0.&lt;/strong&gt; SPDX is the other major machine-readable bill-of-materials standard, with an ISO/IEC 5962 lineage, and its 3.0 revision added a Security profile [@spdx-spec]. That profile is oriented toward vulnerability and VEX communication -- expressing whether a component is affected by a known vulnerability -- rather than toward modeling cryptographic assets in their own right [@spdx-security].VEX, the Vulnerability Exploitability eXchange, is a machine-readable statement about whether a given vulnerability actually affects a product. It answers &quot;are we exploitable?&quot;, which is a different question from &quot;what cryptography do we run?&quot; -- which is why an inventory built around VEX is a different tool from one built around crypto-assets. CBOM, by contrast, ships purpose-built &lt;code&gt;cryptographic-asset&lt;/code&gt; types and the &lt;code&gt;implements&lt;/code&gt; versus &lt;code&gt;uses&lt;/code&gt; edges that make the inventory a graph [@ibm-cbom].&lt;/p&gt;
&lt;p&gt;The practical read: if you are inventorying cryptography to prioritize a migration, CBOM is the crypto-native choice, and it is the artifact Executive Order 14412 names by title [@eo14412]. If your organization is already standardized on SPDX and VEX workflows, SPDX 3.0 can carry crypto information at a coarser grain and keep you on one toolchain. Both, importantly, live in the same document as your SBOM, so this is a modeling choice, not a parallel-infrastructure choice.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Dimension&lt;/th&gt;
&lt;th&gt;CycloneDX CBOM&lt;/th&gt;
&lt;th&gt;SPDX 3.0&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;&lt;tr&gt;
&lt;td&gt;Steward&lt;/td&gt;
&lt;td&gt;OWASP CycloneDX&lt;/td&gt;
&lt;td&gt;Linux Foundation / SPDX (ISO/IEC 5962 lineage)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Crypto-asset modeling&lt;/td&gt;
&lt;td&gt;Purpose-built &lt;code&gt;cryptographic-asset&lt;/code&gt; types&lt;/td&gt;
&lt;td&gt;Security profile, less crypto-specialized&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Dependency semantics&lt;/td&gt;
&lt;td&gt;&lt;code&gt;implements&lt;/code&gt; versus &lt;code&gt;uses&lt;/code&gt; edges&lt;/td&gt;
&lt;td&gt;General relationships, VEX-oriented&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Primary orientation&lt;/td&gt;
&lt;td&gt;Cryptographic inventory&lt;/td&gt;
&lt;td&gt;Vulnerability and VEX communication&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Executive Order 14412 alignment&lt;/td&gt;
&lt;td&gt;Named target artifact&lt;/td&gt;
&lt;td&gt;Not named&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;&lt;/table&gt;
&lt;p&gt;&lt;strong&gt;The tooling choice: open versus commercial.&lt;/strong&gt; The open reference implementation is CBOMkit, an IBM and Post-Quantum Cryptography Alliance suite whose modules cover source scanning (Hyperion), binary and container scanning (Theia), viewing (Coeus), compliance (Themis), and repository storage (Mnemosyne) [@cbomkit] [@ibm-cbomkit-blog]. Open tooling wins on transparency, on integrating into continuous integration, and on being the reference producer of the exact CBOM format the policy layer names.&lt;/p&gt;
&lt;p&gt;It struggles outside its rule set -- languages or libraries it does not yet recognize -- and on completeness when it lacks build context. CBOMkit&apos;s own documentation is candid about the second limit: scanning without a full build &quot;potentially reduces completeness and accuracy of the findings since some Java symbols may not be resolved&quot; [@cbomkit].&lt;/p&gt;
&lt;p&gt;The commercial alternative is the category of cryptographic-posture-management platforms: closed, multi-surface products that add correlation to business services and data flows. They win on breadth and on tying a raw finding to &quot;which revenue-bearing service is this?&quot; They cost money, keep their data models proprietary, and -- this is the part no budget fixes -- run into the exact same theoretical ceiling as the open tools.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Dimension&lt;/th&gt;
&lt;th&gt;Open (CBOMkit)&lt;/th&gt;
&lt;th&gt;Commercial cryptographic-posture management&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;&lt;tr&gt;
&lt;td&gt;Discovery surfaces&lt;/td&gt;
&lt;td&gt;Source, plus binary and container; extensible&lt;/td&gt;
&lt;td&gt;Multi-surface breadth out of the box&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Output format&lt;/td&gt;
&lt;td&gt;CycloneDX CBOM (the reference producer)&lt;/td&gt;
&lt;td&gt;Often proprietary, typically exports CBOM&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Correlation to business services&lt;/td&gt;
&lt;td&gt;Limited&lt;/td&gt;
&lt;td&gt;A primary selling point&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Cost&lt;/td&gt;
&lt;td&gt;Free and open&lt;/td&gt;
&lt;td&gt;Licensed&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Completeness ceiling&lt;/td&gt;
&lt;td&gt;Bounded by rule set and build context&lt;/td&gt;
&lt;td&gt;The same theoretical ceiling&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;&lt;/table&gt;
&lt;p&gt;&lt;strong&gt;The discovery-method choice&lt;/strong&gt; is the five surfaces from the previous section, and the honest summary bears repeating: each is genuinely strong somewhere and genuinely blind somewhere else, and none is complete alone. Static analysis owns your source; binary analysis owns your firmware; passive monitoring owns live traffic; probing owns external posture; certificate scanning owns the PKI. The right answer is never &quot;pick one.&quot; It is &quot;run several and merge.&quot;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Note:&lt;/strong&gt; There is no independent, peer-reviewed benchmark that ranks these schemas or tools by recall and precision on a shared corpus of real systems. The comparisons above are by design and coverage profile, not by measured performance numbers -- and any vendor deck that quotes a precise detection percentage is quoting itself. Treat coverage claims as architecture, not as evidence.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;Every one of these choices trades coverage for cost, or specialization for breadth, and not one of them escapes a deeper problem they all share. Whatever schema you standardize on and whatever tools you buy or build, there is a hard limit on how complete your inventory can ever be -- and, with unsettling symmetry, a second hard limit on how much of your cryptography you can rotate at all.&lt;/p&gt;
&lt;h2&gt;8. Two Ceilings the Hard Problem Cannot Lift&lt;/h2&gt;
&lt;p&gt;Here is the uncomfortable core of the whole subject -- the most important idea in this guide after the thesis itself. Complete visibility into your cryptography is not merely expensive. It is impossible. And so, separately, is complete agility. Each verb has its own independent, provable ceiling, and the two ceilings have different shapes. Ask the budget question directly: with unlimited money and every tool on the market, could you reach 100 percent? No -- and the reasons you cannot are not the same for the two halves.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;The SEE ceiling is undecidability.&lt;/strong&gt; The question at the center of discovery is not the tidy one it first appears. What a scanner must answer, for arbitrary deployed code, is &lt;em&gt;does this program use cryptographic primitive C somewhere inside it?&lt;/em&gt; -- think of a network daemon that happens to call AES while going about its ordinary work. That is the operative question, and it is provably unanswerable in general.&lt;/p&gt;
&lt;p&gt;So is its stricter cousin, &lt;em&gt;does this program compute C?&lt;/em&gt; -- is the program&apos;s entire input-output behavior the AES map itself? The two are undecidable for different reasons, and keeping them apart is the difference between a slogan and a proof.&lt;/p&gt;

Two distinct computability results cap automated discovery. Whether a program *computes* a given primitive -- whether its input-output function is, say, the AES map -- is a non-trivial semantic property of the function the program computes, so it is undecidable directly by Rice&apos;s theorem, which holds that every non-trivial property of the function a program computes is undecidable [@rice1953]. But the question discovery actually asks -- whether a program *uses* a primitive C internally while computing something else -- is not a property of the program&apos;s external function at all, because two programs with identical outputs can differ in whether they call C. Rice&apos;s theorem therefore does not apply directly; that case&apos;s undecidability follows instead from a reduction to the halting problem. Either way, no algorithm decides it for all programs.
&lt;p&gt;The applied cryptography-detection literature reaches the same wall from the practical side, and it supplies the third leg of the attribution. Gröbert, Willems, and Holz, in their 2011 RAID paper on identifying cryptographic primitives in binary programs, show that binary crypto detection is fundamentally best-effort, and that no detector defeats arbitrary obfuscation: sufficiently transformed code can be made indistinguishable from non-cryptographic code [@grobert-raid2011].&lt;/p&gt;
&lt;p&gt;Put the three arguments together -- Rice&apos;s theorem for &lt;em&gt;computes C&lt;/em&gt;, the halting-problem reduction for &lt;em&gt;uses C internally&lt;/em&gt;, and Gröbert for &lt;em&gt;survives obfuscation&lt;/em&gt; -- and the conclusion is firm: 100 percent automated cryptographic discovery is not achievable in the general case.The attribution is deliberately three-part. &lt;em&gt;Does P compute C?&lt;/em&gt; is undecidable by Rice&apos;s theorem [@rice1953]. The operative &lt;em&gt;does P use C internally?&lt;/em&gt; is a halting-problem reduction, not Rice, because it is not a property of P&apos;s external function. And &lt;em&gt;no detector defeats arbitrary obfuscation&lt;/em&gt; is Gröbert, Willems, and Holz at RAID 2011 [@grobert-raid2011]. Three different arguments, one conclusion. It is not a tooling gap that a better scanner will someday close. It is a computability limit.&lt;/p&gt;
&lt;p&gt;This is the rigorous reason automated discovery must always be paired with human validation, and it instantiates in every messy corner of a real estate -- obfuscated and packed binaries, hand-rolled cryptography, dynamically loaded modules, firmware and operational-technology devices with decade-long lifetimes, and third-party or SaaS systems you simply cannot reach to scan.&lt;/p&gt;

The regulator agrees, in writing. As reported by Nextgov, CISA&apos;s guidance states that the agency &quot;has not been able to confirm the full scope of cryptographic algorithm detection capabilities that will be available via automated cryptographic discovery tools,&quot; and that &quot;the inventory process requires both manual data collection and the use of automated support&quot; [@nextgov-cisa]. The body pushing hardest for automated discovery is explicit that automation alone will not get you to a complete inventory. Bounded coverage is not a vendor&apos;s excuse; it is the official operating assumption.
&lt;p&gt;&lt;strong&gt;The ROTATE ceiling is irreversibility.&lt;/strong&gt; Suppose, impossibly, you had perfect visibility. Some cryptography still cannot be rotated, because it was committed to the world in a form that cannot be recalled. RFC 7696 states the canonical case precisely: the digital signature on an intermediate certification authority certificate &quot;is often expected to last decades, which hinders the transition away from a weak signature algorithm,&quot; and once a long-lived certificate is issued under a given algorithm, relying parties &quot;cannot stop supporting it without invalidating all of the subordinate certificates&quot; [@rfc7696].&lt;/p&gt;
&lt;p&gt;The same irreversibility applies to every long-lived signature already emitted, to trust anchors and root stores embedded in devices, to firmware and hardware with parameters fixed at manufacture, and to protocols that shipped with no negotiation mechanism at all. These are not discovery failures. You can see them perfectly. The &lt;em&gt;rotate&lt;/em&gt; half is simply, structurally impossible for them after the fact.&lt;/p&gt;

flowchart TD
    PQM[Post-quantum migration] --&amp;gt; SEE[&quot;SEE, run-time inventory&quot;]
    PQM --&amp;gt; ROT[&quot;ROTATE, design-time agility&quot;]
    SEE --&amp;gt; U[&quot;Ceiling, undecidability (halting reduction, Rice&apos;s theorem, RAID 2011)&quot;]
    ROT --&amp;gt; I[&quot;Ceiling, irreversibility (RFC 7696 section 2.6)&quot;]
    U --&amp;gt; UEX[&quot;Obfuscated binaries, hand-rolled crypto, SaaS opacity&quot;]
    I --&amp;gt; IEX[&quot;Long-lived signatures, trust anchors, firmware&quot;]
&lt;p&gt;The undecidability ceiling is easy to feel with a five-line example. A naive static detector greps for a known cipher name. It catches the direct call and misses the identical algorithm the moment the name is assembled at runtime.&lt;/p&gt;
&lt;p&gt;{`
// Pedagogical illustration, not a proof and not production.
// A naive static detector: it scans source for a known cipher literal.
function naiveDetect(source) {
  const known = [&quot;aes-128-gcm&quot;, &quot;aes-256-gcm&quot;, &quot;chacha20-poly1305&quot;];
  return known.filter(name =&amp;gt; source.includes(&apos;&quot;&apos; + name + &apos;&quot;&apos;));
}&lt;/p&gt;
&lt;p&gt;// Case 1: the algorithm is named directly. The detector sees it.
const direct = &apos;const c = crypto.createCipheriv(&quot;aes-128-gcm&quot;, key, iv);&apos;;&lt;/p&gt;
&lt;p&gt;// Case 2: the SAME algorithm, selected through a name built at runtime.
const hidden = [
  &apos;const parts = [&quot;aes&quot;, &quot;128&quot;, &quot;gcm&quot;];&apos;,
  &apos;const alg = parts.join(&quot;-&quot;);&apos;,
  &apos;const c = crypto.createCipheriv(alg, key, iv);&apos;
].join(&quot; &quot;);&lt;/p&gt;
&lt;p&gt;console.log(&quot;direct  -&amp;gt;&quot;, naiveDetect(direct)); // [&quot;aes-128-gcm&quot;]  found
console.log(&quot;hidden  -&amp;gt;&quot;, naiveDetect(hidden)); // []              missed
`}&lt;/p&gt;
&lt;p&gt;A real scanner is far cleverer than this, and a determined obfuscator is far cleverer still. The demo is not a proof of undecidability -- it is a picture of why the problem is undecidable: any fixed detector can be evaded by a program that constructs its cryptography in a way the detector does not model.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Note:&lt;/strong&gt; A certificate scan is not a cryptographic inventory. Neither is a network scan. Each sees exactly one surface -- the PKI, or the wire -- and even the union of all five surfaces is provably bounded below complete coverage. Anyone who hands you a single-surface scan and calls it &quot;our crypto inventory&quot; has confused a slice for the whole.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;So the attainable optimum is not a complete inventory and never was. It is a high-coverage, multi-surface, human-validated approximation whose residual incompleteness is acknowledged rather than hidden.You can push coverage upward asymptotically by adding surfaces and manual review, but never to a &lt;em&gt;proven&lt;/em&gt; 100 percent. The mature deliverable is therefore bounded assurance -- a statement of how thoroughly you looked -- not a bare list that silently claims a completeness it cannot possibly guarantee. Coverage rises toward the ceiling; it never touches it.&lt;/p&gt;
&lt;p&gt;If completeness is provably out of reach, then the goal cannot be a bare list that claims a coverage it cannot back. It has to be &lt;em&gt;bounded assurance&lt;/em&gt;: a statement of which surfaces were scanned, with which tools, under which caveats. Building that -- along with everything else this young discipline has not finished -- is where the live research sits.&lt;/p&gt;
&lt;h2&gt;9. Where the Research and Standardization Are Still Live&lt;/h2&gt;
&lt;p&gt;The substrate exists and the deadline is fixed, but the discipline is young, and several load-bearing pieces are still under construction. The question that organizes the frontier is simple: what has to be solved before a CBOM can be trusted the way a mature SBOM is trusted today?&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Trustworthy attestation of completeness is the flagship open problem.&lt;/strong&gt; A CBOM asserts what a set of tools &lt;em&gt;found&lt;/em&gt;. Nothing in it attests to what they &lt;em&gt;missed&lt;/em&gt; -- and the previous section proved that what they miss can never be driven to zero. So a consumer of your CBOM needs something more honest than a list: &lt;em&gt;bounded assurance&lt;/em&gt;, a signed statement of how far the inventory was actually pushed.&lt;/p&gt;
&lt;p&gt;Concretely, a standard completeness-attestation profile would pin down four minimum elements: &lt;strong&gt;surface coverage&lt;/strong&gt; (which of the five discovery surfaces were actually run against this target, and which were not); &lt;strong&gt;tools and versions&lt;/strong&gt; (which discovery tools, at which versions and rule packs, since a surface&apos;s recall is bounded by the specific catalog it matches against); &lt;strong&gt;coverage and exclusion caveats&lt;/strong&gt; (unscanned repositories, un-executed binary paths, unsupported languages, unreachable air-gapped or SaaS systems, the scanned-without-build-context case); and &lt;strong&gt;residual manual-validation scope&lt;/strong&gt; (what a human reviewed, and what still awaits review).&lt;/p&gt;
&lt;p&gt;The striking part is that the plumbing to carry all four already ships. CycloneDX Attestations (CDXA) landed in the same v1.6 line as CBOM, providing machine-readable &quot;attestations to the veracity and completeness of those claims&quot; [@owasp-cdx16] [@cdx-attestations].&lt;/p&gt;
&lt;p&gt;Its object model maps onto the profile almost one-to-one: a top-level &lt;code&gt;declarations&lt;/code&gt; object whose &lt;code&gt;targets&lt;/code&gt; name the CBOM the claim is about; &lt;code&gt;claims&lt;/code&gt; that each carry a &lt;code&gt;predicate&lt;/code&gt; (for example, &quot;all five surfaces scanned for target T&quot;), its &lt;code&gt;reasoning&lt;/code&gt;, linked &lt;code&gt;evidence&lt;/code&gt;, and -- decisively -- &lt;code&gt;counterEvidence&lt;/code&gt;, the schema&apos;s native field for &lt;em&gt;what undercuts the claim&lt;/em&gt;, which is exactly where the blind spots the last section says can never be zero would be recorded; &lt;code&gt;evidence&lt;/code&gt; items with &lt;code&gt;created&lt;/code&gt; and &lt;code&gt;expires&lt;/code&gt; timestamps, which also give an inventory&apos;s assurance an explicit shelf-life; and &lt;code&gt;assessors&lt;/code&gt; carrying a &lt;code&gt;thirdParty&lt;/code&gt; boolean that separates self-assessment from an independent audit, the whole declaration closed with an &lt;code&gt;affirmation&lt;/code&gt; and an enveloped &lt;code&gt;signature&lt;/code&gt; [@cdx-16-json].CDXA already carries completeness claims: &lt;code&gt;claims.counterEvidence&lt;/code&gt; records what undercuts a claim, and &lt;code&gt;evidence.expires&lt;/code&gt; gives the assurance a shelf-life [@cdx-16-json]. So the gap is a missing standard &lt;em&gt;profile&lt;/em&gt; -- an agreed catalog of which claims a CBOM must assert -- not missing plumbing.&lt;/p&gt;
&lt;p&gt;So the gap is not missing machinery; it is a missing &lt;em&gt;standard profile&lt;/em&gt; -- an agreed, named set of claims a CBOM must assert to count as completeness-attested -- plus the absence of any shared, peer-reviewed benchmark against which a tool&apos;s recall and precision could be measured.The absence of a public discovery benchmark is why no honest vendor can quote you a real recall number. There is no shared corpus of representative systems with a known ground-truth inventory to measure against, so &quot;we detect 98 percent of cryptography&quot; is, at present, an unfalsifiable claim rather than a measured result.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Note:&lt;/strong&gt; The most consequential unsolved problem in cryptographic inventory is not building a more powerful scanner. It is being able to state, verifiably, how thorough a given inventory is. Bounded assurance -- an honest account of coverage and its gaps -- is worth more to a downstream consumer than a longer list that silently overclaims what it saw. Attestation is the direct answer to the undecidability ceiling.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;strong&gt;Four more problems are visibly in motion.&lt;/strong&gt; &lt;em&gt;Schema convergence:&lt;/em&gt; ACDI tools still emit tool-specific shapes, and CBOM and SPDX 3.0 coexist with no agreed crosswalk between their cryptographic representations [@ibm-cbom] [@spdx-spec]. A real crosswalk is not a field-rename -- it has to preserve crypto-asset identity, the family-versus-variant distinction, and the dependency semantics, so that CycloneDX&apos;s &lt;code&gt;provides&lt;/code&gt; and &lt;code&gt;dependsOn&lt;/code&gt; edges are not flattened into a mapping that collapses &quot;this library &lt;em&gt;contains&lt;/em&gt; X&quot; into &quot;this application &lt;em&gt;uses&lt;/em&gt; X&quot; [@cdx-16-json].&lt;/p&gt;
&lt;p&gt;&lt;em&gt;Continuous versus point-in-time inventory:&lt;/em&gt; a CBOM is stale the instant code ships, a certificate rotates, or traffic shifts; continuous inventory is practical for source and network surfaces and much harder for binary, firmware, and SaaS, so most inventories today are snapshots that begin aging immediately.&lt;/p&gt;
&lt;p&gt;&lt;em&gt;Correlation to business context:&lt;/em&gt; &quot;AES-128-GCM at file X, line 51&quot; does not tell you which service depends on it, which data it protects, or how long that data must stay secret -- yet that is precisely the input $x$ and the business priority that Mosca&apos;s inequality needs, so the gap between a technical finding and a risk decision is still bridged by humans.&lt;/p&gt;
&lt;p&gt;&lt;em&gt;Supply-chain propagation:&lt;/em&gt; most of an application&apos;s cryptography lives in its transitive dependencies, and while the data model supports composition -- via BOM-Link references between documents, enveloped signatures for provenance, and merge and de-duplication keyed on a stable identity such as OID plus package URL plus &lt;code&gt;bom-ref&lt;/code&gt; -- the practice of publishing, signing, and merging upstream CBOMs the way SBOMs are beginning to flow is still nascent [@cdx-16-json].&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;And one problem loops straight back to the theory.&lt;/strong&gt; Signature- and rule-based detectors recognize only cryptography they already have a rule for. Early post-quantum hybrids, experimental constructions, and hand-rolled primitives evade the catalog -- which is the undecidability ceiling of the previous section wearing everyday clothes [@grobert-raid2011]. Taken together, these open problems share a theme: the model for cryptography is settled, and the practices that make the model trustworthy, current, and composable are still being written.&lt;/p&gt;
&lt;p&gt;None of this is a reason to wait, because the deadline will not. The research frontier and the compliance clock run in parallel, which means the practitioner&apos;s job is not to wait for the discipline to mature. It is to build the best inventory achievable now, bound it honestly, and improve it continuously. Here is how to start this quarter.&lt;/p&gt;
&lt;h2&gt;10. Doing It This Quarter&lt;/h2&gt;
&lt;p&gt;Strip away the theory and the policy, and a concrete, deadline-aware workflow remains -- one any team on the 2030 hook can start now. Five steps, each tied to one of the two verbs.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Step 1 -- Build agility in (ROTATE, forward).&lt;/strong&gt; For everything you build from here on, apply the RFC 7696 patterns: put an indirection layer between your application and its cryptography, use registered algorithm identifiers, hardcode no primitives, and keep your mandatory-to-implement set in a companion configuration so it can change without a rebuild [@rfc7696]. Done well, the eventual post-quantum swap becomes a configuration change rather than a re-architecture. This step does not touch your legacy estate -- it stops that estate from growing.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Step 2 -- Run multi-surface discovery (SEE).&lt;/strong&gt; Not one tool. A mix, matched to the surfaces from earlier: a static scan of owned source in continuous integration with CBOMkit-Hyperion and its Sonar Cryptography plugin [@sonar-crypto] [@ibm-cbomkit-blog]; a binary and container scan with CBOMkit-Theia for third-party artifacts and firmware [@cbomkit]; passive network monitoring for live ground-truth; active probing for an external capability census; and certificate and key-store scanning first if you are triaging the 2031 signature deadline. Then budget a permanent manual-validation line item for the residual the tools cannot reach -- because, as established, that residual never reaches zero [@nextgov-cisa].&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Step 3 -- Emit a CBOM (SEE, substrate).&lt;/strong&gt; Roll the merged findings into a CycloneDX CBOM of the current line -- CBOM was introduced in v1.6 and carried into v1.7 -- validate it, and store it as an artifact right next to your SBOM [@owasp-cdx16] [@cdx-spec-17]. Version it over time so you can diff this quarter against last, and keep the history in a repository such as CBOMkit-Mnemosyne [@cbomkit].&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Step 4 -- Prioritize (SEE to decision).&lt;/strong&gt; Run Mosca&apos;s inequality over the graph. Rank by harvest-now-decrypt-later exposure and timing, $x + y &amp;gt; z$, and map the result onto the mandated dates: confidentiality and key establishment toward December 31, 2030, signatures toward December 31, 2031 [@gri-mosca] [@eo14412]. The output is a queue, not a wish list.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Step 5 -- Migrate to algorithms that already ship (ROTATE, execute).&lt;/strong&gt; The endpoints of the queue are the subject of the companion posts in this series: &lt;a href=&quot;https://paragmali.com/blog/the-thirty-year-migration-ships-in-a-pip-install-how-post-qu/&quot; rel=&quot;noopener&quot;&gt;ML-KEM arriving in a &lt;code&gt;pip install&lt;/code&gt;&lt;/a&gt;, &lt;a href=&quot;https://paragmali.com/blog/post-quantum-cryptography-on-windows-the-thirty-year-migrati/&quot; rel=&quot;noopener&quot;&gt;ML-KEM and ML-DSA in Windows SChannel and SymCrypt&lt;/a&gt;, and the &lt;a href=&quot;https://paragmali.com/blog/rotating-every-cipher-schannel-and-the-twenty-year-algorithm/&quot; rel=&quot;noopener&quot;&gt;twenty-year SChannel algorithm-agility story&lt;/a&gt; that shows the rotate half working at scale in one real TLS stack. The replacement primitives are finished and shipping -- FIPS 203, 204, and 205 since August 2024 [@fips203] [@pyca-changelog] [@ms-pqc-windows]. The entire stack above exists to produce the prioritized list those endpoints execute against.&lt;/p&gt;

flowchart TD
    A[Build agility into new code] --&amp;gt; B[Run multi-surface discovery]
    B --&amp;gt; C[Emit and validate a CycloneDX CBOM]
    C --&amp;gt; D{&quot;x + y exceeds z?&quot;}
    D --&amp;gt;|yes| E[Migrate now to shipping PQC algorithms]
    D --&amp;gt;|no| F[Queue and keep monitoring z]
    E --&amp;gt; G[Re-scan and version the CBOM]
    F --&amp;gt; G
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Step&lt;/th&gt;
&lt;th&gt;Method&lt;/th&gt;
&lt;th&gt;Effort&lt;/th&gt;
&lt;th&gt;Best suited for&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;&lt;tr&gt;
&lt;td&gt;Build agility in&lt;/td&gt;
&lt;td&gt;RFC 7696 patterns in new code&lt;/td&gt;
&lt;td&gt;Design-time, low ongoing&lt;/td&gt;
&lt;td&gt;Greenfield and active codebases&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Discover owned source&lt;/td&gt;
&lt;td&gt;Static scan in CI (Hyperion / Sonar)&lt;/td&gt;
&lt;td&gt;Low, continuous&lt;/td&gt;
&lt;td&gt;Code you wrote&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Discover third-party and firmware&lt;/td&gt;
&lt;td&gt;Binary and container scan (Theia)&lt;/td&gt;
&lt;td&gt;Medium&lt;/td&gt;
&lt;td&gt;Artifacts you did not build&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Discover live traffic&lt;/td&gt;
&lt;td&gt;Passive network plus active probing&lt;/td&gt;
&lt;td&gt;Medium&lt;/td&gt;
&lt;td&gt;Ground-truth and external posture&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Discover the PKI&lt;/td&gt;
&lt;td&gt;Certificate and key-store scan&lt;/td&gt;
&lt;td&gt;Low&lt;/td&gt;
&lt;td&gt;The 2031 signature deadline&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Prioritize&lt;/td&gt;
&lt;td&gt;Mosca&apos;s inequality over the CBOM&lt;/td&gt;
&lt;td&gt;Low&lt;/td&gt;
&lt;td&gt;Ordering the migration queue&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Migrate&lt;/td&gt;
&lt;td&gt;Adopt shipping PQC (companion posts)&lt;/td&gt;
&lt;td&gt;High&lt;/td&gt;
&lt;td&gt;The assets the queue surfaces first&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;&lt;/table&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Note:&lt;/strong&gt; If you remember a single operational rule, make it this: run a mix of surfaces, roll the results up into one CBOM, and validate the residual by hand. Every common failure in this space is a shortcut around that rule -- trusting one tool, one surface, or one snapshot.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;The pitfalls are predictable, and each is a shortcut past something earlier in this guide. Scanning Java source without building it leaves symbols unresolved and findings incomplete, exactly as CBOMkit&apos;s documentation warns [@cbomkit]. Treating a certificate scan, or a network scan, as a finished inventory mistakes one surface for the estate. Collapsing family into variant -- recording &quot;AES&quot; instead of &quot;AES-128-GCM&quot; -- throws away the property that makes a finding actionable [@ibm-cbom]. Losing the &lt;code&gt;implements&lt;/code&gt; versus &lt;code&gt;uses&lt;/code&gt; distinction flattens the graph back into a list. And citing a stale CycloneDX version number invites a reviewer to distrust the rest.&lt;/p&gt;

A concrete starting move, before any of the harder surfaces: build one representative service, run a static CBOM scan of it in your CI pipeline with CBOMkit-Hyperion and the Sonar Cryptography plugin, and commit the resulting CycloneDX CBOM next to that service&apos;s SBOM [@sonar-crypto]. You will have a real, validated, versioned crypto inventory for one service by Friday -- and a template for the next hundred. Start where you have source and build context, because that is the surface where the tools are strongest.
&lt;p&gt;Do all five steps and you have converted an impossible-sounding mandate into a bounded, prioritized, machine-actionable program -- and, in the process, confronted the one truth the whole field converged on. That truth is worth stating plainly, alongside the misconceptions that keep tripping teams up.&lt;/p&gt;
&lt;h2&gt;11. Misconceptions, Questions, and the One Truth&lt;/h2&gt;
&lt;p&gt;Almost every misconception in this space is a shortcut past one of the two verbs. &quot;Post-quantum cryptography is the hard part&quot; skips the SEE half -- the new algorithms are finished and shipping [@fips203] [@pyca-changelog] [@ms-pqc-windows]; discovery is the bottleneck. &quot;CBOM is a separate schema from CycloneDX or the SBOM&quot; misreads the substrate -- it is the v1.6 extension of the same document, and can live in the same file [@owasp-cdx16].&lt;/p&gt;
&lt;p&gt;&quot;SP 1800-38 is a finalized NIST standard&quot; over-reads a preliminary draft [@sp1800-38-guide]. &quot;Executive Order 14412 binds everyone&quot; over-reads its scope -- federal agencies and covered contractors are mandated, critical infrastructure is encouraged, and EO 14412 is not EO 14413 [@eo14412]. &quot;We can just scan the network&quot; trusts one surface for the whole estate. And &quot;a spreadsheet of our certificates is a cryptographic inventory&quot; mistakes a stale, single-surface document for a machine-actionable, dependency-aware graph. Each error is a verb half-done.&lt;/p&gt;


No. FIPS 203, 204, and 205 were standardized in August 2024 [@fips203], and ML-KEM is now a `pip install` away and built into Windows [@pyca-changelog] [@ms-pqc-windows]. The binding constraint is discovering where the quantum-vulnerable algorithms already live across your estate. You cannot rotate what you cannot see.


No. The Cryptography Bill of Materials is an extension of the same CycloneDX BOM document, introduced in v1.6 in April 2024 [@owasp-cdx16]. A CBOM can live in the same file as your SBOM, produced and consumed by the same tools [@ibm-cbom].


No. It is a preliminary, initial public draft NCCoE practice guide [@sp1800-38-guide]. Use it for its discovery reference architecture, which is genuinely useful, but state its draft status rather than citing it as a finalized standard.


Only if you are a federal agency or a covered federal contractor; critical infrastructure operators are encouraged, not mandated [@eo14412]. Note also that EO 14412 (&quot;Securing the Nation Against Advanced Cryptographic Attacks&quot;) is not EO 14413, a separate order on quantum innovation [@eo14412].


No. Passive and active network discovery see only cryptography that transits an observed link. They miss data at rest, embedded and operational-technology devices, internal-only applications, and SaaS you cannot reach. A network scan is one surface, not an inventory.


Not a maintainable one. It is stale the moment it is written, it is not machine-actionable, it cannot be prioritized as a graph, and a certificate list sees only the public-key infrastructure surface. A CycloneDX CBOM is the machine-actionable substitute [@ibm-cbom].


No, and not because the tools are immature. Complete automated cryptographic discovery is undecidable in general: the operative question -- whether a program *uses* a primitive internally -- reduces to the halting problem, and Gröbert, Willems, and Holz (RAID 2011) show no detector defeats arbitrary obfuscation. So manual validation is a permanent complement, and the honest deliverable is bounded assurance [@grobert-raid2011] [@nextgov-cisa].

&lt;p&gt;So here is the whole argument in one breath. Post-quantum migration is two verbs, not one. You must be able to ROTATE your cryptography, and you must be able to SEE where it all lives. The replacement algorithms are finished and shipping -- FIPS 203, 204, and 205 since August 2024 [@fips203], a &lt;code&gt;pip install&lt;/code&gt; away and built into Windows [@pyca-changelog] [@ms-pqc-windows] -- yet the 2030 and 2031 deadlines are hard [@eo14412]. The field completed the ROTATE lineage decades before it closed the SEE lineage: rigidity gave way to negotiation, negotiation hardened into RFC 7696, and RFC 7696 was restated as national risk-management guidance in NIST CSWP 39 [@rfc7696] [@cswp39] -- while the inventory half sat unsolved through the spreadsheet era until a 2022 mandate forced it open, automated discovery gave it scale, and CBOM finally gave it a data model [@omb-m2302] [@ibm-cbom]. CBOM is where the two verbs meet: cryptography modeled as a first-class, machine-readable, dependency-aware asset, now named in federal law [@eo14412].&lt;/p&gt;
&lt;p&gt;And the two ceilings keep the claim honest. Undecidability caps what you can see; irreversibility caps what you can rotate [@grobert-raid2011] [@rfc7696]. So the mature goal is never a bare 100 percent. It is bounded assurance for the seeing, and structural honesty about the un-rotatable. The algorithms, it turns out, were the easy part.&lt;/p&gt;

The algorithms were the easy part. You cannot rotate what you cannot see.
&lt;p&gt;&amp;lt;StudyGuide slug=&quot;you-cannot-rotate-what-you-cannot-see&quot; keyTerms={[
  { term: &quot;Crypto-agility&quot;, definition: &quot;The design-time ability to change cryptographic algorithms without re-architecting the systems that depend on them (RFC 7696).&quot; },
  { term: &quot;HNDL&quot;, definition: &quot;Harvest-now-decrypt-later: recording ciphertext today to decrypt once a quantum computer exists; a confidentiality threat, not a signature threat.&quot; },
  { term: &quot;CRQC&quot;, definition: &quot;A cryptographically relevant quantum computer, large enough to run Shor&apos;s algorithm against deployed RSA and elliptic-curve keys.&quot; },
  { term: &quot;SBOM&quot;, definition: &quot;A machine-readable inventory of software components and their dependencies.&quot; },
  { term: &quot;CBOM&quot;, definition: &quot;A Cryptography Bill of Materials: a CycloneDX extension modeling crypto-assets and their dependencies.&quot; },
  { term: &quot;implements vs uses&quot;, definition: &quot;CBOM edges: a library implements an algorithm, an application uses it; together they form a queryable graph.&quot; },
  { term: &quot;MTI algorithm&quot;, definition: &quot;Mandatory-to-implement algorithms kept in a companion doc so the required set can change without re-issuing the base protocol.&quot; },
  { term: &quot;ACDI&quot;, definition: &quot;Automated Cryptography Discovery and Inventory: CISA&apos;s term for tools that auto-enumerate quantum-vulnerable cryptography.&quot; },
  { term: &quot;OID&quot;, definition: &quot;Object identifier: a globally unique dotted-decimal algorithm name (SHA-256 is 2.16.840.1.101.3.4.2.1); the machine-mergeable identity a scanner resolves a finding to.&quot; },
  { term: &quot;Detection mechanism&quot;, definition: &quot;How discovery works: static analysis lifts a recognized API call to an OID; binary analysis matches S-box and round constants or measures runtime entropy and avalanche.&quot; },
  { term: &quot;Mosca&apos;s inequality&quot;, definition: &quot;Migrate now when data shelf-life plus migration time exceeds the time to a quantum computer.&quot; },
  { term: &quot;Undecidability ceiling&quot;, definition: &quot;Complete automated discovery is undecidable: whether a program uses a primitive internally reduces to the halting problem, and whether it computes one is undecidable by Rice&apos;s theorem.&quot; },
  { term: &quot;Irreversibility ceiling&quot;, definition: &quot;Long-lived signatures, trust anchors, and firmware cannot be rotated after the fact, capping agility independently of visibility.&quot; }
]} questions={[
  { q: &quot;Why are Executive Order 14412&apos;s key-establishment and signature deadlines a year apart?&quot;, a: &quot;Harvest-now-decrypt-later threatens confidentiality and key establishment now (2030), while signatures cannot be forged retroactively (2031).&quot; },
  { q: &quot;Why is a scan finding of &apos;AES&apos; not actionable, while &apos;AES-128-GCM at file X line 51&apos; is?&quot;, a: &quot;CBOM&apos;s family-versus-variant property: the variant and its location are what let you decide and act; the family alone cannot be prioritized.&quot; },
  { q: &quot;Why must automated discovery always be paired with manual validation?&quot;, a: &quot;Because complete automated discovery is undecidable in general, so any tool&apos;s coverage is bounded below 100 percent.&quot; },
  { q: &quot;What single operational habit best characterizes a mature crypto-inventory program?&quot;, a: &quot;Run a mix of discovery surfaces, roll them up into one CBOM, and validate the residual by hand.&quot; }
]} /&amp;gt;&lt;/p&gt;
</content:encoded><category>post-quantum-cryptography</category><category>crypto-agility</category><category>cbom</category><category>cryptographic-inventory</category><category>cyclonedx</category><category>sbom</category><category>crypto-migration</category><category>pqc</category><author>noreply@paragmali.com (Parag Mali)</author></item></channel></rss>