Commit b96d1fe3 authored by Arun Sharma's avatar Arun Sharma Committed by David Mosberger

[PATCH] ia64: make ia32 core dumps work

The attached patch implements core dump functionality for IA-32
applications running on ia64.
parent 315d5ee1
...@@ -19,6 +19,7 @@ ...@@ -19,6 +19,7 @@
#include <asm/signal.h> #include <asm/signal.h>
#include "ia32priv.h" #include "ia32priv.h"
#include "elfcore32.h"
#define CONFIG_BINFMT_ELF32 #define CONFIG_BINFMT_ELF32
......
/*
* IA-32 ELF core dump support.
*
* Copyright (C) 2003 Arun Sharma <arun.sharma@intel.com>
*
* Derived from the x86_64 version
*/
#ifndef _ELFCORE32_H_
#define _ELFCORE32_H_
#define USE_ELF_CORE_DUMP 1
/* Override elfcore.h */
#define _LINUX_ELFCORE_H 1
typedef unsigned int elf_greg_t;
#define ELF_NGREG (sizeof (struct user_regs_struct32) / sizeof(elf_greg_t))
typedef elf_greg_t elf_gregset_t[ELF_NGREG];
typedef struct ia32_user_i387_struct elf_fpregset_t;
typedef struct ia32_user_fxsr_struct elf_fpxregset_t;
struct elf_siginfo
{
int si_signo; /* signal number */
int si_code; /* extra code */
int si_errno; /* errno */
};
#define jiffies_to_timeval(a,b) do { (b)->tv_usec = 0; (b)->tv_sec = (a)/HZ; }while(0)
struct elf_prstatus
{
struct elf_siginfo pr_info; /* Info associated with signal */
short pr_cursig; /* Current signal */
unsigned int pr_sigpend; /* Set of pending signals */
unsigned int pr_sighold; /* Set of held signals */
pid_t pr_pid;
pid_t pr_ppid;
pid_t pr_pgrp;
pid_t pr_sid;
struct compat_timeval pr_utime; /* User time */
struct compat_timeval pr_stime; /* System time */
struct compat_timeval pr_cutime; /* Cumulative user time */
struct compat_timeval pr_cstime; /* Cumulative system time */
elf_gregset_t pr_reg; /* GP registers */
int pr_fpvalid; /* True if math co-processor being used. */
};
#define ELF_PRARGSZ (80) /* Number of chars for args */
struct elf_prpsinfo
{
char pr_state; /* numeric process state */
char pr_sname; /* char for pr_state */
char pr_zomb; /* zombie */
char pr_nice; /* nice val */
unsigned int pr_flag; /* flags */
__u16 pr_uid;
__u16 pr_gid;
pid_t pr_pid, pr_ppid, pr_pgrp, pr_sid;
/* Lots missing */
char pr_fname[16]; /* filename of executable */
char pr_psargs[ELF_PRARGSZ]; /* initial part of arg list */
};
#define ELF_CORE_COPY_REGS(pr_reg, regs) \
pr_reg[0] = regs->r11; \
pr_reg[1] = regs->r9; \
pr_reg[2] = regs->r10; \
pr_reg[3] = regs->r14; \
pr_reg[4] = regs->r15; \
pr_reg[5] = regs->r13; \
pr_reg[6] = regs->r8; \
pr_reg[7] = regs->r16 & 0xffff; \
pr_reg[8] = (regs->r16 >> 16) & 0xffff; \
pr_reg[9] = (regs->r16 >> 32) & 0xffff; \
pr_reg[10] = (regs->r16 >> 48) & 0xffff; \
pr_reg[11] = regs->r1; \
pr_reg[12] = regs->cr_iip; \
pr_reg[13] = regs->r17 & 0xffff; \
asm volatile ("mov %0=ar.eflag ;;" \
: "=r"(pr_reg[14])); \
pr_reg[15] = regs->r12; \
pr_reg[16] = (regs->r17 >> 16) & 0xffff;
static inline void elf_core_copy_regs(elf_gregset_t *elfregs,
struct pt_regs *regs)
{
ELF_CORE_COPY_REGS((*elfregs), regs)
}
static inline int elf_core_copy_task_regs(struct task_struct *t,
elf_gregset_t* elfregs)
{
struct pt_regs *pp = ia64_task_regs(t);
ELF_CORE_COPY_REGS((*elfregs), pp);
return 1;
}
static inline int
elf_core_copy_task_fpregs(struct task_struct *tsk, elf_fpregset_t *fpu)
{
struct ia32_user_i387_struct *fpstate = (void*)fpu;
if (!tsk->used_math)
return 0;
save_ia32_fpstate(tsk, fpstate);
return 1;
}
#define ELF_CORE_COPY_XFPREGS 1
static inline int
elf_core_copy_task_xfpregs(struct task_struct *tsk, elf_fpxregset_t *xfpu)
{
struct ia32_user_fxsr_struct *fpxstate = (void*) xfpu;
if (!tsk->used_math)
return 0;
save_ia32_fpxstate(tsk, fpxstate);
return 1;
}
#endif /* _ELFCORE32_H_ */
...@@ -295,7 +295,6 @@ struct old_linux32_dirent { ...@@ -295,7 +295,6 @@ struct old_linux32_dirent {
#define IA32_TSS_OFFSET (IA32_PAGE_OFFSET + PAGE_SIZE) #define IA32_TSS_OFFSET (IA32_PAGE_OFFSET + PAGE_SIZE)
#define IA32_LDT_OFFSET (IA32_PAGE_OFFSET + 2*PAGE_SIZE) #define IA32_LDT_OFFSET (IA32_PAGE_OFFSET + 2*PAGE_SIZE)
#define USE_ELF_CORE_DUMP
#define ELF_EXEC_PAGESIZE IA32_PAGE_SIZE #define ELF_EXEC_PAGESIZE IA32_PAGE_SIZE
/* /*
...@@ -312,20 +311,6 @@ void ia64_elf32_init(struct pt_regs *regs); ...@@ -312,20 +311,6 @@ void ia64_elf32_init(struct pt_regs *regs);
#define elf_addr_t u32 #define elf_addr_t u32
/* ELF register definitions. This is needed for core dump support. */
#define ELF_NGREG 128 /* XXX fix me */
#define ELF_NFPREG 128 /* XXX fix me */
typedef unsigned long elf_greg_t;
typedef elf_greg_t elf_gregset_t[ELF_NGREG];
typedef struct {
unsigned long w0;
unsigned long w1;
} elf_fpreg_t;
typedef elf_fpreg_t elf_fpregset_t[ELF_NFPREG];
/* This macro yields a bitmask that programs can use to figure out /* This macro yields a bitmask that programs can use to figure out
what instruction set this CPU supports. */ what instruction set this CPU supports. */
#define ELF_HWCAP 0 #define ELF_HWCAP 0
...@@ -472,6 +457,23 @@ extern void ia32_load_segment_descriptors (struct task_struct *task); ...@@ -472,6 +457,23 @@ extern void ia32_load_segment_descriptors (struct task_struct *task);
asm volatile ("ldf.fill f6=[%2];; stfe [%1]=f6" : "=f"(f6): "r"(dst), "r"(src) : "memory"); \ asm volatile ("ldf.fill f6=[%2];; stfe [%1]=f6" : "=f"(f6): "r"(dst), "r"(src) : "memory"); \
} while(0) } while(0)
struct user_regs_struct32 {
__u32 ebx, ecx, edx, esi, edi, ebp, eax;
unsigned short ds, __ds, es, __es;
unsigned short fs, __fs, gs, __gs;
__u32 orig_eax, eip;
unsigned short cs, __cs;
__u32 eflags, esp;
unsigned short ss, __ss;
};
/* Prototypes for use in elfcore32.h */
int save_ia32_fpstate (struct task_struct *tsk,
struct ia32_user_i387_struct *save);
int save_ia32_fpxstate (struct task_struct *tsk,
struct ia32_user_fxsr_struct *save);
#endif /* !CONFIG_IA32_SUPPORT */ #endif /* !CONFIG_IA32_SUPPORT */
#endif /* _ASM_IA64_IA32_H */ #endif /* _ASM_IA64_IA32_H */
...@@ -1866,7 +1866,7 @@ get_fpreg (int regno, struct _fpreg_ia32 *reg, struct pt_regs *ptp, struct switc ...@@ -1866,7 +1866,7 @@ get_fpreg (int regno, struct _fpreg_ia32 *reg, struct pt_regs *ptp, struct switc
return; return;
} }
static int int
save_ia32_fpstate (struct task_struct *tsk, struct ia32_user_i387_struct *save) save_ia32_fpstate (struct task_struct *tsk, struct ia32_user_i387_struct *save)
{ {
struct switch_stack *swp; struct switch_stack *swp;
...@@ -1928,7 +1928,7 @@ restore_ia32_fpstate (struct task_struct *tsk, struct ia32_user_i387_struct *sav ...@@ -1928,7 +1928,7 @@ restore_ia32_fpstate (struct task_struct *tsk, struct ia32_user_i387_struct *sav
return 0; return 0;
} }
static int int
save_ia32_fpxstate (struct task_struct *tsk, struct ia32_user_fxsr_struct *save) save_ia32_fpxstate (struct task_struct *tsk, struct ia32_user_fxsr_struct *save)
{ {
struct switch_stack *swp; struct switch_stack *swp;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment