{"answers":{"affected":"2 open source packages ship an affected version, including ml-dsa.","exploited":"There is no known exploitation of GHSA-h37v-hp6w-2pp8 in the wild and no public exploit code.","fix":"Upgrade ml-dsa to 0.1.0-rc.5 or later.","what":"GHSA-h37v-hp6w-2pp8 is a vulnerability in ml-dsa, published on 2 Feb 2026. An attacker can exploit it over the internet without logging in, with no action from the victim."},"fix_prompt":"Check this codebase for GHSA-h37v-hp6w-2pp8 and fix it if it is affected.\n\nWhat it is: GHSA-h37v-hp6w-2pp8 is a vulnerability in ml-dsa, published on 2 Feb 2026. An attacker can exploit it over the internet without logging in, with no action from the victim.\nExploitation: There is no known exploitation of GHSA-h37v-hp6w-2pp8 in the wild and no public exploit code.\n\nAffected packages and fixed versions:\n- ml-dsa (crates.io): affected all versions; fixed in 0.1.0-rc.5\n- ml-dsa (crates.io): affected all versions; fixed in 0.1.0-rc.5\n\nTask:\n1. Search the dependency manifests and lockfiles (for example package.json, package-lock.json, requirements.txt, poetry.lock, uv.lock, pom.xml, build.gradle, go.mod, Cargo.lock, Gemfile.lock) and any Dockerfiles for the affected packages, including transitive dependencies.\n2. If an affected version is in use, upgrade it to the fixed version for its release line with the project's package manager, so the lockfile is regenerated. Prefer the smallest upgrade that fixes it.\n3. If there is no fix, or the upgrade would break the build, do not guess: explain the risk and the safest workaround instead.\n4. Run the tests and summarise what changed and why.\n5. If nothing in the project is affected, say so and change nothing.\n\nReference: https://insights.sbomify.com/GHSA-h37v-hp6w-2pp8/ (Markdown: https://insights.sbomify.com/GHSA-h37v-hp6w-2pp8/index.md)","id":"GHSA-h37v-hp6w-2pp8","markdown":"https://insights.sbomify.com/GHSA-h37v-hp6w-2pp8/index.md","name":"GHSA-h37v-hp6w-2pp8","record":{"aliases":[],"analysis":{"component_type":"library","fix_type":"patch","impacts":["denial_of_service"],"network_reachable":"yes","non_default_config":false,"product_category":"Rust cryptographic library","requires_auth":"none","summary":"An off-by-two error in the ml-dsa library causes valid signatures to fail verification, leading to denial of service for users relying on this cryptographic implementation.","user_interaction":"not_required","vuln_class":"other"},"analysis_generated_by":"qwen3.8-flash-next","assigner":null,"cpe":[],"cvss":{"score":null,"severity":null,"source":null,"vector":null,"version":null},"cwes":[],"description":"### Summary\n\nThere's a bug in the `use_hint` function where it adds 1 instead of subtracting 1 when the decomposed low bits `r0` equal exactly zero. FIPS 204 Algorithm 40 is pretty clear that `r0 \u003e 0` means strictly positive, but the current code treats zero as positive. This causes valid signatures to potentially fail verification when this edge case gets hit.\n\n### Details\n\nThe issue is in `ml-dsa/src/hint.rs` in the `use_hint` function. Here's what FIPS 204 Algorithm 40 says:\n\n```\n3: if h = 1 and r0 \u003e 0  return (r1 + 1) mod m\n4: if h = 1 and r0 \u003c= 0  return (r1 − 1) mod m\n```\n\nLine 3 uses `r0 \u003e 0` (strictly greater than zero), and line 4 uses `r0 \u003c= 0` (less than or equal, which includes zero). So when `r0 = 0`, the spec says to subtract 1.\n\nBut the current implementation does this:\n\n```rust\nif h \u0026\u0026 r0.0 \u003c= gamma2 {\n    Elem::new((r1.0 + 1) % m)\n} else if h \u0026\u0026 r0.0 \u003e= BaseField::Q - gamma2 {\n    Elem::new((r1.0 + m - 1) % m)\n}\n```\n\nThe problem is `r0.0 \u003c= gamma2` includes zero. When `r0 = 0`, this condition is true (since `0 \u003c= gamma2`), so it adds 1. But according to the spec, `r0 = 0` should fall into the `r0 \u003c= 0` case and subtract 1 instead.\n\nThe result is +1 when it should be -1, which is an off by two error mod m.\n\n### PoC\n\nTake MLDSA 44 where γ2 = 95,232 and m = 44.\n\nIf `use_hint(true, 0)` is called:\n- `Decompose(0)` gives `(r1=0, r0=0)`\n- The condition `r0.0 \u003c= gamma2` is `0 \u003c= 95232` which is true\n- So it returns `(0 + 1) % 44 = 1`\n\nBut FIPS 204 says:\n- `r0 \u003e 0` is `0 \u003e 0` which is false\n- `r0 ≤ 0` is `0 ≤ 0` which is true\n- So it should return `(0 - 1) mod 44 = 43`\n\nThe function returns 1 when it should return 43.\n\nThis can happen in real signatures whenever any coefficient of the `w'` vector happens to be a multiple of 2γ2, which makes its decomposed `r0` equal zero. It's not super common but it's definitely possible, and when it hits, verification will fail for a completely valid signature.\n\n### Impact\n\nThis is a FIPS 204 compliance bug that affects signature verification. When the edge case triggers, valid signatures get rejected. Since MLDSA is supposed to be used for high security post quantum cryptography, having verification randomly fail isn't great. It's also theoretically possible that the mismatch between what signing expects and what verification does could be exploited somehow, though that would need more looking into.\n\nThe fix is straightforward, just change the condition to explicitly check for positive values:\n\n```rust\nif h \u0026\u0026 r0.0 \u003e 0 \u0026\u0026 r0.0 \u003c= gamma2 {\n    Elem::new((r1.0 + 1) % m)\n} else if h {\n    Elem::new((r1.0 + m - 1) % m)\n}\n```","ecosystems":["crates.io"],"exploits":{"exploitdb":null,"first_seen":null,"github_poc":null,"max_poc_stars":null,"metasploit":null,"nuclei":null,"refs":[],"tier":null},"has_fix":true,"headline":"ml-dsa's UseHint function has off by two error when r0 equals zero","id":"GHSA-h37v-hp6w-2pp8","indexable":true,"kev":null,"kind":"advisory","links":{"ecosystem":"crates.io","product":null,"products":[],"type":"other","year":"2026"},"n_packages":2,"n_references":null,"packages":[{"ecosystem":"crates.io","fixed":["0.1.0-rc.5"],"introduced":["0"],"last_affected":[],"package":"ml-dsa","purl":null,"source":"GHSA-h37v-hp6w-2pp8"},{"ecosystem":"crates.io","fixed":["0.1.0-rc.5"],"introduced":["0"],"last_affected":[],"package":"ml-dsa","purl":"pkg:cargo/ml-dsa","source":"GHSA-h37v-hp6w-2pp8"}],"products":null,"published":"2026-02-02","related":[],"sources":[{"class":"attribution","licence":"CC BY 4.0","name":"GitHub Advisory Database","prefix":"GHSA"}],"ssvc":{"automatable":null,"exploitation":null,"technical_impact":null},"state":null,"updated":null,"vendors":null},"summary":"An off-by-two error in the ml-dsa library causes valid signatures to fail verification, leading to denial of service for users relying on this cryptographic implementation.","url":"https://insights.sbomify.com/GHSA-h37v-hp6w-2pp8/"}