fs: systemPath runtime native (step 2b of #68, commit 1 of 2) #559

Closed
opened 2026-10-28 23:14:34 +00:00 by orion · 2 comments
Collaborator

Context

Step 2b of #68 (PATH slice 2, the boundary). Step 1 (#419) taught the compiler Into<Path> native parameters, step 2 (#547) made every path parameter of std/fs Into<Path> (landed). What slice 2 still names is systemPath: public fn systemPath(path: Path): String, "the path as the operating system of this machine reads it: for a foreign function and for a child process" (PATH.md section 6).

The conversion exists only in C and only on Windows: torb_platform_system_path in runtime/platform.c answers a wchar_t * (backslashes, \\?\ above MAX_PATH), declared under #if defined(_WIN32) in runtime/include/torb.h, and the POSIX half needs none of it (a path is bytes there). No std function can reach it, so systemPath needs a new native, and a new native takes two commits under the seed rule of CLAUDE.md "Seed and breaking changes". This issue is commit 1 of 2: the runtime function and its manifest row. The std/fs wrapper is commit 2 and follows as its own step once the published seed knows the row.

Source

  • docs/design/PATH.md section 6 ("std/fs answers Path values", the systemPath signature) and the diagram in section 1, section 8 slice 2

Goal

The runtime offers torb_file_system_path(torb_text path, torb_text *out) (name by the existing torb_file_* convention), which answers the / text of a path in the form this machine's operating system takes, as UTF-8 text: unchanged on POSIX; on Windows the same text that torb_platform_system_path builds (backslashes, \\?\ where the plain form would be too long), converted back to UTF-8 with torb_platform_utf8. The native-manifest row fileSystemPath in compiler/src/backend/c/natives.trb maps a private native fn fileSystemPath(path: String): String onto it.

Acceptance criteria

  • runtime/file.c (or runtime/platform.c, whichever already holds the neighbouring conversions) implements the function; runtime/include/torb.h declares it outside the _WIN32 block with a doc comment saying what it answers
  • POSIX: the answer is byte-identical to the argument, including a non-ASCII name and an empty text; a C test in runtime/tests/ pins it and runs in the forge CI
  • Windows: a case in runtime/tests/platform_test.c under #if defined(_WIN32) pins C:/a/b -> C:\a\b, a share path, and a path above MAX_PATH -> \\?\C:\...; it is built by the GitHub mirror's portable.yml, so the PR states that the forge CI cannot run it
  • The manifest row exists in compiler/src/backend/c/natives.trb with the C signature text; the manifest tests of the compiler (compiler/tests/) pass with the new row and list it
  • No std source declares or calls the native yet. If the build rejects a manifest row that no std declaration uses, the PR body quotes the diagnostic and the split moves: this commit is then the runtime function and its C tests only, and the row plus the private declaration go to the next step with the wrapper
  • docs/design/PATH.md status header gets one sentence: the runtime half of systemPath is in, the std/fs function is not; the header stays "partly implemented"

Seed

Yes: a new native (a manifest row the compiler looks up). Two-commit rule: this issue is commit 1 (teach, nothing in std, compiler/ or tools/ calls it yet). The published seed has to contain this commit before step 2c (the std/fs wrapper) is pushed, or CI cannot bootstrap it; publishing the seed (the forge's seed workflow or the nightly) stays with Torben and the nightly, not with the loop.

Scope

  • runtime/file.c or runtime/platform.c, runtime/include/torb.h, runtime/tests/
  • compiler/src/backend/c/natives.trb (the one row) and the manifest tests
  • the one PATH.md sentence

Out of scope

  • The public systemPath(path: Path): String in std/fs and its tests and docs (step 2c of #68)
  • Changing IoError.path, list, absolutePath (steps 3 and 4), Process taking a Path working directory
  • seed/, releases, the seed workflow

Dependencies

Part of #68. Steps 1 (#419) and 2 (#547) are closed and on main. Nothing else open.

Commits

One feat(runtime) commit for the function, the row and the tests; a second docs(fs) commit for the PATH.md sentence only if the PR reads better that way.

## Context Step 2b of #68 (PATH slice 2, the boundary). Step 1 (#419) taught the compiler `Into<Path>` native parameters, step 2 (#547) made every path parameter of `std/fs` `Into<Path>` (landed). What slice 2 still names is `systemPath`: `public fn systemPath(path: Path): String`, "the path as the operating system of this machine reads it: for a foreign function and for a child process" (PATH.md section 6). The conversion exists only in C and only on Windows: `torb_platform_system_path` in `runtime/platform.c` answers a `wchar_t *` (backslashes, `\\?\` above `MAX_PATH`), declared under `#if defined(_WIN32)` in `runtime/include/torb.h`, and the POSIX half needs none of it (a path is bytes there). No `std` function can reach it, so `systemPath` needs a **new native**, and a new native takes two commits under the seed rule of `CLAUDE.md` "Seed and breaking changes". This issue is commit 1 of 2: the runtime function and its manifest row. The `std/fs` wrapper is commit 2 and follows as its own step once the published seed knows the row. ## Source - `docs/design/PATH.md` section 6 ("`std/fs` answers `Path` values", the `systemPath` signature) and the diagram in section 1, section 8 slice 2 ## Goal The runtime offers `torb_file_system_path(torb_text path, torb_text *out)` (name by the existing `torb_file_*` convention), which answers the `/` text of a path in the form this machine's operating system takes, as UTF-8 text: unchanged on POSIX; on Windows the same text that `torb_platform_system_path` builds (backslashes, `\\?\` where the plain form would be too long), converted back to UTF-8 with `torb_platform_utf8`. The native-manifest row `fileSystemPath` in `compiler/src/backend/c/natives.trb` maps a private `native fn fileSystemPath(path: String): String` onto it. ## Acceptance criteria - [ ] `runtime/file.c` (or `runtime/platform.c`, whichever already holds the neighbouring conversions) implements the function; `runtime/include/torb.h` declares it outside the `_WIN32` block with a doc comment saying what it answers - [ ] POSIX: the answer is byte-identical to the argument, including a non-ASCII name and an empty text; a C test in `runtime/tests/` pins it and runs in the forge CI - [ ] Windows: a case in `runtime/tests/platform_test.c` under `#if defined(_WIN32)` pins `C:/a/b` -> `C:\a\b`, a share path, and a path above `MAX_PATH` -> `\\?\C:\...`; it is built by the GitHub mirror's `portable.yml`, so the PR states that the forge CI cannot run it - [ ] The manifest row exists in `compiler/src/backend/c/natives.trb` with the C signature text; the manifest tests of the compiler (`compiler/tests/`) pass with the new row and list it - [ ] No `std` source declares or calls the native yet. If the build rejects a manifest row that no `std` declaration uses, the PR body quotes the diagnostic and the split moves: this commit is then the runtime function and its C tests only, and the row plus the private declaration go to the next step with the wrapper - [ ] `docs/design/PATH.md` status header gets one sentence: the runtime half of `systemPath` is in, the `std/fs` function is not; the header stays "partly implemented" ## Seed Yes: a new native (a manifest row the compiler looks up). Two-commit rule: this issue is commit 1 (teach, nothing in `std`, `compiler/` or `tools/` calls it yet). The published seed has to contain this commit before step 2c (the `std/fs` wrapper) is pushed, or CI cannot bootstrap it; publishing the seed (the forge's `seed` workflow or the nightly) stays with Torben and the nightly, not with the loop. ## Scope - `runtime/file.c` or `runtime/platform.c`, `runtime/include/torb.h`, `runtime/tests/` - `compiler/src/backend/c/natives.trb` (the one row) and the manifest tests - the one PATH.md sentence ## Out of scope - The public `systemPath(path: Path): String` in `std/fs` and its tests and docs (step 2c of #68) - Changing `IoError.path`, `list`, `absolutePath` (steps 3 and 4), `Process` taking a `Path` working directory - `seed/`, releases, the seed workflow ## Dependencies Part of #68. Steps 1 (#419) and 2 (#547) are closed and on `main`. Nothing else open. ## Commits One `feat(runtime)` commit for the function, the row and the tests; a second `docs(fs)` commit for the PATH.md sentence only if the PR reads better that way.
Author
Collaborator

[loop:torbscript] claim implement by session:loop-torbscript-20261029 until 2026-10-29T05:22:42Z

[loop:torbscript] claim implement by session:loop-torbscript-20261029 until 2026-10-29T05:22:42Z
Author
Collaborator

[loop:torbscript] implement: runtime function torb_file_system_path (file.c over a new torb_platform_system_path_text in platform.c, POSIX identity, Windows via torb_platform_system_path + torb_platform_utf8), manifest row fileSystemPath (Direct native answering the String, so the C signature returns torb_text instead of the out parameter the issue sketched; reasoning in the PR body), audit row in NATIVES.md (205 keep / 562 total), torb_natives.h and machine_natives.c written to what the generator produces (thunk 98, later thunks renumbered, count 332), POSIX C test in file_test.c, Windows cases in platform_test.c (forge CI cannot run them), one PATH.md sentence. One commit. No local build: the agent host has no C compiler and bootstrap is off limits, so everything is unverified until CI. PR #560, forge CI queued for 20+ min with no job started (runner backlog), next: waiting (forge CI queued; then review). If the natives test finds the generated files differ from the generator, regenerate with torb natives --header in a fix round. ~150k tokens.

[loop:torbscript] implement: runtime function torb_file_system_path (file.c over a new torb_platform_system_path_text in platform.c, POSIX identity, Windows via torb_platform_system_path + torb_platform_utf8), manifest row fileSystemPath (Direct native answering the String, so the C signature returns torb_text instead of the out parameter the issue sketched; reasoning in the PR body), audit row in NATIVES.md (205 keep / 562 total), torb_natives.h and machine_natives.c written to what the generator produces (thunk 98, later thunks renumbered, count 332), POSIX C test in file_test.c, Windows cases in platform_test.c (forge CI cannot run them), one PATH.md sentence. One commit. No local build: the agent host has no C compiler and bootstrap is off limits, so everything is unverified until CI. PR https://git.torb.dev/torbscript/language/pulls/560, forge CI queued for 20+ min with no job started (runner backlog), next: waiting (forge CI queued; then review). If the natives test finds the generated files differ from the generator, regenerate with torb natives --header in a fix round. ~150k tokens.
argus closed this issue 2026-10-29 00:46:50 +00:00
Sign in to join this conversation.
No labels
loop
ready
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set

Reference
torbscript/language#559
No description provided.