source: scrub iter-code / Decision-N residue from inline comments

Follow-up to bcd4181: the remaining ~530 inline `//` and `///`
comments still carrying opaque shorthand are now reformulated to
their content phrases. The only surviving `iter-<code>` reference
in source is the literal filename
`docs/journals/2026-05-13-iter-mq.3.md` (a real journal file).

Sweep covered:
  - `// Iter X.Y: <text>` prefixes (Iter 13a / 14a / 14e / 15g-aux /
    16b.x / 16d / 16e / 18b / 18c.x / 18d.x / 18e / 18g.x / 19a /
    19a.1 / 19b / 20a / 20f / 22-floats.x / 22b.x / 22c / 23.x /
    24.1 / cli-diag-human / hs.x / str-concat / etc.) — fully
    removed; the descriptive text that followed each prefix stays.
  - `// (Decision N)` and `per Decision N` and `Decision N axis 3` —
    replaced with the content phrase plus the relevant contract
    file (`design/contracts/tail-calls.md` for Decision 8,
    `design/contracts/memory-model.md` for Decision 10,
    `design/contracts/typeclasses.md` and `design/models/typeclasses.md`
    for Decision 11, `design/contracts/authoring-surface.md` for
    Decision 6, "the transitional dual-allocator" for Decision 9,
    "Effect prose" for Decision 3).
  - `// mq.X / mq.X (Task N) / mq.X journal / mq.X invariant` ->
    "the canonical-class-form rule / Class-class repurpose /
    method-dispatch-refactor journal / canonical-class-form
    invariant".
  - `// ct.X / ct.X (canonical-type-names) / ct.1.5a + ctt.2 /
    ct.2 Task N` -> "the canonical-form rule for type references /
    the canonical-form normalisation step / canonical-type-lookup
    refactor".
  - `// eob.X` -> "heap-Str-ABI" / "the Str carve-out".
  - `// rpe.X` -> "the per-type-print-op retirement".
  - `// post-mq.X / Pre-ct.X / pre-mq.X` -> "post-canonical-class-form" /
    "Pre-canonical-type-form" etc.
  - `/// Iter X regression: / /// Iter X.Y: / /// Iter A arm-close /
    /// Iter ct.4 (...): / /// Iter rpe.1 ...` -> descriptive
    phrases.

The journal filename in `crates/ailang-core/src/workspace.rs:573`
stays verbatim because it points at an actual file under
`docs/journals/`.

