commit f6144f7b9232f9bf220a6f87a34d9e9ecee3f0c5 (tree)
parent ae00e4293104b83014ee33629b85e7be6050552a
Author: Motiejus Jakštys <motiejus@jakstys.lt>
Date: Sun, 15 Feb 2026 09:42:08 +0000
astgen: fix optional.zig corpus - callExpr fullBodyExpr, comptimeExpr rvalue, restoreErrRetIndex ctx
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Diffstat:
2 files changed, 33 insertions(+), 16 deletions(-)
diff --git a/stage0/.claude/skills/port-astgen/worker-prompt.md b/stage0/.claude/skills/port-astgen/worker-prompt.md
@@ -54,8 +54,7 @@ Focus on differences that affect output:
- String table entries
- Break payload values (operand_src_node)
-Do NOT guess. Read both implementations completely and compare
-mechanically.
+Do NOT guess. Read both implementations completely and compare mechanically.
### Step 4: Port the fix
@@ -68,12 +67,21 @@ Apply the minimal mechanical change to `astgen.c` to match the upstream. Run
- `string_bytes_len` diff decreased
- First tag mismatch position moved later
+You should mark progress marker (whatever it is from the above) *in/near the
+comment of the skipped test*.
+
+Once there is *any* progress, you MUST clean up and commit per sections below.
+Do not try to fix everything at once -- clean up & commit early & often.
+
### Step 5: Clean up
1. Remove ALL `fprintf`/`printf` debug statements from `astgen.c`.
2. Remove `#include <stdio.h>` if it was added for debugging.
3. If the test still fails: re-add the `if (true) return error.SkipZigTest;`
line with a TODO comment describing the remaining diff.
+4. Test if other compilers or valgrind did not regress, fix if it did:
+
+ zig build fmt-zig0 && zig build all-zig0 -Dvalgrind |& grep -v Warning
### Step 6: Return result
@@ -93,7 +101,7 @@ COMMIT_MSG: <one-line descriptive message about what was ported/fixed>
- **Mechanical copy only.** Do not invent new approaches. If the upstream does
X, do X in C.
- **Never remove zig-cache.**
-- **Never print to stdout/stderr in committed code.** Debug prints are
+- **NEVER print to stdout/stderr in committed code.** Debug prints are
temporary only.
- **Functions must appear in the same order as in the upstream Zig file.**
- **Prefer finding systematic differences for catching bugs** instead of
diff --git a/stage0/astgen.c b/stage0/astgen.c
@@ -9,7 +9,6 @@
#include <assert.h>
#include <stdlib.h>
#include <string.h>
-
// --- Declaration.Flags.Id enum (Zir.zig:2724) ---
typedef enum {
@@ -581,6 +580,7 @@ static uint32_t reserveInstructionIndex(AstGenCtx* ag) {
memset(&ag->inst_datas[idx], 0, sizeof(ZirInstData));
ag->inst_tags[idx] = (ZirInstTag)0;
ag->inst_len++;
+ (void)idx; /* debug: used in trace below when enabled */
return idx;
}
@@ -2918,7 +2918,7 @@ static uint32_t comptimeExpr(
case AST_NODE_IDENTIFIER: {
uint32_t prim = tryResolvePrimitiveIdent(gz, node);
if (prim != ZIR_REF_NONE)
- return prim;
+ return rvalue(gz, rl, prim, node);
break; // non-primitive: fall through to block_comptime wrapping
}
case AST_NODE_NUMBER_LITERAL:
@@ -6200,7 +6200,7 @@ static uint32_t callExpr(
for (uint32_t i = 0; i < args_len; i++) {
GenZir arg_block = makeSubBlock(gz, scope);
uint32_t arg_ref
- = exprRl(&arg_block, &arg_block.base, arg_rl, args[i]);
+ = fullBodyExpr(&arg_block, &arg_block.base, arg_rl, args[i]);
// break_inline with param_node src (AstGen.zig:10108).
int32_t param_src
@@ -11062,15 +11062,25 @@ static void restoreErrRetIndex(GenZir* gz, uint32_t block_inst, ResultLoc rl,
if (eval == EVAL_TO_ERROR_NEVER) {
op = ZIR_REF_NONE; // always restore/pop
} else {
- // EVAL_TO_ERROR_MAYBE
- // Simplified: without ri.ctx, treat non-ptr RL as result
- // (AstGen.zig:2131-2144).
- if (rl.tag == RL_PTR) {
- op = addUnNode(gz, ZIR_INST_LOAD, rl.data, node);
- } else if (rl.tag == RL_INFERRED_PTR) {
- op = ZIR_REF_NONE;
- } else {
- op = result;
+ // EVAL_TO_ERROR_MAYBE (AstGen.zig:2131-2144).
+ switch (rl.ctx) {
+ case RI_CTX_ERROR_HANDLING_EXPR:
+ case RI_CTX_RETURN:
+ case RI_CTX_FN_ARG:
+ case RI_CTX_CONST_INIT:
+ if (rl.tag == RL_PTR) {
+ op = addUnNode(gz, ZIR_INST_LOAD, rl.data, node);
+ } else if (rl.tag == RL_INFERRED_PTR) {
+ op = ZIR_REF_NONE;
+ } else if (rl.tag == RL_DESTRUCTURE) {
+ return; // value must be a tuple or array, so never restore/pop
+ } else {
+ op = result;
+ }
+ break;
+ default:
+ op = ZIR_REF_NONE; // always restore/pop
+ break;
}
}
addRestoreErrRetIndexBlock(gz, block_inst, op, node);
@@ -16917,7 +16927,6 @@ Zir astGen(const Ast* ast) {
AstGenCtx ag;
memset(&ag, 0, sizeof(ag));
ag.tree = ast;
-
// Initial allocations (AstGen.zig:162-172).
uint32_t nodes_len = ast->nodes.len;
uint32_t init_cap = nodes_len > 8 ? nodes_len : 8;