Correct misunderstanding with zip64 extra records

This commit is contained in:
Justine Tunney 2023-11-18 14:35:57 -08:00
parent dbd8176ea8
commit 3e6d536822
No known key found for this signature in database
GPG key ID: BE714B4575D6E328
9 changed files with 96 additions and 78 deletions

View file

@ -16,10 +16,10 @@
TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
PERFORMANCE OF THIS SOFTWARE. PERFORMANCE OF THIS SOFTWARE.
*/ */
#include "libc/errno.h"
#include "libc/intrin/kprintf.h" #include "libc/intrin/kprintf.h"
#include "libc/intrin/safemacros.internal.h" #include "libc/intrin/safemacros.internal.h"
#include "libc/log/internal.h" #include "libc/log/internal.h"
#include "libc/errno.h"
#include "libc/thread/thread.h" #include "libc/thread/thread.h"
/** /**
@ -30,8 +30,6 @@
relegated void __start_fatal(const char *file, int line) { relegated void __start_fatal(const char *file, int line) {
pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, 0); pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, 0);
__restore_tty(); __restore_tty();
kprintf("%r%serror%s:%s:%d:%s%s: ", !__nocolor ? "\e[J\e[30;101m" : "", kprintf("%r%serror%s:%s:%d%s: ", !__nocolor ? "\e[J\e[30;101m" : "",
!__nocolor ? "\e[94;49m" : "", file, line, !__nocolor ? "\e[94;49m" : "", file, line, !__nocolor ? "\e[0m" : "");
firstnonnull(program_invocation_short_name, "unknown"),
!__nocolor ? "\e[0m" : "");
} }

View file

@ -21,17 +21,18 @@
/** /**
* Returns compressed size in bytes from zip central directory header. * Returns compressed size in bytes from zip central directory header.
*/ */
uint64_t GetZipCfileCompressedSize(const uint8_t *z) { int64_t GetZipCfileCompressedSize(const uint8_t *z) {
uint64_t x; if (ZIP_CFILE_COMPRESSEDSIZE(z) != 0xFFFFFFFFu) {
const uint8_t *p, *pe; return ZIP_CFILE_COMPRESSEDSIZE(z);
if ((x = ZIP_CFILE_COMPRESSEDSIZE(z)) == 0xFFFFFFFF) { }
for (p = ZIP_CFILE_EXTRA(z), pe = p + ZIP_CFILE_EXTRASIZE(z); p < pe; const uint8_t *p = ZIP_CFILE_EXTRA(z);
p += ZIP_EXTRA_SIZE(p)) { const uint8_t *pe = p + ZIP_CFILE_EXTRASIZE(z);
if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64 && for (; p < pe; p += ZIP_EXTRA_SIZE(p)) {
8 + 8 <= ZIP_EXTRA_CONTENTSIZE(p)) { if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64) {
return READ64LE(ZIP_EXTRA_CONTENT(p) + 8); if (8 <= ZIP_EXTRA_CONTENTSIZE(p)) {
return READ64LE(ZIP_EXTRA_CONTENT(p));
} }
} }
} }
return x; return -1;
} }

View file

@ -21,17 +21,25 @@
/** /**
* Returns offset of local file header. * Returns offset of local file header.
*/ */
uint64_t GetZipCfileOffset(const uint8_t *z) { int64_t GetZipCfileOffset(const uint8_t *z) {
uint64_t x; if (ZIP_CFILE_OFFSET(z) != 0xFFFFFFFFu) {
const uint8_t *p, *pe; return ZIP_CFILE_OFFSET(z);
if ((x = ZIP_CFILE_OFFSET(z)) == 0xFFFFFFFF) { }
for (p = ZIP_CFILE_EXTRA(z), pe = p + ZIP_CFILE_EXTRASIZE(z); p < pe; const uint8_t *p = ZIP_CFILE_EXTRA(z);
p += ZIP_EXTRA_SIZE(p)) { const uint8_t *pe = p + ZIP_CFILE_EXTRASIZE(z);
if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64 && for (; p < pe; p += ZIP_EXTRA_SIZE(p)) {
16 + 8 <= ZIP_EXTRA_CONTENTSIZE(p)) { if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64) {
return READ64LE(ZIP_EXTRA_CONTENT(p) + 16); int offset = 0;
if (ZIP_CFILE_COMPRESSEDSIZE(z) == 0xFFFFFFFFu) {
offset += 8;
}
if (ZIP_CFILE_UNCOMPRESSEDSIZE(z) == 0xFFFFFFFFu) {
offset += 8;
}
if (offset + 8 <= ZIP_EXTRA_CONTENTSIZE(p)) {
return READ64LE(ZIP_EXTRA_CONTENT(p) + offset);
} }
} }
} }
return x; return -1;
} }

