Remove dead code.
[novacoin.git] / src / serialize.cpp
1 #include "serialize.h"
2 #include "hash.h"
3
4 template<typename Stream>
5 void WriteCompactSize(Stream& os, uint64_t nSize)
6 {
7     if (nSize < 0xfd)
8     {
9         auto chSize = (uint8_t)nSize;
10         WRITEDATA(os, chSize);
11     }
12     else if (nSize <= std::numeric_limits<uint16_t>::max())
13     {
14         uint8_t chSize = 0xfd;
15         auto xSize = (uint16_t)nSize;
16         WRITEDATA(os, chSize);
17         WRITEDATA(os, xSize);
18     }
19     else if (nSize <= std::numeric_limits<uint32_t>::max())
20     {
21         uint8_t chSize = 0xfe;
22         auto xSize = (uint32_t)nSize;
23         WRITEDATA(os, chSize);
24         WRITEDATA(os, xSize);
25     }
26     else
27     {
28         uint8_t chSize = 0xff;
29         auto xSize = nSize;
30         WRITEDATA(os, chSize);
31         WRITEDATA(os, xSize);
32     }
33     return;
34 }
35
36
37 template<typename Stream>
38 uint64_t ReadCompactSize(Stream& is)
39 {
40     uint8_t chSize;
41     READDATA(is, chSize);
42     uint64_t nSizeRet = 0;
43     if (chSize < 0xfd)
44     {
45         nSizeRet = chSize;
46     }
47     else if (chSize == 0xfd)
48     {
49         uint16_t xSize;
50         READDATA(is, xSize);
51         nSizeRet = xSize;
52     }
53     else if (chSize == 0xfe)
54     {
55         uint32_t xSize;
56         READDATA(is, xSize);
57         nSizeRet = xSize;
58     }
59     else
60     {
61         uint64_t xSize;
62         READDATA(is, xSize);
63         nSizeRet = xSize;
64     }
65     if (nSizeRet > (uint64_t)MAX_SIZE)
66         throw std::ios_base::failure("ReadCompactSize() : size too large");
67     return nSizeRet;
68 }
69
70
71
72 // Template instantiation
73
74 template void WriteCompactSize<CAutoFile>(CAutoFile&, uint64_t);
75 template void WriteCompactSize<CDataStream>(CDataStream&, uint64_t);
76 template void WriteCompactSize<CHashWriter>(CHashWriter&, uint64_t);
77
78 template uint64_t ReadCompactSize<CAutoFile>(CAutoFile&);
79 template uint64_t ReadCompactSize<CDataStream>(CDataStream&);
80
81 //
82 //CAutoFile
83 //
84
85 CAutoFile::CAutoFile(FILE* filenew, int nTypeIn, int nVersionIn)
86 {
87     file = filenew;
88     nType = nTypeIn;
89     nVersion = nVersionIn;
90     state = 0;
91     exceptmask = std::ios::badbit | std::ios::failbit;
92 }
93
94 CAutoFile::~CAutoFile()
95 {
96     fclose();
97 }
98
99 void CAutoFile::fclose()
100 {
101     if (file != NULL && file != stdin && file != stdout && file != stderr)
102         ::fclose(file);
103     file = NULL;
104 }
105
106 void CAutoFile::setstate(short bits, const char* psz)
107 {
108     state |= bits;
109     if (state & exceptmask)
110         throw std::ios_base::failure(psz);
111 }
112
113 CAutoFile& CAutoFile::read(char* pch, size_t nSize)
114 {
115     if (!file)
116         throw std::ios_base::failure("CAutoFile::read : file handle is NULL");
117     if (fread(pch, 1, nSize, file) != nSize)
118         setstate(std::ios::failbit, feof(file) ? "CAutoFile::read : end of file" : "CAutoFile::read : fread failed");
119     return (*this);
120 }
121
122 CAutoFile& CAutoFile::write(const char* pch, size_t nSize)
123 {
124     if (!file)
125         throw std::ios_base::failure("CAutoFile::write : file handle is NULL");
126     if (fwrite(pch, 1, nSize, file) != nSize)
127         setstate(std::ios::failbit, "CAutoFile::write : write failed");
128     return (*this);
129 }
130
131 //
132 //CBufferedFile
133 //
134
135 void CBufferedFile::setstate(short bits, const char *psz)
136 {
137     state |= bits;
138     if (state & exceptmask)
139         throw std::ios_base::failure(psz);
140 }
141
142 bool CBufferedFile::Fill()
143 {
144     auto pos = (uint32_t)(nSrcPos % vchBuf.size());
145     auto readNow = (uint32_t)(vchBuf.size() - pos);
146     auto nAvail = (uint32_t)(vchBuf.size() - (nSrcPos - nReadPos) - nRewind);
147     if (nAvail < readNow)
148         readNow = nAvail;
149     if (readNow == 0)
150         return false;
151     size_t read = fread((void*)&vchBuf[pos], 1, readNow, src);
152     if (read == 0) {
153         setstate(std::ios_base::failbit, feof(src) ? "CBufferedFile::Fill : end of file" : "CBufferedFile::Fill : fread failed");
154         return false;
155     } else {
156         nSrcPos += read;
157         return true;
158     }
159 }
160
161 CBufferedFile::CBufferedFile(FILE *fileIn, uint64_t nBufSize, uint64_t nRewindIn, int nTypeIn, int nVersionIn) :
162     src(fileIn), nSrcPos(0), nReadPos(0), nReadLimit(std::numeric_limits<uint64_t>::max()), nRewind(nRewindIn), vchBuf(nBufSize, 0),
163     state(0), exceptmask(std::ios_base::badbit | std::ios_base::failbit), nType(nTypeIn), nVersion(nVersionIn) { }
164
165 bool CBufferedFile::good() const
166 {
167     return state == 0;
168 }
169
170 bool CBufferedFile::eof() const
171 {
172     return nReadPos == nSrcPos && feof(src);
173 }
174
175 CBufferedFile& CBufferedFile::read(char *pch, size_t nSize)
176 {
177     if (nSize + nReadPos > nReadLimit)
178         throw std::ios_base::failure("Read attempted past buffer limit");
179     if (nSize + nRewind > vchBuf.size())
180         throw std::ios_base::failure("Read larger than buffer size");
181     while (nSize > 0) {
182         if (nReadPos == nSrcPos)
183             Fill();
184         auto pos = (uint32_t)(nReadPos % vchBuf.size());
185         auto nNow = nSize;
186         if (nNow + pos > vchBuf.size())
187             nNow = vchBuf.size() - pos;
188         if (nNow + nReadPos > nSrcPos)
189             nNow = (size_t)(nSrcPos - nReadPos);
190         memcpy(pch, &vchBuf[pos], nNow);
191         nReadPos += nNow;
192         pch += nNow;
193         nSize -= nNow;
194     }
195     return (*this);
196 }
197
198 uint64_t CBufferedFile::GetPos()
199 {
200     return nReadPos;
201 }
202
203 bool CBufferedFile::SetPos(uint64_t nPos)
204 {
205     nReadPos = nPos;
206     if (nReadPos + nRewind < nSrcPos) {
207         nReadPos = nSrcPos - nRewind;
208         return false;
209     } else if (nReadPos > nSrcPos) {
210         nReadPos = nSrcPos;
211         return false;
212     } else {
213         return true;
214     }
215 }
216
217 bool CBufferedFile::Seek(uint64_t nPos)
218 {
219     long nLongPos = (long)nPos;
220     if (nPos != (uint64_t)nLongPos)
221         return false;
222     if (fseek(src, nLongPos, SEEK_SET))
223         return false;
224     nLongPos = ftell(src);
225     nSrcPos = nLongPos;
226     nReadPos = nLongPos;
227     state = 0;
228     return true;
229 }
230
231 bool CBufferedFile::SetLimit(uint64_t nPos)
232 {
233     if (nPos < nReadPos)
234         return false;
235     nReadLimit = nPos;
236     return true;
237 }
238
239 void CBufferedFile::FindByte(char ch)
240 {
241     for ( ; ; ) {
242         if (nReadPos == nSrcPos)
243             Fill();
244         if (vchBuf[nReadPos % vchBuf.size()] == ch)
245             break;
246         nReadPos++;
247     }
248 }