From e95f46eeffbb80b6fd3aee699c5189516e20ffb7 Mon Sep 17 00:00:00 2001 From: Motiejus Date: Thu, 26 Feb 2026 05:21:49 +0000 Subject: [PATCH] =?UTF-8?q?sema:=20fix=20ZIR=E2=86=92IP=20signedness=20inv?= =?UTF-8?q?ersion,=20resolve=20Signedness/AddressSpace=20types?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit ZIR uses the Zig Signedness enum convention (signed=0, unsigned=1) while the InternPool uses the inverted convention (unsigned=0, signed=1). Fix both places that read signedness from ZIR: resolveEnumDeclFromZir (for explicit enum tag types) and zirIntType (for int_type instructions). Add resolveBuiltinDeclTypes() to resolve BuiltinDecl types from std.builtin in order, matching Sema.zig's analyzeMemoizedState. Currently resolves Signedness and AddressSpace, creating IP entries $213-$251. Co-Authored-By: Claude Opus 4.6 --- stage0/sema.c | 42 ++++++++++++++++++++++++++++++++++++++---- 1 file changed, 38 insertions(+), 4 deletions(-) diff --git a/stage0/sema.c b/stage0/sema.c index 2afa2b29fa..f0286bee1d 100644 --- a/stage0/sema.c +++ b/stage0/sema.c @@ -2775,13 +2775,16 @@ static InternPoolIndex resolveEnumDeclFromZir( if (tt_inst < zir->inst_len && zir->inst_tags[tt_inst] == ZIR_INST_INT_TYPE) { uint16_t bits = zir->inst_datas[tt_inst].int_type.bit_count; - uint8_t signedness + // ZIR uses Zig Signedness enum: signed=0, unsigned=1. + // IP uses: unsigned=0, signed=1. Invert. + uint8_t zir_sign = zir->inst_datas[tt_inst].int_type.signedness; + uint8_t ip_sign = (zir_sign == 0) ? 1 : 0; InternPoolKey itk; memset(&itk, 0, sizeof(itk)); itk.tag = IP_KEY_INT_TYPE; itk.data.int_type.bits = bits; - itk.data.int_type.signedness = signedness; + itk.data.int_type.signedness = ip_sign; int_tag_type = ipIntern(s_module_ip, itk); } } @@ -3073,6 +3076,28 @@ static void internStringLiteral(const char* str) { (void)ipIntern(s_module_ip, bytes2_key); } +// --- resolveBuiltinDeclTypes --- +// Resolve BuiltinDecl types from std.builtin namespace. +// Ported from Sema.zig analyzeMemoizedState (main stage). +// This resolves types in BuiltinDecl order: Signedness, AddressSpace, +// CallingConvention, etc. +static void resolveBuiltinDeclTypes(uint32_t builtin_ns_idx) { + // BuiltinDecl types in order (main stage only). + // Each is looked up in std.builtin and resolved. + static const char* const builtin_type_names[] = { + "Signedness", + "AddressSpace", + }; + uint32_t n_types + = sizeof(builtin_type_names) / sizeof(builtin_type_names[0]); + for (uint32_t i = 0; i < n_types; i++) { + uint32_t nav + = findNavInNamespace(builtin_ns_idx, builtin_type_names[i]); + if (nav != UINT32_MAX) + (void)ensureNavValUpToDate(nav); + } +} + // --- resolveStartComptimePreamble --- // Create the IP entries that the Zig compiler generates when processing // start.zig's comptime block. This block evaluates builtin.zig_backend @@ -3194,6 +3219,12 @@ static void resolveStartComptimePreamble(void) { // start.zig's else branch evaluates @hasDecl(root, "main") which // triggers interning of the string literal "main". internStringLiteral("main"); + + // --- $213+: BuiltinDecl type resolution --- + // The Zig compiler calls analyzeMemoizedState which resolves types + // from std.builtin in BuiltinDecl order. Port this by resolving each + // declaration via ensureNavValUpToDate. + resolveBuiltinDeclTypes(builtin_ns_idx); } // --- findDeclImportPathFromZir --- @@ -9142,13 +9173,16 @@ static void zirUnreachable(Sema* sema, SemaBlock* block, uint32_t inst) { // --- zirIntType --- // Ported from src/Sema.zig zirIntType. static AirInstRef zirIntType(Sema* sema, uint32_t inst) { - uint8_t signedness = sema->code.inst_datas[inst].int_type.signedness; + // ZIR uses Zig Signedness enum: signed=0, unsigned=1. + // IP uses: unsigned=0, signed=1. Invert. + uint8_t zir_sign = sema->code.inst_datas[inst].int_type.signedness; + uint8_t ip_sign = (zir_sign == 0) ? 1 : 0; uint16_t bit_count = sema->code.inst_datas[inst].int_type.bit_count; InternPoolKey key; memset(&key, 0, sizeof(key)); key.tag = IP_KEY_INT_TYPE; key.data.int_type.bits = bit_count; - key.data.int_type.signedness = signedness; + key.data.int_type.signedness = ip_sign; return AIR_REF_FROM_IP(ipIntern(sema->ip, key)); }