This commit is contained in:
jed
2011-10-20 16:34:22 -07:00
parent 650ee74391
commit 0416d64fdc
16 changed files with 176 additions and 101 deletions

Binary file not shown.

View File

@@ -17,6 +17,12 @@ Ledger::Ledger(uint32 index)
mIndex=index; mIndex=index;
mValidSig=false; mValidSig=false;
mValidHash=false; mValidHash=false;
mValidationSeqNum=0;
}
Ledger::Ledger(newcoin::FullLedger& ledger)
{
setTo(ledger);
} }
// TODO: we should probably make a shared pointer type for each of these PB types // TODO: we should probably make a shared pointer type for each of these PB types
@@ -25,7 +31,7 @@ newcoin::FullLedger* Ledger::createFullLedger()
// TODO: do we need to hash and create accounts map first? // TODO: do we need to hash and create accounts map first?
newcoin::FullLedger* ledger=new newcoin::FullLedger(); newcoin::FullLedger* ledger=new newcoin::FullLedger();
ledger->set_index(mIndex); ledger->set_index(mIndex);
ledger->set_hash(mHash); ledger->set_hash(mHash.begin(),mHash.GetSerializeSize());
pair<uint160, pair<uint64,uint32> >& account=pair<uint160, pair<uint64,uint32> >(); pair<uint160, pair<uint64,uint32> >& account=pair<uint160, pair<uint64,uint32> >();
BOOST_FOREACH(account,mAccounts) BOOST_FOREACH(account,mAccounts)
@@ -49,11 +55,13 @@ void Ledger::setTo(newcoin::FullLedger& ledger)
mValidSig=false; mValidSig=false;
mValidHash=false; mValidHash=false;
mParentHash=Transaction::protobufToInternalHash(ledger.parenthash());
int numAccounts=ledger.accounts_size(); int numAccounts=ledger.accounts_size();
for(int n=0; n<numAccounts; n++) for(int n=0; n<numAccounts; n++)
{ {
const newcoin::Account& account=ledger.accounts(n); const newcoin::Account& account=ledger.accounts(n);
mAccounts[ NewcoinAddress::protobufToInternal(account.address()) ] = pair<uint64,uint32>(account.amount(),account.seqnum()); mAccounts[ NewcoinAddress::protobufToInternal(account.address()) ] = Account(account.amount(),account.seqnum());
} }
int numTrans=ledger.transactions_size(); int numTrans=ledger.transactions_size();
@@ -64,6 +72,15 @@ void Ledger::setTo(newcoin::FullLedger& ledger)
} }
} }
Ledger::pointer Ledger::getParent()
{
if(!mParent)
{
mParent=theApp->getLedgerMaster().getLedger(mParentHash);
}
return(mParent);
}
bool Ledger::load(std::string dir) bool Ledger::load(std::string dir)
{ {
string filename=strprintf("%s%u.ledger",dir,mIndex); string filename=strprintf("%s%u.ledger",dir,mIndex);
@@ -114,54 +131,32 @@ Ledger::Account* Ledger::getAccount(uint160& address)
return(NULL); return(NULL);
} }
string& Ledger::getHash() uint256& Ledger::getHash()
{ {
if(!mValidHash) hash(); if(!mValidHash) hash();
return(mHash); return(mHash);
} }
string& Ledger::getSignature() uint256& Ledger::getSignature()
{ {
if(!mValidSig) sign(); if(!mValidSig) sign();
return(mSignature); return(mSignature);
} }
void Ledger::publish() void Ledger::publishValidation()
{ {
PackedMessage::pointer packet=Peer::createValidation(shared_from_this()); PackedMessage::pointer packet=Peer::createValidation(shared_from_this());
theApp->getConnectionPool().relayMessage(NULL,packet); theApp->getConnectionPool().relayMessage(NULL,packet);
} }
void Ledger::finalize()
{
}
void Ledger::sign() void Ledger::sign()
{ {
// TODO: // TODO:
} }
void Ledger::calcMoneyMap()
{
/*
// start with map from the previous ledger
// go through every transaction
Ledger::pointer parent=theApp->getLedgerMaster().getLedger(mIndex-1);
if(parent)
{
mMoneyMap.clear();
mMoneyMap=parent->getMoneyMap();
mBundle.updateMap(mMoneyMap);
// TODO: strip the 0 ones
} */
}
void Ledger::hash() void Ledger::hash()
{ {
calcMoneyMap();
// TODO: // TODO:
} }

