| ... | ... | @@ -374,66 +374,7 @@ pub fn generateSymbol( |
| 374 | 374 | |
| 375 | 375 | return Result.ok; |
| 376 | 376 | }, |
| 377 | | .field_ptr => { |
| 378 | | const field_ptr = typed_value.val.castTag(.field_ptr).?.data; |
| 379 | | const container_ptr = field_ptr.container_ptr; |
| 380 | | |
| 381 | | switch (container_ptr.tag()) { |
| 382 | | .decl_ref => { |
| 383 | | const decl_index = container_ptr.castTag(.decl_ref).?.data; |
| 384 | | const decl = mod.declPtr(decl_index); |
| 385 | | const addend = blk: { |
| 386 | | switch (decl.ty.zigTypeTag()) { |
| 387 | | .Struct => { |
| 388 | | const addend = decl.ty.structFieldOffset(field_ptr.field_index, target); |
| 389 | | break :blk @intCast(u32, addend); |
| 390 | | }, |
| 391 | | .Pointer => { |
| 392 | | assert(decl.ty.isSlice()); |
| 393 | | var buf: Type.SlicePtrFieldTypeBuffer = undefined; |
| 394 | | const addend = switch (field_ptr.field_index) { |
| 395 | | 0 => 0, |
| 396 | | 1 => decl.ty.slicePtrFieldType(&buf).abiSize(target), |
| 397 | | else => unreachable, |
| 398 | | }; |
| 399 | | break :blk @intCast(u32, addend); |
| 400 | | }, |
| 401 | | else => return Result{ |
| 402 | | .fail = try ErrorMsg.create( |
| 403 | | bin_file.allocator, |
| 404 | | src_loc, |
| 405 | | "TODO implement generateSymbol for pointer type value: '{s}'", |
| 406 | | .{@tagName(typed_value.val.tag())}, |
| 407 | | ), |
| 408 | | }, |
| 409 | | } |
| 410 | | }; |
| 411 | | return lowerDeclRef(bin_file, src_loc, typed_value, decl_index, code, debug_output, .{ |
| 412 | | .parent_atom_index = reloc_info.parent_atom_index, |
| 413 | | .addend = (reloc_info.addend orelse 0) + addend, |
| 414 | | }); |
| 415 | | }, |
| 416 | | .field_ptr => { |
| 417 | | switch (try generateSymbol(bin_file, src_loc, .{ |
| 418 | | .ty = typed_value.ty, |
| 419 | | .val = container_ptr, |
| 420 | | }, code, debug_output, reloc_info)) { |
| 421 | | .ok => {}, |
| 422 | | .fail => |em| return Result{ .fail = em }, |
| 423 | | } |
| 424 | | return Result.ok; |
| 425 | | }, |
| 426 | | else => return Result{ |
| 427 | | .fail = try ErrorMsg.create( |
| 428 | | bin_file.allocator, |
| 429 | | src_loc, |
| 430 | | "TODO implement generateSymbol for pointer type value: '{s}'", |
| 431 | | .{@tagName(typed_value.val.tag())}, |
| 432 | | ), |
| 433 | | }, |
| 434 | | } |
| 435 | | }, |
| 436 | | .elem_ptr => return lowerParentPtr( |
| 377 | .field_ptr, .elem_ptr => return lowerParentPtr( |
| 437 | 378 | bin_file, |
| 438 | 379 | src_loc, |
| 439 | 380 | typed_value, |
| ... | ... | @@ -846,16 +787,12 @@ pub fn generateSymbol( |
| 846 | 787 | }, |
| 847 | 788 | else => unreachable, |
| 848 | 789 | }, |
| 849 | | else => |t| { |
| 850 | | return Result{ |
| 851 | | .fail = try ErrorMsg.create( |
| 852 | | bin_file.allocator, |
| 853 | | src_loc, |
| 854 | | "TODO implement generateSymbol for type '{s}'", |
| 855 | | .{@tagName(t)}, |
| 856 | | ), |
| 857 | | }; |
| 858 | | }, |
| 790 | else => |t| return Result{ .fail = try ErrorMsg.create( |
| 791 | bin_file.allocator, |
| 792 | src_loc, |
| 793 | "TODO implement generateSymbol for type '{s}'", |
| 794 | .{@tagName(t)}, |
| 795 | ) }, |
| 859 | 796 | } |
| 860 | 797 | } |
| 861 | 798 | |
| ... | ... | @@ -871,6 +808,38 @@ fn lowerParentPtr( |
| 871 | 808 | const target = bin_file.options.target; |
| 872 | 809 | |
| 873 | 810 | switch (parent_ptr.tag()) { |
| 811 | .field_ptr => { |
| 812 | const field_ptr = parent_ptr.castTag(.field_ptr).?.data; |
| 813 | return lowerParentPtr( |
| 814 | bin_file, |
| 815 | src_loc, |
| 816 | typed_value, |
| 817 | field_ptr.container_ptr, |
| 818 | code, |
| 819 | debug_output, |
| 820 | reloc_info.offset(@intCast(u32, switch (field_ptr.container_ty.zigTypeTag()) { |
| 821 | .Pointer => offset: { |
| 822 | assert(field_ptr.container_ty.isSlice()); |
| 823 | var buf: Type.SlicePtrFieldTypeBuffer = undefined; |
| 824 | break :offset switch (field_ptr.field_index) { |
| 825 | 0 => 0, |
| 826 | 1 => field_ptr.container_ty.slicePtrFieldType(&buf).abiSize(target), |
| 827 | else => unreachable, |
| 828 | }; |
| 829 | }, |
| 830 | .Struct, .Union => field_ptr.container_ty.structFieldOffset( |
| 831 | field_ptr.field_index, |
| 832 | target, |
| 833 | ), |
| 834 | else => return Result{ .fail = try ErrorMsg.create( |
| 835 | bin_file.allocator, |
| 836 | src_loc, |
| 837 | "TODO implement lowerParentPtr for field_ptr with a container of type {}", |
| 838 | .{field_ptr.container_ty.fmt(bin_file.options.module.?)}, |
| 839 | ) }, |
| 840 | })), |
| 841 | ); |
| 842 | }, |
| 874 | 843 | .elem_ptr => { |
| 875 | 844 | const elem_ptr = parent_ptr.castTag(.elem_ptr).?.data; |
| 876 | 845 | return lowerParentPtr( |