| 1 |  | 
 
 
 
 
 | 2 | #include "zfstream.h" | 
 
 
 
 
 | 3 |  | 
 
 
 
 
 | 4 | gzfilebuf::gzfilebuf() : | 
 
 
 
 
 | 5 | file(NULL), | 
 
 
 
 
 | 6 | mode(0), | 
 
 
 
 
 | 7 | own_file_descriptor(0) | 
 
 
 
 
 | 8 | { } | 
 
 
 
 
 | 9 |  | 
 
 
 
 
 | 10 | gzfilebuf::~gzfilebuf() { | 
 
 
 
 
 | 11 |  | 
 
 
 
 
 | 12 | sync(); | 
 
 
 
 
 | 13 | if ( own_file_descriptor ) | 
 
 
 
 
 | 14 | close(); | 
 
 
 
 
 | 15 |  | 
 
 
 
 
 | 16 | } | 
 
 
 
 
 | 17 |  | 
 
 
 
 
 | 18 | gzfilebuf *gzfilebuf::open( const char *name, | 
 
 
 
 
 | 19 | int io_mode ) { | 
 
 
 
 
 | 20 |  | 
 
 
 
 
 | 21 | if ( is_open() ) | 
 
 
 
 
 | 22 | return NULL; | 
 
 
 
 
 | 23 |  | 
 
 
 
 
 | 24 | char char_mode[10]; | 
 
 
 
 
 | 25 | char *p = char_mode; | 
 
 
 
 
 | 26 |  | 
 
 
 
 
 | 27 | if ( io_mode & ios::in ) { | 
 
 
 
 
 | 28 | mode = ios::in; | 
 
 
 
 
 | 29 | *p++ = 'r'; | 
 
 
 
 
 | 30 | } else if ( io_mode & ios::app ) { | 
 
 
 
 
 | 31 | mode = ios::app; | 
 
 
 
 
 | 32 | *p++ = 'a'; | 
 
 
 
 
 | 33 | } else { | 
 
 
 
 
 | 34 | mode = ios::out; | 
 
 
 
 
 | 35 | *p++ = 'w'; | 
 
 
 
 
 | 36 | } | 
 
 
 
 
 | 37 |  | 
 
 
 
 
 | 38 | if ( io_mode & ios::binary ) { | 
 
 
 
 
 | 39 | mode |= ios::binary; | 
 
 
 
 
 | 40 | *p++ = 'b'; | 
 
 
 
 
 | 41 | } | 
 
 
 
 
 | 42 |  | 
 
 
 
 
 | 43 | // Hard code the compression level | 
 
 
 
 
 | 44 | if ( io_mode & (ios::out|ios::app )) { | 
 
 
 
 
 | 45 | *p++ = '9'; | 
 
 
 
 
 | 46 | } | 
 
 
 
 
 | 47 |  | 
 
 
 
 
 | 48 | // Put the end-of-string indicator | 
 
 
 
 
 | 49 | *p = '\0'; | 
 
 
 
 
 | 50 |  | 
 
 
 
 
 | 51 | if ( (file = gzopen(name, char_mode)) == NULL ) | 
 
 
 
 
 | 52 | return NULL; | 
 
 
 
 
 | 53 |  | 
 
 
 
 
 | 54 | own_file_descriptor = 1; | 
 
 
 
 
 | 55 |  | 
 
 
 
 
 | 56 | return this; | 
 
 
 
 
 | 57 |  | 
 
 
 
 
 | 58 | } | 
 
 
 
 
 | 59 |  | 
 
 
 
 
 | 60 | gzfilebuf *gzfilebuf::attach( int file_descriptor, | 
 
 
 
 
 | 61 | int io_mode ) { | 
 
 
 
 
 | 62 |  | 
 
 
 
 
 | 63 | if ( is_open() ) | 
 
 
 
 
 | 64 | return NULL; | 
 
 
 
 
 | 65 |  | 
 
 
 
 
 | 66 | char char_mode[10]; | 
 
 
 
 
 | 67 | char *p = char_mode; | 
 
 
 
 
 | 68 |  | 
 
 
 
 
 | 69 | if ( io_mode & ios::in ) { | 
 
 
 
 
 | 70 | mode = ios::in; | 
 
 
 
 
 | 71 | *p++ = 'r'; | 
 
 
 
 
 | 72 | } else if ( io_mode & ios::app ) { | 
 
 
 
 
 | 73 | mode = ios::app; | 
 
 
 
 
 | 74 | *p++ = 'a'; | 
 
 
 
 
 | 75 | } else { | 
 
 
 
 
 | 76 | mode = ios::out; | 
 
 
 
 
 | 77 | *p++ = 'w'; | 
 
 
 
 
 | 78 | } | 
 
 
 
 
 | 79 |  | 
 
 
 
 
 | 80 | if ( io_mode & ios::binary ) { | 
 
 
 
 
 | 81 | mode |= ios::binary; | 
 
 
 
 
 | 82 | *p++ = 'b'; | 
 
 
 
 
 | 83 | } | 
 
 
 
 
 | 84 |  | 
 
 
 
 
 | 85 | // Hard code the compression level | 
 
 
 
 
 | 86 | if ( io_mode & (ios::out|ios::app )) { | 
 
 
 
 
 | 87 | *p++ = '9'; | 
 
 
 
 
 | 88 | } | 
 
 
 
 
 | 89 |  | 
 
 
 
 
 | 90 | // Put the end-of-string indicator | 
 
 
 
 
 | 91 | *p = '\0'; | 
 
 
 
 
 | 92 |  | 
 
 
 
 
 | 93 | if ( (file = gzdopen(file_descriptor, char_mode)) == NULL ) | 
 
 
 
 
 | 94 | return NULL; | 
 
 
 
 
 | 95 |  | 
 
 
 
 
 | 96 | own_file_descriptor = 0; | 
 
 
 
 
 | 97 |  | 
 
 
 
 
 | 98 | return this; | 
 
 
 
 
 | 99 |  | 
 
 
 
 
 | 100 | } | 
 
 
 
 
 | 101 |  | 
 
 
 
 
 | 102 | gzfilebuf *gzfilebuf::close() { | 
 
 
 
 
 | 103 |  | 
 
 
 
 
 | 104 | if ( is_open() ) { | 
 
 
 
 
 | 105 |  | 
 
 
 
 
 | 106 | sync(); | 
 
 
 
 
 | 107 | gzclose( file ); | 
 
 
 
 
 | 108 | file = NULL; | 
 
 
 
 
 | 109 |  | 
 
 
 
 
 | 110 | } | 
 
 
 
 
 | 111 |  | 
 
 
 
 
 | 112 | return this; | 
 
 
 
 
 | 113 |  | 
 
 
 
 
 | 114 | } | 
 
 
 
 
 | 115 |  | 
 
 
 
 
 | 116 | int gzfilebuf::setcompressionlevel( int comp_level ) { | 
 
 
 
 
 | 117 |  | 
 
 
 
 
 | 118 | return gzsetparams(file, comp_level, -2); | 
 
 
 
 
 | 119 |  | 
 
 
 
 
 | 120 | } | 
 
 
 
 
 | 121 |  | 
 
 
 
 
 | 122 | int gzfilebuf::setcompressionstrategy( int comp_strategy ) { | 
 
 
 
 
 | 123 |  | 
 
 
 
 
 | 124 | return gzsetparams(file, -2, comp_strategy); | 
 
 
 
 
 | 125 |  | 
 
 
 
 
 | 126 | } | 
 
 
 
 
 | 127 |  | 
 
 
 
 
 | 128 |  | 
 
 
 
 
 | 129 | streampos gzfilebuf::seekoff( streamoff off, ios::seek_dir dir, int which ) { | 
 
 
 
 
 | 130 |  | 
 
 
 
 
 | 131 | return streampos(EOF); | 
 
 
 
 
 | 132 |  | 
 
 
 
 
 | 133 | } | 
 
 
 
 
 | 134 |  | 
 
 
 
 
 | 135 | int gzfilebuf::underflow() { | 
 
 
 
 
 | 136 |  | 
 
 
 
 
 | 137 | // If the file hasn't been opened for reading, error. | 
 
 
 
 
 | 138 | if ( !is_open() || !(mode & ios::in) ) | 
 
 
 
 
 | 139 | return EOF; | 
 
 
 
 
 | 140 |  | 
 
 
 
 
 | 141 | // if a buffer doesn't exists, allocate one. | 
 
 
 
 
 | 142 | if ( !base() ) { | 
 
 
 
 
 | 143 |  | 
 
 
 
 
 | 144 | if ( (allocate()) == EOF ) | 
 
 
 
 
 | 145 | return EOF; | 
 
 
 
 
 | 146 | setp(0,0); | 
 
 
 
 
 | 147 |  | 
 
 
 
 
 | 148 | } else { | 
 
 
 
 
 | 149 |  | 
 
 
 
 
 | 150 | if ( in_avail() ) | 
 
 
 
 
 | 151 | return (unsigned char) *gptr(); | 
 
 
 
 
 | 152 |  | 
 
 
 
 
 | 153 | if ( out_waiting() ) { | 
 
 
 
 
 | 154 | if ( flushbuf() == EOF ) | 
 
 
 
 
 | 155 | return EOF; | 
 
 
 
 
 | 156 | } | 
 
 
 
 
 | 157 |  | 
 
 
 
 
 | 158 | } | 
 
 
 
 
 | 159 |  | 
 
 
 
 
 | 160 | // Attempt to fill the buffer. | 
 
 
 
 
 | 161 |  | 
 
 
 
 
 | 162 | int result = fillbuf(); | 
 
 
 
 
 | 163 | if ( result == EOF ) { | 
 
 
 
 
 | 164 | // disable get area | 
 
 
 
 
 | 165 | setg(0,0,0); | 
 
 
 
 
 | 166 | return EOF; | 
 
 
 
 
 | 167 | } | 
 
 
 
 
 | 168 |  | 
 
 
 
 
 | 169 | return (unsigned char) *gptr(); | 
 
 
 
 
 | 170 |  | 
 
 
 
 
 | 171 | } | 
 
 
 
 
 | 172 |  | 
 
 
 
 
 | 173 | int gzfilebuf::overflow( int c ) { | 
 
 
 
 
 | 174 |  | 
 
 
 
 
 | 175 | if ( !is_open() || !(mode & ios::out) ) | 
 
 
 
 
 | 176 | return EOF; | 
 
 
 
 
 | 177 |  | 
 
 
 
 
 | 178 | if ( !base() ) { | 
 
 
 
 
 | 179 | if ( allocate() == EOF ) | 
 
 
 
 
 | 180 | return EOF; | 
 
 
 
 
 | 181 | setg(0,0,0); | 
 
 
 
 
 | 182 | } else { | 
 
 
 
 
 | 183 | if (in_avail()) { | 
 
 
 
 
 | 184 | return EOF; | 
 
 
 
 
 | 185 | } | 
 
 
 
 
 | 186 | if (out_waiting()) { | 
 
 
 
 
 | 187 | if (flushbuf() == EOF) | 
 
 
 
 
 | 188 | return EOF; | 
 
 
 
 
 | 189 | } | 
 
 
 
 
 | 190 | } | 
 
 
 
 
 | 191 |  | 
 
 
 
 
 | 192 | int bl = blen(); | 
 
 
 
 
 | 193 | setp( base(), base() + bl); | 
 
 
 
 
 | 194 |  | 
 
 
 
 
 | 195 | if ( c != EOF ) { | 
 
 
 
 
 | 196 |  | 
 
 
 
 
 | 197 | *pptr() = c; | 
 
 
 
 
 | 198 | pbump(1); | 
 
 
 
 
 | 199 |  | 
 
 
 
 
 | 200 | } | 
 
 
 
 
 | 201 |  | 
 
 
 
 
 | 202 | return 0; | 
 
 
 
 
 | 203 |  | 
 
 
 
 
 | 204 | } | 
 
 
 
 
 | 205 |  | 
 
 
 
 
 | 206 | int gzfilebuf::sync() { | 
 
 
 
 
 | 207 |  | 
 
 
 
 
 | 208 | if ( !is_open() ) | 
 
 
 
 
 | 209 | return EOF; | 
 
 
 
 
 | 210 |  | 
 
 
 
 
 | 211 | if ( out_waiting() ) | 
 
 
 
 
 | 212 | return flushbuf(); | 
 
 
 
 
 | 213 |  | 
 
 
 
 
 | 214 | return 0; | 
 
 
 
 
 | 215 |  | 
 
 
 
 
 | 216 | } | 
 
 
 
 
 | 217 |  | 
 
 
 
 
 | 218 | int gzfilebuf::flushbuf() { | 
 
 
 
 
 | 219 |  | 
 
 
 
 
 | 220 | int n; | 
 
 
 
 
 | 221 | char *q; | 
 
 
 
 
 | 222 |  | 
 
 
 
 
 | 223 | q = pbase(); | 
 
 
 
 
 | 224 | n = pptr() - q; | 
 
 
 
 
 | 225 |  | 
 
 
 
 
 | 226 | if ( gzwrite( file, q, n) < n ) | 
 
 
 
 
 | 227 | return EOF; | 
 
 
 
 
 | 228 |  | 
 
 
 
 
 | 229 | setp(0,0); | 
 
 
 
 
 | 230 |  | 
 
 
 
 
 | 231 | return 0; | 
 
 
 
 
 | 232 |  | 
 
 
 
 
 | 233 | } | 
 
 
 
 
 | 234 |  | 
 
 
 
 
 | 235 | int gzfilebuf::fillbuf() { | 
 
 
 
 
 | 236 |  | 
 
 
 
 
 | 237 | int required; | 
 
 
 
 
 | 238 | char *p; | 
 
 
 
 
 | 239 |  | 
 
 
 
 
 | 240 | p = base(); | 
 
 
 
 
 | 241 |  | 
 
 
 
 
 | 242 | required = blen(); | 
 
 
 
 
 | 243 |  | 
 
 
 
 
 | 244 | int t = gzread( file, p, required ); | 
 
 
 
 
 | 245 |  | 
 
 
 
 
 | 246 | if ( t <= 0) return EOF; | 
 
 
 
 
 | 247 |  | 
 
 
 
 
 | 248 | setg( base(), base(), base()+t); | 
 
 
 
 
 | 249 |  | 
 
 
 
 
 | 250 | return t; | 
 
 
 
 
 | 251 |  | 
 
 
 
 
 | 252 | } | 
 
 
 
 
 | 253 |  | 
 
 
 
 
 | 254 | gzfilestream_common::gzfilestream_common() : | 
 
 
 
 
 | 255 | ios( gzfilestream_common::rdbuf() ) | 
 
 
 
 
 | 256 | { } | 
 
 
 
 
 | 257 |  | 
 
 
 
 
 | 258 | gzfilestream_common::~gzfilestream_common() | 
 
 
 
 
 | 259 | { } | 
 
 
 
 
 | 260 |  | 
 
 
 
 
 | 261 | void gzfilestream_common::attach( int fd, int io_mode ) { | 
 
 
 
 
 | 262 |  | 
 
 
 
 
 | 263 | if ( !buffer.attach( fd, io_mode) ) | 
 
 
 
 
 | 264 | clear( ios::failbit | ios::badbit ); | 
 
 
 
 
 | 265 | else | 
 
 
 
 
 | 266 | clear(); | 
 
 
 
 
 | 267 |  | 
 
 
 
 
 | 268 | } | 
 
 
 
 
 | 269 |  | 
 
 
 
 
 | 270 | void gzfilestream_common::open( const char *name, int io_mode ) { | 
 
 
 
 
 | 271 |  | 
 
 
 
 
 | 272 | if ( !buffer.open( name, io_mode ) ) | 
 
 
 
 
 | 273 | clear( ios::failbit | ios::badbit ); | 
 
 
 
 
 | 274 | else | 
 
 
 
 
 | 275 | clear(); | 
 
 
 
 
 | 276 |  | 
 
 
 
 
 | 277 | } | 
 
 
 
 
 | 278 |  | 
 
 
 
 
 | 279 | void gzfilestream_common::close() { | 
 
 
 
 
 | 280 |  | 
 
 
 
 
 | 281 | if ( !buffer.close() ) | 
 
 
 
 
 | 282 | clear( ios::failbit | ios::badbit ); | 
 
 
 
 
 | 283 |  | 
 
 
 
 
 | 284 | } | 
 
 
 
 
 | 285 |  | 
 
 
 
 
 | 286 | gzfilebuf *gzfilestream_common::rdbuf() | 
 
 
 
 
 | 287 | { | 
 
 
 
 
 | 288 | return &buffer; | 
 
 
 
 
 | 289 | } | 
 
 
 
 
 | 290 |  | 
 
 
 
 
 | 291 | gzifstream::gzifstream() : | 
 
 
 
 
 | 292 | ios( gzfilestream_common::rdbuf() ) | 
 
 
 
 
 | 293 | { | 
 
 
 
 
 | 294 | clear( ios::badbit ); | 
 
 
 
 
 | 295 | } | 
 
 
 
 
 | 296 |  | 
 
 
 
 
 | 297 | gzifstream::gzifstream( const char *name, int io_mode ) : | 
 
 
 
 
 | 298 | ios( gzfilestream_common::rdbuf() ) | 
 
 
 
 
 | 299 | { | 
 
 
 
 
 | 300 | gzfilestream_common::open( name, io_mode ); | 
 
 
 
 
 | 301 | } | 
 
 
 
 
 | 302 |  | 
 
 
 
 
 | 303 | gzifstream::gzifstream( int fd, int io_mode ) : | 
 
 
 
 
 | 304 | ios( gzfilestream_common::rdbuf() ) | 
 
 
 
 
 | 305 | { | 
 
 
 
 
 | 306 | gzfilestream_common::attach( fd, io_mode ); | 
 
 
 
 
 | 307 | } | 
 
 
 
 
 | 308 |  | 
 
 
 
 
 | 309 | gzifstream::~gzifstream() { } | 
 
 
 
 
 | 310 |  | 
 
 
 
 
 | 311 | gzofstream::gzofstream() : | 
 
 
 
 
 | 312 | ios( gzfilestream_common::rdbuf() ) | 
 
 
 
 
 | 313 | { | 
 
 
 
 
 | 314 | clear( ios::badbit ); | 
 
 
 
 
 | 315 | } | 
 
 
 
 
 | 316 |  | 
 
 
 
 
 | 317 | gzofstream::gzofstream( const char *name, int io_mode ) : | 
 
 
 
 
 | 318 | ios( gzfilestream_common::rdbuf() ) | 
 
 
 
 
 | 319 | { | 
 
 
 
 
 | 320 | gzfilestream_common::open( name, io_mode ); | 
 
 
 
 
 | 321 | } | 
 
 
 
 
 | 322 |  | 
 
 
 
 
 | 323 | gzofstream::gzofstream( int fd, int io_mode ) : | 
 
 
 
 
 | 324 | ios( gzfilestream_common::rdbuf() ) | 
 
 
 
 
 | 325 | { | 
 
 
 
 
 | 326 | gzfilestream_common::attach( fd, io_mode ); | 
 
 
 
 
 | 327 | } | 
 
 
 
 
 | 328 |  | 
 
 
 
 
 | 329 | gzofstream::~gzofstream() { } |