#!/usr/bin/python3
'''
Copyright (c) Apple Inc. 2021
SPDX-License-Identifier: BSD-2-Clause-Patent

Example usage:
OvmfPkg/build.sh qemu -gdb tcp::9000
lldb -o "gdb-remote localhost:9000" -o "command script import efi_lldb.py"
'''

import optparse
import shlex
import subprocess
import uuid
import sys
import os
from pathlib import Path
from efi_debugging import EfiDevicePath, EfiConfigurationTable, EfiTpl
from efi_debugging import EfiHob, GuidNames, EfiStatusClass, EfiBootMode
from efi_debugging import PeTeImage, patch_ctypes

try:
    # Just try for LLDB in case PYTHONPATH is already correctly setup
    import lldb
except ImportError:
    try:
        env = os.environ.copy()
        env['LLDB_DEFAULT_PYTHON_VERSION'] = str(sys.version_info.major)
        lldb_python_path = subprocess.check_output(
            ["xcrun", "lldb", "-P"], env=env).decode("utf-8").strip()
        sys.path.append(lldb_python_path)
        import lldb
    except ValueError:
        print("Couldn't find LLDB.framework from lldb -P")
        print("PYTHONPATH should match the currently selected lldb")
        sys.exit(-1)


class LldbFileObject(object):
    '''
    Class that fakes out file object to abstract lldb from the generic code.
    For lldb this is memory so we don't have a concept of the end of the file.
    '''

    def __init__(self, process):
        # _exe_ctx is lldb.SBExecutionContext
        self._process = process
        self._offset = 0
        self._SBError = lldb.SBError()

    def tell(self):
        return self._offset

    def read(self, size=-1):
        if size == -1:
            # arbitrary default size
            size = 0x1000000

        data = self._process.ReadMemory(self._offset, size, self._SBError)
        if self._SBError.fail:
            raise MemoryError(
                f'lldb could not read memory 0x{size:x} '
                f' bytes from 0x{self._offset:08x}')
        else:
            return data

    def readable(self):
        return True

    def seek(self, offset, whence=0):
        if whence == 0:
            self._offset = offset
        elif whence == 1:
            self._offset += offset
        else:
            # whence == 2 is seek from end
            raise NotImplementedError

    def seekable(self):
        return True

    def write(self, data):
        result = self._process.WriteMemory(self._offset, data, self._SBError)
        if self._SBError.fail:
            raise MemoryError(
                f'lldb could not write memory to 0x{self._offset:08x}')
        return result

    def writable(self):
        return True

    def truncate(self, size=None):
        raise NotImplementedError

    def flush(self):
        raise NotImplementedError

    def fileno(self):
        raise NotImplementedError


