Initial import

This commit is contained in:
Justine Tunney 2020-06-15 07:18:57 -07:00
commit c91b3c5006
14915 changed files with 590219 additions and 0 deletions

36
libc/zipos/close.c Normal file
View file

@ -0,0 +1,36 @@
/*-*- mode:c;indent-tabs-mode:nil;c-basic-offset:2;tab-width:8;coding:utf-8 -*-│
vi: set net ft=c ts=2 sts=2 sw=2 fenc=utf-8 :vi
Copyright 2020 Justine Alexandra Roberts Tunney
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; version 2 of the License.
This program is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
02110-1301 USA
*/
#include "libc/assert.h"
#include "libc/calls/internal.h"
#include "libc/mem/mem.h"
#include "libc/zipos/zipos.h"
/**
* Closes compressed object.
*
* @param fd is vetted by close()
*/
int __zipos_close(struct ZiposHandle *h) {
if (h) {
munmap(h->map, h->mapsize);
free(h);
}
return 0;
}

40
libc/zipos/find.c Normal file
View file

@ -0,0 +1,40 @@
/*-*- mode:c;indent-tabs-mode:nil;c-basic-offset:2;tab-width:8;coding:utf-8 -*-│
vi: set net ft=c ts=2 sts=2 sw=2 fenc=utf-8 :vi
Copyright 2020 Justine Alexandra Roberts Tunney
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; version 2 of the License.
This program is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
02110-1301 USA
*/
#include "ape/relocations.h"
#include "libc/assert.h"
#include "libc/runtime/rbx.h"
#include "libc/runtime/runtime.h"
#include "libc/str/str.h"
#include "libc/zip.h"
#include "libc/zipos/zipos.h"
ssize_t __zipos_find(const struct ZiposUri *name) {
size_t i, cf;
assert(ZIP_CDIR_MAGIC(__zip_end) == kZipCdirHdrMagic);
for (i = 0, cf = ZIP_CDIR_OFFSET(__zip_end); i < ZIP_CDIR_RECORDS(__zip_end);
++i, cf += ZIP_CFILE_HDRSIZE(&_base[0] + cf)) {
assert(ZIP_CFILE_MAGIC(&_base[0] + cf) == kZipCfileHdrMagic);
if (name->len == ZIP_CFILE_NAMESIZE(&_base[0] + cf) &&
memcmp(name->path, ZIP_CFILE_NAME(&_base[0] + cf), name->len) == 0) {
return cf;
}
}
return -1;
}

30
libc/zipos/fstat.c Normal file
View file

@ -0,0 +1,30 @@
/*-*- mode:c;indent-tabs-mode:nil;c-basic-offset:2;tab-width:8;coding:utf-8 -*-│
vi: set net ft=c ts=2 sts=2 sw=2 fenc=utf-8 :vi
Copyright 2020 Justine Alexandra Roberts Tunney
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; version 2 of the License.
This program is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
02110-1301 USA
*/
#include "libc/zipos/zipos.h"
/**
* Reads file metadata from αcτµαlly pδrταblε εxεcµταblε object store.
*
* @param uri is obtained via __zipos_parseuri()
* @asyncsignalsafe
*/
int __zipos_fstat(const struct ZiposHandle *h, struct stat *st) {
return __zipos_stat_impl(h->cfile, st);
}

148
libc/zipos/open.c Normal file
View file

