{"record":{"id":"f32008bfd7a0021f","repo":"embassy-rs/embassy","slug":"trng-consecutive-health-check-failures-increa","errorCode":null,"errorMessage":"TRNG: {} consecutive health check failures. Increase Config::sample_count.","messagePattern":"TRNG: (.+?) consecutive health check failures\\. Increase Config::sample_count\\.","errorType":"panic","errorClass":null,"httpStatus":null,"severity":"error","filePath":"embassy-rp/src/trng.rs","lineNumber":330,"sourceCode":"\n    /// Unmask all interrupt sources. The interrupt handler masks them when it fires.\n    fn unmask_irq(&self) {\n        self.info.regs.rng_imr().write(|w| {\n            w.set_ehr_valid_int_mask(false);\n            w.set_autocorr_err_int_mask(false);\n            w.set_crngt_err_int_mask(false);\n            w.set_vn_err_int_mask(false);\n        });\n    }\n\n    fn blocking_wait_for_successful_generation(&self) {\n        let regs = self.info.regs;\n        let mut failures = 0;\n        while regs.trng_valid().read().ehr_valid().not() {\n            if self.handle_health_check_status() {\n                failures += 1;\n                if failures >= MAX_HEALTH_CHECK_RETRIES {\n                    panic!(\n                        \"TRNG: {} consecutive health check failures. Increase Config::sample_count.\",\n                        MAX_HEALTH_CHECK_RETRIES\n                    );\n                }\n            }\n        }\n    }\n\n    /// Read out a completed block. Reading `EHR_DATA5` clears the result registers\n    /// and starts the next generation.\n    fn read_ehr_registers_into_array(&mut self, buffer: &mut [u8; TRNG_BLOCK_SIZE_BYTES]) {\n        let regs = self.info.regs;\n        let ehr_data_regs = [\n            regs.ehr_data0(),\n            regs.ehr_data1(),\n            regs.ehr_data2(),\n            regs.ehr_data3(),\n            regs.ehr_data4(),","sourceCodeStart":312,"sourceCodeEnd":348,"githubUrl":"https://github.com/embassy-rs/embassy/blob/463a07b963419a1bfe61d5d597c44acb810afb8b/embassy-rp/src/trng.rs#L312-L348","documentation":"The RP235x hardware TRNG runs entropy health checks on every random number generation. When the EHR valid flag never asserts and the health-check status reports failure MAX_HEALTH_CHECK_RETRIES times consecutively, the blocking wait gives up and panics, telling the user to raise `Config::sample_count`. Repeated health-check failures indicate the entropy source is producing insufficient/unhealthy samples for the current sample_count setting.","triggerScenarios":"Calling `blocking_next_u32`, `blocking_next_u64`, or `blocking_fill_bytes` on the TRNG when the hardware health check fails MAX_HEALTH_CHECK_RETRIES consecutive times — usually because Config::sample_count is too low for the chip's noise source (e.g. default sample count too small at current clock/temperature conditions).","commonSituations":"RP235x boards with the TRNG configured with a small sample_count; noisy power/clock conditions weakening the ring-oscillator entropy; code copied from examples with aggressive (small) sample counts to speed up generation.","solutions":["Increase `Config::sample_count` (raise it substantially, e.g. multiply by 2-10) so the health check accumulates enough entropy before validation","Retry generation at a higher level with backoff, since failures can be transient under marginal conditions","Check power supply and clock configuration — unstable analog supply degrades the entropy source and can cause persistent health-check failures","If failures persist across sample_count increases, treat the TRNG as faulty and route through a software RNG seeded from a different source"],"exampleFix":"// before\nlet mut trng = Trng::new(p.TRNG, Config { sample_count: 100 });\nlet n = trng.blocking_next_u32();\n// after\nlet mut trng = Trng::new(p.TRNG, Config { sample_count: 2000 });\nlet n = trng.blocking_next_u32();","handlingStrategy":"validation","validationCode":"fn cfg_ok(cfg: &Config) -> Result<(), &'static str> {\n    if cfg.sample_count < 1000 { Err(\"sample_count too low for reliable TRNG health checks\") } else { Ok(()) }\n}","typeGuard":null,"tryCatchPattern":"// panics in no_std; validate config and use the async API with retry instead of blocking\ndefensive: tune sample_count upward until health checks pass reliably","preventionTips":["Start with conservative (large) sample_count values and only reduce after field testing","Log health-check failure counts via handle_health_check_status equivalents before hitting the cap","Watch for environmental causes: brownouts, noisy supplies, extreme temperatures"],"tags":["embedded","rp235x","trng","random","hardware"],"backgroundTag":"invalid-config-value","analyzedSha":"463a07b963419a1bfe61d5d597c44acb810afb8b","analyzedAt":"2026-09-10T13:38:26.660Z","contentChangedAt":"2026-09-10T13:38:26.660Z","schemaVersion":2},"datasetVersion":"2026-09-16T04:17:20.429Z"}