class EfiSymbols:
    """
    Class to manage EFI Symbols
    You need to pass file, and exe_ctx to load symbols.
    You can print(EfiSymbols()) to see the currently loaded symbols
    """

    loaded = {}
    stride = None
    range = None
    verbose = False

    def __init__(self, target=None):
        if target:
            EfiSymbols.target = target
            EfiSymbols._file = LldbFileObject(target.process)

    @ classmethod
    def __str__(cls):
        return ''.join(f'{pecoff}\n' for (pecoff, _) in cls.loaded.values())

    @ classmethod
    def configure_search(cls, stride, range, verbose=False):
        cls.stride = stride
        cls.range = range
        cls.verbose = verbose

    @ classmethod
    def clear(cls):
        cls.loaded = {}

    @ classmethod
    def add_symbols_for_pecoff(cls, pecoff):
        '''Tell lldb the location of the .text and .data sections.'''

        if pecoff.LoadAddress in cls.loaded:
            return 'Already Loaded: '

        module = cls.target.AddModule(None, None, str(pecoff.CodeViewUuid))
        if not module:
            module = cls.target.AddModule(pecoff.CodeViewPdb,
                                          None,
                                          str(pecoff.CodeViewUuid))
        if module.IsValid():
            SBError = cls.target.SetModuleLoadAddress(
                module, pecoff.LoadAddress + pecoff.TeAdjust)
            if SBError.success:
                cls.loaded[pecoff.LoadAddress] = (pecoff, module)
                return ''

        return 'Symbols NOT FOUND: '

    @ classmethod
    def address_to_symbols(cls, address, reprobe=False):
        '''
        Given an address search backwards for a PE/COFF (or TE) header
        and load symbols. Return a status string.
        '''
        if not isinstance(address, int):
            address = int(address)

        pecoff, _ = cls.address_in_loaded_pecoff(address)
        if not reprobe and pecoff is not None:
            # skip the probe of the remote
            return f'{pecoff} is already loaded'

        pecoff = PeTeImage(cls._file, None)
        if pecoff.pcToPeCoff(address, cls.stride, cls.range):
            res = cls.add_symbols_for_pecoff(pecoff)
            return f'{res}{pecoff}'
        else:
            return f'0x{address:08x} not in a PE/COFF (or TE) image'

    @ classmethod
    def address_in_loaded_pecoff(cls, address):
        if not isinstance(address, int):
            address = int(address)

        for (pecoff, module) in cls.loaded.values():
            if (address >= pecoff.LoadAddress and
                    address <= pecoff.EndLoadAddress):

                return pecoff, module

        return None, None

    @ classmethod
    def unload_symbols(cls, address):
        pecoff, module = cls.address_in_loaded_pecoff(address)
        if module:
            name = str(module)
            cls.target.ClearModuleLoadAddress(module)
            cls.target.RemoveModule(module)
            del cls.loaded[pecoff.LoadAddress]
            return f'{name:s} was unloaded'
        return f'0x{address:x} was not in a loaded image'


def arg_to_address(frame, arg):
    ''' convert an lldb command arg into a memory address (addr_t)'''

    if arg is None:
        return None

    arg_str = arg if isinstance(arg, str) else str(arg)
    SBValue = frame.EvaluateExpression(arg_str)
    if SBValue.error.fail:
        return arg

    if (SBValue.TypeIsPointerType() or
            SBValue.value_type == lldb.eValueTypeRegister or
            SBValue.value_type == lldb.eValueTypeRegisterSet or
            SBValue.value_type == lldb.eValueTypeConstResult):
        try:
            addr = SBValue.GetValueAsAddress()
        except ValueError:
            addr = SBValue.unsigned
    else:
        try:
            addr = SBValue.address_of.GetValueAsAddress()
        except ValueError:
            addr = SBValue.address_of.unsigned

    return addr


def arg_to_data(frame, arg):
    ''' convert an lldb command arg into a data vale (uint32_t/uint64_t)'''
    if not isinstance(arg, str):
        arg_str = str(str)

    SBValue = frame.EvaluateExpression(arg_str)
    return SBValue.unsigned


class EfiDevicePathCommand:

    def create_options(self):
        ''' standard lldb command help/options parser'''
        usage = "usage: %prog [options]"
        description = '''Command that can EFI Config Tables
'''

        # Pass add_help_option = False, since this keeps the command in line
        # with lldb commands, and we wire up "help command" to work by
        # providing the long & short help methods below.
        self.parser = optparse.OptionParser(
            description=description,
            prog='devicepath',
            usage=usage,
            add_help_option=False)

        self.parser.add_option(
            '-v',
            '--verbose',
            action='store_true',
            dest='verbose',
            help='hex dump extra data',
            default=False)

        self.parser.add_option(
            '-n',
            '--node',
            action='store_true',
            dest='node',
            help='dump a single device path node',
            default=False)

        self.parser.add_option(
            '-h',
            '--help',
            action='store_true',
            dest='help',
            help='Show help for the command',
            default=False)

    def get_short_help(self):
        '''standard lldb function method'''
        return "Display EFI Tables"

    def get_long_help(self):
        '''standard lldb function method'''
        return self.help_string

    def __init__(self, debugger, internal_dict):
        '''standard lldb function method'''
        self.create_options()
        self.help_string = self.parser.format_help()

    def __call__(self, debugger, command, exe_ctx, result):
        '''standard lldb function method'''
        # Use the Shell Lexer to properly parse up command options just like a
        # shell would
        command_args = shlex.split(command)

        try:
            (options, args) = self.parser.parse_args(command_args)
            dev_list = []
            for arg in args:
                dev_list.append(arg_to_address(exe_ctx.frame, arg))
        except ValueError:
            # if you don't handle exceptions, passing an incorrect argument
            # to the OptionParser will cause LLDB to exit (courtesy of
            # OptParse dealing with argument errors by throwing SystemExit)
            result.SetError("option parsing failed")
            return

        if options.help:
            self.parser.print_help()
            return

        file = LldbFileObject(exe_ctx.process)

        for dev_addr in dev_list:
            if options.node:
                print(EfiDevicePath(file).device_path_node_str(
                    dev_addr, options.verbose))
            else:
                device_path = EfiDevicePath(file, dev_addr, options.verbose)
                if device_path.valid():
                    print(device_path)


class EfiHobCommand:
    def create_options(self):
        ''' standard lldb command help/options parser'''
        usage = "usage: %prog [options]"
        description = '''Command that can EFI dump EFI HOBs'''

        # Pass add_help_option = False, since this keeps the command in line
        # with lldb commands, and we wire up "help command" to work by
        # providing the long & short help methods below.
        self.parser = optparse.OptionParser(
            description=description,
            prog='table',
            usage=usage,
            add_help_option=False)

        self.parser.add_option(
            '-a',
            '--address',
            type="int",
            dest='address',
            help='Parse HOBs from address',
            default=None)

        self.parser.add_option(
            '-t',
            '--type',
            type="int",
            dest='type',
            help='Only dump HOBS of his type',
            default=None)

        self.parser.add_option(
            '-v',
            '--verbose',
            action='store_true',
            dest='verbose',
            help='hex dump extra data',
            default=False)

        self.parser.add_option(
            '-h',
            '--help',
            action='store_true',
            dest='help',
            help='Show help for the command',
            default=False)

    def get_short_help(self):
        '''standard lldb function method'''
        return "Display EFI Hobs"

    def get_long_help(self):
        '''standard lldb function method'''
        return self.help_string

    def __init__(self, debugger, internal_dict):
        '''standard lldb function method'''
        self.create_options()
        self.help_string = self.parser.format_help()

    def __call__(self, debugger, command, exe_ctx, result):
        '''standard lldb function method'''
        # Use the Shell Lexer to properly parse up command options just like a
        # shell would
        command_args = shlex.split(command)

        try:
            (options, _) = self.parser.parse_args(command_args)
        except ValueError:
            # if you don't handle exceptions, passing an incorrect argument
            # to the OptionParser will cause LLDB to exit (courtesy of
            # OptParse dealing with argument errors by throwing SystemExit)
            result.SetError("option parsing failed")
            return

        if options.help:
            self.parser.print_help()
            return

        address = arg_to_address(exe_ctx.frame, options.address)

        file = LldbFileObject(exe_ctx.process)
        hob = EfiHob(file, address, options.verbose).get_hob_by_type(
            options.type)
        print(hob)


