mirror of
https://github.com/ziglang/zig.git
synced 2024-11-23 12:50:13 +00:00
translate-c: Fix issues translating macro define of hex float constant
* Fix incorrect result when the first digit after the decimal point is not 0-9 - eg 0x0.ap0 * Fix compiler panic when the number starts with `0X` with a capital `X` - eg 0X0p0 * Fix compiler panic when the number has a decimal point immediately after `0x` - eg 0x.0p0
This commit is contained in:
parent
0d0f277954
commit
aa5514fcf2
@ -5603,7 +5603,25 @@ fn parseCNumLit(c: *Context, m: *MacroCtx) ParseError!Node {
|
||||
.FloatLiteral => |suffix| {
|
||||
if (suffix != .none) lit_bytes = lit_bytes[0 .. lit_bytes.len - 1];
|
||||
|
||||
if (mem.indexOfScalar(u8, lit_bytes, '.')) |dot_index| {
|
||||
if (lit_bytes.len >= 2 and std.ascii.eqlIgnoreCase(lit_bytes[0..2], "0x")) {
|
||||
if (mem.indexOfScalar(u8, lit_bytes, '.')) |dot_index| {
|
||||
if (dot_index == 2) {
|
||||
lit_bytes = try std.fmt.allocPrint(c.arena, "0x0{s}", .{lit_bytes[2..]});
|
||||
} else if (dot_index + 1 == lit_bytes.len or !std.ascii.isXDigit(lit_bytes[dot_index + 1])) {
|
||||
// If the literal lacks a digit after the `.`, we need to
|
||||
// add one since `0x1.p10` would be invalid syntax in Zig.
|
||||
lit_bytes = try std.fmt.allocPrint(c.arena, "0x{s}0{s}", .{
|
||||
lit_bytes[2 .. dot_index + 1],
|
||||
lit_bytes[dot_index + 1 ..],
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
if (lit_bytes[1] == 'X') {
|
||||
// Hexadecimal with capital X, valid in C but not in Zig
|
||||
lit_bytes = try std.fmt.allocPrint(c.arena, "0x{s}", .{lit_bytes[2..]});
|
||||
}
|
||||
} else if (mem.indexOfScalar(u8, lit_bytes, '.')) |dot_index| {
|
||||
if (dot_index == 0) {
|
||||
lit_bytes = try std.fmt.allocPrint(c.arena, "0{s}", .{lit_bytes});
|
||||
} else if (dot_index + 1 == lit_bytes.len or !std.ascii.isDigit(lit_bytes[dot_index + 1])) {
|
||||
|
@ -1137,6 +1137,7 @@ pub fn addCases(cases: *tests.TranslateCContext) void {
|
||||
\\#define BAR .12345
|
||||
\\#define baz 1e1
|
||||
\\#define BAZ 42e-3f
|
||||
\\#define foobar -73.L
|
||||
, &[_][]const u8{
|
||||
"pub const foo = @as(f32, 3.14);",
|
||||
"pub const bar = @as(c_longdouble, 16.0e-2);",
|
||||
@ -1144,6 +1145,21 @@ pub fn addCases(cases: *tests.TranslateCContext) void {
|
||||
"pub const BAR = 0.12345;",
|
||||
"pub const baz = 1e1;",
|
||||
"pub const BAZ = @as(f32, 42e-3);",
|
||||
"pub const foobar = -@as(c_longdouble, 73.0);",
|
||||
});
|
||||
|
||||
cases.add("macro defines hexadecimal float",
|
||||
\\#define FOO 0xf7p38
|
||||
\\#define BAR -0X8F.BP5F
|
||||
\\#define FOOBAR 0X0P+0
|
||||
\\#define BAZ -0x.0a5dp+12
|
||||
\\#define FOOBAZ 0xfE.P-1l
|
||||
, &[_][]const u8{
|
||||
"pub const FOO = 0xf7p38;",
|
||||
"pub const BAR = -@as(f32, 0x8F.BP5);",
|
||||
"pub const FOOBAR = 0x0P+0;",
|
||||
"pub const BAZ = -0x0.0a5dp+12;",
|
||||
"pub const FOOBAZ = @as(c_longdouble, 0xfE.0P-1);",
|
||||
});
|
||||
|
||||
cases.add("comments",
|
||||
|
Loading…
Reference in New Issue
Block a user