+2001-12-27 Mark Kettenis <kettenis@gnu.org>
+
+ * config/i386/tm-i386.h (FP7_REGNUM, FIRST_FPU_CTRL_REGNUM,
+ FCTRL_REGNUM, FPC_REGNUM, FSTAT_REGNUM, FTAG_REGNUM, FCS_REGNUM,
+ FCOFF_REGNUM, FDS_REGNUM, FDOFF_REGNUM, FOP_REGNUM,
+ LAST_FPU_CTRL_REGNUM, XMM0_REGNUM, XMM7_REGNUM, MXCSR_REGNUM,
+ IS_FP_REGNUM, IS_SSE_REGNUM): Removed.
+ (FP0_REGNUM): Define conditionally depending on HAVE_I387_REGS.
+ (SIZEOF_FPU_CTRL_REGS): Hardcode value.
+ * i386-tdep.h (struct gdbarch_tdep): Change such that it contains
+ a single member `num_xmm_regs'.
+ (FPC_REGNUM): New macro.
+ (FIRST_FPU_REGNUM, LAST_FPU_REGNUM, FISRT_XMM_REGNUM,
+ LAST_XMM_REGNUM, MXCSR_REGNUM, FIRST_FPU_CTRL_REGNUM,
+ LAST_FPU_CTRL_REGNUM): Removed.
+ (FCTRL_REGNUM, FSTAT_REGNUM, FTAG_REGNUM, FOP_REGNUM, XMM0_REGNUM,
+ MXCSR_REGNUM): Define unconditionally. Change macros to match the
+ comment describing the register layout.
+ (FISEG_REGNUM, FIOFF_REGNUM, FOSEG_REGNUM, FOOFF_REGNUM): New macros.
+ (FP_REGNUM_P, FPC_REGNUM_P, SSE_REGNUM_P): New macros.
+ (IS_FP_REGNUM, IS_FPU_CTRL_REGNUM, IS_SSE_REGNUM): Make obsolete,
+ unconditionally define in terms of FP_REGNUM_P, FPC_REGNUM_P and
+ SSE_REGNUM_P).
+ (FCS_REGNUM, FCOFF_REGNUM, FDS_REGNUM, FDOFF_REGNUM): Make
+ obsolete, unconditionally define in terms of FISEG_REGNUM,
+ FIOFF_REGNUM, FOSEG_REGNUM, FOOFF_REGNUM.
+ * i386-tdep.c (i386_gdbarch_init): Initialize `num_xmm_regs'
+ member of `struct gdbarch_tdep'.
+ * x86-64-tdep.c (i386_gdbarch_init): Change initialization of
+ `struct gdbarch_tdep'.
+ * i387-nat.c (FCS_REGNUM, FCOFF_REGNUM, FDS_REGNUM, FDOFF_REGNUM):
+ Replace with FISEG_REGNUM, FIOFF_REGNUM, FOSEG_REGNUM and
+ FOOFF_REGNUM. Use FPC_REGNUM instead of FIRST_FPU_CTRL_REGNUM.
+ Use XMM0_REGNUM instead of LAST_FPU_CTRL_REGNUM.
+
2001-12-25 Andrew Cagney <ac131313@redhat.com>
* cli/cli-script.c (execute_control_command): Replace value_ptr
#define PC_REGNUM 8 /* (eip) Contains program counter */
#define PS_REGNUM 9 /* (ps) Contains processor status */
-/* These registers are present only if HAVE_I387_REGS is #defined.
- We promise that FP0 .. FP7 will always be consecutive register numbers. */
-#define FP0_REGNUM 16 /* first FPU floating-point register */
-#define FP7_REGNUM 23 /* last FPU floating-point register */
-
-/* All of these control registers (except for FCOFF and FDOFF) are
- sixteen bits long (at most) in the FPU, but are zero-extended to
- thirty-two bits in GDB's register file. This makes it easier to
- compute the size of the control register file, and somewhat easier
- to convert to and from the FSAVE instruction's 32-bit format. */
-#define FIRST_FPU_CTRL_REGNUM 24
-#define FCTRL_REGNUM 24 /* FPU control word */
-#define FPC_REGNUM 24 /* old name for FCTRL_REGNUM */
-#define FSTAT_REGNUM 25 /* FPU status word */
-#define FTAG_REGNUM 26 /* FPU register tag word */
-#define FCS_REGNUM 27 /* FPU instruction's code segment selector
- 16 bits, called "FPU Instruction Pointer
- Selector" in the x86 manuals */
-#define FCOFF_REGNUM 28 /* FPU instruction's offset within segment
- ("Fpu Code OFFset") */
-#define FDS_REGNUM 29 /* FPU operand's data segment */
-#define FDOFF_REGNUM 30 /* FPU operand's offset within segment */
-#define FOP_REGNUM 31 /* FPU opcode, bottom eleven bits */
-#define LAST_FPU_CTRL_REGNUM 31
-
-/* These registers are present only if HAVE_SSE_REGS is #defined.
- We promise that XMM0 .. XMM7 will always have consecutive reg numbers. */
-#define XMM0_REGNUM 32 /* first SSE data register */
-#define XMM7_REGNUM 39 /* last SSE data register */
-#define MXCSR_REGNUM 40 /* Streaming SIMD Extension control/status */
-
-#define IS_FP_REGNUM(n) (FP0_REGNUM <= (n) && (n) <= FP7_REGNUM)
-#define IS_SSE_REGNUM(n) (XMM0_REGNUM <= (n) && (n) <= XMM7_REGNUM)
+/* First FPU data register. */
+#ifdef HAVE_I387_REGS
+#define FP0_REGNUM 16
+#else
+#define FP0_REGNUM 0
+#endif
/* Return the name of register REG. */
yields REGISTER_BYTES. */
#define SIZEOF_GREGS (NUM_GREGS * 4)
#define SIZEOF_FPU_REGS (8 * 10)
-#define SIZEOF_FPU_CTRL_REGS \
- ((LAST_FPU_CTRL_REGNUM - FIRST_FPU_CTRL_REGNUM + 1) * 4)
+#define SIZEOF_FPU_CTRL_REGS (8 * 4)
#define SIZEOF_SSE_REGS (8 * 16 + 4)
tdep = XMALLOC (struct gdbarch_tdep);
gdbarch = gdbarch_alloc (&info, tdep);
+ /* FIXME: kettenis/2001-11-24: Although not all IA-32 processors
+ have the SSE registers, it's easier to set the default to 8. */
+ tdep->num_xmm_regs = 8;
+
set_gdbarch_use_generic_dummy_frames (gdbarch, 0);
/* Call dummy code. */
#ifndef I386_TDEP_H
#define I386_TDEP_H
+/* GDB's i386 target supports both the 32-bit Intel Architecture
+ (IA-32) and the 64-bit AMD x86-64 architecture. Internally it uses
+ a similar register layout for both.
+
+ - General purpose registers
+ - FPU data registers
+ - FPU control registers
+ - SSE data registers
+ - SSE control register
+
+ The general purpose registers for the x86-64 architecture are quite
+ different from IA-32. Therefore, the FP0_REGNUM target macro
+ determines the register number at which the FPU data registers
+ start. The number of FPU data and control registers is the same
+ for both architectures. The number of SSE registers however,
+ differs and is determined by the num_xmm_regs member of `struct
+ gdbarch_tdep'. */
+
+/* i386 architecture specific information. */
+struct gdbarch_tdep
+{
+ /* Number of SSE registers. */
+ int num_xmm_regs;
+};
+
+/* Floating-point registers. */
+
#define FPU_REG_RAW_SIZE 10
-#if !defined (XMM0_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define XMM0_REGNUM FIRST_XMM_REGNUM
-#endif
-#if !defined (FIRST_FPU_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define FIRST_FPU_REGNUM FP0_REGNUM
-#endif
-#if !defined (LAST_FPU_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define LAST_FPU_REGNUM (gdbarch_tdep (current_gdbarch)->last_fpu_regnum)
-#endif
-#if !defined (FIRST_XMM_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define FIRST_XMM_REGNUM (gdbarch_tdep (current_gdbarch)->first_xmm_regnum)
-#endif
-#if !defined (LAST_XMM_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define LAST_XMM_REGNUM (gdbarch_tdep (current_gdbarch)->last_xmm_regnum)
-#endif
-#if !defined (MXCSR_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define MXCSR_REGNUM (gdbarch_tdep (current_gdbarch)->mxcsr_regnum)
-#endif
-#if !defined (FIRST_FPU_CTRL_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define FIRST_FPU_CTRL_REGNUM (gdbarch_tdep (current_gdbarch)->first_fpu_ctrl_regnum)
-#endif
-#if !defined (LAST_FPU_CTRL_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define LAST_FPU_CTRL_REGNUM (FIRST_FPU_CTRL_REGNUM + 7)
-#endif
-
-/* All of these control registers (except for FCOFF and FDOFF) are
- sixteen bits long (at most) in the FPU, but are zero-extended to
- thirty-two bits in GDB's register file. This makes it easier to
- compute the size of the control register file, and somewhat easier
- to convert to and from the FSAVE instruction's 32-bit format. */
+/* All FPU control regusters (except for FIOFF and FOOFF) are 16-bit
+ (at most) in the FPU, but are zero-extended to 32 bits in GDB's
+ register cache. */
+
+/* "Generic" floating point control register. */
+#define FPC_REGNUM (FP0_REGNUM + 8)
+
/* FPU control word. */
-#if !defined (FCTRL_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define FCTRL_REGNUM (FIRST_FPU_CTRL_REGNUM)
-#endif
+#define FCTRL_REGNUM FPC_REGNUM
+
/* FPU status word. */
-#if !defined (FSTAT_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define FSTAT_REGNUM (FIRST_FPU_CTRL_REGNUM + 1)
-#endif
+#define FSTAT_REGNUM (FPC_REGNUM + 1)
+
/* FPU register tag word. */
-#if !defined (FTAG_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define FTAG_REGNUM (FIRST_FPU_CTRL_REGNUM + 2)
-#endif
-/* FPU instruction's code segment selector 16 bits, called "FPU Instruction
- Pointer Selector" in the x86 manuals. */
-#if !defined (FCS_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define FCS_REGNUM (FIRST_FPU_CTRL_REGNUM + 3)
-#endif
-/* FPU instruction's offset within segment ("Fpu Code OFFset"). */
-#if !defined (FCOFF_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define FCOFF_REGNUM (FIRST_FPU_CTRL_REGNUM + 4)
-#endif
+#define FTAG_REGNUM (FPC_REGNUM + 2)
+
+/* FPU instruction's code segment selector, called "FPU Instruction
+ Pointer Selector" in the IA-32 manuals. */
+#define FISEG_REGNUM (FPC_REGNUM + 3)
+
+/* FPU instruction's offset within segment. */
+#define FIOFF_REGNUM (FPC_REGNUM + 4)
+
/* FPU operand's data segment. */
-#if !defined (FDS_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define FDS_REGNUM (FIRST_FPU_CTRL_REGNUM + 5)
-#endif
-/* FPU operand's offset within segment. */
-#if !defined (FDOFF_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define FDOFF_REGNUM (FIRST_FPU_CTRL_REGNUM + 6)
-#endif
+#define FOSEG_REGNUM (FPC_REGNUM + 5)
+
+/* FPU operand's offset within segment */
+#define FOOFF_REGNUM (FPC_REGNUM + 6)
+
/* FPU opcode, bottom eleven bits. */
-#if !defined (FOP_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define FOP_REGNUM (FIRST_FPU_CTRL_REGNUM + 7)
-#endif
+#define FOP_REGNUM (FPC_REGNUM + 7)
-/* i386 architecture specific information. */
-struct gdbarch_tdep
-{
- int last_fpu_regnum;
- int first_xmm_regnum;
- int last_xmm_regnum;
- int mxcsr_regnum; /* Streaming SIMD Extension control/status. */
- int first_fpu_ctrl_regnum;
-};
+/* Return non-zero if N corresponds to a FPU data registers. */
+#define FP_REGNUM_P(n) (FP0_REGNUM <= (n) && (n) < FPC_REGNUM)
+
+/* Return non-zero if N corresponds to a FPU control register. */
+#define FPC_REGNUM_P(n) (FPC_REGNUM <= (n) && (n) < XMM0_REGNUM)
+
+/* SSE registers. */
+
+/* First SSE data register. */
+#define XMM0_REGNUM (FPC_REGNUM + 8)
+
+/* SSE control/status register. */
+#define MXCSR_REGNUM \
+ (XMM0_REGNUM + gdbarch_tdep (current_gdbarch)->num_xmm_regs)
+
+/* Return non-zero if N corresponds to a SSE data register. */
+#define SSE_REGNUM_P(n) (XMM0_REGNUM <= (n) && (n) < MXCSR_REGNUM)
+
+/* FIXME: kettenis/2001-11-24: Obsolete macro's. */
+#define FCS_REGNUM FISEG_REGNUM
+#define FCOFF_REGNUM FIOFF_REGNUM
+#define FDS_REGNUM FOSEG_REGNUM
+#define FDOFF_REGNUM FOOFF_REGNUM
+#define IS_FP_REGNUM(n) FP_REGNUM_P (n)
+#define IS_FPU_CTRL_REGNUM(n) FPC_REGNUM_P (n)
+#define IS_SSE_REGNUM(n) SSE_REGNUM_P (n)
-#if !defined (IS_FP_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define IS_FP_REGNUM(n) (FIRST_FPU_REGNUM <= (n) && (n) <= LAST_FPU_REGNUM)
-#endif
-#if !defined (IS_FPU_CTRL_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define IS_FPU_CTRL_REGNUM(n) (FIRST_FPU_CTRL_REGNUM <= (n) && (n) <= LAST_FPU_CTRL_REGNUM)
-#endif
-#if !defined (IS_SSE_REGNUM) || (GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL)
-#define IS_SSE_REGNUM(n) (FIRST_XMM_REGNUM <= (n) && (n) <= LAST_XMM_REGNUM)
-#endif
-
-#endif
+#endif /* i386-tdep.h */
0, /* FCTRL_REGNUM (16 bits). */
4, /* FSTAT_REGNUM (16 bits). */
8, /* FTAG_REGNUM (16 bits). */
- 16, /* FCS_REGNUM (16 bits). */
- 12, /* FCOFF_REGNUM. */
- 24, /* FDS_REGNUM. */
- 20, /* FDOFF_REGNUM. */
+ 16, /* FISEG_REGNUM (16 bits). */
+ 12, /* FIOFF_REGNUM. */
+ 24, /* FOSEG_REGNUM. */
+ 20, /* FOOFF_REGNUM. */
18 /* FOP_REGNUM (bottom 11 bits). */
};
{
/* Most of the FPU control registers occupy only 16 bits in
the fsave area. Give those a special treatment. */
- if (regnum >= FIRST_FPU_CTRL_REGNUM
- && regnum != FCOFF_REGNUM && regnum != FDOFF_REGNUM)
+ if (regnum >= FPC_REGNUM
+ && regnum != FIOFF_REGNUM && regnum != FOOFF_REGNUM)
{
unsigned int val = *(unsigned short *) (FSAVE_ADDR (fsave, regnum));
{
int i;
- for (i = FP0_REGNUM; i <= LAST_FPU_CTRL_REGNUM; i++)
+ for (i = FP0_REGNUM; i < XMM0_REGNUM; i++)
i387_supply_register (i, fsave);
}
{
int i;
- for (i = FP0_REGNUM; i <= LAST_FPU_CTRL_REGNUM; i++)
+ for (i = FP0_REGNUM; i < XMM0_REGNUM; i++)
if (regnum == -1 || regnum == i)
{
/* Most of the FPU control registers occupy only 16 bits in
the fsave area. Give those a special treatment. */
- if (i >= FIRST_FPU_CTRL_REGNUM
- && i != FCOFF_REGNUM && i != FDOFF_REGNUM)
+ if (i >= FPC_REGNUM
+ && i != FIOFF_REGNUM && i != FOOFF_REGNUM)
{
if (i == FOP_REGNUM)
{
0, /* FCTRL_REGNUM (16 bits). */
2, /* FSTAT_REGNUM (16 bits). */
4, /* FTAG_REGNUM (16 bits). */
- 12, /* FCS_REGNUM (16 bits). */
- 8, /* FCOFF_REGNUM. */
- 20, /* FDS_REGNUM (16 bits). */
- 16, /* FDOFF_REGNUM. */
+ 12, /* FISEG_REGNUM (16 bits). */
+ 8, /* FIOFF_REGNUM. */
+ 20, /* FOSEG_REGNUM (16 bits). */
+ 16, /* FOOFF_REGNUM. */
6, /* FOP_REGNUM (bottom 11 bits). */
160, /* XMM0_REGNUM through ... */
176,
{
/* Most of the FPU control registers occupy only 16 bits in
the fxsave area. Give those a special treatment. */
- if (i >= FIRST_FPU_CTRL_REGNUM && i < XMM0_REGNUM
- && i != FCOFF_REGNUM && i != FDOFF_REGNUM)
+ if (i >= FPC_REGNUM && i < XMM0_REGNUM
+ && i != FIOFF_REGNUM && i != FOOFF_REGNUM)
{
unsigned long val = *(unsigned short *) (FXSAVE_ADDR (fxsave, i));
{
/* Most of the FPU control registers occupy only 16 bits in
the fxsave area. Give those a special treatment. */
- if (i >= FIRST_FPU_CTRL_REGNUM && i < XMM0_REGNUM
- && i != FCOFF_REGNUM && i != FDOFF_REGNUM)
+ if (i >= FPC_REGNUM && i < XMM0_REGNUM
+ && i != FIOFF_REGNUM && i != FDOFF_REGNUM)
{
if (i == FOP_REGNUM)
{
{
case bfd_mach_x86_64:
case bfd_mach_x86_64_intel_syntax:
- tdep->last_fpu_regnum = 25;
- tdep->first_xmm_regnum = 34;
- tdep->last_xmm_regnum = 49;
- tdep->mxcsr_regnum = 50;
- tdep->first_fpu_ctrl_regnum = 26;
+ tdep->num_xmm_regs = 16;
break;
case bfd_mach_i386_i386:
case bfd_mach_i386_i8086: