1    	#ifdef SOPLEX_WITH_ZLIB
2    	
3    	// ============================================================================
4    	// gzstream, C++ iostream classes wrapping the zlib compression library.
5    	// Copyright (C) 2001  Deepak Bandyopadhyay, Lutz Kettner
6    	//
7    	// This library is free software; you can redistribute it and/or
8    	// modify it under the terms of the GNU Lesser General Public
9    	// License as published by the Free Software Foundation; either
10   	// version 2.1 of the License, or (at your option) any later version.
11   	//
12   	// This library is distributed in the hope that it will be useful,
13   	// but WITHOUT ANY WARRANTY; without even the implied warranty of
14   	// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15   	// Lesser General Public License for more details.
16   	//
17   	// You should have received a copy of the GNU Lesser General Public
18   	// License along with this library; if not, write to the Free Software
19   	// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
20   	// ============================================================================
21   	//
22   	// File          : gzstream.h
23   	// Revision      : $Revision: 1.8 $
24   	// Revision_date : $Date: 2005/11/09 13:53:50 $
25   	// Author(s)     : Deepak Bandyopadhyay, Lutz Kettner
26   	//
27   	// Standard streambuf implementation following Nicolai Josuttis, "The
28   	// Standard C++ Library".
29   	// ============================================================================
30   	
31   	/**@file gzstream.h
32   	 * @brief Utilities for handling gzipped input and output streams.
33   	 */
34   	#ifndef _GZSTREAM_H_
35   	#define _GZSTREAM_H_ 1
36   	
37   	// standard C++ with new header file names and std:: namespace
38   	#include <iostream>
39   	#include <fstream>
40   	#include <zlib.h>
41   	
42   	#define SOPLEX_GZSTREAM_NAMESPACE gzstream
43   	
44   	#ifdef SOPLEX_GZSTREAM_NAMESPACE
45   	namespace SOPLEX_GZSTREAM_NAMESPACE
46   	{
47   	#endif
48   	
49   	// ----------------------------------------------------------------------------
50   	//    Internal classes to implement gzstream. See below for user classes.
51   	// ----------------------------------------------------------------------------
52   	
53   	// ----------------------------------------------------------------------------
54   	//    class gzstreambuf
55   	// ----------------------------------------------------------------------------
56   	
57   	/**@class gzstreambuf
58   	   @brief Internal class to implement gzstream.
59   	*/
60   	class gzstreambuf
61   	   : public std::streambuf
62   	{
63   	private:
64   	
65   	   //------------------------------------
66   	   /**@name Types */
67   	   ///@{
68   	   ///
69   	   static const int bufferSize = 47 + 256; ///< size of data buff
70   	   // totals 512 bytes under g++ for igzstream at the end.
71   	   ///@}
72   	
73   	   //------------------------------------
74   	   /**@name Data */
75   	   ///@{
76   	   gzFile           file;               ///< file handle for compressed file
77   	   char             buffer[bufferSize]; ///< data buffer
78   	   char             opened;             ///< open/close state of stream
79   	   unsigned int     mode;               ///< I/O mode
80   	   ///@}
81   	
82   	   //------------------------------------
83   	   /**@name Internal helpers */
84   	   ///@{
85   	   ///
86   	   int flush_buffer();
87   	   ///@}
88   	
89   	public:
90   	
91   	   //------------------------------------
92   	   /**@name Construction / destruction */
93   	   ///@{
94   	   /// default constructor
95   	   gzstreambuf()
96   	      : file(0)
97   	      , opened(0)
98   	      , mode(0)
99   	   {
100  	      setp(buffer, buffer + (bufferSize - 1));
101  	      setg(buffer + 4,      // beginning of putback area
102  	           buffer + 4,     // read position
103  	           buffer + 4);    // end position
104  	      // ASSERT: both input & output capabilities will not be used together
105  	   }
106  	   /// destructor
107  	   ~gzstreambuf()
108  	   {
109  	      close();
110  	   }
111  	   ///@}
112  	
113  	   //------------------------------------
114  	   /**@name Interface */
115  	   ///@{
116  	   ///
117  	   int is_open()
118  	   {
119  	      return opened;
120  	   }
121  	   ///
122  	   gzstreambuf* open(const char* name, int open_mode);
123  	   ///
124  	   gzstreambuf* close();
125  	   ///
126  	   virtual int     overflow(int c = EOF);
127  	   ///
128  	   virtual int     underflow();
129  	   ///
130  	   virtual int     sync();
131  	   ///@}
132  	};
133  	
134  	// ----------------------------------------------------------------------------
135  	//    class gzstreambase
136  	// ----------------------------------------------------------------------------
137  	
138  	/**@class gzstreambase
139  	   @brief Internal class to implement gzstream.
140  	*/
141  	class gzstreambase
142  	   : virtual public std::ios
143  	{
144  	protected:
145  	
146  	   //------------------------------------
147  	   /**@name Data */
148  	   ///@{
149  	   ///
150  	   gzstreambuf buf;
151  	   ///@}
152  	
153  	public:
154  	
155  	   //------------------------------------
156  	   /**@name Construction / destruction */
157  	   ///@{
158  	   /// default constructor
159  	   gzstreambase()
160  	   {
161  	      init(&buf);
162  	   }
163  	   /// full constructor
164  	   gzstreambase(const char* _name, int _open_mode);
165  	   /// destructor
166  	   ~gzstreambase();
167  	   ///@}
168  	
169  	   //------------------------------------
170  	   /**@name Interface */
171  	   ///@{
172  	   ///
173  	   void open(const char* _name, int _open_mode);
174  	   ///
175  	   void close();
176  	   ///
177  	   gzstreambuf* rdbuf()
178  	   {
179  	      return &buf;
180  	   }
181  	   ///@}
182  	};
183  	
184  	// ----------------------------------------------------------------------------
185  	// User classes. Use igzstream and ogzstream analogously to ifstream and
186  	// ofstream respectively. They read and write files based on the gz*
187  	// function interface of the zlib. Files are compatible with gzip compression.
188  	// ----------------------------------------------------------------------------
189  	
190  	// ----------------------------------------------------------------------------
191  	//    class igzstream
192  	// ----------------------------------------------------------------------------
193  	
194  	/**@class igzstream
195  	   @brief Class to implement a gzip'd input stream.
196  	*/
197  	class igzstream
198  	   : public std::istream
199  	   , public gzstreambase
200  	{
201  	public:
202  	
203  	   //------------------------------------
204  	   /**@name Construction / destruction */
205  	   ///@{
206  	   /// default constructor
207  	   igzstream()
208  	      : std::istream(&buf)
209  	   {}
210  	   /// full constructor
211  	   igzstream(const char*  _name,
212  	             int          _open_mode = std::ios::in)
213  	      : std::istream(&buf)
214  	      , gzstreambase(_name, _open_mode)
215  	   {}
216  	   ///@}
217  	
218  	   //------------------------------------
219  	   /**@name Interface */
220  	   ///@{
221  	   ///
222  	   gzstreambuf* rdbuf()
223  	   {
224  	      return gzstreambase::rdbuf();
225  	   }
226  	   ///
227  	   void open(const char*  _name,
228  	             int          _open_mode = std::ios::in)
229  	   {
230  	      gzstreambase::open(_name, _open_mode);
231  	   }
232  	   ///@}
233  	};
234  	
235  	// ----------------------------------------------------------------------------
236  	//    class ogzstream
237  	// ----------------------------------------------------------------------------
238  	
239  	/**@class ogzstream
240  	   @brief Class to implement a gzip'd output stream.
241  	*/
242  	class ogzstream
243  	   : public gzstreambase
244  	   , public std::ostream
245  	{
246  	public:
247  	
248  	   //------------------------------------
249  	   /**@name Construction / destruction */
250  	   ///@{
251  	   /// default constructor
252  	   ogzstream()
253  	      : std::ostream(&buf)
254  	   {}
255  	   /// full constructor
256  	   explicit
257  	   ogzstream(const char* _name,
258  	             int         _open_mode = std::ios::out)
259  	      : gzstreambase(_name, _open_mode)
260  	      , std::ostream(&buf)
261  	   {}
262  	   ///@}
263  	
264  	   //------------------------------------
265  	   /**@name Interface */
266  	   ///@{
267  	   ///
268  	   gzstreambuf* rdbuf()
269  	   {
270  	      return gzstreambase::rdbuf();
271  	   }
272  	   ///
273  	   void open(const char*  _name,
274  	             int          _open_mode = std::ios::out)
275  	   {
276  	      gzstreambase::open(_name, _open_mode);
277  	   }
278  	};
279  	
280  	#ifdef SOPLEX_GZSTREAM_NAMESPACE
281  	} // namespace SOPLEX_GZSTREAM_NAMESPACE
282  	#endif
283  	
284  	#endif // _GZSTREAM_H_
285  	// ============================================================================
286  	// EOF //
287  	
288  	#endif
289