authorgravatar for mason@anthropicstudios.comMason Remaley <mason@anthropicstudios.com> 2025-02-21 18:40:57-08:00
committergravatar for noreply@github.comGitHub <noreply@github.com> 2025-02-21 21:40:57-05:00
log339b628d4c8a850c6d819e88fb3b84b86e8b5927
treecb31173da17ada279298a0a37224fefed9024f02
parent65e7ede4994237f160e8db558e74da113f886f98
signaturebadge-check Signed by PGP key B5690EEEBB952194

Output `zig targets` as ZON instead of JSON (#22939)

* Adds startTupleField/startStructField, makes pattern in print targets less verbose * Makes some enums into strings * Start/finish renamed to begin/end I feel bad changing this, but I don't know why I named them this way in the first place. Begin/end is consistent with the json API, and with other APIs in the wild that follow this pattern. Better to change now than later.

2 files changed, 277 insertions(+), 189 deletions(-)

lib/std/zon/stringify.zig+196-88
......@@ -438,17 +438,17 @@ pub const SerializeContainerOptions = struct {
438438/// * `multilineString`
439439///
440440/// For manual serialization of containers, see:
441/// * `startStruct`
442/// * `startTuple`
441/// * `beginStruct`
442/// * `beginTuple`
443443///
444444/// # Example
445445/// ```zig
446446/// var sz = serializer(writer, .{});
447/// var vec2 = try sz.startStruct(.{});
447/// var vec2 = try sz.beginStruct(.{});
448448/// try vec2.field("x", 1.5, .{});
449449/// try vec2.fieldPrefix();
450450/// try sz.value(2.5);
451/// try vec2.finish();
451/// try vec2.end();
452452/// ```
453453pub fn Serializer(Writer: type) type {
454454 return struct {
......@@ -525,22 +525,22 @@ pub fn Serializer(Writer: type) type {
525525 }
526526 },
527527 .array => {
528 var container = try self.startTuple(
528 var container = try self.beginTuple(
529529 .{ .whitespace_style = .{ .fields = val.len } },
530530 );
531531 for (val) |item_val| {
532532 try container.fieldArbitraryDepth(item_val, options);
533533 }
534 try container.finish();
534 try container.end();
535535 },
536536 .@"struct" => |@"struct"| if (@"struct".is_tuple) {
537 var container = try self.startTuple(
537 var container = try self.beginTuple(
538538 .{ .whitespace_style = .{ .fields = @"struct".fields.len } },
539539 );
540540 inline for (val) |field_value| {
541541 try container.fieldArbitraryDepth(field_value, options);
542542 }
543 try container.finish();
543 try container.end();
544544 } else {
545545 // Decide which fields to emit
546546 const fields, const skipped: [@"struct".fields.len]bool = if (options.emit_default_optional_fields) b: {
......@@ -562,7 +562,7 @@ pub fn Serializer(Writer: type) type {
562562 };
563563
564564 // Emit those fields
565 var container = try self.startStruct(
565 var container = try self.beginStruct(
566566 .{ .whitespace_style = .{ .fields = fields } },
567567 );
568568 inline for (@"struct".fields, skipped) |field_info, skip| {
......@@ -574,7 +574,7 @@ pub fn Serializer(Writer: type) type {
574574 );
575575 }
576576 }
577 try container.finish();
577 try container.end();
578578 },
579579 .@"union" => |@"union"| {
580580 comptime assert(@"union".tag_type != null);
......@@ -582,7 +582,7 @@ pub fn Serializer(Writer: type) type {
582582 inline else => |pl, tag| if (@TypeOf(pl) == void)
583583 try self.writer.print(".{s}", .{@tagName(tag)})
584584 else {
585 var container = try self.startStruct(.{ .whitespace_style = .{ .fields = 1 } });
585 var container = try self.beginStruct(.{ .whitespace_style = .{ .fields = 1 } });
586586
587587 try container.fieldArbitraryDepth(
588588 @tagName(tag),
......@@ -590,7 +590,7 @@ pub fn Serializer(Writer: type) type {
590590 options,
591591 );
592592
593 try container.finish();
593 try container.end();
594594 },
595595 }
596596 },
......@@ -600,13 +600,13 @@ pub fn Serializer(Writer: type) type {
600600 try self.writer.writeAll("null");
601601 },
602602 .vector => |vector| {
603 var container = try self.startTuple(
603 var container = try self.beginTuple(
604604 .{ .whitespace_style = .{ .fields = vector.len } },
605605 );
606606 for (0..vector.len) |i| {
607607 try container.fieldArbitraryDepth(val[i], options);
608608 }
609 try container.finish();
609 try container.end();
610610 },
611611
612612 else => comptime unreachable,
......@@ -691,18 +691,18 @@ pub fn Serializer(Writer: type) type {
691691 comptime assert(canSerializeType(@TypeOf(val)));
692692 switch (@typeInfo(@TypeOf(val))) {
693693 .@"struct" => {
694 var container = try self.startTuple(.{ .whitespace_style = .{ .fields = val.len } });
694 var container = try self.beginTuple(.{ .whitespace_style = .{ .fields = val.len } });
695695 inline for (val) |item_val| {
696696 try container.fieldArbitraryDepth(item_val, options);
697697 }
698 try container.finish();
698 try container.end();
699699 },
700700 .pointer, .array => {
701 var container = try self.startTuple(.{ .whitespace_style = .{ .fields = val.len } });
701 var container = try self.beginTuple(.{ .whitespace_style = .{ .fields = val.len } });
702702 for (val) |item_val| {
703703 try container.fieldArbitraryDepth(item_val, options);
704704 }
705 try container.finish();
705 try container.end();
706706 },
707707 else => comptime unreachable,
708708 }
......@@ -767,19 +767,19 @@ pub fn Serializer(Writer: type) type {
767767 }
768768
769769 /// Create a `Struct` for writing ZON structs field by field.
770 pub fn startStruct(
770 pub fn beginStruct(
771771 self: *Self,
772772 options: SerializeContainerOptions,
773773 ) Writer.Error!Struct {
774 return Struct.start(self, options);
774 return Struct.begin(self, options);
775775 }
776776
777777 /// Creates a `Tuple` for writing ZON tuples field by field.
778 pub fn startTuple(
778 pub fn beginTuple(
779779 self: *Self,
780780 options: SerializeContainerOptions,
781781 ) Writer.Error!Tuple {
782 return Tuple.start(self, options);
782 return Tuple.begin(self, options);
783783 }
784784
785785 fn indent(self: *Self) Writer.Error!void {
......@@ -812,17 +812,17 @@ pub fn Serializer(Writer: type) type {
812812 pub const Tuple = struct {
813813 container: Container,
814814
815 fn start(parent: *Self, options: SerializeContainerOptions) Writer.Error!Tuple {
815 fn begin(parent: *Self, options: SerializeContainerOptions) Writer.Error!Tuple {
816816 return .{
817 .container = try Container.start(parent, .anon, options),
817 .container = try Container.begin(parent, .anon, options),
818818 };
819819 }
820820
821821 /// Finishes serializing the tuple.
822822 ///
823823 /// Prints a trailing comma as configured when appropriate, and the closing bracket.
824 pub fn finish(self: *Tuple) Writer.Error!void {
825 try self.container.finish();
824 pub fn end(self: *Tuple) Writer.Error!void {
825 try self.container.end();
826826 self.* = undefined;
827827 }
828828
......@@ -855,6 +855,24 @@ pub fn Serializer(Writer: type) type {
855855 try self.container.fieldArbitraryDepth(null, val, options);
856856 }
857857
858 /// Starts a field with a struct as a value. Returns the struct.
859 pub fn beginStructField(
860 self: *Tuple,
861 options: SerializeContainerOptions,
862 ) Writer.Error!Struct {
863 try self.fieldPrefix();
864 return self.container.serializer.beginStruct(options);
865 }
866
867 /// Starts a field with a tuple as a value. Returns the tuple.
868 pub fn beginTupleField(
869 self: *Tuple,
870 options: SerializeContainerOptions,
871 ) Writer.Error!Tuple {
872 try self.fieldPrefix();
873 return self.container.serializer.beginTuple(options);
874 }
875
858876 /// Print a field prefix. This prints any necessary commas, and whitespace as
859877 /// configured. Useful if you want to serialize the field value yourself.
860878 pub fn fieldPrefix(self: *Tuple) Writer.Error!void {
......@@ -866,17 +884,17 @@ pub fn Serializer(Writer: type) type {
866884 pub const Struct = struct {
867885 container: Container,
868886
869 fn start(parent: *Self, options: SerializeContainerOptions) Writer.Error!Struct {
887 fn begin(parent: *Self, options: SerializeContainerOptions) Writer.Error!Struct {
870888 return .{
871 .container = try Container.start(parent, .named, options),
889 .container = try Container.begin(parent, .named, options),
872890 };
873891 }
874892
875893 /// Finishes serializing the struct.
876894 ///
877895 /// Prints a trailing comma as configured when appropriate, and the closing bracket.
878 pub fn finish(self: *Struct) Writer.Error!void {
879 try self.container.finish();
896 pub fn end(self: *Struct) Writer.Error!void {
897 try self.container.end();
880898 self.* = undefined;
881899 }
882900
......@@ -912,6 +930,26 @@ pub fn Serializer(Writer: type) type {
912930 try self.container.fieldArbitraryDepth(name, val, options);
913931 }
914932
933 /// Starts a field with a struct as a value. Returns the struct.
934 pub fn beginStructField(
935 self: *Struct,
936 name: []const u8,
937 options: SerializeContainerOptions,
938 ) Writer.Error!Struct {
939 try self.fieldPrefix(name);
940 return self.container.serializer.beginStruct(options);
941 }
942
943 /// Starts a field with a tuple as a value. Returns the tuple.
944 pub fn beginTupleField(
945 self: *Struct,
946 name: []const u8,
947 options: SerializeContainerOptions,
948 ) Writer.Error!Tuple {
949 try self.fieldPrefix(name);
950 return self.container.serializer.beginTuple(options);
951 }
952
915953 /// Print a field prefix. This prints any necessary commas, the field name (escaped if
916954 /// necessary) and whitespace as configured. Useful if you want to serialize the field
917955 /// value yourself.
......@@ -928,7 +966,7 @@ pub fn Serializer(Writer: type) type {
928966 options: SerializeContainerOptions,
929967 empty: bool,
930968
931 fn start(
969 fn begin(
932970 sz: *Self,
933971 field_style: FieldStyle,
934972 options: SerializeContainerOptions,
......@@ -943,7 +981,7 @@ pub fn Serializer(Writer: type) type {
943981 };
944982 }
945983
946 fn finish(self: *Container) Writer.Error!void {
984 fn end(self: *Container) Writer.Error!void {
947985 if (self.options.shouldWrap()) self.serializer.indent_level -|= 1;
948986 if (!self.empty) {
949987 if (self.options.shouldWrap()) {
......@@ -1139,52 +1177,52 @@ test "std.zon stringify whitespace, low level API" {
11391177
11401178 // Empty containers
11411179 {
1142 var container = try sz.startStruct(.{});
1143 try container.finish();
1180 var container = try sz.beginStruct(.{});
1181 try container.end();
11441182 try std.testing.expectEqualStrings(".{}", buf.items);
11451183 buf.clearRetainingCapacity();
11461184 }
11471185
11481186 {
1149 var container = try sz.startTuple(.{});
1150 try container.finish();
1187 var container = try sz.beginTuple(.{});
1188 try container.end();
11511189 try std.testing.expectEqualStrings(".{}", buf.items);
11521190 buf.clearRetainingCapacity();
11531191 }
11541192
11551193 {
1156 var container = try sz.startStruct(.{ .whitespace_style = .{ .wrap = false } });
1157 try container.finish();
1194 var container = try sz.beginStruct(.{ .whitespace_style = .{ .wrap = false } });
1195 try container.end();
11581196 try std.testing.expectEqualStrings(".{}", buf.items);
11591197 buf.clearRetainingCapacity();
11601198 }
11611199
11621200 {
1163 var container = try sz.startTuple(.{ .whitespace_style = .{ .wrap = false } });
1164 try container.finish();
1201 var container = try sz.beginTuple(.{ .whitespace_style = .{ .wrap = false } });
1202 try container.end();
11651203 try std.testing.expectEqualStrings(".{}", buf.items);
11661204 buf.clearRetainingCapacity();
11671205 }
11681206
11691207 {
1170 var container = try sz.startStruct(.{ .whitespace_style = .{ .fields = 0 } });
1171 try container.finish();
1208 var container = try sz.beginStruct(.{ .whitespace_style = .{ .fields = 0 } });
1209 try container.end();
11721210 try std.testing.expectEqualStrings(".{}", buf.items);
11731211 buf.clearRetainingCapacity();
11741212 }
11751213
11761214 {
1177 var container = try sz.startTuple(.{ .whitespace_style = .{ .fields = 0 } });
1178 try container.finish();
1215 var container = try sz.beginTuple(.{ .whitespace_style = .{ .fields = 0 } });
1216 try container.end();
11791217 try std.testing.expectEqualStrings(".{}", buf.items);
11801218 buf.clearRetainingCapacity();
11811219 }
11821220
11831221 // Size 1
11841222 {
1185 var container = try sz.startStruct(.{});
1223 var container = try sz.beginStruct(.{});
11861224 try container.field("a", 1, .{});
1187 try container.finish();
1225 try container.end();
11881226 if (whitespace) {
11891227 try std.testing.expectEqualStrings(
11901228 \\.{
......@@ -1198,9 +1236,9 @@ test "std.zon stringify whitespace, low level API" {
11981236 }
11991237
12001238 {
1201 var container = try sz.startTuple(.{});
1239 var container = try sz.beginTuple(.{});
12021240 try container.field(1, .{});
1203 try container.finish();
1241 try container.end();
12041242 if (whitespace) {
12051243 try std.testing.expectEqualStrings(
12061244 \\.{
......@@ -1214,9 +1252,9 @@ test "std.zon stringify whitespace, low level API" {
12141252 }
12151253
12161254 {
1217 var container = try sz.startStruct(.{ .whitespace_style = .{ .wrap = false } });
1255 var container = try sz.beginStruct(.{ .whitespace_style = .{ .wrap = false } });
12181256 try container.field("a", 1, .{});
1219 try container.finish();
1257 try container.end();
12201258 if (whitespace) {
12211259 try std.testing.expectEqualStrings(".{ .a = 1 }", buf.items);
12221260 } else {
......@@ -1228,9 +1266,9 @@ test "std.zon stringify whitespace, low level API" {
12281266 {
12291267 // We get extra spaces here, since we didn't know up front that there would only be one
12301268 // field.
1231 var container = try sz.startTuple(.{ .whitespace_style = .{ .wrap = false } });
1269 var container = try sz.beginTuple(.{ .whitespace_style = .{ .wrap = false } });
12321270 try container.field(1, .{});
1233 try container.finish();
1271 try container.end();
12341272 if (whitespace) {
12351273 try std.testing.expectEqualStrings(".{ 1 }", buf.items);
12361274 } else {
......@@ -1240,9 +1278,9 @@ test "std.zon stringify whitespace, low level API" {
12401278 }
12411279
12421280 {
1243 var container = try sz.startStruct(.{ .whitespace_style = .{ .fields = 1 } });
1281 var container = try sz.beginStruct(.{ .whitespace_style = .{ .fields = 1 } });
12441282 try container.field("a", 1, .{});
1245 try container.finish();
1283 try container.end();
12461284 if (whitespace) {
12471285 try std.testing.expectEqualStrings(".{ .a = 1 }", buf.items);
12481286 } else {
......@@ -1252,19 +1290,19 @@ test "std.zon stringify whitespace, low level API" {
12521290 }
12531291
12541292 {
1255 var container = try sz.startTuple(.{ .whitespace_style = .{ .fields = 1 } });
1293 var container = try sz.beginTuple(.{ .whitespace_style = .{ .fields = 1 } });
12561294 try container.field(1, .{});
1257 try container.finish();
1295 try container.end();
12581296 try std.testing.expectEqualStrings(".{1}", buf.items);
12591297 buf.clearRetainingCapacity();
12601298 }
12611299
12621300 // Size 2
12631301 {
1264 var container = try sz.startStruct(.{});
1302 var container = try sz.beginStruct(.{});
12651303 try container.field("a", 1, .{});
12661304 try container.field("b", 2, .{});
1267 try container.finish();
1305 try container.end();
12681306 if (whitespace) {
12691307 try std.testing.expectEqualStrings(
12701308 \\.{
......@@ -1279,10 +1317,10 @@ test "std.zon stringify whitespace, low level API" {
12791317 }
12801318
12811319 {
1282 var container = try sz.startTuple(.{});
1320 var container = try sz.beginTuple(.{});
12831321 try container.field(1, .{});
12841322 try container.field(2, .{});
1285 try container.finish();
1323 try container.end();
12861324 if (whitespace) {
12871325 try std.testing.expectEqualStrings(
12881326 \\.{
......@@ -1297,10 +1335,10 @@ test "std.zon stringify whitespace, low level API" {
12971335 }
12981336
12991337 {
1300 var container = try sz.startStruct(.{ .whitespace_style = .{ .wrap = false } });
1338 var container = try sz.beginStruct(.{ .whitespace_style = .{ .wrap = false } });
13011339 try container.field("a", 1, .{});
13021340 try container.field("b", 2, .{});
1303 try container.finish();
1341 try container.end();
13041342 if (whitespace) {
13051343 try std.testing.expectEqualStrings(".{ .a = 1, .b = 2 }", buf.items);
13061344 } else {
......@@ -1310,10 +1348,10 @@ test "std.zon stringify whitespace, low level API" {
13101348 }
13111349
13121350 {
1313 var container = try sz.startTuple(.{ .whitespace_style = .{ .wrap = false } });
1351 var container = try sz.beginTuple(.{ .whitespace_style = .{ .wrap = false } });
13141352 try container.field(1, .{});
13151353 try container.field(2, .{});
1316 try container.finish();
1354 try container.end();
13171355 if (whitespace) {
13181356 try std.testing.expectEqualStrings(".{ 1, 2 }", buf.items);
13191357 } else {
......@@ -1323,10 +1361,10 @@ test "std.zon stringify whitespace, low level API" {
13231361 }
13241362
13251363 {
1326 var container = try sz.startStruct(.{ .whitespace_style = .{ .fields = 2 } });
1364 var container = try sz.beginStruct(.{ .whitespace_style = .{ .fields = 2 } });
13271365 try container.field("a", 1, .{});
13281366 try container.field("b", 2, .{});
1329 try container.finish();
1367 try container.end();
13301368 if (whitespace) {
13311369 try std.testing.expectEqualStrings(".{ .a = 1, .b = 2 }", buf.items);
13321370 } else {
......@@ -1336,10 +1374,10 @@ test "std.zon stringify whitespace, low level API" {
13361374 }
13371375
13381376 {
1339 var container = try sz.startTuple(.{ .whitespace_style = .{ .fields = 2 } });
1377 var container = try sz.beginTuple(.{ .whitespace_style = .{ .fields = 2 } });
13401378 try container.field(1, .{});
13411379 try container.field(2, .{});
1342 try container.finish();
1380 try container.end();
13431381 if (whitespace) {
13441382 try std.testing.expectEqualStrings(".{ 1, 2 }", buf.items);
13451383 } else {
......@@ -1350,11 +1388,11 @@ test "std.zon stringify whitespace, low level API" {
13501388
13511389 // Size 3
13521390 {
1353 var container = try sz.startStruct(.{});
1391 var container = try sz.beginStruct(.{});
13541392 try container.field("a", 1, .{});
13551393 try container.field("b", 2, .{});
13561394 try container.field("c", 3, .{});
1357 try container.finish();
1395 try container.end();
13581396 if (whitespace) {
13591397 try std.testing.expectEqualStrings(
13601398 \\.{
......@@ -1370,11 +1408,11 @@ test "std.zon stringify whitespace, low level API" {
13701408 }
13711409
13721410 {
1373 var container = try sz.startTuple(.{});
1411 var container = try sz.beginTuple(.{});
13741412 try container.field(1, .{});
13751413 try container.field(2, .{});
13761414 try container.field(3, .{});
1377 try container.finish();
1415 try container.end();
13781416 if (whitespace) {
13791417 try std.testing.expectEqualStrings(
13801418 \\.{
......@@ -1390,11 +1428,11 @@ test "std.zon stringify whitespace, low level API" {
13901428 }
13911429
13921430 {
1393 var container = try sz.startStruct(.{ .whitespace_style = .{ .wrap = false } });
1431 var container = try sz.beginStruct(.{ .whitespace_style = .{ .wrap = false } });
13941432 try container.field("a", 1, .{});
13951433 try container.field("b", 2, .{});
13961434 try container.field("c", 3, .{});
1397 try container.finish();
1435 try container.end();
13981436 if (whitespace) {
13991437 try std.testing.expectEqualStrings(".{ .a = 1, .b = 2, .c = 3 }", buf.items);
14001438 } else {
......@@ -1404,11 +1442,11 @@ test "std.zon stringify whitespace, low level API" {
14041442 }
14051443
14061444 {
1407 var container = try sz.startTuple(.{ .whitespace_style = .{ .wrap = false } });
1445 var container = try sz.beginTuple(.{ .whitespace_style = .{ .wrap = false } });
14081446 try container.field(1, .{});
14091447 try container.field(2, .{});
14101448 try container.field(3, .{});
1411 try container.finish();
1449 try container.end();
14121450 if (whitespace) {
14131451 try std.testing.expectEqualStrings(".{ 1, 2, 3 }", buf.items);
14141452 } else {
......@@ -1418,11 +1456,11 @@ test "std.zon stringify whitespace, low level API" {
14181456 }
14191457
14201458 {
1421 var container = try sz.startStruct(.{ .whitespace_style = .{ .fields = 3 } });
1459 var container = try sz.beginStruct(.{ .whitespace_style = .{ .fields = 3 } });
14221460 try container.field("a", 1, .{});
14231461 try container.field("b", 2, .{});
14241462 try container.field("c", 3, .{});
1425 try container.finish();
1463 try container.end();
14261464 if (whitespace) {
14271465 try std.testing.expectEqualStrings(
14281466 \\.{
......@@ -1438,11 +1476,11 @@ test "std.zon stringify whitespace, low level API" {
14381476 }
14391477
14401478 {
1441 var container = try sz.startTuple(.{ .whitespace_style = .{ .fields = 3 } });
1479 var container = try sz.beginTuple(.{ .whitespace_style = .{ .fields = 3 } });
14421480 try container.field(1, .{});
14431481 try container.field(2, .{});
14441482 try container.field(3, .{});
1445 try container.finish();
1483 try container.end();
14461484 if (whitespace) {
14471485 try std.testing.expectEqualStrings(
14481486 \\.{
......@@ -1459,10 +1497,10 @@ test "std.zon stringify whitespace, low level API" {
14591497
14601498 // Nested objects where the outer container doesn't wrap but the inner containers do
14611499 {
1462 var container = try sz.startStruct(.{ .whitespace_style = .{ .wrap = false } });
1500 var container = try sz.beginStruct(.{ .whitespace_style = .{ .wrap = false } });
14631501 try container.field("first", .{ 1, 2, 3 }, .{});
14641502 try container.field("second", .{ 4, 5, 6 }, .{});
1465 try container.finish();
1503 try container.end();
14661504 if (whitespace) {
14671505 try std.testing.expectEqualStrings(
14681506 \\.{ .first = .{
......@@ -2016,26 +2054,26 @@ test "std.zon depth limits" {
20162054 try sz.value(3, .{});
20172055 try sz.valueArbitraryDepth(maybe_recurse, .{});
20182056
2019 var s = try sz.startStruct(.{});
2057 var s = try sz.beginStruct(.{});
20202058 try std.testing.expectError(error.ExceededMaxDepth, s.fieldMaxDepth("a", 1, .{}, 0));
20212059 try s.fieldMaxDepth("b", 4, .{}, 1);
20222060 try s.field("c", 5, .{});
20232061 try s.fieldArbitraryDepth("d", maybe_recurse, .{});
2024 try s.finish();
2062 try s.end();
20252063
2026 var t = try sz.startTuple(.{});
2064 var t = try sz.beginTuple(.{});
20272065 try std.testing.expectError(error.ExceededMaxDepth, t.fieldMaxDepth(1, .{}, 0));
20282066 try t.fieldMaxDepth(6, .{}, 1);
20292067 try t.field(7, .{});
20302068 try t.fieldArbitraryDepth(maybe_recurse, .{});
2031 try t.finish();
2069 try t.end();
20322070
2033 var a = try sz.startTuple(.{});
2071 var a = try sz.beginTuple(.{});
20342072 try std.testing.expectError(error.ExceededMaxDepth, a.fieldMaxDepth(1, .{}, 0));
20352073 try a.fieldMaxDepth(8, .{}, 1);
20362074 try a.field(9, .{});
20372075 try a.fieldArbitraryDepth(maybe_recurse, .{});
2038 try a.finish();
2076 try a.end();
20392077
20402078 try std.testing.expectEqualStrings(
20412079 \\23.{}.{
......@@ -2315,3 +2353,73 @@ test "std.zon pointers" {
23152353 , val, .{});
23162354 }
23172355}
2356
2357test "std.zon tuple/struct field" {
2358 var buf = std.ArrayList(u8).init(std.testing.allocator);
2359 defer buf.deinit();
2360 var sz = serializer(buf.writer(), .{});
2361
2362 // Test on structs
2363 {
2364 var root = try sz.beginStruct(.{});
2365 {
2366 var tuple = try root.beginTupleField("foo", .{});
2367 try tuple.field(0, .{});
2368 try tuple.field(1, .{});
2369 try tuple.end();
2370 }
2371 {
2372 var strct = try root.beginStructField("bar", .{});
2373 try strct.field("a", 0, .{});
2374 try strct.field("b", 1, .{});
2375 try strct.end();
2376 }
2377 try root.end();
2378
2379 try std.testing.expectEqualStrings(
2380 \\.{
2381 \\ .foo = .{
2382 \\ 0,
2383 \\ 1,
2384 \\ },
2385 \\ .bar = .{
2386 \\ .a = 0,
2387 \\ .b = 1,
2388 \\ },
2389 \\}
2390 , buf.items);
2391 buf.clearRetainingCapacity();
2392 }
2393
2394 // Test on tuples
2395 {
2396 var root = try sz.beginTuple(.{});
2397 {
2398 var tuple = try root.beginTupleField(.{});
2399 try tuple.field(0, .{});
2400 try tuple.field(1, .{});
2401 try tuple.end();
2402 }
2403 {
2404 var strct = try root.beginStructField(.{});
2405 try strct.field("a", 0, .{});
2406 try strct.field("b", 1, .{});
2407 try strct.end();
2408 }
2409 try root.end();
2410
2411 try std.testing.expectEqualStrings(
2412 \\.{
2413 \\ .{
2414 \\ 0,
2415 \\ 1,
2416 \\ },
2417 \\ .{
2418 \\ .a = 0,
2419 \\ .b = 1,
2420 \\ },
2421 \\}
2422 , buf.items);
2423 buf.clearRetainingCapacity();
2424 }
2425}
src/print_targets.zig+81-101
......@@ -40,121 +40,101 @@ pub fn cmdTargets(
4040
4141 var bw = io.bufferedWriter(stdout);
4242 const w = bw.writer();
43 var jws = std.json.writeStream(w, .{ .whitespace = .indent_1 });
43 var sz = std.zon.stringify.serializer(w, .{});
4444
45 try jws.beginObject();
46
47 try jws.objectField("arch");
48 try jws.beginArray();
49 for (meta.fieldNames(Target.Cpu.Arch)) |field| {
50 try jws.write(field);
51 }
52 try jws.endArray();
45 {
46 var root_obj = try sz.beginStruct(.{});
5347
54 try jws.objectField("os");
55 try jws.beginArray();
56 for (meta.fieldNames(Target.Os.Tag)) |field| {
57 try jws.write(field);
58 }
59 try jws.endArray();
48 try root_obj.field("arch", meta.fieldNames(Target.Cpu.Arch), .{});
49 try root_obj.field("os", meta.fieldNames(Target.Os.Tag), .{});
50 try root_obj.field("abi", meta.fieldNames(Target.Abi), .{});
6051
61 try jws.objectField("abi");
62 try jws.beginArray();
63 for (meta.fieldNames(Target.Abi)) |field| {
64 try jws.write(field);
65 }
66 try jws.endArray();
67
68 try jws.objectField("libc");
69 try jws.beginArray();
70 for (std.zig.target.available_libcs) |libc| {
71 const tmp = try std.fmt.allocPrint(allocator, "{s}-{s}-{s}", .{
72 @tagName(libc.arch), @tagName(libc.os), @tagName(libc.abi),
73 });
74 defer allocator.free(tmp);
75 try jws.write(tmp);
76 }
77 try jws.endArray();
78
79 try jws.objectField("glibc");
80 try jws.beginArray();
81 for (glibc_abi.all_versions) |ver| {
82 const tmp = try std.fmt.allocPrint(allocator, "{}", .{ver});
83 defer allocator.free(tmp);
84 try jws.write(tmp);
85 }
86 try jws.endArray();
87
88 try jws.objectField("cpus");
89 try jws.beginObject();
90 for (meta.tags(Target.Cpu.Arch)) |arch| {
91 try jws.objectField(@tagName(arch));
92 try jws.beginObject();
93 for (arch.allCpuModels()) |model| {
94 try jws.objectField(model.name);
95 try jws.beginArray();
96 for (arch.allFeaturesList(), 0..) |feature, i_usize| {
97 const index = @as(Target.Cpu.Feature.Set.Index, @intCast(i_usize));
98 if (model.features.isEnabled(index)) {
99 try jws.write(feature.name);
100 }
52 {
53 var libc_obj = try root_obj.beginTupleField("libc", .{});
54 for (std.zig.target.available_libcs) |libc| {
55 const tmp = try std.fmt.allocPrint(allocator, "{s}-{s}-{s}", .{
56 @tagName(libc.arch), @tagName(libc.os), @tagName(libc.abi),
57 });
58 defer allocator.free(tmp);
59 try libc_obj.field(tmp, .{});
10160 }
102 try jws.endArray();
61 try libc_obj.end();
10362 }
104 try jws.endObject();
105 }
106 try jws.endObject();
107
108 try jws.objectField("cpuFeatures");
109 try jws.beginObject();
110 for (meta.tags(Target.Cpu.Arch)) |arch| {
111 try jws.objectField(@tagName(arch));
112 try jws.beginArray();
113 for (arch.allFeaturesList()) |feature| {
114 try jws.write(feature.name);
63
64 {
65 var glibc_obj = try root_obj.beginTupleField("glibc", .{});
66 for (glibc_abi.all_versions) |ver| {
67 const tmp = try std.fmt.allocPrint(allocator, "{}", .{ver});
68 defer allocator.free(tmp);
69 try glibc_obj.field(tmp, .{});
70 }
71 try glibc_obj.end();
11572 }
116 try jws.endArray();
117 }
118 try jws.endObject();
11973
120 try jws.objectField("native");
121 try jws.beginObject();
122 {
123 const triple = try native_target.zigTriple(allocator);
124 defer allocator.free(triple);
125 try jws.objectField("triple");
126 try jws.write(triple);
127 }
128 {
129 try jws.objectField("cpu");
130 try jws.beginObject();
131 try jws.objectField("arch");
132 try jws.write(@tagName(native_target.cpu.arch));
74 {
75 var cpus_obj = try root_obj.beginStructField("cpus", .{});
76 for (meta.tags(Target.Cpu.Arch)) |arch| {
77 var arch_obj = try cpus_obj.beginStructField(@tagName(arch), .{});
78 for (arch.allCpuModels()) |model| {
79 var features = try arch_obj.beginTupleField(model.name, .{});
80 for (arch.allFeaturesList(), 0..) |feature, i_usize| {
81 const index = @as(Target.Cpu.Feature.Set.Index, @intCast(i_usize));
82 if (model.features.isEnabled(index)) {
83 try features.field(feature.name, .{});
84 }
85 }
86 try features.end();
87 }
88 try arch_obj.end();
89 }
90 try cpus_obj.end();
91 }
13392
134 try jws.objectField("name");
135 const cpu = native_target.cpu;
136 try jws.write(cpu.model.name);
93 {
94 var cpu_features_obj = try root_obj.beginStructField("cpu_features", .{});
95 for (meta.tags(Target.Cpu.Arch)) |arch| {
96 var arch_features = try cpu_features_obj.beginTupleField(@tagName(arch), .{});
97 for (arch.allFeaturesList()) |feature| {
98 try arch_features.field(feature.name, .{});
99 }
100 try arch_features.end();
101 }
102 try cpu_features_obj.end();
103 }
137104
138105 {
139 try jws.objectField("features");
140 try jws.beginArray();
141 for (native_target.cpu.arch.allFeaturesList(), 0..) |feature, i_usize| {
142 const index = @as(Target.Cpu.Feature.Set.Index, @intCast(i_usize));
143 if (cpu.features.isEnabled(index)) {
144 try jws.write(feature.name);
106 var native_obj = try root_obj.beginStructField("native", .{});
107 {
108 const triple = try native_target.zigTriple(allocator);
109 defer allocator.free(triple);
110 try native_obj.field("triple", triple, .{});
111 }
112 {
113 var cpu_obj = try native_obj.beginStructField("cpu", .{});
114 try cpu_obj.field("arch", @tagName(native_target.cpu.arch), .{});
115
116 try cpu_obj.field("name", native_target.cpu.model.name, .{});
117
118 {
119 var features = try native_obj.beginTupleField("features", .{});
120 for (native_target.cpu.arch.allFeaturesList(), 0..) |feature, i_usize| {
121 const index = @as(Target.Cpu.Feature.Set.Index, @intCast(i_usize));
122 if (native_target.cpu.features.isEnabled(index)) {
123 try features.field(feature.name, .{});
124 }
125 }
126 try features.end();
145127 }
128 try cpu_obj.end();
146129 }
147 try jws.endArray();
130
131 try native_obj.field("os", @tagName(native_target.os.tag), .{});
132 try native_obj.field("abi", @tagName(native_target.abi), .{});
133 try native_obj.end();
148134 }
149 try jws.endObject();
150 }
151 try jws.objectField("os");
152 try jws.write(@tagName(native_target.os.tag));
153 try jws.objectField("abi");
154 try jws.write(@tagName(native_target.abi));
155 try jws.endObject();
156135
157 try jws.endObject();
136 try root_obj.end();
137 }
158138
159139 try w.writeByte('\n');
160140 return bw.flush();