Update the breakpoint feature
[clinton/Virtual-Jaguar-Rx.git] / src / debugger / ELFManager.cpp
index 7f3857f..d180138 100644 (file)
@@ -4,22 +4,30 @@
 // by Jean-Paul Mari
 //
 // JPM = Jean-Paul Mari <djipi.mari@gmail.com>
+//  RG = Richard Goedeken
 //
 // WHO  WHEN        WHAT
 // ---  ----------  ------------------------------------------------------------
-// JPM  12/01/2016  Created this file
-// JPM  12/01/2016  ELF format support
-// JPM  13/07/2017  ELF DWARF format support
+// JPM   Jan./2016  Created this file and added ELF format support
+// JPM  07/13/2017  ELF DWARF format support improvement
+// JPM  10/20/2018  Added function name support from ELF structure
+// JPM  03/13/2020  Added ELF & DWARF .debug* types
+//  RG   Jan./2021  Linux build fixes
 //
 
 #include <stdlib.h>
 #include <string.h>
-#include "libelf/libelf.h"
-#include "libelf/gelf.h"
+#include <sys/types.h>
+#include <sys/stat.h>
+#include "libelf.h"
+#include "gelf.h"
 #include "libdwarf.h"
 #include "log.h"
 #include "ELFManager.h"
-#include "DwarfManager.h"
+#include "DWARFManager.h"
+
+
+//#define LOG_SUPPORT                                  // Support log
 
 
 typedef struct {
@@ -45,18 +53,23 @@ ELFSectionType      ELFTabSectionType[] =   {
        { ".data", ELF_data_TYPE },
        { ".bss", ELF_bss_TYPE },
        { ".heap", ELF_heap_TYPE },
+       { ".debug", ELF_debug_TYPE      },
+       { ".comment", ELF_comment_TYPE },
+       { ".shstrtab", ELF_shstrtab_TYPE },
+       { ".symtab", ELF_symtab_TYPE },
+       { ".strtab", ELF_strtab_TYPE },
+       { ".debug_abbrev", ELF_debug_abbrev_TYPE },
        { ".debug_aranges", ELF_debug_aranges_TYPE },
+       { ".debug_frame", ELF_debug_frame_TYPE },
        { ".debug_info", ELF_debug_info_TYPE },
-       { ".debug_abbrev", ELF_debug_abbrev_TYPE },
        { ".debug_line", ELF_debug_line_TYPE },
-       { ".debug_frame", ELF_debug_frame_TYPE },
-       { ".debug_str", ELF_debug_str_TYPE },
        { ".debug_loc", ELF_debug_loc_TYPE },
+       { ".debug_macinfo", ELF_debug_macinfo_TYPE },
+       { ".debug_pubnames", ELF_debug_pubnames_TYPE },
+       { ".debug_pubtypes", ELF_debug_pubtypes_TYPE },
        { ".debug_ranges", ELF_debug_ranges_TYPE },
-       { ".comment", ELF_comment_TYPE },
-       { ".shstrtab", ELF_shstrtab_TYPE },
-       { ".symtab", ELF_symtab_TYPE },
-       { ".strtab", ELF_strtab_TYPE }
+       { ".debug_str", ELF_debug_str_TYPE },
+       { ".debug_types", ELF_debug_types_TYPE }
 };
 
 
@@ -136,9 +149,9 @@ void        ELFManager_Init(void)
 
 
 // ELF manager Dwarf Initialisation
-bool   ELFManager_DwarfInit(Elf *PtrElfMem)
+bool   ELFManager_DwarfInit(Elf *PtrElfMem, struct stat FileElfInfo)
 {
-       return (ElfDwarf = (DWARFManager_ElfInit(PtrElfMem) == DW_DLV_OK) ? true : false);
+       return (ElfDwarf = (DWARFManager_ElfInit(PtrElfMem, FileElfInfo) == DW_DLV_OK) ? true : false);
 }
 
 
@@ -218,7 +231,7 @@ size_t ELFManager_GetAdrFromSymbolName(char *SymbolName)
        size_t Adr = 0;
        GElf_Sym *PtrST, ST;
 
-       if (ELFtab != NULL)
+       if (ELFtab && SymbolName)
        {
                for (size_t i = 0; i < NbELFtabStruct; i++)
                {
@@ -241,6 +254,39 @@ size_t ELFManager_GetAdrFromSymbolName(char *SymbolName)
 }
 
 
+// Get function name from his address
+// Return NULL if function name is not found
+char *ELFManager_GetFunctionName(size_t Adr)
+{
+       char *SymbolName = NULL;
+       GElf_Sym *PtrST, ST;
+
+       if (ELFtab != NULL)
+       {
+               for (size_t i = 0; i < NbELFtabStruct; i++)
+               {
+                       if ((ELFtab[i]->Type == ELF_symtab_TYPE) && ((ELFtab[i]->PtrDataTab) != NULL))
+                       {
+                               int j = 0;
+
+                               while ((PtrST = gelf_getsym(ELFtab[i]->PtrDataTab, j++, &ST)) != NULL)
+                               {
+                                       if (PtrST->st_value == Adr)
+                                       {
+                                               if (ELF32_ST_TYPE(PtrST->st_info) == STT_FUNC)
+                                               {
+                                                       SymbolName = ELFManager_GetSymbolnameFromSymbolindex(PtrST->st_name);
+                                               }
+                                       }
+                               }
+                       }
+               }
+       }
+
+       return SymbolName;
+}
+
+
 // Get Symbol name from his address
 // Return NULL if Symbol name is not found
 char *ELFManager_GetSymbolnameFromAdr(size_t Adr)
@@ -260,7 +306,9 @@ char *ELFManager_GetSymbolnameFromAdr(size_t Adr)
                                {
                                        if (PtrST->st_value == Adr)
                                        {
+#ifdef LOG_SUPPORT
                                                WriteLog("ELF: .symtab: DATA: st_info=%0x, st_name=%0x, st_other=%0x, st_shndx=%0x, st_size=%0x, st_value=%0x\n", PtrST->st_info, PtrST->st_name, PtrST->st_other, PtrST->st_shndx, PtrST->st_size, PtrST->st_value);
+#endif
                                                SymbolName = ELFManager_GetSymbolnameFromSymbolindex(PtrST->st_name);
                                        }
                                }