lib/io: port mode/whence/error + reader/writer/closer fn-aliases (#94 fold-d)

New lib/io/types.ww mirrors ref/hare/io/types.ha — the surrounding
port that lives alongside the existing lib/io/io.ww (pre-vtable
stream + eof + underread). Hare splits the same way (stream.ha +
types.ha share `module io`); ww does the equivalent via dir-enum.

Each type cites Hare per CLAUDE.md rule 9:
  - mode    (enum u8)  — ref/hare/io/types.ha:29-34. RDWR=3 (not
                         Hare's `READ | WRITE`) because ww enum-value
                         positions don't fold expressions; bitfield
                         value SSoT preserved, divergence inline.
  - whence  (enum i32) — ref/hare/io/types.ha:37-41. Hare leaves the
                         underlying implicit; ww requires one. i32
                         matches the `off` type fold-e wires in.
  - error              — ref/hare/io/types.ha:11. Hare spreads
                         `errors::error`; lib/errors not ported, so
                         the union carries the two tags observable
                         in this fold: underread (from io.ww) and
                         the predeclared `nomem` (#29, type.c:72 /
                         check.ww:78). NOT redefined here.
  - reader/writer/closer — ref/hare/io/types.ha:46/51/55. EOF=eof
                           (not Hare's `done` singleton) per #93
                           and the io.ww:8 rationale. `*stream`
                           forward-refs the existing pre-vtable
                           struct in io.ww; same cross-file pattern
                           Hare uses.

Drew signoff (this fold only): seeker, copier, strerror, and the
EOF=done singleton DEFERRED to fold-e — they need the `handle` sum
and #93's done landing. Hare's `_unsafe` carve-out unaffected.

eof / underread / stream re-used from io.ww (NOT redefined); io.ww
keeps the pre-vtable struct unchanged, ditto its WHY-comments.

Combined.ww regen (#110): selfhost/cmd/{w6c,wwdump}/main.combined.ww
auto-pulled the new types.ww via dir-enum (+52 lines each, same
package io). Makefile dep lines for wwdump_ww + w6c_ww add the new
source so editing it triggers rebuild.

Probe: test/wcc/768_io_types_run.c — 5 rows × 2 stages = 10
invocations. Pins enum value/underlying + the three fn-type aliases
at the param slot. Both siblings filed inline in the probe header:

  - #189 wwstage `let r: io.reader = fn_name;` bails "let: not
    assignable". cstage accepts. Param + struct-field paths work
    in both stages, so io vtable port is unblocked. Probe uses
    the alias only at the param slot.
  - #190 wwstage match-arm on cross-module variant tag bails
    "case: not a variant of scrutinee (io.eof | io.error)". Likely
    same family as #178. cstage accepts. Probe uses `is` instead
    of `match` for the variant gate.

make test: 201/201 (was 200; +1 from 768). 990-997 byte-id +
combined_ww_fresh + sizelint all green.
This commit is contained in:
2026-05-28 21:58:06 +09:00
parent c07f96fc35
commit 635429bef8
5 changed files with 426 additions and 2 deletions

View File

@@ -113,7 +113,7 @@ $(BIN)/wwdump_ww: selfhost/cmd/wwdump/main.ww \
selfhost/cmd/wcc/cgen.ww selfhost/cmd/wcc/cgenexpr.ww \
selfhost/cmd/wcc/cgenstmt.ww selfhost/cmd/wcc/cgenutil.ww \
selfhost/cmd/wcc/cgendecl.ww \
lib/os/os.ww lib/rt/malloc.ww lib/time/time.ww lib/strconv/strconv.ww lib/strconv/stof_data.ww lib/strconv/decimal.ww lib/strconv/stof.ww lib/strconv/ftos_data.ww lib/strconv/ftos.ww lib/strings/strings.ww lib/bytes/bytes.ww lib/encoding/utf8/utf8.ww lib/ascii/ascii.ww lib/io/io.ww lib/memio/memio.ww lib/fmt/fmt.ww \
lib/os/os.ww lib/rt/malloc.ww lib/time/time.ww lib/strconv/strconv.ww lib/strconv/stof_data.ww lib/strconv/decimal.ww lib/strconv/stof.ww lib/strconv/ftos_data.ww lib/strconv/ftos.ww lib/strings/strings.ww lib/bytes/bytes.ww lib/encoding/utf8/utf8.ww lib/ascii/ascii.ww lib/io/io.ww lib/io/types.ww lib/memio/memio.ww lib/fmt/fmt.ww \
$(BIN)/ww $(BIN)/w6c $(BIN)/w6a $(BIN)/w6l \
$(LIB)/libwwrt.a | $(BIN)
@mkdir -p $(BIN)/wwdump_ww.d
@@ -135,7 +135,7 @@ $(BIN)/w6c_ww: selfhost/cmd/w6c/main.ww \
selfhost/cmd/wcc/cgen.ww selfhost/cmd/wcc/cgenexpr.ww \
selfhost/cmd/wcc/cgenstmt.ww selfhost/cmd/wcc/cgenutil.ww \
selfhost/cmd/wcc/cgendecl.ww \
lib/os/os.ww lib/rt/malloc.ww lib/time/time.ww lib/strconv/strconv.ww lib/strconv/stof_data.ww lib/strconv/decimal.ww lib/strconv/stof.ww lib/strconv/ftos_data.ww lib/strconv/ftos.ww lib/strings/strings.ww lib/bytes/bytes.ww lib/encoding/utf8/utf8.ww lib/ascii/ascii.ww lib/io/io.ww lib/memio/memio.ww lib/fmt/fmt.ww \
lib/os/os.ww lib/rt/malloc.ww lib/time/time.ww lib/strconv/strconv.ww lib/strconv/stof_data.ww lib/strconv/decimal.ww lib/strconv/stof.ww lib/strconv/ftos_data.ww lib/strconv/ftos.ww lib/strings/strings.ww lib/bytes/bytes.ww lib/encoding/utf8/utf8.ww lib/ascii/ascii.ww lib/io/io.ww lib/io/types.ww lib/memio/memio.ww lib/fmt/fmt.ww \
$(BIN)/ww $(BIN)/w6c $(BIN)/w6a $(BIN)/w6l \
$(LIB)/libwwrt.a | $(BIN)
@mkdir -p $(BIN)/w6c_ww.d
@@ -318,6 +318,7 @@ TESTS = $(BIN)/test_smoke $(BIN)/test_lex $(BIN)/test_parse $(BIN)/test_check \
$(BIN)/test_star_fn_deref \
$(BIN)/test_star_fn_deref_call \
$(BIN)/test_match_variant_dispatch \
$(BIN)/test_io_types_run \
$(BIN)/test_use_promote_alias \
$(BIN)/test_field_signed $(BIN)/test_frame_argcount \
$(BIN)/test_selfhost $(BIN)/test_w6a_ww $(BIN)/test_w6l_ww \
@@ -632,6 +633,12 @@ $(BIN)/test_match_variant_dispatch: test/wcc/767_match_variant_dispatch.c \
$(LIB)/libwwrt.a | $(BIN)
$(CC) $(CFLAGS) -o $@ $<
$(BIN)/test_io_types_run: test/wcc/768_io_types_run.c \
$(BIN)/ww $(BIN)/w6c $(BIN)/w6a $(BIN)/w6l \
$(BIN)/ww_ww $(BIN)/w6c_ww $(BIN)/w6a_ww $(BIN)/w6l_ww \
$(LIB)/libwwrt.a | $(BIN)
$(CC) $(CFLAGS) -o $@ $<
$(BIN)/test_arrlit_str_full: test/wcc/711_arrlit_str_full.c \
$(BIN)/ww $(BIN)/w6c $(BIN)/w6a $(BIN)/w6l \
$(BIN)/ww_ww $(BIN)/w6c_ww $(BIN)/w6a_ww $(BIN)/w6l_ww \