Print this page
3451 archive libraries with no symbols shouldn't require a string table
@@ -103,50 +103,57 @@
register size_t n;
if (is64) {
if (sz < 8 || (sz - 8) / 8 < (n = get8(off))) {
_elf_seterr(EFMT_ARSYMSZ, 0);
- return (0);
+ return (NULL);
}
} else {
if (sz < 4 || (sz - 4) / 4 < (n = get4(off))) {
_elf_seterr(EFMT_ARSYMSZ, 0);
- return (0);
+ return (NULL);
}
}
off += eltsize;
endoff = off + n * eltsize;
/*
- * string table must be present, null terminated
+ * If there are symbols in the symbol table, a
+ * string table must be present and NULL terminated.
+ *
+ * The format dictates that the string table must always be
+ * present, however in the case of an archive containing no
+ * symbols GNU ar will not create one. We are permissive for
+ * the sake of compatibility.
*/
-
- if (((str = (char *)endoff) >= endstr) ||
- (*(endstr - 1) != '\0')) {
+ if ((n > 0) && (((str = (char *)endoff) >= endstr) ||
+ (*(endstr - 1) != '\0'))) {
_elf_seterr(EFMT_ARSYM, 0);
- return (0);
+ return (NULL);
}
/*
+ * There is always at least one entry returned if a symtab
+ * exists since the table's last entry is an artificial one
+ * with a NULL as_name, but is included in the count.
+ *
* overflow can occur here, but not likely
*/
-
*e = n + 1;
- n = sizeof (Elf_Arsym) * (n + 1);
- if ((oas = malloc(n)) == 0) {
+ if ((oas = calloc(n + 1, sizeof (Elf_Arsym))) == NULL) {
_elf_seterr(EMEM_ARSYM, errno);
- return (0);
+ return (NULL);
}
}
{
register Elf_Arsym *as = (Elf_Arsym *)oas;
while (off < endoff) {
if (str >= endstr) {
_elf_seterr(EFMT_ARSYMSTR, 0);
free(oas);
- return (0);
+ return (NULL);
}
if (is64)
as->as_off = get8(off);
else
as->as_off = get4(off);
@@ -156,11 +163,11 @@
off += eltsize;
while (*str++ != '\0')
/* LINTED */
;
}
- as->as_name = 0;
+ as->as_name = NULL;
as->as_off = 0;
as->as_hash = ~(unsigned long)0L;
}
return (oas);
}