| ... | @@ -421,7 +421,11 @@ pub const StackIterator = struct { | ... | @@ -421,7 +421,11 @@ pub const StackIterator = struct { |
| 421 | // stacks with frames that don't use a frame pointer (ie. -fomit-frame-pointer). | 421 | // stacks with frames that don't use a frame pointer (ie. -fomit-frame-pointer). |
| 422 | debug_info: ?*DebugInfo, | 422 | debug_info: ?*DebugInfo, |
| 423 | dwarf_context: if (supports_context) DW.UnwindContext else void = undefined, | 423 | dwarf_context: if (supports_context) DW.UnwindContext else void = undefined, |
| 424 | const supports_context = @hasDecl(os.system, "ucontext_t"); | 424 | const supports_context = @hasDecl(os.system, "ucontext_t") and |
| | 425 | (builtin.os.tag != .linux or switch (builtin.cpu.arch) { |
| | 426 | .mips, .riscv64 => false, |
| | 427 | else => true, |
| | 428 | }); |
| 425 | | 429 | |
| 426 | pub fn init(first_address: ?usize, fp: ?usize) StackIterator { | 430 | pub fn init(first_address: ?usize, fp: ?usize) StackIterator { |
| 427 | if (native_arch == .sparc64) { | 431 | if (native_arch == .sparc64) { |
| ... | @@ -528,7 +532,7 @@ pub const StackIterator = struct { | ... | @@ -528,7 +532,7 @@ pub const StackIterator = struct { |
| 528 | | 532 | |
| 529 | fn next_dwarf(self: *StackIterator) !void { | 533 | fn next_dwarf(self: *StackIterator) !void { |
| 530 | const module = try self.debug_info.?.getModuleForAddress(self.dwarf_context.pc); | 534 | const module = try self.debug_info.?.getModuleForAddress(self.dwarf_context.pc); |
| 531 | if (module.getDwarfInfo()) |di| { | 535 | if (try module.getDwarfInfoForAddress(self.debug_info.?.allocator, self.dwarf_context.pc)) |di| { |
| 532 | self.dwarf_context.reg_ctx.eh_frame = true; | 536 | self.dwarf_context.reg_ctx.eh_frame = true; |
| 533 | self.dwarf_context.reg_ctx.is_macho = di.is_macho; | 537 | self.dwarf_context.reg_ctx.is_macho = di.is_macho; |
| 534 | try di.unwindFrame(self.debug_info.?.allocator, &self.dwarf_context, module.base_address); | 538 | try di.unwindFrame(self.debug_info.?.allocator, &self.dwarf_context, module.base_address); |
| ... | @@ -1684,6 +1688,26 @@ pub const ModuleDebugInfo = switch (native_os) { | ... | @@ -1684,6 +1688,26 @@ pub const ModuleDebugInfo = switch (native_os) { |
| 1684 | return info; | 1688 | return info; |
| 1685 | } | 1689 | } |
| 1686 | | 1690 | |
| | 1691 | fn getOFileForAddress(self: *@This(), allocator: mem.Allocator, address: usize) !?*OFileInfo { |
| | 1692 | nosuspend { |
| | 1693 | const relocated_address = address - self.base_address; |
| | 1694 | const symbol = machoSearchSymbols(self.symbols, relocated_address) orelse |
| | 1695 | return null; |
| | 1696 | |
| | 1697 | const o_file_path = mem.sliceTo(self.strings[symbol.ofile..], 0); |
| | 1698 | var o_file_info = self.ofiles.get(o_file_path) orelse |
| | 1699 | (self.loadOFile(allocator, o_file_path) catch |err| switch (err) { |
| | 1700 | error.FileNotFound, |
| | 1701 | error.MissingDebugInfo, |
| | 1702 | error.InvalidDebugInfo, |
| | 1703 | => return null, |
| | 1704 | else => return err, |
| | 1705 | }); |
| | 1706 | |
| | 1707 | return &o_file_info.di; |
| | 1708 | } |
| | 1709 | } |
| | 1710 | |
| 1687 | pub fn getSymbolAtAddress(self: *@This(), allocator: mem.Allocator, address: usize) !SymbolInfo { | 1711 | pub fn getSymbolAtAddress(self: *@This(), allocator: mem.Allocator, address: usize) !SymbolInfo { |
| 1688 | nosuspend { | 1712 | nosuspend { |
| 1689 | // Translate the VA into an address into this object | 1713 | // Translate the VA into an address into this object |
| ... | @@ -1749,40 +1773,38 @@ pub const ModuleDebugInfo = switch (native_os) { | ... | @@ -1749,40 +1773,38 @@ pub const ModuleDebugInfo = switch (native_os) { |
| 1749 | } | 1773 | } |
| 1750 | } | 1774 | } |
| 1751 | | 1775 | |
| 1752 | pub fn getDwarfInfo(self: *@This()) ?*const DW.DwarfInfo { | 1776 | pub fn getDwarfInfoForAddress(self: *@This(), allocator: mem.Allocator, address: usize) !?*const DW.DwarfInfo { |
| 1753 | // TODO: Implement | 1777 | nosuspend { |
| 1754 | _ = self; | 1778 | const relocated_address = address - self.base_address; |
| 1755 | return null; | 1779 | const symbol = machoSearchSymbols(self.symbols, relocated_address) orelse |
| | 1780 | return null; |
| | 1781 | |
| | 1782 | const o_file_path = mem.sliceTo(self.strings[symbol.ofile..], 0); |
| | 1783 | var o_file_info = self.ofiles.get(o_file_path) orelse |
| | 1784 | (self.loadOFile(allocator, o_file_path) catch |err| switch (err) { |
| | 1785 | error.FileNotFound, |
| | 1786 | error.MissingDebugInfo, |
| | 1787 | error.InvalidDebugInfo, |
| | 1788 | => return null, |
| | 1789 | else => return err, |
| | 1790 | }); |
| | 1791 | |
| | 1792 | return &o_file_info.di; |
| | 1793 | } |
| 1756 | } | 1794 | } |
| 1757 | }, | 1795 | }, |
| 1758 | .uefi, .windows => struct { | 1796 | .uefi, .windows => struct { |
| 1759 | base_address: usize, | 1797 | base_address: usize, |
| 1760 | debug_data: PdbOrDwarf, | 1798 | debug_data: PdbOrDwarf, |
| 1761 | coff_image_base: u64, | 1799 | coff_image_base: u64, |
| | 1800 | /// Only used if debug_data is .pdb |
| 1762 | coff_section_headers: []coff.SectionHeader, | 1801 | coff_section_headers: []coff.SectionHeader, |
| 1763 | | 1802 | |
| 1764 | fn deinit(self: *@This(), allocator: mem.Allocator) void { | 1803 | fn deinit(self: *@This(), allocator: mem.Allocator) void { |
| 1765 | switch (self.debug_data) { | | |
| 1766 | .dwarf => |*dwarf| { | | |
| 1767 | allocator.free(dwarf.debug_info); | | |
| 1768 | allocator.free(dwarf.debug_abbrev); | | |
| 1769 | allocator.free(dwarf.debug_str); | | |
| 1770 | allocator.free(dwarf.debug_line); | | |
| 1771 | if (dwarf.debug_str_offsets) |d| allocator.free(d); | | |
| 1772 | if (dwarf.debug_line_str) |d| allocator.free(d); | | |
| 1773 | if (dwarf.debug_ranges) |d| allocator.free(d); | | |
| 1774 | if (dwarf.debug_loclists) |d| allocator.free(d); | | |
| 1775 | if (dwarf.debug_rnglists) |d| allocator.free(d); | | |
| 1776 | if (dwarf.debug_addr) |d| allocator.free(d); | | |
| 1777 | if (dwarf.debug_names) |d| allocator.free(d); | | |
| 1778 | if (dwarf.debug_frame) |d| allocator.free(d); | | |
| 1779 | }, | | |
| 1780 | .pdb => { | | |
| 1781 | allocator.free(self.coff_section_headers); | | |
| 1782 | }, | | |
| 1783 | } | | |
| 1784 | | | |
| 1785 | self.debug_data.deinit(allocator); | 1804 | self.debug_data.deinit(allocator); |
| | 1805 | if (self.debug_data == .pdb) { |
| | 1806 | allocator.free(self.coff_section_headers); |
| | 1807 | } |
| 1786 | } | 1808 | } |
| 1787 | | 1809 | |
| 1788 | pub fn getSymbolAtAddress(self: *@This(), allocator: mem.Allocator, address: usize) !SymbolInfo { | 1810 | pub fn getSymbolAtAddress(self: *@This(), allocator: mem.Allocator, address: usize) !SymbolInfo { |
| ... | @@ -1835,7 +1857,10 @@ pub const ModuleDebugInfo = switch (native_os) { | ... | @@ -1835,7 +1857,10 @@ pub const ModuleDebugInfo = switch (native_os) { |
| 1835 | }; | 1857 | }; |
| 1836 | } | 1858 | } |
| 1837 | | 1859 | |
| 1838 | pub fn getDwarfInfo(self: *@This()) ?*const DW.DwarfInfo { | 1860 | pub fn getDwarfInfoForAddress(self: *@This(), allocator: mem.Allocator, address: usize) !?*const DW.DwarfInfo { |
| | 1861 | _ = allocator; |
| | 1862 | _ = address; |
| | 1863 | |
| 1839 | return switch (self.debug_data) { | 1864 | return switch (self.debug_data) { |
| 1840 | .dwarf => |*dwarf| dwarf, | 1865 | .dwarf => |*dwarf| dwarf, |
| 1841 | else => null, | 1866 | else => null, |
| ... | @@ -1860,7 +1885,9 @@ pub const ModuleDebugInfo = switch (native_os) { | ... | @@ -1860,7 +1885,9 @@ pub const ModuleDebugInfo = switch (native_os) { |
| 1860 | return getSymbolFromDwarf(allocator, relocated_address, &self.dwarf); | 1885 | return getSymbolFromDwarf(allocator, relocated_address, &self.dwarf); |
| 1861 | } | 1886 | } |
| 1862 | | 1887 | |
| 1863 | pub fn getDwarfInfo(self: *@This()) ?*const DW.DwarfInfo { | 1888 | pub fn getDwarfInfoForAddress(self: *@This(), allocator: mem.Allocator, address: usize) !?*const DW.DwarfInfo { |
| | 1889 | _ = allocator; |
| | 1890 | _ = address; |
| 1864 | return &self.dwarf; | 1891 | return &self.dwarf; |
| 1865 | } | 1892 | } |
| 1866 | }, | 1893 | }, |
| ... | @@ -1877,8 +1904,10 @@ pub const ModuleDebugInfo = switch (native_os) { | ... | @@ -1877,8 +1904,10 @@ pub const ModuleDebugInfo = switch (native_os) { |
| 1877 | return SymbolInfo{}; | 1904 | return SymbolInfo{}; |
| 1878 | } | 1905 | } |
| 1879 | | 1906 | |
| 1880 | pub fn getDwarfInfo(self: *@This()) ?*const DW.DwarfInfo { | 1907 | pub fn getDwarfInfoForAddress(self: *@This(), allocator: mem.Allocator, address: usize) !?*const DW.DwarfInfo { |
| 1881 | _ = self; | 1908 | _ = self; |
| | 1909 | _ = allocator; |
| | 1910 | _ = address; |
| 1882 | return null; | 1911 | return null; |
| 1883 | } | 1912 | } |
| 1884 | }, | 1913 | }, |