X-Git-Url: http://www.chiark.greenend.org.uk/ucgi/~yarrgweb/git?p=ypp-sc-tools.web-live.git;a=blobdiff_plain;f=pctb%2Fcommon.c;h=f95e585866657f8d8e29c19c7c31b5daeae9c977;hp=2c2a085a30e9fdaa7ded64ffa7b10c82f31208ac;hb=2e3f8f6ab168a6824dac1430473c7299018a1b0f;hpb=61e9f852b6991232730eee7b73798b3afcf321b2 diff --git a/pctb/common.c b/pctb/common.c index 2c2a085..f95e585 100644 --- a/pctb/common.c +++ b/pctb/common.c @@ -49,31 +49,12 @@ int dbfile_gzopen(const char *basepath_spec) { assert(!dbfile); basepath= basepath_spec; - //uncomppath= masprintf("%s (uncompressed)", basepath); char *zpath= masprintf("%s.gz", basepath); - int zfd= open(zpath, O_RDONLY); + int e= gzopen(zpath, O_RDONLY, &dbfile, &dbzcat, 0); free(zpath); - - if (zfd<0) { sysassert(errno==ENOENT); return 0; } - - int pipefds[2]; - sysassert(! pipe(pipefds) ); - - sysassert( (dbzcat=fork()) != -1 ); - if (!dbzcat) { - sysassert( dup2(zfd,0)==0 ); - sysassert( dup2(pipefds[1],1)==1 ); - sysassert(! close(zfd) ); - sysassert(! close(pipefds[0]) ); - sysassert(! close(pipefds[1]) ); - execlp("zcat","zcat",(char*)0); - sysassert(!"execlp zcat"); - } - sysassert(! close(zfd) ); - sysassert(! close(pipefds[1]) ); - sysassert( dbfile= fdopen(pipefds[0], "r") ); - + if (e) { errno=e; sysassert(errno==ENOENT); return 0; } + return 1; } @@ -89,19 +70,7 @@ int dbfile_open(const char *tpath) { } void dbfile_close(void) { - if (!dbfile) return; - - sysassert(!ferror(dbfile)); - sysassert(!fclose(dbfile)); - - if (dbzcat != -1) { - char *zcatstr= masprintf("zcat %s.gz", basepath); - waitpid_check_exitstatus(dbzcat,zcatstr,1); - free(zcatstr); - dbzcat= -1; - } - - dbfile= 0; + gzclose(&dbfile, &dbzcat, basepath); } #define dbassertgl(x) ((x) ? (void)0 : dbfile_assertfail(file,line,#x)) @@ -148,3 +117,52 @@ void dbfile_assertfail(const char *file, int line, const char *m) { " %s", file,line, m); } + +int gzopen(const char *zpath, int oflags, FILE **f_r, pid_t *pid_r, + const char *gziplevel /* 0 for read; may be 0, or "-1" etc. */) { + + int zfd= open(zpath, oflags, 0666); + if (!zfd) return errno; + + int pipefds[2]; + sysassert(! pipe(pipefds) ); + + int oi,io; const char *cmd; const char *stdiomode; + switch ((oflags & O_ACCMODE)) { + case O_RDONLY: oi=0; io=1; cmd="gunzip"; stdiomode="r"; break; + case O_WRONLY: oi=1; io=0; cmd="gzip"; stdiomode="w"; break; + default: abort(); + } + + sysassert( (*pid_r=fork()) != -1 ); + if (!*pid_r) { + sysassert( dup2(zfd,oi)==oi ); + sysassert( dup2(pipefds[io],io)==io ); + sysassert(! close(zfd) ); + sysassert(! close(pipefds[0]) ); + sysassert(! close(pipefds[1]) ); + execlp(cmd,cmd,gziplevel,(char*)0); + sysassert(!"execlp gzip/gunzip"); + } + sysassert(! close(zfd) ); + sysassert(! close(pipefds[io]) ); + sysassert( *f_r= fdopen(pipefds[oi], stdiomode) ); + + return 0; +} + +void gzclose(FILE **f, pid_t *p, const char *what) { + if (!*f) return; + + sysassert(!ferror(*f)); + sysassert(!fclose(*f)); + + if (*p != -1) { + char *process= masprintf("%s (de)compressor",what); + waitpid_check_exitstatus(*p,process,1); + free(process); + *p= -1; + } + + *f= 0; +}