class EfiTableCommand:

    def create_options(self):
        ''' standard lldb command help/options parser'''
        usage = "usage: %prog [options]"
        description = '''Command that can display EFI Config Tables
'''

        # Pass add_help_option = False, since this keeps the command in line
        # with lldb commands, and we wire up "help command" to work by
        # providing the long & short help methods below.
        self.parser = optparse.OptionParser(
            description=description,
            prog='table',
            usage=usage,
            add_help_option=False)

        self.parser.add_option(
            '-h',
            '--help',
            action='store_true',
            dest='help',
            help='Show help for the command',
            default=False)

    def get_short_help(self):
        '''standard lldb function method'''
        return "Display EFI Tables"

    def get_long_help(self):
        '''standard lldb function method'''
        return self.help_string

    def __init__(self, debugger, internal_dict):
        '''standard lldb function method'''
        self.create_options()
        self.help_string = self.parser.format_help()

    def __call__(self, debugger, command, exe_ctx, result):
        '''standard lldb function method'''
        # Use the Shell Lexer to properly parse up command options just like a
        # shell would
        command_args = shlex.split(command)

        try:
            (options, _) = self.parser.parse_args(command_args)
        except ValueError:
            # if you don't handle exceptions, passing an incorrect argument
            # to the OptionParser will cause LLDB to exit (courtesy of
            # OptParse dealing with argument errors by throwing SystemExit)
            result.SetError("option parsing failed")
            return

        if options.help:
            self.parser.print_help()
            return

        gST = exe_ctx.target.FindFirstGlobalVariable('gST')
        if gST.error.fail:
            print('Error: This command requires symbols for gST to be loaded')
            return

        file = LldbFileObject(exe_ctx.process)
        table = EfiConfigurationTable(file, gST.unsigned)
        if table:
            print(table, '\n')


class EfiGuidCommand:

    def create_options(self):
        ''' standard lldb command help/options parser'''
        usage = "usage: %prog [options]"
        description = '''
            Command that can display all EFI GUID's or give info on a
            specific GUID's
            '''
        self.parser = optparse.OptionParser(
            description=description,
            prog='guid',
            usage=usage,
            add_help_option=False)

        self.parser.add_option(
            '-n',
            '--new',
            action='store_true',
            dest='new',
            help='Generate a new GUID',
            default=False)

        self.parser.add_option(
            '-v',
            '--verbose',
            action='store_true',
            dest='verbose',
            help='Also display GUID C structure values',
            default=False)

        self.parser.add_option(
            '-h',
            '--help',
            action='store_true',
            dest='help',
            help='Show help for the command',
            default=False)

    def get_short_help(self):
        '''standard lldb function method'''
        return "Display EFI GUID's"

    def get_long_help(self):
        '''standard lldb function method'''
        return self.help_string

    def __init__(self, debugger, internal_dict):
        '''standard lldb function method'''
        self.create_options()
        self.help_string = self.parser.format_help()

    def __call__(self, debugger, command, exe_ctx, result):
        '''standard lldb function method'''
        # Use the Shell Lexer to properly parse up command options just like a
        # shell would
        command_args = shlex.split(command)

        try:
            (options, args) = self.parser.parse_args(command_args)
            if len(args) >= 1:
                # guid { 0x414e6bdd, 0xe47b, 0x47cc,
                #      { 0xb2, 0x44, 0xbb, 0x61, 0x02, 0x0c,0xf5, 0x16 }}
                # this generates multiple args
                arg = ' '.join(args)
        except ValueError:
            # if you don't handle exceptions, passing an incorrect argument
            # to the OptionParser will cause LLDB to exit (courtesy of
            # OptParse dealing with argument errors by throwing SystemExit)
            result.SetError("option parsing failed")
            return

        if options.help:
            self.parser.print_help()
            return

        if options.new:
            guid = uuid.uuid4()
            print(str(guid).upper())
            print(GuidNames.to_c_guid(guid))
            return

        if len(args) > 0:
            if GuidNames.is_guid_str(arg):
                # guid 05AD34BA-6F02-4214-952E-4DA0398E2BB9
                key = arg.lower()
                name = GuidNames.to_name(key)
            elif GuidNames.is_c_guid(arg):
                # guid { 0x414e6bdd, 0xe47b, 0x47cc,
                #      { 0xb2, 0x44, 0xbb, 0x61, 0x02, 0x0c,0xf5, 0x16 }}
                key = GuidNames.from_c_guid(arg)
                name = GuidNames.to_name(key)
            else:
                # guid gEfiDxeServicesTableGuid
                name = arg
                try:
                    key = GuidNames.to_guid(name)
                    name = GuidNames.to_name(key)
                except ValueError:
                    return

            extra = f'{GuidNames.to_c_guid(key)}: ' if options.verbose else ''
            print(f'{key}: {extra}{name}')

        else:
            for key, value in GuidNames._dict_.items():
                if options.verbose:
                    extra = f'{GuidNames.to_c_guid(key)}: '
                else:
                    extra = ''
                print(f'{key}: {extra}{value}')