@ -0,0 +1,148 @@
/*-*- mode:c;indent-tabs-mode:nil;c-basic-offset:2;tab-width:8;coding:utf-8 -*-│
vi: set net ft=c ts=2 sts=2 sw=2 fenc=utf-8 :vi
Copyright 2020 Justine Alexandra Roberts Tunney
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; version 2 of the License.
This program is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
02110-1301 USA
*/
#include "ape/relocations.h"
#include "libc/assert.h"
#include "libc/calls/calls.h"
#include "libc/calls/internal.h"
#include "libc/calls/struct/sigset.h"
#include "libc/calls/struct/stat.h"
#include "libc/conv/sizemultiply.h"
#include "libc/dce.h"
#include "libc/macros.h"
#include "libc/mem/mem.h"
#include "libc/runtime/rbx.h"
#include "libc/runtime/runtime.h"
#include "libc/str/str.h"
#include "libc/str/undeflate.h"
#include "libc/sysv/consts/map.h"
#include "libc/sysv/consts/o.h"
#include "libc/sysv/consts/prot.h"
#include "libc/sysv/consts/sig.h"
#include "libc/sysv/errfuns.h"
#include "libc/zip.h"
#include "libc/zipos/zipos.h"
#include "third_party/zlib/zlib.h"
static int __zipos_inflate_fast(struct ZiposHandle *h, uint8_t *data,
size_t size) {
int rc;
z_stream zs;
zs.opaque = &h;
zs.next_in = data;
zs.avail_in = size;
zs.total_in = size;
zs.next_out = h->mem;
zs.avail_out = h->size;
zs.total_out = h->size;
zs.zfree = Z_NULL;
zs.zalloc = Z_NULL;
if (inflateInit2(&zs, -MAX_WBITS) == Z_OK) {
switch (inflate(&zs, Z_NO_FLUSH)) {
case Z_STREAM_END:
rc = 0;
break;
case Z_MEM_ERROR:
rc = enomem();
break;
case Z_DATA_ERROR:
rc = eio();
break;
case Z_NEED_DICT:
rc = enotsup(); /* TODO(jart): Z_NEED_DICT */
break;
default:
abort();
}
inflateEnd(&zs);
} else {
rc = enomem();
}
return rc;
}
static int __zipos_inflate_tiny(struct ZiposHandle *h, uint8_t *data,
size_t size) {
struct DeflateState ds;
return undeflate(h->mem, h->size, data, size, &ds) != -1 ? 0 : eio();
}
static int __zipos_load(size_t cf, unsigned flags, int mode) {
int fd;
size_t lf;
struct ZiposHandle *h;
lf = ZIP_CFILE_OFFSET(&_base[0] + cf);
assert(ZIP_LFILE_MAGIC(&_base[0] + lf) == kZipLfileHdrMagic);
assert(ZIP_LFILE_COMPRESSIONMETHOD(&_base[0] + lf) == kZipCompressionNone ||
ZIP_LFILE_COMPRESSIONMETHOD(&_base[0] + lf) == kZipCompressionDeflate);
if ((fd = createfd()) == -1) return -1;
if (!(h = calloc(1, sizeof(*h)))) return -1;
h->cfile = cf;
if ((h->size = ZIP_LFILE_UNCOMPRESSEDSIZE(&_base[0] + lf))) {
if (ZIP_LFILE_COMPRESSIONMETHOD(&_base[0] + lf)) {
assert(ZIP_LFILE_COMPRESSEDSIZE(&_base[0] + lf));
h->mapsize = ROUNDUP(h->size + FRAMESIZE, FRAMESIZE);
if ((h->map = mapanon(h->mapsize)) != MAP_FAILED) {
h->mem = h->map + FRAMESIZE / 2;
if ((IsTiny() ? __zipos_inflate_tiny : __zipos_inflate_fast)(
h, ZIP_LFILE_CONTENT(&_base[0] + lf),
ZIP_LFILE_COMPRESSEDSIZE(&_base[0] + lf)) == -1) {
fd = -1;
}
} else {
fd = -1;
}
} else {
h->mem = ZIP_LFILE_CONTENT(&_base[0] + lf);
}
}
if (!IsTiny() && fd != -1 &&
crc32_z(0, h->mem, h->size) != ZIP_LFILE_CRC32(&_base[0] + lf)) {
fd = eio();
}
if (fd != -1) {
g_fds.p[fd].kind = kFdZip;
g_fds.p[fd].handle = (intptr_t)h;
g_fds.p[fd].flags = flags;
} else {
__zipos_close(h);
}
return fd;
}
/**
* Loads compressed file from αcτµαlly pδrταblε εxεcµταblε object store.
*
* @param uri is obtained via __zipos_parseuri()
* @asyncsignalsafe
*/
int __zipos_open(const struct ZiposUri *name, unsigned flags, int mode) {
int fd;
ssize_t cf;
sigset_t oldmask;
assert((flags & O_ACCMODE) == O_RDONLY);
sigprocmask(SIG_BLOCK, &kSigsetFull, &oldmask);
if ((cf = __zipos_find(name)) != -1) {
fd = __zipos_load(cf, flags, mode);
} else {
fd = enoent();
}
sigprocmask(SIG_SETMASK, &oldmask, NULL);
return fd;
}

