Sync various bits of work.

This commit is contained in:
JoelKatz
2012-01-13 00:15:34 -08:00
parent 2782c2dafe
commit c35ca834a7
7 changed files with 49 additions and 177 deletions

View File

@@ -91,6 +91,7 @@ void Application::run()
// temporary // temporary
mWallet.load(); mWallet.load();
mWallet.syncToLedger(true, &(*secondLedger));
// temporary // temporary
mIOService.run(); // This blocks mIOService.run(); // This blocks

View File

@@ -38,14 +38,14 @@ bool u160ToHuman(uint160& buf, std::string& retStr)
return(true); return(true);
} }
uint160 uint256::to160() const base_uint160 uint256::to160() const
{ {
uint160 m; uint160 m;
memcpy(&m, this, sizeof(uint160)); memcpy(&m, this, sizeof(uint160));
return m; return m;
} }
uint256 uint160::to256() const base_uint256 uint160::to256() const
{ {
uint256 m; uint256 m;
memcpy(&m, this, sizeof(this)); memcpy(&m, this, sizeof(this));

View File

@@ -237,14 +237,25 @@ Ledger::TransResult Ledger::removeTransaction(Transaction::pointer trans)
} }
Ledger::TransResult Ledger::hasTransaction(Transaction::pointer trans) Ledger::TransResult Ledger::hasTransaction(Transaction::pointer trans)
{ { // Is this transaction in this ledger? If not, could it go in it?
boost::recursive_mutex::scoped_lock sl(mLock); boost::recursive_mutex::scoped_lock sl(mLock);
if(mTransactionMap==NULL) return TR_ERROR; if(mTransactionMap==NULL) return TR_ERROR;
try try
{ {
Transaction::pointer t=getTransaction(trans->getID()); Transaction::pointer t=getTransaction(trans->getID());
if(t==NULL) return TR_NOTFOUND; if(!!t) return TR_ALREADY;
return TR_SUCCESS;
if(trans->getSourceLedger()>mLedgerSeq) return TR_BADLSEQ;
AccountState::pointer fromAccount=getAccountState(trans->getFromAccount());
if(!fromAccount) return TR_BADACCT; // cannot send from non-existent account
// may be in a previous ledger
if(fromAccount->getSeq()>trans->getFromAccountSeq()) return TR_PASTASEQ;
if(fromAccount->getSeq()<trans->getFromAccountSeq()) return TR_PREASEQ;
if(fromAccount->getBalance()<trans->getAmount()) return TR_INSUFF;
return TR_NOTFOUND;
} }
catch (SHAMapException) catch (SHAMapException)
{ {
@@ -385,152 +396,3 @@ Ledger::pointer Ledger::loadByHash(const uint256& ledgerHash)
sql.append("';"); sql.append("';");
return getSQL(sql); return getSQL(sql);
} }
#if 0
// returns true if the from account has enough for the transaction and seq num is correct
bool Ledger::addTransaction(Transaction::pointer trans,bool checkDuplicate)
{
if(checkDuplicate && hasTransaction(trans)) return(false);
if(mParent)
{ // check the lineage of the from addresses
uint160 address=protobufTo160(trans->from());
if(mAccounts.count(address))
{
pair<uint64,uint32> account=mAccounts[address];
if( (account.first<trans->amount()) &&
(trans->seqnum()==account.second) )
{
account.first -= trans->amount();
account.second++;
mAccounts[address]=account;
uint160 destAddress=protobufTo160(trans->dest());
Account destAccount=mAccounts[destAddress];
destAccount.first += trans->amount();
mAccounts[destAddress]=destAccount;
mValidSig=false;
mValidHash=false;
mTransactions.push_back(trans);
if(mChild)
{
mChild->parentAddedTransaction(trans);
}
return(true);
}else
{
mDiscardedTransactions.push_back(trans);
return false;
}
}else
{
mDiscardedTransactions.push_back(trans);
return false;
}
}else
{ // we have no way to know so just hold on to it but don't add to the accounts
mValidSig=false;
mValidHash=false;
mDiscardedTransactions.push_back(trans);
return(true);
}
}
// Don't check the amounts. We will do this at the end.
void Ledger::addTransactionAllowNeg(Transaction::pointer trans)
{
uint160 fromAddress=protobufTo160(trans->from());
if(mAccounts.count(fromAddress))
{
Account fromAccount=mAccounts[fromAddress];
if(trans->seqnum()==fromAccount.second)
{
fromAccount.first -= trans->amount();
fromAccount.second++;
mAccounts[fromAddress]=fromAccount;
uint160 destAddress=protobufTo160(trans->dest());
Account destAccount=mAccounts[destAddress];
destAccount.first += trans->amount();
mAccounts[destAddress]=destAccount;
mTransactions.push_back(trans);
}else
{ // invalid seqnum
mDiscardedTransactions.push_back(trans);
}
}else
{
if(trans->seqnum()==0)
{
mAccounts[fromAddress]=Account(-((int64)trans->amount()),1);
uint160 destAddress=protobufTo160(trans->dest());
Account destAccount=mAccounts[destAddress];
destAccount.first += trans->amount();
mAccounts[destAddress]=destAccount;
mTransactions.push_back(trans);
}else
{
mDiscardedTransactions.push_back(trans);
}
}
}
// Must look for transactions to discard to make this account positive
// When we chuck transactions it might cause other accounts to need correcting
void Ledger::correctAccount(const uint160& address)
{
list<uint160> effected;
// do this in reverse so we take of the higher seqnum first
for( list<Transaction::pointer>::reverse_iterator iter=mTransactions.rbegin(); iter != mTransactions.rend(); )
{
Transaction::pointer trans= *iter;
if(protobufTo160(trans->from()) == address)
{
Account fromAccount=mAccounts[address];
assert(fromAccount.second==trans->seqnum()+1);
if(fromAccount.first<0)
{
fromAccount.first += trans->amount();
fromAccount.second --;
mAccounts[address]=fromAccount;
uint160 destAddress=protobufTo160(trans->dest());
Account destAccount=mAccounts[destAddress];
destAccount.first -= trans->amount();
mAccounts[destAddress]=destAccount;
if(destAccount.first<0) effected.push_back(destAddress);
list<Transaction::pointer>::iterator temp=mTransactions.erase( --iter.base() );
if(fromAccount.first>=0) break;
iter=list<Transaction::pointer>::reverse_iterator(temp);
}else break;
}else iter--;
}
BOOST_FOREACH(uint160& address,effected)
{
correctAccount(address);
}
}
#endif

View File

@@ -17,8 +17,8 @@ protected:
int mAccountSeq; int mAccountSeq;
// local usage tracking // local usage tracking
uint64 mBalance; // The balance, from the last ledger uint64 mLgrBalance; // The balance, from the last ledger
uint64 mBalanceLT; // The balance, after all local transactions int64 mTxnDelta; // The balance changes from local/pending transactions
uint32 mTxnSeq; // The sequence number of the next transaction uint32 mTxnSeq; // The sequence number of the next transaction
public: public:
@@ -41,9 +41,10 @@ public:
uint32 getTxnSeq() const { return mTxnSeq; } uint32 getTxnSeq() const { return mTxnSeq; }
uint32 incTxnSeq() { return mTxnSeq++; } uint32 incTxnSeq() { return mTxnSeq++; }
uint64 getBalance() const { return mBalance; } int64 getEffectiveBalance() const { return static_cast<int64_t>(mLgrBalance)+mTxnDelta; }
void credit(uint64 amount) { mBalance+=amount; } void credit(uint64 amount) { mTxnDelta+=amount; }
void debit(uint64 amount) { assert(mBalance>=amount); mBalance-=amount; } void debit(uint64 amount) { mTxnDelta-=amount; }
void setLedgerBalance(uint64_t lb) { mLgrBalance=lb; }
}; };
class LocalAccountFamily class LocalAccountFamily
@@ -119,6 +120,7 @@ public:
uint32 getAcctSeq() const; uint32 getAcctSeq() const;
uint64 getBalance() const; uint64 getBalance() const;
void setLedgerBalance(uint64_t ledgerBalance);
void incAcctSeq(uint32 transAcctSeq); void incAcctSeq(uint32 transAcctSeq);
CKey::pointer getPublicKey(); CKey::pointer getPublicKey();

View File

@@ -9,6 +9,7 @@
#include "boost/interprocess/sync/scoped_lock.hpp" #include "boost/interprocess/sync/scoped_lock.hpp"
#include "Wallet.h" #include "Wallet.h"
#include "Ledger.h"
#include "NewcoinAddress.h" #include "NewcoinAddress.h"
#include "Application.h" #include "Application.h"
@@ -20,7 +21,7 @@
LocalAccountEntry::LocalAccountEntry(const uint160& accountFamily, int accountSeq, EC_POINT* rootPubKey) : LocalAccountEntry::LocalAccountEntry(const uint160& accountFamily, int accountSeq, EC_POINT* rootPubKey) :
mPublicKey(new CKey(accountFamily, rootPubKey, accountSeq)), mPublicKey(new CKey(accountFamily, rootPubKey, accountSeq)),
mAccountFamily(accountFamily), mAccountSeq(accountSeq), mAccountFamily(accountFamily), mAccountSeq(accountSeq),
mBalance(0), mBalanceLT(0), mTxnSeq(0) mLgrBalance(0), mTxnDelta(0), mTxnSeq(0)
{ {
mAcctID=mPublicKey->GetAddress().GetHash160(); mAcctID=mPublicKey->GetAddress().GetHash160();
if(theApp!=NULL) mPublicKey=theApp->getPubKeyCache().store(mAcctID, mPublicKey); if(theApp!=NULL) mPublicKey=theApp->getPubKeyCache().store(mAcctID, mPublicKey);
@@ -401,7 +402,14 @@ uint64 LocalAccount::getBalance() const
{ {
LocalAccountEntry::pointer la(mFamily->get(mSeq)); LocalAccountEntry::pointer la(mFamily->get(mSeq));
if(!la) return 0; if(!la) return 0;
return la->getBalance(); return la->getEffectiveBalance();
}
void LocalAccount::setLedgerBalance(uint64_t lb)
{
LocalAccountEntry::pointer la(mFamily->get(mSeq));
if(!la) return ;
la->setLedgerBalance(lb);
} }
CKey::pointer LocalAccount::getPublicKey() CKey::pointer LocalAccount::getPublicKey()
@@ -794,18 +802,17 @@ void Wallet::syncToLedger(bool force, Ledger* ledger)
{ {
boost::recursive_mutex::scoped_lock sl(mLock); boost::recursive_mutex::scoped_lock sl(mLock);
if(!force && (mLedger>=ledger->getLedgerSeq())) return; if(!force && (mLedger>=ledger->getLedgerSeq())) return;
for(std::map<uint160, LocalAccount::pointer>::iterator it=mAccounts.begin(); it!=mAccounts.end(); ++it) for(std::map<uint256, LocalTransaction::pointer>::iterator xit=mTransactions.begin();
{ xit!=mTransactions.end(); ++xit)
LocalAccount::pointer& lac=it->second; { // check each transaction, see if it's in the ledger or allowed in the ledger
AccountState::pointer acs=ledger->getAccountState(it->first); // WRITEME
if(!acs) }
{ // account is not in the ledger for(std::map<uint160, LocalAccount::pointer>::iterator ait=mAccounts.begin(); ait!=mAccounts.end(); ++ait)
// WRITEME { // check each account, see if our ledger balance matches
} LocalAccount::pointer& lac=ait->second;
else AccountState::pointer acs=ledger->getAccountState(ait->first);
{ // account is in the ledger if(!acs) lac->setLedgerBalance(0);
// WRITEME else lac->setLedgerBalance(acs->getBalance());
}
} }
if(mLedger<ledger->getLedgerSeq()) mLedger=ledger->getLedgerSeq(); if(mLedger<ledger->getLedgerSeq()) mLedger=ledger->getLedgerSeq();
} }

View File

@@ -300,7 +300,7 @@ public:
while (isxdigit(*psz)) while (isxdigit(*psz))
{ {
*this <<= 4; *this <<= 4;
int n = phexdigit[*psz++]; int n = phexdigit[(int) *psz++];
*this += n; *this += n;
} }
if (fNegative) if (fNegative)

View File

@@ -320,7 +320,7 @@ public:
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0xa,0xb,0xc,0xd,0xe,0xf,0,0,0,0,0,0,0,0,0 }; 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0xa,0xb,0xc,0xd,0xe,0xf,0,0,0,0,0,0,0,0,0 };
const char* pbegin = psz; const char* pbegin = psz;
while (phexdigit[*psz] || *psz == '0') while (phexdigit[(int) *psz] || *psz == '0')
psz++; psz++;
psz--; psz--;
unsigned char* p1 = (unsigned char*)pn; unsigned char* p1 = (unsigned char*)pn;
@@ -470,7 +470,7 @@ public:
*this = 0; *this = 0;
} }
uint256 to256() const; base_uint256 to256() const;
}; };
inline bool operator==(const uint160& a, uint64 b) { return (base_uint160)a == b; } inline bool operator==(const uint160& a, uint64 b) { return (base_uint160)a == b; }
@@ -586,7 +586,7 @@ public:
*this = 0; *this = 0;
} }
uint160 to160() const; base_uint160 to160() const;
}; };