Add command line argument parser

Signed-off-by: Juraj Oravec <jurajoravec@mailo.com>
This commit is contained in:
Juraj Oravec 2024-05-11 14:40:38 +02:00
parent 191487fc50
commit b1256f9072
Signed by: SGOrava
GPG Key ID: 13660A3F1D9F093B

48
main.py
View File

@ -1,15 +1,18 @@
#!/bin/python #!/bin/python
import os
import sys import sys
import math import math
import argparse
from bear import formats from bear import formats
from elftools.dwarf.locationlists import LocationParser, LocationExpr from elftools.dwarf.locationlists import LocationParser, LocationExpr
from elftools.dwarf.dwarf_expr import DWARFExprParser, DWARFExprOp, DW_OP_opcode2name from elftools.dwarf.dwarf_expr import DWARFExprParser, DWARFExprOp, DW_OP_opcode2name
from bear.dwarfone import DWARFExprParserV1 from bear.dwarfone import DWARFExprParserV1
SCRIPT_VERSION = '0.1.0'
configuration = { configuration = {
"include_file_name": False, 'include_file_name': False,
} }
@ -43,7 +46,7 @@ def load_children(parent_die):
# QMessageBox(QMessageBox.Icon.Warning, "DWARF Explorer", # QMessageBox(QMessageBox.Icon.Warning, "DWARF Explorer",
# "This executable file is corrupt or incompatible with the current version of DWARF Explorer. Please consider creating a new issue at https://github.com/sevaa/dwex/, and share this file with the tech support.", # "This executable file is corrupt or incompatible with the current version of DWARF Explorer. Please consider creating a new issue at https://github.com/sevaa/dwex/, and share this file with the tech support.",
# QMessageBox.StandardButton.Ok, QApplication.instance().win).show() # QMessageBox.StandardButton.Ok, QApplication.instance().win).show()
print("This executable file is corrupt or incompatible with the current version of Bear.") print("This executable file is corrupt or incompatible.")
parent_die._children = [] parent_die._children = []
@ -69,7 +72,8 @@ class Bear():
cu._lineprogram = None cu._lineprogram = None
cu._exprparser = None cu._exprparser = None
return cu return cu
di._unsorted_CUs = [decorate_cu(cu, i) for (i, cu) in enumerate(di.iter_CUs())] # We'll need them first thing, might as well load here # We'll need them first thing, might as well load here
di._unsorted_CUs = [decorate_cu(cu, i) for (i, cu) in enumerate(di.iter_CUs())]
if not len(di._unsorted_CUs): if not len(di._unsorted_CUs):
return None # Weird, but saw it once - debug sections present, but no CUs return None # Weird, but saw it once - debug sections present, but no CUs
# For quick CU search by offset within the info section, regardless of sorting # For quick CU search by offset within the info section, regardless of sorting
@ -157,7 +161,8 @@ class Bear():
if die_type.tag == 'DW_TAG_base_type': if die_type.tag == 'DW_TAG_base_type':
real_type_name = safe_DIE_name(die_type, '?') real_type_name = safe_DIE_name(die_type, '?')
if real_type_name != '?' and real_type_name != entry['type']: if real_type_name != '?' and real_type_name != entry['type']:
entry['type'] = '{name} ({real})'.format(name=entry['type'], real=safe_DIE_name(die_type, '?')) entry['type'] = '{name} ({real})'.format(name=entry['type'],
real=safe_DIE_name(die_type, '?'))
elif die_type.tag == "DW_TAG_structure_type": elif die_type.tag == "DW_TAG_structure_type":
load_children(die_type) load_children(die_type)
child_dies = [] child_dies = []
@ -214,14 +219,16 @@ class Bear():
for CU in self.myVariables: for CU in self.myVariables:
for child in CU['children']: for child in CU['children']:
if configuration["include_file_name"]: if configuration["include_file_name"]:
self.pettanko(child, CU['name']) self.pettanko(child, CU['name'], ":")
else: else:
self.pettanko(child) self.pettanko(child)
def pettanko(self, entry : dict, a_parent_name : str = ""): def pettanko(self, entry : dict, a_parent_name : str = '', separator : str = '.'):
flat_entry = dict() flat_entry = dict()
if a_parent_name: if a_parent_name:
flat_entry['name'] = '{0}.{1}'.format(a_parent_name, entry['name']) flat_entry['name'] = '{parent}{separator}{child}'.format(parent=a_parent_name,
separator=separator,
child=entry['name'])
else: else:
flat_entry['name'] = entry['name'] flat_entry['name'] = entry['name']
@ -245,7 +252,7 @@ class Bear():
if 'number_of_elements' in entry: if 'number_of_elements' in entry:
for index in range(0, entry['number_of_elements']): for index in range(0, entry['number_of_elements']):
kid = flat_entry.copy() kid = flat_entry.copy()
kid['name'] = '{0}[{1}]'.format(flat_entry['name'], index) kid['name'] = '{name}[{index}]'.format(name=flat_entry['name'], index=index)
kid['address'] = hex(int(flat_entry['address'], 16) + entry['size_byte'] * index) kid['address'] = hex(int(flat_entry['address'], 16) + entry['size_byte'] * index)
self.pettanko(kid) self.pettanko(kid)
@ -258,7 +265,8 @@ class Bear():
def pretty_print(self): def pretty_print(self):
for entry in self.flat_list: for entry in self.flat_list:
print('{address}\t{variable_name}'.format(address=entry['address'], variable_name=entry['name'])) print('{address}\t{variable_name}'.format(address=entry['address'],
variable_name=entry['name']))
def parse_location(self, die, attr): def parse_location(self, die, attr):
di = die.dwarfinfo di = die.dwarfinfo
@ -287,7 +295,27 @@ def main():
from bear.patch import monkeypatch from bear.patch import monkeypatch
monkeypatch() monkeypatch()
bear = Bear("/home/juraj/projects/Playground_C/build/playground_c") parser = argparse.ArgumentParser(
description='Expands symbols (global variables) types.',
epilog='Data displayed by this script are informative only!'
)
parser.add_argument('elf_file', metavar='file', type=str, nargs='?',
help='ELF file to try to extract symbols')
parser.add_argument('--include-file-name', dest='include_file_name', action='store_true',
help='Display filename at the beginning')
parser.add_argument('--version', action='version',
version='%(prog)s {version}'.format(version=SCRIPT_VERSION))
args = parser.parse_args()
from pprint import pprint
configuration['include_file_name'] = args.include_file_name
if not os.path.exists(args.elf_file):
eprint('File {elf_file} does not exist!'.format(elf_file=args.elf_file))
exit(1)
bear = Bear(args.elf_file)
bear.flatten_type() bear.flatten_type()
bear.pretty_print() bear.pretty_print()