Tests: full `cargo test --workspace` green (80/80 test-result blocks
clean, no FAILED line). design_index_pin 5/5 + docs_honesty_pin 5/5
gating tests pass.
This commit is contained in:
2026-05-20 09:58:04 +02:00
parent bcd41810f4
commit ac4d545570
43 changed files with 1004 additions and 1000 deletions
+20 -20
View File
@@ -32,7 +32,7 @@ use super::synth::llvm_type;
use super::{AllocStrategy, Emitter, FnSig, Result};
impl<'a> Emitter<'a> {
/// Iter 18c.4: emit a `void @drop_<module>_<TypeName>(ptr %p)`
/// emit a `void @drop_<module>_<TypeName>(ptr %p)`
/// function that decrements the refcount of every pointer-typed
/// field of every ctor, then frees the outer box.
///
@@ -160,7 +160,7 @@ impl<'a> Emitter<'a> {
self.body.push_str(&out);
}
/// Iter 18e: emit `drop_<m>_<T>` for a `(drop-iterative)` type.
/// emit `drop_<m>_<T>` for a `(drop-iterative)` type.
/// Replaces the recursive cascade in [`Self::emit_drop_fn_for_type`]
/// with an iterative-with-explicit-worklist body so cells of
/// arbitrary chain depth can free without consuming proportional
@@ -328,7 +328,7 @@ impl<'a> Emitter<'a> {
self.body.push_str(&out);
}
/// Iter 18e helper: is `fty` the same ADT as `td_name` in the
/// is `fty` the same ADT as `td_name` in the
/// current module? Used by the iterative-drop body to decide
/// "push to worklist" (same type) vs. "call its drop fn directly"
/// (different type).
@@ -365,7 +365,7 @@ impl<'a> Emitter<'a> {
}
}
/// Iter 18c.4: pick the drop-fn symbol to call for a single
/// pick the drop-fn symbol to call for a single
/// pointer-typed field. Routes ADT fields to their own
/// `drop_<owner>_<T>` symbol so the recursion cascades through
/// recursive types (List, Tree). Falls back to `ailang_rc_dec`
@@ -430,7 +430,7 @@ impl<'a> Emitter<'a> {
}
}
/// Iter 18c.3: predicate the `Term::Let` lowering uses to decide
/// predicate the `Term::Let` lowering uses to decide
/// whether a let-binder owns a fresh RC-heap allocation that
/// codegen should `dec` at scope close.
///
@@ -443,7 +443,7 @@ impl<'a> Emitter<'a> {
/// non-escaping ones become stack `alloca`s and must NOT be
/// `dec`'d (they are freed by LLVM at fn return).
///
/// Iter 18g.2 widens this to include `Term::App` whose callee's
/// The widened input set includes `Term::App` whose callee's
/// fn-type carries `ret_mode == Own`. The mode contract states that
/// the callee hands the returned cell's ownership to the caller's
/// frame; the let-scope close is the right place for the caller's
@@ -464,7 +464,7 @@ impl<'a> Emitter<'a> {
!self.non_escape.contains(&term_ptr)
}
Term::App { callee, .. } => {
// Iter 18g.2: a call whose callee carries
// a call whose callee carries
// `ret_mode == Own` hands a fresh heap allocation to
// the caller's frame. Trackable. `Borrow` and
// `Implicit` ret-modes do not carry that signal —
@@ -479,7 +479,7 @@ impl<'a> Emitter<'a> {
}
}
/// Iter 18g.2: lookup helper for a callee's `ret_mode`. Returns
/// lookup helper for a callee's `ret_mode`. Returns
/// `Some(mode)` when the callee resolves to a fn-typed term;
/// `None` for shapes whose type is not a `Type::Fn` (typechecker
/// would already have rejected an App on a non-fn, but the helper
@@ -494,7 +494,7 @@ impl<'a> Emitter<'a> {
}
}
/// Iter 18c.4: pick the drop-fn symbol to call at the close of a
/// pick the drop-fn symbol to call at the close of a
/// trackable `Term::Let` scope. For a `Term::Ctor` binder the
/// symbol is `drop_<owner>_<TypeName>` — derived from the ctor's
/// `type_name` (which already encodes the owning module via the
@@ -524,7 +524,7 @@ impl<'a> Emitter<'a> {
.get(val_ssa)
.cloned()
.unwrap_or_else(|| "ailang_rc_dec".to_string()),
// Iter 18g.2: an Own-returning call hands a freshly heap-
// an Own-returning call hands a freshly heap-
// allocated cell whose static type is the callee's
// `ret`. Resolve the per-type drop fn from that ret-type
// so the cascade walks the cell's pointer-typed children
@@ -559,7 +559,7 @@ impl<'a> Emitter<'a> {
}
}
/// Iter 18g.tidy.fu2: tag-conditional partial-drop helper.
/// tag-conditional partial-drop helper.
/// Emits `void @partial_drop_<m>_<T>(ptr %p, i64 %mask)` —
/// structurally parallel to [`Self::emit_drop_fn_for_type`] but
/// gates each ptr-field dec on a bit of `%mask`. If bit j of the
@@ -699,7 +699,7 @@ impl<'a> Emitter<'a> {
self.body.push_str(&out);
}
/// Iter 18g.tidy.fu2: resolve the `partial_drop_<owner>_<T>`
/// resolve the `partial_drop_<owner>_<T>`
/// symbol for a type, parallel to the existing per-type drop
/// dispatch in `field_drop_call`. Returns `None` for non-ADT
/// types (Str, fn-typed, type-vars) — callers fall back to
@@ -728,7 +728,7 @@ impl<'a> Emitter<'a> {
}
}
/// Iter 18g.tidy.fu2: build the i64 moved-slots bitmask for a
/// build the i64 moved-slots bitmask for a
/// `partial_drop_<m>_<T>` call. Bit j is set iff slot j is in
/// `moved`. We reject slot indices ≥ 64 with `None` — no
/// language-level ADT has that many fields, but the cap is
@@ -747,7 +747,7 @@ impl<'a> Emitter<'a> {
Some(mask)
}
/// Iter 18d.3: emit a partial-drop sequence inline at a let-close
/// emit a partial-drop sequence inline at a let-close
/// site whose binder has moved-out pattern slots. Replaces the
/// uniform `drop_<m>_<T>(ptr)` call: load each pointer-typed
/// field whose slot index is NOT in `moved`, dispatch through
@@ -757,11 +757,11 @@ impl<'a> Emitter<'a> {
/// transferred to a pattern-bound binder that owns the dec
/// for them.
///
/// Iter 18g.2 widened the input set to `Term::App` (Own-
/// returning call). The static per-field emission below is keyed
/// The widened input set includes `Term::App` (Own-returning
/// call). The static per-field emission below is keyed
/// against a `Term::Ctor`'s known ctor; a `Term::App` binder
/// whose body pattern-matches it has a *dynamic* runtime tag.
/// Iter 18g.tidy.fu2 closes that path: instead of falling back
/// instead of falling back
/// to shallow `ailang_rc_dec` (which leaked the unmoved fields),
/// we route through the tag-conditional helper
/// [`Self::emit_partial_drop_fn_for_type`], which dispatches on
@@ -775,7 +775,7 @@ impl<'a> Emitter<'a> {
let (type_name, ctor_name) = match value {
Term::Ctor { type_name, ctor, .. } => (type_name.as_str(), ctor.as_str()),
_ => {
// Iter 18g.tidy.fu2: dynamic-tag partial-drop via the
// dynamic-tag partial-drop via the
// per-type helper. `value` is `Term::App` (Own-
// returning) — the binder's static type is the App's
// ret type, recovered through `synth_arg_type` /
@@ -836,7 +836,7 @@ impl<'a> Emitter<'a> {
Ok(())
}
/// Iter 18c.4: build the IR text for a closure env's drop fn.
/// build the IR text for a closure env's drop fn.
/// Layout: 8 bytes per capture, in declaration order.
/// For each pointer-typed capture, emit a load + drop call;
/// finally `ailang_rc_dec` the env block.
@@ -878,7 +878,7 @@ impl<'a> Emitter<'a> {
out
}
/// Iter 18c.4: build the IR text for a closure pair's drop fn.
/// build the IR text for a closure pair's drop fn.
/// Layout: { ptr thunk, ptr env } — env at offset 8.
/// Loads env, calls the env drop, then decs the pair box.
pub(crate) fn build_pair_drop_fn(