Skip to content

compiler crash: const_ptr_pointee_unchecked_no_isf. #7019

Closed
@vrischmann

Description

@vrischmann

Hello,

using Zig version 0.6.0+5430642fa I'm getting the following crash:

Assertion failed at ../src/stage1/ir.cpp:873 in const_ptr_pointee_unchecked_no_isf. This is a bug in the Zig compiler.
/home/vincent/dev/devtools/zig/src/stage1.zig:167:5: 0x9e008c in stage2_panic (zig1)
    @panic(ptr[0..len]);
    ^
../src/stage1/util.cpp:20:17: 0x13b8f4d in zig_panic (../src/stage1/util.cpp)
../src/stage1/util_base.hpp:53:18: 0x14059f1 in zig_assert (../src/stage1/ir.cpp)
../src/stage1/ir.cpp:873:5: 0x1407f6d in const_ptr_pointee_unchecked_no_isf (../src/stage1/ir.cpp)
../src/stage1/ir.cpp:894:46: 0x14080db in const_ptr_pointee_unchecked (../src/stage1/ir.cpp)
../src/stage1/ir.cpp:10602:48: 0x1428681 in const_ptr_pointee (../src/stage1/ir.cpp)
../src/stage1/ir.cpp:22898:48: 0x14557e1 in ir_analyze_instruction_field_ptr (../src/stage1/ir.cpp)
../src/stage1/ir.cpp:31885:52: 0x14781b7 in ir_analyze_instruction_base (../src/stage1/ir.cpp)
../src/stage1/ir.cpp:32208:65: 0x14791b8 in ir_analyze (../src/stage1/ir.cpp)
../src/stage1/ir.cpp:13651:38: 0x1433a7f in ir_eval_const_value (../src/stage1/ir.cpp)
../src/stage1/ir.cpp:20479:43: 0x144c39a in ir_analyze_fn_call (../src/stage1/ir.cpp)
../src/stage1/ir.cpp:20916:43: 0x144e15a in ir_analyze_fn_call_src (../src/stage1/ir.cpp)
../src/stage1/ir.cpp:21163:42: 0x144f03f in ir_analyze_instruction_call (../src/stage1/ir.cpp)
../src/stage1/ir.cpp:31887:47: 0x14781cf in ir_analyze_instruction_base (../src/stage1/ir.cpp)
../src/stage1/ir.cpp:32208:65: 0x14791b8 in ir_analyze (../src/stage1/ir.cpp)
../src/stage1/analyze.cpp:4987:44: 0x14c5d56 in analyze_fn_ir (../src/stage1/analyze.cpp)
../src/stage1/analyze.cpp:5103:18: 0x14c6309 in analyze_fn_body (../src/stage1/analyze.cpp)
../src/stage1/analyze.cpp:5215:28: 0x14c6b16 in semantic_analyze (../src/stage1/analyze.cpp)
../src/stage1/codegen.cpp:9258:25: 0x13dfab8 in gen_root_source (../src/stage1/codegen.cpp)
../src/stage1/codegen.cpp:9307:20: 0x13dfe0c in codegen_build_object (../src/stage1/codegen.cpp)
../src/stage1/stage1.cpp:126:25: 0x13b4d0e in zig_stage1_build_object (../src/stage1/stage1.cpp)
/home/vincent/dev/devtools/zig/src/stage1.zig:139:32: 0xccd2e4 in Module.build_object (zig1)
        zig_stage1_build_object(mod);
                               ^
/home/vincent/dev/devtools/zig/src/Compilation.zig:2799:31: 0xb3e8f7 in Compilation.updateStage1Module (zig1)
    stage1_module.build_object();
                              ^
