rlm@1
|
1 // InOutTempBuffer.cpp
|
rlm@1
|
2
|
rlm@1
|
3 #include "StdAfx.h"
|
rlm@1
|
4
|
rlm@1
|
5 #include "InOutTempBuffer.h"
|
rlm@1
|
6 #include "../../Common/Defs.h"
|
rlm@1
|
7 // #include "Windows/Defs.h"
|
rlm@1
|
8
|
rlm@1
|
9 #include "StreamUtils.h"
|
rlm@1
|
10
|
rlm@1
|
11 using namespace NWindows;
|
rlm@1
|
12 using namespace NFile;
|
rlm@1
|
13 using namespace NDirectory;
|
rlm@1
|
14
|
rlm@1
|
15 static UInt32 kTmpBufferMemorySize = (1 << 20);
|
rlm@1
|
16
|
rlm@1
|
17 static LPCTSTR kTempFilePrefixString = TEXT("iot");
|
rlm@1
|
18
|
rlm@1
|
19 CInOutTempBuffer::CInOutTempBuffer():
|
rlm@1
|
20 _buffer(NULL)
|
rlm@1
|
21 {
|
rlm@1
|
22 }
|
rlm@1
|
23
|
rlm@1
|
24 void CInOutTempBuffer::Create()
|
rlm@1
|
25 {
|
rlm@1
|
26 _buffer = new Byte[kTmpBufferMemorySize];
|
rlm@1
|
27 }
|
rlm@1
|
28
|
rlm@1
|
29 CInOutTempBuffer::~CInOutTempBuffer()
|
rlm@1
|
30 {
|
rlm@1
|
31 delete []_buffer;
|
rlm@1
|
32 }
|
rlm@1
|
33 void CInOutTempBuffer::InitWriting()
|
rlm@1
|
34 {
|
rlm@1
|
35 _bufferPosition = 0;
|
rlm@1
|
36 _tmpFileCreated = false;
|
rlm@1
|
37 _fileSize = 0;
|
rlm@1
|
38 }
|
rlm@1
|
39
|
rlm@1
|
40 bool CInOutTempBuffer::WriteToFile(const void *data, UInt32 size)
|
rlm@1
|
41 {
|
rlm@1
|
42 if (size == 0)
|
rlm@1
|
43 return true;
|
rlm@1
|
44 if(!_tmpFileCreated)
|
rlm@1
|
45 {
|
rlm@1
|
46 CSysString tempDirPath;
|
rlm@1
|
47 if(!MyGetTempPath(tempDirPath))
|
rlm@1
|
48 return false;
|
rlm@1
|
49 if (_tempFile.Create(tempDirPath, kTempFilePrefixString, _tmpFileName) == 0)
|
rlm@1
|
50 return false;
|
rlm@1
|
51 // _outFile.SetOpenCreationDispositionCreateAlways();
|
rlm@1
|
52 if(!_outFile.Create(_tmpFileName, true))
|
rlm@1
|
53 return false;
|
rlm@1
|
54 _tmpFileCreated = true;
|
rlm@1
|
55 }
|
rlm@1
|
56 UInt32 processedSize;
|
rlm@1
|
57 if(!_outFile.Write(data, size, processedSize))
|
rlm@1
|
58 return false;
|
rlm@1
|
59 _fileSize += processedSize;
|
rlm@1
|
60 return (processedSize == size);
|
rlm@1
|
61 }
|
rlm@1
|
62
|
rlm@1
|
63 bool CInOutTempBuffer::FlushWrite()
|
rlm@1
|
64 {
|
rlm@1
|
65 return _outFile.Close();
|
rlm@1
|
66 }
|
rlm@1
|
67
|
rlm@1
|
68 bool CInOutTempBuffer::Write(const void *data, UInt32 size)
|
rlm@1
|
69 {
|
rlm@1
|
70 if(_bufferPosition < kTmpBufferMemorySize)
|
rlm@1
|
71 {
|
rlm@1
|
72 UInt32 curSize = MyMin(kTmpBufferMemorySize - _bufferPosition, size);
|
rlm@1
|
73 memmove(_buffer + _bufferPosition, (const Byte *)data, curSize);
|
rlm@1
|
74 _bufferPosition += curSize;
|
rlm@1
|
75 size -= curSize;
|
rlm@1
|
76 data = ((const Byte *)data) + curSize;
|
rlm@1
|
77 _fileSize += curSize;
|
rlm@1
|
78 }
|
rlm@1
|
79 return WriteToFile(data, size);
|
rlm@1
|
80 }
|
rlm@1
|
81
|
rlm@1
|
82 bool CInOutTempBuffer::InitReading()
|
rlm@1
|
83 {
|
rlm@1
|
84 _currentPositionInBuffer = 0;
|
rlm@1
|
85 if(_tmpFileCreated)
|
rlm@1
|
86 return _inFile.Open(_tmpFileName);
|
rlm@1
|
87 return true;
|
rlm@1
|
88 }
|
rlm@1
|
89
|
rlm@1
|
90 HRESULT CInOutTempBuffer::WriteToStream(ISequentialOutStream *stream)
|
rlm@1
|
91 {
|
rlm@1
|
92 if (_currentPositionInBuffer < _bufferPosition)
|
rlm@1
|
93 {
|
rlm@1
|
94 UInt32 sizeToWrite = _bufferPosition - _currentPositionInBuffer;
|
rlm@1
|
95 RINOK(WriteStream(stream, _buffer + _currentPositionInBuffer, sizeToWrite));
|
rlm@1
|
96 _currentPositionInBuffer += sizeToWrite;
|
rlm@1
|
97 }
|
rlm@1
|
98 if (!_tmpFileCreated)
|
rlm@1
|
99 return true;
|
rlm@1
|
100 for (;;)
|
rlm@1
|
101 {
|
rlm@1
|
102 UInt32 localProcessedSize;
|
rlm@1
|
103 if (!_inFile.ReadPart(_buffer, kTmpBufferMemorySize, localProcessedSize))
|
rlm@1
|
104 return E_FAIL;
|
rlm@1
|
105 if (localProcessedSize == 0)
|
rlm@1
|
106 return S_OK;
|
rlm@1
|
107 RINOK(WriteStream(stream, _buffer, localProcessedSize));
|
rlm@1
|
108 }
|
rlm@1
|
109 }
|
rlm@1
|
110
|
rlm@1
|
111 STDMETHODIMP CSequentialOutTempBufferImp::Write(const void *data, UInt32 size, UInt32 *processedSize)
|
rlm@1
|
112 {
|
rlm@1
|
113 if (!_buffer->Write(data, size))
|
rlm@1
|
114 {
|
rlm@1
|
115 if (processedSize != NULL)
|
rlm@1
|
116 *processedSize = 0;
|
rlm@1
|
117 return E_FAIL;
|
rlm@1
|
118 }
|
rlm@1
|
119 if (processedSize != NULL)
|
rlm@1
|
120 *processedSize = size;
|
rlm@1
|
121 return S_OK;
|
rlm@1
|
122 }
|