From c1f0c64757928756b94198dfccab530842f04d3d Mon Sep 17 00:00:00 2001 From: David Gonzalez Martin Date: Sun, 23 Mar 2025 13:13:15 +0100 Subject: [PATCH] Add implicit backing type for 'bits' type --- src/compiler.bbb | 26 +++++++++++++++++++++ src/converter.zig | 42 ++++++++++++++++++++++------------ src/converter_test.zig | 4 ++++ tests/bits_no_backing_type.bbb | 13 +++++++++++ 4 files changed, 71 insertions(+), 14 deletions(-) create mode 100644 tests/bits_no_backing_type.bbb diff --git a/src/compiler.bbb b/src/compiler.bbb index 6fe2fb7..d192d43 100644 --- a/src/compiler.bbb +++ b/src/compiler.bbb @@ -1,3 +1,18 @@ +OSProtectionFlags = bits +{ + read: u1, + write: u1, + execute: u1, +} + +OSMapFlags = bits +{ + private: u1, + anonymous: u1, + no_reserve: u1, + populate: u1, +} + Arena = struct { reserved_size: u64, @@ -9,6 +24,17 @@ Arena = struct minimum_position: u64 = #byte_size(Arena); +ArenaInitialization = struct +{ + reserved_size: u64, + granularity: u64, + initial_size: u64, +} + +arena_initialize = fn (initialization: ArenaInitialization) &Arena +{ +} + [export] main = fn [cc(c)] () s32 { return 0; diff --git a/src/converter.zig b/src/converter.zig index bf3fe58..f700f13 100644 --- a/src/converter.zig +++ b/src/converter.zig @@ -5151,22 +5151,18 @@ pub noinline fn convert(arena: *Arena, options: ConvertOptions) void { }; }, .bits => { - // TODO: allow implicit backing type? - const backing_type = converter.parse_type(module); - if (backing_type.bb != .integer) { - converter.report_error(); - } - - if (backing_type.get_bit_size() > 64) { - converter.report_error(); - } + const allow_implicit_type = converter.content[converter.offset] == left_brace; + const maybe_backing_type: ?*Type = switch (allow_implicit_type) { + true => null, + false => converter.parse_type(module), + }; converter.skip_space(); converter.expect_character(left_brace); var field_buffer: [128]Field = undefined; - var llvm_debug_field_buffer: [128]*llvm.DI.Type.Derived = undefined; + var field_line_buffer: [128]u32 = undefined; var field_count: usize = 0; var field_bit_offset: u64 = 0; @@ -5179,6 +5175,7 @@ pub noinline fn convert(arena: *Arena, options: ConvertOptions) void { } const field_line = converter.get_line(); + field_line_buffer[field_count] = field_line; const field_name = converter.parse_identifier(); @@ -5199,10 +5196,9 @@ pub noinline fn convert(arena: *Arena, options: ConvertOptions) void { const field_bit_size = field_type.get_bit_size(); - if (module.llvm.di_builder) |di_builder| { - const member_type = di_builder.create_bit_field_member_type(module.llvm.global_scope, field_name, module.llvm.file, field_line, field_bit_size, field_bit_offset, 0, .{}, backing_type.llvm.debug); - llvm_debug_field_buffer[field_count] = member_type; - } + // if (module.llvm.di_builder) |di_builder| { + // llvm_debug_field_buffer[field_count] = member_type; + // } field_bit_offset += field_bit_size; @@ -5216,11 +5212,29 @@ pub noinline fn convert(arena: *Arena, options: ConvertOptions) void { const fields = module.arena.allocate(Field, field_count); @memcpy(fields, field_buffer[0..field_count]); + const field_lines = field_line_buffer[0..field_count]; + + const backing_type = if (maybe_backing_type) |bt| bt else module.integer_type(@intCast(@max(8, lib.next_power_of_two(field_bit_offset))), false); + if (backing_type.bb != .integer) { + converter.report_error(); + } + + if (backing_type.get_bit_size() > 64) { + converter.report_error(); + } + const bit_size = backing_type.get_bit_size(); const bit_alignment = backing_type.get_bit_alignment(); + var llvm_debug_field_buffer: [128]*llvm.DI.Type.Derived = undefined; const debug_member_types = llvm_debug_field_buffer[0..field_count]; + if (module.llvm.di_builder) |di_builder| { + for (fields, debug_member_types, field_lines) |field, *debug_member_type, field_line| { + debug_member_type.* = di_builder.create_bit_field_member_type(module.llvm.global_scope, field.name, module.llvm.file, field_line, field.type.get_bit_size(), field_bit_offset, 0, .{}, backing_type.llvm.debug); + } + } + _ = module.types.add(.{ .name = global_name, .llvm = .{ diff --git a/src/converter_test.zig b/src/converter_test.zig index 081683c..430d23d 100644 --- a/src/converter_test.zig +++ b/src/converter_test.zig @@ -372,3 +372,7 @@ test "varargs" { test "byte_size" { try invsrc(@src()); } + +test "bits_no_backing_type" { + try invsrc(@src()); +} diff --git a/tests/bits_no_backing_type.bbb b/tests/bits_no_backing_type.bbb new file mode 100644 index 0000000..7dea283 --- /dev/null +++ b/tests/bits_no_backing_type.bbb @@ -0,0 +1,13 @@ +A = bits { + a: u1, + b: u1, +} + +[export] main = fn [cc(c)] () s32 +{ + >a: A = { + .a = 1, + .b = 1, + }; + return #extend(a.a - a.b); +}