Page Menu
Home
FreeBSD
Search
Configure Global Search
Log In
Files
F163283487
D57034.id177945.diff
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Flag For Later
Award Token
Size
4 KB
Referenced Files
None
Subscribers
None
D57034.id177945.diff
View Options
diff --git a/lib/libc/gen/nlist.c b/lib/libc/gen/nlist.c
--- a/lib/libc/gen/nlist.c
+++ b/lib/libc/gen/nlist.c
@@ -85,6 +85,8 @@
#define ISLAST(p) (p->n_un.n_name == 0 || p->n_un.n_name[0] == 0)
+static int elf_scan_symtab(Elf_Shdr *, Elf_Ehdr *, int, char *, size_t,
+ struct nlist *, int);
static void elf_sym_to_nlist(struct nlist *, Elf_Sym *, Elf_Shdr *, int);
/*
@@ -123,14 +125,11 @@
struct nlist *p;
Elf_Off symoff = 0, symstroff = 0;
Elf_Size symsize = 0, symstrsize = 0;
- Elf_Ssize cc, i;
+ Elf_Ssize i;
int nent = -1;
int errsave;
- Elf_Sym sbuf[1024];
- Elf_Sym *s;
Elf_Ehdr ehdr;
- char *strtab = NULL;
- Elf_Shdr *shdr = NULL;
+ Elf_Shdr *shdr;
Elf_Size shdr_size;
void *base;
struct stat st;
@@ -158,39 +157,6 @@
return (-1);
shdr = (Elf_Shdr *)base;
- /*
- * Find the symbol table entry and it's corresponding
- * string table entry. Version 1.1 of the ABI states
- * that there is only one symbol table but that this
- * could change in the future.
- */
- for (i = 0; i < ehdr.e_shnum; i++) {
- if (shdr[i].sh_type == SHT_SYMTAB) {
- symoff = shdr[i].sh_offset;
- symsize = shdr[i].sh_size;
- symstroff = shdr[shdr[i].sh_link].sh_offset;
- symstrsize = shdr[shdr[i].sh_link].sh_size;
- break;
- }
- }
-
- /* Check for files too large to mmap. */
- if (symstrsize > SIZE_T_MAX) {
- errno = EFBIG;
- goto done;
- }
- /*
- * Map string table into our address space. This gives us
- * an easy way to randomly access all the strings, without
- * making the memory allocation permanent as with malloc/free
- * (i.e., munmap will return it to the system).
- */
- base = mmap(NULL, (size_t)symstrsize, PROT_READ, MAP_PRIVATE, fd,
- (off_t)symstroff);
- if (base == MAP_FAILED)
- goto done;
- strtab = (char *)base;
-
/*
* clean out any left-over information for all valid entries.
* Type and value defined to be 0 if not found; historical
@@ -210,14 +176,70 @@
++nent;
}
- /* Don't process any further if object is stripped. */
- if (symoff == 0)
- goto done;
-
- if (lseek(fd, (off_t) symoff, SEEK_SET) == -1) {
- nent = -1;
- goto done;
+ /*
+ * Find the symbol table entry and it's corresponding
+ * string table entry. Version 1.1 of the ABI states
+ * that there is only one symbol table but that this
+ * could change in the future.
+ */
+ for (i = 0; nent > 0 && i < ehdr.e_shnum; i++) {
+ if (shdr[i].sh_type != SHT_SYMTAB &&
+ shdr[i].sh_type != SHT_DYNSYM)
+ continue;
+ symoff = shdr[i].sh_offset;
+ symsize = shdr[i].sh_size;
+ symstroff = shdr[shdr[i].sh_link].sh_offset;
+ symstrsize = shdr[shdr[i].sh_link].sh_size;
+
+ /* Don't process any further if object is stripped. */
+ if (symoff == 0 || symsize == 0) {
+ errno = ENOENT;
+ continue;
+ }
+
+ /* Check for files too large to mmap. */
+ if (symstrsize > SIZE_T_MAX) {
+ errno = EFBIG;
+ continue;
+ }
+
+ /*
+ * Map string table into our address space. This gives us
+ * an easy way to randomly access all the strings, without
+ * making the memory allocation permanent as with
+ * malloc/free (i.e., munmap will return it to the
+ * system).
+ */
+ base = mmap(NULL, (size_t)symstrsize, PROT_READ,
+ MAP_PRIVATE, fd, (off_t)symstroff);
+ if (base == MAP_FAILED)
+ continue;
+
+ if (lseek(fd, (off_t)symoff, SEEK_SET) == -1)
+ nent = -1;
+ else
+ nent = elf_scan_symtab(shdr, &ehdr, fd, base,
+ symsize, list, nent);
+
+ errsave = errno;
+ munmap(base, symstrsize);
+ errno = errsave;
}
+ errsave = errno;
+ munmap(shdr, shdr_size);
+ errno = errsave;
+ return (nent);
+}
+
+static int
+elf_scan_symtab(Elf_Shdr *shdr, Elf_Ehdr *ehdr, int fd, char *strtab,
+ size_t symsize, struct nlist *list, int nent)
+{
+ Elf_Sym sbuf[1024];
+ Elf_Sym *s;
+ char *name;
+ struct nlist *p;
+ Elf_Ssize cc;
while (symsize > 0 && nent > 0) {
cc = MIN(symsize, sizeof(sbuf));
@@ -225,31 +247,18 @@
break;
symsize -= cc;
for (s = sbuf; cc > 0 && nent > 0; ++s, cc -= sizeof(*s)) {
- char *name;
- struct nlist *p;
-
name = strtab + s->st_name;
if (name[0] == '\0')
continue;
- for (p = list; !ISLAST(p); p++) {
+ for (p = list; nent > 0 && !ISLAST(p); p++) {
if ((p->n_un.n_name[0] == '_' &&
- strcmp(name, p->n_un.n_name+1) == 0)
- || strcmp(name, p->n_un.n_name) == 0) {
+ strcmp(name, p->n_un.n_name+1) == 0) ||
+ strcmp(name, p->n_un.n_name) == 0)
elf_sym_to_nlist(p, s, shdr,
- ehdr.e_shnum);
- if (--nent <= 0)
- break;
- }
+ ehdr->e_shnum);
}
}
}
- done:
- errsave = errno;
- if (strtab != NULL)
- munmap(strtab, symstrsize);
- if (shdr != NULL)
- munmap(shdr, shdr_size);
- errno = errsave;
return (nent);
}
File Metadata
Details
Attached
Mime Type
text/plain
Expires
Wed, Jul 22, 5:40 PM (17 h, 56 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
33217057
Default Alt Text
D57034.id177945.diff (4 KB)
Attached To
Mode
D57034: nlist: Handle multiple symbol tables
Attached
Detach File
Event Timeline
Log In to Comment