@zigc/lib 0.17.0-dev.644 → 0.17.0-dev.667

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (124) hide show
  1. package/compiler/Maker/ScannedConfig.zig +4 -3
  2. package/compiler/Maker/Step/FindProgram.zig +2 -2
  3. package/compiler/Maker/Watch/FsEvents.zig +3 -2
  4. package/compiler/Maker.zig +2 -2
  5. package/compiler/aro/aro/Attribute.zig +52 -51
  6. package/compiler/aro/aro/Compilation.zig +5 -5
  7. package/compiler/aro/aro/Diagnostics.zig +7 -7
  8. package/compiler/aro/aro/Parser.zig +2 -2
  9. package/compiler/aro/aro/Tree.zig +11 -11
  10. package/compiler/aro/aro/features.zig +4 -4
  11. package/compiler/aro/aro/text_literal.zig +2 -2
  12. package/compiler/aro/backend/Interner.zig +14 -13
  13. package/compiler/configurer.zig +2 -2
  14. package/compiler/resinator/bmp.zig +3 -2
  15. package/compiler/resinator/code_pages.zig +14 -12
  16. package/compiler/resinator/cvtres.zig +11 -10
  17. package/compiler/resinator/errors.zig +18 -22
  18. package/compiler/resinator/lang.zig +7 -7
  19. package/compiler/resinator/parse.zig +1 -1
  20. package/compiler/translate-c/ast.zig +6 -6
  21. package/docs/wasm/markdown/Document.zig +3 -3
  22. package/docs/wasm/markdown/Parser.zig +3 -3
  23. package/libc/include/powerpc-linux-gnu/bits/struct_mutex.h +2 -2
  24. package/libc/include/s390x-linux-gnu/bits/fenv.h +2 -2
  25. package/libc/include/s390x-linux-gnu/bits/struct_mutex.h +2 -2
  26. package/libc/include/x86-linux-gnu/bits/struct_mutex.h +2 -2
  27. package/package.json +1 -1
  28. package/std/Build/Cache.zig +2 -2
  29. package/std/Build/Configuration.zig +19 -16
  30. package/std/Build/Step/ConfigHeader.zig +3 -2
  31. package/std/Build/Step/Options.zig +28 -22
  32. package/std/Build.zig +52 -53
  33. package/std/Io/Kqueue.zig +2 -2
  34. package/std/Io/Reader.zig +1 -1
  35. package/std/Io/Threaded.zig +18 -15
  36. package/std/Io/Uring.zig +2 -2
  37. package/std/Io/Writer.zig +18 -18
  38. package/std/Io/net.zig +3 -1
  39. package/std/Io.zig +7 -6
  40. package/std/Progress.zig +2 -2
  41. package/std/Target/aarch64.zig +2 -2
  42. package/std/Target/alpha.zig +2 -2
  43. package/std/Target/amdgcn.zig +2 -2
  44. package/std/Target/arc.zig +2 -2
  45. package/std/Target/arm.zig +2 -2
  46. package/std/Target/avr.zig +2 -2
  47. package/std/Target/bpf.zig +2 -2
  48. package/std/Target/csky.zig +2 -2
  49. package/std/Target/hexagon.zig +2 -2
  50. package/std/Target/hppa.zig +2 -2
  51. package/std/Target/kvx.zig +2 -2
  52. package/std/Target/lanai.zig +2 -2
  53. package/std/Target/loongarch.zig +2 -2
  54. package/std/Target/m68k.zig +2 -2
  55. package/std/Target/mips.zig +2 -2
  56. package/std/Target/msp430.zig +2 -2
  57. package/std/Target/nvptx.zig +2 -2
  58. package/std/Target/powerpc.zig +2 -2
  59. package/std/Target/propeller.zig +2 -2
  60. package/std/Target/riscv.zig +2 -2
  61. package/std/Target/s390x.zig +2 -2
  62. package/std/Target/sparc.zig +2 -2
  63. package/std/Target/spirv.zig +2 -2
  64. package/std/Target/ve.zig +2 -2
  65. package/std/Target/wasm.zig +2 -2
  66. package/std/Target/x86.zig +2 -2
  67. package/std/Target/xcore.zig +2 -2
  68. package/std/Target/xtensa.zig +2 -2
  69. package/std/Target.zig +4 -4
  70. package/std/c/darwin.zig +1 -1
  71. package/std/coff.zig +1 -1
  72. package/std/crypto/aes/aesni.zig +1 -1
  73. package/std/crypto/aes/armcrypto.zig +4 -4
  74. package/std/crypto/aes/soft.zig +4 -4
  75. package/std/crypto/aes.zig +12 -0
  76. package/std/crypto/codecs/asn1/Oid.zig +8 -8
  77. package/std/crypto/codecs/asn1/der/Decoder.zig +7 -7
  78. package/std/crypto/codecs/asn1/der/Encoder.zig +10 -8
  79. package/std/crypto/phc_encoding.zig +23 -20
  80. package/std/crypto/timing_safe.zig +1 -1
  81. package/std/crypto/tls/Client.zig +3 -3
  82. package/std/crypto/tls.zig +1 -1
  83. package/std/debug/Dwarf/Unwind/VirtualMachine.zig +11 -5
  84. package/std/debug/ElfFile.zig +12 -8
  85. package/std/debug/MachOFile.zig +2 -2
  86. package/std/debug/SelfInfo/MachO.zig +44 -17
  87. package/std/debug/SelfInfo/Windows.zig +2 -2
  88. package/std/elf.zig +7 -7
  89. package/std/enums.zig +66 -67
  90. package/std/gpu.zig +1 -1
  91. package/std/hash/auto_hash.zig +8 -8
  92. package/std/hash/verify.zig +3 -3
  93. package/std/http/Client.zig +2 -2
  94. package/std/json/Stringify.zig +14 -14
  95. package/std/json/static.zig +47 -31
  96. package/std/lang.zig +65 -97
  97. package/std/math.zig +2 -2
  98. package/std/mem/Allocator.zig +9 -9
  99. package/std/mem.zig +86 -102
  100. package/std/meta/trailer_flags.zig +26 -19
  101. package/std/meta.zig +131 -171
  102. package/std/multi_array_list.zig +49 -57
  103. package/std/os/uefi/protocol/device_path.zig +8 -7
  104. package/std/os/uefi/tables/boot_services.zig +1 -1
  105. package/std/os/windows.zig +9 -15
  106. package/std/sort/pdq.zig +22 -5
  107. package/std/start.zig +6 -6
  108. package/std/testing/Smith.zig +35 -21
  109. package/std/testing.zig +15 -15
  110. package/std/zig/Ast.zig +4 -4
  111. package/std/zig/AstGen.zig +42 -42
  112. package/std/zig/ErrorBundle.zig +16 -13
  113. package/std/zig/LibCInstallation.zig +11 -11
  114. package/std/zig/Parse.zig +6 -6
  115. package/std/zig/Zir.zig +10 -10
  116. package/std/zig/c_translation/helpers.zig +2 -2
  117. package/std/zig/llvm/BitcodeReader.zig +3 -3
  118. package/std/zig/llvm/Builder.zig +124 -93
  119. package/std/zig/llvm/bitcode_writer.zig +4 -4
  120. package/std/zig/system/windows.zig +11 -11
  121. package/std/zig/system.zig +4 -4
  122. package/std/zig.zig +4 -4
  123. package/std/zon/Serializer.zig +28 -23
  124. package/std/zon/parse.zig +83 -61
