authorgravatar for thejoshwolfe@gmail.comJosh Wolfe <thejoshwolfe@gmail.com> 2023-07-22 18:52:26-04:00
committergravatar for noreply@github.comGitHub <noreply@github.com> 2023-07-22 18:52:26-04:00
logc72a9feabe455a5bbb5e27cfbd973ff3e6700500
tree20cbb41e5af42c2feb44803a4dfbea2bd5c88b8d
parent2ad16248d7d4352ed9bb7270084042bb76369770
signaturebadge-question-mark Signed by PGP key 4AEE18F83AFDEB23

std.json: support parsing json at comptime using FixedBufferAllocator (#16488)


2 files changed, 27 insertions(+), 2 deletions(-)

lib/std/heap.zig+2-2
...@@ -436,7 +436,7 @@ pub const FixedBufferAllocator = struct {...@@ -436,7 +436,7 @@ pub const FixedBufferAllocator = struct {
436 const self: *FixedBufferAllocator = @ptrCast(@alignCast(ctx));436 const self: *FixedBufferAllocator = @ptrCast(@alignCast(ctx));
437 _ = log2_buf_align;437 _ = log2_buf_align;
438 _ = return_address;438 _ = return_address;
439 assert(self.ownsSlice(buf)); // sanity check439 assert(@inComptime() or self.ownsSlice(buf));
440440
441 if (!self.isLastAllocation(buf)) {441 if (!self.isLastAllocation(buf)) {
442 if (new_size > buf.len) return false;442 if (new_size > buf.len) return false;
...@@ -465,7 +465,7 @@ pub const FixedBufferAllocator = struct {...@@ -465,7 +465,7 @@ pub const FixedBufferAllocator = struct {
465 const self: *FixedBufferAllocator = @ptrCast(@alignCast(ctx));465 const self: *FixedBufferAllocator = @ptrCast(@alignCast(ctx));
466 _ = log2_buf_align;466 _ = log2_buf_align;
467 _ = return_address;467 _ = return_address;
468 assert(self.ownsSlice(buf)); // sanity check468 assert(@inComptime() or self.ownsSlice(buf));
469469
470 if (self.isLastAllocation(buf)) {470 if (self.isLastAllocation(buf)) {
471 self.end_index -= buf.len;471 self.end_index -= buf.len;
lib/std/json/static_test.zig+25
...@@ -901,3 +901,28 @@ test "json parse allocate when streaming" {...@@ -901,3 +901,28 @@ test "json parse allocate when streaming" {
901 try testing.expectEqualSlices(u8, parsed.not_const, "non const string");901 try testing.expectEqualSlices(u8, parsed.not_const, "non const string");
902 try testing.expectEqualSlices(u8, parsed.is_const, "const string");902 try testing.expectEqualSlices(u8, parsed.is_const, "const string");
903}903}
904
905test "parse at comptime" {
906 const doc =
907 \\{
908 \\ "vals": {
909 \\ "testing": 1,
910 \\ "production": 42
911 \\ },
912 \\ "uptime": 9999
913 \\}
914 ;
915 const Config = struct {
916 vals: struct { testing: u8, production: u8 },
917 uptime: u64,
918 };
919 const config = comptime x: {
920 var buf: [32]u8 = undefined;
921 var fba = std.heap.FixedBufferAllocator.init(&buf);
922 const res = parseFromSliceLeaky(Config, fba.allocator(), doc, .{});
923 // Assert no error can occur since we are
924 // parsing this JSON at comptime!
925 break :x res catch unreachable;
926 };
927 comptime testing.expectEqual(@as(u64, 9999), config.uptime) catch unreachable;
928}