37
libc/zipos/parseuri.c Normal file
View file

@ -0,0 +1,37 @@
/*-*- mode:c;indent-tabs-mode:nil;c-basic-offset:2;tab-width:8;coding:utf-8 -*-│
vi: set net ft=c ts=2 sts=2 sw=2 fenc=utf-8 :vi
Copyright 2020 Justine Alexandra Roberts Tunney
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; version 2 of the License.
This program is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
02110-1301 USA
*/
#include "libc/str/str.h"
#include "libc/zipos/zipos.h"
const char kZiposSchemePrefix[4] = "zip:";
/**
* Extracts information about ZIP URI if it is one.
*/
ssize_t __zipos_parseuri(const char *uri, struct ZiposUri *out) {
size_t len;
if ((len = strlen(uri)) >= sizeof(kZiposSchemePrefix) && len < PATH_MAX &&
memcmp(uri, kZiposSchemePrefix, sizeof(kZiposSchemePrefix)) == 0) {
out->path = uri + sizeof(kZiposSchemePrefix);
return (out->len = len - sizeof(kZiposSchemePrefix));
} else {
return -1;
}
}

44
libc/zipos/read.c Normal file
View file

@ -0,0 +1,44 @@
/*-*- mode:c;indent-tabs-mode:nil;c-basic-offset:2;tab-width:8;coding:utf-8 -*-│
vi: set net ft=c ts=2 sts=2 sw=2 fenc=utf-8 :vi
Copyright 2020 Justine Alexandra Roberts Tunney
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; version 2 of the License.
This program is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
02110-1301 USA
*/
#include "libc/assert.h"
#include "libc/bits/safemacros.h"
#include "libc/calls/internal.h"
#include "libc/calls/struct/iovec.h"
#include "libc/str/str.h"
#include "libc/zipos/zipos.h"
/**
* Reads data from zip store object.
*
* @return [1..size] bytes on success, 0 on EOF, or -1 w/ errno; with
* exception of size==0, in which case return zero means no error
* @asyncsignalsafe
*/
ssize_t __zipos_read(struct ZiposHandle *h, const struct iovec *iov,
size_t iovlen, ssize_t opt_offset) {
size_t i, b, x, y;
x = y = opt_offset != -1 ? opt_offset : h->pos;
for (i = 0; i < iovlen && y < h->size; ++i, y += b) {
b = min(iov[i].iov_len, h->size - y);
memcpy(iov[i].iov_base, h->mem + y, b);
}
if (opt_offset != -1) h->pos = y;
return y - x;
}

38
libc/zipos/stat-impl.c Normal file
View file

@ -0,0 +1,38 @@
/*-*- mode:c;indent-tabs-mode:nil;c-basic-offset:2;tab-width:8;coding:utf-8 -*-│
vi: set net ft=c ts=2 sts=2 sw=2 fenc=utf-8 :vi
Copyright 2020 Justine Alexandra Roberts Tunney
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; version 2 of the License.
This program is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
02110-1301 USA
*/
#include "libc/bits/safemacros.h"
#include "libc/calls/calls.h"
#include "libc/calls/struct/stat.h"
#include "libc/runtime/rbx.h"
#include "libc/str/str.h"
#include "libc/zip.h"
#include "libc/zipos/zipos.h"
int __zipos_stat_impl(size_t cf, struct stat *st) {
memset(st, 0, sizeof(*st));
if (ZIP_CFILE_FILEATTRCOMPAT(&_base[0] + cf) == kZipOsUnix) {
st->st_mode = ZIP_CFILE_EXTERNALATTRIBUTES(&_base[0] + cf) >> 16;
} else {
st->st_mode = 0100644;
}
st->st_size = ZIP_CFILE_UNCOMPRESSEDSIZE(&_base[0] + cf);
st->st_blocks = roundup(ZIP_CFILE_COMPRESSEDSIZE(&_base[0] + cf), 512) / 512;
return 0;
}

