This is the mail archive of the libc-alpha@sourceware.org mailing list for the glibc 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]

Re: PATCH: Add x32 arch_prctl support


> Change it to unsigned long long int makes it impossible
> to get address as pointer since it will override memory on stack.

There is some misunderstanding.  What I suggested would not make any
difference to the compiled code of arch_prctl.

> I am trying to limit my x32 GDB change as small as possible:
> 
> hjl@gnu-6 gdb]$ grep PTRACE_ARCH_PRCTL  amd64-linux-nat.c
> #ifndef PTRACE_ARCH_PRCTL
> #define PTRACE_ARCH_PRCTL      30
> 	  if (ptrace (PTRACE_ARCH_PRCTL, lwpid, base, ARCH_GET_FS) == 0)
> 	  if (ptrace (PTRACE_ARCH_PRCTL, lwpid, base, ARCH_GET_GS) == 0)
> [hjl@gnu-6 gdb]$
> 
> Without PTRACE_ARCH_PRCTL means I have to write a whole
> new patch to use the new interface.   It will make it harder to enable
> x32 in GDB.

Sometimes the least change everywhere is not the cleanest answer anywhere.

diff --git a/gdb/amd64-linux-nat.c b/gdb/amd64-linux-nat.c
index 5ebba3a..aaa1e62 100644
--- a/gdb/amd64-linux-nat.c
+++ b/gdb/amd64-linux-nat.c
@@ -479,11 +479,41 @@ ps_get_thread_area (const struct ps_prochandle *ph,
       switch (idx)
 	{
 	case FS:
-	  if (ptrace (PTRACE_ARCH_PRCTL, lwpid, base, ARCH_GET_FS) == 0)
+	  if (sizeof(unsigned long) == 4)
+	    {
+	      /* PTRACE_ARCH_PRCTL is obsolete since 2.6.25, where the
+		 fs_base and gs_base fields of user_regs_struct can be
+		 used directly.  We use it only to support older
+		 kernels.  But x32 kernels do not support it, so we
+		 don't try to use it.  There were no x32 kernels so old
+		 that fs_base wasn't usable.  */
+	      unsigned long fs;
+	      errno = 0;
+	      fs = ptrace (PTRACE_PEEKUSR, lwpid,
+			   offsetof (struct user_regs_struct, fs_base), 0);
+	      if (errno == 0)
+		{
+		  *base = fs;
+		  return PS_OK;
+		}
+	    }
+	  else if (ptrace (PTRACE_ARCH_PRCTL, lwpid, base, ARCH_GET_FS) == 0)
 	    return PS_OK;
 	  break;
 	case GS:
-	  if (ptrace (PTRACE_ARCH_PRCTL, lwpid, base, ARCH_GET_GS) == 0)
+	  if (sizeof(unsigned long) == 4)
+	    {
+	      unsigned long gs;
+	      errno = 0;
+	      gs = ptrace (PTRACE_PEEKUSR, lwpid,
+			   offsetof (struct user_regs_struct, gs_base), 0);
+	      if (errno == 0)
+		{
+		  *base = gs;
+		  return PS_OK;
+		}
+	    }
+	  else if (ptrace (PTRACE_ARCH_PRCTL, lwpid, base, ARCH_GET_GS) == 0)
 	    return PS_OK;
 	  break;
 	default:                   /* Should not happen.  */


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