1 // OutBuffer.cpp 2 3 #include "StdAfx.h" 4 5 #include "../../../C/Alloc.h" 6 7 #include "OutBuffer.h" 8 Create(UInt32 bufSize)9bool COutBuffer::Create(UInt32 bufSize) throw() 10 { 11 const UInt32 kMinBlockSize = 1; 12 if (bufSize < kMinBlockSize) 13 bufSize = kMinBlockSize; 14 if (_buf != 0 && _bufSize == bufSize) 15 return true; 16 Free(); 17 _bufSize = bufSize; 18 _buf = (Byte *)::MidAlloc(bufSize); 19 return (_buf != 0); 20 } 21 Free()22void COutBuffer::Free() throw() 23 { 24 ::MidFree(_buf); 25 _buf = 0; 26 } 27 Init()28void COutBuffer::Init() throw() 29 { 30 _streamPos = 0; 31 _limitPos = _bufSize; 32 _pos = 0; 33 _processedSize = 0; 34 _overDict = false; 35 #ifdef _NO_EXCEPTIONS 36 ErrorCode = S_OK; 37 #endif 38 } 39 GetProcessedSize() const40UInt64 COutBuffer::GetProcessedSize() const throw() 41 { 42 UInt64 res = _processedSize + _pos - _streamPos; 43 if (_streamPos > _pos) 44 res += _bufSize; 45 return res; 46 } 47 48 FlushPart()49HRESULT COutBuffer::FlushPart() throw() 50 { 51 // _streamPos < _bufSize 52 UInt32 size = (_streamPos >= _pos) ? (_bufSize - _streamPos) : (_pos - _streamPos); 53 HRESULT result = S_OK; 54 #ifdef _NO_EXCEPTIONS 55 result = ErrorCode; 56 #endif 57 if (_buf2 != 0) 58 { 59 memcpy(_buf2, _buf + _streamPos, size); 60 _buf2 += size; 61 } 62 63 if (_stream != 0 64 #ifdef _NO_EXCEPTIONS 65 && (ErrorCode == S_OK) 66 #endif 67 ) 68 { 69 UInt32 processedSize = 0; 70 result = _stream->Write(_buf + _streamPos, size, &processedSize); 71 size = processedSize; 72 } 73 _streamPos += size; 74 if (_streamPos == _bufSize) 75 _streamPos = 0; 76 if (_pos == _bufSize) 77 { 78 _overDict = true; 79 _pos = 0; 80 } 81 _limitPos = (_streamPos > _pos) ? _streamPos : _bufSize; 82 _processedSize += size; 83 return result; 84 } 85 Flush()86HRESULT COutBuffer::Flush() throw() 87 { 88 #ifdef _NO_EXCEPTIONS 89 if (ErrorCode != S_OK) 90 return ErrorCode; 91 #endif 92 93 while (_streamPos != _pos) 94 { 95 HRESULT result = FlushPart(); 96 if (result != S_OK) 97 return result; 98 } 99 return S_OK; 100 } 101 FlushWithCheck()102void COutBuffer::FlushWithCheck() 103 { 104 HRESULT result = Flush(); 105 #ifdef _NO_EXCEPTIONS 106 ErrorCode = result; 107 #else 108 if (result != S_OK) 109 throw COutBufferException(result); 110 #endif 111 } 112