Files
sx/examples/optionals/0914-optionals-typed-array-literal-null-element.sx
agra 28bb101a4a fix: literal element typing — typed-array null element, tuple coercion, positional var element (0173-0175)
0173: resolveArrayLiteralType gained no arm for [N]T/[]T heads, so a
([2]?i64).[...] head lost its ?i64 element type and a bare null reached
LLVM as const_null(.unresolved). Route structural heads through
resolveTypeWithBindings; validate an undefined element name in the head
via UnknownTypeChecker (semantic_diagnostics.zig) instead of a silent
empty-struct stub (no-silent-fallback).

0174: positional .{...} against a TUPLE target now coerces each element
to TupleInfo.fields[i] (was neither struct nor array, so uncoerced).

0175: a positional struct literal with a bare-variable element was
misclassified as a named shorthand (parser puns .{x} -> x=x), zeroing
the fields. has_names now consults the struct definition to reclassify a
punned non-field name as positional; positional coercion uses the
lowered value's real getRefType.

Regressions: optionals/0914, types/0199, types/0200, diagnostics/1196.
Verified by 4 adversarial reviews; suite 784/0. Filed adjacent bug 0176
(protocol-typed struct field method call aborts).
2026-06-23 00:25:28 +03:00

33 lines
1.2 KiB
Plaintext

// Typed `.[ ... ]` array literal whose element type is an optional and whose
// elements include a bare `null` resolve the element type from the literal's
// type head, so `null` lowers as `const_null(?T)` (not `.unresolved`).
//
// Regression (issue 0173): `([N]?T).[ ... ]` reached LLVM with an
// `.unresolved`-typed `const_null` and panicked, because the array-literal
// type-head resolver had no arm for an `array_type_expr`/`slice_type_expr`
// head — the `?T` element type was lost.
#import "modules/std.sx";
Pt :: struct { x: i64 = 0; y: i64 = 0; }
main :: () {
a := ([2]?i64).[ null, 7 ];
print("{}\n", a[1] ?? -1); // 7
b := ([3]?i64).[ null, null, 5 ];
print("{} {} {}\n", b[0] ?? -1, b[1] ?? -1, b[2] ?? -1); // -1 -1 5
// Optional struct payload element + a bare null sibling.
c := ([2]?Pt).[ null, .{ x = 1, y = 2 } ];
p := c[1] ?? Pt.{};
print("{} {}\n", p.x, p.y); // 1 2
// A typed slice head `[]?T` with a null element resolves too.
s : []?i64 = .[ null, 3 ];
print("{}\n", s[1] ?? -1); // 3
// A non-optional typed `.[...]` array still works (no regression).
d := ([3]i64).[ 1, 2, 3 ];
print("{} {} {}\n", d[0], d[1], d[2]); // 1 2 3
}