36
libc/zipos/stat.c Normal file
View file

@ -0,0 +1,36 @@
/*-*- mode:c;indent-tabs-mode:nil;c-basic-offset:2;tab-width:8;coding:utf-8 -*-│
vi: set net ft=c ts=2 sts=2 sw=2 fenc=utf-8 :vi
Copyright 2020 Justine Alexandra Roberts Tunney
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; version 2 of the License.
This program is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
02110-1301 USA
*/
#include "libc/sysv/errfuns.h"
#include "libc/zipos/zipos.h"
/**
* Reads file metadata from αcτµαlly pδrταblε εxεcµταblε object store.
*
* @param uri is obtained via __zipos_parseuri()
* @asyncsignalsafe
*/
int __zipos_stat(const struct ZiposUri *name, struct stat *st) {
ssize_t cf;
if ((cf = __zipos_find(name)) != -1) {
return __zipos_stat_impl(cf, st);
} else {
return enoent();
}
}

View file

@ -0,0 +1,58 @@
/*-*- mode:asm; indent-tabs-mode:t; tab-width:8; coding:utf-8 -*-│
vi: set et ft=asm ts=8 tw=8 fenc=utf-8 :vi
Copyright 2020 Justine Alexandra Roberts Tunney
This program is free software; you can redistribute it and/or modify │
it under the terms of the GNU General Public License as published by
the Free Software Foundation; version 2 of the License. │
This program is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of │
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software │
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
02110-1301 USA
*/
#include "ape/relocations.h"
#include "libc/zip.h"
#include "libc/macros.h"
/ ZIP Central Directory.
.section .piro.data.sort.zip.3,"a",@progbits
.hidden __zip_start
.globl __zip_start
.type __zip_start,@object
.align kZipCdirAlign
__zip_start:
.previous/*
...
decentralized content
...
*/.section .piro.data.sort.zip.5,"a",@progbits
.align kZipCdirAlign
__zip_end:
.long kZipCdirHdrMagic # magic
.short 0 # disk
.short 0 # starting disk
.short v_zip_records # records on disk
.short v_zip_records # records
.long v_zip_cdirsize # size of central directory
.long RVA(__zip_start) # central directory offset
.short v_zip_commentsize # comment size
.endobj __zip_end,globl,hidden
.weak v_zip_records
.weak v_zip_cdirsize
.weak v_zip_commentsize
.previous
yoink __zipos_close
yoink __zipos_fstat
yoink __zipos_open
yoink __zipos_parseuri
yoink __zipos_read
yoink __zipos_stat
yoink __FILE__

39
libc/zipos/zipos.h Normal file
View file

@ -0,0 +1,39 @@
#ifndef COSMOPOLITAN_LIBC_ZIPOS_ZIPOS_H_
#define COSMOPOLITAN_LIBC_ZIPOS_ZIPOS_H_
#if !(__ASSEMBLER__ + __LINKER__ + 0)
COSMOPOLITAN_C_START_
struct stat;
struct iovec;
struct ZiposUri {
const char *path;
size_t len;
};
struct ZiposHandle {
uint8_t *mem; /* deflated file base */
size_t size; /* byte length of file */
size_t pos; /* read/write byte offset state */
uint32_t cfile; /* central directory entry rva */
uint8_t *map;
size_t mapsize;
};
extern const char kZiposSchemePrefix[4];
ssize_t __zipos_parseuri(const char *, struct ZiposUri *);
ssize_t __zipos_find(const struct ZiposUri *);
int __zipos_close(struct ZiposHandle *);
int __zipos_open(const struct ZiposUri *, unsigned, int);
int __zipos_stat(const struct ZiposUri *, struct stat *);
int __zipos_fstat(const struct ZiposHandle *, struct stat *);
int __zipos_stat_impl(size_t, struct stat *);
ssize_t __zipos_read(struct ZiposHandle *, const struct iovec *, size_t,
ssize_t);
ssize_t __zipos_write(struct ZiposHandle *, const struct iovec *, size_t,
ssize_t);
COSMOPOLITAN_C_END_
#endif /* !(__ASSEMBLER__ + __LINKER__ + 0) */
#endif /* COSMOPOLITAN_LIBC_ZIPOS_ZIPOS_H_ */

