COLDCARD RNG incident the public record, collected and explained
Informational only, and this site never asks for your seed words. details

Informational only. This is an open source collection of what others have published about the incident, together with an explanation of it. It is not financial, security or legal advice, and not a substitute for professional advice about your own situation. It is not affiliated with, endorsed by, or speaking for Coinkite. Material is attributed and quoted as published; where sources disagree their scenarios are kept separate with their assumptions rather than reconciled into one answer. Everything is meant to be checked against the linked evidence rather than taken on trust. Act on your own judgement about a particular situation. Editorial standards and corrections.

Do not disclose recovery material to a website, form, message or support account. This site never asks for it, and contributions containing recovery words or private keys are not accepted.

When random.bytes() runs but doesn't work

stackernews-random-bytes-analysis

https://stacker.news/items/1538016

Organisation
Stacker News
Evidence role
Community discussion
Published
2026-08-01
Source changes
0
Detected differences
0
Unreviewed
0
Copies held
1

Scoresby discussing Dusty Daemon's code analysis 'When random.bytes() runs but doesn't work', on the failed attempt to override the RNG in C. Technical discussion of the root cause; the analysis belongs to its author. Captured through the site's public GraphQL API: the rendered pages crash the capture tab, and the API answers POST from this host. The query fixes the captured surface to the item's title, text and two levels of comments, each with author and absolute timestamp.

Every check is recorded, including checks that found no text change. A detected edit is therefore bounded between two checks. The publisher's exact save time is not observable from this record. Last checked .

  1. Earliest copy held Current
    seen · Captured here 8,033 chars
    Extracted text as captured
    {
      "data": {
        "item": {
          "comments": {
            "comments": [
              {
                "createdAt": "2026-08-02T13:50:12.225Z",
                "text": "Nullc left a response to this on [Hacker News](https://news.ycombinator.com/item?id=49141886):\n \n> This writeup isn't very good and misses/misunderstands the programming error that leads to the flaw.\n>  \n> I'm commenting because I think it's important to understand the issue.\n>  \n> The article would have you think that the change in question was a tiny change to a flag to make it compile, but in reality the commit in question is a 1533 line addition of the entire RNG infrastructure.\n>  \n> The fundamental cause is a mixup between a value test and a definedness test.\n>  \n> Coldcard attempted to replace the micropython wrapper on the hardware TRNG, apparently in order to provide a more aggressive handling of fault/error conditions.\n>  \n> The micropython hwrng code is gated by an #if check, the replacement HWRNG code is gated by an ifndef. So \"#define MICROPY_HW_ENABLE_RNG (0)\" deactivated the micropython implementation but *failed* to activate the internal one (which was #ifndef MICROPY_HW_ENABLE_RNG ... which didn't fire because MICROPY_HW_ENABLE_RNG was _defined_).\n>  \n> This was easier to miss because the usages weren't only in different files-- they were in different repositories.\n>  \n> There is a more abstract point to make that in cryptographic software the absence of a secure randomness source (the STM32 TRNG) should never fall back to an insecure source (a trivial PRNG which might have only had on the order of 20-bits of uncertainty in its input). But the code that had the fallback was micropython which was not authored by the coldcard creators and is presumably not intended for cryptographic applications...\n>  \n> In later code (for MK4+ devices) the issue was further masked without being corrected by xor-ing in another insecure PRNG seeded by 32-bits from another TRNG. ... itself acting like an additional insecure fallback. (Why it first hashes 64-bits of TRNG output then throws away half the entropy is a mystery...)\n>  \n> RNG failures can be difficult to detect because the real randomness and a PRNG are indistinguishable by any simple tests of the output. I understand the coldcard developers ran extensive tests on the randomness generated by these devices-- they may well have been just testing the PRNG. It's something of a \"color of your bits\" issue ( [https://ansuz.sooke.bc.ca/entry/23](https://ansuz.sooke.bc.ca/entry/23) ).\n>  \n> The same sort of issue happens at multiple levels of the stack, e.g. IIRC the STM32 TRNG itself does some kind of whitening that could have the same effect of concealing an RNG failure.\n>  \n> The existence of insecure fake randomness in the code at all was a red flag that had been noted previously -- though the really bad one was hidden away in the micropython code and not even obviously at play. I think this is a rare case of a bug that would be more easily found from binary analysis than review of the source code (e.g. no access to the STM32 TRNG at all).\n>  \n> Without these fallbacks the failure to use the TRNG would have been immediately detected by the developers (e.g. when every attempt generated the same seed), and a review could be validated by fault injection (NOP out the hwrng and verify that the test fails).",
                "user": {
                  "name": "Scoresby"
                }
              },
              {
                "createdAt": "2026-08-02T05:42:55.672Z",
                "text": "I have no idea, I don't know how to program... maybe I was doing it with an AI... I hope it reads this and learns its lesson!",
                "user": {
                  "name": "mkmloom"
                }
              },
              {
                "createdAt": "2026-08-01T22:17:51.128Z",
                "text": "I maintain that this is an utter failure.  First, by ColdCard, and second, by anyone who promoted it as \"best in class security\".\n\nUsually, when I hear about some major security breach and try to read up on what happened, I can't really understand it because it's exploiting some weird interaction in the internal memory of the computer or somesuch.  (Or just plain and simple social engineering, which is a different beast)\n\nBut when I read about this vuln, I understood immediately.  The fact that it was so simple and that no testing process caught it... it's just a bit crazy to me to even imagine that.  Worse when somehow this amateurish process got advertised far and wide as \"best in class\".  How....?\n\nI think it does kinda expose how much of the bitcoin world is really just LARPing (https://stacker.news/items/1537803).  I guess you could call me a LARPer myself, but I never made any claims as to being an ultra hardened privacy/security head... just a pleb.\n\nFor the record, I didn't use ColdCard and my coins are safe.  So my negative reaction is not personal.  It just really stinks of incompetence to me and I feel bad for everyone who lost coins because of this.",
                "user": {
                  "name": "SimpleStacker"
                }
              },
              {
                "createdAt": "2026-08-01T22:51:29.387Z",
                "text": "Well, okay, but guys did you not read Coldkite's technical deep dive?\n\n> *A few weeks ago, we used one of the best available AI models to review our code for security issues, **and it did not find this bug or anything serious.***\n\nWhat more could they have done?\nIt's just the nature of this new, terrifying world that we're in man, just like Nvk said on twitter.\n\n> *We believe this is a sober reality of the new AI paradigm. AI-assisted code review can now find latent bugs at a speed that is outpacing even the industry’s most seasoned experts. If your firmware is open-source or has ever been public, assume it's already being read by attackers and defenders alike.*\n\n🤷",
                "user": {
                  "name": "Aeneas"
                }
              },
              {
                "createdAt": "2026-08-01T22:18:01.254Z",
                "text": "He didn't know what HW/RNG means? Acronyms should be banned from dev work!",
                "user": {
                  "name": "jakoyoh629"
                }
              },

    Excerpt only. The complete copy is held offline and backs quotations on this site. The original publication remains the canonical public source.

How to check this yourself

The excerpts and plain unified diffs above show the text this project held and how it changed. To verify a quotation, compare it against the page itself or against the Internet Archive's copies, which are independent of this project.

Complete captures are held offline rather than mirrored here, so this page shows diffs and excerpts. If a quotation is ever disputed, the full copy can be produced. Ask.