]>
git.saurik.com Git - wxWidgets.git/blob - src/common/zstream.cpp
   1 ///////////////////////////////////////////////////////////////////////////// 
   3 // Purpose:     Compressed stream classes 
   4 // Author:      Guilhem Lavaux 
   8 // Copyright:   (c) Guilhem Lavaux 
   9 // Licence:     wxWindows licence 
  10 ///////////////////////////////////////////////////////////////////////////// 
  13 #pragma implementation "zstream.h" 
  16 // For compilers that support precompilation, includes "wx.h". 
  17 #include "wx/wxprec.h" 
  23 #if wxUSE_ZLIB && wxUSE_STREAMS 
  25 #include "wx/zstream.h" 
  30 // normally, the compiler options should contain -I../zlib, but it is 
  31 // apparently not the case for all MSW makefiles and so, unless we use 
  32 // configure (which defines __WX_SETUP_H__) or it is explicitly overridden by 
  33 // the user (who can define wxUSE_ZLIB_H_IN_PATH), we hardcode the path here 
  34 #if defined(__WXMSW__) && !defined(__WX_SETUP_H__) && !defined(wxUSE_ZLIB_H_IN_PATH) 
  35    #include "../zlib/zlib.h" 
  40 #define ZSTREAM_BUFFER_SIZE 1024 
  42 ////////////////////// 
  44 ////////////////////// 
  46 wxZlibInputStream::wxZlibInputStream(wxInputStream
& stream
) 
  47   : wxFilterInputStream(stream
) 
  51   // I need a private stream buffer. 
  52   m_inflate 
= new z_stream_s
; 
  54   m_inflate
->zalloc 
= (alloc_func
)0; 
  55   m_inflate
->zfree 
= (free_func
)0; 
  56   m_inflate
->opaque 
= (voidpf
)0; 
  58   err 
= inflateInit(m_inflate
); 
  60     inflateEnd(m_inflate
); 
  65   m_z_buffer 
= new unsigned char[ZSTREAM_BUFFER_SIZE
]; 
  66   m_z_size 
= ZSTREAM_BUFFER_SIZE
; 
  68   m_inflate
->avail_in 
= 0; 
  69   m_inflate
->next_in 
= NULL
; 
  72 wxZlibInputStream::~wxZlibInputStream() 
  74   inflateEnd(m_inflate
); 
  78 size_t wxZlibInputStream::OnSysRead(void *buffer
, size_t size
) 
  82   m_inflate
->next_out 
= (unsigned char *)buffer
; 
  83   m_inflate
->avail_out 
= size
; 
  85   while (m_inflate
->avail_out 
> 0) { 
  86     if (m_inflate
->avail_in 
== 0) { 
  88       m_parent_i_stream
->Read(m_z_buffer
, wxMin(m_z_size
, size
)); 
  89       m_inflate
->next_in 
= m_z_buffer
; 
  90       m_inflate
->avail_in 
= m_parent_i_stream
->LastRead(); 
  92       if (m_parent_i_stream
->LastError() != wxStream_NOERROR 
&& 
  93           m_parent_i_stream
->LastError() != wxStream_EOF
) 
  95         m_lasterror 
= m_parent_i_stream
->LastError(); 
  96         return 0; // failed to read anything 
  99       if ( m_inflate
->avail_in 
== 0 ) 
 102           m_lasterror 
= wxStream_EOF
; 
 106     err 
= inflate(m_inflate
, Z_FINISH
); 
 107     if (err 
== Z_STREAM_END
) 
 108       return (size 
- m_inflate
->avail_out
); 
 111   return size
-m_inflate
->avail_out
; 
 114 ////////////////////// 
 115 // wxZlibOutputStream 
 116 ////////////////////// 
 118 wxZlibOutputStream::wxZlibOutputStream(wxOutputStream
& stream
, int level
) 
 119  : wxFilterOutputStream(stream
) 
 123   m_deflate 
= new z_stream_s
; 
 125   m_deflate
->zalloc 
= (alloc_func
)0; 
 126   m_deflate
->zfree 
= (free_func
)0; 
 127   m_deflate
->opaque 
= (voidpf
)0; 
 129   if (level 
== -1) level 
= Z_DEFAULT_COMPRESSION
; 
 130   wxASSERT_MSG(level 
>= 0 && level 
<= 9, wxT("wxZlibOutputStream compression level must be between 0 and 9!")); 
 132   err 
= deflateInit(m_deflate
, level
); 
 134     deflateEnd(m_deflate
); 
 138   m_z_buffer 
= new unsigned char[ZSTREAM_BUFFER_SIZE
]; 
 139   m_z_size 
= ZSTREAM_BUFFER_SIZE
; 
 141   m_deflate
->avail_in 
= 0; 
 142   m_deflate
->next_out 
= m_z_buffer
; 
 143   m_deflate
->avail_out 
= m_z_size
; 
 146 wxZlibOutputStream::~wxZlibOutputStream() 
 152   err 
= deflate(m_deflate
, Z_FINISH
); 
 153   if (err 
!= Z_STREAM_END
)  
 155     wxLogDebug( wxT("wxZlibOutputStream: an error occured while closing the stream.\n") ); 
 159   deflateEnd(m_deflate
); 
 164 void wxZlibOutputStream::Sync() 
 168   m_parent_o_stream
->Write(m_z_buffer
, m_z_size
-m_deflate
->avail_out
); 
 169   m_deflate
->next_out  
= m_z_buffer
; 
 170   m_deflate
->avail_out 
= m_z_size
; 
 172   err 
= deflate(m_deflate
, Z_FULL_FLUSH
); 
 177   // Fixed by "Stefan Csomor" <csomor@advancedconcepts.ch> 
 178   while( m_deflate
->avail_out 
== 0 ) 
 180      m_parent_o_stream
->Write(m_z_buffer
, m_z_size 
); 
 181      m_deflate
->next_out  
= m_z_buffer
; 
 182      m_deflate
->avail_out 
= m_z_size
; 
 183      err 
= deflate(m_deflate
, Z_FULL_FLUSH
); 
 190   m_parent_o_stream
->Write(m_z_buffer
, m_z_size
-m_deflate
->avail_out
); 
 191   m_deflate
->next_out  
= m_z_buffer
; 
 192   m_deflate
->avail_out 
= m_z_size
; 
 195 size_t wxZlibOutputStream::OnSysWrite(const void *buffer
, size_t size
) 
 199   m_deflate
->next_in 
= (unsigned char *)buffer
; 
 200   m_deflate
->avail_in 
= size
; 
 202   while (m_deflate
->avail_in 
> 0) { 
 204     if (m_deflate
->avail_out 
== 0) { 
 205       m_parent_o_stream
->Write(m_z_buffer
, m_z_size
); 
 206       if (m_parent_o_stream
->LastError() != wxStream_NOERROR
) 
 207         return (size 
- m_deflate
->avail_in
); 
 209       m_deflate
->next_out 
= m_z_buffer
; 
 210       m_deflate
->avail_out 
= m_z_size
; 
 213     err 
= deflate(m_deflate
, Z_NO_FLUSH
); 
 215       return (size 
- m_deflate
->avail_in
); 
 221   // wxUSE_ZLIB && wxUSE_STREAMS