This is the mail archive of the binutils@sourceware.cygnus.com mailing list for the binutils project.


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

Patch: Add support for Linux x86 SSE core files



This patch allows GDB to access x86 SSE registers as dumped in a core
file under Linux.

At the moment, the Linux kernel does not include the SSE registers at
all in core files.  I have published kernel patches to dump them in
the way expected by the patch below, but it remains to be seen whether
my kernel patch will be integrated into the main Linux distribution.
If it is not accepted, or the Linux developers decide to dump the SSE
registers in a note with a different name or type number, then this
patch will be harmless, but useless.


1999-11-04  Jim Blandy  <jimb@zenia.red-bean.com>

	Add support for x86 SSE registers in ELF core files.
	* elf.c (elfcore_make_note_pseudosection): New function.
	(elfcore_grok_prfpreg): Use it.
	(elfcore_grok_prxfpreg): New function.
	(elfcore_grok_note): Recognize Linux NT_PRXFPREG notes.

Index: bfd/elf.c
===================================================================
RCS file: /cvs/cvsfiles/devo/bfd/elf.c,v
retrieving revision 1.241.10.1
retrieving revision 1.241.10.2
diff -c -r1.241.10.1 -r1.241.10.2
*** elf.c	1999/10/29 22:37:11	1.241.10.1
--- elf.c	1999/11/04 07:02:36	1.241.10.2
***************
*** 4987,5014 ****
  #endif /* defined (HAVE_PRSTATUS_T) */
  
  
! /* There isn't a consistent prfpregset_t across platforms,
!    but it doesn't matter, because we don't have to pick this
!    data structure apart. */
  
  static boolean
! elfcore_grok_prfpreg (abfd, note)
       bfd* abfd;
       Elf_Internal_Note* note;
  {
    char buf[100];
!   char* name;
    asection* sect;
  
!   /* Make a ".reg2/999" section. */
  
!   sprintf (buf, ".reg2/%d", elfcore_make_pid (abfd));
!   name = bfd_alloc (abfd, strlen (buf) + 1);
!   if (name == NULL)
      return false;
!   strcpy (name, buf);
  
!   sect = bfd_make_section (abfd, name);
    if (sect == NULL)
      return false;
    sect->_raw_size = note->descsz;
--- 4987,5019 ----
  #endif /* defined (HAVE_PRSTATUS_T) */
  
  
! /* Create a pseudosection containing the exact contents of NOTE.  This
!    actually creates up to two pseudosections:
!    - For the single-threaded case, a section named NAME, unless
!      such a section already exists.
!    - For the multi-threaded case, a section named "NAME/PID", where
!      PID is elfcore_make_pid (abfd).
!    Both pseudosections have identical contents: the contents of NOTE.  */
  
  static boolean
! elfcore_make_note_pseudosection (abfd, name, note)
       bfd* abfd;
+      char *name;
       Elf_Internal_Note* note;
  {
    char buf[100];
!   char *threaded_name;
    asection* sect;
  
!   /* Build the section name.  */
  
!   sprintf (buf, "%s/%d", name, elfcore_make_pid (abfd));
!   threaded_name = bfd_alloc (abfd, strlen (buf) + 1);
!   if (threaded_name == NULL)
      return false;
!   strcpy (threaded_name, buf);
  
!   sect = bfd_make_section (abfd, threaded_name);
    if (sect == NULL)
      return false;
    sect->_raw_size = note->descsz;
***************
*** 5016,5027 ****
    sect->flags = SEC_HAS_CONTENTS;
    sect->alignment_power = 2;
  
!   if (! elfcore_maybe_make_sect (abfd, ".reg2", sect))
      return false;
  
    return true;
  }
  
  #if defined (HAVE_PRPSINFO_T)
  # define elfcore_psinfo_t prpsinfo_t
  #endif
--- 5021,5057 ----
    sect->flags = SEC_HAS_CONTENTS;
    sect->alignment_power = 2;
  
!   if (! elfcore_maybe_make_sect (abfd, name, sect))
      return false;
  
    return true;
  }
  
+ 
+ /* There isn't a consistent prfpregset_t across platforms,
+    but it doesn't matter, because we don't have to pick this
+    data structure apart. */
+ static boolean
+ elfcore_grok_prfpreg (abfd, note)
+      bfd* abfd;
+      Elf_Internal_Note* note;
+ {
+   return elfcore_make_note_pseudosection (abfd, ".reg2", note);
+ }
+ 
+ 
+ /* Linux dumps the Intel SSE regs in a note named "LINUX" with a note
+    type of 5 (NT_PRXFPREG).  Just include the whole note's contents
+    literally.  */
+ static boolean
+ elfcore_grok_prxfpreg (abfd, note)
+      bfd* abfd;
+      Elf_Internal_Note* note;
+ {
+   return elfcore_make_note_pseudosection (abfd, ".reg-xfp", note);
+ }
+ 
+ 
  #if defined (HAVE_PRPSINFO_T)
  # define elfcore_psinfo_t prpsinfo_t
  #endif
***************
*** 5231,5236 ****
--- 5261,5273 ----
  
      case NT_FPREGSET:		/* FIXME: rename to NT_PRFPREG */
        return elfcore_grok_prfpreg (abfd, note);
+ 
+     case NT_PRXFPREG:		/* Linux SSE extension */
+       if (note->namesz == 5
+ 	  && ! strcmp (note->namedata, "LINUX"))
+ 	return elfcore_grok_prxfpreg (abfd, note);
+       else
+ 	return true;
  
  #if defined (HAVE_PRPSINFO_T) || defined (HAVE_PSINFO_T)
      case NT_PRPSINFO:

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