io.error grows errors.invalid (ref/hare/io/types.ha:11 spreads
...errors::error, which includes it; Hare's memio seek returns it on
out-of-bounds, stream.ha:134-136) — appended last so existing member
tags stay put; no exhaustive io.error matches exist in lib.
seekfn mirrors ref/hare/memio/stream.ha:122-140 over the flat header,
shared by fixed/dynamic/dynamicfrom (Hare wires the same seek into
both vtables). The io.off-vs-i64 arithmetic runs on an i64 copy:
cstage binop typing is nominal on aliases, wwstage accepts (filed,
ww-core #54).
791's stream_seek_unsupported row re-pins st_seek's void-arm on a
hand-built seekerless vtable: its old premise (memio wires no seeker)
is retired by this commit; memio seek success is pinned by memiotest.
w6c/wwdump main.combined.ww regen'd: they embed lib/io + lib/memio
(the freshness gates are blind to this — embedded-source discipline);
w6a/w6l/ww don't embed io, verified untouched.
Ports ref/hare/io handle.ha: a handle is (file | *stream); ww stream is already *vtable (#94 collapse) so the payload is (file | stream). file=i32 (Hare int is 32-bit, ww int is 8B word -- width-faithful, USER-ruled). read/write/close/seek/tell match on the handle: file-arm to os.read/write/close/lseek (os plays Hare sys role), stream-arm to the unchanged st_* vtable bodies; seeker is the 4th vtable slot (copier deferred). On a file-arm syscall error the stub returns errors.unsupported with a #199b marker -- faithful errno to io.error needs io.error to spread ...errors.error (#204/#199b-blocked); only the error value is lossy until then, the type stays faithful. Regenerates w6c/wwdump combined.ww.