# P15-021 Stage0 Decision

Status: `GO`. B19b source is authorized; B19a remains `STOP-NO-SOURCE`.

P15-021 is the xattr Bloom fast-negative candidate. The gate uses a real,
byte-reproducible EROFS image generated by `mkfs.erofs` 1.8.6, an independent
on-disk parser, a temporary file-local `erofs_xxh32` prototype, frozen Linux
format/use-site anchors, and five cold provider-metadata-read samples. It does
not link a prototype into the DUT KLD and does not modify `src/**`.

The required matrix is hit, proven miss, collision false positive, unknown
filter format, feature off, malformed shared-count metadata, malformed shared
ID metadata, positive FreeBSD errno, 64-worker replay, one million generated
names without a false negative, and owned cleanup. Unknown formats and feature
off must scan. A collision must scan. Structural corruption reached before or
during the scan must remain `EINTEGRITY` rather than becoming `ENOATTR`.

The gate command is:

```sh
timeout -k 10 240 tests/pre15/gates/P15-021.sh \
  --base 666e52f710363df07f7c93919eb835d41092d011 \
  --output OUTPUT
```

## Frozen Identity

The gate BASE is `666e52f710363df07f7c93919eb835d41092d011`.
`P15-021-input.json` freezes the three DUT source files, Linux `erofs_fs.h` and
`xattr.c`, FreeBSD 15 source HEAD
`106727738dcfb6c001b46f25363b91cece970085`, erofs-utils HEAD
`7db78788b000999e2de88decd2ba90654f26171c`, host tools, format constants,
thresholds, seven endian/seed vectors, one million generated names, 64 workers,
and the exact gate/source write sets. FreeBSD has no public xxh32 API; its only
copies are private Zstd/OpenZFS sources, so the authorized implementation is
file-local and namespaced as `erofs_xxh32`.

The generated prototype source SHA256 is
`3fe1a7a64ce4386d74f5f49455fe8bef2a2ee55a03eb72593a89d4dec70c1b4b`.
Its temporary host binary SHA256 is
`9910baed4d018a0257f38377bb48857a3205ee42d9f0ff279db71e63e5ba695b`;
the binary is evidence only, is not committed, and is never linked into the DUT
KLD.

## Fixture And Oracle

`mkfs.erofs` 1.8.6 generated the filter-bearing image twice from 64 peers and
one target with eight shared user xattrs. The two images were byte-identical;
the valid fixture SHA256 is
`b06b7c4c30adb3684d11505edf815dc0a395c03f6a95120b3150361008a182cb`.
The independent parser handles multi-block directories and separately decodes
inode xattr headers, inline entries, shared IDs, and shared entries. Legal
valid, unknown-reserved, and feature-off images pass `fsck.erofs`.

The seven-case matrix passes: present hit, proven miss, collision false
positive, unknown filter, feature off, malformed shared count, and out-of-range
shared ID. Miss alone takes the fast-negative. Hit and collision perform the
complete scan; unknown format and feature off perform the unchanged complete
scan. Corrupt header/shared metadata returns positive FreeBSD `EINTEGRITY=97`,
while valid absence returns positive `ENOATTR=87`.

The candidate implementation, independent Python xxh32, system libxxhash, and
the frozen Linux seed/endianness vectors agree. One million deterministic random
names across EROFS indexes 1/2/3/4/6 produce no candidate/oracle difference and
no false negative in 1,024 constructed valid filters. Sixty-four workers
complete 1,280 mixed lookups with identical bytes/errno.

## Benefit And Decision

Five cold samples of 200 real-fixture misses each are stable. Baseline metadata
read calls are `3400,3400,3400,3400,3400`; candidate calls are
`400,400,400,400,400`, an 88.235 percent reduction. Baseline cold unique
provider blocks are `400,400,400,400,400`; candidate blocks are
`200,200,200,200,200`, a 50 percent reduction. Both exceed the mandatory 25
percent threshold. The model counts the extra header/shared-ID reads on
positive and collision paths and therefore does not hide their overhead.

G03 is `GO` for P15-021. Only a proven negative may bypass the full scan; all
other outcomes retain the current FreeBSD extattr namespace, VOP transfer,
positive errno, metadata buffer ownership, and lock-free immutable lookup
behavior. Linux supplies the format/hash comparison, not FreeBSD vnode/cache or
locking semantics.

Attempt 1 stopped at the fixed-vector check because five hexadecimal hashes
were transcribed to incorrect decimal JSON values. Python and libxxhash agreed
on the hexadecimal values and bits; the input-only correction was replayed
under a new output directory. Attempts 2 and 3 then produced identical semantic
results and fixture hashes. Attempt 3 evidence is retained at
`/work/pre15-evidence/20260815T-P15-021-G03-attempt-3`; its `SHA256SUMS` digest
is `b81fe1b94048dbc3d17c62c95aba6a5de9e068e2a15639ca55ea60fe5a251e07`.
No QEMU or full feature suite was run for the Stage0 decision. Source remained
unchanged, owned temporary files/processes are zero, and protected PID 26318,
port 9222, and the base bp were untouched.
