mirror of
https://github.com/tobast/libunwind-eh_elf.git
synced 2024-11-05 01:09:27 +01:00
Update.
(Logical change 1.162)
This commit is contained in:
parent
f913dd3bd1
commit
fcd8dad37e
6 changed files with 109 additions and 44 deletions
5
TODO
5
TODO
|
@ -4,7 +4,6 @@
|
|||
implements its own runtime loader).
|
||||
- document split local-only/generic libraries and separate libunwind-ptrace.a
|
||||
convenience-library
|
||||
- implement non-local versions of dwarf_readXX()
|
||||
- document new "tdep" member in unw_proc_info_t structure
|
||||
- for DWARF 2, use a dummy CIE entry with an augmentation that
|
||||
provides the dyn-info-list-address
|
||||
|
@ -19,6 +18,10 @@ Testing:
|
|||
|
||||
=== taken care of:
|
||||
|
||||
+ Switch ia64 (and rest over) to using Debug() instead of debug()
|
||||
+ implement non-local versions of dwarf_readXX()
|
||||
+ consolidate mostly architecture-independent code such as
|
||||
unw_get_accessors() into shared files
|
||||
+ caching is pretty fundamentally broken, what should happen is this:
|
||||
o On unw_init_local()/unw_init_remote(), libunwind should validate
|
||||
that the cached information is still valid and, if not, flush the
|
||||
|
|
|
@ -46,6 +46,10 @@ uc_addr (ucontext_t *uc, int reg)
|
|||
|
||||
switch (reg)
|
||||
{
|
||||
case UNW_X86_GS: addr = &uc->uc_mcontext.gregs[REG_GS]; break;
|
||||
case UNW_X86_FS: addr = &uc->uc_mcontext.gregs[REG_FS]; break;
|
||||
case UNW_X86_ES: addr = &uc->uc_mcontext.gregs[REG_ES]; break;
|
||||
case UNW_X86_DS: addr = &uc->uc_mcontext.gregs[REG_DS]; break;
|
||||
case UNW_X86_EAX: addr = &uc->uc_mcontext.gregs[REG_EAX]; break;
|
||||
case UNW_X86_EBX: addr = &uc->uc_mcontext.gregs[REG_EBX]; break;
|
||||
case UNW_X86_ECX: addr = &uc->uc_mcontext.gregs[REG_ECX]; break;
|
||||
|
@ -55,6 +59,10 @@ uc_addr (ucontext_t *uc, int reg)
|
|||
case UNW_X86_EBP: addr = &uc->uc_mcontext.gregs[REG_EBP]; break;
|
||||
case UNW_X86_EIP: addr = &uc->uc_mcontext.gregs[REG_EIP]; break;
|
||||
case UNW_X86_ESP: addr = &uc->uc_mcontext.gregs[REG_ESP]; break;
|
||||
case UNW_X86_TRAPNO: addr = &uc->uc_mcontext.gregs[REG_TRAPNO]; break;
|
||||
case UNW_X86_CS: addr = &uc->uc_mcontext.gregs[REG_CS]; break;
|
||||
case UNW_X86_EFLAGS: addr = &uc->uc_mcontext.gregs[REG_EFL]; break;
|
||||
case UNW_X86_SS: addr = &uc->uc_mcontext.gregs[REG_SS]; break;
|
||||
|
||||
default:
|
||||
addr = NULL;
|
||||
|
@ -65,7 +73,7 @@ uc_addr (ucontext_t *uc, int reg)
|
|||
# ifdef UNW_LOCAL_ONLY
|
||||
|
||||
void *
|
||||
_Ux86_uc_addr (ucontext_t *uc, int reg)
|
||||
tdep_uc_addr (ucontext_t *uc, int reg)
|
||||
{
|
||||
return uc_addr (uc, reg);
|
||||
}
|
||||
|
@ -117,13 +125,11 @@ access_reg (unw_addr_space_t as, unw_regnum_t reg, unw_word_t *val, int write,
|
|||
unw_word_t *addr;
|
||||
ucontext_t *uc = arg;
|
||||
|
||||
#if 0
|
||||
if (reg >= UNW_IA64_FR && reg < UNW_IA64_FR + 128)
|
||||
if (unw_is_fpreg (reg))
|
||||
goto badreg;
|
||||
#endif
|
||||
|
||||
addr = uc_addr (uc, reg);
|
||||
if (!addr)
|
||||
Debug (16, "reg = %s\n", unw_regname (reg));
|
||||
if (!(addr = uc_addr (uc, reg)))
|
||||
goto badreg;
|
||||
|
||||
if (write)
|
||||
|
@ -147,31 +153,26 @@ static int
|
|||
access_fpreg (unw_addr_space_t as, unw_regnum_t reg, unw_fpreg_t *val,
|
||||
int write, void *arg)
|
||||
{
|
||||
#if 1
|
||||
printf ("access_fpreg: screams to get implemented, doesn't it?\n");
|
||||
return 0;
|
||||
#else
|
||||
ucontext_t *uc = arg;
|
||||
unw_fpreg_t *addr;
|
||||
|
||||
if (reg < UNW_IA64_FR || reg >= UNW_IA64_FR + 128)
|
||||
if (!unw_is_fpreg (reg))
|
||||
goto badreg;
|
||||
|
||||
addr = uc_addr (uc, reg);
|
||||
if (!addr)
|
||||
if (!(addr = uc_addr (uc, reg)))
|
||||
goto badreg;
|
||||
|
||||
if (write)
|
||||
{
|
||||
Debug (12, "%s <- %016lx.%016lx\n",
|
||||
unw_regname (reg), val->raw.bits[1], val->raw.bits[0]);
|
||||
Debug (12, "%s <- %08lx.%08lx.%08lx\n", unw_regname (reg),
|
||||
((long *)val)[0], ((long *)val)[1], ((long *)val)[2]);
|
||||
*(unw_fpreg_t *) addr = *val;
|
||||
}
|
||||
else
|
||||
{
|
||||
*val = *(unw_fpreg_t *) addr;
|
||||
Debug (12, "%s -> %016lx.%016lx\n",
|
||||
unw_regname (reg), val->raw.bits[1], val->raw.bits[0]);
|
||||
Debug (12, "%s -> %08lx.%08lx.%08lx\n", unw_regname (reg),
|
||||
((long *)val)[0], ((long *)val)[1], ((long *)val)[2]);
|
||||
}
|
||||
return 0;
|
||||
|
||||
|
@ -179,7 +180,6 @@ access_fpreg (unw_addr_space_t as, unw_regnum_t reg, unw_fpreg_t *val,
|
|||
Debug (1, "bad register number %u\n", reg);
|
||||
/* attempt to access a non-preserved register */
|
||||
return -UNW_EBADREG;
|
||||
#endif
|
||||
}
|
||||
|
||||
static int
|
||||
|
@ -203,6 +203,7 @@ x86_local_addr_space_init (void)
|
|||
local_addr_space.acc.access_fpreg = access_fpreg;
|
||||
local_addr_space.acc.resume = x86_local_resume;
|
||||
local_addr_space.acc.get_proc_name = get_static_proc_name;
|
||||
unw_flush_cache (&local_addr_space, 0, 0);
|
||||
}
|
||||
|
||||
#endif /* !UNW_REMOTE_ONLY */
|
||||
|
|
|
@ -41,8 +41,10 @@ unw_init_local (unw_cursor_t *cursor, ucontext_t *uc)
|
|||
{
|
||||
struct cursor *c = (struct cursor *) cursor;
|
||||
|
||||
if (x86_needs_initialization)
|
||||
x86_init ();
|
||||
if (tdep_needs_initialization)
|
||||
tdep_init ();
|
||||
|
||||
Debug (2, "(cursor=%p)\n", c);
|
||||
|
||||
c->dwarf.as = unw_local_addr_space;
|
||||
c->dwarf.as_arg = uc;
|
||||
|
|
|
@ -34,8 +34,10 @@ unw_init_remote (unw_cursor_t *cursor, unw_addr_space_t as, void *as_arg)
|
|||
#else /* !UNW_LOCAL_ONLY */
|
||||
struct cursor *c = (struct cursor *) cursor;
|
||||
|
||||
if (x86_needs_initialization)
|
||||
x86_init ();
|
||||
if (tdep_needs_initialization)
|
||||
tdep_init ();
|
||||
|
||||
Debug (2, "(cursor=%p)\n", c);
|
||||
|
||||
c->dwarf.as = as;
|
||||
c->dwarf.as_arg = as_arg;
|
||||
|
|
|
@ -2,16 +2,82 @@
|
|||
|
||||
/* Define various structure offsets to simplify cross-compilation. */
|
||||
|
||||
/* Offsets for x86 Linux "ucontext_t": */
|
||||
|
||||
#define LINUX_UC_FLAGS_OFF 0x00
|
||||
#define LINUX_UC_LINK_OFF 0x04
|
||||
#define LINUX_UC_STACK_OFF 0x08
|
||||
#define LINUX_UC_MCONTEXT_OFF 0x14
|
||||
#define LINUX_UC_SIGMASK_OFF 0x6c
|
||||
|
||||
/* The struct sigcontext is located at an offset of 4
|
||||
from the stack pointer in the signal frame. */
|
||||
|
||||
#define LINUX_SC_ESP_OFF 0x1c
|
||||
#define LINUX_SC_EBP_OFF 0x18
|
||||
#define LINUX_SC_EIP_OFF 0x38
|
||||
/* Offsets for x86 Linux "struct sigcontext": */
|
||||
|
||||
/* With SA_SIGINFO set, we believe that basically the same
|
||||
layout is used for ucontext_t, except that 20 bytes are added
|
||||
at the beginning. */
|
||||
#define LINUX_UC_ESP_OFF (LINUX_SC_ESP_OFF+20)
|
||||
#define LINUX_UC_EBP_OFF (LINUX_SC_EBP_OFF+20)
|
||||
#define LINUX_UC_EIP_OFF (LINUX_SC_EIP_OFF+20)
|
||||
#define LINUX_SC_GS_OFF 0x00
|
||||
#define LINUX_SC_GSH_OFF 0x02
|
||||
#define LINUX_SC_FS_OFF 0x04
|
||||
#define LINUX_SC_FSH_OFF 0x06
|
||||
#define LINUX_SC_ES_OFF 0x08
|
||||
#define LINUX_SC_ESH_OFF 0x0a
|
||||
#define LINUX_SC_DS_OFF 0x0c
|
||||
#define LINUX_SC_DSH_OFF 0x0e
|
||||
#define LINUX_SC_EDI_OFF 0x10
|
||||
#define LINUX_SC_ESI_OFF 0x14
|
||||
#define LINUX_SC_EBP_OFF 0x18
|
||||
#define LINUX_SC_ESP_OFF 0x1c
|
||||
#define LINUX_SC_EBX_OFF 0x20
|
||||
#define LINUX_SC_EDX_OFF 0x24
|
||||
#define LINUX_SC_ECX_OFF 0x28
|
||||
#define LINUX_SC_EAX_OFF 0x2c
|
||||
#define LINUX_SC_TRAPNO_OFF 0x30
|
||||
#define LINUX_SC_ERR_OFF 0x34
|
||||
#define LINUX_SC_EIP_OFF 0x38
|
||||
#define LINUX_SC_CS_OFF 0x3c
|
||||
#define LINUX_SC_CSH_OFF 0x3e
|
||||
#define LINUX_SC_EFLAGS_OFF 0x40
|
||||
#define LINUX_SC_ESP_AT_SIGNAL_OFF 0x44
|
||||
#define LINUX_SC_SS_OFF 0x48
|
||||
#define LINUX_SC_SSH_OFF 0x4a
|
||||
#define LINUX_SC_FPSTATE_OFF 0x4c
|
||||
#define LINUX_SC_OLDMASK_OFF 0x50
|
||||
#define LINUX_SC_CR2_OFF 0x54
|
||||
|
||||
/* Offsets for x86 Linux "struct _fpstate": */
|
||||
|
||||
#define LINUX_FPSTATE_CW_OFF 0x000
|
||||
#define LINUX_FPSTATE_SW_OFF 0x004
|
||||
#define LINUX_FPSTATE_TAG_OFF 0x008
|
||||
#define LINUX_FPSTATE_IPOFF_OFF 0x00c
|
||||
#define LINUX_FPSTATE_CSSEL_OFF 0x010
|
||||
#define LINUX_FPSTATE_DATAOFF_OFF 0x014
|
||||
#define LINUX_FPSTATE_DATASEL_OFF 0x018
|
||||
#define LINUX_FPSTATE_ST0_OFF 0x01c
|
||||
#define LINUX_FPSTATE_ST1_OFF 0x026
|
||||
#define LINUX_FPSTATE_ST2_OFF 0x030
|
||||
#define LINUX_FPSTATE_ST3_OFF 0x03a
|
||||
#define LINUX_FPSTATE_ST4_OFF 0x044
|
||||
#define LINUX_FPSTATE_ST5_OFF 0x04e
|
||||
#define LINUX_FPSTATE_ST6_OFF 0x058
|
||||
#define LINUX_FPSTATE_ST7_OFF 0x062
|
||||
#define LINUX_FPSTATE_STATUS_OFF 0x06c
|
||||
#define LINUX_FPSTATE_MAGIC_OFF 0x06e
|
||||
#define LINUX_FPSTATE_FXSR_ENV_OFF 0x070
|
||||
#define LINUX_FPSTATE_MXCSR_OFF 0x088
|
||||
#define LINUX_FPSTATE_FXSR_ST0_OFF 0x090
|
||||
#define LINUX_FPSTATE_FXSR_ST1_OFF 0x0a0
|
||||
#define LINUX_FPSTATE_FXSR_ST2_OFF 0x0b0
|
||||
#define LINUX_FPSTATE_FXSR_ST3_OFF 0x0c0
|
||||
#define LINUX_FPSTATE_FXSR_ST4_OFF 0x0d0
|
||||
#define LINUX_FPSTATE_FXSR_ST5_OFF 0x0e0
|
||||
#define LINUX_FPSTATE_FXSR_ST6_OFF 0x0f0
|
||||
#define LINUX_FPSTATE_FXSR_ST7_OFF 0x100
|
||||
#define LINUX_FPSTATE_XMM0_OFF 0x110
|
||||
#define LINUX_FPSTATE_XMM1_OFF 0x120
|
||||
#define LINUX_FPSTATE_XMM2_OFF 0x130
|
||||
#define LINUX_FPSTATE_XMM3_OFF 0x140
|
||||
#define LINUX_FPSTATE_XMM4_OFF 0x150
|
||||
#define LINUX_FPSTATE_XMM5_OFF 0x160
|
||||
#define LINUX_FPSTATE_XMM6_OFF 0x170
|
||||
#define LINUX_FPSTATE_XMM7_OFF 0x180
|
||||
|
|
|
@ -48,23 +48,14 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */
|
|||
#define TRAPNO 10
|
||||
#define ST0 11
|
||||
|
||||
#define x86_lock UNW_ARCH_OBJ(lock)
|
||||
#define x86_needs_initialization UNW_ARCH_OBJ(needs_initialization)
|
||||
#define x86_init UNW_ARCH_OBJ(init)
|
||||
#define x86_access_reg UNW_OBJ(access_reg)
|
||||
#define x86_access_fpreg UNW_OBJ(access_fpreg)
|
||||
#define x86_lock UNW_OBJ(lock)
|
||||
#define x86_local_resume UNW_OBJ(local_resume)
|
||||
#define x86_local_addr_space_init UNW_OBJ(local_addr_space_init)
|
||||
#define x86_scratch_loc UNW_OBJ(scratch_loc)
|
||||
|
||||
extern int x86_needs_initialization;
|
||||
|
||||
extern void x86_init (void);
|
||||
extern int x86_access_reg (struct cursor *c, unw_regnum_t reg,
|
||||
unw_word_t *valp, int write);
|
||||
extern int x86_access_fpreg (struct cursor *c, unw_regnum_t reg,
|
||||
unw_fpreg_t *valp, int write);
|
||||
extern void x86_local_addr_space_init (void);
|
||||
extern int x86_local_resume (unw_addr_space_t as, unw_cursor_t *cursor,
|
||||
void *arg);
|
||||
extern dwarf_loc_t x86_scratch_loc (struct cursor *c, unw_regnum_t reg);
|
||||
|
||||
#endif /* unwind_i_h */
|
||||
|
|
Loading…
Reference in a new issue