diff --git a/README.md b/README.md index d31157a..608c7a0 100644 --- a/README.md +++ b/README.md @@ -15,3 +15,27 @@ Sporel.exe --module=lib-core.maps-test ``` Output is TAP version 13 on stdout; exit-code = failure-count (0 = all pass). + +## Coverage Statements (2026-05-16 Fault-Injection Audit) + +Verified via deliberate-mutation in fixture-mirror; mutations reverted after observation. + +### Caught Mutations + +| # | Mutation | Caught by | +|---|---|---| +| M1 | `M.tile_at` renamed to `M._tile_at_disabled` (API-break) | Runtime error "attempt to call a nil value (field 'tile_at')" — test aborts at assertion 4 | +| M2 | `M.is_walkable` body prefixed with `do return false end` (always-false logic) | Assertion "grass interior walkable" (ok 7) — `not ok` with actual=false | + +### Uncaught Mutations (Gaps) + +| # | Mutation | Why uncaught | Severity | +|---|---|---|---| +| M3 | OOB guard in `M.tile_at` removed (`if tx < 0 or ...` commented out) | Lua's 1-indexed tables return `nil` for index 0 and negative indices, so all tested OOB coordinates (`-1,0` and `0,16`) still incidentally produce `nil` without the guard | Low | + +**Resolution per Gap:** +- Gap M3: Headless-reachable in principle, but OOB guard is coincidentally shadowed by Lua nil-on-out-of-range semantics for all tested coordinates. The existing assertions (`tile_at(-1,0)=nil`, `tile_at(0,16)=nil`) pass whether the guard is present or not. Cheap fill would require a case where removal causes *non-nil* (e.g. a wrapping scenario) — not applicable here. Classify as Future-Slice B: note that guard correctness is invisible to current test vectors; no cheap fix available (asserting the guard itself is not meaningful headless-side). + +### Tested Production-Lib Surface + +`lib-core.maps` v0.1.0 — Tests cover behavior of: `maps.load`, `maps.set_current`, `maps.size`, `maps.tile_size`, `maps.tile_at` (2-arg and 3-arg nil-fallback forms), `maps.is_walkable`, `maps.list`.