docs: ASCII typography and style normalization across all repo text
Replace every em dash with real punctuation (rewrites, not hyphen swaps) in docs, code comments, scripts, configs, and the port records; convert en dashes, curly quotes, ellipsis glyphs, arrows, and section signs to ASCII; drop machine-writing tell phrases from living docs. ADR titles now use a colon. The M2 bring-up DTS model string carried an em dash into the patch series and its record echoes; fixed at both, and the full series re-verified to apply cleanly onto pristine 6.18.46. One comment in freshness.h deliberately names the em dash glyph the UI renders as the unknown mark; that is data, kept as prose naming it. Verified: cargo tests (sim, config-lint, rs485-bridge), shellcheck, both driver MC/DC harnesses, patches-apply.
This commit is contained in:
@@ -2,7 +2,7 @@
|
||||
|
||||
Static target-config gates: catches flash-time config faults the behavioural sim cannot: mistakes in the
|
||||
*memory map*, not the logic. The first check is the one that would have caught the
|
||||
**c8a3 brick** — a boot-loaded coprocessor firmware dropped at `0x40000`, which is
|
||||
**c8a3 brick**: a boot-loaded coprocessor firmware dropped at `0x40000`, which is
|
||||
a `reserved-memory` carve-out on Thunder-Boot boards but plain kernel RAM on the 86 Panel,
|
||||
so the MCU and the kernel fought over the same DRAM and the board hung before eth0.
|
||||
|
||||
@@ -15,7 +15,7 @@ Every address the idblock loader drops MCU firmware to must sit inside a
|
||||
hpmcu/mcu/amp entry) in `[LOADER_OPTION]`, with its `LOAD_ADDR` from
|
||||
`[LOADERn_PARAM]`.
|
||||
- **Reserved ranges** come from the devicetree: every `reg = <addr size>` inside a
|
||||
`reserved-memory { … }` node.
|
||||
`reserved-memory { ... }` node.
|
||||
|
||||
A load outside all reservations is a failure (non-zero exit).
|
||||
|
||||
@@ -37,6 +37,6 @@ found; `2` = usage/IO error.
|
||||
|
||||
The suite encodes the brick as a regression: the real Thunder-Boot `.ini`
|
||||
(Hpmcu @ `0x40000`) *fails* against a DT with no `rtos@40000` node and *passes*
|
||||
once the reservation is added — and the 86 Panel's non-TB loader (no boot-loaded MCU)
|
||||
always passes. See `../../docs/architecture.md` §5 and, for the hardware hazard,
|
||||
once the reservation is added, and the 86 Panel's non-TB loader (no boot-loaded MCU)
|
||||
always passes. See `../../docs/architecture.md` section 5 and, for the hardware hazard,
|
||||
the `boot-loaded-mcu-0x40000-hazard` note.
|
||||
|
||||
@@ -1,10 +1,10 @@
|
||||
//! config-lint — static target-config checks the behavioural sim cannot cover.
|
||||
//! config-lint: static target-config checks the behavioural sim cannot cover.
|
||||
//!
|
||||
//! The c8a3 brick was a memory-map fault, not a logic bug: the boot-loaded MCU's
|
||||
//! load address (`0x40000`) is a `reserved-memory` carve-out on Thunder-Boot
|
||||
//! boards but plain kernel RAM on ours, so the coprocessor firmware and the kernel
|
||||
//! fought over the same DRAM and the board hung before eth0. No sim catches that —
|
||||
//! it needs a static check against the target devicetree: **every address the
|
||||
//! fought over the same DRAM and the board hung before eth0. No sim catches that.
|
||||
//! It needs a static check against the target devicetree: **every address the
|
||||
//! idblock loader drops MCU firmware to must sit inside a `reserved-memory` node.**
|
||||
//!
|
||||
//! This module parses the two authoritative artifacts (the rkbin loader `.ini`
|
||||
@@ -38,7 +38,7 @@ pub struct Finding {
|
||||
pub msg: String,
|
||||
}
|
||||
|
||||
/// A byte that can appear inside a devicetree node/property identifier — used to
|
||||
/// A byte that can appear inside a devicetree node/property identifier: used to
|
||||
/// require a token boundary before a `reg` property, so substrings like `reg-names`
|
||||
/// or a `region-*` node label are not matched as the `reg` property itself.
|
||||
fn is_ident_byte(b: u8) -> bool {
|
||||
@@ -54,19 +54,19 @@ fn parse_addr(s: &str) -> Option<u64> {
|
||||
}
|
||||
}
|
||||
|
||||
/// Loaders that are part of the normal RK boot chain — DDR init, SPL/miniloader, the
|
||||
/// secure monitor, U-Boot — and are NOT boot-loaded coprocessor firmware, so their
|
||||
/// Loaders that are part of the normal RK boot chain (DDR init, SPL/miniloader, the
|
||||
/// secure monitor, U-Boot) and are NOT boot-loaded coprocessor firmware, so their
|
||||
/// LOAD_ADDR (if any) is the vendor boot flow, not a DRAM carve-out that must be
|
||||
/// reserved. Anything NOT on this allowlist that declares a LOAD_ADDR is treated as
|
||||
/// a coprocessor load and checked (**fail closed**): a future MCU named
|
||||
/// "Rtos"/"Bl32"/"M0" must not slip through an MCU-*name* allowlist the way the
|
||||
/// original `hpmcu`/`mcu`/`amp` substring test would have — that is exactly the
|
||||
/// original `hpmcu`/`mcu`/`amp` substring test would have: that is exactly the
|
||||
/// c8a3 0x40000-brick class this tool exists to catch.
|
||||
///
|
||||
/// Matched as a WHOLE normalized name (separators stripped), never a substring, so a
|
||||
/// coprocessor whose vendor name merely *contains* a boot-chain word — "AudioLoader"
|
||||
/// ⊃ "loader", "SplRtos" ⊃ "spl", "Bl32" (≠ "bl31") — is still checked, not waved
|
||||
/// through. Over-inclusion here would only over-report (the safe direction); a missed
|
||||
/// coprocessor whose vendor name merely *contains* a boot-chain word ("AudioLoader"
|
||||
/// contains "loader", "SplRtos" contains "spl", "Bl32" is not "bl31") is still checked,
|
||||
/// not waved through. Over-inclusion here would only over-report (the safe direction); a missed
|
||||
/// coprocessor is the dangerous one.
|
||||
fn is_known_safe_loader(name: &str) -> bool {
|
||||
let n: String = name
|
||||
@@ -185,8 +185,8 @@ pub fn parse_reserved_ranges(dt: &str) -> Vec<Range> {
|
||||
j += 1;
|
||||
}
|
||||
// scan `reg = <addr size>` PROPERTY tokens inside [start, j). Match `reg` as
|
||||
// a whole token — identifier boundary before it, `=` after optional space —
|
||||
// so a `reg-names` property or a `region-*@…` node label (both contain the
|
||||
// a whole token (identifier boundary before it, `=` after optional space),
|
||||
// so a `reg-names` property or a `region-*@...` node label (both contain the
|
||||
// substring "reg") is not misparsed into a bogus range.
|
||||
let block = &dt[start..j.min(dt.len())];
|
||||
let bb = block.as_bytes();
|
||||
@@ -234,8 +234,8 @@ pub fn check(loads: &[McuLoad], reserved: &[Range]) -> Vec<Finding> {
|
||||
.map(|l| Finding {
|
||||
load: l.clone(),
|
||||
msg: format!(
|
||||
"{}={} loads MCU firmware at {:#x} but no reserved-memory node covers it \
|
||||
— kernel/MCU DRAM collision (the 0x40000 brick class)",
|
||||
"{}={} loads MCU firmware at {:#x} but no reserved-memory node covers it: \
|
||||
kernel/MCU DRAM collision (the 0x40000 brick class)",
|
||||
l.loader, l.name, l.load_addr
|
||||
),
|
||||
})
|
||||
@@ -338,7 +338,7 @@ FLAG=0x10007
|
||||
"#;
|
||||
|
||||
/// Regression (correctness review): `reg` must match as a whole property token,
|
||||
/// not a bare substring — the `region-*` label, `reg-names`, and the
|
||||
/// not a bare substring: the `region-*` label, `reg-names`, and the
|
||||
/// `interrupts` cells must NOT be misparsed into extra ranges.
|
||||
#[test]
|
||||
fn reg_token_not_substring() {
|
||||
@@ -349,7 +349,7 @@ FLAG=0x10007
|
||||
}
|
||||
|
||||
// A future coprocessor loader named nothing like hpmcu/mcu/amp, at an
|
||||
// unreserved DRAM address — the exact case an MCU-name allowlist would miss.
|
||||
// unreserved DRAM address: the exact case an MCU-name allowlist would miss.
|
||||
const UNKNOWN_MCU_INI: &str = r#"
|
||||
[LOADER_OPTION]
|
||||
NUM=2
|
||||
@@ -378,7 +378,7 @@ LOAD_ADDR=0x40000
|
||||
}
|
||||
|
||||
// Coprocessor names that merely *contain* a safe boot-chain word, each with a
|
||||
// LOAD_ADDR: "AudioLoader" ⊃ "loader", "SplRtos" ⊃ "spl", "Bl32" (≠ "bl31").
|
||||
// LOAD_ADDR: "AudioLoader" contains "loader", "SplRtos" contains "spl", "Bl32" is not "bl31".
|
||||
const SUBSTRING_TRAP_INI: &str = r#"
|
||||
[LOADER_OPTION]
|
||||
NUM=4
|
||||
@@ -399,7 +399,7 @@ LOAD_ADDR=0x70000
|
||||
"#;
|
||||
|
||||
/// Regression (2nd-pass correctness review): the safe allowlist matches a WHOLE
|
||||
/// normalized name, never a substring — a coprocessor whose name contains a
|
||||
/// normalized name, never a substring: a coprocessor whose name contains a
|
||||
/// boot-chain word must NOT be waved through. FlashData (a real boot component,
|
||||
/// no LOAD_ADDR here) stays safe; the three coprocessors are all checked.
|
||||
#[test]
|
||||
|
||||
@@ -1,13 +1,13 @@
|
||||
//! config-lint CLI — the MCU-load-vs-reserved-memory gate as a CI check.
|
||||
//! config-lint CLI: the MCU-load-vs-reserved-memory gate as a CI check.
|
||||
//!
|
||||
//! Usage:
|
||||
//! config-lint --ini <loader.ini> --dt <devicetree.dts>
|
||||
//!
|
||||
//! The `--dt` argument accepts a `.dts`/`.dtsi` or the flattened output of
|
||||
//! `dtc -I dtb -O dts built.dtb` (preferred in CI — it resolves includes and
|
||||
//! `dtc -I dtb -O dts built.dtb` (preferred in CI: it resolves includes and
|
||||
//! overlays, so it reflects what the board will actually boot). Exits non-zero
|
||||
//! and prints each offending MCU load if any lands outside a `reserved-memory`
|
||||
//! node — the 0x40000 brick class.
|
||||
//! node: the 0x40000 brick class.
|
||||
|
||||
use std::process::ExitCode;
|
||||
use warden_config_lint::{check, parse_ini_mcu_loads, parse_reserved_ranges};
|
||||
@@ -56,7 +56,7 @@ fn main() -> ExitCode {
|
||||
let findings = check(&loads, &reserved);
|
||||
|
||||
if loads.is_empty() {
|
||||
println!("config-lint: no boot-loaded MCU firmware in {ini_path} — nothing to reserve.");
|
||||
println!("config-lint: no boot-loaded MCU firmware in {ini_path}: nothing to reserve.");
|
||||
} else {
|
||||
println!(
|
||||
"config-lint: {} MCU load(s) in {ini_path}, {} reserved-memory range(s) in {dt_path}.",
|
||||
@@ -66,11 +66,11 @@ fn main() -> ExitCode {
|
||||
}
|
||||
|
||||
if findings.is_empty() {
|
||||
println!("config-lint: OK — every MCU load is inside a reserved-memory node.");
|
||||
println!("config-lint: OK: every MCU load is inside a reserved-memory node.");
|
||||
ExitCode::SUCCESS
|
||||
} else {
|
||||
for f in &findings {
|
||||
eprintln!("config-lint: FAIL — {}", f.msg);
|
||||
eprintln!("config-lint: FAIL: {}", f.msg);
|
||||
}
|
||||
ExitCode::FAILURE
|
||||
}
|
||||
|
||||
+4
-4
@@ -1,10 +1,10 @@
|
||||
#!/usr/bin/env python3
|
||||
"""flowgen — generate mermaid flowcharts for the workflows the SDK tests.
|
||||
"""flowgen: generate mermaid flowcharts for the workflows the SDK tests.
|
||||
|
||||
future-features-2 asks that the test harness "produce flowcharts of every workflow
|
||||
and process that it tests so a user can understand them better", each carrying its
|
||||
benchmark. This emits one `docs/workflows/<name>.md` per workflow: an outcome-first
|
||||
flowchart (from the modelled decision path) plus the workflow's metric — a benchmark
|
||||
flowchart (from the modelled decision path) plus the workflow's metric: a benchmark
|
||||
ns/op for the sim-modelled hardware workflows, or the MC/DC result for the Tier-1
|
||||
driver workflows.
|
||||
|
||||
@@ -86,7 +86,7 @@ WORKFLOWS = [
|
||||
"name": "relay-drive",
|
||||
"title": "Relay Drive",
|
||||
"outcome": "A relay is exported transparently and driven without disturbing a held contact.",
|
||||
"metric": ("mcdc", "relays.c — 40/40 conditions, 100% MC/DC (CI-enforced)"),
|
||||
"metric": ("mcdc", "relays.c: 40/40 conditions, 100% MC/DC (CI-enforced)"),
|
||||
"mermaid": """flowchart TD
|
||||
A[warden_relay_set idx,on] --> B{idx < COUNT?}
|
||||
B -- no --> Z[no-op]
|
||||
@@ -104,7 +104,7 @@ WORKFLOWS = [
|
||||
"name": "freshness-contract",
|
||||
"title": "UI Freshness Contract",
|
||||
"outcome": "The UI never shows a stale number: it holds briefly, then marks unknown.",
|
||||
"metric": ("mcdc", "freshness.c — 66/66 conditions, 100% MC/DC (CI-enforced)"),
|
||||
"metric": ("mcdc", "freshness.c: 66/66 conditions, 100% MC/DC (CI-enforced)"),
|
||||
"mermaid": """flowchart TD
|
||||
A[produce] --> B{result}
|
||||
B -- OK --> V[render value, save last]
|
||||
|
||||
Reference in New Issue
Block a user