A C++ wrapper class for the zlib


The zlib compression library

The zlib library is lossless data-compression library written in C (for more informatio, see the zlib Home Page). The zlib is related to gzip.
As a C++ user, I thought it would be nice to use the zlib thru the iostream interface. I didn't have enough to wrap perfectly the zlib facilities, so I used zlib's high level interface.
The izipstream and ozipstream classes below can be used as regular iostreams. They work fine with the HPUX HP C++ compiler 10.22 (based on cfront). The last version of zlib working with HPUX 10 can be found in The HP-UX Porting and Archive Centre.

Code

Header: file zipiostream.h

/* wrapping the zlib with iostream using gzFile setbuf NYI Jean-Louis Ardoint 1996 */ #include <iostream.h> #include <zlib.h> class zipstreambuf : public streambuf { public: static const int openprot; private: char opened; int mode; gzFile file; public: zipstreambuf() { opened = 0; } int is_open() { return opened; } zipstreambuf* open(const char * name, int om); zipstreambuf* close(); ~zipstreambuf() { close(); } virtual int overflow(int=EOF); virtual int underflow(); virtual int sync() ; /* NYI virtual streambuf* setbuf(char* p, int len) ; */ }; class zipstreambase : virtual public ios { zipstreambuf buf; public: zipstreambase() {init(&buf);} zipstreambase(const char* name, int mode); ~zipstreambase(); void open(const char* name, int mode); void close(); // NYI void setbuf(char* p, int l); zipstreambuf* rdbuf() { return &buf; } }; class izipstream : public zipstreambase, public istream { public: izipstream() {} izipstream(const char* name, int mode=ios::in) : zipstreambase(name,mode) {} zipstreambuf* rdbuf() {return zipstreambase::rdbuf(); } void open(const char* name) {zipstreambase::open(name,ios::in);} }; class ozipstream : public zipstreambase, public ostream { public: ozipstream() {} ozipstream(const char* name, int mode=ios::out) : zipstreambase(name,mode) {} zipstreambuf* rdbuf() {return zipstreambase::rdbuf(); } void open(const char* name) {zipstreambase::open(name,ios::out);} };

Body: file zipiostream.cc

#include <zipiostream.h> zipstreambuf* zipstreambuf::open(const char* name, int om) { if (is_open()) return (zipstreambuf*)0; mode = om; // no append nor read/write mode if ((mode & ios::ate) || (mode & ios::app) || ((mode & ios::in) && (mode & ios::out))) return (zipstreambuf*)0; char fmode[10]; char * fmodeptr = fmode; if (mode & ios::in) { *fmodeptr++ = 'r'; } else if (mode & ios::out) *fmodeptr++ = 'w'; *fmodeptr++ = 'b'; *fmodeptr = '\0'; file = gzopen(name,fmode); if (file == NULL) return (zipstreambuf*)0; opened = 1; return this; } zipstreambuf * zipstreambuf::close() { if (opened) { sync(); opened = 0; if (gzclose(file) == Z_OK) return this; } return (zipstreambuf*)0; } int zipstreambuf::underflow() { if (gptr() && gptr() < egptr()) return zapeof(*gptr()); if (!(mode&ios::in) || !opened || allocate()==EOF) return EOF; int count = gzread(file,base(),blen()); if (count < 1) { setg(0,0,0); return EOF; } setg(base(),base(),base()+count); return zapeof(*base()); } int zipstreambuf::overflow(int c) { if (!(mode&ios::out) || !opened || allocate()==EOF) return EOF; if (gptr() && egptr() > gptr()) return EOF; setg(0,0,0); // make sure there is a put area if (!pptr()) setp(base(),base()); int w = pptr() -pbase(); if (c != EOF) { *pptr() = c; ++w; } if (gzwrite(file,pbase(),w)) { setp(base(),ebuf()-1); return zapeof(c); } setp(0,0); return EOF; } int zipstreambuf::sync() { if (gptr() && egptr() > gptr()) return EOF; if (pptr() && pptr() > pbase()) return overflow(EOF); return 0; } // CLASS zipstreambase zipstreambase::zipstreambase(const char* name, int mode) { init(&buf); open(name,mode); } zipstreambase::~zipstreambase() { if(buf.is_open()) buf.close(); } void zipstreambase::open(const char* name, int mode) { if (!buf.open(name,mode)) clear(rdstate() & ios::badbit); } void zipstreambase::close() { if (buf.is_open()) if (!buf.close()) clear(rdstate() & ios::badbit); }

Back to my homepage

Last modified Feb 21, 1997


This page hosted by GeoCities Get your own Free Home Page


1