public inbox for gdb-patches@sourceware.org
 help / color / mirror / Atom feed
From: Jan Kratochvil <jan.kratochvil@redhat.com>
To: gdb-patches@sourceware.org
Cc: Aleksandar Ristovski <ARistovski@qnx.com>
Subject: [PATCH v7 06/10] Prepare linux_find_memory_regions_full & co. for move
Date: Sun, 14 Jun 2015 19:26:00 -0000	[thread overview]
Message-ID: <20150614192630.18346.76001.stgit@host1.jankratochvil.net> (raw)
In-Reply-To: <20150614192542.18346.87859.stgit@host1.jankratochvil.net>

Hi,

prepare code for move into gdb/common/.

Approved by:
	https://sourceware.org/ml/gdb-patches/2014-05/msg00371.html


Jan


gdb/ChangeLog
2014-02-26  Aleksandar Ristovski  <aristovski@qnx.com
	    Jan Kratochvil  <jan.kratochvil@redhat.com>

	Prepare linux_find_memory_regions_full & co. for move.
	* linux-tdep.c (linux_find_memory_region_ftype): Comment.
	(linux_find_memory_regions_full): Change signature and prepare
	for moving to linux-maps.
	(linux_find_memory_regions_data): Rename field 'obfd' to 'data'.
	(linux_find_memory_regions_thunk): New.
	(linux_find_memory_regions_thunk): Use 'data' field instead of 'obfd'.
	(linux_find_memory_regions_gdb): New.
	(linux_find_memory_regions): Rename argument 'obfd' to 'func_data'.
	(linux_make_mappings_corefile_notes): Use
	linux_find_memory_regions_gdb.
	* target.c (read_alloc_pread_ftype): New typedef.
	(target_fileio_read_alloc_1_pread): New function.
	(read_alloc): Refactor from target_fileio_read_alloc_1.
	(read_stralloc_func_ftype): New typedef.
	(target_fileio_read_alloc_1): New implementation. Use read_alloc.
	(read_stralloc): Refactored from target_fileio_read_stralloc.
	(target_fileio_read_stralloc): New implementation, use read_stralloc.
---
 gdb/linux-tdep.c |  121 +++++++++++++++++++++++++++++++++---------------------
 gdb/target.c     |   96 +++++++++++++++++++++++++++++--------------
 2 files changed, 138 insertions(+), 79 deletions(-)

diff --git a/gdb/linux-tdep.c b/gdb/linux-tdep.c
index c81f71b..fb59305 100644
--- a/gdb/linux-tdep.c
+++ b/gdb/linux-tdep.c
@@ -1098,6 +1098,10 @@ linux_core_info_proc (struct gdbarch *gdbarch, const char *args,
     error (_("unable to handle request"));
 }
 