58
libc/zipos/zipos.mk Normal file
View file

@ -0,0 +1,58 @@
#-*-mode:makefile-gmake;indent-tabs-mode:t;tab-width:8;coding:utf-8-*-┐
#───vi: set et ft=make ts=8 tw=8 fenc=utf-8 :vi───────────────────────┘
PKGS += LIBC_ZIPOS
LIBC_ZIPOS_ARTIFACTS += LIBC_ZIPOS_A
LIBC_ZIPOS = $(LIBC_ZIPOS_A_DEPS) $(LIBC_ZIPOS_A)
LIBC_ZIPOS_A = o/$(MODE)/libc/zipos/zipos.a
LIBC_ZIPOS_A_FILES := $(wildcard libc/zipos/*)
LIBC_ZIPOS_A_HDRS = $(filter %.h,$(LIBC_ZIPOS_A_FILES))
LIBC_ZIPOS_A_SRCS_S = $(filter %.S,$(LIBC_ZIPOS_A_FILES))
LIBC_ZIPOS_A_SRCS_C = $(filter %.c,$(LIBC_ZIPOS_A_FILES))
LIBC_ZIPOS_A_SRCS = \
$(LIBC_ZIPOS_A_SRCS_S) \
$(LIBC_ZIPOS_A_SRCS_C)
LIBC_ZIPOS_A_OBJS = \
$(LIBC_ZIPOS_A_SRCS:%=o/$(MODE)/%.zip.o) \
$(LIBC_ZIPOS_A_SRCS_S:%.S=o/$(MODE)/%.o) \
$(LIBC_ZIPOS_A_SRCS_C:%.c=o/$(MODE)/%.o)
LIBC_ZIPOS_A_CHECKS = \
$(LIBC_ZIPOS_A).pkg \
$(LIBC_ZIPOS_A_HDRS:%=o/$(MODE)/%.ok)
LIBC_ZIPOS_A_DIRECTDEPS = \
LIBC_CALLS \
LIBC_MEM \
LIBC_NEXGEN32E \
LIBC_RUNTIME \
LIBC_SYSV \
LIBC_STR \
LIBC_STUBS \
THIRD_PARTY_ZLIB
LIBC_ZIPOS_A_DEPS := \
$(call uniq,$(foreach zipos,$(LIBC_ZIPOS_A_DIRECTDEPS),$($(zipos))))
$(LIBC_ZIPOS_A):libc/zipos/ \
$(LIBC_ZIPOS_A).pkg \
$(LIBC_ZIPOS_A_OBJS)
$(LIBC_ZIPOS_A).pkg: \
$(LIBC_ZIPOS_A_OBJS) \
$(foreach zipos,$(LIBC_ZIPOS_A_DIRECTDEPS),$($(zipos)_A).pkg)
LIBC_ZIPOS_LIBS = $(foreach zipos,$(LIBC_ZIPOS_ARTIFACTS),$($(zipos)))
LIBC_ZIPOS_SRCS = $(foreach zipos,$(LIBC_ZIPOS_ARTIFACTS),$($(zipos)_SRCS))
LIBC_ZIPOS_HDRS = $(foreach zipos,$(LIBC_ZIPOS_ARTIFACTS),$($(zipos)_HDRS))
LIBC_ZIPOS_BINS = $(foreach zipos,$(LIBC_ZIPOS_ARTIFACTS),$($(zipos)_BINS))
LIBC_ZIPOS_CHECKS = $(foreach zipos,$(LIBC_ZIPOS_ARTIFACTS),$($(zipos)_CHECKS))
LIBC_ZIPOS_OBJS = $(foreach zipos,$(LIBC_ZIPOS_ARTIFACTS),$($(zipos)_OBJS))
LIBC_ZIPOS_TESTS = $(foreach zipos,$(LIBC_ZIPOS_ARTIFACTS),$($(zipos)_TESTS))
$(LIBC_ZIPOS_OBJS): $(BUILD_FILES) libc/zipos/zipos.mk
.PHONY: o/$(MODE)/libc/zipos
o/$(MODE)/libc/zipos: $(LIBC_ZIPOS_CHECKS)