Files
erofs-freebsd-out-tree/docs/pre11-batch-c.md
T
2026-08-18 09:20:44 +02:00

100 lines
3.7 KiB
Markdown

# Pre11 Batch C: ACL Parsing Responsibilities
## Scope
This batch mechanically separates POSIX ACL wire-format parsing from the
FreeBSD vnode and xattr acquisition path.
Modified files:
- `src/xattr.c`
- `docs/pre11-batch-c.md`
No xattr body loading, header-only xattr behavior, namespace handling, public
VOP interface, build configuration, or test infrastructure was changed.
## Responsibility Split
`erofs_get_acl()` continues to own:
- mount option and ACL type validation;
- the default-ACL directory restriction;
- no-ACL filter handling and mode fallback;
- xattr namespace and name selection;
- both `erofs_getxattr()` stages;
- FreeBSD `uio` and `iovec` setup;
- `ENOATTR` fallback and the stack input buffer.
The new `erofs_posix_acl_from_xattr()` receives an already-read buffer and
owns only wire-format validation and ACL population. It borrows both the input
buffer and output ACL and performs no allocation, release, lookup, or vnode
operation.
`erofs_acl_from_mode()` now receives the inode mode directly. This preserves
the original fallback writes while preventing the parser from depending on an
`erofs_node`.
## Moved-Code Mapping
The parsing block formerly at the end of `erofs_get_acl()` was moved in the
same statement order into `erofs_posix_acl_from_xattr()`:
1. Header length and entry-size remainder validation.
2. Header copy and version validation.
3. Entry count calculation and maximum check.
4. Zero-entry mode fallback.
5. `acl_cnt` assignment and phase initialization.
6. Permission validation before tag-phase validation.
7. Tag phase transitions and `UINT32_MAX` rules.
8. Duplicate named user and group ID checks.
9. ACL entry writes and undefined-ID mapping.
10. The short-circuit `phase != 6 || acl_posix1e_check(aclp) != 0` check.
No ACL zeroing or additional field initialization was added. Partial ACL
mutation on malformed input remains possible exactly as before.
## Branch Matrix
| Input or state | Preserved result |
| --- | --- |
| POSIX ACL mount option disabled | `EOPNOTSUPP` in caller |
| Unsupported ACL type | `EINVAL` in caller |
| Default ACL requested for non-directory | `EINVAL` in caller |
| No-ACL filter match | Mode-derived ACL in caller |
| ACL xattr absent | Mode-derived ACL in caller |
| Xattr lookup/read failure | Original error from caller |
| Oversized xattr or nonzero UIO residual | `EINTEGRITY` in caller |
| Short or misaligned wire value | `EINTEGRITY` in parser |
| Unsupported wire version | `EINTEGRITY` in parser |
| Entry count above limit | `EINTEGRITY` in parser |
| Zero entries | Mode-derived ACL in parser |
| Invalid permission, phase, tag, or ID | `EINTEGRITY` in parser |
| Duplicate named user/group ID | `EINTEGRITY` in parser |
| Missing required mask or incomplete phase | `EINTEGRITY` in parser |
| Valid ACL | Identical ACL entry population and success |
## Resource And Error Audit
- The input buffer remains stack-owned by `erofs_get_acl()`.
- The parser does not allocate, free, or retain pointers.
- There are no new cleanup paths.
- Xattr errors, UIO residual errors, wire errors, and ACL validation errors
retain their previous ordering.
- `erofs_xattr_load_body()` and its release paths were not modified.
- The optional header validation helper was intentionally omitted to avoid
touching the known header-only behavior.
## Static Verification
The batch is validated with:
- a strict two-file path whitelist;
- unique definitions of `erofs_get_acl()`, `erofs_acl_from_mode()`, and
`erofs_posix_acl_from_xattr()`;
- pre/post comparison of parser returns, phase transitions, ACL writes, and
duplicate-ID checks;
- `git diff --check`;
- confirmation that `erofs_xattr_load_body()` is absent from the source diff.
No build, QEMU smoke test, or feature test was run for this mechanical split.