View file

@ -21,17 +21,22 @@
/** /**
* Returns uncompressed size in bytes from zip central directory header. * Returns uncompressed size in bytes from zip central directory header.
*/ */
uint64_t GetZipCfileUncompressedSize(const uint8_t *z) { int64_t GetZipCfileUncompressedSize(const uint8_t *z) {
uint64_t x; if (ZIP_CFILE_UNCOMPRESSEDSIZE(z) != 0xFFFFFFFFu) {
const uint8_t *p, *pe; return ZIP_CFILE_UNCOMPRESSEDSIZE(z);
if ((x = ZIP_CFILE_UNCOMPRESSEDSIZE(z)) == 0xFFFFFFFF) { }
for (p = ZIP_CFILE_EXTRA(z), pe = p + ZIP_CFILE_EXTRASIZE(z); p < pe; const uint8_t *p = ZIP_CFILE_EXTRA(z);
p += ZIP_EXTRA_SIZE(p)) { const uint8_t *pe = p + ZIP_CFILE_EXTRASIZE(z);
if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64 && for (; p < pe; p += ZIP_EXTRA_SIZE(p)) {
0 + 8 <= ZIP_EXTRA_CONTENTSIZE(p)) { if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64) {
return READ64LE(ZIP_EXTRA_CONTENT(p) + 0); int offset = 0;
if (ZIP_CFILE_COMPRESSEDSIZE(z) == 0xFFFFFFFFu) {
offset += 8;
}
if (offset + 8 <= ZIP_EXTRA_CONTENTSIZE(p)) {
return READ64LE(ZIP_EXTRA_CONTENT(p) + offset);
} }
} }
} }
return x; return -1;
} }

View file

@ -21,17 +21,18 @@
/** /**
* Returns compressed size in bytes from zip local file header. * Returns compressed size in bytes from zip local file header.
*/ */
uint64_t GetZipLfileCompressedSize(const uint8_t *z) { int64_t GetZipLfileCompressedSize(const uint8_t *z) {
uint64_t x; if (ZIP_LFILE_COMPRESSEDSIZE(z) != 0xFFFFFFFFu) {
const uint8_t *p, *pe; return ZIP_LFILE_COMPRESSEDSIZE(z);
if ((x = ZIP_LFILE_COMPRESSEDSIZE(z)) == 0xFFFFFFFF) { }
for (p = ZIP_LFILE_EXTRA(z), pe = p + ZIP_LFILE_EXTRASIZE(z); p < pe; const uint8_t *p = ZIP_LFILE_EXTRA(z);
p += ZIP_EXTRA_SIZE(p)) { const uint8_t *pe = p + ZIP_LFILE_EXTRASIZE(z);
if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64 && for (; p < pe; p += ZIP_EXTRA_SIZE(p)) {
8 + 8 <= ZIP_EXTRA_CONTENTSIZE(p)) { if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64) {
return READ64LE(ZIP_EXTRA_CONTENT(p) + 8); if (8 <= ZIP_EXTRA_CONTENTSIZE(p)) {
return READ64LE(ZIP_EXTRA_CONTENT(p));
} }
} }
} }
return x; return -1;
} }

View file

@ -21,18 +21,22 @@
/** /**
* Returns uncompressed size in bytes from zip local file header. * Returns uncompressed size in bytes from zip local file header.
*/ */
uint64_t GetZipLfileUncompressedSize(const uint8_t *z) { int64_t GetZipLfileUncompressedSize(const uint8_t *z) {
uint64_t x; if (ZIP_LFILE_UNCOMPRESSEDSIZE(z) != 0xFFFFFFFFu) {
const uint8_t *p, *pe; return ZIP_LFILE_UNCOMPRESSEDSIZE(z);
x = ZIP_LFILE_UNCOMPRESSEDSIZE(z); }
if (x == 0xFFFFFFFF) { const uint8_t *p = ZIP_LFILE_EXTRA(z);
for (p = ZIP_LFILE_EXTRA(z), pe = p + ZIP_LFILE_EXTRASIZE(z); p < pe; const uint8_t *pe = p + ZIP_LFILE_EXTRASIZE(z);
p += ZIP_EXTRA_SIZE(p)) { for (; p < pe; p += ZIP_EXTRA_SIZE(p)) {
if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64 && if (ZIP_EXTRA_HEADERID(p) == kZipExtraZip64) {
0 + 8 <= ZIP_EXTRA_CONTENTSIZE(p)) { int offset = 0;
return READ64LE(ZIP_EXTRA_CONTENT(p) + 0); if (ZIP_LFILE_COMPRESSEDSIZE(z) == 0xFFFFFFFFu) {
offset += 8;
}
if (offset + 8 <= ZIP_EXTRA_CONTENTSIZE(p)) {
return READ64LE(ZIP_EXTRA_CONTENT(p) + offset);
} }
} }
} }
return x; return -1;
} }

View file

@ -102,6 +102,7 @@
#define kZipLfileHdrMagic ZM_(0x04034b50) /* PK♥♦ "PK\3\4" */ #define kZipLfileHdrMagic ZM_(0x04034b50) /* PK♥♦ "PK\3\4" */
#define kZipLfileHdrMinSize 30 #define kZipLfileHdrMinSize 30
#define kZipLfileOffsetVersionNeeded 4
#define kZipLfileOffsetGeneralflag 6 #define kZipLfileOffsetGeneralflag 6
#define kZipLfileOffsetCompressionmethod 8 #define kZipLfileOffsetCompressionmethod 8
#define kZipLfileOffsetLastmodifiedtime 10 #define kZipLfileOffsetLastmodifiedtime 10
@ -228,11 +229,11 @@ uint64_t GetZipCdirRecords(const uint8_t *);
const void *GetZipCdirComment(const uint8_t *); const void *GetZipCdirComment(const uint8_t *);
uint64_t GetZipCdirSize(const uint8_t *); uint64_t GetZipCdirSize(const uint8_t *);
uint64_t GetZipCdirCommentSize(const uint8_t *); uint64_t GetZipCdirCommentSize(const uint8_t *);
uint64_t GetZipCfileUncompressedSize(const uint8_t *); int64_t GetZipCfileCompressedSize(const uint8_t *);
uint64_t GetZipCfileCompressedSize(const uint8_t *); int64_t GetZipCfileUncompressedSize(const uint8_t *);
uint64_t GetZipCfileOffset(const uint8_t *); int64_t GetZipCfileOffset(const uint8_t *);
uint64_t GetZipLfileUncompressedSize(const uint8_t *); int64_t GetZipLfileCompressedSize(const uint8_t *);
uint64_t GetZipLfileCompressedSize(const uint8_t *); int64_t GetZipLfileUncompressedSize(const uint8_t *);
void GetZipCfileTimestamps(const uint8_t *, struct timespec *, void GetZipCfileTimestamps(const uint8_t *, struct timespec *,
struct timespec *, struct timespec *, int); struct timespec *, struct timespec *, int);

View file

@ -676,7 +676,7 @@ static void LoadSymbols(Elf64_Ehdr *e, Elf64_Off size, const char *path) {
WRITE32LE(cfile, kZipCfileHdrMagic); WRITE32LE(cfile, kZipCfileHdrMagic);
cfile[4] = kZipCosmopolitanVersion; cfile[4] = kZipCosmopolitanVersion;
cfile[5] = kZipOsUnix; cfile[5] = kZipOsUnix;
cfile[6] = kZipEra1993; cfile[6] = kZipEra2001;
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));
@ -690,8 +690,8 @@ static void LoadSymbols(Elf64_Ehdr *e, Elf64_Off size, const char *path) {
unsigned char *lfile = Malloc(lfile_size); unsigned char *lfile = Malloc(lfile_size);
bzero(lfile, lfile_size); bzero(lfile, lfile_size);
WRITE32LE(lfile, kZipLfileHdrMagic); WRITE32LE(lfile, kZipLfileHdrMagic);
cfile[4] = kZipEra1993; WRITE16LE(lfile + kZipLfileOffsetVersionNeeded, kZipEra2001);
cfile[5] = kZipOsDos; WRITE16LE(lfile + kZipLfileOffsetGeneralflag, kZipGflagUtf8);
WRITE16LE(lfile + kZipLfileOffsetCompressionmethod, kZipCompressionDeflate); WRITE16LE(lfile + kZipLfileOffsetCompressionmethod, kZipCompressionDeflate);
WRITE16LE(lfile + kZipLfileOffsetLastmodifieddate, DOS_DATE(2023, 7, 29)); WRITE16LE(lfile + kZipLfileOffsetLastmodifieddate, DOS_DATE(2023, 7, 29));
WRITE16LE(lfile + kZipLfileOffsetLastmodifiedtime, DOS_TIME(0, 0, 0)); WRITE16LE(lfile + kZipLfileOffsetLastmodifiedtime, DOS_TIME(0, 0, 0));

View file

@ -263,7 +263,7 @@ struct Strings {
struct String { struct String {
size_t n; size_t n;
const char *s; const char *s;
} * p; } *p;
}; };
struct DeflateGenerator { struct DeflateGenerator {
@ -291,7 +291,7 @@ static struct Servers {
struct Server { struct Server {
int fd; int fd;
struct sockaddr_in addr; struct sockaddr_in addr;
} * p; } *p;
} servers; } servers;
static struct Freelist { static struct Freelist {
@ -305,7 +305,7 @@ static struct Unmaplist {
int f; int f;
void *p; void *p;
size_t n; size_t n;
} * p; } *p;
} unmaplist; } unmaplist;
static struct Psks { static struct Psks {
@ -316,7 +316,7 @@ static struct Psks {
char *identity; char *identity;
size_t identity_len; size_t identity_len;
char *s; char *s;
} * p; } *p;
} psks; } psks;
static struct Suites { static struct Suites {
@ -335,7 +335,7 @@ static struct Redirects {
int code; int code;
struct String path; struct String path;
struct String location; struct String location;
} * p; } *p;
} redirects; } redirects;
static struct Assets { static struct Assets {
@ -350,8 +350,8 @@ static struct Assets {
struct File { struct File {
struct String path; struct String path;
struct stat st; struct stat st;
} * file; } *file;
} * p; } *p;
} assets; } assets;
static struct TrustedIps { static struct TrustedIps {
@ -359,7 +359,7 @@ static struct TrustedIps {
struct TrustedIp { struct TrustedIp {
uint32_t ip; uint32_t ip;
uint32_t mask; uint32_t mask;
} * p; } *p;
} trustedips; } trustedips;
struct TokenBucket { struct TokenBucket {
@ -393,7 +393,7 @@ static struct Shared {
#undef C #undef C
} c; } c;
pthread_spinlock_t montermlock; pthread_spinlock_t montermlock;
} * shared; } *shared;
static const char kCounterNames[] = static const char kCounterNames[] =
#define C(x) #x "\0" #define C(x) #x "\0"
@ -3695,8 +3695,8 @@ static void StoreAsset(const char *path, size_t pathlen, const char *data,
p = WRITE16LE(p, mtime); p = WRITE16LE(p, mtime);
p = WRITE16LE(p, mdate); p = WRITE16LE(p, mdate);
p = WRITE32LE(p, crc); p = WRITE32LE(p, crc);
p = WRITE32LE(p, MIN(uselen, 0xffffffff)); p = WRITE32LE(p, 0xffffffffu);
p = WRITE32LE(p, MIN(datalen, 0xffffffff)); p = WRITE32LE(p, 0xffffffffu);
p = WRITE16LE(p, pathlen); p = WRITE16LE(p, pathlen);
p = WRITE16LE(p, v[2].iov_len); p = WRITE16LE(p, v[2].iov_len);
v[1].iov_len = pathlen; v[1].iov_len = pathlen;
@ -3755,8 +3755,8 @@ static void StoreAsset(const char *path, size_t pathlen, const char *data,
p = WRITE16LE(p, mtime); p = WRITE16LE(p, mtime);
p = WRITE16LE(p, mdate); p = WRITE16LE(p, mdate);
p = WRITE32LE(p, crc); p = WRITE32LE(p, crc);
p = WRITE32LE(p, MIN(uselen, 0xffffffff)); p = WRITE32LE(p, 0xffffffffu);
p = WRITE32LE(p, MIN(datalen, 0xffffffff)); p = WRITE32LE(p, 0xffffffffu);
p = WRITE16LE(p, pathlen); p = WRITE16LE(p, pathlen);
p = WRITE16LE(p, v[8].iov_len + v[9].iov_len); p = WRITE16LE(p, v[8].iov_len + v[9].iov_len);
p = WRITE16LE(p, 0); p = WRITE16LE(p, 0);
@ -3764,7 +3764,7 @@ static void StoreAsset(const char *path, size_t pathlen, const char *data,
p = WRITE16LE(p, iattrs); p = WRITE16LE(p, iattrs);
p = WRITE16LE(p, dosmode); p = WRITE16LE(p, dosmode);
p = WRITE16LE(p, mode); p = WRITE16LE(p, mode);
p = WRITE32LE(p, MIN(zsize, 0xffffffff)); p = WRITE32LE(p, 0xffffffffu);
v[7].iov_len = pathlen; v[7].iov_len = pathlen;
v[7].iov_base = (void *)path; v[7].iov_base = (void *)path;
// zip64 end of central directory // zip64 end of central directory