class EfiSymbolicateCommand(object):
    '''Class to abstract an lldb command'''

    def create_options(self):
        ''' standard lldb command help/options parser'''
        usage = "usage: %prog [options]"
        description = '''Command that can load EFI PE/COFF and TE image
        symbols. If you are having trouble in PEI try adding --pei.
        '''

        # Pass add_help_option = False, since this keeps the command in line
        # with lldb commands, and we wire up "help command" to work by
        # providing the long & short help methods below.
        self.parser = optparse.OptionParser(
            description=description,
            prog='efi_symbols',
            usage=usage,
            add_help_option=False)

        self.parser.add_option(
            '-a',
            '--address',
            type="int",
            dest='address',
            help='Load symbols for image at address',
            default=None)

        self.parser.add_option(
            '-f',
            '--frame',
            action='store_true',
            dest='frame',
            help='Load symbols for current stack frame',
            default=False)

        self.parser.add_option(
            '-p',
            '--pc',
            action='store_true',
            dest='pc',
            help='Load symbols for pc',
            default=False)

        self.parser.add_option(
            '--pei',
            action='store_true',
            dest='pei',
            help='Load symbols for PEI (searches every 4 bytes)',
            default=False)

        self.parser.add_option(
            '-e',
            '--extended',
            action='store_true',
            dest='extended',
            help='Try to load all symbols based on config tables.',
            default=False)

        self.parser.add_option(
            '-r',
            '--range',
            type="long",
            dest='range',
            help='How far to search backward for start of PE/COFF Image',
            default=None)

        self.parser.add_option(
            '-s',
            '--stride',
            type="long",
            dest='stride',
            help='Boundary to search for PE/COFF header',
            default=None)

        self.parser.add_option(
            '-t',
            '--thread',
            action='store_true',
            dest='thread',
            help='Load symbols for the frames of all threads',
            default=False)

        self.parser.add_option(
            '-h',
            '--help',
            action='store_true',
            dest='help',
            help='Show help for the command',
            default=False)

    def get_short_help(self):
        '''standard lldb function method'''
        return (
            "Load symbols based on an address that is part of"
            " a PE/COFF EFI image.")

    def get_long_help(self):
        '''standard lldb function method'''
        return self.help_string

    def __init__(self, debugger, unused):
        '''standard lldb function method'''
        self.create_options()
        self.help_string = self.parser.format_help()

    def lldb_print(self, lldb_str):
        # capture command out like an lldb command
        self.result.PutCString(lldb_str)
        # flush the output right away
        self.result.SetImmediateOutputFile(
            self.exe_ctx.target.debugger.GetOutputFile())

    def __call__(self, debugger, command, exe_ctx, result):
        '''standard lldb function method'''
        # Use the Shell Lexer to properly parse up command options just like a
        # shell would
        command_args = shlex.split(command)

        try:
            (options, _) = self.parser.parse_args(command_args)
        except ValueError:
            # if you don't handle exceptions, passing an incorrect argument
            # to the OptionParser will cause LLDB to exit (courtesy of
            # OptParse dealing with argument errors by throwing SystemExit)
            result.SetError("option parsing failed")
            return

        if options.help:
            self.parser.print_help()
            return

        file = LldbFileObject(exe_ctx.process)
        efi_symbols = EfiSymbols(exe_ctx.target)
        self.result = result
        self.exe_ctx = exe_ctx

        if options.pei:
            # XIP code ends up on a 4 byte boundary.
            options.stride = 4
            options.range = 0x100000
        efi_symbols.configure_search(options.stride, options.range)

        if not options.pc and options.address is None:
            # default to
            options.frame = True

        if options.frame:
            if not exe_ctx.frame.IsValid():
                result.SetError("invalid frame")
                return

            threads = exe_ctx.process.threads if options.thread else [
                exe_ctx.thread]

            for thread in threads:
                for frame in thread:
                    res = efi_symbols.address_to_symbols(frame.pc)
                    self.lldb_print(res)

        else:
            if options.address is not None:
                address = options.address
            elif options.pc:
                try:
                    address = exe_ctx.thread.GetSelectedFrame().pc
                except ValueError:
                    result.SetError("invalid pc")
                    return
            else:
                address = 0

            res = efi_symbols.address_to_symbols(address.pc)
            print(res)

        if options.extended:

            gST = exe_ctx.target.FindFirstGlobalVariable('gST')
            if gST.error.fail:
                print('Error: This command requires symbols to be loaded')
            else:
                table = EfiConfigurationTable(file, gST.unsigned)
                for address, _ in table.DebugImageInfo():
                    res = efi_symbols.address_to_symbols(address)
                    self.lldb_print(res)

        # keep trying module file names until we find a GUID xref file
        for m in exe_ctx.target.modules:
            if GuidNames.add_build_guid_file(str(m.file)):
                break


