Skip to content

undefined is not set to 0xAA pattern in Debug mode #25942

Description

@truly-not-taken

Zig Version

0.15.2

Steps to Reproduce and Observed Behavior

An undefined in a mildly complex expression is not set to a debug value of 0xAA pattern.

test "undefined is 0xAA in Debug mode" {
    const baz: u32 = undefined;
    try std.testing.expectEqual(0xAAAAAAAA, baz); // OK

    const bar: u32 = if (true) undefined else 69; // known at comptime
    try std.testing.expectEqual(0xAAAAAAAA, bar); // OK

    var runtime_known = false;
    runtime_known = !runtime_known;
    const foo: u32 = if (runtime_known) undefined else 42;
    try std.testing.expectEqual(0xAAAAAAAA, foo); // FAILS
}

On my linux-x86_64 machine the actual value of foo is sometimes 0x00000001 and sometimes some other garbage.

Documentation implies that undefined bytes are set to 0xAA.

Relevant forum post: https://ziggit.dev/t/reading-a-filled-nullable/13037/9

Expected Behavior

undefined is 0xAA in safety-checked modes even if it comes from a complex expression.

If this actually works as intended I expect the documentation to explain it.

I understand that accessing undefined is Illegal anyway. My concern is usefulness of 0xAA to detect undefined when debugging.

Activity

  1. added
    bugObserved behavior contradicts documented or intended behavior
    on Nov 16, 2025
  2. truly-not-taken commented on Nov 16, 2025

    @truly-not-taken
    Author

    The documentation says:

    However, this behavior is only an implementation feature, not a language semantic, so it is not guaranteed to be observable to code.

    This is vague enough to be ignored by newbies (me including). An example of such absence of guarantee would improve the documentation.

  3. mlugg commented on Nov 16, 2025

    @mlugg
    Member

    An example of such absence of guarantee

    I think it's mainly talking about other compiler implementations and release modes and such; in other words, saying that the Zig language specification does not guarantee this.

    Put differently: this is indeed a bug in the compiler (your report is entirely valid), but it doesn't mean we're implementing the (hypothetical) Zig language specification incorrectly; only that there is a bug in a debugging aid our compiler provides.

  4. added this to the urgent milestone on Nov 16, 2025
  5. aznashwan commented on Nov 16, 2025

    @aznashwan
    Contributor

    Duplicate Related to #24100?

  6. jacobly0 commented on Nov 17, 2025

    @jacobly0
    Member

    I fail to see how this is a backend bug, there's no way to fill in the relevant info from the frontend:

    --- a/src/codegen/x86_64/CodeGen.zig
    +++ b/src/codegen/x86_64/CodeGen.zig
    @@ -177058,7 +177058,9 @@ fn airBr(self: *CodeGen, inst: Air.Inst.Index) !void {
                 try self.getValue(block_tracking.short, br.block_inst);
                 break :dst block_tracking.short;
             };
    -        try self.genCopy(block_ty, dst_mcv, try self.resolveInst(br.operand), .{});
    +        try self.genCopy(block_ty, dst_mcv, try self.resolveInst(br.operand), .{
    +            .safety = ???,
    +        });
             break :result dst_mcv;
         };
  7. added
    frontendTokenization, parsing, AstGen, Sema, and Liveness.
    and removed on Nov 17, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugObserved behavior contradicts documented or intended behaviorfrontendTokenization, parsing, AstGen, Sema, and Liveness.

    Type

    No type

    Projects

    No projects

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions