- fix: handle elf64 note sections correctly.
authorjbj <devnull@localhost>
Sat, 13 Mar 2004 13:34:44 +0000 (13:34 +0000)
committerjbj <devnull@localhost>
Sat, 13 Mar 2004 13:34:44 +0000 (13:34 +0000)
CVS patchset: 7171
CVS date: 2004/03/13 13:34:44

CHANGES
file/src/readelf.c
rpm.spec.in

diff --git a/CHANGES b/CHANGES
index 459c125360a894a0f6254d6ea843008dad7f987c..4366fee4b1352739a552e2ed7ab063d730208e63 100644 (file)
--- a/CHANGES
+++ b/CHANGES
@@ -31,7 +31,9 @@
        - add sparcv8 and enable elf32/elf64 Zon sparc64 (#117302).
        - fix: --querybynumber looped.
        - fix: ENOTSUP filter from lsetfilecon borkage.
-  
+       - fix: increase file context regex parse buffer to BUFSIZ.
+       - fix: handle elf64 note sections correctly.
+
 4.2.1 -> 4.2.2:
        - unify signal handling in librpmio, use condvar to deliver signal.
        - make peace with libtool-1.5, autoconf-2.59, automake-1.8.
index 6e2207349dc5166fa6849b3257c641f8b733d1d1..23914c8d7d93597dd09e15be63b84aafc9804a28 100644 (file)
@@ -103,9 +103,6 @@ getu64(const fmagic fm, uint64_t value)
 #define ph_align       (fm->cls == ELFCLASS32          \
                         ? (ph32.p_align ? getu32(fm, ph32.p_align) : 4) \
                         : (ph64.p_align ? getu64(fm, ph64.p_align) : 4))
-#define nh_size                (fm->cls == ELFCLASS32          \
-                        ? sizeof *nh32                 \
-                        : sizeof *nh64)
 #define nh_type                (fm->cls == ELFCLASS32          \
                         ? getu32(fm, nh32->n_type)     \
                         : getu32(fm, nh64->n_type))
@@ -171,7 +168,10 @@ dophn_exec(fmagic fm, off_t off, int num, size_t size)
        char *shared_libraries = "";
        char nbuf[BUFSIZ];
        int bufsize;
-       size_t offset, nameoffset;
+       size_t offset, end, noff, doff;
+       size_t align = (fm->cls == ELFCLASS32 ? 4 : 8);
+#define ALIGNED_LEN(len) (((len) + align - 1) & ~(align - 1))
+       int printed;
 
        if (size != ph_size) {
                error(EXIT_FAILURE, 0, "corrupted program header size.\n");
@@ -212,43 +212,38 @@ dophn_exec(fmagic fm, off_t off, int num, size_t size)
                                /*@notreached@*/
                        }
                        offset = 0;
+                       printed = 0;
                        for (;;) {
-                               if (offset >= bufsize)
+                               end = offset + 12;
+                               if (end >= bufsize)
                                        /*@innerbreak@*/ break;
+
                                if (fm->cls == ELFCLASS32)
                                        nh32 = (Elf32_Nhdr *)&nbuf[offset];
                                else
                                        nh64 = (Elf64_Nhdr *)&nbuf[offset];
-                               offset += nh_size;
-       
-                               if (offset + nh_namesz >= bufsize) {
-                                       /*
-                                        * We're past the end of the buffer.
-                                        */
-                                       /*@innerbreak@*/ break;
-                               }
-
-                               nameoffset = offset;
-                               offset += nh_namesz;
-                               offset = ((offset+ph_align-1)/ph_align)*ph_align;
 
-                               if ((nh_namesz == 0) && (nh_descsz == 0)) {
-                                       /*
-                                        * We're out of note headers.
-                                        */
+                               offset = end;   /* skip note header. */
+                               end = offset    + ALIGNED_LEN (nh_namesz)
+                                               + ALIGNED_LEN (nh_descsz);
+                               if (end > bufsize)
                                        /*@innerbreak@*/ break;
-                               }
 
-                               if (offset + nh_descsz >= bufsize)
-                                       /*@innerbreak@*/ break;
+                               noff = offset;
+                               doff = ALIGNED_LEN(offset + nh_namesz);
+                               offset = end;
+
+                               if (printed)
+                                       continue;
 
                                if (nh_namesz == 4 &&
-                                   strcmp(&nbuf[nameoffset], "GNU") == 0 &&
+                                   strcmp(&nbuf[noff], "GNU") == 0 &&
                                    nh_type == NT_GNU_VERSION &&
                                    nh_descsz == 16) {
                                        uint32_t *desc =
-                                           (uint32_t *)&nbuf[offset];
+                                           (uint32_t *)&nbuf[doff];
 
+                                       if (!printed)
                                        file_printf(fm, ", for GNU/");
                                        switch (getu32(fm, desc[0])) {
                                        case GNU_OS_LINUX:
@@ -268,10 +263,11 @@ dophn_exec(fmagic fm, off_t off, int num, size_t size)
                                            getu32(fm, desc[1]),
                                            getu32(fm, desc[2]),
                                            getu32(fm, desc[3]));
+                                       printed = 1;
                                }
 
                                if (nh_namesz == 7 &&
-                                   strcmp(&nbuf[nameoffset], "NetBSD") == 0 &&
+                                   strcmp(&nbuf[noff], "NetBSD") == 0 &&
                                    nh_type == NT_NETBSD_VERSION &&
                                    nh_descsz == 4) {
                                        file_printf(fm, ", for NetBSD");
@@ -279,14 +275,15 @@ dophn_exec(fmagic fm, off_t off, int num, size_t size)
                                         * Version number is stuck at 199905,
                                         * and hence is basically content-free.
                                         */
+                                       printed = 1;
                                }
 
                                if (nh_namesz == 8 &&
-                                   strcmp(&nbuf[nameoffset], "FreeBSD") == 0 &&
+                                   strcmp(&nbuf[noff], "FreeBSD") == 0 &&
                                    nh_type == NT_FREEBSD_VERSION &&
                                    nh_descsz == 4) {
                                        uint32_t desc = getu32(fm,
-                                           *(uint32_t *)&nbuf[offset]);
+                                           *(uint32_t *)&nbuf[doff]);
                                        file_printf(fm, ", for FreeBSD");
                                        /*
                                         * Contents is __FreeBSD_version,
@@ -303,14 +300,16 @@ dophn_exec(fmagic fm, off_t off, int num, size_t size)
                                        if (desc / 1000 % 10 > 0)
                                                file_printf(fm, ".%d",
                                                    desc / 1000 % 10);
+                                       printed = 1;
                                }
 
                                if (nh_namesz == 8 &&
-                                   strcmp(&nbuf[nameoffset], "OpenBSD") == 0 &&
+                                   strcmp(&nbuf[noff], "OpenBSD") == 0 &&
                                    nh_type == NT_OPENBSD_VERSION &&
                                    nh_descsz == 4) {
                                        file_printf(fm, ", for OpenBSD");
                                        /* Content of note is always 0 */
+                                       printed = 1;
                                }
                        }
                        if ((lseek(fm->fd, ph_offset + offset, SEEK_SET)) == -1) {
@@ -434,7 +433,7 @@ dophn_core(fmagic fm, off_t off, int num, size_t size)
                                nh32 = (Elf32_Nhdr *)&nbuf[offset];
                        else
                                nh64 = (Elf64_Nhdr *)&nbuf[offset];
-                       offset += nh_size;
+                       offset += 12;
 
                        /*
                         * Check whether this note has the name "CORE" or
index 91a573a0e93e0a8c3ba0f60e4107d070c33dd757..95c8c984030b952cc04f75668a1fcd94e707a3c7 100644 (file)
@@ -20,7 +20,7 @@ Name: rpm
 %define version @VERSION@
 Version: %{version}
 %{expand: %%define rpm_version %{version}}
-Release: 0.20
+Release: 0.21
 Group: System Environment/Base
 Source: ftp://ftp.rpm.org/pub/rpm/dist/rpm-4.0.x/rpm-%{rpm_version}.tar.gz
 License: GPL
@@ -485,6 +485,10 @@ exit 0
 %{__includedir}/popt.h
 
 %changelog
+* Fri Mar 12 2004 Jeff Johnson <jbj@jbj.org> 4.3-0.21
+- fix: increase file context regex parse buffer to BUFSIZ.
+- fix: handle elf64 note sections correctly.
+
 * Wed Mar 10 2004 Jeff Johnson <jbj@jbj.org> 4.3-0.20
 - add sparcv8 and enable elf32/elf64 Zon sparc64 (#117302).
 - fix: --querybynumber looped.