Logo Search packages:      
Sourcecode: harbour version File versions  Download package

DWORD CZipArchive::ReadFile ( void *  pBuf,
DWORD  iSize 
)

Decompress currently opened file to the buffer.

Parameters:
pBuf buffer to receive data
iSize the size of the buffer
Returns:
the number of bytes read
See also:
OpenFile
Note:
Throws exceptions.

Definition at line 316 of file ziparchive.cpp.

References CheckForError(), CryptDecodeBuffer(), CurrentFile(), extract, CZipAutoBuffer::GetSize(), m_iFileOpened, m_info, CZipArchive::CZipInternalInfo::m_pBuffer, m_storage, CZipArchive::CZipInternalInfo::m_stream, CZipArchive::CZipInternalInfo::m_uComprLeft, CZipArchive::CZipInternalInfo::m_uCrc32, CZipFileHeader::m_uMethod, CZipArchive::CZipInternalInfo::m_uUncomprLeft, and CZipStorage::Read().

Referenced by ExtractFile(), and TestFile().

{
      if (m_iFileOpened != extract)
      {
            TRACE(_T("%s(%i) : Current file must be opened.\n"),__FILE__,__LINE__);
            return 0;
      }

      if (!pBuf || !iSize)
            return 0;

      m_info.m_stream.next_out = (Bytef*)pBuf;
      m_info.m_stream.avail_out = iSize > m_info.m_uUncomprLeft
            ? m_info.m_uUncomprLeft : iSize;


      DWORD iRead = 0;

      // may happen when the file is 0 sized
      bool bForce = m_info.m_stream.avail_out == 0 && m_info.m_uComprLeft > 0;
      while (m_info.m_stream.avail_out > 0 || (bForce && m_info.m_uComprLeft > 0))
      {
            if ((m_info.m_stream.avail_in == 0) &&
                  (m_info.m_uComprLeft >= 0)) // Also when there are zero bytes left!
            {
                  DWORD uToRead = m_info.m_pBuffer.GetSize();
                  if (m_info.m_uComprLeft < uToRead)
                        uToRead = m_info.m_uComprLeft;

                  if (uToRead == 0)
                  {
                        uToRead = 1; // Add dummy byte at end of compressed data.
                  }
                  else
                  {
                        m_storage.Read(m_info.m_pBuffer, uToRead, false);
                        CryptDecodeBuffer(uToRead);
                  }

                  m_info.m_uComprLeft -= uToRead;

                  m_info.m_stream.next_in = (Bytef*)(char*)m_info.m_pBuffer;
                  m_info.m_stream.avail_in = uToRead;
            }

            if (CurrentFile()->m_uMethod == 0)
            {
                  DWORD uToCopy = m_info.m_stream.avail_out < m_info.m_stream.avail_in
                        ? m_info.m_stream.avail_out : m_info.m_stream.avail_in;

                  memcpy(m_info.m_stream.next_out, m_info.m_stream.next_in, uToCopy);

                  m_info.m_uCrc32 = crc32(m_info.m_uCrc32, m_info.m_stream.next_out, uToCopy);

                  m_info.m_uUncomprLeft -= uToCopy;
                  m_info.m_stream.avail_in -= uToCopy;
                  m_info.m_stream.avail_out -= uToCopy;
                  m_info.m_stream.next_out += uToCopy;
                  m_info.m_stream.next_in += uToCopy;
            m_info.m_stream.total_out += uToCopy;
                  iRead += uToCopy;
            }
            else
            {
                  DWORD uTotal = m_info.m_stream.total_out;
                  Bytef* pOldBuf =  m_info.m_stream.next_out;
                  int err = inflate(&m_info.m_stream, Z_SYNC_FLUSH);
                  DWORD uToCopy = m_info.m_stream.total_out - uTotal;

                  m_info.m_uCrc32 = crc32(m_info.m_uCrc32, pOldBuf, uToCopy);

                  m_info.m_uUncomprLeft -= uToCopy;
                  iRead += uToCopy;

                  if (err == Z_STREAM_END)
                        return iRead;

                  CheckForError(err);
            }
      }

      return iRead;
}


Generated by  Doxygen 1.6.0   Back to index