| ... | ... | @@ -239,7 +239,7 @@ pub const Die = struct { |
| 239 | 239 | return switch (form_value.*) { |
| 240 | 240 | .addr => |value| value, |
| 241 | 241 | .addrx => |index| di.readDebugAddr(compile_unit, index), |
| 242 | | else => error.InvalidDebugInfo, |
| 242 | else => bad(), |
| 243 | 243 | }; |
| 244 | 244 | } |
| 245 | 245 | |
| ... | ... | @@ -252,7 +252,7 @@ pub const Die = struct { |
| 252 | 252 | const form_value = self.getAttr(id) orelse return error.MissingDebugInfo; |
| 253 | 253 | return switch (form_value.*) { |
| 254 | 254 | .Const => |value| value.asUnsignedLe(), |
| 255 | | else => error.InvalidDebugInfo, |
| 255 | else => bad(), |
| 256 | 256 | }; |
| 257 | 257 | } |
| 258 | 258 | |
| ... | ... | @@ -260,7 +260,7 @@ pub const Die = struct { |
| 260 | 260 | const form_value = self.getAttr(id) orelse return error.MissingDebugInfo; |
| 261 | 261 | return switch (form_value.*) { |
| 262 | 262 | .ref => |value| value, |
| 263 | | else => error.InvalidDebugInfo, |
| 263 | else => bad(), |
| 264 | 264 | }; |
| 265 | 265 | } |
| 266 | 266 | |
| ... | ... | @@ -2159,7 +2159,7 @@ pub const ElfModule = struct { |
| 2159 | 2159 | if (mem.eql(u8, name, ".gnu_debuglink")) { |
| 2160 | 2160 | const gnu_debuglink = try chopSlice(mapped_mem, shdr.sh_offset, shdr.sh_size); |
| 2161 | 2161 | const debug_filename = mem.sliceTo(@as([*:0]const u8, @ptrCast(gnu_debuglink.ptr)), 0); |
| 2162 | | const crc_offset = mem.alignForward(usize, @intFromPtr(&debug_filename[debug_filename.len]) + 1, 4) - @intFromPtr(gnu_debuglink.ptr); |
| 2162 | const crc_offset = mem.alignForward(usize, debug_filename.len + 1, 4); |
| 2163 | 2163 | const crc_bytes = gnu_debuglink[crc_offset..][0..4]; |
| 2164 | 2164 | separate_debug_crc = mem.readInt(u32, crc_bytes, native_endian); |
| 2165 | 2165 | separate_debug_filename = debug_filename; |
| ... | ... | @@ -2253,25 +2253,30 @@ pub const ElfModule = struct { |
| 2253 | 2253 | if (elf_filename != null and mem.eql(u8, elf_filename.?, separate_filename)) |
| 2254 | 2254 | return error.MissingDebugInfo; |
| 2255 | 2255 | |
| 2256 | | // <cwd>/<gnu_debuglink> |
| 2257 | | if (loadPath( |
| 2258 | | gpa, |
| 2259 | | .{ |
| 2260 | | .root_dir = std.Build.Cache.Directory.cwd(), |
| 2261 | | .sub_path = separate_filename, |
| 2262 | | }, |
| 2263 | | null, |
| 2264 | | separate_debug_crc, |
| 2265 | | &sections, |
| 2266 | | mapped_mem, |
| 2267 | | )) |debug_info| { |
| 2268 | | return debug_info; |
| 2269 | | } else |_| {} |
| 2270 | | |
| 2271 | | // <cwd>/.debug/<gnu_debuglink> |
| 2272 | | { |
| 2256 | exe_dir: { |
| 2257 | var exe_dir_buf: [std.fs.max_path_bytes]u8 = undefined; |
| 2258 | const exe_dir_path = std.fs.selfExeDirPath(&exe_dir_buf) catch break :exe_dir; |
| 2259 | var exe_dir = std.fs.openDirAbsolute(exe_dir_path, .{}) catch break :exe_dir; |
| 2260 | defer exe_dir.close(); |
| 2261 | |
| 2262 | // <exe_dir>/<gnu_debuglink> |
| 2263 | if (loadPath( |
| 2264 | gpa, |
| 2265 | .{ |
| 2266 | .root_dir = .{ .path = null, .handle = exe_dir }, |
| 2267 | .sub_path = separate_filename, |
| 2268 | }, |
| 2269 | null, |
| 2270 | separate_debug_crc, |
| 2271 | &sections, |
| 2272 | mapped_mem, |
| 2273 | )) |debug_info| { |
| 2274 | return debug_info; |
| 2275 | } else |_| {} |
| 2276 | |
| 2277 | // <exe_dir>/.debug/<gnu_debuglink> |
| 2273 | 2278 | const path: Path = .{ |
| 2274 | | .root_dir = std.Build.Cache.Directory.cwd(), |
| 2279 | .root_dir = .{ .path = null, .handle = exe_dir }, |
| 2275 | 2280 | .sub_path = try std.fs.path.join(gpa, &.{ ".debug", separate_filename }), |
| 2276 | 2281 | }; |
| 2277 | 2282 | defer gpa.free(path.sub_path); |