def CHAR16_TypeSummary(valobj, internal_dict):
    '''
    Display CHAR16 as a String in the debugger.
    Note: utf-8 is returned as that is the value for the debugger.
    '''
    SBError = lldb.SBError()
    Str = ''
    if valobj.TypeIsPointerType():
        if valobj.GetValueAsUnsigned() == 0:
            return "NULL"

        # CHAR16 *   max string size 1024
        for i in range(1024):
            Char = valobj.GetPointeeData(i, 1).GetUnsignedInt16(SBError, 0)
            if SBError.fail or Char == 0:
                break
            Str += chr(Char)
        return 'L"' + Str + '"'

    if valobj.num_children == 0:
        # CHAR16
        return "L'" + chr(valobj.unsigned) + "'"

    else:
        # CHAR16 []
        for i in range(valobj.num_children):
            Char = valobj.GetChildAtIndex(i).data.GetUnsignedInt16(SBError, 0)
            if Char == 0:
                break
            Str += chr(Char)
        return 'L"' + Str + '"'

    return Str


def CHAR8_TypeSummary(valobj, internal_dict):
    '''
    Display CHAR8 as a String in the debugger.
    Note: utf-8 is returned as that is the value for the debugger.
    '''
    SBError = lldb.SBError()
    Str = ''
    if valobj.TypeIsPointerType():
        if valobj.GetValueAsUnsigned() == 0:
            return "NULL"

        # CHAR8 *   max string size 1024
        for i in range(1024):
            Char = valobj.GetPointeeData(i, 1).GetUnsignedInt8(SBError, 0)
            if SBError.fail or Char == 0:
                break
            Str += chr(Char)
        Str = '"' + Str + '"'
        return Str

    if valobj.num_children == 0:
        # CHAR8
        return "'" + chr(valobj.unsigned) + "'"
    else:
        # CHAR8 []
        for i in range(valobj.num_children):
            Char = valobj.GetChildAtIndex(i).data.GetUnsignedInt8(SBError, 0)
            if SBError.fail or Char == 0:
                break
            Str += chr(Char)
        return '"' + Str + '"'

    return Str


def EFI_STATUS_TypeSummary(valobj, internal_dict):
    if valobj.TypeIsPointerType():
        return ''
    return str(EfiStatusClass(valobj.unsigned))


def EFI_TPL_TypeSummary(valobj, internal_dict):
    if valobj.TypeIsPointerType():
        return ''
    return str(EfiTpl(valobj.unsigned))


