boot2

Playing with the boostrap
git clone https://git.ryansepassi.com/git/boot2.git
Log | Files | Refs | README

CC parallel work plan

Coordination doc for the next batch of tests/cc/ features. Defines four parallel work streams, the design seams between them, and the sequencing required where streams aren't fully independent.

Companion to CC-PUNCHLIST.md (the per-item checklist) and CC-INTERNALS.md (module layering and the cg-fixture-first workflow). ABI choices below cite P1.md §Arguments and return values.

Tests in scope

Currently failing on aarch64:

Test Stream Failure
cc/082-union-basic D exit 1 — union field offsets bumped like struct
cc/087-sizeof-noeval D exit 2 — sizeof(x++) actually increments x
cc/111-struct-ret-1word A1 compile-fail — return-by-value struct unhandled
cc/112-struct-ret-2word A1 compile-fail — no two-word return path
cc/113-struct-ret-3word A2 compile-fail — no indirect-result path
cc/114-struct-ret-many-args A3 exit 2 — silently truncates
cc/115-struct-ret-3word-many-args A3 exit 2 — silently truncates
cc/116-struct-ret-vararg A3 exit 2 — silently truncates
cc/117-compound-literal B compile-fail — (T){…} unparsed
cc/118-const-expr C compile-fail — const-expr surface incomplete

Stream layout

                         ┌─ A1: 111 + 112  (one-word + two-word direct)
Stream A (sequential) ───┤
struct-return ABI        └─ A2: 113        (indirect-result)
                              │
                              ▼
                         ┌─ A3a: 114 (sret + stack-staged args)   ┐
                         ├─ A3b: 115 (sret + 3-word + many args)  │ parallel
                         └─ A3c: 116 (sret + variadic save area)  ┘

Stream B  (independent, t=0):  117 compound literals
Stream C  (independent, t=0):  118 const-expr evaluator
Stream D  (independent, t=0):  082 union offsets + 087 sizeof no-emit

t=0: A1, B, C, D fan out together. A2 starts when A1 lands. A3a/b/c fan out when A2 lands. Total wall time ≈ A1 + A2 + max(A3).

Stream A — Struct-return ABI

Implements the three result conventions from P1.md §Arguments:

Width Convention a0 a1 Args 0..3
≤ 8B one-word direct result word 0 (caller arg 1) a0..a3
9–16B two-word direct result word 0 result word 1 a0..a3
> 16B indirect-result result-buffer ptr (callee arg 0) a1..a3 (shifted)

In the indirect convention, incoming stack-arg slot 0 corresponds to explicit arg word 3 (not 4). LDARG indexing in the variadic save area must respect this shift.

A1 — one-word and two-word direct

A2 — indirect-result

A3 — sret compositions (parallel)

Each agent picks up one test, mostly composing infrastructure A1+A2 already shipped:

Stream B — Compound literals (117)

C99 §6.5.2.5: (T){ init-list } as a postfix expression. Block-scope only; file-scope literals die explicitly.

Stream C — Const-expr evaluator (118)

Adds parse-const-expr ps → (value . ctype), a self-contained walker that never touches cg.

Stream D — Surgical fixes (082 + 087)

Single agent — both ~30-line changes.

082 — union field offsets

parse-struct-fields (cc.scm:3634) advances offset after every field regardless of kind. For unions all fields must stay at offset 0.

087 — sizeof no-emit

The current sizeof arm at cc.scm:4898 calls parse-unary / parse-expr which emit code for the operand. sizeof(x++) therefore actually increments x.

Cross-stream contracts

Sizeof split (C and D stay independent)

Two distinct callers, two independent mechanisms:

The two paths share the concept (don't evaluate the operand) but not the implementation. They can land in either order.

A1 ↔ B/C/D

Independent. A1 only touches cg-fn-end, cg-call, and parse-return-stmt. B touches parse-cast-or-unary. C adds a new walker plus changes to four call sites that don't overlap with A1. D touches parse-struct-fields and adds two new cg primitives.

A2 ↔ A3

A3 depends on A2's indirect-result implementation. A3a/b/c are independent of each other once A2 has landed.

Workflow per stream

Per CC-INTERNALS §Feature workflow:

  1. cc-cg fixture (red) — drive the cg API directly.
  2. Implement cg primitives until cc-cg green.
  3. cc fixture (red) — full driver.
  4. Implement parser changes until cc green.

Pick the next free <n> per suite. cc-cg currently goes up through 69; cc goes up through 118 (with gaps).

Acceptance

Per stream: make test SUITE=cc ARCH=aarch64 shows the stream's target tests as PASS, no prior tests regress. Final acceptance: all ten currently-failing tests green on aarch64.