+/* Callback function for linux_find_memory_regions_full.  If it returns
+   non-zero linux_find_memory_regions_full returns immediately with that
+   value.  */
+
 typedef int linux_find_memory_region_ftype (ULONGEST vaddr, ULONGEST size,
 					    ULONGEST offset, ULONGEST inode,
 					    int read, int write,
@@ -1105,43 +1109,22 @@ typedef int linux_find_memory_region_ftype (ULONGEST vaddr, ULONGEST size,
 					    const char *filename,
 					    void *data);
 
-/* List memory regions in the inferior for a corefile.  */
+/* List memory regions in the inferior PID matched to FILTERFLAGS for
+   a corefile.  Call FUNC with FUNC_DATA for each such region.  Return
+   immediately with the value returned by FUNC if it is non-zero.
+   *MEMORY_TO_FREE_PTR should be registered to be freed automatically if
+   called FUNC throws an exception.  MEMORY_TO_FREE_PTR can be also
+   passed as NULL if it is not used.  Return -1 if error occurs, 0 if
+   all memory regions have been processed or return the value from FUNC
+   if FUNC returns non-zero.  */
 
 static int
-linux_find_memory_regions_full (struct gdbarch *gdbarch,
+linux_find_memory_regions_full (pid_t pid, enum filterflags filterflags,
 				linux_find_memory_region_ftype *func,
-				void *obfd)
+				void *func_data)
 {
   char mapsfilename[100];
-  char coredumpfilter_name[100];
-  char *data, *coredumpfilterdata;
-  pid_t pid;
-  /* Default dump behavior of coredump_filter (0x33), according to
-     Documentation/filesystems/proc.txt from the Linux kernel
-     tree.  */
-  enum filterflags filterflags = (COREFILTER_ANON_PRIVATE
-				  | COREFILTER_ANON_SHARED
-				  | COREFILTER_ELF_HEADERS
-				  | COREFILTER_HUGETLB_PRIVATE);
-
-  /* We need to know the real target PID to access /proc.  */
-  if (current_inferior ()->fake_pid_p)
-    return 1;
-
-  pid = current_inferior ()->pid;
-
-  if (use_coredump_filter)
-    {
-      xsnprintf (coredumpfilter_name, sizeof (coredumpfilter_name),
-		 "/proc/%d/coredump_filter", pid);
-      coredumpfilterdata = target_fileio_read_stralloc (NULL,
-							coredumpfilter_name);
-      if (coredumpfilterdata != NULL)
-	{
-	  sscanf (coredumpfilterdata, "%x", &filterflags);
-	  xfree (coredumpfilterdata);
-	}
-    }
+  char *data;
 
   xsnprintf (mapsfilename, sizeof mapsfilename, "/proc/%d/smaps", pid);
   data = target_fileio_read_stralloc (NULL, mapsfilename);
@@ -1156,6 +1139,7 @@ linux_find_memory_regions_full (struct gdbarch *gdbarch,
     {
       struct cleanup *cleanup = make_cleanup (xfree, data);
       char *line, *t;
+      int retval = 0;
 
       line = strtok_r (data, "\n", &t);
       while (line != NULL)
@@ -1270,17 +1254,20 @@ linux_find_memory_regions_full (struct gdbarch *gdbarch,
 
 	  /* Invoke the callback function to create the corefile segment.  */
 	  if (should_dump_p)
-	    func (addr, endaddr - addr, offset, inode,
-		  read, write, exec, 1, /* MODIFIED is true because we
-					   want to dump the mapping.  */
-		  filename, obfd);
+	    retval = func (addr, endaddr - addr, offset, inode,
+			   read, write, exec,
+			   1, /* MODIFIED is true because we want to dump the
+				 mapping.  */
+			   filename, func_data);
+	  if (retval != 0)
+	    break;
 	}
 
       do_cleanups (cleanup);
-      return 0;
+      return retval;
     }
 
-  return 1;
+  return -1;
 }
 
 /* A structure for passing information through
@@ -1294,7 +1281,7 @@ struct linux_find_memory_regions_data
 
   /* The original datum.  */
 
-  void *obfd;
+  void *data;
 };
 
 /* A callback for linux_find_memory_regions that converts between the
@@ -1308,7 +1295,48 @@ linux_find_memory_regions_thunk (ULONGEST vaddr, ULONGEST size,
 {
   struct linux_find_memory_regions_data *data = arg;
 
-  return data->func (vaddr, size, read, write, exec, modified, data->obfd);
+  return data->func (vaddr, size, read, write, exec, modified, data->data);
+}
+
+/* Wrapper of linux_find_memory_regions_full handling FAKE_PID_P in GDB.  */
+
+static int
+linux_find_memory_regions_gdb (struct gdbarch *gdbarch,
+			       linux_find_memory_region_ftype *func,
+			       void *func_data)
+{
+  pid_t pid;
+  /* Default dump behavior of coredump_filter (0x33), according to
+     Documentation/filesystems/proc.txt from the Linux kernel
+     tree.  */
+  enum filterflags filterflags = (COREFILTER_ANON_PRIVATE
+				  | COREFILTER_ANON_SHARED
+				  | COREFILTER_ELF_HEADERS
+				  | COREFILTER_HUGETLB_PRIVATE);
+
+  /* We need to know the real target PID so
+     linux_find_memory_regions_full can access /proc.  */
+  if (current_inferior ()->fake_pid_p)
+    return -1;
+
+  pid = current_inferior ()->pid;
+
+  if (use_coredump_filter)
+    {
+      char coredumpfilter_name[100], *coredumpfilterdata;
+
+      xsnprintf (coredumpfilter_name, sizeof (coredumpfilter_name),
+		 "/proc/%d/coredump_filter", pid);
+      coredumpfilterdata = target_fileio_read_stralloc (NULL,
+							coredumpfilter_name);
+      if (coredumpfilterdata != NULL)
+	{
+	  sscanf (coredumpfilterdata, "%x", &filterflags);
+	  xfree (coredumpfilterdata);
+	}
+    }
+
+  return linux_find_memory_regions_full (pid, filterflags, func, func_data);
 }
 
 /* A variant of linux_find_memory_regions_full that is suitable as the
@@ -1316,16 +1344,15 @@ linux_find_memory_regions_thunk (ULONGEST vaddr, ULONGEST size,
 
 static int
 linux_find_memory_regions (struct gdbarch *gdbarch,
-			   find_memory_region_ftype func, void *obfd)
+			   find_memory_region_ftype func, void *func_data)
 {
   struct linux_find_memory_regions_data data;
 
   data.func = func;
-  data.obfd = obfd;
+  data.data = func_data;
 
-  return linux_find_memory_regions_full (gdbarch,
-					 linux_find_memory_regions_thunk,
-					 &data);
+  return linux_find_memory_regions_gdb (gdbarch,
+					linux_find_memory_regions_thunk, &data);
 }
 
 /* Determine which signal stopped execution.  */
@@ -1507,8 +1534,8 @@ linux_make_mappings_corefile_notes (struct gdbarch *gdbarch, bfd *obfd,
   pack_long (buf, long_type, 1);
   obstack_grow (&data_obstack, buf, TYPE_LENGTH (long_type));
 
-  linux_find_memory_regions_full (gdbarch, linux_make_mappings_callback,
-				  &mapping_data);
+  linux_find_memory_regions_gdb (gdbarch, linux_make_mappings_callback,
+				 &mapping_data);
 
   if (mapping_data.file_count != 0)
     {
diff --git a/gdb/target.c b/gdb/target.c
index 4e2d005..2dd3116 100644
--- a/gdb/target.c
+++ b/gdb/target.c
@@ -2973,6 +2973,20 @@ target_fileio_close_cleanup (void *opaque)
   target_fileio_close (fd, &target_errno);
 }
 
+typedef int (read_alloc_pread_ftype) (int handle, gdb_byte *read_buf, int len,
+				      ULONGEST offset, int *target_errno);
+
+/* Helper for target_fileio_read_alloc_1 to make it interruptible.  */
+
+static int
+target_fileio_read_alloc_1_pread (int handle, gdb_byte *read_buf, int len,
+				  ULONGEST offset, int *target_errno)
+{
+  QUIT;
+
+  return target_fileio_pread (handle, read_buf, len, offset, target_errno);
+}
+
 /* Read target file FILENAME, in the filesystem as seen by INF.  If
    INF is NULL, use the filesystem seen by the debugger (GDB or, for
    remote targets, the remote stub).  Store the result in *BUF_P and
@@ -2982,23 +2996,14 @@ target_fileio_close_cleanup (void *opaque)
    more information.  */
 
 static LONGEST
-target_fileio_read_alloc_1 (struct inferior *inf, const char *filename,
-			    gdb_byte **buf_p, int padding)
+read_alloc (gdb_byte **buf_p, int handle, read_alloc_pread_ftype *pread_func,
+	    int padding)
 {
-  struct cleanup *close_cleanup;
   size_t buf_alloc, buf_pos;
   gdb_byte *buf;
   LONGEST n;
-  int fd;
   int target_errno;
 
-  fd = target_fileio_open (inf, filename, FILEIO_O_RDONLY, 0700,
-			   &target_errno);
-  if (fd == -1)
-    return -1;
-
-  close_cleanup = make_cleanup (target_fileio_close_cleanup, &fd);
-
   /* Start by reading up to 4K at a time.  The target will throttle
      this number down if necessary.  */
   buf_alloc = 4096;
@@ -3006,25 +3011,24 @@ target_fileio_read_alloc_1 (struct inferior *inf, const char *filename,
   buf_pos = 0;
   while (1)
     {
-      n = target_fileio_pread (fd, &buf[buf_pos],
-			       buf_alloc - buf_pos - padding, buf_pos,
-			       &target_errno);
-      if (n < 0)
+      n = pread_func (handle, &buf[buf_pos], buf_alloc - buf_pos - padding,
+		      buf_pos, &target_errno);
+      if (n <= 0)
 	{
-	  /* An error occurred.  */
-	  do_cleanups (close_cleanup);
-	  xfree (buf);
-	  return -1;
-	}
-      else if (n == 0)
-	{
-	  /* Read all there was.  */
-	  do_cleanups (close_cleanup);
-	  if (buf_pos == 0)
+	  if (n < 0 || (n == 0 && buf_pos == 0))
 	    xfree (buf);
 	  else
 	    *buf_p = buf;
-	  return buf_pos;
+	  if (n < 0)
+	    {
+	      /* An error occurred.  */
+	      return -1;
+	    }
+	  else
+	    {
+	      /* Read all there was.  */
+	      return buf_pos;
+	    }
 	}
 
       buf_pos += n;
@@ -3035,11 +3039,31 @@ target_fileio_read_alloc_1 (struct inferior *inf, const char *filename,
 	  buf_alloc *= 2;
 	  buf = xrealloc (buf, buf_alloc);
 	}
-
-      QUIT;
     }
 }
 
+typedef LONGEST (read_stralloc_func_ftype) (struct inferior *inf,
+					    const char *filename,
+					    gdb_byte **buf_p, int padding);
+
+static LONGEST
+target_fileio_read_alloc_1 (struct inferior *inf, const char *filename,
+			    gdb_byte **buf_p, int padding)
+{
+  struct cleanup *close_cleanup;
+  int fd, target_errno;
+  LONGEST retval;
+
+  fd = target_fileio_open (inf, filename, FILEIO_O_RDONLY, 0700, &target_errno);
+  if (fd == -1)
+    return -1;
+
+  close_cleanup = make_cleanup (target_fileio_close_cleanup, &fd);
+  retval = read_alloc (buf_p, fd, target_fileio_read_alloc_1_pread, padding);
+  do_cleanups (close_cleanup);
+  return retval;
+}
+
 /* See target.h.  */
 
 LONGEST
@@ -3049,16 +3073,17 @@ target_fileio_read_alloc (struct inferior *inf, const char *filename,
   return target_fileio_read_alloc_1 (inf, filename, buf_p, 0);
 }
 
-/* See target.h.  */
+/* Helper for target_fileio_read_stralloc.  */
 
-char *
-target_fileio_read_stralloc (struct inferior *inf, const char *filename)
+static char *
+read_stralloc (struct inferior *inf, const char *filename,
+	       read_stralloc_func_ftype *func)
 {
   gdb_byte *buffer;
   char *bufstr;
   LONGEST i, transferred;
 
-  transferred = target_fileio_read_alloc_1 (inf, filename, &buffer, 1);
+  transferred = func (inf, filename, &buffer, 1);
   bufstr = (char *) buffer;
 
   if (transferred < 0)
@@ -3082,6 +3107,13 @@ target_fileio_read_stralloc (struct inferior *inf, const char *filename)
   return bufstr;
 }
 
+/* See target.h.  */
+
+char *
+target_fileio_read_stralloc (struct inferior *inf, const char *filename)
+{
+  return read_stralloc (inf, filename, target_fileio_read_alloc_1);
+}
 
 static int
 default_region_ok_for_hw_watchpoint (struct target_ops *self,

  parent reply	other threads:[~2015-06-14 19:26 UTC|newest]

Thread overview: 44+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2015-06-14 19:25 [PATCH v7 00/10] Validate binary before use Jan Kratochvil
2015-06-14 19:25 ` [PATCH v7 01/10] Move utility functions to common/ Jan Kratochvil
2015-06-15 13:22   ` Joel Brobecker
2015-06-15 15:07     ` [commit] " Jan Kratochvil
2015-06-14 19:26 ` [PATCH v7 05/10] Move gdb_regex* " Jan Kratochvil
2015-07-08 14:39   ` Pedro Alves
2015-07-14 20:13     ` Jan Kratochvil
2015-06-14 19:26 ` [PATCH v7 03/10] Code cleanup: Rename enum -> enum filterflags Jan Kratochvil
2015-06-15 13:34   ` Joel Brobecker
2015-06-15 15:12     ` [commit] " Jan Kratochvil
2015-07-08 14:38   ` Pedro Alves
2015-06-14 19:26 ` [PATCH v7 07/10] Move linux_find_memory_regions_full & co Jan Kratochvil
2015-06-14 19:26 ` [PATCH v7 02/10] Merge multiple hex conversions Jan Kratochvil
2015-06-15 13:33   ` Joel Brobecker
2015-06-15 15:09     ` [commit] " Jan Kratochvil
2015-06-14 19:26 ` Jan Kratochvil [this message]
2015-06-14 19:26 ` [PATCH v7 04/10] Create empty nat/linux-maps.[ch] and common/target-utils.[ch] Jan Kratochvil
2015-06-14 19:27 ` [PATCH v7 09/10] Validate symbol file using build-id Jan Kratochvil
2015-06-21 10:16   ` [PATCH v8 " Jan Kratochvil
2015-06-22 12:55     ` Aleksandar Ristovski
2015-06-22 20:37       ` Jan Kratochvil
2015-06-22 20:41         ` Aleksandar Ristovski
2015-06-22 22:25     ` Doug Evans
2015-06-23 20:47       ` Jan Kratochvil
2015-07-08 14:44         ` Pedro Alves
2015-07-12 19:09           ` Jan Kratochvil
2015-07-12 19:29             ` [PATCH v9 " Jan Kratochvil
2015-07-12 19:54               ` Eli Zaretskii
2015-07-12 20:01                 ` Jan Kratochvil
2015-07-13  2:30                   ` Eli Zaretskii
2015-07-13 10:34                 ` Pedro Alves
2015-07-13 12:38                   ` Jan Kratochvil
2015-07-14 16:14                     ` Doug Evans
2015-07-15  8:21                       ` Jan Kratochvil
2015-07-15 14:59                         ` Doug Evans
2015-06-27 21:05       ` [PATCH v8 " Jan Kratochvil
2015-07-08 15:40         ` Doug Evans
2015-07-12 19:27           ` Jan Kratochvil
2015-06-14 19:27 ` [PATCH v7 10/10] Tests for validate " Jan Kratochvil
2015-07-08 14:44   ` Pedro Alves
2015-06-14 19:27 ` [PATCH v7 08/10] gdbserver build-id attribute generator Jan Kratochvil
2015-07-08 14:41   ` Pedro Alves
2015-07-15 16:36 ` [commit] [PATCH v7 00/10] Validate binary before use Jan Kratochvil
2015-07-15 18:33   ` [revert] " Jan Kratochvil

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20150614192630.18346.76001.stgit@host1.jankratochvil.net \
    --to=jan.kratochvil@redhat.com \
    --cc=ARistovski@qnx.com \
    --cc=gdb-patches@sourceware.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).