]>
Commit | Line | Data |
---|---|---|
d247a5d1 | 1 | // Copyright (c) 2009-2010 Satoshi Nakamoto |
db0e8ccd | 2 | // Copyright (c) 2009-2013 The Bitcoin developers |
d247a5d1 JG |
3 | // Distributed under the MIT/X11 software license, see the accompanying |
4 | // file COPYING or http://www.opensource.org/licenses/mit-license.php. | |
5 | ||
d247a5d1 | 6 | #include "miner.h" |
51ed9ec9 BD |
7 | |
8 | #include "core.h" | |
d247a5d1 | 9 | #include "main.h" |
51ed9ec9 BD |
10 | #include "net.h" |
11 | #include "wallet.h" | |
12 | ||
4a85e067 WL |
13 | #ifdef ENABLE_WALLET |
14 | // These globals are only used by the built-in miner | |
8d750f1d | 15 | double dHashesPerSec = 0.0; |
51ed9ec9 | 16 | int64_t nHPSTimerStart = 0; |
4a85e067 | 17 | #endif |
d247a5d1 JG |
18 | |
19 | ////////////////////////////////////////////////////////////////////////////// | |
20 | // | |
21 | // BitcoinMiner | |
22 | // | |
23 | ||
24 | int static FormatHashBlocks(void* pbuffer, unsigned int len) | |
25 | { | |
26 | unsigned char* pdata = (unsigned char*)pbuffer; | |
27 | unsigned int blocks = 1 + ((len + 8) / 64); | |
28 | unsigned char* pend = pdata + 64 * blocks; | |
29 | memset(pdata + len, 0, 64 * blocks - len); | |
30 | pdata[len] = 0x80; | |
31 | unsigned int bits = len * 8; | |
32 | pend[-1] = (bits >> 0) & 0xff; | |
33 | pend[-2] = (bits >> 8) & 0xff; | |
34 | pend[-3] = (bits >> 16) & 0xff; | |
35 | pend[-4] = (bits >> 24) & 0xff; | |
36 | return blocks; | |
37 | } | |
38 | ||
39 | static const unsigned int pSHA256InitState[8] = | |
40 | {0x6a09e667, 0xbb67ae85, 0x3c6ef372, 0xa54ff53a, 0x510e527f, 0x9b05688c, 0x1f83d9ab, 0x5be0cd19}; | |
41 | ||
42 | void SHA256Transform(void* pstate, void* pinput, const void* pinit) | |
43 | { | |
44 | SHA256_CTX ctx; | |
45 | unsigned char data[64]; | |
46 | ||
47 | SHA256_Init(&ctx); | |
48 | ||
49 | for (int i = 0; i < 16; i++) | |
50 | ((uint32_t*)data)[i] = ByteReverse(((uint32_t*)pinput)[i]); | |
51 | ||
52 | for (int i = 0; i < 8; i++) | |
53 | ctx.h[i] = ((uint32_t*)pinit)[i]; | |
54 | ||
55 | SHA256_Update(&ctx, data, sizeof(data)); | |
56 | for (int i = 0; i < 8; i++) | |
57 | ((uint32_t*)pstate)[i] = ctx.h[i]; | |
58 | } | |
59 | ||
60 | // | |
61 | // ScanHash scans nonces looking for a hash with at least some zero bits. | |
62 | // It operates on big endian data. Caller does the byte reversing. | |
63 | // All input buffers are 16-byte aligned. nNonce is usually preserved | |
64 | // between calls, but periodically or if nNonce is 0xffff0000 or above, | |
65 | // the block is rebuilt and nNonce starts over at zero. | |
66 | // | |
67 | unsigned int static ScanHash_CryptoPP(char* pmidstate, char* pdata, char* phash1, char* phash, unsigned int& nHashesDone) | |
68 | { | |
69 | unsigned int& nNonce = *(unsigned int*)(pdata + 12); | |
70 | for (;;) | |
71 | { | |
72 | // Crypto++ SHA256 | |
73 | // Hash pdata using pmidstate as the starting state into | |
74 | // pre-formatted buffer phash1, then hash phash1 into phash | |
75 | nNonce++; | |
76 | SHA256Transform(phash1, pdata, pmidstate); | |
77 | SHA256Transform(phash, phash1, pSHA256InitState); | |
78 | ||
79 | // Return the nonce if the hash has at least some zero bits, | |
80 | // caller will check if it has enough to reach the target | |
81 | if (((unsigned short*)phash)[14] == 0) | |
82 | return nNonce; | |
83 | ||
84 | // If nothing found after trying for a while, return -1 | |
85 | if ((nNonce & 0xffff) == 0) | |
86 | { | |
87 | nHashesDone = 0xffff+1; | |
88 | return (unsigned int) -1; | |
89 | } | |
90 | if ((nNonce & 0xfff) == 0) | |
91 | boost::this_thread::interruption_point(); | |
92 | } | |
93 | } | |
94 | ||
95 | // Some explaining would be appreciated | |
96 | class COrphan | |
97 | { | |
98 | public: | |
4d707d51 | 99 | const CTransaction* ptx; |
d247a5d1 JG |
100 | set<uint256> setDependsOn; |
101 | double dPriority; | |
102 | double dFeePerKb; | |
103 | ||
4d707d51 | 104 | COrphan(const CTransaction* ptxIn) |
d247a5d1 JG |
105 | { |
106 | ptx = ptxIn; | |
107 | dPriority = dFeePerKb = 0; | |
108 | } | |
109 | ||
110 | void print() const | |
111 | { | |
881a85a2 | 112 | LogPrintf("COrphan(hash=%s, dPriority=%.1f, dFeePerKb=%.1f)\n", |
d247a5d1 JG |
113 | ptx->GetHash().ToString().c_str(), dPriority, dFeePerKb); |
114 | BOOST_FOREACH(uint256 hash, setDependsOn) | |
881a85a2 | 115 | LogPrintf(" setDependsOn %s\n", hash.ToString().c_str()); |
d247a5d1 JG |
116 | } |
117 | }; | |
118 | ||
119 | ||
51ed9ec9 BD |
120 | uint64_t nLastBlockTx = 0; |
121 | uint64_t nLastBlockSize = 0; | |
d247a5d1 JG |
122 | |
123 | // We want to sort transactions by priority and fee, so: | |
4d707d51 | 124 | typedef boost::tuple<double, double, const CTransaction*> TxPriority; |
d247a5d1 JG |
125 | class TxPriorityCompare |
126 | { | |
127 | bool byFee; | |
128 | public: | |
129 | TxPriorityCompare(bool _byFee) : byFee(_byFee) { } | |
130 | bool operator()(const TxPriority& a, const TxPriority& b) | |
131 | { | |
132 | if (byFee) | |
133 | { | |
134 | if (a.get<1>() == b.get<1>()) | |
135 | return a.get<0>() < b.get<0>(); | |
136 | return a.get<1>() < b.get<1>(); | |
137 | } | |
138 | else | |
139 | { | |
140 | if (a.get<0>() == b.get<0>()) | |
141 | return a.get<1>() < b.get<1>(); | |
142 | return a.get<0>() < b.get<0>(); | |
143 | } | |
144 | } | |
145 | }; | |
146 | ||
f1dbed92 | 147 | CBlockTemplate* CreateNewBlock(const CScript& scriptPubKeyIn) |
d247a5d1 JG |
148 | { |
149 | // Create new block | |
150 | auto_ptr<CBlockTemplate> pblocktemplate(new CBlockTemplate()); | |
151 | if(!pblocktemplate.get()) | |
152 | return NULL; | |
153 | CBlock *pblock = &pblocktemplate->block; // pointer for convenience | |
154 | ||
155 | // Create coinbase tx | |
156 | CTransaction txNew; | |
157 | txNew.vin.resize(1); | |
158 | txNew.vin[0].prevout.SetNull(); | |
159 | txNew.vout.resize(1); | |
7e170189 | 160 | txNew.vout[0].scriptPubKey = scriptPubKeyIn; |
d247a5d1 JG |
161 | |
162 | // Add our coinbase tx as first transaction | |
163 | pblock->vtx.push_back(txNew); | |
164 | pblocktemplate->vTxFees.push_back(-1); // updated at end | |
165 | pblocktemplate->vTxSigOps.push_back(-1); // updated at end | |
166 | ||
167 | // Largest block you're willing to create: | |
168 | unsigned int nBlockMaxSize = GetArg("-blockmaxsize", MAX_BLOCK_SIZE_GEN/2); | |
169 | // Limit to betweeen 1K and MAX_BLOCK_SIZE-1K for sanity: | |
170 | nBlockMaxSize = std::max((unsigned int)1000, std::min((unsigned int)(MAX_BLOCK_SIZE-1000), nBlockMaxSize)); | |
171 | ||
172 | // How much of the block should be dedicated to high-priority transactions, | |
173 | // included regardless of the fees they pay | |
174 | unsigned int nBlockPrioritySize = GetArg("-blockprioritysize", DEFAULT_BLOCK_PRIORITY_SIZE); | |
175 | nBlockPrioritySize = std::min(nBlockMaxSize, nBlockPrioritySize); | |
176 | ||
177 | // Minimum block size you want to create; block will be filled with free transactions | |
178 | // until there are no more or the block reaches this size: | |
179 | unsigned int nBlockMinSize = GetArg("-blockminsize", 0); | |
180 | nBlockMinSize = std::min(nBlockMaxSize, nBlockMinSize); | |
181 | ||
182 | // Collect memory pool transactions into the block | |
51ed9ec9 | 183 | int64_t nFees = 0; |
d247a5d1 JG |
184 | { |
185 | LOCK2(cs_main, mempool.cs); | |
4c6d41b8 | 186 | CBlockIndex* pindexPrev = chainActive.Tip(); |
d247a5d1 JG |
187 | CCoinsViewCache view(*pcoinsTip, true); |
188 | ||
189 | // Priority order to process transactions | |
190 | list<COrphan> vOrphan; // list memory doesn't move | |
191 | map<uint256, vector<COrphan*> > mapDependers; | |
192 | bool fPrintPriority = GetBoolArg("-printpriority", false); | |
193 | ||
194 | // This vector will be sorted into a priority queue: | |
195 | vector<TxPriority> vecPriority; | |
196 | vecPriority.reserve(mempool.mapTx.size()); | |
4d707d51 GA |
197 | for (map<uint256, CTxMemPoolEntry>::iterator mi = mempool.mapTx.begin(); |
198 | mi != mempool.mapTx.end(); ++mi) | |
d247a5d1 | 199 | { |
4d707d51 | 200 | const CTransaction& tx = mi->second.GetTx(); |
d247a5d1 JG |
201 | if (tx.IsCoinBase() || !IsFinalTx(tx)) |
202 | continue; | |
203 | ||
204 | COrphan* porphan = NULL; | |
205 | double dPriority = 0; | |
51ed9ec9 | 206 | int64_t nTotalIn = 0; |
d247a5d1 JG |
207 | bool fMissingInputs = false; |
208 | BOOST_FOREACH(const CTxIn& txin, tx.vin) | |
209 | { | |
210 | // Read prev transaction | |
211 | if (!view.HaveCoins(txin.prevout.hash)) | |
212 | { | |
213 | // This should never happen; all transactions in the memory | |
214 | // pool should connect to either transactions in the chain | |
215 | // or other transactions in the memory pool. | |
216 | if (!mempool.mapTx.count(txin.prevout.hash)) | |
217 | { | |
881a85a2 | 218 | LogPrintf("ERROR: mempool transaction missing input\n"); |
d247a5d1 JG |
219 | if (fDebug) assert("mempool transaction missing input" == 0); |
220 | fMissingInputs = true; | |
221 | if (porphan) | |
222 | vOrphan.pop_back(); | |
223 | break; | |
224 | } | |
225 | ||
226 | // Has to wait for dependencies | |
227 | if (!porphan) | |
228 | { | |
229 | // Use list for automatic deletion | |
230 | vOrphan.push_back(COrphan(&tx)); | |
231 | porphan = &vOrphan.back(); | |
232 | } | |
233 | mapDependers[txin.prevout.hash].push_back(porphan); | |
234 | porphan->setDependsOn.insert(txin.prevout.hash); | |
4d707d51 | 235 | nTotalIn += mempool.mapTx[txin.prevout.hash].GetTx().vout[txin.prevout.n].nValue; |
d247a5d1 JG |
236 | continue; |
237 | } | |
238 | const CCoins &coins = view.GetCoins(txin.prevout.hash); | |
239 | ||
51ed9ec9 | 240 | int64_t nValueIn = coins.vout[txin.prevout.n].nValue; |
d247a5d1 JG |
241 | nTotalIn += nValueIn; |
242 | ||
243 | int nConf = pindexPrev->nHeight - coins.nHeight + 1; | |
244 | ||
245 | dPriority += (double)nValueIn * nConf; | |
246 | } | |
247 | if (fMissingInputs) continue; | |
248 | ||
d6eb2599 | 249 | // Priority is sum(valuein * age) / modified_txsize |
d247a5d1 | 250 | unsigned int nTxSize = ::GetSerializeSize(tx, SER_NETWORK, PROTOCOL_VERSION); |
4d707d51 | 251 | dPriority = tx.ComputePriority(dPriority, nTxSize); |
d247a5d1 JG |
252 | |
253 | // This is a more accurate fee-per-kilobyte than is used by the client code, because the | |
254 | // client code rounds up the size to the nearest 1K. That's good, because it gives an | |
255 | // incentive to create smaller transactions. | |
0733c1bd | 256 | double dFeePerKb = double(nTotalIn-tx.GetValueOut()) / (double(nTxSize)/1000.0); |
d247a5d1 JG |
257 | |
258 | if (porphan) | |
259 | { | |
260 | porphan->dPriority = dPriority; | |
261 | porphan->dFeePerKb = dFeePerKb; | |
262 | } | |
263 | else | |
4d707d51 | 264 | vecPriority.push_back(TxPriority(dPriority, dFeePerKb, &mi->second.GetTx())); |
d247a5d1 JG |
265 | } |
266 | ||
267 | // Collect transactions into block | |
51ed9ec9 BD |
268 | uint64_t nBlockSize = 1000; |
269 | uint64_t nBlockTx = 0; | |
d247a5d1 JG |
270 | int nBlockSigOps = 100; |
271 | bool fSortedByFee = (nBlockPrioritySize <= 0); | |
272 | ||
273 | TxPriorityCompare comparer(fSortedByFee); | |
274 | std::make_heap(vecPriority.begin(), vecPriority.end(), comparer); | |
275 | ||
276 | while (!vecPriority.empty()) | |
277 | { | |
278 | // Take highest priority transaction off the priority queue: | |
279 | double dPriority = vecPriority.front().get<0>(); | |
280 | double dFeePerKb = vecPriority.front().get<1>(); | |
4d707d51 | 281 | const CTransaction& tx = *(vecPriority.front().get<2>()); |
d247a5d1 JG |
282 | |
283 | std::pop_heap(vecPriority.begin(), vecPriority.end(), comparer); | |
284 | vecPriority.pop_back(); | |
285 | ||
286 | // Size limits | |
287 | unsigned int nTxSize = ::GetSerializeSize(tx, SER_NETWORK, PROTOCOL_VERSION); | |
288 | if (nBlockSize + nTxSize >= nBlockMaxSize) | |
289 | continue; | |
290 | ||
291 | // Legacy limits on sigOps: | |
292 | unsigned int nTxSigOps = GetLegacySigOpCount(tx); | |
293 | if (nBlockSigOps + nTxSigOps >= MAX_BLOCK_SIGOPS) | |
294 | continue; | |
295 | ||
296 | // Skip free transactions if we're past the minimum block size: | |
297 | if (fSortedByFee && (dFeePerKb < CTransaction::nMinTxFee) && (nBlockSize + nTxSize >= nBlockMinSize)) | |
298 | continue; | |
299 | ||
300 | // Prioritize by fee once past the priority size or we run out of high-priority | |
301 | // transactions: | |
302 | if (!fSortedByFee && | |
303 | ((nBlockSize + nTxSize >= nBlockPrioritySize) || !AllowFree(dPriority))) | |
304 | { | |
305 | fSortedByFee = true; | |
306 | comparer = TxPriorityCompare(fSortedByFee); | |
307 | std::make_heap(vecPriority.begin(), vecPriority.end(), comparer); | |
308 | } | |
309 | ||
310 | if (!view.HaveInputs(tx)) | |
311 | continue; | |
312 | ||
0733c1bd | 313 | int64_t nTxFees = view.GetValueIn(tx)-tx.GetValueOut(); |
d247a5d1 JG |
314 | |
315 | nTxSigOps += GetP2SHSigOpCount(tx, view); | |
316 | if (nBlockSigOps + nTxSigOps >= MAX_BLOCK_SIGOPS) | |
317 | continue; | |
318 | ||
319 | CValidationState state; | |
320 | if (!CheckInputs(tx, state, view, true, SCRIPT_VERIFY_P2SH)) | |
321 | continue; | |
322 | ||
323 | CTxUndo txundo; | |
324 | uint256 hash = tx.GetHash(); | |
325 | UpdateCoins(tx, state, view, txundo, pindexPrev->nHeight+1, hash); | |
326 | ||
327 | // Added | |
328 | pblock->vtx.push_back(tx); | |
329 | pblocktemplate->vTxFees.push_back(nTxFees); | |
330 | pblocktemplate->vTxSigOps.push_back(nTxSigOps); | |
331 | nBlockSize += nTxSize; | |
332 | ++nBlockTx; | |
333 | nBlockSigOps += nTxSigOps; | |
334 | nFees += nTxFees; | |
335 | ||
336 | if (fPrintPriority) | |
337 | { | |
881a85a2 | 338 | LogPrintf("priority %.1f feeperkb %.1f txid %s\n", |
d247a5d1 JG |
339 | dPriority, dFeePerKb, tx.GetHash().ToString().c_str()); |
340 | } | |
341 | ||
342 | // Add transactions that depend on this one to the priority queue | |
343 | if (mapDependers.count(hash)) | |
344 | { | |
345 | BOOST_FOREACH(COrphan* porphan, mapDependers[hash]) | |
346 | { | |
347 | if (!porphan->setDependsOn.empty()) | |
348 | { | |
349 | porphan->setDependsOn.erase(hash); | |
350 | if (porphan->setDependsOn.empty()) | |
351 | { | |
352 | vecPriority.push_back(TxPriority(porphan->dPriority, porphan->dFeePerKb, porphan->ptx)); | |
353 | std::push_heap(vecPriority.begin(), vecPriority.end(), comparer); | |
354 | } | |
355 | } | |
356 | } | |
357 | } | |
358 | } | |
359 | ||
360 | nLastBlockTx = nBlockTx; | |
361 | nLastBlockSize = nBlockSize; | |
51ed9ec9 | 362 | LogPrintf("CreateNewBlock(): total size %"PRIu64"\n", nBlockSize); |
d247a5d1 JG |
363 | |
364 | pblock->vtx[0].vout[0].nValue = GetBlockValue(pindexPrev->nHeight+1, nFees); | |
365 | pblocktemplate->vTxFees[0] = -nFees; | |
366 | ||
367 | // Fill in header | |
368 | pblock->hashPrevBlock = pindexPrev->GetBlockHash(); | |
369 | UpdateTime(*pblock, pindexPrev); | |
370 | pblock->nBits = GetNextWorkRequired(pindexPrev, pblock); | |
371 | pblock->nNonce = 0; | |
372 | pblock->vtx[0].vin[0].scriptSig = CScript() << OP_0 << OP_0; | |
373 | pblocktemplate->vTxSigOps[0] = GetLegacySigOpCount(pblock->vtx[0]); | |
374 | ||
375 | CBlockIndex indexDummy(*pblock); | |
376 | indexDummy.pprev = pindexPrev; | |
377 | indexDummy.nHeight = pindexPrev->nHeight + 1; | |
378 | CCoinsViewCache viewNew(*pcoinsTip, true); | |
379 | CValidationState state; | |
380 | if (!ConnectBlock(*pblock, state, &indexDummy, viewNew, true)) | |
381 | throw std::runtime_error("CreateNewBlock() : ConnectBlock failed"); | |
382 | } | |
383 | ||
384 | return pblocktemplate.release(); | |
385 | } | |
386 | ||
4a85e067 | 387 | #ifdef ENABLE_WALLET |
7e170189 JG |
388 | CBlockTemplate* CreateNewBlockWithKey(CReserveKey& reservekey) |
389 | { | |
390 | CPubKey pubkey; | |
391 | if (!reservekey.GetReservedKey(pubkey)) | |
392 | return NULL; | |
393 | ||
394 | CScript scriptPubKey = CScript() << pubkey << OP_CHECKSIG; | |
395 | return CreateNewBlock(scriptPubKey); | |
396 | } | |
4a85e067 | 397 | #endif |
d247a5d1 JG |
398 | |
399 | void IncrementExtraNonce(CBlock* pblock, CBlockIndex* pindexPrev, unsigned int& nExtraNonce) | |
400 | { | |
401 | // Update nExtraNonce | |
402 | static uint256 hashPrevBlock; | |
403 | if (hashPrevBlock != pblock->hashPrevBlock) | |
404 | { | |
405 | nExtraNonce = 0; | |
406 | hashPrevBlock = pblock->hashPrevBlock; | |
407 | } | |
408 | ++nExtraNonce; | |
409 | unsigned int nHeight = pindexPrev->nHeight+1; // Height first in coinbase required for block.version=2 | |
410 | pblock->vtx[0].vin[0].scriptSig = (CScript() << nHeight << CBigNum(nExtraNonce)) + COINBASE_FLAGS; | |
411 | assert(pblock->vtx[0].vin[0].scriptSig.size() <= 100); | |
412 | ||
413 | pblock->hashMerkleRoot = pblock->BuildMerkleTree(); | |
414 | } | |
415 | ||
416 | ||
417 | void FormatHashBuffers(CBlock* pblock, char* pmidstate, char* pdata, char* phash1) | |
418 | { | |
419 | // | |
420 | // Pre-build hash buffers | |
421 | // | |
422 | struct | |
423 | { | |
424 | struct unnamed2 | |
425 | { | |
426 | int nVersion; | |
427 | uint256 hashPrevBlock; | |
428 | uint256 hashMerkleRoot; | |
429 | unsigned int nTime; | |
430 | unsigned int nBits; | |
431 | unsigned int nNonce; | |
432 | } | |
433 | block; | |
434 | unsigned char pchPadding0[64]; | |
435 | uint256 hash1; | |
436 | unsigned char pchPadding1[64]; | |
437 | } | |
438 | tmp; | |
439 | memset(&tmp, 0, sizeof(tmp)); | |
440 | ||
441 | tmp.block.nVersion = pblock->nVersion; | |
442 | tmp.block.hashPrevBlock = pblock->hashPrevBlock; | |
443 | tmp.block.hashMerkleRoot = pblock->hashMerkleRoot; | |
444 | tmp.block.nTime = pblock->nTime; | |
445 | tmp.block.nBits = pblock->nBits; | |
446 | tmp.block.nNonce = pblock->nNonce; | |
447 | ||
448 | FormatHashBlocks(&tmp.block, sizeof(tmp.block)); | |
449 | FormatHashBlocks(&tmp.hash1, sizeof(tmp.hash1)); | |
450 | ||
451 | // Byte swap all the input buffer | |
452 | for (unsigned int i = 0; i < sizeof(tmp)/4; i++) | |
453 | ((unsigned int*)&tmp)[i] = ByteReverse(((unsigned int*)&tmp)[i]); | |
454 | ||
455 | // Precalc the first half of the first hash, which stays constant | |
456 | SHA256Transform(pmidstate, &tmp.block, pSHA256InitState); | |
457 | ||
458 | memcpy(pdata, &tmp.block, 128); | |
459 | memcpy(phash1, &tmp.hash1, 64); | |
460 | } | |
461 | ||
4a85e067 | 462 | #ifdef ENABLE_WALLET |
d247a5d1 JG |
463 | bool CheckWork(CBlock* pblock, CWallet& wallet, CReserveKey& reservekey) |
464 | { | |
465 | uint256 hash = pblock->GetHash(); | |
466 | uint256 hashTarget = CBigNum().SetCompact(pblock->nBits).getuint256(); | |
467 | ||
468 | if (hash > hashTarget) | |
469 | return false; | |
470 | ||
471 | //// debug print | |
881a85a2 GA |
472 | LogPrintf("BitcoinMiner:\n"); |
473 | LogPrintf("proof-of-work found \n hash: %s \ntarget: %s\n", hash.GetHex().c_str(), hashTarget.GetHex().c_str()); | |
d247a5d1 | 474 | pblock->print(); |
881a85a2 | 475 | LogPrintf("generated %s\n", FormatMoney(pblock->vtx[0].vout[0].nValue).c_str()); |
d247a5d1 JG |
476 | |
477 | // Found a solution | |
478 | { | |
479 | LOCK(cs_main); | |
4c6d41b8 | 480 | if (pblock->hashPrevBlock != chainActive.Tip()->GetBlockHash()) |
d247a5d1 JG |
481 | return error("BitcoinMiner : generated block is stale"); |
482 | ||
483 | // Remove key from key pool | |
484 | reservekey.KeepKey(); | |
485 | ||
486 | // Track how many getdata requests this block gets | |
487 | { | |
488 | LOCK(wallet.cs_wallet); | |
489 | wallet.mapRequestCount[pblock->GetHash()] = 0; | |
490 | } | |
491 | ||
492 | // Process this block the same as if we had received it from another node | |
493 | CValidationState state; | |
494 | if (!ProcessBlock(state, NULL, pblock)) | |
495 | return error("BitcoinMiner : ProcessBlock, block not accepted"); | |
496 | } | |
497 | ||
498 | return true; | |
499 | } | |
500 | ||
501 | void static BitcoinMiner(CWallet *pwallet) | |
502 | { | |
881a85a2 | 503 | LogPrintf("BitcoinMiner started\n"); |
d247a5d1 JG |
504 | SetThreadPriority(THREAD_PRIORITY_LOWEST); |
505 | RenameThread("bitcoin-miner"); | |
506 | ||
507 | // Each thread has its own key and counter | |
508 | CReserveKey reservekey(pwallet); | |
509 | unsigned int nExtraNonce = 0; | |
510 | ||
511 | try { while (true) { | |
512 | if (Params().NetworkID() != CChainParams::REGTEST) { | |
513 | // Busy-wait for the network to come online so we don't waste time mining | |
514 | // on an obsolete chain. In regtest mode we expect to fly solo. | |
515 | while (vNodes.empty()) | |
516 | MilliSleep(1000); | |
517 | } | |
518 | ||
519 | // | |
520 | // Create new block | |
521 | // | |
319b1160 | 522 | unsigned int nTransactionsUpdatedLast = mempool.GetTransactionsUpdated(); |
4c6d41b8 | 523 | CBlockIndex* pindexPrev = chainActive.Tip(); |
d247a5d1 | 524 | |
7e170189 | 525 | auto_ptr<CBlockTemplate> pblocktemplate(CreateNewBlockWithKey(reservekey)); |
d247a5d1 JG |
526 | if (!pblocktemplate.get()) |
527 | return; | |
528 | CBlock *pblock = &pblocktemplate->block; | |
529 | IncrementExtraNonce(pblock, pindexPrev, nExtraNonce); | |
530 | ||
881a85a2 | 531 | LogPrintf("Running BitcoinMiner with %"PRIszu" transactions in block (%u bytes)\n", pblock->vtx.size(), |
d247a5d1 JG |
532 | ::GetSerializeSize(*pblock, SER_NETWORK, PROTOCOL_VERSION)); |
533 | ||
534 | // | |
535 | // Pre-build hash buffers | |
536 | // | |
537 | char pmidstatebuf[32+16]; char* pmidstate = alignup<16>(pmidstatebuf); | |
538 | char pdatabuf[128+16]; char* pdata = alignup<16>(pdatabuf); | |
539 | char phash1buf[64+16]; char* phash1 = alignup<16>(phash1buf); | |
540 | ||
541 | FormatHashBuffers(pblock, pmidstate, pdata, phash1); | |
542 | ||
543 | unsigned int& nBlockTime = *(unsigned int*)(pdata + 64 + 4); | |
544 | unsigned int& nBlockBits = *(unsigned int*)(pdata + 64 + 8); | |
545 | unsigned int& nBlockNonce = *(unsigned int*)(pdata + 64 + 12); | |
546 | ||
547 | ||
548 | // | |
549 | // Search | |
550 | // | |
51ed9ec9 | 551 | int64_t nStart = GetTime(); |
d247a5d1 JG |
552 | uint256 hashTarget = CBigNum().SetCompact(pblock->nBits).getuint256(); |
553 | uint256 hashbuf[2]; | |
554 | uint256& hash = *alignup<16>(hashbuf); | |
555 | while (true) | |
556 | { | |
557 | unsigned int nHashesDone = 0; | |
558 | unsigned int nNonceFound; | |
559 | ||
560 | // Crypto++ SHA256 | |
561 | nNonceFound = ScanHash_CryptoPP(pmidstate, pdata + 64, phash1, | |
562 | (char*)&hash, nHashesDone); | |
563 | ||
564 | // Check if something found | |
565 | if (nNonceFound != (unsigned int) -1) | |
566 | { | |
567 | for (unsigned int i = 0; i < sizeof(hash)/4; i++) | |
568 | ((unsigned int*)&hash)[i] = ByteReverse(((unsigned int*)&hash)[i]); | |
569 | ||
570 | if (hash <= hashTarget) | |
571 | { | |
572 | // Found a solution | |
573 | pblock->nNonce = ByteReverse(nNonceFound); | |
574 | assert(hash == pblock->GetHash()); | |
575 | ||
576 | SetThreadPriority(THREAD_PRIORITY_NORMAL); | |
577 | CheckWork(pblock, *pwallet, reservekey); | |
578 | SetThreadPriority(THREAD_PRIORITY_LOWEST); | |
579 | ||
580 | // In regression test mode, stop mining after a block is found. This | |
581 | // allows developers to controllably generate a block on demand. | |
582 | if (Params().NetworkID() == CChainParams::REGTEST) | |
583 | throw boost::thread_interrupted(); | |
584 | ||
585 | break; | |
586 | } | |
587 | } | |
588 | ||
589 | // Meter hashes/sec | |
51ed9ec9 | 590 | static int64_t nHashCounter; |
d247a5d1 JG |
591 | if (nHPSTimerStart == 0) |
592 | { | |
593 | nHPSTimerStart = GetTimeMillis(); | |
594 | nHashCounter = 0; | |
595 | } | |
596 | else | |
597 | nHashCounter += nHashesDone; | |
598 | if (GetTimeMillis() - nHPSTimerStart > 4000) | |
599 | { | |
600 | static CCriticalSection cs; | |
601 | { | |
602 | LOCK(cs); | |
603 | if (GetTimeMillis() - nHPSTimerStart > 4000) | |
604 | { | |
605 | dHashesPerSec = 1000.0 * nHashCounter / (GetTimeMillis() - nHPSTimerStart); | |
606 | nHPSTimerStart = GetTimeMillis(); | |
607 | nHashCounter = 0; | |
51ed9ec9 | 608 | static int64_t nLogTime; |
d247a5d1 JG |
609 | if (GetTime() - nLogTime > 30 * 60) |
610 | { | |
611 | nLogTime = GetTime(); | |
881a85a2 | 612 | LogPrintf("hashmeter %6.0f khash/s\n", dHashesPerSec/1000.0); |
d247a5d1 JG |
613 | } |
614 | } | |
615 | } | |
616 | } | |
617 | ||
618 | // Check for stop or if block needs to be rebuilt | |
619 | boost::this_thread::interruption_point(); | |
620 | if (vNodes.empty() && Params().NetworkID() != CChainParams::REGTEST) | |
621 | break; | |
622 | if (nBlockNonce >= 0xffff0000) | |
623 | break; | |
319b1160 | 624 | if (mempool.GetTransactionsUpdated() != nTransactionsUpdatedLast && GetTime() - nStart > 60) |
d247a5d1 | 625 | break; |
4c6d41b8 | 626 | if (pindexPrev != chainActive.Tip()) |
d247a5d1 JG |
627 | break; |
628 | ||
629 | // Update nTime every few seconds | |
630 | UpdateTime(*pblock, pindexPrev); | |
631 | nBlockTime = ByteReverse(pblock->nTime); | |
632 | if (TestNet()) | |
633 | { | |
634 | // Changing pblock->nTime can change work required on testnet: | |
635 | nBlockBits = ByteReverse(pblock->nBits); | |
636 | hashTarget = CBigNum().SetCompact(pblock->nBits).getuint256(); | |
637 | } | |
638 | } | |
639 | } } | |
640 | catch (boost::thread_interrupted) | |
641 | { | |
881a85a2 | 642 | LogPrintf("BitcoinMiner terminated\n"); |
d247a5d1 JG |
643 | throw; |
644 | } | |
645 | } | |
646 | ||
c8b74258 | 647 | void GenerateBitcoins(bool fGenerate, CWallet* pwallet, int nThreads) |
d247a5d1 JG |
648 | { |
649 | static boost::thread_group* minerThreads = NULL; | |
650 | ||
d247a5d1 JG |
651 | if (nThreads < 0) { |
652 | if (Params().NetworkID() == CChainParams::REGTEST) | |
653 | nThreads = 1; | |
654 | else | |
655 | nThreads = boost::thread::hardware_concurrency(); | |
656 | } | |
657 | ||
658 | if (minerThreads != NULL) | |
659 | { | |
660 | minerThreads->interrupt_all(); | |
661 | delete minerThreads; | |
662 | minerThreads = NULL; | |
663 | } | |
664 | ||
665 | if (nThreads == 0 || !fGenerate) | |
666 | return; | |
667 | ||
668 | minerThreads = new boost::thread_group(); | |
669 | for (int i = 0; i < nThreads; i++) | |
670 | minerThreads->create_thread(boost::bind(&BitcoinMiner, pwallet)); | |
671 | } | |
672 | ||
4a85e067 | 673 | #endif |
d247a5d1 | 674 |