View File

@@ -23,8 +23,10 @@ private:
bool mFaith; //TODO: if you will bother to validate this ledger or not. You have to accept the first ledger on Faith bool mFaith; //TODO: if you will bother to validate this ledger or not. You have to accept the first ledger on Faith
uint32 mIndex; uint32 mIndex;
std::string mHash; uint256 mHash;
std::string mSignature; uint256 mSignature;
uint256 mParentHash;
uint32 mValidationSeqNum;
@@ -40,7 +42,6 @@ private:
Ledger::pointer mChild; Ledger::pointer mChild;
void calcMoneyMap();
void sign(); void sign();
void hash(); void hash();
void addTransactionRecalculate(TransactionPtr trans); void addTransactionRecalculate(TransactionPtr trans);
@@ -48,6 +49,8 @@ private:
public: public:
typedef boost::shared_ptr<Ledger> pointer; typedef boost::shared_ptr<Ledger> pointer;
Ledger(uint32 index); Ledger(uint32 index);
Ledger(newcoin::FullLedger& ledger);
void setTo(newcoin::FullLedger& ledger); void setTo(newcoin::FullLedger& ledger);
void save(std::string dir); void save(std::string dir);
@@ -55,9 +58,9 @@ public:
void recalculate(bool recursive=true); void recalculate(bool recursive=true);
void publish(); void publishValidation();
void finalize();
std::list<TransactionPtr>& getTransactions(){ return(mTransactions); }
bool hasTransaction(TransactionPtr trans); bool hasTransaction(TransactionPtr trans);
int64 getAmountHeld(uint160& address); int64 getAmountHeld(uint160& address);
@@ -67,13 +70,16 @@ public:
void addIgnoredValidation(newcoin::Validation& valid); void addIgnoredValidation(newcoin::Validation& valid);
uint32 getIndex(){ return(mIndex); } uint32 getIndex(){ return(mIndex); }
std::string& getHash(); uint256& getHash();
std::string& getSignature(); uint256& getSignature();
uint32 getValidSeqNum(){ return(mValidationSeqNum); }
unsigned int getNumTransactions(){ return(mTransactions.size()); } unsigned int getNumTransactions(){ return(mTransactions.size()); }
std::map<uint160, std::pair<int64,uint32> >& getAccounts(){ return(mAccounts); } std::map<uint160, std::pair<int64,uint32> >& getAccounts(){ return(mAccounts); }
Account* getAccount(uint160& address); Account* getAccount(uint160& address);
newcoin::FullLedger* createFullLedger(); newcoin::FullLedger* createFullLedger();
Ledger::pointer getParent();
}; };

View File

@@ -24,7 +24,7 @@ bool LedgerHistory::loadLedger(uint32 index)
// this will see if the ledger is in memory // this will see if the ledger is in memory
// if not it will check disk and load it // if not it will check disk and load it
// if not it will return NULL // if not it will return NULL
Ledger::pointer LedgerHistory::getLedger(uint32 index) Ledger::pointer LedgerHistory::getAcceptedLedger(uint32 index)
{ {
if(mAcceptedLedgers.count(index)) if(mAcceptedLedgers.count(index))
return(mAcceptedLedgers[index]); return(mAcceptedLedgers[index]);

View File

@@ -23,9 +23,10 @@ public:
void load(); void load();
void addLedger(Ledger::pointer ledger); void addLedger(Ledger::pointer ledger);
void addAcceptedLedger(Ledger::pointer ledger);
Ledger::pointer getLedger(uint32 index); Ledger::pointer getAcceptedLedger(uint32 index);
Ledger::pointer getLedger(uint256 hash); Ledger::pointer getLedger(uint256& hash);
}; };
#endif #endif

View File

