| ... | @@ -1111,7 +1111,7 @@ pub const Object = struct { | ... | @@ -1111,7 +1111,7 @@ pub const Object = struct { |
| 1111 | // } | 1111 | // } |
| 1112 | | 1112 | |
| 1113 | const lhs = wip.arg(0); | 1113 | const lhs = wip.arg(0); |
| 1114 | const rhs = try o.builder.intValue(Builder.Type.err_int, errors_len); | 1114 | const rhs = try o.builder.intValue(try o.errorIntType(), errors_len); |
| 1115 | const is_lt = try wip.icmp(.ult, lhs, rhs, ""); | 1115 | const is_lt = try wip.icmp(.ult, lhs, rhs, ""); |
| 1116 | _ = try wip.ret(is_lt); | 1116 | _ = try wip.ret(is_lt); |
| 1117 | try wip.finish(); | 1117 | try wip.finish(); |
| ... | @@ -3111,6 +3111,10 @@ pub const Object = struct { | ... | @@ -3111,6 +3111,10 @@ pub const Object = struct { |
| 3111 | return variable_index; | 3111 | return variable_index; |
| 3112 | } | 3112 | } |
| 3113 | | 3113 | |
| | 3114 | fn errorIntType(o: *Object) Allocator.Error!Builder.Type { |
| | 3115 | return o.builder.intType(o.module.errorSetBits()); |
| | 3116 | } |
| | 3117 | |
| 3114 | fn lowerType(o: *Object, t: Type) Allocator.Error!Builder.Type { | 3118 | fn lowerType(o: *Object, t: Type) Allocator.Error!Builder.Type { |
| 3115 | const ty = try o.lowerTypeInner(t); | 3119 | const ty = try o.lowerTypeInner(t); |
| 3116 | const mod = o.module; | 3120 | const mod = o.module; |
| ... | @@ -3182,7 +3186,7 @@ pub const Object = struct { | ... | @@ -3182,7 +3186,7 @@ pub const Object = struct { |
| 3182 | .bool_type => .i1, | 3186 | .bool_type => .i1, |
| 3183 | .void_type => .void, | 3187 | .void_type => .void, |
| 3184 | .type_type => unreachable, | 3188 | .type_type => unreachable, |
| 3185 | .anyerror_type => Builder.Type.err_int, | 3189 | .anyerror_type => try o.errorIntType(), |
| 3186 | .comptime_int_type, | 3190 | .comptime_int_type, |
| 3187 | .comptime_float_type, | 3191 | .comptime_float_type, |
| 3188 | .noreturn_type, | 3192 | .noreturn_type, |
| ... | @@ -3203,7 +3207,7 @@ pub const Object = struct { | ... | @@ -3203,7 +3207,7 @@ pub const Object = struct { |
| 3203 | .optional_noreturn_type => unreachable, | 3207 | .optional_noreturn_type => unreachable, |
| 3204 | .anyerror_void_error_union_type, | 3208 | .anyerror_void_error_union_type, |
| 3205 | .adhoc_inferred_error_set_type, | 3209 | .adhoc_inferred_error_set_type, |
| 3206 | => Builder.Type.err_int, | 3210 | => try o.errorIntType(), |
| 3207 | .generic_poison_type, | 3211 | .generic_poison_type, |
| 3208 | .empty_struct_type, | 3212 | .empty_struct_type, |
| 3209 | => unreachable, | 3213 | => unreachable, |
| ... | @@ -3272,16 +3276,17 @@ pub const Object = struct { | ... | @@ -3272,16 +3276,17 @@ pub const Object = struct { |
| 3272 | }, | 3276 | }, |
| 3273 | .anyframe_type => @panic("TODO implement lowerType for AnyFrame types"), | 3277 | .anyframe_type => @panic("TODO implement lowerType for AnyFrame types"), |
| 3274 | .error_union_type => |error_union_type| { | 3278 | .error_union_type => |error_union_type| { |
| 3275 | const error_type = Builder.Type.err_int; | 3279 | const error_type = try o.errorIntType(); |
| 3276 | if (!error_union_type.payload_type.toType().hasRuntimeBitsIgnoreComptime(mod)) | 3280 | if (!error_union_type.payload_type.toType().hasRuntimeBitsIgnoreComptime(mod)) |
| 3277 | return error_type; | 3281 | return error_type; |
| 3278 | const payload_type = try o.lowerType(error_union_type.payload_type.toType()); | 3282 | const payload_type = try o.lowerType(error_union_type.payload_type.toType()); |
| | 3283 | const err_int_ty = try mod.errorIntType(); |
| 3279 | | 3284 | |
| 3280 | const payload_align = error_union_type.payload_type.toType().abiAlignment(mod); | 3285 | const payload_align = error_union_type.payload_type.toType().abiAlignment(mod); |
| 3281 | const error_align = Type.err_int.abiAlignment(mod); | 3286 | const error_align = err_int_ty.abiAlignment(mod); |
| 3282 | | 3287 | |
| 3283 | const payload_size = error_union_type.payload_type.toType().abiSize(mod); | 3288 | const payload_size = error_union_type.payload_type.toType().abiSize(mod); |
| 3284 | const error_size = Type.err_int.abiSize(mod); | 3289 | const error_size = err_int_ty.abiSize(mod); |
| 3285 | | 3290 | |
| 3286 | var fields: [3]Builder.Type = undefined; | 3291 | var fields: [3]Builder.Type = undefined; |
| 3287 | var fields_len: usize = 2; | 3292 | var fields_len: usize = 2; |
| ... | @@ -3542,7 +3547,7 @@ pub const Object = struct { | ... | @@ -3542,7 +3547,7 @@ pub const Object = struct { |
| 3542 | }, | 3547 | }, |
| 3543 | .enum_type => |enum_type| try o.lowerType(enum_type.tag_ty.toType()), | 3548 | .enum_type => |enum_type| try o.lowerType(enum_type.tag_ty.toType()), |
| 3544 | .func_type => |func_type| try o.lowerTypeFn(func_type), | 3549 | .func_type => |func_type| try o.lowerTypeFn(func_type), |
| 3545 | .error_set_type, .inferred_error_set_type => Builder.Type.err_int, | 3550 | .error_set_type, .inferred_error_set_type => try o.errorIntType(), |
| 3546 | // values, not types | 3551 | // values, not types |
| 3547 | .undef, | 3552 | .undef, |
| 3548 | .runtime_value, | 3553 | .runtime_value, |
| ... | @@ -3725,7 +3730,7 @@ pub const Object = struct { | ... | @@ -3725,7 +3730,7 @@ pub const Object = struct { |
| 3725 | }, | 3730 | }, |
| 3726 | .err => |err| { | 3731 | .err => |err| { |
| 3727 | const int = try mod.getErrorValue(err.name); | 3732 | const int = try mod.getErrorValue(err.name); |
| 3728 | const llvm_int = try o.builder.intConst(Builder.Type.err_int, int); | 3733 | const llvm_int = try o.builder.intConst(try o.errorIntType(), int); |
| 3729 | return llvm_int; | 3734 | return llvm_int; |
| 3730 | }, | 3735 | }, |
| 3731 | .error_union => |error_union| { | 3736 | .error_union => |error_union| { |
| ... | @@ -3734,8 +3739,9 @@ pub const Object = struct { | ... | @@ -3734,8 +3739,9 @@ pub const Object = struct { |
| 3734 | .ty = ty.errorUnionSet(mod).toIntern(), | 3739 | .ty = ty.errorUnionSet(mod).toIntern(), |
| 3735 | .name = err_name, | 3740 | .name = err_name, |
| 3736 | } }), | 3741 | } }), |
| 3737 | .payload => (try mod.intValue(Type.err_int, 0)).toIntern(), | 3742 | .payload => (try mod.intValue(try mod.errorIntType(), 0)).toIntern(), |
| 3738 | }; | 3743 | }; |
| | 3744 | const err_int_ty = try mod.errorIntType(); |
| 3739 | const payload_type = ty.errorUnionPayload(mod); | 3745 | const payload_type = ty.errorUnionPayload(mod); |
| 3740 | if (!payload_type.hasRuntimeBitsIgnoreComptime(mod)) { | 3746 | if (!payload_type.hasRuntimeBitsIgnoreComptime(mod)) { |
| 3741 | // We use the error type directly as the type. | 3747 | // We use the error type directly as the type. |
| ... | @@ -3743,7 +3749,7 @@ pub const Object = struct { | ... | @@ -3743,7 +3749,7 @@ pub const Object = struct { |
| 3743 | } | 3749 | } |
| 3744 | | 3750 | |
| 3745 | const payload_align = payload_type.abiAlignment(mod); | 3751 | const payload_align = payload_type.abiAlignment(mod); |
| 3746 | const error_align = Type.err_int.abiAlignment(mod); | 3752 | const error_align = err_int_ty.abiAlignment(mod); |
| 3747 | const llvm_error_value = try o.lowerValue(err_val); | 3753 | const llvm_error_value = try o.lowerValue(err_val); |
| 3748 | const llvm_payload_value = try o.lowerValue(switch (error_union.val) { | 3754 | const llvm_payload_value = try o.lowerValue(switch (error_union.val) { |
| 3749 | .err_name => try mod.intern(.{ .undef = payload_type.toIntern() }), | 3755 | .err_name => try mod.intern(.{ .undef = payload_type.toIntern() }), |
| ... | @@ -4285,8 +4291,9 @@ pub const Object = struct { | ... | @@ -4285,8 +4291,9 @@ pub const Object = struct { |
| 4285 | return parent_ptr; | 4291 | return parent_ptr; |
| 4286 | } | 4292 | } |
| 4287 | | 4293 | |
| | 4294 | const err_int_ty = try mod.errorIntType(); |
| 4288 | const payload_align = payload_ty.abiAlignment(mod); | 4295 | const payload_align = payload_ty.abiAlignment(mod); |
| 4289 | const err_align = Type.err_int.abiAlignment(mod); | 4296 | const err_align = err_int_ty.abiAlignment(mod); |
| 4290 | const index: u32 = if (payload_align.compare(.gt, err_align)) 2 else 1; | 4297 | const index: u32 = if (payload_align.compare(.gt, err_align)) 2 else 1; |
| 4291 | return o.builder.gepConst(.inbounds, try o.lowerType(eu_ty), parent_ptr, null, &.{ | 4298 | return o.builder.gepConst(.inbounds, try o.lowerType(eu_ty), parent_ptr, null, &.{ |
| 4292 | try o.builder.intConst(.i32, 0), try o.builder.intConst(.i32, index), | 4299 | try o.builder.intConst(.i32, 0), try o.builder.intConst(.i32, index), |
| ... | @@ -5399,7 +5406,7 @@ pub const FuncGen = struct { | ... | @@ -5399,7 +5406,7 @@ pub const FuncGen = struct { |
| 5399 | // Functions with an empty error set are emitted with an error code | 5406 | // Functions with an empty error set are emitted with an error code |
| 5400 | // return type and return zero so they can be function pointers coerced | 5407 | // return type and return zero so they can be function pointers coerced |
| 5401 | // to functions that return anyerror. | 5408 | // to functions that return anyerror. |
| 5402 | _ = try self.wip.ret(try o.builder.intValue(Builder.Type.err_int, 0)); | 5409 | _ = try self.wip.ret(try o.builder.intValue(try o.errorIntType(), 0)); |
| 5403 | } else { | 5410 | } else { |
| 5404 | _ = try self.wip.retVoid(); | 5411 | _ = try self.wip.retVoid(); |
| 5405 | } | 5412 | } |
| ... | @@ -5441,7 +5448,7 @@ pub const FuncGen = struct { | ... | @@ -5441,7 +5448,7 @@ pub const FuncGen = struct { |
| 5441 | // Functions with an empty error set are emitted with an error code | 5448 | // Functions with an empty error set are emitted with an error code |
| 5442 | // return type and return zero so they can be function pointers coerced | 5449 | // return type and return zero so they can be function pointers coerced |
| 5443 | // to functions that return anyerror. | 5450 | // to functions that return anyerror. |
| 5444 | _ = try self.wip.ret(try o.builder.intValue(Builder.Type.err_int, 0)); | 5451 | _ = try self.wip.ret(try o.builder.intValue(try o.errorIntType(), 0)); |
| 5445 | } else { | 5452 | } else { |
| 5446 | _ = try self.wip.retVoid(); | 5453 | _ = try self.wip.retVoid(); |
| 5447 | } | 5454 | } |
| ... | @@ -5788,24 +5795,25 @@ pub const FuncGen = struct { | ... | @@ -5788,24 +5795,25 @@ pub const FuncGen = struct { |
| 5788 | const payload_ty = err_union_ty.errorUnionPayload(mod); | 5795 | const payload_ty = err_union_ty.errorUnionPayload(mod); |
| 5789 | const payload_has_bits = payload_ty.hasRuntimeBitsIgnoreComptime(mod); | 5796 | const payload_has_bits = payload_ty.hasRuntimeBitsIgnoreComptime(mod); |
| 5790 | const err_union_llvm_ty = try o.lowerType(err_union_ty); | 5797 | const err_union_llvm_ty = try o.lowerType(err_union_ty); |
| | 5798 | const error_type = try o.errorIntType(); |
| 5791 | | 5799 | |
| 5792 | if (!err_union_ty.errorUnionSet(mod).errorSetIsEmpty(mod)) { | 5800 | if (!err_union_ty.errorUnionSet(mod).errorSetIsEmpty(mod)) { |
| 5793 | const loaded = loaded: { | 5801 | const loaded = loaded: { |
| 5794 | if (!payload_has_bits) { | 5802 | if (!payload_has_bits) { |
| 5795 | // TODO add alignment to this load | 5803 | // TODO add alignment to this load |
| 5796 | break :loaded if (operand_is_ptr) | 5804 | break :loaded if (operand_is_ptr) |
| 5797 | try fg.wip.load(.normal, Builder.Type.err_int, err_union, .default, "") | 5805 | try fg.wip.load(.normal, error_type, err_union, .default, "") |
| 5798 | else | 5806 | else |
| 5799 | err_union; | 5807 | err_union; |
| 5800 | } | 5808 | } |
| 5801 | const err_field_index = errUnionErrorOffset(payload_ty, mod); | 5809 | const err_field_index = try errUnionErrorOffset(payload_ty, mod); |
| 5802 | if (operand_is_ptr or isByRef(err_union_ty, mod)) { | 5810 | if (operand_is_ptr or isByRef(err_union_ty, mod)) { |
| 5803 | const err_field_ptr = | 5811 | const err_field_ptr = |
| 5804 | try fg.wip.gepStruct(err_union_llvm_ty, err_union, err_field_index, ""); | 5812 | try fg.wip.gepStruct(err_union_llvm_ty, err_union, err_field_index, ""); |
| 5805 | // TODO add alignment to this load | 5813 | // TODO add alignment to this load |
| 5806 | break :loaded try fg.wip.load( | 5814 | break :loaded try fg.wip.load( |
| 5807 | .normal, | 5815 | .normal, |
| 5808 | Builder.Type.err_int, | 5816 | error_type, |
| 5809 | err_field_ptr, | 5817 | err_field_ptr, |
| 5810 | .default, | 5818 | .default, |
| 5811 | "", | 5819 | "", |
| ... | @@ -5813,7 +5821,7 @@ pub const FuncGen = struct { | ... | @@ -5813,7 +5821,7 @@ pub const FuncGen = struct { |
| 5813 | } | 5821 | } |
| 5814 | break :loaded try fg.wip.extractValue(err_union, &.{err_field_index}, ""); | 5822 | break :loaded try fg.wip.extractValue(err_union, &.{err_field_index}, ""); |
| 5815 | }; | 5823 | }; |
| 5816 | const zero = try o.builder.intValue(Builder.Type.err_int, 0); | 5824 | const zero = try o.builder.intValue(error_type, 0); |
| 5817 | const is_err = try fg.wip.icmp(.ne, loaded, zero, ""); | 5825 | const is_err = try fg.wip.icmp(.ne, loaded, zero, ""); |
| 5818 | | 5826 | |
| 5819 | const return_block = try fg.wip.block(1, "TryRet"); | 5827 | const return_block = try fg.wip.block(1, "TryRet"); |
| ... | @@ -5827,7 +5835,7 @@ pub const FuncGen = struct { | ... | @@ -5827,7 +5835,7 @@ pub const FuncGen = struct { |
| 5827 | } | 5835 | } |
| 5828 | if (is_unused) return .none; | 5836 | if (is_unused) return .none; |
| 5829 | if (!payload_has_bits) return if (operand_is_ptr) err_union else .none; | 5837 | if (!payload_has_bits) return if (operand_is_ptr) err_union else .none; |
| 5830 | const offset = errUnionPayloadOffset(payload_ty, mod); | 5838 | const offset = try errUnionPayloadOffset(payload_ty, mod); |
| 5831 | if (operand_is_ptr) { | 5839 | if (operand_is_ptr) { |
| 5832 | return fg.wip.gepStruct(err_union_llvm_ty, err_union, offset, ""); | 5840 | return fg.wip.gepStruct(err_union_llvm_ty, err_union, offset, ""); |
| 5833 | } else if (isByRef(err_union_ty, mod)) { | 5841 | } else if (isByRef(err_union_ty, mod)) { |
| ... | @@ -7053,7 +7061,8 @@ pub const FuncGen = struct { | ... | @@ -7053,7 +7061,8 @@ pub const FuncGen = struct { |
| 7053 | const operand_ty = self.typeOf(un_op); | 7061 | const operand_ty = self.typeOf(un_op); |
| 7054 | const err_union_ty = if (operand_is_ptr) operand_ty.childType(mod) else operand_ty; | 7062 | const err_union_ty = if (operand_is_ptr) operand_ty.childType(mod) else operand_ty; |
| 7055 | const payload_ty = err_union_ty.errorUnionPayload(mod); | 7063 | const payload_ty = err_union_ty.errorUnionPayload(mod); |
| 7056 | const zero = try o.builder.intValue(Builder.Type.err_int, 0); | 7064 | const error_type = try o.errorIntType(); |
| | 7065 | const zero = try o.builder.intValue(error_type, 0); |
| 7057 | | 7066 | |
| 7058 | if (err_union_ty.errorUnionSet(mod).errorSetIsEmpty(mod)) { | 7067 | if (err_union_ty.errorUnionSet(mod).errorSetIsEmpty(mod)) { |
| 7059 | const val: Builder.Constant = switch (cond) { | 7068 | const val: Builder.Constant = switch (cond) { |
| ... | @@ -7072,13 +7081,13 @@ pub const FuncGen = struct { | ... | @@ -7072,13 +7081,13 @@ pub const FuncGen = struct { |
| 7072 | return self.wip.icmp(cond, loaded, zero, ""); | 7081 | return self.wip.icmp(cond, loaded, zero, ""); |
| 7073 | } | 7082 | } |
| 7074 | | 7083 | |
| 7075 | const err_field_index = errUnionErrorOffset(payload_ty, mod); | 7084 | const err_field_index = try errUnionErrorOffset(payload_ty, mod); |
| 7076 | | 7085 | |
| 7077 | const loaded = if (operand_is_ptr or isByRef(err_union_ty, mod)) loaded: { | 7086 | const loaded = if (operand_is_ptr or isByRef(err_union_ty, mod)) loaded: { |
| 7078 | const err_union_llvm_ty = try o.lowerType(err_union_ty); | 7087 | const err_union_llvm_ty = try o.lowerType(err_union_ty); |
| 7079 | const err_field_ptr = | 7088 | const err_field_ptr = |
| 7080 | try self.wip.gepStruct(err_union_llvm_ty, operand, err_field_index, ""); | 7089 | try self.wip.gepStruct(err_union_llvm_ty, operand, err_field_index, ""); |
| 7081 | break :loaded try self.wip.load(.normal, Builder.Type.err_int, err_field_ptr, .default, ""); | 7090 | break :loaded try self.wip.load(.normal, error_type, err_field_ptr, .default, ""); |
| 7082 | } else try self.wip.extractValue(operand, &.{err_field_index}, ""); | 7091 | } else try self.wip.extractValue(operand, &.{err_field_index}, ""); |
| 7083 | return self.wip.icmp(cond, loaded, zero, ""); | 7092 | return self.wip.icmp(cond, loaded, zero, ""); |
| 7084 | } | 7093 | } |
| ... | @@ -7173,7 +7182,7 @@ pub const FuncGen = struct { | ... | @@ -7173,7 +7182,7 @@ pub const FuncGen = struct { |
| 7173 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { | 7182 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 7174 | return if (operand_is_ptr) operand else .none; | 7183 | return if (operand_is_ptr) operand else .none; |
| 7175 | } | 7184 | } |
| 7176 | const offset = errUnionPayloadOffset(payload_ty, mod); | 7185 | const offset = try errUnionPayloadOffset(payload_ty, mod); |
| 7177 | const err_union_llvm_ty = try o.lowerType(err_union_ty); | 7186 | const err_union_llvm_ty = try o.lowerType(err_union_ty); |
| 7178 | if (operand_is_ptr) { | 7187 | if (operand_is_ptr) { |
| 7179 | return self.wip.gepStruct(err_union_llvm_ty, operand, offset, ""); | 7188 | return self.wip.gepStruct(err_union_llvm_ty, operand, offset, ""); |
| ... | @@ -7200,27 +7209,28 @@ pub const FuncGen = struct { | ... | @@ -7200,27 +7209,28 @@ pub const FuncGen = struct { |
| 7200 | const ty_op = self.air.instructions.items(.data)[inst].ty_op; | 7209 | const ty_op = self.air.instructions.items(.data)[inst].ty_op; |
| 7201 | const operand = try self.resolveInst(ty_op.operand); | 7210 | const operand = try self.resolveInst(ty_op.operand); |
| 7202 | const operand_ty = self.typeOf(ty_op.operand); | 7211 | const operand_ty = self.typeOf(ty_op.operand); |
| | 7212 | const error_type = try o.errorIntType(); |
| 7203 | const err_union_ty = if (operand_is_ptr) operand_ty.childType(mod) else operand_ty; | 7213 | const err_union_ty = if (operand_is_ptr) operand_ty.childType(mod) else operand_ty; |
| 7204 | if (err_union_ty.errorUnionSet(mod).errorSetIsEmpty(mod)) { | 7214 | if (err_union_ty.errorUnionSet(mod).errorSetIsEmpty(mod)) { |
| 7205 | if (operand_is_ptr) { | 7215 | if (operand_is_ptr) { |
| 7206 | return operand; | 7216 | return operand; |
| 7207 | } else { | 7217 | } else { |
| 7208 | return o.builder.intValue(Builder.Type.err_int, 0); | 7218 | return o.builder.intValue(error_type, 0); |
| 7209 | } | 7219 | } |
| 7210 | } | 7220 | } |
| 7211 | | 7221 | |
| 7212 | const payload_ty = err_union_ty.errorUnionPayload(mod); | 7222 | const payload_ty = err_union_ty.errorUnionPayload(mod); |
| 7213 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { | 7223 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 7214 | if (!operand_is_ptr) return operand; | 7224 | if (!operand_is_ptr) return operand; |
| 7215 | return self.wip.load(.normal, Builder.Type.err_int, operand, .default, ""); | 7225 | return self.wip.load(.normal, error_type, operand, .default, ""); |
| 7216 | } | 7226 | } |
| 7217 | | 7227 | |
| 7218 | const offset = errUnionErrorOffset(payload_ty, mod); | 7228 | const offset = try errUnionErrorOffset(payload_ty, mod); |
| 7219 | | 7229 | |
| 7220 | if (operand_is_ptr or isByRef(err_union_ty, mod)) { | 7230 | if (operand_is_ptr or isByRef(err_union_ty, mod)) { |
| 7221 | const err_union_llvm_ty = try o.lowerType(err_union_ty); | 7231 | const err_union_llvm_ty = try o.lowerType(err_union_ty); |
| 7222 | const err_field_ptr = try self.wip.gepStruct(err_union_llvm_ty, operand, offset, ""); | 7232 | const err_field_ptr = try self.wip.gepStruct(err_union_llvm_ty, operand, offset, ""); |
| 7223 | return self.wip.load(.normal, Builder.Type.err_int, err_field_ptr, .default, ""); | 7233 | return self.wip.load(.normal, error_type, err_field_ptr, .default, ""); |
| 7224 | } | 7234 | } |
| 7225 | | 7235 | |
| 7226 | return self.wip.extractValue(operand, &.{offset}, ""); | 7236 | return self.wip.extractValue(operand, &.{offset}, ""); |
| ... | @@ -7234,15 +7244,16 @@ pub const FuncGen = struct { | ... | @@ -7234,15 +7244,16 @@ pub const FuncGen = struct { |
| 7234 | const err_union_ty = self.typeOf(ty_op.operand).childType(mod); | 7244 | const err_union_ty = self.typeOf(ty_op.operand).childType(mod); |
| 7235 | | 7245 | |
| 7236 | const payload_ty = err_union_ty.errorUnionPayload(mod); | 7246 | const payload_ty = err_union_ty.errorUnionPayload(mod); |
| 7237 | const non_error_val = try o.builder.intValue(Builder.Type.err_int, 0); | 7247 | const non_error_val = try o.builder.intValue(try o.errorIntType(), 0); |
| 7238 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { | 7248 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 7239 | _ = try self.wip.store(.normal, non_error_val, operand, .default); | 7249 | _ = try self.wip.store(.normal, non_error_val, operand, .default); |
| 7240 | return operand; | 7250 | return operand; |
| 7241 | } | 7251 | } |
| 7242 | const err_union_llvm_ty = try o.lowerType(err_union_ty); | 7252 | const err_union_llvm_ty = try o.lowerType(err_union_ty); |
| 7243 | { | 7253 | { |
| 7244 | const error_alignment = Type.err_int.abiAlignment(mod).toLlvm(); | 7254 | const err_int_ty = try mod.errorIntType(); |
| 7245 | const error_offset = errUnionErrorOffset(payload_ty, mod); | 7255 | const error_alignment = err_int_ty.abiAlignment(mod).toLlvm(); |
| | 7256 | const error_offset = try errUnionErrorOffset(payload_ty, mod); |
| 7246 | // First set the non-error value. | 7257 | // First set the non-error value. |
| 7247 | const non_null_ptr = try self.wip.gepStruct(err_union_llvm_ty, operand, error_offset, ""); | 7258 | const non_null_ptr = try self.wip.gepStruct(err_union_llvm_ty, operand, error_offset, ""); |
| 7248 | _ = try self.wip.store(.normal, non_error_val, non_null_ptr, error_alignment); | 7259 | _ = try self.wip.store(.normal, non_error_val, non_null_ptr, error_alignment); |
| ... | @@ -7250,7 +7261,7 @@ pub const FuncGen = struct { | ... | @@ -7250,7 +7261,7 @@ pub const FuncGen = struct { |
| 7250 | // Then return the payload pointer (only if it is used). | 7261 | // Then return the payload pointer (only if it is used). |
| 7251 | if (self.liveness.isUnused(inst)) return .none; | 7262 | if (self.liveness.isUnused(inst)) return .none; |
| 7252 | | 7263 | |
| 7253 | const payload_offset = errUnionPayloadOffset(payload_ty, mod); | 7264 | const payload_offset = try errUnionPayloadOffset(payload_ty, mod); |
| 7254 | return self.wip.gepStruct(err_union_llvm_ty, operand, payload_offset, ""); | 7265 | return self.wip.gepStruct(err_union_llvm_ty, operand, payload_offset, ""); |
| 7255 | } | 7266 | } |
| 7256 | | 7267 | |
| ... | @@ -7353,11 +7364,11 @@ pub const FuncGen = struct { | ... | @@ -7353,11 +7364,11 @@ pub const FuncGen = struct { |
| 7353 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { | 7364 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 7354 | return operand; | 7365 | return operand; |
| 7355 | } | 7366 | } |
| 7356 | const ok_err_code = try o.builder.intValue(Builder.Type.err_int, 0); | 7367 | const ok_err_code = try o.builder.intValue(try o.errorIntType(), 0); |
| 7357 | const err_un_llvm_ty = try o.lowerType(err_un_ty); | 7368 | const err_un_llvm_ty = try o.lowerType(err_un_ty); |
| 7358 | | 7369 | |
| 7359 | const payload_offset = errUnionPayloadOffset(payload_ty, mod); | 7370 | const payload_offset = try errUnionPayloadOffset(payload_ty, mod); |
| 7360 | const error_offset = errUnionErrorOffset(payload_ty, mod); | 7371 | const error_offset = try errUnionErrorOffset(payload_ty, mod); |
| 7361 | if (isByRef(err_un_ty, mod)) { | 7372 | if (isByRef(err_un_ty, mod)) { |
| 7362 | const directReturn = self.isNextRet(body_tail); | 7373 | const directReturn = self.isNextRet(body_tail); |
| 7363 | const result_ptr = if (directReturn) | 7374 | const result_ptr = if (directReturn) |
| ... | @@ -7369,7 +7380,8 @@ pub const FuncGen = struct { | ... | @@ -7369,7 +7380,8 @@ pub const FuncGen = struct { |
| 7369 | }; | 7380 | }; |
| 7370 | | 7381 | |
| 7371 | const err_ptr = try self.wip.gepStruct(err_un_llvm_ty, result_ptr, error_offset, ""); | 7382 | const err_ptr = try self.wip.gepStruct(err_un_llvm_ty, result_ptr, error_offset, ""); |
| 7372 | const error_alignment = Type.err_int.abiAlignment(mod).toLlvm(); | 7383 | const err_int_ty = try mod.errorIntType(); |
| | 7384 | const error_alignment = err_int_ty.abiAlignment(mod).toLlvm(); |
| 7373 | _ = try self.wip.store(.normal, ok_err_code, err_ptr, error_alignment); | 7385 | _ = try self.wip.store(.normal, ok_err_code, err_ptr, error_alignment); |
| 7374 | const payload_ptr = try self.wip.gepStruct(err_un_llvm_ty, result_ptr, payload_offset, ""); | 7386 | const payload_ptr = try self.wip.gepStruct(err_un_llvm_ty, result_ptr, payload_offset, ""); |
| 7375 | const payload_ptr_ty = try mod.singleMutPtrType(payload_ty); | 7387 | const payload_ptr_ty = try mod.singleMutPtrType(payload_ty); |
| ... | @@ -7393,8 +7405,8 @@ pub const FuncGen = struct { | ... | @@ -7393,8 +7405,8 @@ pub const FuncGen = struct { |
| 7393 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) return operand; | 7405 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) return operand; |
| 7394 | const err_un_llvm_ty = try o.lowerType(err_un_ty); | 7406 | const err_un_llvm_ty = try o.lowerType(err_un_ty); |
| 7395 | | 7407 | |
| 7396 | const payload_offset = errUnionPayloadOffset(payload_ty, mod); | 7408 | const payload_offset = try errUnionPayloadOffset(payload_ty, mod); |
| 7397 | const error_offset = errUnionErrorOffset(payload_ty, mod); | 7409 | const error_offset = try errUnionErrorOffset(payload_ty, mod); |
| 7398 | if (isByRef(err_un_ty, mod)) { | 7410 | if (isByRef(err_un_ty, mod)) { |
| 7399 | const directReturn = self.isNextRet(body_tail); | 7411 | const directReturn = self.isNextRet(body_tail); |
| 7400 | const result_ptr = if (directReturn) | 7412 | const result_ptr = if (directReturn) |
| ... | @@ -7406,7 +7418,8 @@ pub const FuncGen = struct { | ... | @@ -7406,7 +7418,8 @@ pub const FuncGen = struct { |
| 7406 | }; | 7418 | }; |
| 7407 | | 7419 | |
| 7408 | const err_ptr = try self.wip.gepStruct(err_un_llvm_ty, result_ptr, error_offset, ""); | 7420 | const err_ptr = try self.wip.gepStruct(err_un_llvm_ty, result_ptr, error_offset, ""); |
| 7409 | const error_alignment = Type.err_int.abiAlignment(mod).toLlvm(); | 7421 | const err_int_ty = try mod.errorIntType(); |
| | 7422 | const error_alignment = err_int_ty.abiAlignment(mod).toLlvm(); |
| 7410 | _ = try self.wip.store(.normal, operand, err_ptr, error_alignment); | 7423 | _ = try self.wip.store(.normal, operand, err_ptr, error_alignment); |
| 7411 | const payload_ptr = try self.wip.gepStruct(err_un_llvm_ty, result_ptr, payload_offset, ""); | 7424 | const payload_ptr = try self.wip.gepStruct(err_un_llvm_ty, result_ptr, payload_offset, ""); |
| 7412 | const payload_ptr_ty = try mod.singleMutPtrType(payload_ty); | 7425 | const payload_ptr_ty = try mod.singleMutPtrType(payload_ty); |
| ... | @@ -9363,7 +9376,7 @@ pub const FuncGen = struct { | ... | @@ -9363,7 +9376,7 @@ pub const FuncGen = struct { |
| 9363 | | 9376 | |
| 9364 | for (names) |name| { | 9377 | for (names) |name| { |
| 9365 | const err_int = mod.global_error_set.getIndex(name).?; | 9378 | const err_int = mod.global_error_set.getIndex(name).?; |
| 9366 | const this_tag_int_value = try o.builder.intConst(Builder.Type.err_int, err_int); | 9379 | const this_tag_int_value = try o.builder.intConst(try o.errorIntType(), err_int); |
| 9367 | try wip_switch.addCase(this_tag_int_value, valid_block, &self.wip); | 9380 | try wip_switch.addCase(this_tag_int_value, valid_block, &self.wip); |
| 9368 | } | 9381 | } |
| 9369 | self.wip.cursor = .{ .block = valid_block }; | 9382 | self.wip.cursor = .{ .block = valid_block }; |
| ... | @@ -9545,7 +9558,7 @@ pub const FuncGen = struct { | ... | @@ -9545,7 +9558,7 @@ pub const FuncGen = struct { |
| 9545 | if (o.builder.getGlobal(name)) |llvm_fn| return llvm_fn.ptrConst(&o.builder).kind.function; | 9558 | if (o.builder.getGlobal(name)) |llvm_fn| return llvm_fn.ptrConst(&o.builder).kind.function; |
| 9546 | | 9559 | |
| 9547 | const function_index = try o.builder.addFunction( | 9560 | const function_index = try o.builder.addFunction( |
| 9548 | try o.builder.fnType(.i1, &.{Builder.Type.err_int}, .normal), | 9561 | try o.builder.fnType(.i1, &.{try o.errorIntType()}, .normal), |
| 9549 | name, | 9562 | name, |
| 9550 | toLlvmAddressSpace(.generic, o.module.getTarget()), | 9563 | toLlvmAddressSpace(.generic, o.module.getTarget()), |
| 9551 | ); | 9564 | ); |
| ... | @@ -10880,7 +10893,7 @@ fn lowerFnRetTy(o: *Object, fn_info: InternPool.Key.FuncType) Allocator.Error!Bu | ... | @@ -10880,7 +10893,7 @@ fn lowerFnRetTy(o: *Object, fn_info: InternPool.Key.FuncType) Allocator.Error!Bu |
| 10880 | // If the return type is an error set or an error union, then we make this | 10893 | // If the return type is an error set or an error union, then we make this |
| 10881 | // anyerror return type instead, so that it can be coerced into a function | 10894 | // anyerror return type instead, so that it can be coerced into a function |
| 10882 | // pointer type which has anyerror as the return type. | 10895 | // pointer type which has anyerror as the return type. |
| 10883 | return if (return_type.isError(mod)) Builder.Type.err_int else .void; | 10896 | return if (return_type.isError(mod)) try o.errorIntType() else .void; |
| 10884 | } | 10897 | } |
| 10885 | const target = mod.getTarget(); | 10898 | const target = mod.getTarget(); |
| 10886 | switch (fn_info.cc) { | 10899 | switch (fn_info.cc) { |
| ... | @@ -11633,12 +11646,14 @@ fn buildAllocaInner( | ... | @@ -11633,12 +11646,14 @@ fn buildAllocaInner( |
| 11633 | return wip.conv(.unneeded, alloca, .ptr, ""); | 11646 | return wip.conv(.unneeded, alloca, .ptr, ""); |
| 11634 | } | 11647 | } |
| 11635 | | 11648 | |
| 11636 | fn errUnionPayloadOffset(payload_ty: Type, mod: *Module) u1 { | 11649 | fn errUnionPayloadOffset(payload_ty: Type, mod: *Module) !u1 { |
| 11637 | return @intFromBool(Type.err_int.abiAlignment(mod).compare(.gt, payload_ty.abiAlignment(mod))); | 11650 | const err_int_ty = try mod.errorIntType(); |
| | 11651 | return @intFromBool(err_int_ty.abiAlignment(mod).compare(.gt, payload_ty.abiAlignment(mod))); |
| 11638 | } | 11652 | } |
| 11639 | | 11653 | |
| 11640 | fn errUnionErrorOffset(payload_ty: Type, mod: *Module) u1 { | 11654 | fn errUnionErrorOffset(payload_ty: Type, mod: *Module) !u1 { |
| 11641 | return @intFromBool(Type.err_int.abiAlignment(mod).compare(.lte, payload_ty.abiAlignment(mod))); | 11655 | const err_int_ty = try mod.errorIntType(); |
| | 11656 | return @intFromBool(err_int_ty.abiAlignment(mod).compare(.lte, payload_ty.abiAlignment(mod))); |
| 11642 | } | 11657 | } |
| 11643 | | 11658 | |
| 11644 | /// Returns true for asm constraint (e.g. "=*m", "=r") if it accepts a memory location | 11659 | /// Returns true for asm constraint (e.g. "=*m", "=r") if it accepts a memory location |