Skip to content

Instantly share code, notes, and snippets.

@julian-klode
Last active June 24, 2024 13:47
Show Gist options
  • Save julian-klode/85e55553f85c410a1b856a93dce77208 to your computer and use it in GitHub Desktop.
Save julian-klode/85e55553f85c410a1b856a93dce77208 to your computer and use it in GitHub Desktop.
#!/usr/bin/python3
#
# Copyright (C) 2024 Canonical Ltd
#
# SPDX-License-Identifier: GPL-3.0
import os
import sys
from elftools.elf.elffile import ELFFile
def dump_producers(elffile: ELFFile) -> bool:
res = False
dwarfinfo = elffile.get_dwarf_info(follow_links=True)
for CU in dwarfinfo.iter_CUs():
die = CU.get_top_DIE()
if "DW_AT_producer" not in die.attributes:
continue
print(
filename,
"unit",
die.attributes["DW_AT_name"].value.decode("utf-8"),
"produced-by",
die.attributes["DW_AT_producer"].value.decode("utf-8"),
)
res = True
return res
def process_file(filename: str) -> None:
elffile = ELFFile.load_from_path(filename)
print(filename, "elf")
self_debug = dump_producers(elffile)
for sect in elffile.iter_sections():
if sect.name != ".note.gnu.build-id":
continue
for note in sect.iter_notes():
build_id = note["n_desc"]
debug_file = f"/usr/lib/debug/.build-id/{build_id[:2]}/{build_id[2:]}.debug"
if not os.path.exists(debug_file):
if not self_debug:
print(filename, "no-dbgsym", build_id)
continue
if debug_file != filename:
dump_producers(ELFFile.load_from_path(debug_file))
legacy_debug = "/usr/lib/debug" + os.path.realpath(filename)
if os.path.exists(legacy_debug):
dump_producers(ELFFile.load_from_path(legacy_debug))
if __name__ == "__main__":
for filename in sys.argv[1:]:
process_file(filename)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment