diff options
| author | Jimmi Holst Christensen <jhc@dismail.de> | 2022-11-19 10:54:43 +0100 |
|---|---|---|
| committer | Andrew Kelley <andrew@ziglang.org> | 2022-11-19 11:59:33 -0500 |
| commit | adc3fafbc0c46485ae6c218bc791019741b7536c (patch) | |
| tree | 4e1df792c1719d228a2671eb8b3e98e0974b88dd /src/codegen | |
| parent | f746e118795af8f8eb16deefc8f6fed26f3be4dd (diff) | |
| download | zig-adc3fafbc0c46485ae6c218bc791019741b7536c.tar.gz zig-adc3fafbc0c46485ae6c218bc791019741b7536c.zip | |
c backend: Output string literals for array init of bytes
Diffstat (limited to 'src/codegen')
| -rw-r--r-- | src/codegen/c.zig | 87 |
1 files changed, 63 insertions, 24 deletions
diff --git a/src/codegen/c.zig b/src/codegen/c.zig index f582fe7eb1..a06f8e76dd 100644 --- a/src/codegen/c.zig +++ b/src/codegen/c.zig @@ -740,14 +740,24 @@ pub const DeclGen = struct { try writer.writeByte(')'); } - try writer.writeByte('{'); - const c_len = ty.arrayLenIncludingSentinel(); - var index: usize = 0; - while (index < c_len) : (index += 1) { - if (index > 0) try writer.writeAll(", "); - try dg.renderValue(writer, ty.childType(), val, .Initializer); + const ai = ty.arrayInfo(); + if (ai.elem_type.eql(Type.u8, dg.module)) { + try writer.writeByte('"'); + const c_len = ty.arrayLenIncludingSentinel(); + var index: usize = 0; + while (index < c_len) : (index += 1) + try writeStringLiteralChar(writer, 0xaa); + return writer.writeByte('"'); + } else { + try writer.writeByte('{'); + const c_len = ty.arrayLenIncludingSentinel(); + var index: usize = 0; + while (index < c_len) : (index += 1) { + if (index > 0) try writer.writeAll(", "); + try dg.renderValue(writer, ty.childType(), val, .Initializer); + } + return writer.writeByte('}'); } - return writer.writeByte('}'); }, .ComptimeInt, .ComptimeFloat, @@ -931,25 +941,48 @@ pub const DeclGen = struct { } try writer.writeByte('}'); }, + .bytes => { + try writer.print("{s}", .{fmtStringLiteral(val.castTag(.bytes).?.data)}); + }, + .str_lit => { + const str_lit = val.castTag(.str_lit).?.data; + const bytes = dg.module.string_literal_bytes.items[str_lit.index..][0..str_lit.len]; + try writer.print("{s}", .{fmtStringLiteral(bytes)}); + }, else => { // Fall back to generic implementation. var arena = std.heap.ArenaAllocator.init(dg.gpa); defer arena.deinit(); const arena_allocator = arena.allocator(); - try writer.writeByte('{'); const ai = ty.arrayInfo(); - var index: usize = 0; - while (index < ai.len) : (index += 1) { - if (index != 0) try writer.writeByte(','); - const elem_val = try val.elemValue(dg.module, arena_allocator, index); - try dg.renderValue(writer, ai.elem_type, elem_val, .Initializer); - } - if (ai.sentinel) |s| { - if (index != 0) try writer.writeByte(','); - try dg.renderValue(writer, ai.elem_type, s, .Initializer); + if (ai.elem_type.eql(Type.u8, dg.module)) { + try writer.writeByte('"'); + var index: usize = 0; + while (index < ai.len) : (index += 1) { + const elem_val = try val.elemValue(dg.module, arena_allocator, index); + const elem_val_u8 = @intCast(u8, elem_val.toUnsignedInt(target)); + try writeStringLiteralChar(writer, elem_val_u8); + } + if (ai.sentinel) |s| { + const s_u8 = @intCast(u8, s.toUnsignedInt(target)); + try writeStringLiteralChar(writer, s_u8); + } + try writer.writeByte('"'); + } else { + try writer.writeByte('{'); + var index: usize = 0; + while (index < ai.len) : (index += 1) { + if (index != 0) try writer.writeByte(','); + const elem_val = try val.elemValue(dg.module, arena_allocator, index); + try dg.renderValue(writer, ai.elem_type, elem_val, .Initializer); + } + if (ai.sentinel) |s| { + if (index != 0) try writer.writeByte(','); + try dg.renderValue(writer, ai.elem_type, s, .Initializer); + } + try writer.writeByte('}'); } - try writer.writeByte('}'); }, } }, @@ -5618,7 +5651,17 @@ fn formatStringLiteral( ) @TypeOf(writer).Error!void { if (fmt.len != 1 or fmt[0] != 's') @compileError("Invalid fmt: " ++ fmt); try writer.writeByte('\"'); - for (str) |c| switch (c) { + for (str) |c| + try writeStringLiteralChar(writer, c); + try writer.writeByte('\"'); +} + +fn fmtStringLiteral(str: []const u8) std.fmt.Formatter(formatStringLiteral) { + return .{ .data = str }; +} + +fn writeStringLiteralChar(writer: anytype, c: u8) !void { + switch (c) { 7 => try writer.writeAll("\\a"), 8 => try writer.writeAll("\\b"), '\t' => try writer.writeAll("\\t"), @@ -5631,11 +5674,7 @@ fn formatStringLiteral( ' '...'~' => try writer.writeByte(c), else => try writer.print("\\{o:0>3}", .{c}), }, - }; - try writer.writeByte('\"'); -} -fn fmtStringLiteral(str: []const u8) std.fmt.Formatter(formatStringLiteral) { - return .{ .data = str }; + } } fn undefPattern(comptime IntType: type) IntType { |
