This is the mail archive of the gdb-patches@sources.redhat.com mailing list for the GDB project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[PATCH] i386 register shuffle


This is a first step towards cleaning up the register numbering scheme
used for the i386.  All possible numberings are now parametrized by
FP0_REGNUM and gdbarch_tdep (current_gdbarch)->num_xmm_regs.  This
patch makes i386-tdep.h the definitive source for information about
the register layout.

Mark

Index: ChangeLog
from  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.

Index: i386-tdep.h
===================================================================
RCS file: /cvs/src/src/gdb/i386-tdep.h,v
retrieving revision 1.3
diff -u -p -r1.3 i386-tdep.h
--- i386-tdep.h 2001/11/12 22:27:35 1.3
+++ i386-tdep.h 2001/12/27 15:14:13
@@ -22,90 +22,92 @@
 #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
+
+/* 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)
 
-#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.  */
 /* 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)
 
-#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
+/* 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)
 
-#endif
+#endif /* i386-tdep.h */
Index: i386-tdep.c
===================================================================
RCS file: /cvs/src/src/gdb/i386-tdep.c,v
retrieving revision 1.47
diff -u -p -r1.47 i386-tdep.c
--- i386-tdep.c 2001/12/02 18:29:08 1.47
+++ i386-tdep.c 2001/12/27 15:14:14
@@ -1218,6 +1218,10 @@ i386_gdbarch_init (struct gdbarch_info i
   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.  */
Index: x86-64-tdep.c
===================================================================
RCS file: /cvs/src/src/gdb/x86-64-tdep.c,v
retrieving revision 1.5
diff -u -p -r1.5 x86-64-tdep.c
--- x86-64-tdep.c 2001/12/11 22:16:48 1.5
+++ x86-64-tdep.c 2001/12/27 15:14:14
@@ -817,11 +817,7 @@ i386_gdbarch_init (struct gdbarch_info i
     {
     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:
Index: i387-nat.c
===================================================================
RCS file: /cvs/src/src/gdb/i387-nat.c,v
retrieving revision 1.8
diff -u -p -r1.8 i387-nat.c
--- i387-nat.c 2001/12/13 17:34:52 1.8
+++ i387-nat.c 2001/12/27 15:14:14
@@ -49,10 +49,10 @@ static int fsave_offset[] =
   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).  */
 };
 
@@ -68,8 +68,8 @@ i387_supply_register (int regnum, char *
 {
   /* 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));
 
@@ -94,7 +94,7 @@ i387_supply_fsave (char *fsave)
 {
   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);
 }
 
@@ -108,13 +108,13 @@ i387_fill_fsave (char *fsave, int regnum
 {
   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)
 	      {
@@ -154,10 +154,10 @@ static int fxsave_offset[] =
   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,
@@ -189,8 +189,8 @@ i387_supply_fxsave (char *fxsave)
     {
       /* 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));
 
@@ -252,8 +252,8 @@ i387_fill_fxsave (char *fxsave, int regn
       {
 	/* 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)
 	      {
Index: config/i386/tm-i386.h
===================================================================
RCS file: /cvs/src/src/gdb/config/i386/tm-i386.h,v
retrieving revision 1.26
diff -u -p -r1.26 tm-i386.h
--- config/i386/tm-i386.h 2001/12/15 16:53:23 1.26
+++ config/i386/tm-i386.h 2001/12/27 15:14:14
@@ -140,40 +140,13 @@ extern CORE_ADDR i386_saved_pc_after_cal
 #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 */
+/* First FPU data register.  */
+#ifdef HAVE_I387_REGS
+#define FP0_REGNUM 16
+#else
+#define FP0_REGNUM 0
+#endif
 
-#define IS_FP_REGNUM(n) (FP0_REGNUM <= (n) && (n) <= FP7_REGNUM)
-#define IS_SSE_REGNUM(n) (XMM0_REGNUM <= (n) && (n) <= XMM7_REGNUM)
-
 /* Return the name of register REG.  */
 
 #define REGISTER_NAME(reg) i386_register_name ((reg))
@@ -200,8 +173,7 @@ extern int i386_dwarf_reg_to_regnum (int
    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)
 
 


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]