From c012cb44938577841f11454d3f44794f460ac059 Mon Sep 17 00:00:00 2001 From: Guillaume Wenzek Date: Tue, 25 Nov 2025 11:13:50 +0100 Subject: [PATCH 1/3] add missing floating point literals --- src/MacroTranslator.zig | 13 +++++++++---- .../f64_integer_suffix_after_float_literal.c | 5 +++++ 2 files changed, 14 insertions(+), 4 deletions(-) create mode 100644 test/cases/translate/f64_integer_suffix_after_float_literal.c diff --git a/src/MacroTranslator.zig b/src/MacroTranslator.zig index 82d0ae4..1f524b2 100644 --- a/src/MacroTranslator.zig +++ b/src/MacroTranslator.zig @@ -350,12 +350,17 @@ fn parseCNumLit(mt: *MacroTranslator) ParseError!ZigNode { if (is_float) { const type_node = try ZigTag.type.create(arena, switch (suffix) { .F16 => "f16", - .F => "f32", - .None => "f64", + .F, .F32 => "f32", + .None, .F32x, .F64 => "f64", .L => "c_longdouble", - .W => "f80", + .W, .F64x => "f80", .Q, .F128 => "f128", - else => unreachable, + .BF16 => "u16", + + else => { + try mt.fail("TODO: float literal suffix: '{s}'", .{suffix_str}); + return error.ParseError; + }, }); const rhs = try ZigTag.float_literal.create(arena, bytes.items); return ZigTag.as.create(arena, .{ .lhs = type_node, .rhs = rhs }); diff --git a/test/cases/translate/f64_integer_suffix_after_float_literal.c b/test/cases/translate/f64_integer_suffix_after_float_literal.c new file mode 100644 index 0000000..3fb7a1e --- /dev/null +++ b/test/cases/translate/f64_integer_suffix_after_float_literal.c @@ -0,0 +1,5 @@ +#define PI_F64 3.141592653589793F64 + +// translate +// +// pub const PI_F64 = @as(f64, 3.141592653589793); From 64a596c1ad793011687f3a2ba3a6914572d46af4 Mon Sep 17 00:00:00 2001 From: Guillaume Wenzek Date: Tue, 25 Nov 2025 11:55:52 +0100 Subject: [PATCH 2/3] convert bf16 to u16 --- src/MacroTranslator.zig | 21 +++++++++++++++++-- .../bf16_suffix_after_float_literal.c | 5 +++++ ...ral.c => f64_suffix_after_float_literal.c} | 0 3 files changed, 24 insertions(+), 2 deletions(-) create mode 100644 test/cases/translate/bf16_suffix_after_float_literal.c rename test/cases/translate/{f64_integer_suffix_after_float_literal.c => f64_suffix_after_float_literal.c} (100%) diff --git a/src/MacroTranslator.zig b/src/MacroTranslator.zig index 1f524b2..c2e5694 100644 --- a/src/MacroTranslator.zig +++ b/src/MacroTranslator.zig @@ -355,8 +355,17 @@ fn parseCNumLit(mt: *MacroTranslator) ParseError!ZigNode { .L => "c_longdouble", .W, .F64x => "f80", .Q, .F128 => "f128", - .BF16 => "u16", - + .BF16 => { + // Zig doesn't support BFloat16, so the best thing we can do is convert it to u16, + // so that the value is bit-to-bit identic between the emitted Zig and original C code. + // https://github.com/ziglang/zig/issues/3148 + const value_u16 = parseBfloat16AsU16(bytes.items); + std.debug.assert(bytes.capacity >= 6); // guaranteed since we allocated literal len + 3 + const bf16_hex = std.fmt.bufPrint(bytes.allocatedSlice(), "0x{x}", .{value_u16}) catch unreachable; + const rhs = try ZigTag.integer_literal.create(arena, bf16_hex); + const type_node = try ZigTag.type.create(arena, "u16"); + return ZigTag.as.create(arena, .{ .lhs = type_node, .rhs = rhs }); + }, else => { try mt.fail("TODO: float literal suffix: '{s}'", .{suffix_str}); return error.ParseError; @@ -1359,3 +1368,11 @@ fn parseCUnaryExpr(mt: *MacroTranslator, scope: *Scope) ParseError!ZigNode { return try mt.parseCPostfixExpr(scope, null); } + +fn parseBfloat16AsU16(bytes: []const u8) u16 { + const value_f32 = std.fmt.parseFloat(f32, bytes) catch math.nan(f32); + var int: u32 = @bitCast(value_f32); + // Round up if needed. + int += 0x8000; + return @truncate(int >> 16); +} diff --git a/test/cases/translate/bf16_suffix_after_float_literal.c b/test/cases/translate/bf16_suffix_after_float_literal.c new file mode 100644 index 0000000..c2ed626 --- /dev/null +++ b/test/cases/translate/bf16_suffix_after_float_literal.c @@ -0,0 +1,5 @@ +#define EXACT_BF16 0.007873535BF16 + +// translate +// +// pub const EXACT_BF16 = @as(u16, 0x3c01); diff --git a/test/cases/translate/f64_integer_suffix_after_float_literal.c b/test/cases/translate/f64_suffix_after_float_literal.c similarity index 100% rename from test/cases/translate/f64_integer_suffix_after_float_literal.c rename to test/cases/translate/f64_suffix_after_float_literal.c From 92fd6d8e297153a7d17c9c9c780c3f2d655e98c7 Mon Sep 17 00:00:00 2001 From: Guillaume Wenzek Date: Tue, 25 Nov 2025 22:13:16 +0100 Subject: [PATCH 3/3] remove bf16 support --- src/MacroTranslator.zig | 19 ------------------- .../bf16_suffix_after_float_literal.c | 5 ----- 2 files changed, 24 deletions(-) delete mode 100644 test/cases/translate/bf16_suffix_after_float_literal.c diff --git a/src/MacroTranslator.zig b/src/MacroTranslator.zig index c2e5694..6280166 100644 --- a/src/MacroTranslator.zig +++ b/src/MacroTranslator.zig @@ -355,17 +355,6 @@ fn parseCNumLit(mt: *MacroTranslator) ParseError!ZigNode { .L => "c_longdouble", .W, .F64x => "f80", .Q, .F128 => "f128", - .BF16 => { - // Zig doesn't support BFloat16, so the best thing we can do is convert it to u16, - // so that the value is bit-to-bit identic between the emitted Zig and original C code. - // https://github.com/ziglang/zig/issues/3148 - const value_u16 = parseBfloat16AsU16(bytes.items); - std.debug.assert(bytes.capacity >= 6); // guaranteed since we allocated literal len + 3 - const bf16_hex = std.fmt.bufPrint(bytes.allocatedSlice(), "0x{x}", .{value_u16}) catch unreachable; - const rhs = try ZigTag.integer_literal.create(arena, bf16_hex); - const type_node = try ZigTag.type.create(arena, "u16"); - return ZigTag.as.create(arena, .{ .lhs = type_node, .rhs = rhs }); - }, else => { try mt.fail("TODO: float literal suffix: '{s}'", .{suffix_str}); return error.ParseError; @@ -1368,11 +1357,3 @@ fn parseCUnaryExpr(mt: *MacroTranslator, scope: *Scope) ParseError!ZigNode { return try mt.parseCPostfixExpr(scope, null); } - -fn parseBfloat16AsU16(bytes: []const u8) u16 { - const value_f32 = std.fmt.parseFloat(f32, bytes) catch math.nan(f32); - var int: u32 = @bitCast(value_f32); - // Round up if needed. - int += 0x8000; - return @truncate(int >> 16); -} diff --git a/test/cases/translate/bf16_suffix_after_float_literal.c b/test/cases/translate/bf16_suffix_after_float_literal.c deleted file mode 100644 index c2ed626..0000000 --- a/test/cases/translate/bf16_suffix_after_float_literal.c +++ /dev/null @@ -1,5 +0,0 @@ -#define EXACT_BF16 0.007873535BF16 - -// translate -// -// pub const EXACT_BF16 = @as(u16, 0x3c01);