| ... | @@ -10414,11 +10414,12 @@ pub const Value = struct { | ... | @@ -10414,11 +10414,12 @@ pub const Value = struct { |
| 10414 | } }, | 10414 | } }, |
| 10415 | .error_union => |error_union| { | 10415 | .error_union => |error_union| { |
| 10416 | const error_union_type = ip.indexToKey(error_union.ty).error_union_type; | 10416 | const error_union_type = ip.indexToKey(error_union.ty).error_union_type; |
| | 10417 | const error_set_ty: ZigType = .fromInterned(error_union_type.error_set_type); |
| 10417 | const payload_ty: ZigType = .fromInterned(error_union_type.payload_type); | 10418 | const payload_ty: ZigType = .fromInterned(error_union_type.payload_type); |
| 10418 | if (!ip.isNoReturn(error_union_type.error_set_type) and | 10419 | const error_set_offset = codegen.errUnionErrorOffset(payload_ty, zcu); |
| 10419 | offset == codegen.errUnionErrorOffset(payload_ty, zcu)) | 10420 | const error_set_size = error_set_ty.abiSize(zcu); |
| 10420 | { | 10421 | if (offset >= error_set_offset and offset + size <= error_set_offset + error_set_size) { |
| 10421 | offset = 0; | 10422 | offset -= error_set_offset; |
| 10422 | continue :constant_key switch (error_union.val) { | 10423 | continue :constant_key switch (error_union.val) { |
| 10423 | .err_name => |err_name| .{ .err = .{ | 10424 | .err_name => |err_name| .{ .err = .{ |
| 10424 | .ty = error_union_type.error_set_type, | 10425 | .ty = error_union_type.error_set_type, |
| ... | @@ -10430,15 +10431,18 @@ pub const Value = struct { | ... | @@ -10430,15 +10431,18 @@ pub const Value = struct { |
| 10430 | } }, | 10431 | } }, |
| 10431 | }; | 10432 | }; |
| 10432 | } | 10433 | } |
| 10433 | assert(payload_ty.hasRuntimeBitsIgnoreComptime(zcu)); | 10434 | const payload_offset = codegen.errUnionPayloadOffset(payload_ty, zcu); |
| 10434 | offset -= @intCast(codegen.errUnionPayloadOffset(payload_ty, zcu)); | 10435 | const payload_size = payload_ty.abiSize(zcu); |
| 10435 | switch (error_union.val) { | 10436 | if (offset >= payload_offset and offset + size <= payload_offset + payload_size) { |
| 10436 | .err_name => continue :constant_key .{ .undef = error_union_type.payload_type }, | 10437 | offset -= payload_offset; |
| 10437 | .payload => |payload| { | 10438 | switch (error_union.val) { |
| 10438 | constant = payload; | 10439 | .err_name => continue :constant_key .{ .undef = error_union_type.payload_type }, |
| 10439 | constant_key = ip.indexToKey(payload); | 10440 | .payload => |payload| { |
| 10440 | continue :constant_key constant_key; | 10441 | constant = payload; |
| 10441 | }, | 10442 | constant_key = ip.indexToKey(payload); |
| | 10443 | continue :constant_key constant_key; |
| | 10444 | }, |
| | 10445 | } |
| 10442 | } | 10446 | } |
| 10443 | }, | 10447 | }, |
| 10444 | .enum_tag => |enum_tag| continue :constant_key .{ .int = ip.indexToKey(enum_tag.int).int }, | 10448 | .enum_tag => |enum_tag| continue :constant_key .{ .int = ip.indexToKey(enum_tag.int).int }, |
| ... | @@ -10975,7 +10979,17 @@ fn hasRepeatedByteRepr(isel: *Select, constant: Constant) error{OutOfMemory}!?u8 | ... | @@ -10975,7 +10979,17 @@ fn hasRepeatedByteRepr(isel: *Select, constant: Constant) error{OutOfMemory}!?u8 |
| 10975 | fn writeToMemory(isel: *Select, constant: Constant, buffer: []u8) error{OutOfMemory}!bool { | 10979 | fn writeToMemory(isel: *Select, constant: Constant, buffer: []u8) error{OutOfMemory}!bool { |
| 10976 | const zcu = isel.pt.zcu; | 10980 | const zcu = isel.pt.zcu; |
| 10977 | const ip = &zcu.intern_pool; | 10981 | const ip = &zcu.intern_pool; |
| 10978 | switch (ip.indexToKey(constant.toIntern())) { | 10982 | if (try isel.writeKeyToMemory(ip.indexToKey(constant.toIntern()), buffer)) return true; |
| | 10983 | constant.writeToMemory(isel.pt, buffer) catch |err| switch (err) { |
| | 10984 | error.OutOfMemory => return error.OutOfMemory, |
| | 10985 | error.ReinterpretDeclRef, error.Unimplemented, error.IllDefinedMemoryLayout => return false, |
| | 10986 | }; |
| | 10987 | return true; |
| | 10988 | } |
| | 10989 | fn writeKeyToMemory(isel: *Select, constant_key: InternPool.Key, buffer: []u8) error{OutOfMemory}!bool { |
| | 10990 | const zcu = isel.pt.zcu; |
| | 10991 | const ip = &zcu.intern_pool; |
| | 10992 | switch (constant_key) { |
| 10979 | .int_type, | 10993 | .int_type, |
| 10980 | .ptr_type, | 10994 | .ptr_type, |
| 10981 | .array_type, | 10995 | .array_type, |
| ... | @@ -10997,6 +11011,37 @@ fn writeToMemory(isel: *Select, constant: Constant, buffer: []u8) error{OutOfMem | ... | @@ -10997,6 +11011,37 @@ fn writeToMemory(isel: *Select, constant: Constant, buffer: []u8) error{OutOfMem |
| 10997 | .empty_enum_value, | 11011 | .empty_enum_value, |
| 10998 | .memoized_call, | 11012 | .memoized_call, |
| 10999 | => unreachable, // not a runtime value | 11013 | => unreachable, // not a runtime value |
| | 11014 | .err => |err| { |
| | 11015 | const error_int = ip.getErrorValueIfExists(err.name).?; |
| | 11016 | switch (buffer.len) { |
| | 11017 | else => unreachable, |
| | 11018 | inline 1...4 => |size| std.mem.writeInt( |
| | 11019 | @Type(.{ .int = .{ .signedness = .unsigned, .bits = 8 * size } }), |
| | 11020 | buffer[0..size], |
| | 11021 | @intCast(error_int), |
| | 11022 | isel.target.cpu.arch.endian(), |
| | 11023 | ), |
| | 11024 | } |
| | 11025 | }, |
| | 11026 | .error_union => |error_union| { |
| | 11027 | const error_union_type = ip.indexToKey(error_union.ty).error_union_type; |
| | 11028 | const error_set_ty: ZigType = .fromInterned(error_union_type.error_set_type); |
| | 11029 | const payload_ty: ZigType = .fromInterned(error_union_type.payload_type); |
| | 11030 | const error_set = buffer[@intCast(codegen.errUnionErrorOffset(payload_ty, zcu))..][0..@intCast(error_set_ty.abiSize(zcu))]; |
| | 11031 | switch (error_union.val) { |
| | 11032 | .err_name => |err_name| if (!try isel.writeKeyToMemory(.{ .err = .{ |
| | 11033 | .ty = error_set_ty.toIntern(), |
| | 11034 | .name = err_name, |
| | 11035 | } }, error_set)) return false, |
| | 11036 | .payload => |payload| { |
| | 11037 | if (!try isel.writeToMemory( |
| | 11038 | .fromInterned(payload), |
| | 11039 | buffer[@intCast(codegen.errUnionPayloadOffset(payload_ty, zcu))..][0..@intCast(payload_ty.abiSize(zcu))], |
| | 11040 | )) return false; |
| | 11041 | @memset(error_set, 0); |
| | 11042 | }, |
| | 11043 | } |
| | 11044 | }, |
| 11000 | .opt => |opt| { | 11045 | .opt => |opt| { |
| 11001 | const child_size: usize = @intCast(ZigType.fromInterned(ip.indexToKey(opt.ty).opt_type).abiSize(zcu)); | 11046 | const child_size: usize = @intCast(ZigType.fromInterned(ip.indexToKey(opt.ty).opt_type).abiSize(zcu)); |
| 11002 | switch (opt.val) { | 11047 | switch (opt.val) { |
| ... | @@ -11008,7 +11053,6 @@ fn writeToMemory(isel: *Select, constant: Constant, buffer: []u8) error{OutOfMem | ... | @@ -11008,7 +11053,6 @@ fn writeToMemory(isel: *Select, constant: Constant, buffer: []u8) error{OutOfMem |
| 11008 | if (!ZigType.fromInterned(opt.ty).optionalReprIsPayload(zcu)) buffer[child_size] = @intFromBool(true); | 11053 | if (!ZigType.fromInterned(opt.ty).optionalReprIsPayload(zcu)) buffer[child_size] = @intFromBool(true); |
| 11009 | }, | 11054 | }, |
| 11010 | } | 11055 | } |
| 11011 | return true; | | |
| 11012 | }, | 11056 | }, |
| 11013 | .aggregate => |aggregate| switch (ip.indexToKey(aggregate.ty)) { | 11057 | .aggregate => |aggregate| switch (ip.indexToKey(aggregate.ty)) { |
| 11014 | else => unreachable, | 11058 | else => unreachable, |
| ... | @@ -11027,9 +11071,8 @@ fn writeToMemory(isel: *Select, constant: Constant, buffer: []u8) error{OutOfMem | ... | @@ -11027,9 +11071,8 @@ fn writeToMemory(isel: *Select, constant: Constant, buffer: []u8) error{OutOfMem |
| 11027 | elem_offset += elem_size; | 11071 | elem_offset += elem_size; |
| 11028 | }, | 11072 | }, |
| 11029 | } | 11073 | } |
| 11030 | return true; | | |
| 11031 | }, | 11074 | }, |
| 11032 | .vector_type => {}, | 11075 | .vector_type => return false, |
| 11033 | .struct_type => { | 11076 | .struct_type => { |
| 11034 | const loaded_struct = ip.loadStructType(aggregate.ty); | 11077 | const loaded_struct = ip.loadStructType(aggregate.ty); |
| 11035 | switch (loaded_struct.layout) { | 11078 | switch (loaded_struct.layout) { |
| ... | @@ -11052,9 +11095,8 @@ fn writeToMemory(isel: *Select, constant: Constant, buffer: []u8) error{OutOfMem | ... | @@ -11052,9 +11095,8 @@ fn writeToMemory(isel: *Select, constant: Constant, buffer: []u8) error{OutOfMem |
| 11052 | }), buffer[@intCast(field_offset)..][0..@intCast(field_size)])) return false; | 11095 | }), buffer[@intCast(field_offset)..][0..@intCast(field_size)])) return false; |
| 11053 | field_offset += field_size; | 11096 | field_offset += field_size; |
| 11054 | } | 11097 | } |
| 11055 | return true; | | |
| 11056 | }, | 11098 | }, |
| 11057 | .@"extern", .@"packed" => {}, | 11099 | .@"extern", .@"packed" => return false, |
| 11058 | } | 11100 | } |
| 11059 | }, | 11101 | }, |
| 11060 | .tuple_type => |tuple_type| { | 11102 | .tuple_type => |tuple_type| { |
| ... | @@ -11071,15 +11113,10 @@ fn writeToMemory(isel: *Select, constant: Constant, buffer: []u8) error{OutOfMem | ... | @@ -11071,15 +11113,10 @@ fn writeToMemory(isel: *Select, constant: Constant, buffer: []u8) error{OutOfMem |
| 11071 | }), buffer[@intCast(field_offset)..][0..@intCast(field_size)])) return false; | 11113 | }), buffer[@intCast(field_offset)..][0..@intCast(field_size)])) return false; |
| 11072 | field_offset += field_size; | 11114 | field_offset += field_size; |
| 11073 | } | 11115 | } |
| 11074 | return true; | | |
| 11075 | }, | 11116 | }, |
| 11076 | }, | 11117 | }, |
| 11077 | else => {}, | 11118 | else => return false, |
| 11078 | } | 11119 | } |
| 11079 | constant.writeToMemory(isel.pt, buffer) catch |err| switch (err) { | | |
| 11080 | error.OutOfMemory => return error.OutOfMemory, | | |
| 11081 | error.ReinterpretDeclRef, error.Unimplemented, error.IllDefinedMemoryLayout => return false, | | |
| 11082 | }; | | |
| 11083 | return true; | 11120 | return true; |
| 11084 | } | 11121 | } |
| 11085 | | 11122 | |