def EFI_GUID_TypeSummary(valobj, internal_dict):
    if valobj.TypeIsPointerType():
        return ''
    return str(GuidNames(bytes(valobj.data.uint8)))


def EFI_BOOT_MODE_TypeSummary(valobj, internal_dict):
    if valobj.TypeIsPointerType():
        return ''
    '''Return #define name for EFI_BOOT_MODE'''
    return str(EfiBootMode(valobj.unsigned))


def lldb_type_formaters(debugger, mod_name):
    '''Teach lldb about EFI types'''

    category = debugger.GetDefaultCategory()
    FormatBool = lldb.SBTypeFormat(lldb.eFormatBoolean)
    category.AddTypeFormat(lldb.SBTypeNameSpecifier("BOOLEAN"), FormatBool)

    FormatHex = lldb.SBTypeFormat(lldb.eFormatHex)
    category.AddTypeFormat(lldb.SBTypeNameSpecifier("UINT64"), FormatHex)
    category.AddTypeFormat(lldb.SBTypeNameSpecifier("INT64"), FormatHex)
    category.AddTypeFormat(lldb.SBTypeNameSpecifier("UINT32"), FormatHex)
    category.AddTypeFormat(lldb.SBTypeNameSpecifier("INT32"), FormatHex)
    category.AddTypeFormat(lldb.SBTypeNameSpecifier("UINT16"), FormatHex)
    category.AddTypeFormat(lldb.SBTypeNameSpecifier("INT16"), FormatHex)
    category.AddTypeFormat(lldb.SBTypeNameSpecifier("UINT8"), FormatHex)
    category.AddTypeFormat(lldb.SBTypeNameSpecifier("INT8"), FormatHex)
    category.AddTypeFormat(lldb.SBTypeNameSpecifier("UINTN"), FormatHex)
    category.AddTypeFormat(lldb.SBTypeNameSpecifier("INTN"), FormatHex)
    category.AddTypeFormat(lldb.SBTypeNameSpecifier("CHAR8"), FormatHex)
    category.AddTypeFormat(lldb.SBTypeNameSpecifier("CHAR16"), FormatHex)
    category.AddTypeFormat(lldb.SBTypeNameSpecifier(
        "EFI_PHYSICAL_ADDRESS"), FormatHex)
    category.AddTypeFormat(lldb.SBTypeNameSpecifier(
        "PHYSICAL_ADDRESS"), FormatHex)
    category.AddTypeFormat(lldb.SBTypeNameSpecifier("EFI_LBA"), FormatHex)
    category.AddTypeFormat(
        lldb.SBTypeNameSpecifier("EFI_BOOT_MODE"), FormatHex)
    category.AddTypeFormat(lldb.SBTypeNameSpecifier(
        "EFI_FV_FILETYPE"), FormatHex)

    #
    # Smart type printing for EFI
    #

    debugger.HandleCommand(
        f'type summary add GUID - -python-function '
        f'{mod_name}.EFI_GUID_TypeSummary')
    debugger.HandleCommand(
        f'type summary add EFI_GUID --python-function '
        f'{mod_name}.EFI_GUID_TypeSummary')
    debugger.HandleCommand(
        f'type summary add EFI_STATUS --python-function '
        f'{mod_name}.EFI_STATUS_TypeSummary')
    debugger.HandleCommand(
        f'type summary add EFI_TPL - -python-function '
        f'{mod_name}.EFI_TPL_TypeSummary')
    debugger.HandleCommand(
        f'type summary add EFI_BOOT_MODE --python-function '
        f'{mod_name}.EFI_BOOT_MODE_TypeSummary')

    debugger.HandleCommand(
        f'type summary add CHAR16 --python-function '
        f'{mod_name}.CHAR16_TypeSummary')

    # W605 this is the correct escape sequence for the lldb command
    debugger.HandleCommand(
        f'type summary add --regex "CHAR16 \[[0-9]+\]" '  # noqa: W605
        f'--python-function {mod_name}.CHAR16_TypeSummary')

    debugger.HandleCommand(
        f'type summary add CHAR8 --python-function '
        f'{mod_name}.CHAR8_TypeSummary')

    # W605 this is the correct escape sequence for the lldb command
    debugger.HandleCommand(
        f'type summary add --regex "CHAR8 \[[0-9]+\]"  '  # noqa: W605
        f'--python-function {mod_name}.CHAR8_TypeSummary')


