mirror of
https://github.com/jart/cosmopolitan.git
synced 2025-05-29 16:52:28 +00:00
Fix unzip warning with apelink generated symtabs
This commit is contained in:
parent
3e6d536822
commit
0c89516ac5
17 changed files with 192 additions and 59 deletions
|
@ -27,7 +27,7 @@ int64_t GetZipCfileCompressedSize(const uint8_t *z) {
|
||||||
}
|
}
|
||||||
const uint8_t *p = ZIP_CFILE_EXTRA(z);
|
const uint8_t *p = ZIP_CFILE_EXTRA(z);
|
||||||
const uint8_t *pe = p + ZIP_CFILE_EXTRASIZE(z);
|
const uint8_t *pe = p + ZIP_CFILE_EXTRASIZE(z);
|
||||||
for (; p < pe; p += ZIP_EXTRA_SIZE(p)) {
|
for (; p + ZIP_EXTRA_SIZE(p) <= pe; p += ZIP_EXTRA_SIZE(p)) {
|
||||||
if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64) {
|
if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64) {
|
||||||
if (8 <= ZIP_EXTRA_CONTENTSIZE(p)) {
|
if (8 <= ZIP_EXTRA_CONTENTSIZE(p)) {
|
||||||
return READ64LE(ZIP_EXTRA_CONTENT(p));
|
return READ64LE(ZIP_EXTRA_CONTENT(p));
|
||||||
|
|
|
@ -27,7 +27,7 @@ int64_t GetZipCfileOffset(const uint8_t *z) {
|
||||||
}
|
}
|
||||||
const uint8_t *p = ZIP_CFILE_EXTRA(z);
|
const uint8_t *p = ZIP_CFILE_EXTRA(z);
|
||||||
const uint8_t *pe = p + ZIP_CFILE_EXTRASIZE(z);
|
const uint8_t *pe = p + ZIP_CFILE_EXTRASIZE(z);
|
||||||
for (; p < pe; p += ZIP_EXTRA_SIZE(p)) {
|
for (; p + ZIP_EXTRA_SIZE(p) <= pe; p += ZIP_EXTRA_SIZE(p)) {
|
||||||
if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64) {
|
if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64) {
|
||||||
int offset = 0;
|
int offset = 0;
|
||||||
if (ZIP_CFILE_COMPRESSEDSIZE(z) == 0xFFFFFFFFu) {
|
if (ZIP_CFILE_COMPRESSEDSIZE(z) == 0xFFFFFFFFu) {
|
||||||
|
|
|
@ -27,7 +27,7 @@ int64_t GetZipCfileUncompressedSize(const uint8_t *z) {
|
||||||
}
|
}
|
||||||
const uint8_t *p = ZIP_CFILE_EXTRA(z);
|
const uint8_t *p = ZIP_CFILE_EXTRA(z);
|
||||||
const uint8_t *pe = p + ZIP_CFILE_EXTRASIZE(z);
|
const uint8_t *pe = p + ZIP_CFILE_EXTRASIZE(z);
|
||||||
for (; p < pe; p += ZIP_EXTRA_SIZE(p)) {
|
for (; p + ZIP_EXTRA_SIZE(p) <= pe; p += ZIP_EXTRA_SIZE(p)) {
|
||||||
if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64) {
|
if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64) {
|
||||||
int offset = 0;
|
int offset = 0;
|
||||||
if (ZIP_CFILE_COMPRESSEDSIZE(z) == 0xFFFFFFFFu) {
|
if (ZIP_CFILE_COMPRESSEDSIZE(z) == 0xFFFFFFFFu) {
|
||||||
|
|
|
@ -27,7 +27,7 @@ int64_t GetZipLfileCompressedSize(const uint8_t *z) {
|
||||||
}
|
}
|
||||||
const uint8_t *p = ZIP_LFILE_EXTRA(z);
|
const uint8_t *p = ZIP_LFILE_EXTRA(z);
|
||||||
const uint8_t *pe = p + ZIP_LFILE_EXTRASIZE(z);
|
const uint8_t *pe = p + ZIP_LFILE_EXTRASIZE(z);
|
||||||
for (; p < pe; p += ZIP_EXTRA_SIZE(p)) {
|
for (; p + ZIP_EXTRA_SIZE(p) <= pe; p += ZIP_EXTRA_SIZE(p)) {
|
||||||
if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64) {
|
if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64) {
|
||||||
if (8 <= ZIP_EXTRA_CONTENTSIZE(p)) {
|
if (8 <= ZIP_EXTRA_CONTENTSIZE(p)) {
|
||||||
return READ64LE(ZIP_EXTRA_CONTENT(p));
|
return READ64LE(ZIP_EXTRA_CONTENT(p));
|
||||||
|
|
|
@ -27,7 +27,7 @@ int64_t GetZipLfileUncompressedSize(const uint8_t *z) {
|
||||||
}
|
}
|
||||||
const uint8_t *p = ZIP_LFILE_EXTRA(z);
|
const uint8_t *p = ZIP_LFILE_EXTRA(z);
|
||||||
const uint8_t *pe = p + ZIP_LFILE_EXTRASIZE(z);
|
const uint8_t *pe = p + ZIP_LFILE_EXTRASIZE(z);
|
||||||
for (; p < pe; p += ZIP_EXTRA_SIZE(p)) {
|
for (; p + ZIP_EXTRA_SIZE(p) <= pe; p += ZIP_EXTRA_SIZE(p)) {
|
||||||
if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64) {
|
if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64) {
|
||||||
int offset = 0;
|
int offset = 0;
|
||||||
if (ZIP_LFILE_COMPRESSEDSIZE(z) == 0xFFFFFFFFu) {
|
if (ZIP_LFILE_COMPRESSEDSIZE(z) == 0xFFFFFFFFu) {
|
||||||
|
|
|
@ -89,6 +89,8 @@
|
||||||
|
|
||||||
#define kZipCfileHdrMagic ZM_(0x02014b50) /* PK☺☻ "PK\1\2" */
|
#define kZipCfileHdrMagic ZM_(0x02014b50) /* PK☺☻ "PK\1\2" */
|
||||||
#define kZipCfileHdrMinSize 46
|
#define kZipCfileHdrMinSize 46
|
||||||
|
#define kZipCfileOffsetVersionMadeBy 4
|
||||||
|
#define kZipCfileOffsetVersionNeeded 6
|
||||||
#define kZipCfileOffsetGeneralflag 8
|
#define kZipCfileOffsetGeneralflag 8
|
||||||
#define kZipCfileOffsetCompressionmethod 10
|
#define kZipCfileOffsetCompressionmethod 10
|
||||||
#define kZipCfileOffsetLastmodifiedtime 12
|
#define kZipCfileOffsetLastmodifiedtime 12
|
||||||
|
|
|
@ -674,9 +674,10 @@ static void LoadSymbols(Elf64_Ehdr *e, Elf64_Off size, const char *path) {
|
||||||
unsigned char *cfile = Malloc(cfile_size);
|
unsigned char *cfile = Malloc(cfile_size);
|
||||||
bzero(cfile, cfile_size);
|
bzero(cfile, cfile_size);
|
||||||
WRITE32LE(cfile, kZipCfileHdrMagic);
|
WRITE32LE(cfile, kZipCfileHdrMagic);
|
||||||
cfile[4] = kZipCosmopolitanVersion;
|
WRITE16LE(cfile + kZipCfileOffsetVersionMadeBy,
|
||||||
cfile[5] = kZipOsUnix;
|
kZipOsUnix << 8 | kZipCosmopolitanVersion);
|
||||||
cfile[6] = kZipEra2001;
|
WRITE16LE(cfile + kZipCfileOffsetVersionNeeded, kZipEra2001);
|
||||||
|
WRITE16LE(cfile + kZipCfileOffsetGeneralflag, kZipGflagUtf8);
|
||||||
WRITE16LE(cfile + kZipCfileOffsetCompressionmethod, kZipCompressionDeflate);
|
WRITE16LE(cfile + kZipCfileOffsetCompressionmethod, kZipCompressionDeflate);
|
||||||
WRITE16LE(cfile + kZipCfileOffsetLastmodifieddate, DOS_DATE(2023, 7, 29));
|
WRITE16LE(cfile + kZipCfileOffsetLastmodifieddate, DOS_DATE(2023, 7, 29));
|
||||||
WRITE16LE(cfile + kZipCfileOffsetLastmodifiedtime, DOS_TIME(0, 0, 0));
|
WRITE16LE(cfile + kZipCfileOffsetLastmodifiedtime, DOS_TIME(0, 0, 0));
|
||||||
|
@ -1813,9 +1814,11 @@ int main(int argc, char *argv[]) {
|
||||||
int i, j;
|
int i, j;
|
||||||
Elf64_Off offset;
|
Elf64_Off offset;
|
||||||
Elf64_Xword prologue_bytes;
|
Elf64_Xword prologue_bytes;
|
||||||
#ifndef NDEBUG
|
|
||||||
|
#ifdef MODE_DBG
|
||||||
ShowCrashReports();
|
ShowCrashReports();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
prog = argv[0];
|
prog = argv[0];
|
||||||
if (!prog) prog = "apelink";
|
if (!prog) prog = "apelink";
|
||||||
|
|
||||||
|
@ -2080,7 +2083,8 @@ int main(int argc, char *argv[]) {
|
||||||
p = stpcpy(p, " count=");
|
p = stpcpy(p, " count=");
|
||||||
loader->ddarg_size1 = p;
|
loader->ddarg_size1 = p;
|
||||||
p = GenerateDecimalOffsetRelocation(p);
|
p = GenerateDecimalOffsetRelocation(p);
|
||||||
p = stpcpy(p, " bs=1 2>/dev/null | gzip -dc >\"$t.$$\" ||exit\n");
|
p = stpcpy(
|
||||||
|
p, " bs=1 2>/dev/null | /usr/bin/gzip -dc >\"$t.$$\" ||exit\n");
|
||||||
if (loader->macho_offset) {
|
if (loader->macho_offset) {
|
||||||
p = stpcpy(p, "/bin/dd if=\"$t.$$\" of=\"$t.$$\"");
|
p = stpcpy(p, "/bin/dd if=\"$t.$$\" of=\"$t.$$\"");
|
||||||
p = stpcpy(p, " skip=");
|
p = stpcpy(p, " skip=");
|
||||||
|
|
|
@ -294,7 +294,7 @@ int main(int argc, char *argv[]) {
|
||||||
struct ar_hdr header1;
|
struct ar_hdr header1;
|
||||||
struct ar_hdr header2;
|
struct ar_hdr header2;
|
||||||
|
|
||||||
#ifndef NDEBUG
|
#ifdef MODE_DBG
|
||||||
ShowCrashReports();
|
ShowCrashReports();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
|
@ -837,7 +837,7 @@ int main(int argc, char *argv[]) {
|
||||||
char *s, *q, **envp;
|
char *s, *q, **envp;
|
||||||
int ws, opt, exitcode;
|
int ws, opt, exitcode;
|
||||||
|
|
||||||
#ifndef NDEBUG
|
#ifdef MODE_DBG
|
||||||
ShowCrashReports();
|
ShowCrashReports();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
|
@ -1078,7 +1078,7 @@ static void Pwrite(int fd, const void *data, size_t size, uint64_t offset) {
|
||||||
}
|
}
|
||||||
|
|
||||||
int main(int argc, char *argv[]) {
|
int main(int argc, char *argv[]) {
|
||||||
#ifndef NDEBUG
|
#ifdef MODE_DBG
|
||||||
ShowCrashReports();
|
ShowCrashReports();
|
||||||
#endif
|
#endif
|
||||||
// get program name
|
// get program name
|
||||||
|
|
|
@ -124,6 +124,8 @@ static const uint32_t kSourceExts[] = {
|
||||||
EXT("c"), // c
|
EXT("c"), // c
|
||||||
EXT("cc"), // c++
|
EXT("cc"), // c++
|
||||||
EXT("cpp"), // c++
|
EXT("cpp"), // c++
|
||||||
|
EXT("cu"), // cuda
|
||||||
|
EXT("m"), // objective c
|
||||||
};
|
};
|
||||||
|
|
||||||
static char *names;
|
static char *names;
|
||||||
|
@ -667,7 +669,7 @@ int main(int argc, char *argv[]) {
|
||||||
ssize_t rc;
|
ssize_t rc;
|
||||||
size_t i, n;
|
size_t i, n;
|
||||||
char *makefile;
|
char *makefile;
|
||||||
#ifndef NDEBUG
|
#ifdef MODE_DBG
|
||||||
ShowCrashReports();
|
ShowCrashReports();
|
||||||
#endif
|
#endif
|
||||||
prog = argv[0];
|
prog = argv[0];
|
||||||
|
|
|
@ -71,7 +71,7 @@
|
||||||
" INPUT is an elf executable made by the unix linker\n" \
|
" INPUT is an elf executable made by the unix linker\n" \
|
||||||
"\n"
|
"\n"
|
||||||
|
|
||||||
#ifndef NDEBUG
|
#ifdef MODE_DBG
|
||||||
#define DEBUG(...) kprintf("DEBUG: " __VA_ARGS__)
|
#define DEBUG(...) kprintf("DEBUG: " __VA_ARGS__)
|
||||||
#else
|
#else
|
||||||
#define DEBUG(...) (void)0
|
#define DEBUG(...) (void)0
|
||||||
|
|
|
@ -114,7 +114,7 @@ struct Packages {
|
||||||
Elf64_Xword symcount; // not persisted
|
Elf64_Xword symcount; // not persisted
|
||||||
int section_offset;
|
int section_offset;
|
||||||
int section_count;
|
int section_count;
|
||||||
} * p;
|
} *p;
|
||||||
} objects;
|
} objects;
|
||||||
struct Sections {
|
struct Sections {
|
||||||
size_t i, n;
|
size_t i, n;
|
||||||
|
@ -128,7 +128,7 @@ struct Packages {
|
||||||
kBss,
|
kBss,
|
||||||
kOther,
|
kOther,
|
||||||
} kind;
|
} kind;
|
||||||
} * p;
|
} *p;
|
||||||
} sections;
|
} sections;
|
||||||
struct Symbols {
|
struct Symbols {
|
||||||
size_t i, n;
|
size_t i, n;
|
||||||
|
@ -139,9 +139,9 @@ struct Packages {
|
||||||
uint8_t type : 4;
|
uint8_t type : 4;
|
||||||
uint16_t object; // pkg->objects.p[object]
|
uint16_t object; // pkg->objects.p[object]
|
||||||
uint16_t section; // pkg->sections.p[section]
|
uint16_t section; // pkg->sections.p[section]
|
||||||
} * p; // persisted as pkg+RVA
|
} *p; // persisted as pkg+RVA
|
||||||
} symbols, undefs; // TODO(jart): hash undefs?
|
} symbols, undefs; // TODO(jart): hash undefs?
|
||||||
} * *p; // persisted across multiple files
|
} **p; // persisted across multiple files
|
||||||
};
|
};
|
||||||
|
|
||||||
struct Relas {
|
struct Relas {
|
||||||
|
@ -150,7 +150,7 @@ struct Relas {
|
||||||
struct Rela {
|
struct Rela {
|
||||||
const char *symbol_name;
|
const char *symbol_name;
|
||||||
const char *object_path;
|
const char *object_path;
|
||||||
} * p;
|
} *p;
|
||||||
} prtu;
|
} prtu;
|
||||||
|
|
||||||
static wontreturn void Die(const char *path, const char *reason) {
|
static wontreturn void Die(const char *path, const char *reason) {
|
||||||
|
@ -649,7 +649,7 @@ int main(int argc, char *argv[]) {
|
||||||
if (argc == 2 && !strcmp(argv[1], "-n")) {
|
if (argc == 2 && !strcmp(argv[1], "-n")) {
|
||||||
exit(0);
|
exit(0);
|
||||||
}
|
}
|
||||||
#ifndef NDEBUG
|
#ifdef MODE_DBG
|
||||||
ShowCrashReports();
|
ShowCrashReports();
|
||||||
#endif
|
#endif
|
||||||
bzero(&pkg, sizeof(pkg));
|
bzero(&pkg, sizeof(pkg));
|
||||||
|
|
|
@ -312,7 +312,7 @@ int main(int argc, char *argv[]) {
|
||||||
void *map;
|
void *map;
|
||||||
ssize_t size;
|
ssize_t size;
|
||||||
const char *path;
|
const char *path;
|
||||||
#ifndef NDEBUG
|
#ifdef MODE_DBG
|
||||||
ShowCrashReports();
|
ShowCrashReports();
|
||||||
#endif
|
#endif
|
||||||
for (i = 1; i < argc; ++i) {
|
for (i = 1; i < argc; ++i) {
|
||||||
|
|
|
@ -809,7 +809,7 @@ int main(int argc, char *argv[]) {
|
||||||
if (g_daemonize) Daemonize();
|
if (g_daemonize) Daemonize();
|
||||||
Serve();
|
Serve();
|
||||||
free(g_psk);
|
free(g_psk);
|
||||||
#if IsModeDbg()
|
#ifdef MODE_DBG
|
||||||
CheckForMemoryLeaks();
|
CheckForMemoryLeaks();
|
||||||
CheckForFileLeaks();
|
CheckForFileLeaks();
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -211,7 +211,7 @@ static void CopyZip(void) {
|
||||||
}
|
}
|
||||||
|
|
||||||
int main(int argc, char *argv[]) {
|
int main(int argc, char *argv[]) {
|
||||||
#ifndef NDEBUG
|
#ifdef MODE_DBG
|
||||||
ShowCrashReports();
|
ShowCrashReports();
|
||||||
#endif
|
#endif
|
||||||
prog = argv[0];
|
prog = argv[0];
|
||||||
|
|
|
@ -21,6 +21,7 @@
|
||||||
#include "libc/fmt/libgen.h"
|
#include "libc/fmt/libgen.h"
|
||||||
#include "libc/fmt/wintime.internal.h"
|
#include "libc/fmt/wintime.internal.h"
|
||||||
#include "libc/intrin/bits.h"
|
#include "libc/intrin/bits.h"
|
||||||
|
#include "libc/intrin/kprintf.h"
|
||||||
#include "libc/intrin/safemacros.internal.h"
|
#include "libc/intrin/safemacros.internal.h"
|
||||||
#include "libc/log/check.h"
|
#include "libc/log/check.h"
|
||||||
#include "libc/log/log.h"
|
#include "libc/log/log.h"
|
||||||
|
@ -28,6 +29,7 @@
|
||||||
#include "libc/mem/mem.h"
|
#include "libc/mem/mem.h"
|
||||||
#include "libc/nexgen32e/crc32.h"
|
#include "libc/nexgen32e/crc32.h"
|
||||||
#include "libc/nt/struct/filetime.h"
|
#include "libc/nt/struct/filetime.h"
|
||||||
|
#include "libc/stdckdint.h"
|
||||||
#include "libc/stdio/stdio.h"
|
#include "libc/stdio/stdio.h"
|
||||||
#include "libc/stdio/sysparam.h"
|
#include "libc/stdio/sysparam.h"
|
||||||
#include "libc/str/str.h"
|
#include "libc/str/str.h"
|
||||||
|
@ -150,21 +152,71 @@ void ShowExtendedTimestamp(uint8_t *p, size_t n, bool islocal) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void ShowZip64(uint8_t *p, size_t n, bool islocal) {
|
void ShowZip64(uint8_t *lf, uint8_t *p, size_t n, bool islocal) {
|
||||||
if (n >= 8) {
|
int i = 0;
|
||||||
show(".quad", _gc(xasprintf("%lu", READ64LE(p))),
|
|
||||||
_gc(xasprintf("uncompressed size (%,ld)", READ64LE(p))));
|
uint32_t uncompsize;
|
||||||
|
if (islocal) {
|
||||||
|
uncompsize = ZIP_LFILE_UNCOMPRESSEDSIZE(lf);
|
||||||
|
} else {
|
||||||
|
uncompsize = ZIP_CFILE_UNCOMPRESSEDSIZE(lf);
|
||||||
}
|
}
|
||||||
if (n >= 16) {
|
if (uncompsize == 0xffffffffu) {
|
||||||
show(".quad", _gc(xasprintf("%lu", READ64LE(p + 8))),
|
if (i + 8 <= n) {
|
||||||
_gc(xasprintf("compressed size (%,ld)", READ64LE(p + 8))));
|
show(".quad", _gc(xasprintf("0x%lx", READ64LE(p + i))),
|
||||||
|
_gc(xasprintf("uncompressed size (%,ld)", READ64LE(p + i))));
|
||||||
|
} else {
|
||||||
|
kprintf("/\tWARNING: ZIP64 EXTRA MISSING UNCOMPRESSED SIZE\n");
|
||||||
|
}
|
||||||
|
i += 8;
|
||||||
}
|
}
|
||||||
if (n >= 24) {
|
|
||||||
show(".quad", _gc(xasprintf("%lu", READ64LE(p + 16))),
|
uint32_t compsize;
|
||||||
_gc(xasprintf("lfile hdr offset (%,ld)", READ64LE(p + 16))));
|
if (islocal) {
|
||||||
|
compsize = ZIP_LFILE_COMPRESSEDSIZE(lf);
|
||||||
|
} else {
|
||||||
|
compsize = ZIP_CFILE_COMPRESSEDSIZE(lf);
|
||||||
}
|
}
|
||||||
if (n >= 28) {
|
if (compsize == 0xffffffffu) {
|
||||||
show(".long", _gc(xasprintf("%u", READ32LE(p + 24))), "disk number");
|
if (i + 8 <= n) {
|
||||||
|
show(".quad", _gc(xasprintf("0x%lx", READ64LE(p + i))),
|
||||||
|
_gc(xasprintf("compressed size (%,ld)", READ64LE(p + i))));
|
||||||
|
} else {
|
||||||
|
kprintf("/\tWARNING: ZIP64 EXTRA MISSING COMPRESSED SIZE\n");
|
||||||
|
}
|
||||||
|
i += 8;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!islocal) {
|
||||||
|
uint32_t offset;
|
||||||
|
offset = ZIP_CFILE_OFFSET(lf);
|
||||||
|
if (offset == 0xffffffffu) {
|
||||||
|
if (i + 8 <= n) {
|
||||||
|
show(".quad", _gc(xasprintf("0x%lx", READ64LE(p + i))),
|
||||||
|
_gc(xasprintf("lfile offset (%,ld)", READ64LE(p + i))));
|
||||||
|
} else {
|
||||||
|
kprintf("/\tWARNING: ZIP64 EXTRA MISSING OFFSET\n");
|
||||||
|
}
|
||||||
|
i += 8;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!islocal) {
|
||||||
|
uint16_t disk;
|
||||||
|
disk = ZIP_CFILE_DISK(lf);
|
||||||
|
if (disk == 0xffff) {
|
||||||
|
if (i + 4 <= n) {
|
||||||
|
show(".long", _gc(xasprintf("0x%x", READ32LE(p + i))),
|
||||||
|
_gc(xasprintf("lfile disk (%,ld)", READ32LE(p + i))));
|
||||||
|
} else {
|
||||||
|
kprintf("/\tWARNING: ZIP64 EXTRA MISSING DISK\n");
|
||||||
|
}
|
||||||
|
i += 8;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (i != n) {
|
||||||
|
kprintf("/\tWARNING: ZIP64 EXTRA HAS SUPERFLUOUS CONTENT\n");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -180,7 +232,7 @@ void ShowInfoZipNewUnixExtra(uint8_t *p, size_t n, bool islocal) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void ShowExtra(uint8_t *extra, bool islocal) {
|
void ShowExtra(uint8_t *lf, uint8_t *extra, bool islocal) {
|
||||||
switch (ZIP_EXTRA_HEADERID(extra)) {
|
switch (ZIP_EXTRA_HEADERID(extra)) {
|
||||||
case kZipExtraNtfs:
|
case kZipExtraNtfs:
|
||||||
ShowNtfs(ZIP_EXTRA_CONTENT(extra), ZIP_EXTRA_CONTENTSIZE(extra));
|
ShowNtfs(ZIP_EXTRA_CONTENT(extra), ZIP_EXTRA_CONTENTSIZE(extra));
|
||||||
|
@ -190,7 +242,7 @@ void ShowExtra(uint8_t *extra, bool islocal) {
|
||||||
ZIP_EXTRA_CONTENTSIZE(extra), islocal);
|
ZIP_EXTRA_CONTENTSIZE(extra), islocal);
|
||||||
break;
|
break;
|
||||||
case kZipExtraZip64:
|
case kZipExtraZip64:
|
||||||
ShowZip64(ZIP_EXTRA_CONTENT(extra), ZIP_EXTRA_CONTENTSIZE(extra),
|
ShowZip64(lf, ZIP_EXTRA_CONTENT(extra), ZIP_EXTRA_CONTENTSIZE(extra),
|
||||||
islocal);
|
islocal);
|
||||||
break;
|
break;
|
||||||
case kZipExtraInfoZipNewUnixExtra:
|
case kZipExtraInfoZipNewUnixExtra:
|
||||||
|
@ -216,7 +268,8 @@ void ShowExternalAttributes(uint8_t *cf) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void ShowExtras(uint8_t *extras, uint16_t extrassize, bool islocal) {
|
void ShowExtras(uint8_t *lf, uint8_t *extras, uint16_t extrassize,
|
||||||
|
bool islocal) {
|
||||||
int i;
|
int i;
|
||||||
bool first;
|
bool first;
|
||||||
uint8_t *p, *pe;
|
uint8_t *p, *pe;
|
||||||
|
@ -235,7 +288,7 @@ void ShowExtras(uint8_t *extras, uint16_t extrassize, bool islocal) {
|
||||||
first = false;
|
first = false;
|
||||||
printf("%d:", (i + 1) * 10);
|
printf("%d:", (i + 1) * 10);
|
||||||
}
|
}
|
||||||
ShowExtra(p, islocal);
|
ShowExtra(lf, p, islocal);
|
||||||
printf("%d:", (i + 2) * 10);
|
printf("%d:", (i + 2) * 10);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -243,8 +296,8 @@ void ShowExtras(uint8_t *extras, uint16_t extrassize, bool islocal) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void ShowLocalFileHeader(uint8_t *lf, uint16_t idx) {
|
void ShowLocalFileHeader(uint8_t *lf, uint16_t idx) {
|
||||||
printf("\n/\t%s #%hu (%zu %s)\n", "local file", idx + 1,
|
printf("\n/\t%s #%hu (%zu %s @ %#lx)\n", "local file", idx + 1,
|
||||||
ZIP_LFILE_HDRSIZE(lf), "bytes");
|
ZIP_LFILE_HDRSIZE(lf), "bytes", lf - map);
|
||||||
show(".ascii", format(b1, "%`'.*s", 4, lf), "magic");
|
show(".ascii", format(b1, "%`'.*s", 4, lf), "magic");
|
||||||
show(".byte",
|
show(".byte",
|
||||||
firstnonnull(findnamebyid(kZipEraNames, ZIP_LFILE_VERSIONNEED(lf)),
|
firstnonnull(findnamebyid(kZipEraNames, ZIP_LFILE_VERSIONNEED(lf)),
|
||||||
|
@ -283,7 +336,7 @@ void ShowLocalFileHeader(uint8_t *lf, uint16_t idx) {
|
||||||
_gc(strndup(ZIP_LFILE_NAME(lf), ZIP_LFILE_NAMESIZE(lf)))),
|
_gc(strndup(ZIP_LFILE_NAME(lf), ZIP_LFILE_NAMESIZE(lf)))),
|
||||||
"name");
|
"name");
|
||||||
printf("1:");
|
printf("1:");
|
||||||
ShowExtras(ZIP_LFILE_EXTRA(lf), ZIP_LFILE_EXTRASIZE(lf), true);
|
ShowExtras(lf, ZIP_LFILE_EXTRA(lf), ZIP_LFILE_EXTRASIZE(lf), true);
|
||||||
printf("2:");
|
printf("2:");
|
||||||
/* disassemblehex(ZIP_LFILE_CONTENT(lf), ZIP_LFILE_COMPRESSEDSIZE(lf),
|
/* disassemblehex(ZIP_LFILE_CONTENT(lf), ZIP_LFILE_COMPRESSEDSIZE(lf),
|
||||||
* stdout); */
|
* stdout); */
|
||||||
|
@ -340,7 +393,7 @@ void ShowCentralFileHeader(uint8_t *cf) {
|
||||||
if (ZIP_CFILE_OFFSET(cf) == 0xFFFFFFFF) {
|
if (ZIP_CFILE_OFFSET(cf) == 0xFFFFFFFF) {
|
||||||
show(".long", "0xFFFFFFFF", "lfile hdr offset (zip64)");
|
show(".long", "0xFFFFFFFF", "lfile hdr offset (zip64)");
|
||||||
} else {
|
} else {
|
||||||
show(".long", format(b1, "%u", ZIP_CFILE_OFFSET(cf)), "lfile hdr offset");
|
show(".long", format(b1, "0x%x", ZIP_CFILE_OFFSET(cf)), "lfile hdr offset");
|
||||||
}
|
}
|
||||||
printf("0:");
|
printf("0:");
|
||||||
show(".ascii",
|
show(".ascii",
|
||||||
|
@ -348,7 +401,7 @@ void ShowCentralFileHeader(uint8_t *cf) {
|
||||||
_gc(strndup(ZIP_CFILE_NAME(cf), ZIP_CFILE_NAMESIZE(cf)))),
|
_gc(strndup(ZIP_CFILE_NAME(cf), ZIP_CFILE_NAMESIZE(cf)))),
|
||||||
"name");
|
"name");
|
||||||
printf("1:");
|
printf("1:");
|
||||||
ShowExtras(ZIP_CFILE_EXTRA(cf), ZIP_CFILE_EXTRASIZE(cf), false);
|
ShowExtras(cf, ZIP_CFILE_EXTRA(cf), ZIP_CFILE_EXTRASIZE(cf), false);
|
||||||
printf("2:");
|
printf("2:");
|
||||||
show(".ascii",
|
show(".ascii",
|
||||||
format(b1, "%`'.*s", ZIP_CFILE_COMMENTSIZE(cf), ZIP_CFILE_COMMENT(cf)),
|
format(b1, "%`'.*s", ZIP_CFILE_COMMENTSIZE(cf), ZIP_CFILE_COMMENT(cf)),
|
||||||
|
@ -357,8 +410,8 @@ void ShowCentralFileHeader(uint8_t *cf) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void ShowCentralDirHeader32(uint8_t *cd) {
|
void ShowCentralDirHeader32(uint8_t *cd) {
|
||||||
printf("\n/\t%s (%zu %s)\n", "end of central directory header",
|
printf("\n/\t%s (%zu %s @ %#lx)\n", "end of central directory header",
|
||||||
ZIP_CDIR_HDRSIZE(cd), "bytes");
|
ZIP_CDIR_HDRSIZE(cd), "bytes", cd - map);
|
||||||
show(".ascii", format(b1, "%`'.*s", 4, cd), "magic");
|
show(".ascii", format(b1, "%`'.*s", 4, cd), "magic");
|
||||||
show(".short", format(b1, "%hd", ZIP_CDIR_DISK(cd)), "disk");
|
show(".short", format(b1, "%hd", ZIP_CDIR_DISK(cd)), "disk");
|
||||||
show(".short", format(b1, "%hd", ZIP_CDIR_STARTINGDISK(cd)), "startingdisk");
|
show(".short", format(b1, "%hd", ZIP_CDIR_STARTINGDISK(cd)), "startingdisk");
|
||||||
|
@ -366,7 +419,7 @@ void ShowCentralDirHeader32(uint8_t *cd) {
|
||||||
"recordsondisk");
|
"recordsondisk");
|
||||||
show(".short", format(b1, "%hu", ZIP_CDIR_RECORDS(cd)), "records");
|
show(".short", format(b1, "%hu", ZIP_CDIR_RECORDS(cd)), "records");
|
||||||
show(".long", format(b1, "%u", ZIP_CDIR_SIZE(cd)), "size");
|
show(".long", format(b1, "%u", ZIP_CDIR_SIZE(cd)), "size");
|
||||||
show(".long", format(b1, "%u", ZIP_CDIR_OFFSET(cd)), "cfile hdrs offset");
|
show(".long", format(b1, "0x%x", ZIP_CDIR_OFFSET(cd)), "cfile hdrs offset");
|
||||||
show(".short", "1f-0f",
|
show(".short", "1f-0f",
|
||||||
format(b1, "%s (%hu %s)", "commentsize", ZIP_CDIR_COMMENTSIZE(cd),
|
format(b1, "%s (%hu %s)", "commentsize", ZIP_CDIR_COMMENTSIZE(cd),
|
||||||
"bytes"));
|
"bytes"));
|
||||||
|
@ -376,8 +429,8 @@ void ShowCentralDirHeader32(uint8_t *cd) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void ShowCentralDirHeader64(uint8_t *cd) {
|
void ShowCentralDirHeader64(uint8_t *cd) {
|
||||||
printf("\n/\t%s (%zu %s)\n", "zip64 end of central directory header",
|
printf("\n/\t%s (%zu %s @ %#lx)\n", "zip64 end of central directory header",
|
||||||
ZIP_CDIR64_HDRSIZE(cd), "bytes");
|
ZIP_CDIR64_HDRSIZE(cd), "bytes", cd - map);
|
||||||
show(".ascii", format(b1, "%`'.*s", 4, cd), "magic");
|
show(".ascii", format(b1, "%`'.*s", 4, cd), "magic");
|
||||||
show(".quad", format(b1, "%lu", ZIP_CDIR64_HDRSIZE(cd) - 12), "hdr size");
|
show(".quad", format(b1, "%lu", ZIP_CDIR64_HDRSIZE(cd) - 12), "hdr size");
|
||||||
show(".short", format(b1, "%hd", ZIP_CDIR64_VERSIONMADE(cd)), "version made");
|
show(".short", format(b1, "%hd", ZIP_CDIR64_VERSIONMADE(cd)), "version made");
|
||||||
|
@ -388,7 +441,7 @@ void ShowCentralDirHeader64(uint8_t *cd) {
|
||||||
"recordsondisk");
|
"recordsondisk");
|
||||||
show(".quad", format(b1, "%lu", ZIP_CDIR64_RECORDS(cd)), "records");
|
show(".quad", format(b1, "%lu", ZIP_CDIR64_RECORDS(cd)), "records");
|
||||||
show(".quad", format(b1, "%lu", ZIP_CDIR64_SIZE(cd)), "cdir size");
|
show(".quad", format(b1, "%lu", ZIP_CDIR64_SIZE(cd)), "cdir size");
|
||||||
show(".quad", format(b1, "%lu", ZIP_CDIR64_OFFSET(cd)), "cdir offset");
|
show(".quad", format(b1, "0x%lx", ZIP_CDIR64_OFFSET(cd)), "cdir offset");
|
||||||
printf("0:");
|
printf("0:");
|
||||||
disassemblehex(ZIP_CDIR64_COMMENT(cd), ZIP_CDIR64_COMMENTSIZE(cd), stdout);
|
disassemblehex(ZIP_CDIR64_COMMENT(cd), ZIP_CDIR64_COMMENTSIZE(cd), stdout);
|
||||||
printf("1:\n");
|
printf("1:\n");
|
||||||
|
@ -397,19 +450,87 @@ void ShowCentralDirHeader64(uint8_t *cd) {
|
||||||
kZipCdir64LocatorSize, "bytes");
|
kZipCdir64LocatorSize, "bytes");
|
||||||
show(".ascii", format(b1, "%`'.*s", 4, cd), "magic");
|
show(".ascii", format(b1, "%`'.*s", 4, cd), "magic");
|
||||||
show(".long", format(b1, "%d", READ32LE(cd + 4)), "startingdisk");
|
show(".long", format(b1, "%d", READ32LE(cd + 4)), "startingdisk");
|
||||||
show(".quad", format(b1, "%lu", READ64LE(cd + 4 + 4)), "eocd64 offset");
|
show(".quad", format(b1, "0x%lx", READ64LE(cd + 4 + 4)), "eocd64 offset");
|
||||||
show(".long", format(b1, "%d", READ32LE(cd + 4 + 4 + 8)), "totaldisks");
|
show(".long", format(b1, "%d", READ32LE(cd + 4 + 4 + 8)), "totaldisks");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static const char *DescribeZipError(int err) {
|
||||||
|
switch (err) {
|
||||||
|
case kZipErrorEocdNotFound:
|
||||||
|
return "kZipErrorEocdNotFound";
|
||||||
|
case kZipErrorEocdOffsetOverflow:
|
||||||
|
return "kZipErrorEocdOffsetOverflow";
|
||||||
|
case kZipErrorEocdMagicNotFound:
|
||||||
|
return "kZipErrorEocdMagicNotFound";
|
||||||
|
case kZipErrorEocdSizeOverflow:
|
||||||
|
return "kZipErrorEocdSizeOverflow";
|
||||||
|
case kZipErrorEocdDiskMismatch:
|
||||||
|
return "kZipErrorEocdDiskMismatch";
|
||||||
|
case kZipErrorEocdOffsetSizeOverflow:
|
||||||
|
return "kZipErrorEocdOffsetSizeOverflow";
|
||||||
|
case kZipErrorEocdRecordsMismatch:
|
||||||
|
return "kZipErrorEocdRecordsMismatch";
|
||||||
|
case kZipErrorEocdRecordsOverflow:
|
||||||
|
return "kZipErrorEocdRecordsOverflow";
|
||||||
|
case kZipErrorCdirOffsetPastEocd:
|
||||||
|
return "kZipErrorCdirOffsetPastEocd";
|
||||||
|
case kZipErrorEocdLocatorMagic:
|
||||||
|
return "kZipErrorEocdLocatorMagic";
|
||||||
|
case kZipErrorEocdLocatorOffset:
|
||||||
|
return "kZipErrorEocdLocatorOffset";
|
||||||
|
case kZipErrorRaceCondition:
|
||||||
|
return "kZipErrorRaceCondition";
|
||||||
|
case kZipErrorMapFailed:
|
||||||
|
return "kZipErrorMapFailed";
|
||||||
|
case kZipErrorOpenFailed:
|
||||||
|
return "kZipErrorOpenFailed";
|
||||||
|
default:
|
||||||
|
return "unknown";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int IsZipEocd32(const uint8_t *p, size_t n, size_t i) {
|
||||||
|
size_t offset;
|
||||||
|
if (i > n || n - i < kZipCdirHdrMinSize) {
|
||||||
|
return kZipErrorEocdOffsetOverflow;
|
||||||
|
}
|
||||||
|
if (READ32LE(p + i) != kZipCdirHdrMagic) {
|
||||||
|
return kZipErrorEocdMagicNotFound;
|
||||||
|
}
|
||||||
|
if (i + ZIP_CDIR_HDRSIZE(p + i) > n) {
|
||||||
|
return kZipErrorEocdSizeOverflow;
|
||||||
|
}
|
||||||
|
if (ZIP_CDIR_DISK(p + i) != ZIP_CDIR_STARTINGDISK(p + i)) {
|
||||||
|
return kZipErrorEocdDiskMismatch;
|
||||||
|
}
|
||||||
|
if (ZIP_CDIR_RECORDSONDISK(p + i) != ZIP_CDIR_RECORDS(p + i)) {
|
||||||
|
return kZipErrorEocdRecordsMismatch;
|
||||||
|
}
|
||||||
|
if (ZIP_CDIR_RECORDS(p + i) * kZipCfileHdrMinSize > ZIP_CDIR_SIZE(p + i)) {
|
||||||
|
return kZipErrorEocdRecordsOverflow;
|
||||||
|
}
|
||||||
|
if (ckd_add(&offset, ZIP_CDIR_OFFSET(p + i), ZIP_CDIR_SIZE(p + i))) {
|
||||||
|
return kZipErrorEocdOffsetSizeOverflow;
|
||||||
|
}
|
||||||
|
if (offset > i) {
|
||||||
|
return kZipErrorCdirOffsetPastEocd;
|
||||||
|
}
|
||||||
|
return kZipOk;
|
||||||
|
}
|
||||||
|
|
||||||
uint8_t *GetZipCdir32(const uint8_t *p, size_t n) {
|
uint8_t *GetZipCdir32(const uint8_t *p, size_t n) {
|
||||||
int64_t i, e;
|
int64_t i, e, err;
|
||||||
if (n >= kZipCdirHdrMinSize) {
|
if (n >= kZipCdirHdrMinSize) {
|
||||||
i = n - kZipCdirHdrMinSize;
|
i = n - kZipCdirHdrMinSize;
|
||||||
e = MAX(0, n - 65536);
|
e = MAX(0, n - 65536);
|
||||||
for (; i >= e; --i) {
|
for (; i >= e; --i) {
|
||||||
if (READ32LE(p + i) == kZipCdirHdrMagic &&
|
if (READ32LE(p + i) == kZipCdirHdrMagic) {
|
||||||
IsZipEocd32(p, n, i) == kZipOk) {
|
if ((err = IsZipEocd32(p, n, i)) == kZipOk) {
|
||||||
return (/*unconst*/ uint8_t *)(p + i);
|
return (/*unconst*/ uint8_t *)(p + i);
|
||||||
|
}
|
||||||
|
kprintf("warning: found eocd32 magic at offset 0x%lx that didn't look "
|
||||||
|
"like an eocd32 record: %s\n",
|
||||||
|
i, DescribeZipError(err));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -422,9 +543,13 @@ uint8_t *GetZipCdir64(const uint8_t *p, size_t n) {
|
||||||
i = n - kZipCdir64LocatorSize;
|
i = n - kZipCdir64LocatorSize;
|
||||||
e = MAX(0, n - 65536);
|
e = MAX(0, n - 65536);
|
||||||
for (; i >= e; --i) {
|
for (; i >= e; --i) {
|
||||||
if (READ32LE(p + i) == kZipCdir64LocatorMagic &&
|
if (READ32LE(p + i) == kZipCdir64LocatorMagic) {
|
||||||
(j = ZIP_LOCATE64_OFFSET(p + i)) + kZipCdir64HdrMinSize <= n) {
|
if ((j = ZIP_LOCATE64_OFFSET(p + i)) + kZipCdir64HdrMinSize <= n) {
|
||||||
return (uint8_t *)p + j;
|
CHECK_EQ(kZipCdir64HdrMagic, ZIP_CDIR64_MAGIC((uint8_t *)p + j));
|
||||||
|
return (uint8_t *)p + j;
|
||||||
|
}
|
||||||
|
kprintf("warning: found eocd64 locator magic that "
|
||||||
|
"didn't look like an eocd64 locator record\n");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue