This is the mail archive of the binutils@sourceware.org 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]
Other format: [Raw text]

readelf build error on 64-bit hosts


Hi Nick,
>From the PR15181 fix, I believe..

readelf.c: In function âprocess_corefile_note_segmentâ:
readelf.c:13370:23: error: comparison between signed and unsigned integer expressions [-Werror=sign-compare]
readelf.c:13391:23: error: comparison between signed and unsigned integer expressions [-Werror=sign-compare]

On looking at the change, I think there are some other errors too.  This:

      Elf_External_Note * next;
..
	  if (data_remaining < sizeof * next)

will cause a failure if the last note in a note section has namesz and
descsz both zero (Elf_External_Note includes a one byte name array).

What do you think of the following?  

	* readelf.c (offsetof): Define.
	(CHECK_ENTSIZE_VALUES): Remove extraneous indefinite article.
	(process_corefile_note_segment): Allow notes without name or
	desc.  Combine out-of-range checks.  Disallow "negative"
	notesz or descaz.

Index: binutils/readelf.c
===================================================================
RCS file: /cvs/src/src/binutils/readelf.c,v
retrieving revision 1.596
diff -u -p -r1.596 readelf.c
--- binutils/readelf.c	26 Feb 2013 16:59:51 -0000	1.596
+++ binutils/readelf.c	27 Feb 2013 10:06:36 -0000
@@ -160,6 +160,10 @@
 #include "safe-ctype.h"
 #include "filenames.h"
 
+#ifndef offsetof
+#define offsetof(TYPE, MEMBER) ((size_t) &(((TYPE *) 0)->MEMBER))
+#endif
+
 char * program_name = "readelf";
 static long archive_file_offset;
 static unsigned long archive_file_size;
@@ -4754,7 +4758,7 @@ process_section_headers (FILE * file)
       bfd_size_type expected_entsize = is_32bit_elf ? size32 : size64;	    \
       if (section->sh_entsize != expected_entsize)			    \
 	{								\
-	  error (_("Section %d has invalid an sh_entsize of %" BFD_VMA_FMT "x\n"), \
+	  error (_("Section %d has invalid sh_entsize of %" BFD_VMA_FMT "x\n"), \
 		 i, section->sh_entsize);	\
 	  error (_("(Using the expected size of %d for the rest of this dump)\n"), \
 		   (int) expected_entsize); \
@@ -13340,7 +13344,6 @@ process_corefile_note_segment (FILE * fi
   Elf_External_Note * pnotes;
   Elf_External_Note * external;
   int res = 1;
-  bfd_signed_vma data_remaining;
 
   if (length <= 0)
     return 0;
@@ -13356,18 +13359,20 @@ process_corefile_note_segment (FILE * fi
 	  (unsigned long) offset, (unsigned long) length);
   printf (_("  %-20s %10s\tDescription\n"), _("Owner"), _("Data size"));
 
-  data_remaining = length;
-  while (external < (Elf_External_Note *) ((char *) pnotes + length))
+  while ((char *) external < (char *) pnotes + length)
     {
-      Elf_External_Note * next;
       Elf_Internal_Note inote;
+      size_t min_notesz;
+      char *next;
       char * temp = NULL;
+      size_t data_remaining = ((char *) pnotes + length) - (char *) external;
 
       if (!is_ia64_vms ())
         {
 	  /* PR binutils/15191
 	     Make sure that there is enough data to read.  */
-	  if (data_remaining < sizeof * next)
+	  min_notesz = offsetof (Elf_External_Note, name);
+	  if (data_remaining < min_notesz)
 	    {
 	      warn (_("Corrupt note: only %d bytes remain, not enough for a full note\n"),
 		    (int) data_remaining);
@@ -13379,8 +13384,7 @@ process_corefile_note_segment (FILE * fi
           inote.descsz   = BYTE_GET (external->descsz);
           inote.descdata = inote.namedata + align_power (inote.namesz, 2);
           inote.descpos  = offset + (inote.descdata - (char *) pnotes);
-
-          next = (Elf_External_Note *) (inote.descdata + align_power (inote.descsz, 2));
+          next = inote.descdata + align_power (inote.descsz, 2);
         }
       else
         {
@@ -13388,7 +13392,8 @@ process_corefile_note_segment (FILE * fi
 
 	  /* PR binutils/15191
 	     Make sure that there is enough data to read.  */
-	  if (data_remaining < sizeof * vms_external)
+	  min_notesz = offsetof (Elf64_External_VMS_Note, name);
+	  if (data_remaining < min_notesz)
 	    {
 	      warn (_("Corrupt note: only %d bytes remain, not enough for a full note\n"),
 		    (int) data_remaining);
@@ -13402,33 +13407,21 @@ process_corefile_note_segment (FILE * fi
           inote.descsz   = BYTE_GET (vms_external->descsz);
           inote.descdata = inote.namedata + align_power (inote.namesz, 3);
           inote.descpos  = offset + (inote.descdata - (char *) pnotes);
-
-          next = (Elf_External_Note *)
-            (inote.descdata + align_power (inote.descsz, 3));
+          next = inote.descdata + align_power (inote.descsz, 3);
         }
 
-      data_remaining -= ((char *) next - (char *) external);
-      if (data_remaining < 0)
+      if (inote.descdata < (char *) external + min_notesz
+	  || next < (char *) external + min_notesz
+	  || data_remaining < (size_t)(next - (char *) external))
 	{
-	  warn (_("note with invalid namesz &/or descsz found at offset 0x%lx\n"),
+	  warn (_("note with invalid namesz and/or descsz found at offset 0x%lx\n"),
 		(unsigned long) ((char *) external - (char *) pnotes));
 	  warn (_(" type: 0x%lx, namesize: 0x%08lx, descsize: 0x%08lx\n"),
 		inote.type, inote.namesz, inote.descsz);
 	  break;
 	}
 
-      external = next;
-
-      /* Prevent out-of-bounds indexing.  */
-      if (inote.namedata + inote.namesz > (char *) pnotes + length
-	  || inote.namedata + inote.namesz < inote.namedata)
-        {
-          warn (_("note with invalid namesz found at offset 0x%lx\n"),
-                (unsigned long) ((char *) external - (char *) pnotes));
-          warn (_(" type: 0x%lx, namesize: 0x%08lx, descsize: 0x%08lx\n"),
-                inote.type, inote.namesz, inote.descsz);
-          break;
-        }
+      external = (Elf_External_Note *) next;
 
       /* Verify that name is null terminated.  It appears that at least
 	 one version of Linux (RedHat 6.0) generates corefiles that don't


-- 
Alan Modra
Australia Development Lab, IBM


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