@@ -35,10 +35,6 @@ int64 LedgerMaster::getAmountHeld(std::string& addr)
return(mCurrentLedger->getAmountHeld(NewcoinAddress::humanToInternal(addr))); return(mCurrentLedger->getAmountHeld(NewcoinAddress::humanToInternal(addr)));
} }
Ledger::pointer LedgerMaster::getLedger(uint32 index)
{
return(mLedgerHistory.getLedger(index));
}
bool LedgerMaster::isTransactionOnFutureList(TransactionPtr needle) bool LedgerMaster::isTransactionOnFutureList(TransactionPtr needle)
@@ -85,13 +81,16 @@ bool LedgerMaster::addTransaction(TransactionPtr trans)
// TODO: since maybe we are adding a whole bunch at once. we should send at the end of the batch // TODO: since maybe we are adding a whole bunch at once. we should send at the end of the batch
// TODO: do we ever really need to re-propose? // TODO: do we ever really need to re-propose?
//if(mAfterProposed) sendProposal(); //if(mAfterProposed) sendProposal();
theApp->getWallet().transactionChanged(trans);
return(true); return(true);
}else return(false); }else return(false);
}else if(trans->ledgerindex()==mCurrentLedger->getIndex()) }else if(trans->ledgerindex()==mCurrentLedger->getIndex())
{ {
if(mCurrentLedger->hasTransaction(trans)) return(false); if(mCurrentLedger->hasTransaction(trans)) return(false);
if(!isValidTransaction(trans)) return(false); if(!isValidTransaction(trans)) return(false);
return( mCurrentLedger->addTransaction(trans,false) ); if(!mCurrentLedger->addTransaction(trans,false)) return(false);
theApp->getWallet().transactionChanged(trans);
return( true );
}else if(trans->ledgerindex()>mCurrentLedger->getIndex()) }else if(trans->ledgerindex()>mCurrentLedger->getIndex())
{ // in the future { // in the future
@@ -110,51 +109,68 @@ bool LedgerMaster::addTransaction(TransactionPtr trans)
uint32 checkIndex=trans->ledgerindex(); uint32 checkIndex=trans->ledgerindex();
while(checkIndex <= mCurrentLedger->getIndex()) while(checkIndex <= mCurrentLedger->getIndex())
{ {
Ledger::pointer ledger=mLedgerHistory.getLedger(checkIndex); Ledger::pointer ledger=mLedgerHistory.getAcceptedLedger(checkIndex);
if(ledger) if(ledger)
{ {
if(ledger->hasTransaction(trans)) return(false); if(ledger->hasTransaction(trans)) return(false);
} }
checkIndex++; checkIndex++;
} }
if(!mCurrentLedger->addTransaction(trans,false)) return(false);
return( mCurrentLedger->addTransaction(trans,false) ); theApp->getWallet().transactionChanged(trans);
return(true);
} }
} }
void LedgerMaster::gotFullLedger(newcoin::FullLedger& ledger)
void LedgerMaster::addFullLedger(newcoin::FullLedger& ledger)
{ {
// TODO: // check if we already have this ledger
// if this is a historical ledger we don't have we can add it to the history? // check that the hash is correct
// if this is the same index as the finalized ledger we should go through and look for transactions we missed uint256 inHash=Transaction::protobufToInternalHash(ledger.hash());
// if this is a historical ledger but it has more consensus than the one you have use it. Ledger::pointer existingLedger=mLedgerHistory.getLedger( inHash );
if(existingLedger) return;
Ledger::pointer newLedger=Ledger::pointer(new Ledger(ledger));
if(newLedger->getHash()==inHash)
{
mLedgerHistory.addLedger(newLedger);
// add all these in case we are missing some
BOOST_FOREACH(TransactionPtr trans, newLedger->getTransactions())
{
addTransaction(trans);
}
}else cout << "We were sent a bad ledger hash" << endl;
}
void LedgerMaster::startFinalization()
{
mFinalizingLedger=mCurrentLedger;
mCurrentLedger=Ledger::pointer(new Ledger(mCurrentLedger->getIndex()+1));
applyFutureProposals( mFinalizingLedger->getIndex() );
applyFutureTransactions( mCurrentLedger->getIndex() );
} }
void LedgerMaster::sendProposal() void LedgerMaster::sendProposal()
{ {
//mAfterProposed=true;
PackedMessage::pointer packet=Peer::createLedgerProposal(mFinalizingLedger); PackedMessage::pointer packet=Peer::createLedgerProposal(mFinalizingLedger);
theApp->getConnectionPool().relayMessage(NULL,packet); theApp->getConnectionPool().relayMessage(NULL,packet);
} }
void LedgerMaster::nextLedger()
void LedgerMaster::endFinalization()
{ {
// publish past ledger mFinalizingLedger->publishValidation();
// finalize current ledger mLedgerHistory.addAcceptedLedger(mFinalizingLedger);
// start a new ledger mLedgerHistory.addLedger(mFinalizingLedger);
//mAfterProposed=false; mFinalizingLedger=Ledger::pointer();
Ledger::pointer closedLedger=mFinalizingLedger;
mFinalizingLedger=mCurrentLedger;
mCurrentLedger=Ledger::pointer(new Ledger(mCurrentLedger->getIndex()+1));
mFinalizingLedger->finalize();
closedLedger->publish();
mLedgerHistory.addLedger(closedLedger);
applyFutureProposals( mFinalizingLedger->getIndex() );
applyFutureTransactions( mCurrentLedger->getIndex() );
} }
void LedgerMaster::addFutureProposal(Peer::pointer peer,newcoin::ProposeLedger& otherLedger) void LedgerMaster::addFutureProposal(Peer::pointer peer,newcoin::ProposeLedger& otherLedger)
@@ -195,10 +211,10 @@ void LedgerMaster::checkLedgerProposal(Peer::pointer peer, newcoin::ProposeLedge
if(otherLedger.ledgerindex()<mFinalizingLedger->getIndex()) if(otherLedger.ledgerindex()<mFinalizingLedger->getIndex())
{ // you have already closed this ledger { // you have already closed this ledger
Ledger::pointer oldLedger=mLedgerHistory.getLedger(otherLedger.ledgerindex()); Ledger::pointer oldLedger=mLedgerHistory.getAcceptedLedger(otherLedger.ledgerindex());
if(oldLedger) if(oldLedger)
{ {
if( (oldLedger->getHash()!=otherLedger.hash()) && if( (oldLedger->getHash()!=Transaction::protobufToInternalHash(otherLedger.hash())) &&
(oldLedger->getNumTransactions()>=otherLedger.numtransactions())) (oldLedger->getNumTransactions()>=otherLedger.numtransactions()))
{ {
peer->sendLedgerProposal(oldLedger); peer->sendLedgerProposal(oldLedger);
@@ -209,7 +225,7 @@ void LedgerMaster::checkLedgerProposal(Peer::pointer peer, newcoin::ProposeLedge
addFutureProposal(peer,otherLedger); addFutureProposal(peer,otherLedger);
}else }else
{ // you guys are on the same page { // you guys are on the same page
if(mFinalizingLedger->getHash()!=otherLedger.hash()) if(mFinalizingLedger->getHash()!= Transaction::protobufToInternalHash(otherLedger.hash()))
{ {
if( mFinalizingLedger->getNumTransactions()>=otherLedger.numtransactions()) if( mFinalizingLedger->getNumTransactions()>=otherLedger.numtransactions())
{ {

View File

@@ -41,17 +41,20 @@ public:
void save(); void save();
uint32 getCurrentLedgerIndex(); uint32 getCurrentLedgerIndex();
//int getCurrentLedgerSeconds();
Ledger::pointer getLedger(uint32 index); Ledger::pointer getAcceptedLedger(uint32 index){ return(mLedgerHistory.getAcceptedLedger(index)); }
Ledger::pointer getLedger(uint256& hash){ return(mLedgerHistory.getLedger(hash)); }
int64 getAmountHeld(std::string& addr); int64 getAmountHeld(std::string& addr);
int64 getAmountHeld(uint160& addr); int64 getAmountHeld(uint160& addr);
Ledger::Account* getAccount(uint160& addr){ return(mCurrentLedger->getAccount(addr)); } Ledger::Account* getAccount(uint160& addr){ return(mCurrentLedger->getAccount(addr)); }
bool addTransaction(TransactionPtr trans); bool addTransaction(TransactionPtr trans);
void gotFullLedger(newcoin::FullLedger& ledger); void addFullLedger(newcoin::FullLedger& ledger);
void nextLedger(); void startFinalization();
void sendProposal(); void sendProposal();
void endFinalization();
void checkLedgerProposal(Peer::pointer peer,newcoin::ProposeLedger& packet); void checkLedgerProposal(Peer::pointer peer,newcoin::ProposeLedger& packet);
}; };

View File

@@ -107,9 +107,10 @@ PackedMessage::pointer Peer::createFullLedger(Ledger::pointer ledger)
PackedMessage::pointer Peer::createLedgerProposal(Ledger::pointer ledger) PackedMessage::pointer Peer::createLedgerProposal(Ledger::pointer ledger)
{ {
uint256& hash=ledger->getHash();
newcoin::ProposeLedger* prop=new newcoin::ProposeLedger(); newcoin::ProposeLedger* prop=new newcoin::ProposeLedger();
prop->set_ledgerindex(ledger->getIndex()); prop->set_ledgerindex(ledger->getIndex());
prop->set_hash(ledger->getHash()); prop->set_hash(hash.begin(),hash.GetSerializeSize());
prop->set_numtransactions(ledger->getNumTransactions()); prop->set_numtransactions(ledger->getNumTransactions());
PackedMessage::pointer packet(new PackedMessage(PackedMessage::MessagePointer(prop),newcoin::PROPOSE_LEDGER)); PackedMessage::pointer packet(new PackedMessage(PackedMessage::MessagePointer(prop),newcoin::PROPOSE_LEDGER));
@@ -118,10 +119,14 @@ PackedMessage::pointer Peer::createLedgerProposal(Ledger::pointer ledger)
PackedMessage::pointer Peer::createValidation(Ledger::pointer ledger) PackedMessage::pointer Peer::createValidation(Ledger::pointer ledger)
{ {
uint256 hash=ledger->getHash();
uint256 sig=ledger->getSignature();
newcoin::Validation* valid=new newcoin::Validation(); newcoin::Validation* valid=new newcoin::Validation();
valid->set_ledgerindex(ledger->getIndex()); valid->set_ledgerindex(ledger->getIndex());
valid->set_hash(ledger->getHash()); valid->set_hash(hash.begin(),hash.GetSerializeSize());
valid->set_sig(ledger->getSignature()); valid->set_seqnum(ledger->getValidSeqNum());
valid->set_sig(sig.begin(),sig.GetSerializeSize());
valid->set_hanko(theConfig.HANKO); valid->set_hanko(theConfig.HANKO);
@@ -268,7 +273,7 @@ void Peer::receiveHello(newcoin::Hello& packet)
void Peer::receiveGetFullLedger(newcoin::GetFullLedger& gfl) void Peer::receiveGetFullLedger(newcoin::GetFullLedger& gfl)
{ {
sendFullLedger(theApp->getLedgerMaster().getLedger(gfl.ledgerindex())); sendFullLedger(theApp->getLedgerMaster().getLedger(Transaction::protobufToInternalHash(gfl.hash())));
} }
void Peer::receiveValidation(newcoin::Validation& validation) void Peer::receiveValidation(newcoin::Validation& validation)
@@ -294,9 +299,6 @@ void Peer::receiveTransaction(TransactionPtr trans)
// add to the correct transaction bundle and relay if we need to // add to the correct transaction bundle and relay if we need to
if(theApp->getLedgerMaster().addTransaction(trans)) if(theApp->getLedgerMaster().addTransaction(trans))
{ {
// tell the wallet in case it was to us
theApp->getWallet().transactionAdded(trans);
// broadcast it to other Peers // broadcast it to other Peers
ConnectionPool& pool=theApp->getConnectionPool(); ConnectionPool& pool=theApp->getConnectionPool();
PackedMessage::pointer packet(new PackedMessage(PackedMessage::MessagePointer(new newcoin::Transaction(*(trans.get()))),newcoin::TRANSACTION)); PackedMessage::pointer packet(new PackedMessage(PackedMessage::MessagePointer(new newcoin::Transaction(*(trans.get()))),newcoin::TRANSACTION));
@@ -315,7 +317,7 @@ void Peer::receiveProposeLedger(newcoin::ProposeLedger& packet)
void Peer::receiveFullLedger(newcoin::FullLedger& packet) void Peer::receiveFullLedger(newcoin::FullLedger& packet)
{ {
theApp->getLedgerMaster().gotFullLedger(packet); theApp->getLedgerMaster().addFullLedger(packet);
} }
void Peer::connectTo(KnownNode& node) void Peer::connectTo(KnownNode& node)

View File

@@ -31,7 +31,7 @@ void TimingService::start(boost::asio::io_service& ioService)
void TimingService::handleLedger() void TimingService::handleLedger()
{ {
cout << "publish ledger" << endl; cout << "publish ledger" << endl;
theApp->getLedgerMaster().nextLedger(); theApp->getLedgerMaster().startFinalization();
mLedgerTimer->expires_at(mLedgerTimer->expires_at() + boost::posix_time::seconds(theConfig.LEDGER_SECONDS)); mLedgerTimer->expires_at(mLedgerTimer->expires_at() + boost::posix_time::seconds(theConfig.LEDGER_SECONDS));
mLedgerTimer->async_wait(boost::bind(&TimingService::handleLedger, this)); mLedgerTimer->async_wait(boost::bind(&TimingService::handleLedger, this));
@@ -44,3 +44,8 @@ void TimingService::handleProp()
theApp->getLedgerMaster().sendProposal(); theApp->getLedgerMaster().sendProposal();
} }
void TimingService::handleValid()
{
theApp->getLedgerMaster().endFinalization();
}

View File

@@ -11,9 +11,11 @@ class TimingService
{ {
boost::asio::deadline_timer* mLedgerTimer; boost::asio::deadline_timer* mLedgerTimer;
boost::asio::deadline_timer* mPropTimer; boost::asio::deadline_timer* mPropTimer;
boost::asio::deadline_timer* mValidTimer;
void handleLedger(); void handleLedger();
void handleProp(); void handleProp();
void handleValid();
public: public:
TimingService(); TimingService();
void start(boost::asio::io_service& ioService); void start(boost::asio::io_service& ioService);

View File

@@ -17,6 +17,8 @@ public:
static bool isSigValid(TransactionPtr trans); static bool isSigValid(TransactionPtr trans);
static bool isEqual(TransactionPtr t1, TransactionPtr t2); static bool isEqual(TransactionPtr t1, TransactionPtr t2);
static uint256 calcHash(TransactionPtr trans); static uint256 calcHash(TransactionPtr trans);
static uint256 protobufToInternalHash(const std::string& hash);
}; };

View File

@@ -1,29 +1,55 @@
#include "ValidationCollection.h" #include "ValidationCollection.h"
#include "Application.h" #include "Application.h"
#include "NewcoinAddress.h"
#include <boost/foreach.hpp>
bool ValidationCollection::hasValidation(uint256& ledgerHash,uint160& hanko)
{
if(mValidations.count(ledgerHash))
{
BOOST_FOREACH(newcoin::Validation& valid,mValidations[ledgerHash])
{
if(NewcoinAddress::protobufToInternal(valid.hanko()) == hanko) return(true);
}
}
if(mIgnoredValidations.count(ledgerHash))
{
BOOST_FOREACH(newcoin::Validation& valid,mIgnoredValidations[ledgerHash])
{
if(NewcoinAddress::protobufToInternal(valid.hanko()) == hanko) return(true);
}
}
return(false);
}
// TODO: when do we check if we are with the consensus?
void ValidationCollection::addValidation(newcoin::Validation& valid) void ValidationCollection::addValidation(newcoin::Validation& valid)
{ {
// TODO: // TODO: make sure the validation is valid
// make sure we don't already have this validation
// check if we care about this hanko
// make sure the validation is valid
uint256 hash=Transaction::protobufToInternalHash(valid.hash());
uint160 hanko=NewcoinAddress::protobufToInternal(valid.hanko());
// make sure we don't already have this validation
if(hasValidation(hash,hanko)) return;
// check if we care about this hanko
if( theApp->getUNL().findHanko(valid.hanko()) ) if( theApp->getUNL().findHanko(valid.hanko()) )
{ {
mValidations[valid.hash()].push_back(valid); mValidations[hash].push_back(valid);
}else }else
{ {
mIgnoredValidations[hash].push_back(valid);
} }
mMapIndexToValid[valid.ledgerindex()].push_back(valid); mMapIndexToValid[valid.ledgerindex()].push_back(valid);
} }
std::vector<newcoin::Validation>* ValidationCollection::getValidations(uint64 ledgerIndex) std::vector<newcoin::Validation>* ValidationCollection::getValidations(uint32 ledgerIndex)
{ {
if(mMapIndexToValid.count(ledgerIndex)) if(mMapIndexToValid.count(ledgerIndex))
{ {
return(&(mMapIndexToValid[ledgerIndex])); return(&(mMapIndexToValid[ledgerIndex]));
} }
return(NULL) return(NULL);
} }

View File

@@ -3,19 +3,22 @@
#include "newcoin.pb.h" #include "newcoin.pb.h"
#include "uint256.h" #include "uint256.h"
#include "types.h"
class ValidationCollection class ValidationCollection
{ {
// from ledger hash to the validation // from ledger hash to the validation
std::map<uint256, std::vector<newcoin::Validation> > mValidations; std::map<uint256, std::vector<newcoin::Validation> > mValidations;
std::map<uint256, std::vector<newcoin::Validation> > mIgnoredValidations; std::map<uint256, std::vector<newcoin::Validation> > mIgnoredValidations;
std::map<uint64, std::vector<newcoin::Validation> > mMapIndexToValid; std::map<uint32, std::vector<newcoin::Validation> > mMapIndexToValid;
bool hasValidation(uint256& ledgerHash,uint160& hanko);
public: public:
ValidationCollection(); ValidationCollection();
void addValidation(newcoin::Validation& valid); void addValidation(newcoin::Validation& valid);
std::vector<newcoin::Validation>* getValidations(uint64 ledgerIndex); std::vector<newcoin::Validation>* getValidations(uint32 ledgerIndex);
}; };
#endif #endif

View File

@@ -50,9 +50,26 @@ void Wallet::refreshAccounts()
} }
} }
void Wallet::transactionAdded(TransactionPtr trans) void Wallet::transactionChanged(TransactionPtr trans)
{ // TODO: optimize {
refreshAccounts();
BOOST_FOREACH(Account& account, mYourAccounts)
{
if( account.mAddress == NewcoinAddress::protobufToInternal(trans->from()) ||
account.mAddress == NewcoinAddress::protobufToInternal(trans->dest()) )
{
Ledger::Account* ledgerAccount=theApp->getLedgerMaster().getAccount(account.mAddress);
if(ledgerAccount)
{
account.mAmount= ledgerAccount->first;
account.mSeqNum= ledgerAccount->second;
}else
{
account.mAmount=0;
account.mSeqNum=0;
}
}
}
} }
Wallet::Account* Wallet::consolidateAccountOfSize(int64 amount) Wallet::Account* Wallet::consolidateAccountOfSize(int64 amount)
@@ -139,10 +156,6 @@ bool Wallet::Account::signTransaction(TransactionPtr trans)
} }
// Call after CreateTransaction unless you want to abort
bool Wallet::commitTransaction(TransactionPtr trans) bool Wallet::commitTransaction(TransactionPtr trans)
{ {
if(trans) if(trans)

View File

@@ -50,7 +50,7 @@ public:
std::string sendMoneyToAddress(uint160& destAddress, int64 amount); std::string sendMoneyToAddress(uint160& destAddress, int64 amount);
// you may need to update your balances // you may need to update your balances
void transactionAdded(TransactionPtr trans); void transactionChanged(TransactionPtr trans);
}; };

View File

@@ -41,6 +41,7 @@ message Transaction {
// Sequence number is incremented if you must change the ledger that you are validating // Sequence number is incremented if you must change the ledger that you are validating
// You will only need to change validation in cases of incompatible ledgers // You will only need to change validation in cases of incompatible ledgers
// hanko is 160 bits. We store the full public key in the UNL
message Validation { message Validation {
required uint32 ledgerIndex = 1; required uint32 ledgerIndex = 1;
required bytes hash = 2; required bytes hash = 2;