Beginning of dbghelp dwarf2 support:
- add elf_module entry for dwarf2_parse - stubbed dwarf2_parse in new dwarf.c file
This commit is contained in:
parent
402aaa8edb
commit
83f001b6c7
|
@ -9,6 +9,7 @@ IMPORTS = psapi kernel32 ntdll
|
|||
C_SRCS = \
|
||||
coff.c \
|
||||
dbghelp.c \
|
||||
dwarf.c \
|
||||
elf_module.c \
|
||||
image.c \
|
||||
memory.c \
|
||||
|
|
|
@ -356,6 +356,12 @@ extern BOOL stabs_parse(struct module* module, unsigned long load_offset
|
|||
const void* stabs, int stablen,
|
||||
const char* strs, int strtablen);
|
||||
|
||||
/* dwarf.c */
|
||||
extern BOOL dwarf2_parse(struct module* module, unsigned long load_offset,
|
||||
const unsigned char* debug, unsigned int debug_size,
|
||||
const unsigned char* abbrev, unsigned int abbrev_size,
|
||||
const unsigned char* str, unsigned int str_sz);
|
||||
|
||||
/* symbol.c */
|
||||
extern const char* symt_get_name(const struct symt* sym);
|
||||
extern int symt_cmp_addr(const void* p1, const void* p2);
|
||||
|
|
|
@ -0,0 +1,123 @@
|
|||
/*
|
||||
* File dwarf.c - read dwarf2 information from the ELF modules
|
||||
*
|
||||
* Copyright (C) 2005, Raphael Junqueira
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2.1 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library; if not, write to the Free Software
|
||||
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <fcntl.h>
|
||||
#ifdef HAVE_SYS_STAT_H
|
||||
# include <sys/stat.h>
|
||||
#endif
|
||||
#ifdef HAVE_SYS_MMAN_H
|
||||
#include <sys/mman.h>
|
||||
#endif
|
||||
#include <limits.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#ifdef HAVE_UNISTD_H
|
||||
# include <unistd.h>
|
||||
#endif
|
||||
#include <stdio.h>
|
||||
#ifndef PATH_MAX
|
||||
#define PATH_MAX MAX_PATH
|
||||
#endif
|
||||
#include <assert.h>
|
||||
#include <stdarg.h>
|
||||
|
||||
#include "windef.h"
|
||||
#include "winbase.h"
|
||||
#include "winreg.h"
|
||||
#include "winnls.h"
|
||||
|
||||
#include "dbghelp_private.h"
|
||||
|
||||
#include "wine/debug.h"
|
||||
|
||||
WINE_DEFAULT_DEBUG_CHANNEL(dbghelp_dwarf);
|
||||
|
||||
/**
|
||||
*
|
||||
* Main Specs:
|
||||
* http://www.eagercon.com/dwarf/dwarf3std.htm
|
||||
* http://www.eagercon.com/dwarf/dwarf-2.0.0.pdf
|
||||
*
|
||||
* dwarf2.h: http://www.hakpetzna.com/b/binutils/dwarf2_8h-source.html
|
||||
*
|
||||
* example of projects who do dwarf2 parsing:
|
||||
* http://www.x86-64.org/cgi-bin/cvsweb.cgi/binutils.dead/binutils/readelf.c?rev=1.1.1.2
|
||||
* http://elis.ugent.be/diota/log/ltrace_elf.c
|
||||
*/
|
||||
|
||||
typedef struct dwarf2_parse_context_s {
|
||||
const unsigned char* data;
|
||||
} dwarf2_parse_context_t;
|
||||
|
||||
unsigned long dwarf2_leb128_as_unsigned(dwarf2_parse_context_t* ctx)
|
||||
{
|
||||
unsigned long ret = 0;
|
||||
unsigned char byte;
|
||||
unsigned shift = 0;
|
||||
|
||||
assert( NULL != ctx );
|
||||
|
||||
while (1) {
|
||||
byte = *(ctx->data);
|
||||
ctx->data++;
|
||||
ret |= (byte & 0x7f) << shift;
|
||||
shift += 7;
|
||||
if (0 == (byte & 0x80)) { break ; }
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
long dwarf2_leb128_as_signed(dwarf2_parse_context_t* ctx)
|
||||
{
|
||||
long ret = 0;
|
||||
unsigned char byte;
|
||||
unsigned shift = 0;
|
||||
const unsigned size = sizeof(int) * 8;
|
||||
|
||||
assert( NULL != ctx );
|
||||
|
||||
while (1) {
|
||||
byte = *(ctx->data);
|
||||
ctx->data++;
|
||||
ret |= (byte & 0x7f) << shift;
|
||||
shift += 7;
|
||||
if (0 == (byte & 0x80)) { break ; }
|
||||
}
|
||||
/* as spec: sign bit of byte is 2nd high order bit (80x40)
|
||||
* -> 0x80 is used as flag.
|
||||
*/
|
||||
if ((shift < size) && (byte & 0x40)) {
|
||||
ret |= - (1 << shift);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
BOOL dwarf2_parse(struct module* module, unsigned long load_offset,
|
||||
const unsigned char* debug, unsigned int debug_size,
|
||||
const unsigned char* abbrev, unsigned int abbrev_size,
|
||||
const unsigned char* str, unsigned int str_sz)
|
||||
{
|
||||
return FALSE;
|
||||
}
|
|
@ -776,7 +776,9 @@ static BOOL elf_load_debug_info_from_map(struct module* module,
|
|||
BOOL ret = FALSE;
|
||||
const char* shstrtab;
|
||||
int i;
|
||||
int symtab_sect, dynsym_sect, stab_sect, stabstr_sect, debug_sect, debuglink_sect;
|
||||
int symtab_sect, dynsym_sect, stab_sect, stabstr_sect;
|
||||
int debug_sect, debug_str_sect, debug_abbrev_sect, debug_line_sect;
|
||||
int debuglink_sect;
|
||||
struct thunk_area thunks[] =
|
||||
{
|
||||
{"__wine_spec_import_thunks", THUNK_ORDINAL_NOTYPE, 0, 0}, /* inter DLL calls */
|
||||
|
@ -806,8 +808,9 @@ static BOOL elf_load_debug_info_from_map(struct module* module,
|
|||
shstrtab = elf_map_section(fmap, fmap->elfhdr.e_shstrndx);
|
||||
if (shstrtab == NO_MAP) return FALSE;
|
||||
|
||||
symtab_sect = dynsym_sect = stab_sect = stabstr_sect =
|
||||
debug_sect = debuglink_sect = -1;
|
||||
symtab_sect = dynsym_sect = stab_sect = stabstr_sect = -1;
|
||||
debug_sect = debug_str_sect = debug_abbrev_sect = debug_line_sect = -1;
|
||||
debuglink_sect = -1;
|
||||
|
||||
for (i = 0; i < fmap->elfhdr.e_shnum; i++)
|
||||
{
|
||||
|
@ -817,6 +820,12 @@ static BOOL elf_load_debug_info_from_map(struct module* module,
|
|||
stabstr_sect = i;
|
||||
if (strcmp(shstrtab + fmap->sect[i].shdr.sh_name, ".debug_info") == 0)
|
||||
debug_sect = i;
|
||||
if (strcmp(shstrtab + fmap->sect[i].shdr.sh_name, ".debug_str") == 0)
|
||||
debug_str_sect = i;
|
||||
if (strcmp(shstrtab + fmap->sect[i].shdr.sh_name, ".debug_abbrev") == 0)
|
||||
debug_abbrev_sect = i;
|
||||
if (strcmp(shstrtab + fmap->sect[i].shdr.sh_name, ".debug_line") == 0)
|
||||
debug_line_sect = i;
|
||||
if (strcmp(shstrtab + fmap->sect[i].shdr.sh_name, ".gnu_debuglink") == 0)
|
||||
debuglink_sect = i;
|
||||
if ((strcmp(shstrtab + fmap->sect[i].shdr.sh_name, ".symtab") == 0) &&
|
||||
|
@ -874,8 +883,31 @@ static BOOL elf_load_debug_info_from_map(struct module* module,
|
|||
else if (debug_sect != -1)
|
||||
{
|
||||
/* Dwarf 2 debug information */
|
||||
FIXME("Unsupported Dwarf2 information for %s\n",
|
||||
module->module.ModuleName);
|
||||
const char* dw2_debug;
|
||||
const char* dw2_debug_abbrev;
|
||||
const char* dw2_debug_str;
|
||||
|
||||
FIXME("Alpha-support for Dwarf2 information for %s\n", module->module.ModuleName);
|
||||
|
||||
dw2_debug = elf_map_section(fmap, debug_sect);
|
||||
dw2_debug_abbrev = elf_map_section(fmap, debug_abbrev_sect);
|
||||
dw2_debug_str = elf_map_section(fmap, debug_str_sect);
|
||||
if (dw2_debug != NO_MAP && NO_MAP != dw2_debug_abbrev && dw2_debug_str != NO_MAP)
|
||||
{
|
||||
/* OK, now just parse dwarf2 debug infos. */
|
||||
ret = dwarf2_parse(module, module->elf_info->elf_addr,
|
||||
dw2_debug, fmap->sect[debug_sect].shdr.sh_size,
|
||||
dw2_debug_abbrev, fmap->sect[debug_abbrev_sect].shdr.sh_size,
|
||||
dw2_debug_str, fmap->sect[debug_str_sect].shdr.sh_size);
|
||||
}
|
||||
elf_unmap_section(fmap, debug_sect);
|
||||
elf_unmap_section(fmap, debug_abbrev_sect);
|
||||
elf_unmap_section(fmap, debug_str_sect);
|
||||
if (!ret)
|
||||
{
|
||||
WARN("Couldn't correctly read stabs\n");
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
else if (debuglink_sect != -1)
|
||||
{
|
||||
|
|
Loading…
Reference in New Issue