package/std/lang.zig CHANGED
@@ -596,13 +596,8 @@ pub const Type = union(enum) {
596
596
  /// therefore must be kept in sync with the compiler implementation.
597
597
  pub const Pointer = struct {
598
598
  size: Size,
599
- is_const: bool,
600
- is_volatile: bool,
601
- /// `null` means implicit alignment, which is equivalent to `@alignOf(child)`.
602
- alignment: ?usize,
603
- address_space: AddressSpace,
599
+ attrs: Attributes,
604
600
  child: type,
605
- is_allowzero: bool,
606
601
 
607
602
  /// The type of the sentinel is the element type of the pointer, which is
608
603
  /// the value of the `child` field in this struct. However there is no way
@@ -667,44 +662,40 @@ pub const Type = union(enum) {
667
662
 
668
663
  /// This data structure is used by the Zig language code generation and
669
664
  /// therefore must be kept in sync with the compiler implementation.
670
- pub const StructField = struct {
671
- name: [:0]const u8,
672
- type: type,
673
- /// The type of the default value is the type of this struct field, which
674
- /// is the value of the `type` field in this struct. However there is no
675
- /// way to refer to that type here, so we use `*const anyopaque`.
676
- /// See also: `defaultValue`.
677
- default_value_ptr: ?*const anyopaque,
678
- is_comptime: bool,
679
- /// `null` means the field alignment was not explicitly specified. The
680
- /// field will still be aligned to at least `@alignOf` its `type`.
681
- alignment: ?usize,
682
-
683
- /// Loads the field's default value from `default_value_ptr`.
684
- /// Returns `null` if the field has no default value.
685
- pub inline fn defaultValue(comptime sf: StructField) ?sf.type {
686
- const dp: *const sf.type = @ptrCast(@alignCast(sf.default_value_ptr orelse return null));
687
- return dp.*;
688
- }
665
+ pub const Struct = struct {
666
+ is_tuple: bool,
667
+ layout: ContainerLayout,
668
+ /// Always `null` if `layout != .@"packed"`.
669
+ backing_integer: ?type,
689
670
 
690
- /// This data structure is used by the Zig language code generation and
691
- /// therefore must be kept in sync with the compiler implementation.
692
- pub const Attributes = struct {
671
+ field_names: []const [:0]const u8,
672
+ /// Guaranteed to have the same length as `field_names`.
673
+ field_types: []const type,
674
+ /// Guaranteed to have the same length as `field_names`.
675
+ field_attrs: []const FieldAttributes,
676
+
677
+ decl_names: []const [:0]const u8,
678
+
679
+ pub const FieldAttributes = struct {
693
680
  @"comptime": bool = false,
681
+ /// `null` means the field alignment is not explicitly specified. The field will still
682
+ /// be aligned to at least `@alignOf` the field type.
694
683
  @"align": ?usize = null,
684
+ /// The type of the default value is the type of this struct field. However, that type
685
+ /// is not known here, so we use a type-erased pointer instead, which must be cast to
686
+ /// a pointer to the field type.
687
+ ///
688
+ /// See also: `defaultValue`.
695
689
  default_value_ptr: ?*const anyopaque = null,
696
- };
697
- };
698
690
 
699
- /// This data structure is used by the Zig language code generation and
700
- /// therefore must be kept in sync with the compiler implementation.
701
- pub const Struct = struct {
702
- layout: ContainerLayout,
703
- /// Only valid if layout is .@"packed"
704
- backing_integer: ?type = null,
705
- fields: []const StructField,
706
- decls: []const Declaration,
707
- is_tuple: bool,
691
+ /// Loads the field's default value from `default_value_ptr`.
692
+ /// `FieldType` must exactly match the corresponding element of `Struct.field_types`.
693
+ /// Returns `null` if the field has no default value.
694
+ pub inline fn defaultValue(comptime attrs: FieldAttributes, comptime FieldType: type) ?FieldType {
695
+ const dp: *const FieldType = @ptrCast(@alignCast(attrs.default_value_ptr orelse return null));
696
+ return dp.*;
697
+ }
698
+ };
708
699
  };
709
700
 
710
701
  /// This data structure is used by the Zig language code generation and
@@ -722,48 +713,25 @@ pub const Type = union(enum) {
722
713
 
723
714
  /// This data structure is used by the Zig language code generation and
724
715
  /// therefore must be kept in sync with the compiler implementation.
725
- pub const Error = struct {
726
- name: [:0]const u8,
727
- };
728
-
729
- /// This data structure is used by the Zig language code generation and
730
- /// therefore must be kept in sync with the compiler implementation.
731
- pub const ErrorSet = ?[]const Error;
732
-
733
- /// This data structure is used by the Zig language code generation and
734
- /// therefore must be kept in sync with the compiler implementation.
735
- pub const EnumField = struct {
736
- name: [:0]const u8,
737
- value: comptime_int,
716
+ pub const ErrorSet = struct {
717
+ error_names: ?[]const [:0]const u8,
738
718
  };
739
719
 
740
720
  /// This data structure is used by the Zig language code generation and
741
721
  /// therefore must be kept in sync with the compiler implementation.
742
722
  pub const Enum = struct {
743
723
  tag_type: type,
744
- fields: []const EnumField,
745
- decls: []const Declaration,
746
- is_exhaustive: bool,
724
+ mode: Mode,
747
725
 
748
- /// This data structure is used by the Zig language code generation and
749
- /// therefore must be kept in sync with the compiler implementation.
750
- pub const Mode = enum { exhaustive, nonexhaustive };
751
- };
726
+ field_names: []const [:0]const u8,
727
+ /// Guaranteed to have the same length as `field_names`.
728
+ field_values: []const comptime_int,
752
729
 
753
- /// This data structure is used by the Zig language code generation and
754
- /// therefore must be kept in sync with the compiler implementation.
755
- pub const UnionField = struct {
756
- name: [:0]const u8,
757
- type: type,
758
- /// `null` means the field alignment was not explicitly specified. The
759
- /// field will still be aligned to at least `@alignOf` its `type`.
760
- alignment: ?usize,
730
+ decl_names: []const [:0]const u8,
761
731
 
762
732
  /// This data structure is used by the Zig language code generation and
763
733
  /// therefore must be kept in sync with the compiler implementation.
764
- pub const Attributes = struct {
765
- @"align": ?usize = null,
766
- };
734
+ pub const Mode = enum { exhaustive, nonexhaustive };
767
735
  };
768
736
 
769
737
  /// This data structure is used by the Zig language code generation and
@@ -771,36 +739,42 @@ pub const Type = union(enum) {
771
739
  pub const Union = struct {
772
740
  layout: ContainerLayout,
773
741
  tag_type: ?type,
774
- fields: []const UnionField,
775
- decls: []const Declaration,
742
+ /// Always `null` if `layout != .@"packed"`.
743
+ backing_integer: ?type,
744
+
745
+ field_names: []const [:0]const u8,
746
+ /// Guaranteed to have the same length as `field_names`.
747
+ field_types: []const type,
748
+ /// Guaranteed to have the same length as `field_names`.
749
+ field_attrs: []const FieldAttributes,
750
+
751
+ decl_names: []const [:0]const u8,
752
+
753
+ pub const FieldAttributes = struct {
754
+ /// `null` means the field alignment is not explicitly specified. The field will still
755
+ /// be aligned to at least `@alignOf` the field type.
756
+ @"align": ?usize = null,
757
+ };
776
758
  };
777
759
 
778
760
  /// This data structure is used by the Zig language code generation and
779
761
  /// therefore must be kept in sync with the compiler implementation.
780
762
  pub const Fn = struct {
781
- calling_convention: CallingConvention,
763
+ attrs: Attributes,
782
764
  is_generic: bool,
783
- is_var_args: bool,
784
- /// TODO change the language spec to make this not optional.
765
+ /// `null` means the return type is generic, i.e. it depends on a function argument.
785
766
  return_type: ?type,
786
- params: []const Param,
787
767
 
788
- /// This data structure is used by the Zig language code generation and
789
- /// therefore must be kept in sync with the compiler implementation.
790
- pub const Param = struct {
791
- is_generic: bool,
792
- is_noalias: bool,
793
- type: ?type,
794
-
795
- /// This data structure is used by the Zig language code generation and
796
- /// therefore must be kept in sync with the compiler implementation.
797
- pub const Attributes = struct {
798
- @"noalias": bool = false,
799
- };
768
+ /// A `null` element represents either an `anytype` parameter, or a parameter with a generic
769
+ /// type, i.e. where the type depends on a previous function argument.
770
+ param_types: []const ?type,
771
+ /// Guaranteed to have the same length as `param_types`.
772
+ param_attrs: []const ParamAttributes,
773
+
774
+ pub const ParamAttributes = struct {
775
+ @"noalias": bool = false,
800
776
  };
801
777
 
802
- /// This data structure is used by the Zig language code generation and
803
- /// therefore must be kept in sync with the compiler implementation.
804
778
  pub const Attributes = struct {
805
779
  @"callconv": CallingConvention = .auto,
806
780
  varargs: bool = false,
@@ -810,7 +784,7 @@ pub const Type = union(enum) {
810
784
  /// This data structure is used by the Zig language code generation and
811
785
  /// therefore must be kept in sync with the compiler implementation.
812
786
  pub const Opaque = struct {
813
- decls: []const Declaration,
787
+ decl_names: []const [:0]const u8,
814
788
  };
815
789
 
816
790
  /// This data structure is used by the Zig language code generation and
@@ -831,12 +805,6 @@ pub const Type = union(enum) {
831
805
  len: comptime_int,
832
806
  child: type,
833
807
  };
834
-
835
- /// This data structure is used by the Zig language code generation and
836
- /// therefore must be kept in sync with the compiler implementation.
837
- pub const Declaration = struct {
838
- name: [:0]const u8,
839
- };
840
808
  };
841
809
 
842
810
  /// This data structure is used by the Zig language code generation and
package/std/math.zig CHANGED
@@ -1648,8 +1648,8 @@ pub const CompareOperator = enum {
1648
1648
  }
1649
1649
 
1650
1650
  test reverse {
1651
- inline for (@typeInfo(CompareOperator).@"enum".fields) |op_field| {
1652
- const op = @as(CompareOperator, @enumFromInt(op_field.value));
1651
+ inline for (@typeInfo(CompareOperator).@"enum".field_values) |op_field_value| {
1652
+ const op = @as(CompareOperator, @enumFromInt(op_field_value));
1653
1653
  try testing.expect(compare(2, op, 3) == compare(3, op.reverse(), 2));
1654
1654
  try testing.expect(compare(3, op, 3) == compare(3, op.reverse(), 3));
1655
1655
  try testing.expect(compare(4, op, 3) == compare(3, op.reverse(), 4));
@@ -183,7 +183,7 @@ pub fn destroy(self: Allocator, ptr: anytype) void {
183
183
  const non_const_ptr = @as([*]u8, @ptrCast(@constCast(ptr)));
184
184
  self.rawFree(
185
185
  non_const_ptr[0..@sizeOf(T)],
186
- .fromByteUnits(info.alignment orelse @alignOf(T)),
186
+ .fromByteUnits(info.attrs.@"align" orelse @alignOf(T)),
187
187
  @returnAddress(),
188
188
  );
189
189
  }
@@ -331,7 +331,7 @@ pub fn resize(self: Allocator, allocation: anytype, new_len: usize) bool {
331
331
  const new_len_bytes = math.mul(usize, @sizeOf(T), new_len) catch return false;
332
332
  return self.rawResize(
333
333
  old_memory,
334
- .fromByteUnits(slice_info.alignment orelse @alignOf(T)),
334
+ .fromByteUnits(slice_info.attrs.@"align" orelse @alignOf(T)),
335
335
  new_len_bytes,
336
336
  @returnAddress(),
337
337
  );
@@ -377,7 +377,7 @@ pub fn remap(self: Allocator, allocation: anytype, new_len: usize) ?@TypeOf(allo
377
377
  const new_len_bytes = math.mul(usize, @sizeOf(T), new_len) catch return null;
378
378
  const new_ptr = self.rawRemap(
379
379
  old_memory,
380
- .fromByteUnits(slice_info.alignment orelse @alignOf(T)),
380
+ .fromByteUnits(slice_info.attrs.@"align" orelse @alignOf(T)),
381
381
  new_len_bytes,
382
382
  @returnAddress(),
383
383
  ) orelse return null;
@@ -412,11 +412,11 @@ pub fn reallocAdvanced(
412
412
  comptime assert(slice_info.size == .slice);
413
413
  const T = slice_info.child;
414
414
  if (old_mem.len == 0) {
415
- return self.allocAdvancedWithRetAddr(T, .fromByteUnitsOptional(slice_info.alignment), new_n, return_address);
415
+ return self.allocAdvancedWithRetAddr(T, .fromByteUnitsOptional(slice_info.attrs.@"align"), new_n, return_address);
416
416
  }
417
417
  if (new_n == 0) {
418
418
  self.free(old_mem);
419
- const alignment = slice_info.alignment orelse @alignOf(T);
419
+ const alignment = slice_info.attrs.@"align" orelse @alignOf(T);
420
420
  const addr = comptime std.mem.alignBackward(usize, math.maxInt(usize), alignment);
421
421
  const ptr: *align(alignment) [0]T = @ptrFromInt(addr);
422
422
  return ptr;
@@ -425,16 +425,16 @@ pub fn reallocAdvanced(
425
425
  const old_byte_slice: []u8 = @ptrCast(@constCast(mem.absorbSentinel(old_mem)));
426
426
  const byte_count = math.mul(usize, @sizeOf(T), new_n) catch return error.OutOfMemory;
427
427
  // Note: can't set shrunk memory to undefined as memory shouldn't be modified on realloc failure
428
- if (self.rawRemap(old_byte_slice, .fromByteUnits(slice_info.alignment orelse @alignOf(T)), byte_count, return_address)) |p| {
428
+ if (self.rawRemap(old_byte_slice, .fromByteUnits(slice_info.attrs.@"align" orelse @alignOf(T)), byte_count, return_address)) |p| {
429
429
  return @ptrCast(@alignCast(p[0..byte_count]));
430
430
  }
431
431
 
432
- const new_mem = self.rawAlloc(byte_count, .fromByteUnits(slice_info.alignment orelse @alignOf(T)), return_address) orelse
432
+ const new_mem = self.rawAlloc(byte_count, .fromByteUnits(slice_info.attrs.@"align" orelse @alignOf(T)), return_address) orelse
433
433
  return error.OutOfMemory;
434
434
  const copy_len = @min(byte_count, old_byte_slice.len);
435
435
  @memcpy(new_mem[0..copy_len], old_byte_slice[0..copy_len]);
436
436
  @memset(old_byte_slice, undefined);
437
- self.rawFree(old_byte_slice, .fromByteUnits(slice_info.alignment orelse @alignOf(T)), return_address);
437
+ self.rawFree(old_byte_slice, .fromByteUnits(slice_info.attrs.@"align" orelse @alignOf(T)), return_address);
438
438
 
439
439
  return @ptrCast(@alignCast(new_mem[0..byte_count]));
440
440
  }
@@ -448,7 +448,7 @@ pub fn free(self: Allocator, memory: anytype) void {
448
448
  const bytes: []u8 = @ptrCast(@constCast(mem.absorbSentinel(memory)));
449
449
  if (bytes.len == 0) return;
450
450
  @memset(bytes, undefined);
451
- self.rawFree(bytes, .fromByteUnits(slice_info.alignment orelse @alignOf(slice_info.child)), @returnAddress());
451
+ self.rawFree(bytes, .fromByteUnits(slice_info.attrs.@"align" orelse @alignOf(slice_info.child)), @returnAddress());
452
452
  }
453
453
 
454
454
  /// Copies `m` to newly allocated memory. Caller owns the memory.
package/std/mem.zig CHANGED
@@ -297,9 +297,13 @@ pub fn zeroes(comptime T: type) T {
297
297
  return item;
298
298
  } else {
299
299
  var structure: T = undefined;
300
- inline for (struct_info.fields) |field| {
301
- if (!field.is_comptime) {
302
- @field(structure, field.name) = zeroes(field.type);
300
+ inline for (
301
+ struct_info.field_names,
302
+ struct_info.field_types,
303
+ struct_info.field_attrs,
304
+ ) |field_name, field_type, field_attrs| {
305
+ if (!field_attrs.@"comptime") {
306
+ @field(structure, field_name) = zeroes(field_type);
303
307
  }
304
308
  }
305
309
  return structure;
@@ -321,7 +325,7 @@ pub fn zeroes(comptime T: type) T {
321
325
  return null;
322
326
  },
323
327
  .one, .many => {
324
- if (ptr_info.is_allowzero) return @ptrFromInt(0);
328
+ if (ptr_info.attrs.@"allowzero") return @ptrFromInt(0);
325
329
  @compileError("Only nullable and allowzero pointers can be set to zero.");
326
330
  },
327
331
  }
@@ -471,44 +475,49 @@ pub fn zeroInit(comptime T: type, init: anytype) T {
471
475
  switch (@typeInfo(Init)) {
472
476
  .@"struct" => |init_info| {
473
477
  if (init_info.is_tuple) {
474
- if (init_info.fields.len > struct_info.fields.len) {
478
+ if (init_info.field_names.len > struct_info.field_names.len) {
475
479
  @compileError("Tuple initializer has more elements than there are fields in `" ++ @typeName(T) ++ "`");
476
480
  }
477
481
  } else {
478
- inline for (init_info.fields) |field| {
479
- if (!@hasField(T, field.name)) {
480
- @compileError("Encountered an initializer for `" ++ field.name ++ "`, but it is not a field of " ++ @typeName(T));
482
+ inline for (init_info.field_names) |field_name| {
483
+ if (!@hasField(T, field_name)) {
484
+ @compileError("Encountered an initializer for `" ++ field_name ++ "`, but it is not a field of " ++ @typeName(T));
481
485
  }
482
486
  }
483
487
  }
484
488
 
485
489
  var value: T = if (struct_info.layout == .@"extern") zeroes(T) else undefined;
486
490
 
487
- inline for (struct_info.fields, 0..) |field, i| {
488
- if (field.is_comptime) {
491
+ inline for (
492
+ struct_info.field_names,
493
+ struct_info.field_types,
494
+ struct_info.field_attrs,
495
+ 0..,
496
+ ) |f_name, f_type, f_attr, i| {
497
+ if (f_attr.@"comptime") {
489
498
  continue;
490
499
  }
491
500
 
492
- if (init_info.is_tuple and init_info.fields.len > i) {
493
- @field(value, field.name) = @field(init, init_info.fields[i].name);
494
- } else if (@hasField(@TypeOf(init), field.name)) {
495
- switch (@typeInfo(field.type)) {
501
+ if (init_info.is_tuple and init_info.field_names.len > i) {
502
+ @field(value, f_name) = @field(init, init_info.field_names[i]);
503
+ } else if (@hasField(@TypeOf(init), f_name)) {
504
+ switch (@typeInfo(f_type)) {
496
505
  .@"struct" => {
497
- @field(value, field.name) = zeroInit(field.type, @field(init, field.name));
506
+ @field(value, f_name) = zeroInit(f_type, @field(init, f_name));
498
507
  },
499
508
  else => {
500
- @field(value, field.name) = @field(init, field.name);
509
+ @field(value, f_name) = @field(init, f_name);
501
510
  },
502
511
  }
503
- } else if (field.defaultValue()) |val| {
504
- @field(value, field.name) = val;
512
+ } else if (f_attr.defaultValue(f_type)) |val| {
513
+ @field(value, f_name) = val;
505
514
  } else {
506
- switch (@typeInfo(field.type)) {
515
+ switch (@typeInfo(f_type)) {
507
516
  .@"struct" => {
508
- @field(value, field.name) = std.mem.zeroInit(field.type, .{});
517
+ @field(value, f_name) = std.mem.zeroInit(f_type, .{});
509
518
  },
510
519
  else => {
511
- @field(value, field.name) = std.mem.zeroes(@TypeOf(@field(value, field.name)));
520
+ @field(value, f_name) = std.mem.zeroes(@TypeOf(@field(value, f_name)));
512
521
  },
513
522
  }
514
523
  }
@@ -867,13 +876,9 @@ fn Span(comptime T: type) type {
867
876
  .many => ptr_info.sentinel() orelse @compileError("invalid type given to std.mem.span: " ++ @typeName(T)),
868
877
  .c => 0,
869
878
  };
870
- return @Pointer(.slice, .{
871
- .@"const" = ptr_info.is_const,
872
- .@"volatile" = ptr_info.is_volatile,
873
- .@"allowzero" = ptr_info.is_allowzero and ptr_info.size != .c,
874
- .@"align" = ptr_info.alignment,
875
- .@"addrspace" = ptr_info.address_space,
876
- }, ptr_info.child, new_sentinel);
879
+ var attrs = ptr_info.attrs;
880
+ attrs.@"allowzero" = attrs.@"allowzero" and ptr_info.size != .c;
881
+ return @Pointer(.slice, attrs, ptr_info.child, new_sentinel);
877
882
  },
878
883
  else => {},
879
884
  }
@@ -933,13 +938,9 @@ fn SliceTo(comptime T: type, comptime end: std.meta.Elem(T)) type {
933
938
  .many => if (std.meta.sentinel(T)) |s| s == end else true,
934
939
  .c => true,
935
940
  };
936
- return @Pointer(.slice, .{
937
- .@"const" = ptr_info.is_const,
938
- .@"volatile" = ptr_info.is_volatile,
939
- .@"allowzero" = ptr_info.is_allowzero and ptr_info.size != .c,
940
- .@"align" = ptr_info.alignment,
941
- .@"addrspace" = ptr_info.address_space,
942
- }, Elem, if (have_sentinel) end else null);
941
+ var attrs = ptr_info.attrs;
942
+ attrs.@"allowzero" = attrs.@"allowzero" and ptr_info.size != .c;
943
+ return @Pointer(.slice, attrs, Elem, if (have_sentinel) end else null);
943
944
  },
944
945
  else => {},
945
946
  }
@@ -2210,19 +2211,19 @@ pub fn byteSwapAllFieldsAligned(comptime S: type, comptime a: Alignment, ptr: *a
2210
2211
  .@"struct" => |struct_info| {
2211
2212
  if (struct_info.backing_integer) |Int| {
2212
2213
  ptr.* = @bitCast(@byteSwap(@as(Int, @bitCast(ptr.*))));
2213
- } else inline for (std.meta.fields(S)) |f| {
2214
- switch (@typeInfo(f.type)) {
2215
- .@"struct" => byteSwapAllFieldsAligned(f.type, .fromByteUnits(f.alignment orelse @alignOf(f.type)), &@field(ptr, f.name)),
2216
- .@"union", .array => byteSwapAllFieldsAligned(f.type, .fromByteUnits(f.alignment orelse @alignOf(f.type)), &@field(ptr, f.name)),
2214
+ } else inline for (struct_info.field_types, struct_info.field_names, struct_info.field_attrs) |f_type, f_name, f_attr| {
2215
+ switch (@typeInfo(f_type)) {
2216
+ .@"struct" => byteSwapAllFieldsAligned(f_type, .fromByteUnits(f_attr.@"align" orelse @alignOf(f_type)), &@field(ptr, f_name)),
2217
+ .@"union", .array => byteSwapAllFieldsAligned(f_type, .fromByteUnits(f_attr.@"align" orelse @alignOf(f_type)), &@field(ptr, f_name)),
2217
2218
  .@"enum" => {
2218
- @field(ptr, f.name) = @enumFromInt(@byteSwap(@intFromEnum(@field(ptr, f.name))));
2219
+ @field(ptr, f_name) = @enumFromInt(@byteSwap(@intFromEnum(@field(ptr, f_name))));
2219
2220
  },
2220
2221
  .bool => {},
2221
2222
  .float => |float_info| {
2222
- @field(ptr, f.name) = @bitCast(@byteSwap(@as(@Int(.unsigned, float_info.bits), @bitCast(@field(ptr, f.name)))));
2223
+ @field(ptr, f_name) = @bitCast(@byteSwap(@as(@Int(.unsigned, float_info.bits), @bitCast(@field(ptr, f_name)))));
2223
2224
  },
2224
2225
  else => {
2225
- @field(ptr, f.name) = @byteSwap(@field(ptr, f.name));
2226
+ @field(ptr, f_name) = @byteSwap(@field(ptr, f_name));
2226
2227
  },
2227
2228
  }
2228
2229
  }
@@ -2232,9 +2233,9 @@ pub fn byteSwapAllFieldsAligned(comptime S: type, comptime a: Alignment, ptr: *a
2232
2233
  @compileError("byteSwapAllFields expects an untagged union");
2233
2234
  }
2234
2235
 
2235
- const first_size = @bitSizeOf(union_info.fields[0].type);
2236
- inline for (union_info.fields) |field| {
2237
- if (@bitSizeOf(field.type) != first_size) {
2236
+ const first_size = @bitSizeOf(union_info.field_types[0]);
2237
+ inline for (union_info.field_types) |field_type| {
2238
+ if (@bitSizeOf(field_type) != first_size) {
2238
2239
  @compileError("Unable to byte-swap unions with varying field sizes");
2239
2240
  }
2240
2241
  }
@@ -3940,15 +3941,8 @@ pub fn ReverseIterator(comptime T: type) type {
3940
3941
  .many, .c => @compileError("expected slice or pointer to array, found '" ++ @typeName(T) ++ "'"),
3941
3942
  }
3942
3943
  const Element = std.meta.Elem(T);
3943
- const attrs: std.builtin.Type.Pointer.Attributes = .{
3944
- .@"const" = ptr.is_const,
3945
- .@"volatile" = ptr.is_volatile,
3946
- .@"allowzero" = ptr.is_allowzero,
3947
- .@"align" = ptr.alignment,
3948
- .@"addrspace" = ptr.address_space,
3949
- };
3950
- const Pointer = @Pointer(.many, attrs, Element, std.meta.sentinel(T));
3951
- const ElementPointer = @Pointer(.one, attrs, Element, null);
3944
+ const Pointer = @Pointer(.many, ptr.attrs, Element, std.meta.sentinel(T));
3945
+ const ElementPointer = @Pointer(.one, ptr.attrs, Element, null);
3952
3946
  return struct {
3953
3947
  ptr: Pointer,
3954
3948
  index: usize,
@@ -4255,7 +4249,7 @@ pub fn alignPointerOffset(ptr: anytype, align_to: usize) ?usize {
4255
4249
  @compileError("expected many item pointer, got " ++ @typeName(T));
4256
4250
 
4257
4251
  // Do nothing if the pointer is already well-aligned.
4258
- if (align_to <= info.pointer.alignment orelse @alignOf(info.pointer.child))
4252
+ if (align_to <= info.pointer.attrs.@"align" orelse @alignOf(info.pointer.child))
4259
4253
  return 0;
4260
4254
 
4261
4255
  // Calculate the aligned base address with an eye out for overflow.
@@ -4309,17 +4303,14 @@ fn CopyPtrAttrs(
4309
4303
  comptime child: type,
4310
4304
  ) type {
4311
4305
  const ptr = @typeInfo(source).pointer;
4312
- return @Pointer(size, .{
4313
- .@"const" = ptr.is_const,
4314
- .@"volatile" = ptr.is_volatile,
4315
- .@"allowzero" = ptr.is_allowzero,
4316
- .@"align" = ptr.alignment orelse a: {
4317
- // If the new child is aligned differently than the old one, explicitly align the type.
4318
- const want = @alignOf(ptr.child);
4319
- break :a if (@alignOf(child) == want) null else want;
4320
- },
4321
- .@"addrspace" = ptr.address_space,
4322
- }, child, null);
4306
+ var attrs = ptr.attrs;
4307
+ if (attrs.@"align" == null) {
4308
+ const want = @alignOf(ptr.child);
4309
+ if (@alignOf(child) != want) {
4310
+ attrs.@"align" = want;
4311
+ }
4312
+ }
4313
+ return @Pointer(size, attrs, child, null);
4323
4314
  }
4324
4315
 
4325
4316
  fn AsBytesReturnType(comptime P: type) type {
@@ -4383,10 +4374,13 @@ test "asBytes preserves pointer attributes" {
4383
4374
  const in = @typeInfo(@TypeOf(inPtr)).pointer;
4384
4375
  const out = @typeInfo(@TypeOf(outSlice)).pointer;
4385
4376
 
4386
- try testing.expectEqual(in.is_const, out.is_const);
4387
- try testing.expectEqual(in.is_volatile, out.is_volatile);
4388
- try testing.expectEqual(in.is_allowzero, out.is_allowzero);
4389
- try testing.expectEqual(in.alignment, out.alignment);
4377
+ const in_attrs = in.attrs;
4378
+ const out_attrs = out.attrs;
4379
+
4380
+ try testing.expectEqual(in_attrs.@"const", out_attrs.@"const");
4381
+ try testing.expectEqual(in_attrs.@"volatile", out_attrs.@"volatile");
4382
+ try testing.expectEqual(in_attrs.@"allowzero", out_attrs.@"allowzero");
4383
+ try testing.expectEqual(in_attrs.@"align", out_attrs.@"align");
4390
4384
  }
4391
4385
 
4392
4386
  /// Given any value, returns a copy of its bytes in an array.
@@ -4463,13 +4457,13 @@ test "bytesAsValue preserves pointer attributes" {
4463
4457
  const inSlice = @as(*align(16) const volatile [4]u8, @ptrCast(&inArr))[0..];
4464
4458
  const outPtr = bytesAsValue(u32, inSlice);
4465
4459
 
4466
- const in = @typeInfo(@TypeOf(inSlice)).pointer;
4467
- const out = @typeInfo(@TypeOf(outPtr)).pointer;
4460
+ const in_attrs = @typeInfo(@TypeOf(inSlice)).pointer.attrs;
4461
+ const out_attrs = @typeInfo(@TypeOf(outPtr)).pointer.attrs;
4468
4462
 
4469
- try testing.expectEqual(in.is_const, out.is_const);
4470
- try testing.expectEqual(in.is_volatile, out.is_volatile);
4471
- try testing.expectEqual(in.is_allowzero, out.is_allowzero);
4472
- try testing.expectEqual(in.alignment, out.alignment);
4463
+ try testing.expectEqual(in_attrs.@"const", out_attrs.@"const");
4464
+ try testing.expectEqual(in_attrs.@"volatile", out_attrs.@"volatile");
4465
+ try testing.expectEqual(in_attrs.@"allowzero", out_attrs.@"allowzero");
4466
+ try testing.expectEqual(in_attrs.@"align", out_attrs.@"align");
4473
4467
  }
4474
4468
 
4475
4469
  /// Given a pointer to an array of bytes, returns a value of the specified type backed by a
@@ -4566,13 +4560,13 @@ test "bytesAsSlice preserves pointer attributes" {
4566
4560
  const inSlice = @as(*align(16) const volatile [4]u8, @ptrCast(&inArr))[0..];
4567
4561
  const outSlice = bytesAsSlice(u16, inSlice);
4568
4562
 
4569
- const in = @typeInfo(@TypeOf(inSlice)).pointer;
4570
- const out = @typeInfo(@TypeOf(outSlice)).pointer;
4563
+ const in_attrs = @typeInfo(@TypeOf(inSlice)).pointer.attrs;
4564
+ const out_attrs = @typeInfo(@TypeOf(outSlice)).pointer.attrs;
4571
4565
 
4572
- try testing.expectEqual(in.is_const, out.is_const);
4573
- try testing.expectEqual(in.is_volatile, out.is_volatile);
4574
- try testing.expectEqual(in.is_allowzero, out.is_allowzero);
4575
- try testing.expectEqual(in.alignment, out.alignment);
4566
+ try testing.expectEqual(in_attrs.@"const", out_attrs.@"const");
4567
+ try testing.expectEqual(in_attrs.@"volatile", out_attrs.@"volatile");
4568
+ try testing.expectEqual(in_attrs.@"allowzero", out_attrs.@"allowzero");
4569
+ try testing.expectEqual(in_attrs.@"align", out_attrs.@"align");
4576
4570
  }
4577
4571
 
4578
4572
  test "bytesAsSlice with zero-bit element type" {
@@ -4678,25 +4672,19 @@ test "sliceAsBytes preserves pointer attributes" {
4678
4672
  const inSlice = @as(*align(16) const volatile [2]u16, @ptrCast(&inArr))[0..];
4679
4673
  const outSlice = sliceAsBytes(inSlice);
4680
4674
 
4681
- const in = @typeInfo(@TypeOf(inSlice)).pointer;
4682
- const out = @typeInfo(@TypeOf(outSlice)).pointer;
4675
+ const in_attrs = @typeInfo(@TypeOf(inSlice)).pointer.attrs;
4676
+ const out_attrs = @typeInfo(@TypeOf(outSlice)).pointer.attrs;
4683
4677
 
4684
- try testing.expectEqual(in.is_const, out.is_const);
4685
- try testing.expectEqual(in.is_volatile, out.is_volatile);
4686
- try testing.expectEqual(in.is_allowzero, out.is_allowzero);
4687
- try testing.expectEqual(in.alignment, out.alignment);
4678
+ try testing.expectEqual(in_attrs.@"const", out_attrs.@"const");
4679
+ try testing.expectEqual(in_attrs.@"volatile", out_attrs.@"volatile");
4680
+ try testing.expectEqual(in_attrs.@"allowzero", out_attrs.@"allowzero");
4681
+ try testing.expectEqual(in_attrs.@"align", out_attrs.@"align");
4688
4682
  }
4689
4683
 
4690
4684
  fn AbsorbSentinelReturnType(comptime Slice: type) type {
4691
4685
  const info = @typeInfo(Slice).pointer;
4692
4686
  assert(info.size == .slice);
4693
- return @Pointer(.slice, .{
4694
- .@"const" = info.is_const,
4695
- .@"volatile" = info.is_volatile,
4696
- .@"allowzero" = info.is_allowzero,
4697
- .@"addrspace" = info.address_space,
4698
- .@"align" = info.alignment,
4699
- }, info.child, null);
4687
+ return @Pointer(.slice, info.attrs, info.child, null);
4700
4688
  }
4701
4689
 
4702
4690
  /// If the provided slice is not sentinel terminated, do nothing and return that slice.
@@ -4949,13 +4937,9 @@ test "freeing empty string with null-terminated sentinel" {
4949
4937
  /// all other pointer attributes copied from `AttributeSource`.
4950
4938
  fn AlignedSlice(comptime AttributeSource: type, comptime new_alignment: usize) type {
4951
4939
  const ptr = @typeInfo(AttributeSource).pointer;
4952
- return @Pointer(.slice, .{
4953
- .@"const" = ptr.is_const,
4954
- .@"volatile" = ptr.is_volatile,
4955
- .@"allowzero" = ptr.is_allowzero,
4956
- .@"align" = new_alignment,
4957
- .@"addrspace" = ptr.address_space,
4958
- }, ptr.child, null);
4940
+ var attrs = ptr.attrs;
4941
+ attrs.@"align" = new_alignment;
4942
+ return @Pointer(.slice, attrs, ptr.child, null);
4959
4943
  }
4960
4944
 
4961
4945
  /// Returns the largest slice in the given bytes that conforms to the new alignment,