1
0
Fork 0
mirror of https://github.com/tobast/libunwind-eh_elf.git synced 2024-11-18 22:07:38 +01:00

(linux_interrupt): New function.

(update_frame_state): Handle ABI_MARKER_LINUX_INTERRUPT by calling linux_interrupt().
	If c->abi_marker is non-zero, copy it to c->last_abi_marker.

(Logical change 1.89)
This commit is contained in:
hp.com!davidm 2003-04-25 07:44:23 +00:00
parent 43786a3f2d
commit e0160b16b7

View file

@ -59,6 +59,31 @@ linux_sigtramp (struct cursor *c, unw_word_t *num_regsp)
#endif #endif
} }
static inline int
linux_interrupt (struct cursor *c, unw_word_t *num_regsp)
{
#if defined(UNW_LOCAL_ONLY)
/* Perhaps libunwind will some day become the Linux kernel unwinder.
Until such time, linux_interrupt() is needed only for non-local
unwinding. */
return -UNW_EINVAL;
#else
unw_word_t sc_addr, num_regs;
sc_addr = c->sigcontext_addr = c->sp + 0x10;
if ((c->pr & (1UL << LINUX_PT_P_NONSYS)) != 0)
num_regs = c->cfm & 0x7f;
else
num_regs = 0;
/* do what can't be described by unwind directives: */
c->loc[IA64_REG_PFS] = IA64_LOC_ADDR (sc_addr + LINUX_PT_PFS_OFF, 0);
*num_regsp = num_regs; /* size of frame */
return 0;
#endif
}
static inline int static inline int
hpux_sigtramp (struct cursor *c, unw_word_t *num_regsp) hpux_sigtramp (struct cursor *c, unw_word_t *num_regsp)
{ {
@ -221,6 +246,7 @@ update_frame_state (struct cursor *c)
num_regs = 0; num_regs = 0;
if (unlikely (c->abi_marker)) if (unlikely (c->abi_marker))
{ {
c->last_abi_marker = c->abi_marker;
switch (c->abi_marker) switch (c->abi_marker)
{ {
case ABI_MARKER_LINUX_SIGTRAMP: case ABI_MARKER_LINUX_SIGTRAMP:
@ -229,6 +255,12 @@ update_frame_state (struct cursor *c)
return ret; return ret;
break; break;
case ABI_MARKER_LINUX_INTERRUPT:
c->as->abi = ABI_LINUX;
if ((ret = linux_interrupt (c, &num_regs)) < 0)
return ret;
break;
case ABI_MARKER_HP_UX_SIGTRAMP: case ABI_MARKER_HP_UX_SIGTRAMP:
c->as->abi = ABI_HPUX; c->as->abi = ABI_HPUX;
if ((ret = hpux_sigtramp (c, &num_regs)) < 0) if ((ret = hpux_sigtramp (c, &num_regs)) < 0)