mirror of
https://github.com/tobast/libunwind-eh_elf.git
synced 2024-11-15 12:48:12 +01:00
FreeBSD/i386 port. get/setcontext need further work
This commit is contained in:
parent
c61e0b932c
commit
bb41eba56c
4 changed files with 100 additions and 4 deletions
|
@ -27,6 +27,10 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */
|
||||||
|
|
||||||
#include "unwind_i.h"
|
#include "unwind_i.h"
|
||||||
|
|
||||||
|
#if defined(_LITTLE_ENDIAN) && !defined(__LITTLE_ENDIAN)
|
||||||
|
#define __LITTLE_ENDIAN _LITTLE_ENDIAN
|
||||||
|
#endif
|
||||||
|
|
||||||
PROTECTED unw_addr_space_t
|
PROTECTED unw_addr_space_t
|
||||||
unw_create_addr_space (unw_accessors_t *a, int byte_order)
|
unw_create_addr_space (unw_accessors_t *a, int byte_order)
|
||||||
{
|
{
|
||||||
|
|
|
@ -47,6 +47,7 @@ uc_addr (ucontext_t *uc, int reg)
|
||||||
|
|
||||||
switch (reg)
|
switch (reg)
|
||||||
{
|
{
|
||||||
|
#if defined __linux__
|
||||||
case UNW_X86_GS: addr = &uc->uc_mcontext.gregs[REG_GS]; break;
|
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_FS: addr = &uc->uc_mcontext.gregs[REG_FS]; break;
|
||||||
case UNW_X86_ES: addr = &uc->uc_mcontext.gregs[REG_ES]; break;
|
case UNW_X86_ES: addr = &uc->uc_mcontext.gregs[REG_ES]; break;
|
||||||
|
@ -64,6 +65,27 @@ uc_addr (ucontext_t *uc, int reg)
|
||||||
case UNW_X86_CS: addr = &uc->uc_mcontext.gregs[REG_CS]; 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_EFLAGS: addr = &uc->uc_mcontext.gregs[REG_EFL]; break;
|
||||||
case UNW_X86_SS: addr = &uc->uc_mcontext.gregs[REG_SS]; break;
|
case UNW_X86_SS: addr = &uc->uc_mcontext.gregs[REG_SS]; break;
|
||||||
|
#elif defined __FreeBSD__
|
||||||
|
case UNW_X86_GS: addr = &uc->uc_mcontext.mc_gs; break;
|
||||||
|
case UNW_X86_FS: addr = &uc->uc_mcontext.mc_fs; break;
|
||||||
|
case UNW_X86_ES: addr = &uc->uc_mcontext.mc_es; break;
|
||||||
|
case UNW_X86_DS: addr = &uc->uc_mcontext.mc_ds; break;
|
||||||
|
case UNW_X86_EAX: addr = &uc->uc_mcontext.mc_eax; break;
|
||||||
|
case UNW_X86_EBX: addr = &uc->uc_mcontext.mc_ebx; break;
|
||||||
|
case UNW_X86_ECX: addr = &uc->uc_mcontext.mc_ecx; break;
|
||||||
|
case UNW_X86_EDX: addr = &uc->uc_mcontext.mc_edx; break;
|
||||||
|
case UNW_X86_ESI: addr = &uc->uc_mcontext.mc_esi; break;
|
||||||
|
case UNW_X86_EDI: addr = &uc->uc_mcontext.mc_edi; break;
|
||||||
|
case UNW_X86_EBP: addr = &uc->uc_mcontext.mc_ebp; break;
|
||||||
|
case UNW_X86_EIP: addr = &uc->uc_mcontext.mc_eip; break;
|
||||||
|
case UNW_X86_ESP: addr = &uc->uc_mcontext.mc_esp; break;
|
||||||
|
case UNW_X86_TRAPNO: addr = &uc->uc_mcontext.mc_trapno; break;
|
||||||
|
case UNW_X86_CS: addr = &uc->uc_mcontext.mc_cs; break;
|
||||||
|
case UNW_X86_EFLAGS: addr = &uc->uc_mcontext.mc_eflags; break;
|
||||||
|
case UNW_X86_SS: addr = &uc->uc_mcontext.mc_ss; break;
|
||||||
|
#else
|
||||||
|
#error Port me
|
||||||
|
#endif
|
||||||
|
|
||||||
default:
|
default:
|
||||||
addr = NULL;
|
addr = NULL;
|
||||||
|
|
|
@ -38,6 +38,7 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */
|
||||||
_Ux86_getcontext:
|
_Ux86_getcontext:
|
||||||
mov 4(%esp),%eax /* ucontext_t* */
|
mov 4(%esp),%eax /* ucontext_t* */
|
||||||
|
|
||||||
|
#if defined __linux__
|
||||||
/* EAX is not preserved. */
|
/* EAX is not preserved. */
|
||||||
movl $0, (LINUX_UC_MCONTEXT_OFF+LINUX_SC_EAX_OFF)(%eax)
|
movl $0, (LINUX_UC_MCONTEXT_OFF+LINUX_SC_EAX_OFF)(%eax)
|
||||||
|
|
||||||
|
@ -63,11 +64,54 @@ _Ux86_getcontext:
|
||||||
movl %ecx, (LINUX_UC_MCONTEXT_OFF+LINUX_SC_FPSTATE_OFF)(%eax)
|
movl %ecx, (LINUX_UC_MCONTEXT_OFF+LINUX_SC_FPSTATE_OFF)(%eax)
|
||||||
fnstenv (%ecx)
|
fnstenv (%ecx)
|
||||||
fldenv (%ecx)
|
fldenv (%ecx)
|
||||||
|
#elif defined __FreeBSD__
|
||||||
|
/* EAX is not preserved. */
|
||||||
|
movl $0, (FREEBSD_UC_MCONTEXT_EAX_OFF)(%eax)
|
||||||
|
|
||||||
|
movl %ebx, (FREEBSD_UC_MCONTEXT_EBX_OFF)(%eax)
|
||||||
|
movl %ecx, (FREEBSD_UC_MCONTEXT_ECX_OFF)(%eax)
|
||||||
|
movl %edx, (FREEBSD_UC_MCONTEXT_EDX_OFF)(%eax)
|
||||||
|
movl %edi, (FREEBSD_UC_MCONTEXT_EDI_OFF)(%eax)
|
||||||
|
movl %esi, (FREEBSD_UC_MCONTEXT_ESI_OFF)(%eax)
|
||||||
|
movl %ebp, (FREEBSD_UC_MCONTEXT_EBP_OFF)(%eax)
|
||||||
|
|
||||||
|
movl (%esp), %ecx
|
||||||
|
movl %ecx, (FREEBSD_UC_MCONTEXT_OFF_EIP)(%eax)
|
||||||
|
|
||||||
|
leal 4(%esp), %ecx /* Exclude the return address. */
|
||||||
|
movl %ecx, (FREEBSD_UC_MCONTEXT_OFF_ESP)(%eax)
|
||||||
|
|
||||||
|
xorl %ecx, %ecx
|
||||||
|
movw %fs, %cx
|
||||||
|
movl %ecx, (FREEBSD_UC_MCONTEXT_OFF_FS)(%eax)
|
||||||
|
movw %gs, %cx
|
||||||
|
movl %ecx, (FREEBSD_UC_MCONTEXT_OFF_GS)(%eax)
|
||||||
|
movw %ds, %cx
|
||||||
|
movl %ecx, (FREEBSD_UC_MCONTEXT_OFF_DS)(%eax)
|
||||||
|
movw %es, %cx
|
||||||
|
movl %ecx, (FREEBSD_UC_MCONTEXT_OFF_ES)(%eax)
|
||||||
|
movw %ss, %cx
|
||||||
|
movl %ecx, (FREEBSD_UC_MCONTEXT_OFF_SS)(%eax)
|
||||||
|
movw %cs, %cx
|
||||||
|
movl %ecx, (FREEBSD_UC_MCONTEXT_OFF_CS)(%eax)
|
||||||
|
|
||||||
|
pushfl
|
||||||
|
popl (FREEBSD_UC_MCONTEXT_OFF_EFLAGS)(%eax)
|
||||||
|
|
||||||
|
movl $FREEBSD_UC_MCONTEXT_FPOWNED_FPU,FREEBSD_UC_MCONTEXT_OWNEDFP(%eax)
|
||||||
|
movl $FREEBSD_UC_MCONTEXT_FPFMT_XMM,FREEBSD_UC_MCONTEXT_FPFORMAT(%eax)
|
||||||
|
|
||||||
|
leal LINUX_UC_FPREGS_MEM_OFF(%eax), %ecx
|
||||||
|
movl %ecx, (LINUX_UC_MCONTEXT_OFF+LINUX_SC_FPSTATE_OFF)(%eax)
|
||||||
|
fnstenv (%ecx)
|
||||||
|
fldenv (%ecx)
|
||||||
|
|
||||||
|
movl $FREEBSD_UC_MCONTEXT_MC_LEN_VAL, FREEBSD_UC_MCONTEXT_MC_LEN(%eax)
|
||||||
|
#endif
|
||||||
|
|
||||||
xor %eax, %eax
|
xor %eax, %eax
|
||||||
ret
|
ret
|
||||||
|
.size _Ux86_getcontext, . - _Ux86_getcontext
|
||||||
|
|
||||||
#ifdef __linux__
|
/* We do not need executable stack. */
|
||||||
/* We do not need executable stack. */
|
.section .note.GNU-stack,"",@progbits
|
||||||
.section .note.GNU-stack,"",@progbits
|
|
||||||
#endif
|
|
||||||
|
|
|
@ -82,3 +82,29 @@
|
||||||
#define LINUX_FPSTATE_XMM5_OFF 0x160
|
#define LINUX_FPSTATE_XMM5_OFF 0x160
|
||||||
#define LINUX_FPSTATE_XMM6_OFF 0x170
|
#define LINUX_FPSTATE_XMM6_OFF 0x170
|
||||||
#define LINUX_FPSTATE_XMM7_OFF 0x180
|
#define LINUX_FPSTATE_XMM7_OFF 0x180
|
||||||
|
|
||||||
|
#define FREEBSD_UC_MCONTEXT_EAX_OFF 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_EBX_OFF 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_ECX_OFF 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_EDX_OFF 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_EDI_OFF 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_ESI_OFF 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_EBP_OFF 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_OFF_EIP 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_OFF_ESP 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_OFF_FS 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_OFF_GS 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_OFF_DS 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_OFF_ES 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_OFF_SS 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_OFF_CS 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_OFF_EFLAGS 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_OWNEDFP 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_FPFORMAT 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_FPSTATE 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_MC_LEN 0x11
|
||||||
|
|
||||||
|
#define FREEBSD_UC_MCONTEXT_MC_LEN_VAL 0x11
|
||||||
|
#define FREEBSD_UC_MCONTEXT_FPOWNED_FPU 0x20001
|
||||||
|
#define FREEBSD_UC_MCONTEXT_FPFMT_387 0x10001
|
||||||
|
#define FREEBSD_UC_MCONTEXT_FPFMT_XMM 0x10002
|
||||||
|
|
Loading…
Reference in a new issue