/home/vincent/dev/devtools/zig/src/Compilation.zig:1386:36: 0xafcad3 in Compilation.performAllTheWork (zig1)
            self.updateStage1Module(main_progress_node) catch |err| {
                                   ^
/home/vincent/dev/devtools/zig/src/Compilation.zig:1088:31: 0xaf6d87 in Compilation.update (zig1)
    try self.performAllTheWork();
                              ^
/home/vincent/dev/devtools/zig/src/main.zig:1843:20: 0xaaf096 in main.updateModule (zig1)
    try comp.update();
                   ^
/home/vincent/dev/devtools/zig/src/main.zig:1710:21: 0xa062ec in main.buildOutputType (zig1)
    try updateModule(gpa, comp, zir_out_path, hook);
                    ^
/home/vincent/dev/devtools/zig/src/main.zig:165:31: 0x9def66 in main.mainArgs (zig1)
        return buildOutputType(gpa, arena, args, .zig_test);
                              ^
/home/vincent/dev/devtools/zig/src/stage1.zig:45:24: 0x9de77e in main (zig1)
        stage2.mainArgs(gpa, arena, args) catch unreachable;

with this code (it's a little long sorry, I was unable to make a shorter reproducer):

const builtin = @import("builtin");
const std = @import("std");
const mem = std.mem;

pub const BindMarker = union(enum) {
    Type: type,
    NoType: void,
};

pub const ParsedQuery = struct {
    const Self = @This();

    bind_markers: [128]BindMarker,
    nb_bind_markers: usize,

    query: [1024]u8,
    query_size: usize,

    fn from(comptime query: []const u8) Self {
        const State = enum {
            Start,
            BindMarker,
            BindMarkerType,
        };

        comptime var buf: [query.len]u8 = undefined;
        comptime var pos = 0;
        comptime var state = .Start;

        comptime var current_bind_marker_type: [256]u8 = undefined;
        comptime var current_bind_marker_type_pos = 0;

        comptime var parsed_query: ParsedQuery = undefined;
        parsed_query.nb_bind_markers = 0;

        inline for (query) |c, i| {
            switch (state) {
                .Start => switch (c) {
                    '?' => {
                        state = .BindMarker;
                        buf[pos] = c;
                    },
                    else => {
                        buf[pos] = c;
                    },
                },
                .BindMarker => switch (c) {
                    '{' => {
                        state = .BindMarkerType;
                        current_bind_marker_type_pos = 0;
                    },
                    else => {
                        @compileError("a bind marker start (the character ?) must be followed by a bind marker type, eg {integer}");
                    },
                },
                .BindMarkerType => switch (c) {
                    '}' => {
                        state = .Start;

                        const typ = parsed_query.parseType(current_bind_marker_type[0..current_bind_marker_type_pos]);

                        parsed_query.bind_markers[parsed_query.nb_bind_markers].Type = BindMarker{ .Type = typ };
                        parsed_query.nb_bind_markers += 1;
                    },
                    else => {
                        current_bind_marker_type[current_bind_marker_type_pos] = c;
                        current_bind_marker_type_pos += 1;
                    },
                },
                else => {
                    @compileError("invalid state " ++ @tagName(state));
                },
            }

            pos += 1;
        }

        mem.copy(u8, &parsed_query.query, &buf);
        parsed_query.query_size = pos;

        return parsed_query;
    }

    fn parseType(comptime self: *Self, type_info: []const u8) type {
        if (type_info.len <= 0) @compileError("invalid type info " ++ type_info);

        // Integer
        if (mem.eql(u8, "usize", type_info)) return usize;
        if (mem.eql(u8, "isize", type_info)) return isize;

        if (type_info[0] == 'u' or type_info[0] == 'i') {
            return @Type(builtin.TypeInfo{
                .Int = builtin.TypeInfo.Int{
                    .is_signed = type_info[0] == 'i',
                    .bits = std.fmt.parseInt(usize, type_info[1..type_info.len], 10) catch {
                        @compileError("invalid type info " ++ type_info);
                    },
                },
            });
        }

        @compileError("invalid type info " ++ type_info);
    }

    fn getQuery(comptime self: *Self) []const u8 {
        return self.query[0..self.query_size];
    }
};

test "parsed query" {
    const query = "INSERT INTO user(id, name, age) VALUES(?{i32}, ?{usize}, ?{})";

    comptime var parsed_query = ParsedQuery.from(query);
    std.debug.print("parsed query: {}\n", .{parsed_query});
    std.debug.print("parsed query: {}\n", .{parsed_query.getQuery()});
}

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugObserved behavior contradicts documented or intended behaviorstage1The process of building from source via WebAssembly and the C backend.

    Type

    No type

    Projects

    No projects

    Milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions