Merge remote branch 'refs/remotes/svn/trunk' into svn
This commit is contained in:
commit
5d4b0c9026
6 changed files with 119 additions and 27 deletions
|
@ -63,8 +63,7 @@ nmake -f makefile.vc
|
||||||
|
|
||||||
OpenSSL
|
OpenSSL
|
||||||
-------
|
-------
|
||||||
Bitcoin does not use any encryption. If you want to do a no-everything
|
If you want to exclude unused optional algorithms, a few patches are required.
|
||||||
build of OpenSSL to exclude encryption routines, a few patches are required.
|
|
||||||
(instructions for OpenSSL v0.9.8k)
|
(instructions for OpenSSL v0.9.8k)
|
||||||
|
|
||||||
Edit engines\e_gmp.c and engines\e_capi.c and add this #ifndef around
|
Edit engines\e_gmp.c and engines\e_capi.c and add this #ifndef around
|
||||||
|
@ -88,7 +87,7 @@ Build
|
||||||
cd \openssl
|
cd \openssl
|
||||||
ms\mingw32.bat
|
ms\mingw32.bat
|
||||||
|
|
||||||
If you want to use it with MSVC, generate the .lib file
|
If you're using MSVC, generate the .lib file
|
||||||
lib /machine:i386 /def:ms\libeay32.def /out:out\libeay32.lib
|
lib /machine:i386 /def:ms\libeay32.def /out:out\libeay32.lib
|
||||||
|
|
||||||
|
|
||||||
|
|
3
init.cpp
3
init.cpp
|
@ -173,6 +173,7 @@ bool AppInit2(int argc, char* argv[])
|
||||||
" -proxy=<ip:port> \t " + _("Connect through socks4 proxy\n") +
|
" -proxy=<ip:port> \t " + _("Connect through socks4 proxy\n") +
|
||||||
" -addnode=<ip> \t " + _("Add a node to connect to\n") +
|
" -addnode=<ip> \t " + _("Add a node to connect to\n") +
|
||||||
" -connect=<ip> \t\t " + _("Connect only to the specified node\n") +
|
" -connect=<ip> \t\t " + _("Connect only to the specified node\n") +
|
||||||
|
" -paytxfee=<amt> \t " + _("Fee per KB to add to transactions you send\n") +
|
||||||
" -server \t\t " + _("Accept command line and JSON-RPC commands\n") +
|
" -server \t\t " + _("Accept command line and JSON-RPC commands\n") +
|
||||||
" -daemon \t\t " + _("Run in the background as a daemon and accept commands\n") +
|
" -daemon \t\t " + _("Run in the background as a daemon and accept commands\n") +
|
||||||
" -testnet \t\t " + _("Use the test network\n") +
|
" -testnet \t\t " + _("Use the test network\n") +
|
||||||
|
@ -413,7 +414,7 @@ bool AppInit2(int argc, char* argv[])
|
||||||
wxMessageBox(_("Invalid amount for -paytxfee=<amount>"), "Bitcoin");
|
wxMessageBox(_("Invalid amount for -paytxfee=<amount>"), "Bitcoin");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if (nTransactionFee > 1 * COIN)
|
if (nTransactionFee > 0.25 * COIN)
|
||||||
wxMessageBox(_("Warning: -paytxfee is set very high. This is the transaction fee you will pay if you send a transaction."), "Bitcoin", wxOK | wxICON_EXCLAMATION);
|
wxMessageBox(_("Warning: -paytxfee is set very high. This is the transaction fee you will pay if you send a transaction."), "Bitcoin", wxOK | wxICON_EXCLAMATION);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
119
main.cpp
119
main.cpp
|
@ -277,6 +277,34 @@ void EraseOrphanTx(uint256 hash)
|
||||||
// CTransaction
|
// CTransaction
|
||||||
//
|
//
|
||||||
|
|
||||||
|
bool CTransaction::ReadFromDisk(CTxDB& txdb, COutPoint prevout, CTxIndex& txindexRet)
|
||||||
|
{
|
||||||
|
SetNull();
|
||||||
|
if (!txdb.ReadTxIndex(prevout.hash, txindexRet))
|
||||||
|
return false;
|
||||||
|
if (!ReadFromDisk(txindexRet.pos))
|
||||||
|
return false;
|
||||||
|
if (prevout.n >= vout.size())
|
||||||
|
{
|
||||||
|
SetNull();
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool CTransaction::ReadFromDisk(CTxDB& txdb, COutPoint prevout)
|
||||||
|
{
|
||||||
|
CTxIndex txindex;
|
||||||
|
return ReadFromDisk(txdb, prevout, txindex);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool CTransaction::ReadFromDisk(COutPoint prevout)
|
||||||
|
{
|
||||||
|
CTxDB txdb("r");
|
||||||
|
CTxIndex txindex;
|
||||||
|
return ReadFromDisk(txdb, prevout, txindex);
|
||||||
|
}
|
||||||
|
|
||||||
bool CTxIn::IsMine() const
|
bool CTxIn::IsMine() const
|
||||||
{
|
{
|
||||||
CRITICAL_BLOCK(cs_mapWallet)
|
CRITICAL_BLOCK(cs_mapWallet)
|
||||||
|
@ -2882,7 +2910,7 @@ void CallCPUID(int in, int& aret, int& cret)
|
||||||
"mov %2, %%eax; " // in into eax
|
"mov %2, %%eax; " // in into eax
|
||||||
"cpuid;"
|
"cpuid;"
|
||||||
"mov %%eax, %0;" // eax into a
|
"mov %%eax, %0;" // eax into a
|
||||||
"mov %%ecx, %1;" // eax into c
|
"mov %%ecx, %1;" // ecx into c
|
||||||
:"=r"(a),"=r"(c) /* output */
|
:"=r"(a),"=r"(c) /* output */
|
||||||
:"r"(in) /* input */
|
:"r"(in) /* input */
|
||||||
:"%eax","%ecx" /* clobbered register */
|
:"%eax","%ecx" /* clobbered register */
|
||||||
|
@ -3068,42 +3096,97 @@ void BitcoinMiner()
|
||||||
CRITICAL_BLOCK(cs_mapTransactions)
|
CRITICAL_BLOCK(cs_mapTransactions)
|
||||||
{
|
{
|
||||||
CTxDB txdb("r");
|
CTxDB txdb("r");
|
||||||
|
|
||||||
|
// Priority order to process transactions
|
||||||
|
multimap<double, CTransaction*> mapPriority;
|
||||||
|
for (map<uint256, CTransaction>::iterator mi = mapTransactions.begin(); mi != mapTransactions.end(); ++mi)
|
||||||
|
{
|
||||||
|
CTransaction& tx = (*mi).second;
|
||||||
|
if (tx.IsCoinBase() || !tx.IsFinal())
|
||||||
|
continue;
|
||||||
|
|
||||||
|
double dPriority = 0;
|
||||||
|
foreach(const CTxIn& txin, tx.vin)
|
||||||
|
{
|
||||||
|
// Read prev transaction
|
||||||
|
CTransaction txPrev;
|
||||||
|
CTxIndex txindex;
|
||||||
|
if (!txPrev.ReadFromDisk(txdb, txin.prevout, txindex))
|
||||||
|
continue;
|
||||||
|
int64 nValueIn = txPrev.vout[txin.prevout.n].nValue;
|
||||||
|
|
||||||
|
// Read block header
|
||||||
|
int nConf = 0;
|
||||||
|
CBlock block;
|
||||||
|
if (block.ReadFromDisk(txindex.pos.nFile, txindex.pos.nBlockPos, false))
|
||||||
|
{
|
||||||
|
map<uint256, CBlockIndex*>::iterator it = mapBlockIndex.find(block.GetHash());
|
||||||
|
if (it != mapBlockIndex.end())
|
||||||
|
{
|
||||||
|
CBlockIndex* pindex = (*it).second;
|
||||||
|
if (pindex->IsInMainChain())
|
||||||
|
nConf = 1 + nBestHeight - pindex->nHeight;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
dPriority += (double)nValueIn * nConf;
|
||||||
|
|
||||||
|
if (fDebug && mapArgs.count("-printpriority"))
|
||||||
|
printf("priority nValueIn=%-12I64d nConf=%-5d dPriority=%-20.1f\n", nValueIn, nConf, dPriority);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Priority is sum(valuein * age) / txsize
|
||||||
|
dPriority /= ::GetSerializeSize(tx, SER_NETWORK);
|
||||||
|
|
||||||
|
mapPriority.insert(make_pair(-dPriority, &(*mi).second));
|
||||||
|
|
||||||
|
if (fDebug && mapArgs.count("-printpriority"))
|
||||||
|
printf("priority %-20.1f %s\n%s\n", dPriority, tx.GetHash().ToString().substr(0,10).c_str(), tx.ToString().c_str());
|
||||||
|
}
|
||||||
|
|
||||||
|
// Collect transactions into block
|
||||||
map<uint256, CTxIndex> mapTestPool;
|
map<uint256, CTxIndex> mapTestPool;
|
||||||
vector<char> vfAlreadyAdded(mapTransactions.size());
|
|
||||||
uint64 nBlockSize = 1000;
|
uint64 nBlockSize = 1000;
|
||||||
int nBlockSigOps = 100;
|
int nBlockSigOps = 100;
|
||||||
bool fFoundSomething = true;
|
bool fFoundSomething = true;
|
||||||
while (fFoundSomething)
|
while (fFoundSomething)
|
||||||
{
|
{
|
||||||
fFoundSomething = false;
|
fFoundSomething = false;
|
||||||
unsigned int n = 0;
|
for (multimap<double, CTransaction*>::iterator mi = mapPriority.begin(); mi != mapPriority.end();)
|
||||||
for (map<uint256, CTransaction>::iterator mi = mapTransactions.begin(); mi != mapTransactions.end(); ++mi, ++n)
|
|
||||||
{
|
{
|
||||||
if (vfAlreadyAdded[n])
|
CTransaction& tx = *(*mi).second;
|
||||||
continue;
|
|
||||||
CTransaction& tx = (*mi).second;
|
|
||||||
if (tx.IsCoinBase() || !tx.IsFinal())
|
|
||||||
continue;
|
|
||||||
unsigned int nTxSize = ::GetSerializeSize(tx, SER_NETWORK);
|
unsigned int nTxSize = ::GetSerializeSize(tx, SER_NETWORK);
|
||||||
if (nBlockSize + nTxSize >= MAX_BLOCK_SIZE_GEN)
|
if (nBlockSize + nTxSize >= MAX_BLOCK_SIZE_GEN)
|
||||||
|
{
|
||||||
|
mapPriority.erase(mi++);
|
||||||
continue;
|
continue;
|
||||||
|
}
|
||||||
int nTxSigOps = tx.GetSigOpCount();
|
int nTxSigOps = tx.GetSigOpCount();
|
||||||
if (nBlockSigOps + nTxSigOps >= MAX_BLOCK_SIGOPS)
|
if (nBlockSigOps + nTxSigOps >= MAX_BLOCK_SIGOPS)
|
||||||
|
{
|
||||||
|
mapPriority.erase(mi++);
|
||||||
continue;
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
// Transaction fee based on block size
|
// Transaction fee based on block size
|
||||||
int64 nMinFee = tx.GetMinFee(nBlockSize);
|
int64 nMinFee = tx.GetMinFee(nBlockSize);
|
||||||
|
|
||||||
|
// Connecting can fail due to dependency on other memory pool transactions
|
||||||
|
// that aren't in the block yet, so keep trying in later passes
|
||||||
map<uint256, CTxIndex> mapTestPoolTmp(mapTestPool);
|
map<uint256, CTxIndex> mapTestPoolTmp(mapTestPool);
|
||||||
if (!tx.ConnectInputs(txdb, mapTestPoolTmp, CDiskTxPos(1,1,1), pindexPrev, nFees, false, true, nMinFee))
|
if (!tx.ConnectInputs(txdb, mapTestPoolTmp, CDiskTxPos(1,1,1), pindexPrev, nFees, false, true, nMinFee))
|
||||||
|
{
|
||||||
|
mi++;
|
||||||
continue;
|
continue;
|
||||||
|
}
|
||||||
swap(mapTestPool, mapTestPoolTmp);
|
swap(mapTestPool, mapTestPoolTmp);
|
||||||
|
|
||||||
|
// Added
|
||||||
pblock->vtx.push_back(tx);
|
pblock->vtx.push_back(tx);
|
||||||
nBlockSize += nTxSize;
|
nBlockSize += nTxSize;
|
||||||
nBlockSigOps += nTxSigOps;
|
nBlockSigOps += nTxSigOps;
|
||||||
vfAlreadyAdded[n] = true;
|
|
||||||
fFoundSomething = true;
|
fFoundSomething = true;
|
||||||
|
mapPriority.erase(mi++);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -3426,16 +3509,15 @@ bool SelectCoins(int64 nTargetValue, set<CWalletTx*>& setCoinsRet)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
bool CreateTransaction(CScript scriptPubKey, int64 nValue, CWalletTx& wtxNew, CReserveKey& reservekey, int64& nFeeRequiredRet)
|
bool CreateTransaction(CScript scriptPubKey, int64 nValue, CWalletTx& wtxNew, CReserveKey& reservekey, int64& nFeeRet)
|
||||||
{
|
{
|
||||||
nFeeRequiredRet = 0;
|
|
||||||
CRITICAL_BLOCK(cs_main)
|
CRITICAL_BLOCK(cs_main)
|
||||||
{
|
{
|
||||||
// txdb must be opened before the mapWallet lock
|
// txdb must be opened before the mapWallet lock
|
||||||
CTxDB txdb("r");
|
CTxDB txdb("r");
|
||||||
CRITICAL_BLOCK(cs_mapWallet)
|
CRITICAL_BLOCK(cs_mapWallet)
|
||||||
{
|
{
|
||||||
int64 nFee = nTransactionFee;
|
nFeeRet = nTransactionFee;
|
||||||
loop
|
loop
|
||||||
{
|
{
|
||||||
wtxNew.vin.clear();
|
wtxNew.vin.clear();
|
||||||
|
@ -3444,7 +3526,7 @@ bool CreateTransaction(CScript scriptPubKey, int64 nValue, CWalletTx& wtxNew, CR
|
||||||
if (nValue < 0)
|
if (nValue < 0)
|
||||||
return false;
|
return false;
|
||||||
int64 nValueOut = nValue;
|
int64 nValueOut = nValue;
|
||||||
int64 nTotalValue = nValue + nFee;
|
int64 nTotalValue = nValue + nFeeRet;
|
||||||
|
|
||||||
// Choose coins to use
|
// Choose coins to use
|
||||||
set<CWalletTx*> setCoins;
|
set<CWalletTx*> setCoins;
|
||||||
|
@ -3504,13 +3586,16 @@ bool CreateTransaction(CScript scriptPubKey, int64 nValue, CWalletTx& wtxNew, CR
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
// Limit size
|
// Limit size
|
||||||
if (::GetSerializeSize(*(CTransaction*)&wtxNew, SER_NETWORK) >= MAX_BLOCK_SIZE_GEN/5)
|
unsigned int nBytes = ::GetSerializeSize(*(CTransaction*)&wtxNew, SER_NETWORK);
|
||||||
|
if (nBytes >= MAX_BLOCK_SIZE_GEN/5)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
// Check that enough fee is included
|
// Check that enough fee is included
|
||||||
if (nFee < wtxNew.GetMinFee())
|
int64 nPayFee = nTransactionFee * (1 + (int64)nBytes / 1000);
|
||||||
|
int64 nMinFee = wtxNew.GetMinFee();
|
||||||
|
if (nFeeRet < max(nPayFee, nMinFee))
|
||||||
{
|
{
|
||||||
nFee = nFeeRequiredRet = wtxNew.GetMinFee();
|
nFeeRet = max(nPayFee, nMinFee);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
8
main.h
8
main.h
|
@ -76,7 +76,7 @@ bool ProcessMessages(CNode* pfrom);
|
||||||
bool ProcessMessage(CNode* pfrom, string strCommand, CDataStream& vRecv);
|
bool ProcessMessage(CNode* pfrom, string strCommand, CDataStream& vRecv);
|
||||||
bool SendMessages(CNode* pto, bool fSendTrickle);
|
bool SendMessages(CNode* pto, bool fSendTrickle);
|
||||||
int64 GetBalance();
|
int64 GetBalance();
|
||||||
bool CreateTransaction(CScript scriptPubKey, int64 nValue, CWalletTx& wtxNew, CReserveKey& reservekey, int64& nFeeRequiredRet);
|
bool CreateTransaction(CScript scriptPubKey, int64 nValue, CWalletTx& wtxNew, CReserveKey& reservekey, int64& nFeeRet);
|
||||||
bool CommitTransaction(CWalletTx& wtxNew, CReserveKey& reservekey);
|
bool CommitTransaction(CWalletTx& wtxNew, CReserveKey& reservekey);
|
||||||
bool BroadcastTransaction(CWalletTx& wtxNew);
|
bool BroadcastTransaction(CWalletTx& wtxNew);
|
||||||
string SendMoney(CScript scriptPubKey, int64 nValue, CWalletTx& wtxNew, bool fAskFee=false);
|
string SendMoney(CScript scriptPubKey, int64 nValue, CWalletTx& wtxNew, bool fAskFee=false);
|
||||||
|
@ -580,7 +580,6 @@ public:
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
friend bool operator==(const CTransaction& a, const CTransaction& b)
|
friend bool operator==(const CTransaction& a, const CTransaction& b)
|
||||||
{
|
{
|
||||||
return (a.nVersion == b.nVersion &&
|
return (a.nVersion == b.nVersion &&
|
||||||
|
@ -617,6 +616,9 @@ public:
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
bool ReadFromDisk(CTxDB& txdb, COutPoint prevout, CTxIndex& txindexRet);
|
||||||
|
bool ReadFromDisk(CTxDB& txdb, COutPoint prevout);
|
||||||
|
bool ReadFromDisk(COutPoint prevout);
|
||||||
bool DisconnectInputs(CTxDB& txdb);
|
bool DisconnectInputs(CTxDB& txdb);
|
||||||
bool ConnectInputs(CTxDB& txdb, map<uint256, CTxIndex>& mapTestPool, CDiskTxPos posThisTx,
|
bool ConnectInputs(CTxDB& txdb, map<uint256, CTxIndex>& mapTestPool, CDiskTxPos posThisTx,
|
||||||
CBlockIndex* pindexBlock, int64& nFees, bool fBlock, bool fMiner, int64 nMinFee=0);
|
CBlockIndex* pindexBlock, int64& nFees, bool fBlock, bool fMiner, int64 nMinFee=0);
|
||||||
|
@ -1654,7 +1656,7 @@ public:
|
||||||
bool Cancels(const CAlert& alert) const
|
bool Cancels(const CAlert& alert) const
|
||||||
{
|
{
|
||||||
if (!IsInEffect())
|
if (!IsInEffect())
|
||||||
false;
|
return false; // this was a no-op before 31403
|
||||||
return (alert.nID <= nCancel || setCancel.count(alert.nID));
|
return (alert.nID <= nCancel || setCancel.count(alert.nID));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -22,7 +22,7 @@ class CDataStream;
|
||||||
class CAutoFile;
|
class CAutoFile;
|
||||||
static const unsigned int MAX_SIZE = 0x02000000;
|
static const unsigned int MAX_SIZE = 0x02000000;
|
||||||
|
|
||||||
static const int VERSION = 31402;
|
static const int VERSION = 31403;
|
||||||
static const char* pszSubVer = "";
|
static const char* pszSubVer = "";
|
||||||
|
|
||||||
|
|
||||||
|
|
9
ui.cpp
9
ui.cpp
|
@ -196,7 +196,7 @@ int ThreadSafeMessageBox(const string& message, const string& caption, int style
|
||||||
|
|
||||||
bool ThreadSafeAskFee(int64 nFeeRequired, const string& strCaption, wxWindow* parent)
|
bool ThreadSafeAskFee(int64 nFeeRequired, const string& strCaption, wxWindow* parent)
|
||||||
{
|
{
|
||||||
if (nFeeRequired < CENT || fDaemon)
|
if (nFeeRequired < CENT || nFeeRequired <= nTransactionFee || fDaemon)
|
||||||
return true;
|
return true;
|
||||||
string strMessage = strprintf(
|
string strMessage = strprintf(
|
||||||
_("This transaction is over the size limit. You can still send it for a fee of %s, "
|
_("This transaction is over the size limit. You can still send it for a fee of %s, "
|
||||||
|
@ -1966,8 +1966,13 @@ void CSendDialog::OnButtonSend(wxCommandEvent& event)
|
||||||
string strError = SendMoney(scriptPubKey, nValue, wtx, true);
|
string strError = SendMoney(scriptPubKey, nValue, wtx, true);
|
||||||
if (strError == "")
|
if (strError == "")
|
||||||
wxMessageBox(_("Payment sent "), _("Sending..."));
|
wxMessageBox(_("Payment sent "), _("Sending..."));
|
||||||
else if (strError != "ABORTED")
|
else if (strError == "ABORTED")
|
||||||
|
return; // leave send dialog open
|
||||||
|
else
|
||||||
|
{
|
||||||
wxMessageBox(strError + " ", _("Sending..."));
|
wxMessageBox(strError + " ", _("Sending..."));
|
||||||
|
EndModal(false);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
|
Loading…
Reference in a new issue