aboutsummaryrefslogtreecommitdiff
path: root/src/main.h
diff options
context:
space:
mode:
authorPieter Wuille <pieter.wuille@gmail.com>2012-12-30 23:41:41 +0100
committerPieter Wuille <pieter.wuille@gmail.com>2013-01-03 15:29:19 +0100
commit8539361e66eace839060f77f39b770d045e7ce28 (patch)
treec66def3d40aeb33fbb945c1dc28a9eafd11f5005 /src/main.h
parent2cbd71da06a14ffe823440973f8a87032bbe0b1e (diff)
Add checksums to undo data
This should be compatible with older code that didn't write checksums.
Diffstat (limited to 'src/main.h')
-rw-r--r--src/main.h46
1 files changed, 45 insertions, 1 deletions
diff --git a/src/main.h b/src/main.h
index 80fd76452b..557df8bc5f 100644
--- a/src/main.h
+++ b/src/main.h
@@ -746,7 +746,7 @@ public:
READWRITE(vtxundo);
)
- bool WriteToDisk(CDiskBlockPos &pos)
+ bool WriteToDisk(CDiskBlockPos &pos, const uint256 &hashBlock)
{
// Open history file to append
CAutoFile fileout = CAutoFile(OpenUndoFile(pos), SER_DISK, CLIENT_VERSION);
@@ -764,6 +764,12 @@ public:
pos.nPos = (unsigned int)fileOutPos;
fileout << *this;
+ // calculate & write checksum
+ CHashWriter hasher(SER_GETHASH, PROTOCOL_VERSION);
+ hasher << hashBlock;
+ hasher << *this;
+ fileout << hasher.GetHash();
+
// Flush stdio buffers and commit to disk before returning
fflush(fileout);
if (!IsInitialBlockDownload())
@@ -771,6 +777,44 @@ public:
return true;
}
+
+ bool ReadFromDisk(const CDiskBlockPos &pos, const uint256 &hashBlock)
+ {
+ // Open history file to read
+ CAutoFile filein = CAutoFile(OpenUndoFile(pos, true), SER_DISK, CLIENT_VERSION);
+ if (!filein)
+ return error("CBlockUndo::ReadFromDisk() : OpenBlockFile failed");
+
+ // Read block
+ uint256 hashChecksum;
+ try {
+ filein >> *this;
+ }
+ catch (std::exception &e) {
+ return error("%s() : deserialize or I/O error", __PRETTY_FUNCTION__);
+ }
+
+ // for compatibility with pre-release code that didn't write checksums to undo data
+ // TODO: replace by a simply 'filein >> hashChecksum' in the above try block
+ try {
+ filein >> hashChecksum;
+ } catch (std::exception &e) {
+ hashChecksum = 0;
+ }
+ uint32_t hashInit = hashChecksum.Get64(0) & 0xFFFFFFFFUL;
+ if (hashChecksum == 0 || memcmp(&hashInit, pchMessageStart, 4) == 0)
+ return true;
+
+ // Verify checksum
+ CHashWriter hasher(SER_GETHASH, PROTOCOL_VERSION);
+ hasher << hashBlock;
+ hasher << *this;
+ if (hashChecksum != hasher.GetHash())
+ return error("CBlockUndo::ReadFromDisk() : checksum mismatch");
+
+ return true;
+ }
+
};
/** pruned version of CTransaction: only retains metadata and unspent transaction outputs