authorgravatar for mason@anthropicstudios.comMason Remaley <mason@anthropicstudios.com> 2025-08-25 06:03:08-10:00
committergravatar for noreply@github.comGitHub <noreply@github.com> 2025-08-25 18:03:08+02:00
log5a0cf217756491169579b301a676a655b04f489b
tree5aee6a6ebf78125c47f657ba76fc34eacad56b40
parent37f4bee92a78fa4543d723b834a1570e2dd38a13
signaturebadge-check Signed by PGP key B5690EEEBB952194

Adds non allocating alternatives to ZON parse functions (#22916)

* Adds "flat" alternatives to zon.parse.from* that don't support pointers * Fixes documentation * Removes flat postfix from non allocating functions, adds alloc to others * Stops using alloc variant in tests where not needed

1 files changed, 192 insertions(+), 96 deletions(-)

lib/std/zon/parse.zig+192-96
...@@ -1,11 +1,12 @@...@@ -1,11 +1,12 @@
1//! The simplest way to parse ZON at runtime is to use `fromSlice`. If you need to parse ZON at1//! The simplest way to parse ZON at runtime is to use `fromSlice`/`fromSliceAlloc`.
2//! compile time, you may use `@import`.2//!
3//! Note that if you need to parse ZON at compile time, you may use `@import`.
3//!4//!
4//! Parsing from individual Zoir nodes is also available:5//! Parsing from individual Zoir nodes is also available:
5//! * `fromZoir`6//! * `fromZoir`/`fromZoirAlloc`
6//! * `fromZoirNode`7//! * `fromZoirNode`/`fromZoirNodeAlloc`
7//!8//!
8//! For lower level control, it is possible to operate on `std.zig.Zoir` directly.9//! For lower level control over parsing, see `std.zig.Zoir`.
910
10const std = @import("std");11const std = @import("std");
11const builtin = @import("builtin");12const builtin = @import("builtin");
...@@ -254,7 +255,25 @@ pub const Diagnostics = struct {...@@ -254,7 +255,25 @@ pub const Diagnostics = struct {
254///255///
255/// When the parser returns `error.ParseZon`, it will also store a human readable explanation in256/// When the parser returns `error.ParseZon`, it will also store a human readable explanation in
256/// `diag` if non null. If diag is not null, it must be initialized to `.{}`.257/// `diag` if non null. If diag is not null, it must be initialized to `.{}`.
258///
259/// Asserts at compile time that the result type doesn't contain pointers. As such, the result
260/// doesn't need to be freed.
261///
262/// An allocator is still required for temporary allocations made during parsing.
257pub fn fromSlice(263pub fn fromSlice(
264 T: type,
265 gpa: Allocator,
266 source: [:0]const u8,
267 diag: ?*Diagnostics,
268 options: Options,
269) error{ OutOfMemory, ParseZon }!T {
270 comptime assert(!requiresAllocator(T));
271 return fromSliceAlloc(T, gpa, source, diag, options);
272}
273
274/// Like `fromSlice`, but the result may contain pointers. To automatically free the result, see
275/// `free`.
276pub fn fromSliceAlloc(
258 /// The type to deserialize into. May not be or contain any of the following types:277 /// The type to deserialize into. May not be or contain any of the following types:
259 /// * Any comptime-only type, except in a comptime field278 /// * Any comptime-only type, except in a comptime field
260 /// * `type`279 /// * `type`
...@@ -285,11 +304,35 @@ pub fn fromSlice(...@@ -285,11 +304,35 @@ pub fn fromSlice(
285 defer if (diag == null) zoir.deinit(gpa);304 defer if (diag == null) zoir.deinit(gpa);
286305
287 if (diag) |s| s.* = .{};306 if (diag) |s| s.* = .{};
288 return fromZoir(T, gpa, ast, zoir, diag, options);307 return fromZoirAlloc(T, gpa, ast, zoir, diag, options);
289}308}
290309
291/// Like `fromSlice`, but operates on `Zoir` instead of ZON source.310/// Like `fromSlice`, but operates on `Zoir` instead of ZON source.
292pub fn fromZoir(311pub fn fromZoir(
312 T: type,
313 ast: Ast,
314 zoir: Zoir,
315 diag: ?*Diagnostics,
316 options: Options,
317) error{ParseZon}!T {
318 comptime assert(!requiresAllocator(T));
319 var buf: [0]u8 = .{};
320 var failing_allocator = std.heap.FixedBufferAllocator.init(&buf);
321 return fromZoirAlloc(
322 T,
323 failing_allocator.allocator(),
324 ast,
325 zoir,
326 diag,
327 options,
328 ) catch |err| switch (err) {
329 error.OutOfMemory => unreachable, // Checked by comptime assertion above
330 else => |e| return e,
331 };
332}
333
334/// Like `fromSliceAlloc`, but operates on `Zoir` instead of ZON source.
335pub fn fromZoirAlloc(
293 T: type,336 T: type,
294 gpa: Allocator,337 gpa: Allocator,
295 ast: Ast,338 ast: Ast,
...@@ -297,11 +340,37 @@ pub fn fromZoir(...@@ -297,11 +340,37 @@ pub fn fromZoir(
297 diag: ?*Diagnostics,340 diag: ?*Diagnostics,
298 options: Options,341 options: Options,
299) error{ OutOfMemory, ParseZon }!T {342) error{ OutOfMemory, ParseZon }!T {
300 return fromZoirNode(T, gpa, ast, zoir, .root, diag, options);343 return fromZoirNodeAlloc(T, gpa, ast, zoir, .root, diag, options);
301}344}
302345
303/// Like `fromZoir`, but the parse starts on `node` instead of root.346/// Like `fromZoir`, but the parse starts at `node` instead of root.
304pub fn fromZoirNode(347pub fn fromZoirNode(
348 T: type,
349 ast: Ast,
350 zoir: Zoir,
351 node: Zoir.Node.Index,
352 diag: ?*Diagnostics,
353 options: Options,
354) error{ParseZon}!T {
355 comptime assert(!requiresAllocator(T));
356 var buf: [0]u8 = .{};
357 var failing_allocator = std.heap.FixedBufferAllocator.init(&buf);
358 return fromZoirNodeAlloc(
359 T,
360 failing_allocator.allocator(),
361 ast,
362 zoir,
363 node,
364 diag,
365 options,
366 ) catch |err| switch (err) {
367 error.OutOfMemory => unreachable, // Checked by comptime assertion above
368 else => |e| return e,
369 };
370}
371
372/// Like `fromZoirAlloc`, but the parse starts at `node` instead of root.
373pub fn fromZoirNodeAlloc(
305 T: type,374 T: type,
306 gpa: Allocator,375 gpa: Allocator,
307 ast: Ast,376 ast: Ast,
...@@ -1321,7 +1390,7 @@ test "std.zon failure/oom formatting" {...@@ -1321,7 +1390,7 @@ test "std.zon failure/oom formatting" {
1321 });1390 });
1322 var diag: Diagnostics = .{};1391 var diag: Diagnostics = .{};
1323 defer diag.deinit(gpa);1392 defer diag.deinit(gpa);
1324 try std.testing.expectError(error.OutOfMemory, fromSlice(1393 try std.testing.expectError(error.OutOfMemory, fromSliceAlloc(
1325 []const u8,1394 []const u8,
1326 failing_allocator.allocator(),1395 failing_allocator.allocator(),
1327 "\"foo\"",1396 "\"foo\"",
...@@ -1331,7 +1400,7 @@ test "std.zon failure/oom formatting" {...@@ -1331,7 +1400,7 @@ test "std.zon failure/oom formatting" {
1331 try std.testing.expectFmt("", "{f}", .{diag});1400 try std.testing.expectFmt("", "{f}", .{diag});
1332}1401}
13331402
1334test "std.zon fromSlice syntax error" {1403test "std.zon fromSliceAlloc syntax error" {
1335 try std.testing.expectError(1404 try std.testing.expectError(
1336 error.ParseZon,1405 error.ParseZon,
1337 fromSlice(u8, std.testing.allocator, ".{", null, .{}),1406 fromSlice(u8, std.testing.allocator, ".{", null, .{}),
...@@ -1351,9 +1420,9 @@ test "std.zon optional" {...@@ -1351,9 +1420,9 @@ test "std.zon optional" {
13511420
1352 // Deep free1421 // Deep free
1353 {1422 {
1354 const none = try fromSlice(?[]const u8, gpa, "null", null, .{});1423 const none = try fromSliceAlloc(?[]const u8, gpa, "null", null, .{});
1355 try std.testing.expect(none == null);1424 try std.testing.expect(none == null);
1356 const some = try fromSlice(?[]const u8, gpa, "\"foo\"", null, .{});1425 const some = try fromSliceAlloc(?[]const u8, gpa, "\"foo\"", null, .{});
1357 defer free(gpa, some);1426 defer free(gpa, some);
1358 try std.testing.expectEqualStrings("foo", some.?);1427 try std.testing.expectEqualStrings("foo", some.?);
1359 }1428 }
...@@ -1386,10 +1455,10 @@ test "std.zon unions" {...@@ -1386,10 +1455,10 @@ test "std.zon unions" {
1386 {1455 {
1387 const Union = union(enum) { bar: []const u8, baz: bool };1456 const Union = union(enum) { bar: []const u8, baz: bool };
13881457
1389 const noalloc = try fromSlice(Union, gpa, ".{.baz = false}", null, .{});1458 const noalloc = try fromSliceAlloc(Union, gpa, ".{.baz = false}", null, .{});
1390 try std.testing.expectEqual(Union{ .baz = false }, noalloc);1459 try std.testing.expectEqual(Union{ .baz = false }, noalloc);
13911460
1392 const alloc = try fromSlice(Union, gpa, ".{.bar = \"qux\"}", null, .{});1461 const alloc = try fromSliceAlloc(Union, gpa, ".{.bar = \"qux\"}", null, .{});
1393 defer free(gpa, alloc);1462 defer free(gpa, alloc);
1394 try std.testing.expectEqualDeep(Union{ .bar = "qux" }, alloc);1463 try std.testing.expectEqualDeep(Union{ .bar = "qux" }, alloc);
1395 }1464 }
...@@ -1401,7 +1470,7 @@ test "std.zon unions" {...@@ -1401,7 +1470,7 @@ test "std.zon unions" {
1401 defer diag.deinit(gpa);1470 defer diag.deinit(gpa);
1402 try std.testing.expectError(1471 try std.testing.expectError(
1403 error.ParseZon,1472 error.ParseZon,
1404 fromSlice(Union, gpa, ".{.z=2.5}", &diag, .{}),1473 fromSliceAlloc(Union, gpa, ".{.z=2.5}", &diag, .{}),
1405 );1474 );
1406 try std.testing.expectFmt(1475 try std.testing.expectFmt(
1407 \\1:4: error: unexpected field 'z'1476 \\1:4: error: unexpected field 'z'
...@@ -1420,7 +1489,7 @@ test "std.zon unions" {...@@ -1420,7 +1489,7 @@ test "std.zon unions" {
1420 defer diag.deinit(gpa);1489 defer diag.deinit(gpa);
1421 try std.testing.expectError(1490 try std.testing.expectError(
1422 error.ParseZon,1491 error.ParseZon,
1423 fromSlice(Union, gpa, ".{.x=1}", &diag, .{}),1492 fromSliceAlloc(Union, gpa, ".{.x=1}", &diag, .{}),
1424 );1493 );
1425 try std.testing.expectFmt("1:6: error: expected type 'void'\n", "{f}", .{diag});1494 try std.testing.expectFmt("1:6: error: expected type 'void'\n", "{f}", .{diag});
1426 }1495 }
...@@ -1432,7 +1501,7 @@ test "std.zon unions" {...@@ -1432,7 +1501,7 @@ test "std.zon unions" {
1432 defer diag.deinit(gpa);1501 defer diag.deinit(gpa);
1433 try std.testing.expectError(1502 try std.testing.expectError(
1434 error.ParseZon,1503 error.ParseZon,
1435 fromSlice(Union, gpa, ".{.x = 1.5, .y = true}", &diag, .{}),1504 fromSliceAlloc(Union, gpa, ".{.x = 1.5, .y = true}", &diag, .{}),
1436 );1505 );
1437 try std.testing.expectFmt("1:2: error: expected union\n", "{f}", .{diag});1506 try std.testing.expectFmt("1:2: error: expected union\n", "{f}", .{diag});
1438 }1507 }
...@@ -1444,7 +1513,7 @@ test "std.zon unions" {...@@ -1444,7 +1513,7 @@ test "std.zon unions" {
1444 defer diag.deinit(gpa);1513 defer diag.deinit(gpa);
1445 try std.testing.expectError(1514 try std.testing.expectError(
1446 error.ParseZon,1515 error.ParseZon,
1447 fromSlice(Union, gpa, ".{}", &diag, .{}),1516 fromSliceAlloc(Union, gpa, ".{}", &diag, .{}),
1448 );1517 );
1449 try std.testing.expectFmt("1:2: error: expected union\n", "{f}", .{diag});1518 try std.testing.expectFmt("1:2: error: expected union\n", "{f}", .{diag});
1450 }1519 }
...@@ -1454,7 +1523,7 @@ test "std.zon unions" {...@@ -1454,7 +1523,7 @@ test "std.zon unions" {
1454 const Union = union { x: void };1523 const Union = union { x: void };
1455 var diag: Diagnostics = .{};1524 var diag: Diagnostics = .{};
1456 defer diag.deinit(gpa);1525 defer diag.deinit(gpa);
1457 try std.testing.expectError(error.ParseZon, fromSlice(Union, gpa, ".x", &diag, .{}));1526 try std.testing.expectError(error.ParseZon, fromSliceAlloc(Union, gpa, ".x", &diag, .{}));
1458 try std.testing.expectFmt("1:2: error: expected union\n", "{f}", .{diag});1527 try std.testing.expectFmt("1:2: error: expected union\n", "{f}", .{diag});
1459 }1528 }
14601529
...@@ -1463,7 +1532,7 @@ test "std.zon unions" {...@@ -1463,7 +1532,7 @@ test "std.zon unions" {
1463 const Union = union(enum) { x: void };1532 const Union = union(enum) { x: void };
1464 var diag: Diagnostics = .{};1533 var diag: Diagnostics = .{};
1465 defer diag.deinit(gpa);1534 defer diag.deinit(gpa);
1466 try std.testing.expectError(error.ParseZon, fromSlice(Union, gpa, ".y", &diag, .{}));1535 try std.testing.expectError(error.ParseZon, fromSliceAlloc(Union, gpa, ".y", &diag, .{}));
1467 try std.testing.expectFmt(1536 try std.testing.expectFmt(
1468 \\1:2: error: unexpected field 'y'1537 \\1:2: error: unexpected field 'y'
1469 \\1:2: note: supported: 'x'1538 \\1:2: note: supported: 'x'
...@@ -1479,7 +1548,7 @@ test "std.zon unions" {...@@ -1479,7 +1548,7 @@ test "std.zon unions" {
1479 const Union = union(enum) { x: f32 };1548 const Union = union(enum) { x: f32 };
1480 var diag: Diagnostics = .{};1549 var diag: Diagnostics = .{};
1481 defer diag.deinit(gpa);1550 defer diag.deinit(gpa);
1482 try std.testing.expectError(error.ParseZon, fromSlice(Union, gpa, ".x", &diag, .{}));1551 try std.testing.expectError(error.ParseZon, fromSliceAlloc(Union, gpa, ".x", &diag, .{}));
1483 try std.testing.expectFmt("1:2: error: expected union\n", "{f}", .{diag});1552 try std.testing.expectFmt("1:2: error: expected union\n", "{f}", .{diag});
1484 }1553 }
1485}1554}
...@@ -1511,7 +1580,7 @@ test "std.zon structs" {...@@ -1511,7 +1580,7 @@ test "std.zon structs" {
1511 {1580 {
1512 const Foo = struct { bar: []const u8, baz: []const []const u8 };1581 const Foo = struct { bar: []const u8, baz: []const []const u8 };
15131582
1514 const parsed = try fromSlice(1583 const parsed = try fromSliceAlloc(
1515 Foo,1584 Foo,
1516 gpa,1585 gpa,
1517 ".{.bar = \"qux\", .baz = .{\"a\", \"b\"}}",1586 ".{.bar = \"qux\", .baz = .{\"a\", \"b\"}}",
...@@ -1668,7 +1737,7 @@ test "std.zon structs" {...@@ -1668,7 +1737,7 @@ test "std.zon structs" {
1668 {1737 {
1669 var diag: Diagnostics = .{};1738 var diag: Diagnostics = .{};
1670 defer diag.deinit(gpa);1739 defer diag.deinit(gpa);
1671 const parsed = fromSlice([]u8, gpa, "[]u8{1, 2, 3}", &diag, .{});1740 const parsed = fromSliceAlloc([]u8, gpa, "[]u8{1, 2, 3}", &diag, .{});
1672 try std.testing.expectError(error.ParseZon, parsed);1741 try std.testing.expectError(error.ParseZon, parsed);
1673 try std.testing.expectFmt(1742 try std.testing.expectFmt(
1674 \\1:1: error: types are not available in ZON1743 \\1:1: error: types are not available in ZON
...@@ -1737,7 +1806,7 @@ test "std.zon tuples" {...@@ -1737,7 +1806,7 @@ test "std.zon tuples" {
1737 // Deep free1806 // Deep free
1738 {1807 {
1739 const Tuple = struct { []const u8, []const u8 };1808 const Tuple = struct { []const u8, []const u8 };
1740 const parsed = try fromSlice(Tuple, gpa, ".{\"hello\", \"world\"}", null, .{});1809 const parsed = try fromSliceAlloc(Tuple, gpa, ".{\"hello\", \"world\"}", null, .{});
1741 defer free(gpa, parsed);1810 defer free(gpa, parsed);
1742 try std.testing.expectEqualDeep(Tuple{ "hello", "world" }, parsed);1811 try std.testing.expectEqualDeep(Tuple{ "hello", "world" }, parsed);
1743 }1812 }
...@@ -1847,27 +1916,27 @@ test "std.zon arrays and slices" {...@@ -1847,27 +1916,27 @@ test "std.zon arrays and slices" {
18471916
1848 // Slice literals1917 // Slice literals
1849 {1918 {
1850 const zero = try fromSlice([]const u8, gpa, ".{}", null, .{});1919 const zero = try fromSliceAlloc([]const u8, gpa, ".{}", null, .{});
1851 defer free(gpa, zero);1920 defer free(gpa, zero);
1852 try std.testing.expectEqualSlices(u8, @as([]const u8, &.{}), zero);1921 try std.testing.expectEqualSlices(u8, @as([]const u8, &.{}), zero);
18531922
1854 const one = try fromSlice([]u8, gpa, ".{'a'}", null, .{});1923 const one = try fromSliceAlloc([]u8, gpa, ".{'a'}", null, .{});
1855 defer free(gpa, one);1924 defer free(gpa, one);
1856 try std.testing.expectEqualSlices(u8, &.{'a'}, one);1925 try std.testing.expectEqualSlices(u8, &.{'a'}, one);
18571926
1858 const two = try fromSlice([]const u8, gpa, ".{'a', 'b'}", null, .{});1927 const two = try fromSliceAlloc([]const u8, gpa, ".{'a', 'b'}", null, .{});
1859 defer free(gpa, two);1928 defer free(gpa, two);
1860 try std.testing.expectEqualSlices(u8, &.{ 'a', 'b' }, two);1929 try std.testing.expectEqualSlices(u8, &.{ 'a', 'b' }, two);
18611930
1862 const two_comma = try fromSlice([]const u8, gpa, ".{'a', 'b',}", null, .{});1931 const two_comma = try fromSliceAlloc([]const u8, gpa, ".{'a', 'b',}", null, .{});
1863 defer free(gpa, two_comma);1932 defer free(gpa, two_comma);
1864 try std.testing.expectEqualSlices(u8, &.{ 'a', 'b' }, two_comma);1933 try std.testing.expectEqualSlices(u8, &.{ 'a', 'b' }, two_comma);
18651934
1866 const three = try fromSlice([]u8, gpa, ".{'a', 'b', 'c'}", null, .{});1935 const three = try fromSliceAlloc([]u8, gpa, ".{'a', 'b', 'c'}", null, .{});
1867 defer free(gpa, three);1936 defer free(gpa, three);
1868 try std.testing.expectEqualSlices(u8, &.{ 'a', 'b', 'c' }, three);1937 try std.testing.expectEqualSlices(u8, &.{ 'a', 'b', 'c' }, three);
18691938
1870 const sentinel = try fromSlice([:'z']const u8, gpa, ".{'a', 'b', 'c'}", null, .{});1939 const sentinel = try fromSliceAlloc([:'z']const u8, gpa, ".{'a', 'b', 'c'}", null, .{});
1871 defer free(gpa, sentinel);1940 defer free(gpa, sentinel);
1872 const expected_sentinel: [:'z']const u8 = &.{ 'a', 'b', 'c' };1941 const expected_sentinel: [:'z']const u8 = &.{ 'a', 'b', 'c' };
1873 try std.testing.expectEqualSlices(u8, expected_sentinel, sentinel);1942 try std.testing.expectEqualSlices(u8, expected_sentinel, sentinel);
...@@ -1878,7 +1947,7 @@ test "std.zon arrays and slices" {...@@ -1878,7 +1947,7 @@ test "std.zon arrays and slices" {
1878 {1947 {
1879 // Arrays1948 // Arrays
1880 {1949 {
1881 const parsed = try fromSlice([1][]const u8, gpa, ".{\"abc\"}", null, .{});1950 const parsed = try fromSliceAlloc([1][]const u8, gpa, ".{\"abc\"}", null, .{});
1882 defer free(gpa, parsed);1951 defer free(gpa, parsed);
1883 const expected: [1][]const u8 = .{"abc"};1952 const expected: [1][]const u8 = .{"abc"};
1884 try std.testing.expectEqualDeep(expected, parsed);1953 try std.testing.expectEqualDeep(expected, parsed);
...@@ -1886,7 +1955,7 @@ test "std.zon arrays and slices" {...@@ -1886,7 +1955,7 @@ test "std.zon arrays and slices" {
18861955
1887 // Slice literals1956 // Slice literals
1888 {1957 {
1889 const parsed = try fromSlice([]const []const u8, gpa, ".{\"abc\"}", null, .{});1958 const parsed = try fromSliceAlloc([]const []const u8, gpa, ".{\"abc\"}", null, .{});
1890 defer free(gpa, parsed);1959 defer free(gpa, parsed);
1891 const expected: []const []const u8 = &.{"abc"};1960 const expected: []const []const u8 = &.{"abc"};
1892 try std.testing.expectEqualDeep(expected, parsed);1961 try std.testing.expectEqualDeep(expected, parsed);
...@@ -1905,7 +1974,7 @@ test "std.zon arrays and slices" {...@@ -1905,7 +1974,7 @@ test "std.zon arrays and slices" {
19051974
1906 // Slice literals1975 // Slice literals
1907 {1976 {
1908 const sentinel = try fromSlice([:2]align(4) u8, gpa, ".{1}", null, .{});1977 const sentinel = try fromSliceAlloc([:2]align(4) u8, gpa, ".{1}", null, .{});
1909 defer free(gpa, sentinel);1978 defer free(gpa, sentinel);
1910 try std.testing.expectEqual(@as(usize, 1), sentinel.len);1979 try std.testing.expectEqual(@as(usize, 1), sentinel.len);
1911 try std.testing.expectEqual(@as(u8, 1), sentinel[0]);1980 try std.testing.expectEqual(@as(u8, 1), sentinel[0]);
...@@ -1992,7 +2061,7 @@ test "std.zon arrays and slices" {...@@ -1992,7 +2061,7 @@ test "std.zon arrays and slices" {
1992 defer diag.deinit(gpa);2061 defer diag.deinit(gpa);
1993 try std.testing.expectError(2062 try std.testing.expectError(
1994 error.ParseZon,2063 error.ParseZon,
1995 fromSlice([]bool, gpa, ".{'a', 'b', 'c'}", &diag, .{}),2064 fromSliceAlloc([]bool, gpa, ".{'a', 'b', 'c'}", &diag, .{}),
1996 );2065 );
1997 try std.testing.expectFmt("1:3: error: expected type 'bool'\n", "{f}", .{diag});2066 try std.testing.expectFmt("1:3: error: expected type 'bool'\n", "{f}", .{diag});
1998 }2067 }
...@@ -2017,7 +2086,7 @@ test "std.zon arrays and slices" {...@@ -2017,7 +2086,7 @@ test "std.zon arrays and slices" {
2017 defer diag.deinit(gpa);2086 defer diag.deinit(gpa);
2018 try std.testing.expectError(2087 try std.testing.expectError(
2019 error.ParseZon,2088 error.ParseZon,
2020 fromSlice([]u8, gpa, "'a'", &diag, .{}),2089 fromSliceAlloc([]u8, gpa, "'a'", &diag, .{}),
2021 );2090 );
2022 try std.testing.expectFmt("1:1: error: expected array\n", "{f}", .{diag});2091 try std.testing.expectFmt("1:1: error: expected array\n", "{f}", .{diag});
2023 }2092 }
...@@ -2029,7 +2098,7 @@ test "std.zon arrays and slices" {...@@ -2029,7 +2098,7 @@ test "std.zon arrays and slices" {
2029 defer diag.deinit(gpa);2098 defer diag.deinit(gpa);
2030 try std.testing.expectError(2099 try std.testing.expectError(
2031 error.ParseZon,2100 error.ParseZon,
2032 fromSlice([]u8, gpa, " &.{'a', 'b', 'c'}", &diag, .{}),2101 fromSliceAlloc([]u8, gpa, " &.{'a', 'b', 'c'}", &diag, .{}),
2033 );2102 );
2034 try std.testing.expectFmt(2103 try std.testing.expectFmt(
2035 "1:3: error: pointers are not available in ZON\n",2104 "1:3: error: pointers are not available in ZON\n",
...@@ -2044,21 +2113,21 @@ test "std.zon string literal" {...@@ -2044,21 +2113,21 @@ test "std.zon string literal" {
20442113
2045 // Basic string literal2114 // Basic string literal
2046 {2115 {
2047 const parsed = try fromSlice([]const u8, gpa, "\"abc\"", null, .{});2116 const parsed = try fromSliceAlloc([]const u8, gpa, "\"abc\"", null, .{});
2048 defer free(gpa, parsed);2117 defer free(gpa, parsed);
2049 try std.testing.expectEqualStrings(@as([]const u8, "abc"), parsed);2118 try std.testing.expectEqualStrings(@as([]const u8, "abc"), parsed);
2050 }2119 }
20512120
2052 // String literal with escape characters2121 // String literal with escape characters
2053 {2122 {
2054 const parsed = try fromSlice([]const u8, gpa, "\"ab\\nc\"", null, .{});2123 const parsed = try fromSliceAlloc([]const u8, gpa, "\"ab\\nc\"", null, .{});
2055 defer free(gpa, parsed);2124 defer free(gpa, parsed);
2056 try std.testing.expectEqualStrings(@as([]const u8, "ab\nc"), parsed);2125 try std.testing.expectEqualStrings(@as([]const u8, "ab\nc"), parsed);
2057 }2126 }
20582127
2059 // String literal with embedded null2128 // String literal with embedded null
2060 {2129 {
2061 const parsed = try fromSlice([]const u8, gpa, "\"ab\\x00c\"", null, .{});2130 const parsed = try fromSliceAlloc([]const u8, gpa, "\"ab\\x00c\"", null, .{});
2062 defer free(gpa, parsed);2131 defer free(gpa, parsed);
2063 try std.testing.expectEqualStrings(@as([]const u8, "ab\x00c"), parsed);2132 try std.testing.expectEqualStrings(@as([]const u8, "ab\x00c"), parsed);
2064 }2133 }
...@@ -2070,7 +2139,7 @@ test "std.zon string literal" {...@@ -2070,7 +2139,7 @@ test "std.zon string literal" {
2070 defer diag.deinit(gpa);2139 defer diag.deinit(gpa);
2071 try std.testing.expectError(2140 try std.testing.expectError(
2072 error.ParseZon,2141 error.ParseZon,
2073 fromSlice([]u8, gpa, "\"abcd\"", &diag, .{}),2142 fromSliceAlloc([]u8, gpa, "\"abcd\"", &diag, .{}),
2074 );2143 );
2075 try std.testing.expectFmt("1:1: error: expected array\n", "{f}", .{diag});2144 try std.testing.expectFmt("1:1: error: expected array\n", "{f}", .{diag});
2076 }2145 }
...@@ -2080,7 +2149,7 @@ test "std.zon string literal" {...@@ -2080,7 +2149,7 @@ test "std.zon string literal" {
2080 defer diag.deinit(gpa);2149 defer diag.deinit(gpa);
2081 try std.testing.expectError(2150 try std.testing.expectError(
2082 error.ParseZon,2151 error.ParseZon,
2083 fromSlice([]u8, gpa, "\\\\abcd", &diag, .{}),2152 fromSliceAlloc([]u8, gpa, "\\\\abcd", &diag, .{}),
2084 );2153 );
2085 try std.testing.expectFmt("1:1: error: expected array\n", "{f}", .{diag});2154 try std.testing.expectFmt("1:1: error: expected array\n", "{f}", .{diag});
2086 }2155 }
...@@ -2116,7 +2185,7 @@ test "std.zon string literal" {...@@ -2116,7 +2185,7 @@ test "std.zon string literal" {
2116 // Zero terminated slices2185 // Zero terminated slices
2117 {2186 {
2118 {2187 {
2119 const parsed: [:0]const u8 = try fromSlice(2188 const parsed: [:0]const u8 = try fromSliceAlloc(
2120 [:0]const u8,2189 [:0]const u8,
2121 gpa,2190 gpa,
2122 "\"abc\"",2191 "\"abc\"",
...@@ -2129,7 +2198,7 @@ test "std.zon string literal" {...@@ -2129,7 +2198,7 @@ test "std.zon string literal" {
2129 }2198 }
21302199
2131 {2200 {
2132 const parsed: [:0]const u8 = try fromSlice(2201 const parsed: [:0]const u8 = try fromSliceAlloc(
2133 [:0]const u8,2202 [:0]const u8,
2134 gpa,2203 gpa,
2135 "\\\\abc",2204 "\\\\abc",
...@@ -2149,7 +2218,7 @@ test "std.zon string literal" {...@@ -2149,7 +2218,7 @@ test "std.zon string literal" {
2149 defer diag.deinit(gpa);2218 defer diag.deinit(gpa);
2150 try std.testing.expectError(2219 try std.testing.expectError(
2151 error.ParseZon,2220 error.ParseZon,
2152 fromSlice([:1]const u8, gpa, "\"foo\"", &diag, .{}),2221 fromSliceAlloc([:1]const u8, gpa, "\"foo\"", &diag, .{}),
2153 );2222 );
2154 try std.testing.expectFmt("1:1: error: expected array\n", "{f}", .{diag});2223 try std.testing.expectFmt("1:1: error: expected array\n", "{f}", .{diag});
2155 }2224 }
...@@ -2159,7 +2228,7 @@ test "std.zon string literal" {...@@ -2159,7 +2228,7 @@ test "std.zon string literal" {
2159 defer diag.deinit(gpa);2228 defer diag.deinit(gpa);
2160 try std.testing.expectError(2229 try std.testing.expectError(
2161 error.ParseZon,2230 error.ParseZon,
2162 fromSlice([:1]const u8, gpa, "\\\\foo", &diag, .{}),2231 fromSliceAlloc([:1]const u8, gpa, "\\\\foo", &diag, .{}),
2163 );2232 );
2164 try std.testing.expectFmt("1:1: error: expected array\n", "{f}", .{diag});2233 try std.testing.expectFmt("1:1: error: expected array\n", "{f}", .{diag});
2165 }2234 }
...@@ -2171,7 +2240,7 @@ test "std.zon string literal" {...@@ -2171,7 +2240,7 @@ test "std.zon string literal" {
2171 defer diag.deinit(gpa);2240 defer diag.deinit(gpa);
2172 try std.testing.expectError(2241 try std.testing.expectError(
2173 error.ParseZon,2242 error.ParseZon,
2174 fromSlice([]const u8, gpa, "true", &diag, .{}),2243 fromSliceAlloc([]const u8, gpa, "true", &diag, .{}),
2175 );2244 );
2176 try std.testing.expectFmt("1:1: error: expected string\n", "{f}", .{diag});2245 try std.testing.expectFmt("1:1: error: expected string\n", "{f}", .{diag});
2177 }2246 }
...@@ -2182,7 +2251,7 @@ test "std.zon string literal" {...@@ -2182,7 +2251,7 @@ test "std.zon string literal" {
2182 defer diag.deinit(gpa);2251 defer diag.deinit(gpa);
2183 try std.testing.expectError(2252 try std.testing.expectError(
2184 error.ParseZon,2253 error.ParseZon,
2185 fromSlice([]const u8, gpa, ".{false}", &diag, .{}),2254 fromSliceAlloc([]const u8, gpa, ".{false}", &diag, .{}),
2186 );2255 );
2187 try std.testing.expectFmt("1:3: error: expected type 'u8'\n", "{f}", .{diag});2256 try std.testing.expectFmt("1:3: error: expected type 'u8'\n", "{f}", .{diag});
2188 }2257 }
...@@ -2193,7 +2262,7 @@ test "std.zon string literal" {...@@ -2193,7 +2262,7 @@ test "std.zon string literal" {
2193 defer diag.deinit(gpa);2262 defer diag.deinit(gpa);
2194 try std.testing.expectError(2263 try std.testing.expectError(
2195 error.ParseZon,2264 error.ParseZon,
2196 fromSlice([]const i8, gpa, "\"\\a\"", &diag, .{}),2265 fromSliceAlloc([]const i8, gpa, "\"\\a\"", &diag, .{}),
2197 );2266 );
2198 try std.testing.expectFmt("1:3: error: invalid escape character: 'a'\n", "{f}", .{diag});2267 try std.testing.expectFmt("1:3: error: invalid escape character: 'a'\n", "{f}", .{diag});
2199 }2268 }
...@@ -2205,7 +2274,7 @@ test "std.zon string literal" {...@@ -2205,7 +2274,7 @@ test "std.zon string literal" {
2205 defer diag.deinit(gpa);2274 defer diag.deinit(gpa);
2206 try std.testing.expectError(2275 try std.testing.expectError(
2207 error.ParseZon,2276 error.ParseZon,
2208 fromSlice([]const i8, gpa, "\"a\"", &diag, .{}),2277 fromSliceAlloc([]const i8, gpa, "\"a\"", &diag, .{}),
2209 );2278 );
2210 try std.testing.expectFmt("1:1: error: expected array\n", "{f}", .{diag});2279 try std.testing.expectFmt("1:1: error: expected array\n", "{f}", .{diag});
2211 }2280 }
...@@ -2215,7 +2284,7 @@ test "std.zon string literal" {...@@ -2215,7 +2284,7 @@ test "std.zon string literal" {
2215 defer diag.deinit(gpa);2284 defer diag.deinit(gpa);
2216 try std.testing.expectError(2285 try std.testing.expectError(
2217 error.ParseZon,2286 error.ParseZon,
2218 fromSlice([]const i8, gpa, "\\\\a", &diag, .{}),2287 fromSliceAlloc([]const i8, gpa, "\\\\a", &diag, .{}),
2219 );2288 );
2220 try std.testing.expectFmt("1:1: error: expected array\n", "{f}", .{diag});2289 try std.testing.expectFmt("1:1: error: expected array\n", "{f}", .{diag});
2221 }2290 }
...@@ -2228,7 +2297,7 @@ test "std.zon string literal" {...@@ -2228,7 +2297,7 @@ test "std.zon string literal" {
2228 defer diag.deinit(gpa);2297 defer diag.deinit(gpa);
2229 try std.testing.expectError(2298 try std.testing.expectError(
2230 error.ParseZon,2299 error.ParseZon,
2231 fromSlice([]align(2) const u8, gpa, "\"abc\"", &diag, .{}),2300 fromSliceAlloc([]align(2) const u8, gpa, "\"abc\"", &diag, .{}),
2232 );2301 );
2233 try std.testing.expectFmt("1:1: error: expected array\n", "{f}", .{diag});2302 try std.testing.expectFmt("1:1: error: expected array\n", "{f}", .{diag});
2234 }2303 }
...@@ -2238,7 +2307,7 @@ test "std.zon string literal" {...@@ -2238,7 +2307,7 @@ test "std.zon string literal" {
2238 defer diag.deinit(gpa);2307 defer diag.deinit(gpa);
2239 try std.testing.expectError(2308 try std.testing.expectError(
2240 error.ParseZon,2309 error.ParseZon,
2241 fromSlice([]align(2) const u8, gpa, "\\\\abc", &diag, .{}),2310 fromSliceAlloc([]align(2) const u8, gpa, "\\\\abc", &diag, .{}),
2242 );2311 );
2243 try std.testing.expectFmt("1:1: error: expected array\n", "{f}", .{diag});2312 try std.testing.expectFmt("1:1: error: expected array\n", "{f}", .{diag});
2244 }2313 }
...@@ -2253,7 +2322,7 @@ test "std.zon string literal" {...@@ -2253,7 +2322,7 @@ test "std.zon string literal" {
2253 message2: String,2322 message2: String,
2254 message3: String,2323 message3: String,
2255 };2324 };
2256 const parsed = try fromSlice(S, gpa,2325 const parsed = try fromSliceAlloc(S, gpa,
2257 \\.{2326 \\.{
2258 \\ .message =2327 \\ .message =
2259 \\ \\hello, world!2328 \\ \\hello, world!
...@@ -2909,7 +2978,7 @@ test "std.zon free on error" {...@@ -2909,7 +2978,7 @@ test "std.zon free on error" {
2909 y: []const u8,2978 y: []const u8,
2910 z: bool,2979 z: bool,
2911 };2980 };
2912 try std.testing.expectError(error.ParseZon, fromSlice(Struct, std.testing.allocator,2981 try std.testing.expectError(error.ParseZon, fromSliceAlloc(Struct, std.testing.allocator,
2913 \\.{2982 \\.{
2914 \\ .x = "hello",2983 \\ .x = "hello",
2915 \\ .y = "world",2984 \\ .y = "world",
...@@ -2925,7 +2994,7 @@ test "std.zon free on error" {...@@ -2925,7 +2994,7 @@ test "std.zon free on error" {
2925 []const u8,2994 []const u8,
2926 bool,2995 bool,
2927 };2996 };
2928 try std.testing.expectError(error.ParseZon, fromSlice(Struct, std.testing.allocator,2997 try std.testing.expectError(error.ParseZon, fromSliceAlloc(Struct, std.testing.allocator,
2929 \\.{2998 \\.{
2930 \\ "hello",2999 \\ "hello",
2931 \\ "world",3000 \\ "world",
...@@ -2940,7 +3009,7 @@ test "std.zon free on error" {...@@ -2940,7 +3009,7 @@ test "std.zon free on error" {
2940 x: []const u8,3009 x: []const u8,
2941 y: bool,3010 y: bool,
2942 };3011 };
2943 try std.testing.expectError(error.ParseZon, fromSlice(Struct, std.testing.allocator,3012 try std.testing.expectError(error.ParseZon, fromSliceAlloc(Struct, std.testing.allocator,
2944 \\.{3013 \\.{
2945 \\ .x = "hello",3014 \\ .x = "hello",
2946 \\}3015 \\}
...@@ -2949,7 +3018,7 @@ test "std.zon free on error" {...@@ -2949,7 +3018,7 @@ test "std.zon free on error" {
29493018
2950 // Test freeing partially allocated arrays3019 // Test freeing partially allocated arrays
2951 {3020 {
2952 try std.testing.expectError(error.ParseZon, fromSlice(3021 try std.testing.expectError(error.ParseZon, fromSliceAlloc(
2953 [3][]const u8,3022 [3][]const u8,
2954 std.testing.allocator,3023 std.testing.allocator,
2955 \\.{3024 \\.{
...@@ -2965,7 +3034,7 @@ test "std.zon free on error" {...@@ -2965,7 +3034,7 @@ test "std.zon free on error" {
29653034
2966 // Test freeing partially allocated slices3035 // Test freeing partially allocated slices
2967 {3036 {
2968 try std.testing.expectError(error.ParseZon, fromSlice(3037 try std.testing.expectError(error.ParseZon, fromSliceAlloc(
2969 [][]const u8,3038 [][]const u8,
2970 std.testing.allocator,3039 std.testing.allocator,
2971 \\.{3040 \\.{
...@@ -2989,7 +3058,7 @@ test "std.zon free on error" {...@@ -2989,7 +3058,7 @@ test "std.zon free on error" {
2989 // We can also parse types that can't be freed if it's impossible for an error to occur after3058 // We can also parse types that can't be freed if it's impossible for an error to occur after
2990 // the allocation, as is the case here.3059 // the allocation, as is the case here.
2991 {3060 {
2992 const result = try fromSlice(3061 const result = try fromSliceAlloc(
2993 union { x: []const u8 },3062 union { x: []const u8 },
2994 std.testing.allocator,3063 std.testing.allocator,
2995 ".{ .x = \"foo\" }",3064 ".{ .x = \"foo\" }",
...@@ -3008,7 +3077,7 @@ test "std.zon free on error" {...@@ -3008,7 +3077,7 @@ test "std.zon free on error" {
3008 union { x: []const u8 },3077 union { x: []const u8 },
3009 bool,3078 bool,
3010 };3079 };
3011 const result = try fromSlice(3080 const result = try fromSliceAlloc(
3012 S,3081 S,
3013 std.testing.allocator,3082 std.testing.allocator,
3014 ".{ .{ .x = \"foo\" }, true }",3083 ".{ .{ .x = \"foo\" }, true }",
...@@ -3026,7 +3095,7 @@ test "std.zon free on error" {...@@ -3026,7 +3095,7 @@ test "std.zon free on error" {
3026 a: union { x: []const u8 },3095 a: union { x: []const u8 },
3027 b: bool,3096 b: bool,
3028 };3097 };
3029 const result = try fromSlice(3098 const result = try fromSliceAlloc(
3030 S,3099 S,
3031 std.testing.allocator,3100 std.testing.allocator,
3032 ".{ .a = .{ .x = \"foo\" }, .b = true }",3101 ".{ .a = .{ .x = \"foo\" }, .b = true }",
...@@ -3043,7 +3112,7 @@ test "std.zon free on error" {...@@ -3043,7 +3112,7 @@ test "std.zon free on error" {
3043 // Again but for arrays.3112 // Again but for arrays.
3044 {3113 {
3045 const S = [2]union { x: []const u8 };3114 const S = [2]union { x: []const u8 };
3046 const result = try fromSlice(3115 const result = try fromSliceAlloc(
3047 S,3116 S,
3048 std.testing.allocator,3117 std.testing.allocator,
3049 ".{ .{ .x = \"foo\" }, .{ .x = \"bar\" } }",3118 ".{ .{ .x = \"foo\" }, .{ .x = \"bar\" } }",
...@@ -3061,7 +3130,7 @@ test "std.zon free on error" {...@@ -3061,7 +3130,7 @@ test "std.zon free on error" {
3061 // Again but for slices.3130 // Again but for slices.
3062 {3131 {
3063 const S = []union { x: []const u8 };3132 const S = []union { x: []const u8 };
3064 const result = try fromSlice(3133 const result = try fromSliceAlloc(
3065 S,3134 S,
3066 std.testing.allocator,3135 std.testing.allocator,
3067 ".{ .{ .x = \"foo\" }, .{ .x = \"bar\" } }",3136 ".{ .{ .x = \"foo\" }, .{ .x = \"bar\" } }",
...@@ -3114,9 +3183,9 @@ test "std.zon vector" {...@@ -3114,9 +3183,9 @@ test "std.zon vector" {
3114 {3183 {
3115 try std.testing.expectEqual(3184 try std.testing.expectEqual(
3116 @Vector(0, *const u8){},3185 @Vector(0, *const u8){},
3117 try fromSlice(@Vector(0, *const u8), gpa, ".{}", null, .{}),3186 try fromSliceAlloc(@Vector(0, *const u8), gpa, ".{}", null, .{}),
3118 );3187 );
3119 const pointers = try fromSlice(@Vector(3, *const u8), gpa, ".{2, 4, 6}", null, .{});3188 const pointers = try fromSliceAlloc(@Vector(3, *const u8), gpa, ".{2, 4, 6}", null, .{});
3120 defer free(gpa, pointers);3189 defer free(gpa, pointers);
3121 try std.testing.expectEqualDeep(@Vector(3, *const u8){ &2, &4, &6 }, pointers);3190 try std.testing.expectEqualDeep(@Vector(3, *const u8){ &2, &4, &6 }, pointers);
3122 }3191 }
...@@ -3124,9 +3193,9 @@ test "std.zon vector" {...@@ -3124,9 +3193,9 @@ test "std.zon vector" {
3124 {3193 {
3125 try std.testing.expectEqual(3194 try std.testing.expectEqual(
3126 @Vector(0, ?*const u8){},3195 @Vector(0, ?*const u8){},
3127 try fromSlice(@Vector(0, ?*const u8), gpa, ".{}", null, .{}),3196 try fromSliceAlloc(@Vector(0, ?*const u8), gpa, ".{}", null, .{}),
3128 );3197 );
3129 const pointers = try fromSlice(@Vector(3, ?*const u8), gpa, ".{2, null, 6}", null, .{});3198 const pointers = try fromSliceAlloc(@Vector(3, ?*const u8), gpa, ".{2, null, 6}", null, .{});
3130 defer free(gpa, pointers);3199 defer free(gpa, pointers);
3131 try std.testing.expectEqualDeep(@Vector(3, ?*const u8){ &2, null, &6 }, pointers);3200 try std.testing.expectEqualDeep(@Vector(3, ?*const u8){ &2, null, &6 }, pointers);
3132 }3201 }
...@@ -3193,7 +3262,7 @@ test "std.zon vector" {...@@ -3193,7 +3262,7 @@ test "std.zon vector" {
3193 defer diag.deinit(gpa);3262 defer diag.deinit(gpa);
3194 try std.testing.expectError(3263 try std.testing.expectError(
3195 error.ParseZon,3264 error.ParseZon,
3196 fromSlice(@Vector(3, *u8), gpa, ".{1, true, 3}", &diag, .{}),3265 fromSliceAlloc(@Vector(3, *u8), gpa, ".{1, true, 3}", &diag, .{}),
3197 );3266 );
3198 try std.testing.expectFmt("1:6: error: expected type 'u8'\n", "{f}", .{diag});3267 try std.testing.expectFmt("1:6: error: expected type 'u8'\n", "{f}", .{diag});
3199 }3268 }
...@@ -3204,77 +3273,77 @@ test "std.zon add pointers" {...@@ -3204,77 +3273,77 @@ test "std.zon add pointers" {
32043273
3205 // Primitive with varying levels of pointers3274 // Primitive with varying levels of pointers
3206 {3275 {
3207 const result = try fromSlice(*u32, gpa, "10", null, .{});3276 const result = try fromSliceAlloc(*u32, gpa, "10", null, .{});
3208 defer free(gpa, result);3277 defer free(gpa, result);
3209 try std.testing.expectEqual(@as(u32, 10), result.*);3278 try std.testing.expectEqual(@as(u32, 10), result.*);
3210 }3279 }
32113280
3212 {3281 {
3213 const result = try fromSlice(**u32, gpa, "10", null, .{});3282 const result = try fromSliceAlloc(**u32, gpa, "10", null, .{});
3214 defer free(gpa, result);3283 defer free(gpa, result);
3215 try std.testing.expectEqual(@as(u32, 10), result.*.*);3284 try std.testing.expectEqual(@as(u32, 10), result.*.*);
3216 }3285 }
32173286
3218 {3287 {
3219 const result = try fromSlice(***u32, gpa, "10", null, .{});3288 const result = try fromSliceAlloc(***u32, gpa, "10", null, .{});
3220 defer free(gpa, result);3289 defer free(gpa, result);
3221 try std.testing.expectEqual(@as(u32, 10), result.*.*.*);3290 try std.testing.expectEqual(@as(u32, 10), result.*.*.*);
3222 }3291 }
32233292
3224 // Primitive optional with varying levels of pointers3293 // Primitive optional with varying levels of pointers
3225 {3294 {
3226 const some = try fromSlice(?*u32, gpa, "10", null, .{});3295 const some = try fromSliceAlloc(?*u32, gpa, "10", null, .{});
3227 defer free(gpa, some);3296 defer free(gpa, some);
3228 try std.testing.expectEqual(@as(u32, 10), some.?.*);3297 try std.testing.expectEqual(@as(u32, 10), some.?.*);
32293298
3230 const none = try fromSlice(?*u32, gpa, "null", null, .{});3299 const none = try fromSliceAlloc(?*u32, gpa, "null", null, .{});
3231 defer free(gpa, none);3300 defer free(gpa, none);
3232 try std.testing.expectEqual(null, none);3301 try std.testing.expectEqual(null, none);
3233 }3302 }
32343303
3235 {3304 {
3236 const some = try fromSlice(*?u32, gpa, "10", null, .{});3305 const some = try fromSliceAlloc(*?u32, gpa, "10", null, .{});
3237 defer free(gpa, some);3306 defer free(gpa, some);
3238 try std.testing.expectEqual(@as(u32, 10), some.*.?);3307 try std.testing.expectEqual(@as(u32, 10), some.*.?);
32393308
3240 const none = try fromSlice(*?u32, gpa, "null", null, .{});3309 const none = try fromSliceAlloc(*?u32, gpa, "null", null, .{});
3241 defer free(gpa, none);3310 defer free(gpa, none);
3242 try std.testing.expectEqual(null, none.*);3311 try std.testing.expectEqual(null, none.*);
3243 }3312 }
32443313
3245 {3314 {
3246 const some = try fromSlice(?**u32, gpa, "10", null, .{});3315 const some = try fromSliceAlloc(?**u32, gpa, "10", null, .{});
3247 defer free(gpa, some);3316 defer free(gpa, some);
3248 try std.testing.expectEqual(@as(u32, 10), some.?.*.*);3317 try std.testing.expectEqual(@as(u32, 10), some.?.*.*);
32493318
3250 const none = try fromSlice(?**u32, gpa, "null", null, .{});3319 const none = try fromSliceAlloc(?**u32, gpa, "null", null, .{});
3251 defer free(gpa, none);3320 defer free(gpa, none);
3252 try std.testing.expectEqual(null, none);3321 try std.testing.expectEqual(null, none);
3253 }3322 }
32543323
3255 {3324 {
3256 const some = try fromSlice(*?*u32, gpa, "10", null, .{});3325 const some = try fromSliceAlloc(*?*u32, gpa, "10", null, .{});
3257 defer free(gpa, some);3326 defer free(gpa, some);
3258 try std.testing.expectEqual(@as(u32, 10), some.*.?.*);3327 try std.testing.expectEqual(@as(u32, 10), some.*.?.*);
32593328
3260 const none = try fromSlice(*?*u32, gpa, "null", null, .{});3329 const none = try fromSliceAlloc(*?*u32, gpa, "null", null, .{});
3261 defer free(gpa, none);3330 defer free(gpa, none);
3262 try std.testing.expectEqual(null, none.*);3331 try std.testing.expectEqual(null, none.*);
3263 }3332 }
32643333
3265 {3334 {
3266 const some = try fromSlice(**?u32, gpa, "10", null, .{});3335 const some = try fromSliceAlloc(**?u32, gpa, "10", null, .{});
3267 defer free(gpa, some);3336 defer free(gpa, some);
3268 try std.testing.expectEqual(@as(u32, 10), some.*.*.?);3337 try std.testing.expectEqual(@as(u32, 10), some.*.*.?);
32693338
3270 const none = try fromSlice(**?u32, gpa, "null", null, .{});3339 const none = try fromSliceAlloc(**?u32, gpa, "null", null, .{});
3271 defer free(gpa, none);3340 defer free(gpa, none);
3272 try std.testing.expectEqual(null, none.*.*);3341 try std.testing.expectEqual(null, none.*.*);
3273 }3342 }
32743343
3275 // Pointer to an array3344 // Pointer to an array
3276 {3345 {
3277 const result = try fromSlice(*[3]u8, gpa, ".{ 1, 2, 3 }", null, .{});3346 const result = try fromSliceAlloc(*[3]u8, gpa, ".{ 1, 2, 3 }", null, .{});
3278 defer free(gpa, result);3347 defer free(gpa, result);
3279 try std.testing.expectEqual([3]u8{ 1, 2, 3 }, result.*);3348 try std.testing.expectEqual([3]u8{ 1, 2, 3 }, result.*);
3280 }3349 }
...@@ -3297,7 +3366,7 @@ test "std.zon add pointers" {...@@ -3297,7 +3366,7 @@ test "std.zon add pointers" {
3297 .f2 = &null,3366 .f2 = &null,
3298 };3367 };
32993368
3300 const found = try fromSlice(?*Outer, gpa,3369 const found = try fromSliceAlloc(?*Outer, gpa,
3301 \\.{3370 \\.{
3302 \\ .f1 = .{3371 \\ .f1 = .{
3303 \\ .f1 = null,3372 \\ .f1 = null,
...@@ -3317,7 +3386,7 @@ test "std.zon add pointers" {...@@ -3317,7 +3386,7 @@ test "std.zon add pointers" {
3317 defer diag.deinit(gpa);3386 defer diag.deinit(gpa);
3318 try std.testing.expectError(3387 try std.testing.expectError(
3319 error.ParseZon,3388 error.ParseZon,
3320 fromSlice(*const ?*const u8, gpa, "true", &diag, .{}),3389 fromSliceAlloc(*const ?*const u8, gpa, "true", &diag, .{}),
3321 );3390 );
3322 try std.testing.expectFmt("1:1: error: expected type '?u8'\n", "{f}", .{diag});3391 try std.testing.expectFmt("1:1: error: expected type '?u8'\n", "{f}", .{diag});
3323 }3392 }
...@@ -3327,7 +3396,7 @@ test "std.zon add pointers" {...@@ -3327,7 +3396,7 @@ test "std.zon add pointers" {
3327 defer diag.deinit(gpa);3396 defer diag.deinit(gpa);
3328 try std.testing.expectError(3397 try std.testing.expectError(
3329 error.ParseZon,3398 error.ParseZon,
3330 fromSlice(*const ?*const f32, gpa, "true", &diag, .{}),3399 fromSliceAlloc(*const ?*const f32, gpa, "true", &diag, .{}),
3331 );3400 );
3332 try std.testing.expectFmt("1:1: error: expected type '?f32'\n", "{f}", .{diag});3401 try std.testing.expectFmt("1:1: error: expected type '?f32'\n", "{f}", .{diag});
3333 }3402 }
...@@ -3337,7 +3406,7 @@ test "std.zon add pointers" {...@@ -3337,7 +3406,7 @@ test "std.zon add pointers" {
3337 defer diag.deinit(gpa);3406 defer diag.deinit(gpa);
3338 try std.testing.expectError(3407 try std.testing.expectError(
3339 error.ParseZon,3408 error.ParseZon,
3340 fromSlice(*const ?*const @Vector(3, u8), gpa, "true", &diag, .{}),3409 fromSliceAlloc(*const ?*const @Vector(3, u8), gpa, "true", &diag, .{}),
3341 );3410 );
3342 try std.testing.expectFmt("1:1: error: expected type '?@Vector(3, u8)'\n", "{f}", .{diag});3411 try std.testing.expectFmt("1:1: error: expected type '?@Vector(3, u8)'\n", "{f}", .{diag});
3343 }3412 }
...@@ -3347,7 +3416,7 @@ test "std.zon add pointers" {...@@ -3347,7 +3416,7 @@ test "std.zon add pointers" {
3347 defer diag.deinit(gpa);3416 defer diag.deinit(gpa);
3348 try std.testing.expectError(3417 try std.testing.expectError(
3349 error.ParseZon,3418 error.ParseZon,
3350 fromSlice(*const ?*const bool, gpa, "10", &diag, .{}),3419 fromSliceAlloc(*const ?*const bool, gpa, "10", &diag, .{}),
3351 );3420 );
3352 try std.testing.expectFmt("1:1: error: expected type '?bool'\n", "{f}", .{diag});3421 try std.testing.expectFmt("1:1: error: expected type '?bool'\n", "{f}", .{diag});
3353 }3422 }
...@@ -3357,7 +3426,7 @@ test "std.zon add pointers" {...@@ -3357,7 +3426,7 @@ test "std.zon add pointers" {
3357 defer diag.deinit(gpa);3426 defer diag.deinit(gpa);
3358 try std.testing.expectError(3427 try std.testing.expectError(
3359 error.ParseZon,3428 error.ParseZon,
3360 fromSlice(*const ?*const struct { a: i32 }, gpa, "true", &diag, .{}),3429 fromSliceAlloc(*const ?*const struct { a: i32 }, gpa, "true", &diag, .{}),
3361 );3430 );
3362 try std.testing.expectFmt("1:1: error: expected optional struct\n", "{f}", .{diag});3431 try std.testing.expectFmt("1:1: error: expected optional struct\n", "{f}", .{diag});
3363 }3432 }
...@@ -3367,7 +3436,7 @@ test "std.zon add pointers" {...@@ -3367,7 +3436,7 @@ test "std.zon add pointers" {
3367 defer diag.deinit(gpa);3436 defer diag.deinit(gpa);
3368 try std.testing.expectError(3437 try std.testing.expectError(
3369 error.ParseZon,3438 error.ParseZon,
3370 fromSlice(*const ?*const struct { i32 }, gpa, "true", &diag, .{}),3439 fromSliceAlloc(*const ?*const struct { i32 }, gpa, "true", &diag, .{}),
3371 );3440 );
3372 try std.testing.expectFmt("1:1: error: expected optional tuple\n", "{f}", .{diag});3441 try std.testing.expectFmt("1:1: error: expected optional tuple\n", "{f}", .{diag});
3373 }3442 }
...@@ -3377,7 +3446,7 @@ test "std.zon add pointers" {...@@ -3377,7 +3446,7 @@ test "std.zon add pointers" {
3377 defer diag.deinit(gpa);3446 defer diag.deinit(gpa);
3378 try std.testing.expectError(3447 try std.testing.expectError(
3379 error.ParseZon,3448 error.ParseZon,
3380 fromSlice(*const ?*const union { x: void }, gpa, "true", &diag, .{}),3449 fromSliceAlloc(*const ?*const union { x: void }, gpa, "true", &diag, .{}),
3381 );3450 );
3382 try std.testing.expectFmt("1:1: error: expected optional union\n", "{f}", .{diag});3451 try std.testing.expectFmt("1:1: error: expected optional union\n", "{f}", .{diag});
3383 }3452 }
...@@ -3387,7 +3456,7 @@ test "std.zon add pointers" {...@@ -3387,7 +3456,7 @@ test "std.zon add pointers" {
3387 defer diag.deinit(gpa);3456 defer diag.deinit(gpa);
3388 try std.testing.expectError(3457 try std.testing.expectError(
3389 error.ParseZon,3458 error.ParseZon,
3390 fromSlice(*const ?*const [3]u8, gpa, "true", &diag, .{}),3459 fromSliceAlloc(*const ?*const [3]u8, gpa, "true", &diag, .{}),
3391 );3460 );
3392 try std.testing.expectFmt("1:1: error: expected optional array\n", "{f}", .{diag});3461 try std.testing.expectFmt("1:1: error: expected optional array\n", "{f}", .{diag});
3393 }3462 }
...@@ -3397,7 +3466,7 @@ test "std.zon add pointers" {...@@ -3397,7 +3466,7 @@ test "std.zon add pointers" {
3397 defer diag.deinit(gpa);3466 defer diag.deinit(gpa);
3398 try std.testing.expectError(3467 try std.testing.expectError(
3399 error.ParseZon,3468 error.ParseZon,
3400 fromSlice(?[3]u8, gpa, "true", &diag, .{}),3469 fromSliceAlloc(?[3]u8, gpa, "true", &diag, .{}),
3401 );3470 );
3402 try std.testing.expectFmt("1:1: error: expected optional array\n", "{f}", .{diag});3471 try std.testing.expectFmt("1:1: error: expected optional array\n", "{f}", .{diag});
3403 }3472 }
...@@ -3407,7 +3476,7 @@ test "std.zon add pointers" {...@@ -3407,7 +3476,7 @@ test "std.zon add pointers" {
3407 defer diag.deinit(gpa);3476 defer diag.deinit(gpa);
3408 try std.testing.expectError(3477 try std.testing.expectError(
3409 error.ParseZon,3478 error.ParseZon,
3410 fromSlice(*const ?*const []u8, gpa, "true", &diag, .{}),3479 fromSliceAlloc(*const ?*const []u8, gpa, "true", &diag, .{}),
3411 );3480 );
3412 try std.testing.expectFmt("1:1: error: expected optional array\n", "{f}", .{diag});3481 try std.testing.expectFmt("1:1: error: expected optional array\n", "{f}", .{diag});
3413 }3482 }
...@@ -3417,7 +3486,7 @@ test "std.zon add pointers" {...@@ -3417,7 +3486,7 @@ test "std.zon add pointers" {
3417 defer diag.deinit(gpa);3486 defer diag.deinit(gpa);
3418 try std.testing.expectError(3487 try std.testing.expectError(
3419 error.ParseZon,3488 error.ParseZon,
3420 fromSlice(?[]u8, gpa, "true", &diag, .{}),3489 fromSliceAlloc(?[]u8, gpa, "true", &diag, .{}),
3421 );3490 );
3422 try std.testing.expectFmt("1:1: error: expected optional array\n", "{f}", .{diag});3491 try std.testing.expectFmt("1:1: error: expected optional array\n", "{f}", .{diag});
3423 }3492 }
...@@ -3427,7 +3496,7 @@ test "std.zon add pointers" {...@@ -3427,7 +3496,7 @@ test "std.zon add pointers" {
3427 defer diag.deinit(gpa);3496 defer diag.deinit(gpa);
3428 try std.testing.expectError(3497 try std.testing.expectError(
3429 error.ParseZon,3498 error.ParseZon,
3430 fromSlice(*const ?*const []const u8, gpa, "true", &diag, .{}),3499 fromSliceAlloc(*const ?*const []const u8, gpa, "true", &diag, .{}),
3431 );3500 );
3432 try std.testing.expectFmt("1:1: error: expected optional string\n", "{f}", .{diag});3501 try std.testing.expectFmt("1:1: error: expected optional string\n", "{f}", .{diag});
3433 }3502 }
...@@ -3437,7 +3506,7 @@ test "std.zon add pointers" {...@@ -3437,7 +3506,7 @@ test "std.zon add pointers" {
3437 defer diag.deinit(gpa);3506 defer diag.deinit(gpa);
3438 try std.testing.expectError(3507 try std.testing.expectError(
3439 error.ParseZon,3508 error.ParseZon,
3440 fromSlice(*const ?*const enum { foo }, gpa, "true", &diag, .{}),3509 fromSliceAlloc(*const ?*const enum { foo }, gpa, "true", &diag, .{}),
3441 );3510 );
3442 try std.testing.expectFmt("1:1: error: expected optional enum literal\n", "{f}", .{diag});3511 try std.testing.expectFmt("1:1: error: expected optional enum literal\n", "{f}", .{diag});
3443 }3512 }
...@@ -3466,3 +3535,30 @@ test "std.zon stop on node" {...@@ -3466,3 +3535,30 @@ test "std.zon stop on node" {
3466 try std.testing.expectEqual(Zoir.Node{ .float_literal = 1.23 }, result.get(diag.zoir));3535 try std.testing.expectEqual(Zoir.Node{ .float_literal = 1.23 }, result.get(diag.zoir));
3467 }3536 }
3468}3537}
3538
3539test "std.zon no alloc" {
3540 const gpa = std.testing.allocator;
3541
3542 try std.testing.expectEqual(
3543 [3]u8{ 1, 2, 3 },
3544 try fromSlice([3]u8, gpa, ".{ 1, 2, 3 }", null, .{}),
3545 );
3546
3547 const Nested = struct { u8, u8, struct { u8, u8 } };
3548
3549 var ast = try std.zig.Ast.parse(gpa, ".{ 1, 2, .{ 3, 4 } }", .zon);
3550 defer ast.deinit(gpa);
3551
3552 var zoir = try ZonGen.generate(gpa, ast, .{ .parse_str_lits = false });
3553 defer zoir.deinit(gpa);
3554
3555 try std.testing.expectEqual(
3556 Nested{ 1, 2, .{ 3, 4 } },
3557 try fromZoir(Nested, ast, zoir, null, .{}),
3558 );
3559
3560 try std.testing.expectEqual(
3561 Nested{ 1, 2, .{ 3, 4 } },
3562 try fromZoirNode(Nested, ast, zoir, .root, null, .{}),
3563 );
3564}