[ncman] zlib implementation, quick and dirty

This commit is contained in:
nick black 2021-12-06 00:57:48 -05:00 committed by nick black
parent 88e2d34037
commit 8f38689489
2 changed files with 85 additions and 38 deletions

View File

@ -794,16 +794,33 @@ int ncplane_resize_internal(ncplane* n, int keepy, int keepx,
int keptarea = keepleny * keeplenx;
int newarea = ylen * xlen;
size_t fbsize = sizeof(nccell) * newarea;
nccell* fb = malloc(fbsize);
if(fb == NULL){
// an important optimization is the case where nothing needs to be moved,
// true when either the keptarea is 0 or the old and new x dimensions are
// equal, and we're keeping the full x dimension, and any material we're
// keeping starts at the top. in this case, we try to realloc() and avoid
// any copying whatsoever (we otherwise incur at least one copy due to
// always using a new area). set realloced high in this event, so we don't
// free anything.
nccell* fb;
bool realloced = false;
if(keptarea == 0 || (cols == xlen && cols == keeplenx && keepy == 0)){
if((fb = realloc(n->fb, fbsize)) == NULL){
return -1;
}
realloced = true;
}else{
if((fb = malloc(fbsize)) == NULL){
return -1;
}
}
if(n->tam){
loginfo("TAM realloc to %d entries\n", newarea);
// FIXME first, free any disposed auxiliary vectors!
tament* tmptam = realloc(n->tam, sizeof(*tmptam) * newarea);
if(tmptam == NULL){
if(!realloced){
free(fb);
}
return -1;
}
n->tam = tmptam;
@ -831,16 +848,20 @@ int ncplane_resize_internal(ncplane* n, int keepy, int keepx,
n->absy += keepy + yoff;
n->absx += keepx + xoff;
//fprintf(stderr, "absx: %d keepx: %d xoff: %d\n", n->absx, keepx, xoff);
if(keptarea == 0){ // keep nothing, resize/move only
if(keptarea == 0){ // keep nothing, resize/move only.
// if we're keeping nothing, dump the old egcspool. otherwise, we go ahead
// and keep it. perhaps we ought compact it?
memset(fb, 0, sizeof(*fb) * newarea);
egcpool_dump(&n->pool);
n->lenx = xlen;
n->leny = ylen;
free(preserved);
return resize_callbacks_children(n);
}else if(realloced){
// the x dimensions are equal, and we're keeping across the width. only the
// y dimension changed. at worst, we need zero some out.
unsigned tozorch = (ylen - keepleny) * xlen;
if(tozorch){
unsigned zorchoff = keepleny * xlen;
memset(fb + zorchoff, 0, tozorch);
}
}else{
// we currently have maxy rows of maxx cells each. we will be keeping rows
// keepy..keepy + keepleny - 1 and columns keepx..keepx + keeplenx - 1.
// anything else is zerod out. itery is the row we're writing *to*, and we
@ -872,9 +893,12 @@ int ncplane_resize_internal(ncplane* n, int keepy, int keepx,
}
}
}
}
n->lenx = xlen;
n->leny = ylen;
if(!realloced){
free(preserved);
}
return resize_callbacks_children(n);
}

View File

@ -54,6 +54,10 @@ parse_args(int argc, char** argv){
static unsigned char*
map_gzipped_data(unsigned char* buf, size_t* len, unsigned char* ubuf, uint32_t ulen){
struct libdeflate_decompressor* inflate = libdeflate_alloc_decompressor();
if(inflate == NULL){
munmap(buf, *len);
return NULL;
}
size_t outbytes;
enum libdeflate_result r;
r = libdeflate_gzip_decompress(inflate, buf, *len, ubuf, ulen, &outbytes);
@ -66,11 +70,30 @@ map_gzipped_data(unsigned char* buf, size_t* len, unsigned char* ubuf, uint32_t
return ubuf;
}
#else // libz implementation
#error libz not yet implemented, need libdeflate
static unsigned char*
map_gzipped_data(unsigned char* buf, size_t* len, unsigned char* ubuf, uint32_t ulen){
z_stream z = {
.zalloc = Z_NULL,
.zfree = Z_NULL,
.opaque = Z_NULL,
.next_in = buf,
.avail_in = len,
.next_out = ubuf,
.avail_out = ulen,
};
int r = inflateInit(&z);
if(r != Z_OK){
munmap(buf, *len);
return NULL;
}
r = inflate(&z, Z_FLUSH);
munmap(buf, *len);
if(r != Z_STREAM_END){
inflateEnd(&z);
return NULL;
}
inflateEnd(&z);
munmap(buf, *len);
(void)ulen; // FIXME
return NULL;
}
#endif