This is the mail archive of the gdb-patches@sourceware.org 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 4/7 v3] Allow target to decide where to map jump-pad.


This patch adds an IPA function, jump_pad_area_hint, for giving a
hint where to map jump pad buffer, becaus

gdb/gdbserver/ChangeLog

2015-03-30  Wei-cheng Wang  <cole945@gmail.com>

	* tracepoint.c (initialize_tracepoint): Call jump_pad_area_hint
        to get where to map gdb_jump_pad_buffer.  Remove MAP_FIXED.
	* tracepoint.h (jump_pad_area_hint): Add declaration.
	* linux-amd64-ipa.c (jump_pad_area_hint): New function.
	* linux-i386-ipa.c (jump_pad_area_hint): New function.
	* linux-ppc-ipa.c (jump_pad_area_hint): New function.
---
 gdb/gdbserver/linux-amd64-ipa.c | 10 ++++++++++
 gdb/gdbserver/linux-i386-ipa.c  | 10 ++++++++++
 gdb/gdbserver/linux-ppc-ipa.c   | 22 ++++++++++++++++++++++
 gdb/gdbserver/tracepoint.c      |  7 +++----
 gdb/gdbserver/tracepoint.h      |  3 +++
 5 files changed, 48 insertions(+), 4 deletions(-)

diff --git a/gdb/gdbserver/linux-amd64-ipa.c b/gdb/gdbserver/linux-amd64-ipa.c
index a6dfb03..65cd748 100644
--- a/gdb/gdbserver/linux-amd64-ipa.c
+++ b/gdb/gdbserver/linux-amd64-ipa.c
@@ -77,6 +77,16 @@ gdb_agent_get_raw_reg (const unsigned char *raw_regs, int regnum)
   return *(ULONGEST *) (raw_regs + x86_64_ft_collect_regmap[regnum]);
 }
 
+/* See tracepoint.h.  */
+
+uintptr_t
+jump_pad_area_hint (void)
+{
+  /* Allocate scratch buffer aligned on a page boundary, at a low
+     address (close to the main executable's code).  */
+  return sysconf (_SC_PAGE_SIZE);
+}
+
 #ifdef HAVE_UST
 
 #include <ust/processor.h>
diff --git a/gdb/gdbserver/linux-i386-ipa.c b/gdb/gdbserver/linux-i386-ipa.c
index eb30dcd..dc0dfaf 100644
--- a/gdb/gdbserver/linux-i386-ipa.c
+++ b/gdb/gdbserver/linux-i386-ipa.c
@@ -114,6 +114,16 @@ gdb_agent_get_raw_reg (const unsigned char *raw_regs, int regnum)
     return *(int *) (raw_regs + i386_ft_collect_regmap[regnum]);
 }
 
+/* See tracepoint.h.  */
+
+uintptr_t
+jump_pad_area_hint (void)
+{
+  /* Allocate scratch buffer aligned on a page boundary, at a low
+     address (close to the main executable's code).  */
+  return sysconf (_SC_PAGE_SIZE);
+}
+
 #ifdef HAVE_UST
 
 #include <ust/processor.h>
diff --git a/gdb/gdbserver/linux-ppc-ipa.c b/gdb/gdbserver/linux-ppc-ipa.c
index 73d8899..b46fb3c 100644
--- a/gdb/gdbserver/linux-ppc-ipa.c
+++ b/gdb/gdbserver/linux-ppc-ipa.c
@@ -21,6 +21,8 @@
 #include "server.h"
 #include "tracepoint.h"
 
+#include <sys/auxv.h>
+
 #if defined __PPC64__
 void init_registers_powerpc_64l (void);
 extern const struct target_desc *tdesc_powerpc_64l;
@@ -105,6 +107,26 @@ gdb_agent_get_raw_reg (const unsigned char *raw_regs, int regnum)
 			+ ppc_ft_collect_regmap[regnum] * REGSZ);
 }
 
+/* See tracepoint.h.  */
+
+uintptr_t
+jump_pad_area_hint (void)
+{
+  /* Use AT_PHDR address to guess where the main executable is mapped,
+     and try to map the jump pad before it.  The jump pad should be
+     closed enough to the executable for unconditional branch (+/- 32MB). */
+
+  uintptr_t base = getauxval (AT_PHDR);
+  uintptr_t pagesz = sysconf (_SC_PAGE_SIZE);
+  uintptr_t hint = (base & ~(pagesz - 1)) - 30 * pagesz;
+
+  /* Is wrap around?  */
+  if (hint > base)
+    hint = pagesz;
+
+  return hint;
+}
+
 /* Initialize ipa_tdesc and others.  */
 
 void
diff --git a/gdb/gdbserver/tracepoint.c b/gdb/gdbserver/tracepoint.c
index 3ce9580..39660c8 100644
--- a/gdb/gdbserver/tracepoint.c
+++ b/gdb/gdbserver/tracepoint.c
@@ -7370,13 +7370,12 @@ initialize_tracepoint (void)
 
 #define SCRATCH_BUFFER_NPAGES 20
 
-    /* Allocate scratch buffer aligned on a page boundary, at a low
-       address (close to the main executable's code).  */
-    for (addr = pagesize; addr != 0; addr += pagesize)
+    addr = jump_pad_area_hint ();
+    for (; addr != 0; addr += pagesize)
       {
 	gdb_jump_pad_buffer = mmap ((void *) addr, pagesize * SCRATCH_BUFFER_NPAGES,
 				    PROT_READ | PROT_WRITE | PROT_EXEC,
-				    MAP_PRIVATE | MAP_ANONYMOUS | MAP_FIXED,
+				    MAP_PRIVATE | MAP_ANONYMOUS,
 				    -1, 0);
 	if (gdb_jump_pad_buffer != MAP_FAILED)
 	  break;
diff --git a/gdb/gdbserver/tracepoint.h b/gdb/gdbserver/tracepoint.h
index 30d0b58..139894f 100644
--- a/gdb/gdbserver/tracepoint.h
+++ b/gdb/gdbserver/tracepoint.h
@@ -131,6 +131,9 @@ void supply_static_tracepoint_registers (struct regcache *regcache,
 					 CORE_ADDR pc);
 void set_trampoline_buffer_space (CORE_ADDR begin, CORE_ADDR end,
 				  char *errmsg);
+/* Return the address for where to allocate buffer for jump pad.
+   The buffer should be close enough for tracepoints.  */
+uintptr_t jump_pad_area_hint (void);
 
 extern const struct target_desc *ipa_tdesc;
 
-- 
1.9.1


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