Skip to content

Commit 9bb7e50

Browse files
authored
Merge pull request ALSchwalm#11 from mephi42/vmlinux
Allow exporting vmlinux debuginfo
2 parents 3b7ed51 + db9d4d4 commit 9bb7e50

File tree

2 files changed

+50
-7
lines changed

2 files changed

+50
-7
lines changed

src/dwarfexport.cpp

100644100755
Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -724,7 +724,7 @@ void add_debug_info(std::shared_ptr<DwarfGenInfo> info,
724724

725725
// Only consider EXEC segments
726726
// TODO: Skip plt/got?
727-
if (!(seg->perm & SEGPERM_EXEC)) {
727+
if (!(seg->perm & SEGPERM_EXEC) && seg->type != SEG_CODE) {
728728
dwarfexport_log("Segment #", segn, " is not executable. Skipping.");
729729
continue;
730730
}
@@ -740,7 +740,8 @@ void add_debug_info(std::shared_ptr<DwarfGenInfo> info,
740740
f = get_next_func(seg->startEA);
741741

742742
if (f == nullptr) {
743-
dwarfexport_error("get_next_func() failed");
743+
dwarfexport_log("Skipping ", lsegname, " because it has no functions");
744+
continue;
744745
}
745746
}
746747

src/dwarfgen.cpp

100644100755
Lines changed: 47 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -144,7 +144,7 @@ std::shared_ptr<DwarfGenInfo> generate_dwarf_object(const Options &options) {
144144
}
145145

146146
static Elf_Scn *get_last_section(Elf *elf) {
147-
std::size_t count, max_offset = 0;
147+
std::size_t count, max_offset = 0, max_size = 0;
148148
GElf_Shdr shdr;
149149
Elf_Scn *last_scn;
150150

@@ -156,9 +156,14 @@ static Elf_Scn *get_last_section(Elf *elf) {
156156
if (!gelf_getshdr(scn, &shdr)) {
157157
dwarfexport_error("elf_getshdr() failed: ", elf_errmsg(-1));
158158
}
159-
if (shdr.sh_offset > max_offset) {
159+
if (shdr.sh_type == SHT_NOBITS) {
160+
continue;
161+
}
162+
if (shdr.sh_offset > max_offset ||
163+
(shdr.sh_offset == max_offset && shdr.sh_size > max_size)) {
160164
last_scn = scn;
161165
max_offset = shdr.sh_offset;
166+
max_size = shdr.sh_size;
162167
}
163168
}
164169
return last_scn;
@@ -243,6 +248,34 @@ static void add_debug_section_data(std::shared_ptr<DwarfGenInfo> info) {
243248
}
244249
}
245250

251+
static void log_elf(Elf *elf) {
252+
GElf_Ehdr ehdr;
253+
int scn_index;
254+
Elf_Scn *scn;
255+
GElf_Shdr shdr;
256+
257+
if (gelf_getehdr(elf, &ehdr) != &ehdr)
258+
dwarfexport_error("gelf_getehdr() failed: ", elf_errmsg(-1));
259+
260+
for (scn_index = 1; scn_index < ehdr.e_shnum; scn_index++) {
261+
if ((scn = elf_getscn(elf, scn_index)) == NULL)
262+
dwarfexport_error("getshdr() failed: ", elf_errmsg(-1));
263+
if (gelf_getshdr(scn, &shdr) != &shdr)
264+
dwarfexport_error("getshdr() failed: ", elf_errmsg(-1));
265+
dwarfexport_log("Section #", scn_index,
266+
": sh_name=", shdr.sh_name,
267+
", sh_type=", shdr.sh_type,
268+
", sh_flags=", shdr.sh_flags,
269+
", sh_addr=", shdr.sh_addr,
270+
", sh_offset=", shdr.sh_offset,
271+
", sh_size=", shdr.sh_size,
272+
", sh_link=", shdr.sh_link,
273+
", sh_info=", shdr.sh_info,
274+
", sh_addralign=", shdr.sh_addralign,
275+
", sh_entsize=", shdr.sh_entsize);
276+
}
277+
}
278+
246279
static void generate_copy_with_dbg_info(std::shared_ptr<DwarfGenInfo> info,
247280
const std::string &src,
248281
const std::string &dst) {
@@ -284,10 +317,10 @@ static void generate_copy_with_dbg_info(std::shared_ptr<DwarfGenInfo> info,
284317

285318
info->elf = elf_out;
286319

287-
/* Some compilers produce binaries with non-adjacent sections, so
288-
* we cannot use the automatic layout. Suppress it and use the exact
320+
/* Some compilers produce binaries with non-adjacent or overlapping sections,
321+
* so we cannot use the automatic layout. Suppress it and use the exact
289322
* layout from the input. */
290-
if (elf_flagelf(elf_out, ELF_C_SET, ELF_F_LAYOUT) == 0)
323+
if (elf_flagelf(elf_out, ELF_C_SET, ELF_F_LAYOUT | ELF_F_LAYOUT_OVERLAP) == 0)
291324
dwarfexport_error("elf_flagelf failed: ", elf_errmsg(-1));
292325

293326
if (gelf_getehdr(elf_out, &ehdr_out) != &ehdr_out)
@@ -346,8 +379,14 @@ static void generate_copy_with_dbg_info(std::shared_ptr<DwarfGenInfo> info,
346379
dwarfexport_error("gelf_update_shdr() failed: ", elf_errmsg(-1));
347380
}
348381

382+
dwarfexport_log("After copying the original sections:");
383+
log_elf(elf_out);
384+
349385
add_debug_section_data(info);
350386

387+
dwarfexport_log("After adding the debug sections:");
388+
log_elf(elf_out);
389+
351390
// Get the current last section (to fix section header and string table loc)
352391
auto last_scn = get_last_section(elf_out);
353392
GElf_Shdr last_shdr;
@@ -374,6 +413,9 @@ static void generate_copy_with_dbg_info(std::shared_ptr<DwarfGenInfo> info,
374413
if (gelf_update_ehdr(elf_out, &ehdr_out) == 0)
375414
dwarfexport_error("gelf_update_ehdr() failed: ", elf_errmsg(-1));
376415

416+
dwarfexport_log("After fixing various offsets:");
417+
log_elf(elf_out);
418+
377419
if (elf_update(elf_out, ELF_C_WRITE) < 0)
378420
dwarfexport_error("elf_update() failed: ", elf_errmsg(-1));
379421

0 commit comments

Comments
 (0)