| ... | @@ -3789,6 +3789,39 @@ pub const Type = extern union { | ... | @@ -3789,6 +3789,39 @@ pub const Type = extern union { |
| 3789 | } | 3789 | } |
| 3790 | } | 3790 | } |
| 3791 | | 3791 | |
| | 3792 | /// Returns true if the type's layout is already resolved and it is safe |
| | 3793 | /// to use `abiSize`, `abiAlignment` and `bitSize` on it. |
| | 3794 | pub fn layoutIsResolved(ty: Type) bool { |
| | 3795 | switch (ty.zigTypeTag()) { |
| | 3796 | .Struct => { |
| | 3797 | if (ty.castTag(.@"struct")) |struct_ty| { |
| | 3798 | return struct_ty.data.haveLayout(); |
| | 3799 | } |
| | 3800 | return true; |
| | 3801 | }, |
| | 3802 | .Union => { |
| | 3803 | if (ty.cast(Payload.Union)) |union_ty| { |
| | 3804 | return union_ty.data.haveLayout(); |
| | 3805 | } |
| | 3806 | return true; |
| | 3807 | }, |
| | 3808 | .Array => { |
| | 3809 | if (ty.arrayLenIncludingSentinel() == 0) return true; |
| | 3810 | return ty.childType().layoutIsResolved(); |
| | 3811 | }, |
| | 3812 | .Optional => { |
| | 3813 | var buf: Type.Payload.ElemType = undefined; |
| | 3814 | const payload_ty = ty.optionalChild(&buf); |
| | 3815 | return payload_ty.layoutIsResolved(); |
| | 3816 | }, |
| | 3817 | .ErrorUnion => { |
| | 3818 | const payload_ty = ty.errorUnionPayload(); |
| | 3819 | return payload_ty.layoutIsResolved(); |
| | 3820 | }, |
| | 3821 | else => return true, |
| | 3822 | } |
| | 3823 | } |
| | 3824 | |
| 3792 | pub fn isSinglePointer(self: Type) bool { | 3825 | pub fn isSinglePointer(self: Type) bool { |
| 3793 | return switch (self.tag()) { | 3826 | return switch (self.tag()) { |
| 3794 | .single_const_pointer, | 3827 | .single_const_pointer, |
| ... | @@ -6498,12 +6531,7 @@ pub const Type = extern union { | ... | @@ -6498,12 +6531,7 @@ pub const Type = extern union { |
| 6498 | // pointee type needs to be resolved more, that needs to be done before calling | 6531 | // pointee type needs to be resolved more, that needs to be done before calling |
| 6499 | // this ptr() function. | 6532 | // this ptr() function. |
| 6500 | if (d.@"align" != 0) canonicalize: { | 6533 | if (d.@"align" != 0) canonicalize: { |
| 6501 | if (d.pointee_type.castTag(.@"struct")) |struct_ty| { | 6534 | if (!d.pointee_type.layoutIsResolved()) break :canonicalize; |
| 6502 | if (!struct_ty.data.haveLayout()) break :canonicalize; | | |
| 6503 | } | | |
| 6504 | if (d.pointee_type.cast(Payload.Union)) |union_ty| { | | |
| 6505 | if (!union_ty.data.haveLayout()) break :canonicalize; | | |
| 6506 | } | | |
| 6507 | if (d.@"align" == d.pointee_type.abiAlignment(target)) { | 6535 | if (d.@"align" == d.pointee_type.abiAlignment(target)) { |
| 6508 | d.@"align" = 0; | 6536 | d.@"align" = 0; |
| 6509 | } | 6537 | } |