aboutsummaryrefslogtreecommitdiff
path: root/src/main.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/main.cpp')
-rw-r--r--src/main.cpp102
1 files changed, 97 insertions, 5 deletions
diff --git a/src/main.cpp b/src/main.cpp
index b5d8f8f27..b337993cc 100644
--- a/src/main.cpp
+++ b/src/main.cpp
@@ -740,7 +740,31 @@ int CTxIndex::GetDepthInMainChain() const
return 1 + nBestHeight - pindex->nHeight;
}
-
+// Return transaction in tx, and if it was found inside a block, its hash is placed in hashBlock
+bool GetTransaction(const uint256 &hash, CTransaction &tx, uint256 &hashBlock)
+{
+ {
+ LOCK(cs_main);
+ {
+ LOCK(mempool.cs);
+ if (mempool.exists(hash))
+ {
+ tx = mempool.lookup(hash);
+ return true;
+ }
+ }
+ CTxDB txdb("r");
+ CTxIndex txindex;
+ if (tx.ReadFromDisk(txdb, COutPoint(hash, 0), txindex))
+ {
+ CBlock block;
+ if (block.ReadFromDisk(txindex.pos.nFile, txindex.pos.nBlockPos, false))
+ hashBlock = block.GetHash();
+ return true;
+ }
+ }
+ return false;
+}
@@ -1836,7 +1860,7 @@ bool CheckDiskSpace(uint64 nAdditionalBytes)
FILE* OpenBlockFile(unsigned int nFile, unsigned int nBlockPos, const char* pszMode)
{
- if (nFile == -1)
+ if ((nFile < 1) || (nFile == (unsigned int) -1))
return NULL;
FILE* file = fopen((GetDataDir() / strprintf("blk%04d.dat", nFile)).string().c_str(), pszMode);
if (!file)
@@ -2028,6 +2052,62 @@ void PrintBlockTree()
}
}
+bool LoadExternalBlockFile(FILE* fileIn)
+{
+ int nLoaded = 0;
+ {
+ LOCK(cs_main);
+ try {
+ CAutoFile blkdat(fileIn, SER_DISK, CLIENT_VERSION);
+ unsigned int nPos = 0;
+ while (nPos != -1 && blkdat.good() && !fRequestShutdown)
+ {
+ unsigned char pchData[65536];
+ do {
+ fseek(blkdat, nPos, SEEK_SET);
+ int nRead = fread(pchData, 1, sizeof(pchData), blkdat);
+ if (nRead <= 8)
+ {
+ nPos = -1;
+ break;
+ }
+ void* nFind = memchr(pchData, pchMessageStart[0], nRead+1-sizeof(pchMessageStart));
+ if (nFind)
+ {
+ if (memcmp(nFind, pchMessageStart, sizeof(pchMessageStart))==0)
+ {
+ nPos += ((unsigned char*)nFind - pchData) + sizeof(pchMessageStart);
+ break;
+ }
+ nPos += ((unsigned char*)nFind - pchData) + 1;
+ }
+ else
+ nPos += sizeof(pchData) - sizeof(pchMessageStart) + 1;
+ } while(!fRequestShutdown);
+ if (nPos == -1)
+ break;
+ fseek(blkdat, nPos, SEEK_SET);
+ unsigned int nSize;
+ blkdat >> nSize;
+ if (nSize > 0 && nSize <= MAX_BLOCK_SIZE)
+ {
+ CBlock block;
+ blkdat >> block;
+ if (ProcessBlock(NULL,&block))
+ {
+ nLoaded++;
+ nPos += 4 + nSize;
+ }
+ }
+ }
+ }
+ catch (std::exception &e)
+ {
+ }
+ }
+ printf("Loaded %i blocks from external file\n", nLoaded);
+ return nLoaded > 0;
+}
@@ -2398,6 +2478,12 @@ bool static ProcessMessage(CNode* pfrom, string strCommand, CDataStream& vRecv)
return error("message inv size() = %d", vInv.size());
}
+ // find last block in inv vector
+ unsigned int nLastBlock = (unsigned int)(-1);
+ for (unsigned int nInv = 0; nInv < vInv.size(); nInv++) {
+ if (vInv[vInv.size() - 1 - nInv].type == MSG_BLOCK)
+ nLastBlock = vInv.size() - 1 - nInv;
+ }
CTxDB txdb("r");
for (unsigned int nInv = 0; nInv < vInv.size(); nInv++)
{
@@ -2414,9 +2500,15 @@ bool static ProcessMessage(CNode* pfrom, string strCommand, CDataStream& vRecv)
// Always request the last block in an inv bundle (even if we already have it), as it is the
// trigger for the other side to send further invs. If we are stuck on a (very long) side chain,
// this is necessary to connect earlier received orphan blocks to the chain again.
- if (!fAlreadyHave || (inv.type == MSG_BLOCK && nInv==vInv.size()-1))
+ if (fAlreadyHave && nInv == nLastBlock) {
+ // bypass mapAskFor, and send request directly; it must go through.
+ std::vector<CInv> vGetData(1,inv);
+ pfrom->PushMessage("getdata", vGetData);
+ }
+
+ if (!fAlreadyHave)
pfrom->AskFor(inv);
- if (inv.type == MSG_BLOCK && mapOrphanBlocks.count(inv.hash))
+ else if (inv.type == MSG_BLOCK && mapOrphanBlocks.count(inv.hash))
pfrom->PushGetBlocks(pindexBest, GetOrphanRoot(mapOrphanBlocks[inv.hash]));
// Track requests for our stuff
@@ -3195,7 +3287,7 @@ CBlock* CreateNewBlock(CReserveKey& reservekey)
dPriority += (double)nValueIn * nConf;
if (fDebug && GetBoolArg("-printpriority"))
- printf("priority nValueIn=%-12I64d nConf=%-5d dPriority=%-20.1f\n", nValueIn, nConf, dPriority);
+ printf("priority nValueIn=%-12"PRI64d" nConf=%-5d dPriority=%-20.1f\n", nValueIn, nConf, dPriority);
}
// Priority is sum(valuein * age) / txsize