class LldbWorkaround:
    needed = True

    @classmethod
    def activate(cls):
        if cls.needed:
            lldb.debugger.HandleCommand("process handle SIGALRM -n false")
            cls.needed = False


def LoadEmulatorEfiSymbols(frame, bp_loc, internal_dict):
    #
    # This is an lldb breakpoint script, and assumes the breakpoint is on a
    # function with the same prototype as SecGdbScriptBreak(). The
    # argument names are important as lldb looks them up.
    #
    # VOID
    # SecGdbScriptBreak (
    #   char                *FileName,
    #   int                 FileNameLength,
    #   long unsigned int   LoadAddress,
    #   int                 AddSymbolFlag
    #   )
    # {
    #   return;
    # }
    #
    # When the emulator loads a PE/COFF image, it calls the stub function with
    # the filename of the symbol file, the length of the FileName, the
    # load address and a flag to indicate if this is a load or unload operation
    #
    LldbWorkaround().activate()

    symbols = EfiSymbols(frame.thread.process.target)
    LoadAddress = frame.FindVariable("LoadAddress").unsigned
    if frame.FindVariable("AddSymbolFlag").unsigned == 1:
        res = symbols.address_to_symbols(LoadAddress)
    else:
        res = symbols.unload_symbols(LoadAddress)
    print(res)

    # make breakpoint command continue
    return False


def __lldb_init_module(debugger, internal_dict):
    '''
    This initializer is being run from LLDB in the embedded command interpreter
    '''

    mod_name = Path(__file__).stem
    lldb_type_formaters(debugger, mod_name)

    # Add any commands contained in this module to LLDB
    debugger.HandleCommand(
        f'command script add -c {mod_name}.EfiSymbolicateCommand efi_symbols')
    debugger.HandleCommand(
        f'command script add -c {mod_name}.EfiGuidCommand guid')
    debugger.HandleCommand(
        f'command script add -c {mod_name}.EfiTableCommand table')
    debugger.HandleCommand(
        f'command script add -c {mod_name}.EfiHobCommand hob')
    debugger.HandleCommand(
        f'command script add -c {mod_name}.EfiDevicePathCommand devicepath')

    print('EFI specific commands have been installed.')

    # patch the ctypes c_void_p values if the debuggers OS and EFI have
    # different ideas on the size of the debug.
    try:
        patch_ctypes(debugger.GetSelectedTarget().addr_size)
    except ValueError:
        # incase the script is imported and the debugger has not target
        # defaults to sizeof(UINTN) == sizeof(UINT64)
        patch_ctypes()

    try:
        target = debugger.GetSelectedTarget()
        if target.FindFunctions('SecGdbScriptBreak').symbols:
            breakpoint = target.BreakpointCreateByName('SecGdbScriptBreak')
            # Set the emulator breakpoints, if we are in the emulator
            cmd = 'breakpoint command add -s python -F '
            cmd += f'efi_lldb.LoadEmulatorEfiSymbols {breakpoint.GetID()}'
            debugger.HandleCommand(cmd)
            print('Type r to run emulator.')
        else:
            raise ValueError("No Emulator Symbols")

    except ValueError:
        # default action when the script is imported
        debugger.HandleCommand("efi_symbols --frame --extended")
        debugger.HandleCommand("register read")
        debugger.HandleCommand("bt all")


if __name__ == '__main__':
    pass
