mirror of
https://github.com/XRPLF/rippled.git
synced 2025-12-06 17:27:55 +00:00
New canonical transaction order code. Tested and working.
CanonicalTXSet acts much like a map, but sorts the transactions in a simple order that makes them take fewer passed.
This commit is contained in:
53
src/CanonicalTXSet.cpp
Normal file
53
src/CanonicalTXSet.cpp
Normal file
@@ -0,0 +1,53 @@
|
|||||||
|
|
||||||
|
#include "CanonicalTXSet.h"
|
||||||
|
|
||||||
|
bool CanonicalTXKey::operator<(const CanonicalTXKey& key) const
|
||||||
|
{
|
||||||
|
if (mAccount < key.mAccount) return true;
|
||||||
|
if (mAccount > key.mAccount) return false;
|
||||||
|
if (mSeq < key.mSeq) return true;
|
||||||
|
if (mSeq > key.mSeq) return false;
|
||||||
|
return mTXid < key.mTXid;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool CanonicalTXKey::operator>(const CanonicalTXKey& key) const
|
||||||
|
{
|
||||||
|
if (mAccount > key.mAccount) return true;
|
||||||
|
if (mAccount < key.mAccount) return false;
|
||||||
|
if (mSeq > key.mSeq) return true;
|
||||||
|
if (mSeq < key.mSeq) return false;
|
||||||
|
return mTXid > key.mTXid;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool CanonicalTXKey::operator<=(const CanonicalTXKey& key) const
|
||||||
|
{
|
||||||
|
if (mAccount < key.mAccount) return true;
|
||||||
|
if (mAccount > key.mAccount) return false;
|
||||||
|
if (mSeq < key.mSeq) return true;
|
||||||
|
if (mSeq > key.mSeq) return false;
|
||||||
|
return mTXid <= key.mTXid;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool CanonicalTXKey::operator>=(const CanonicalTXKey& key)const
|
||||||
|
{
|
||||||
|
if (mAccount > key.mAccount) return true;
|
||||||
|
if (mAccount < key.mAccount) return false;
|
||||||
|
if (mSeq > key.mSeq) return true;
|
||||||
|
if (mSeq < key.mSeq) return false;
|
||||||
|
return mTXid >= key.mTXid;
|
||||||
|
}
|
||||||
|
|
||||||
|
void CanonicalTXSet::push_back(SerializedTransaction::pointer txn)
|
||||||
|
{
|
||||||
|
uint256 effectiveAccount = mSetHash;
|
||||||
|
effectiveAccount ^= txn->getSourceAccount().getAccountID().to256();
|
||||||
|
mMap.insert(std::make_pair(CanonicalTXKey(effectiveAccount, txn->getSequence(), txn->getTransactionID()), txn));
|
||||||
|
}
|
||||||
|
|
||||||
|
void CanonicalTXSet::eraseInc(iterator& it)
|
||||||
|
{
|
||||||
|
iterator tmp = it++;
|
||||||
|
mMap.erase(tmp);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
53
src/CanonicalTXSet.h
Normal file
53
src/CanonicalTXSet.h
Normal file
@@ -0,0 +1,53 @@
|
|||||||
|
#ifndef __CANONICAL_TX_SET_
|
||||||
|
#define __CANONICAL_TX_SET_
|
||||||
|
|
||||||
|
#include <map>
|
||||||
|
|
||||||
|
#include "uint256.h"
|
||||||
|
#include "SerializedTransaction.h"
|
||||||
|
|
||||||
|
class CanonicalTXKey
|
||||||
|
{
|
||||||
|
protected:
|
||||||
|
uint256 mAccount, mTXid;
|
||||||
|
uint32 mSeq;
|
||||||
|
|
||||||
|
public:
|
||||||
|
CanonicalTXKey(const uint256& account, uint32 seq, const uint256& id)
|
||||||
|
: mAccount(account), mTXid(id), mSeq(seq) { ; }
|
||||||
|
|
||||||
|
bool operator<(const CanonicalTXKey&) const;
|
||||||
|
bool operator>(const CanonicalTXKey&) const;
|
||||||
|
bool operator<=(const CanonicalTXKey&) const;
|
||||||
|
bool operator>=(const CanonicalTXKey&) const;
|
||||||
|
|
||||||
|
bool operator==(const CanonicalTXKey& k) const { return mTXid == k.mTXid; }
|
||||||
|
bool operator!=(const CanonicalTXKey& k) const { return mTXid != k.mTXid; }
|
||||||
|
};
|
||||||
|
|
||||||
|
class CanonicalTXSet
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
typedef std::map<CanonicalTXKey, SerializedTransaction::pointer>::iterator iterator;
|
||||||
|
typedef std::map<CanonicalTXKey, SerializedTransaction::pointer>::const_iterator const_iterator;
|
||||||
|
|
||||||
|
protected:
|
||||||
|
uint256 mSetHash;
|
||||||
|
std::map<CanonicalTXKey, SerializedTransaction::pointer> mMap;
|
||||||
|
|
||||||
|
public:
|
||||||
|
CanonicalTXSet(const uint256& lclHash) : mSetHash(lclHash) { ; }
|
||||||
|
|
||||||
|
void push_back(SerializedTransaction::pointer txn);
|
||||||
|
void erase(const iterator& it) { mMap.erase(it); }
|
||||||
|
void eraseInc(iterator& it);
|
||||||
|
|
||||||
|
iterator begin() { return mMap.begin(); }
|
||||||
|
iterator end() { return mMap.end(); }
|
||||||
|
const_iterator begin() const { return mMap.begin(); }
|
||||||
|
const_iterator end() const { return mMap.end(); }
|
||||||
|
size_t size() const { return mMap.size(); }
|
||||||
|
bool empty() const { return mMap.empty(); }
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
@@ -577,7 +577,7 @@ void LedgerConsensus::Saccept(boost::shared_ptr<LedgerConsensus> This, SHAMap::p
|
|||||||
}
|
}
|
||||||
|
|
||||||
void LedgerConsensus::applyTransactions(SHAMap::pointer set, Ledger::pointer ledger,
|
void LedgerConsensus::applyTransactions(SHAMap::pointer set, Ledger::pointer ledger,
|
||||||
std::list<SerializedTransaction::pointer>& failedTransactions)
|
CanonicalTXSet& failedTransactions)
|
||||||
{
|
{
|
||||||
TransactionEngine engine(ledger);
|
TransactionEngine engine(ledger);
|
||||||
|
|
||||||
@@ -620,16 +620,17 @@ void LedgerConsensus::applyTransactions(SHAMap::pointer set, Ledger::pointer led
|
|||||||
do
|
do
|
||||||
{
|
{
|
||||||
successes = 0;
|
successes = 0;
|
||||||
std::list<SerializedTransaction::pointer>::iterator it = failedTransactions.begin();
|
CanonicalTXSet::iterator it = failedTransactions.begin();
|
||||||
while (it != failedTransactions.end())
|
while (it != failedTransactions.end())
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
TransactionEngineResult result = engine.applyTransaction(**it, tepNO_CHECK_FEE | tepUPDATE_TOTAL, 0);
|
TransactionEngineResult result =
|
||||||
|
engine.applyTransaction(*it->second, tepNO_CHECK_FEE | tepUPDATE_TOTAL, 0);
|
||||||
if (result <= 0)
|
if (result <= 0)
|
||||||
{
|
{
|
||||||
if (result == 0) ++successes;
|
if (result == 0) ++successes;
|
||||||
failedTransactions.erase(it++);
|
failedTransactions.eraseInc(it);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@@ -639,7 +640,7 @@ void LedgerConsensus::applyTransactions(SHAMap::pointer set, Ledger::pointer led
|
|||||||
catch (...)
|
catch (...)
|
||||||
{
|
{
|
||||||
Log(lsWARNING) << " Throws";
|
Log(lsWARNING) << " Throws";
|
||||||
failedTransactions.erase(it++);
|
failedTransactions.eraseInc(it);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} while (successes > 0);
|
} while (successes > 0);
|
||||||
@@ -665,7 +666,7 @@ void LedgerConsensus::accept(SHAMap::pointer set)
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
std::list<SerializedTransaction::pointer> failedTransactions;
|
CanonicalTXSet failedTransactions(set->getHash());
|
||||||
applyTransactions(set, newLCL, failedTransactions);
|
applyTransactions(set, newLCL, failedTransactions);
|
||||||
newLCL->setClosed();
|
newLCL->setClosed();
|
||||||
newLCL->setAccepted();
|
newLCL->setAccepted();
|
||||||
@@ -703,8 +704,7 @@ void LedgerConsensus::accept(SHAMap::pointer set)
|
|||||||
|
|
||||||
ScopedLock sl = theApp->getMasterLedger().getLock();
|
ScopedLock sl = theApp->getMasterLedger().getLock();
|
||||||
|
|
||||||
applyTransactions(theApp->getMasterLedger().getCurrentLedger()->peekTransactionMap(),
|
applyTransactions(theApp->getMasterLedger().getCurrentLedger()->peekTransactionMap(), newOL, failedTransactions);
|
||||||
newOL, failedTransactions);
|
|
||||||
theApp->getMasterLedger().pushLedger(newLCL, newOL);
|
theApp->getMasterLedger().pushLedger(newLCL, newOL);
|
||||||
mState = lcsACCEPTED;
|
mState = lcsACCEPTED;
|
||||||
|
|
||||||
|
|||||||
@@ -12,6 +12,7 @@
|
|||||||
#include "LedgerAcquire.h"
|
#include "LedgerAcquire.h"
|
||||||
#include "LedgerProposal.h"
|
#include "LedgerProposal.h"
|
||||||
#include "Peer.h"
|
#include "Peer.h"
|
||||||
|
#include "CanonicalTXSet.h"
|
||||||
|
|
||||||
class TransactionAcquire : public PeerSet, public boost::enable_shared_from_this<TransactionAcquire>
|
class TransactionAcquire : public PeerSet, public boost::enable_shared_from_this<TransactionAcquire>
|
||||||
{ // A transaction set we are trying to acquire
|
{ // A transaction set we are trying to acquire
|
||||||
@@ -113,7 +114,7 @@ protected:
|
|||||||
void removePosition(LedgerProposal&, bool ours);
|
void removePosition(LedgerProposal&, bool ours);
|
||||||
void sendHaveTxSet(const uint256& set, bool direct);
|
void sendHaveTxSet(const uint256& set, bool direct);
|
||||||
void applyTransactions(SHAMap::pointer transactionSet, Ledger::pointer targetLedger,
|
void applyTransactions(SHAMap::pointer transactionSet, Ledger::pointer targetLedger,
|
||||||
std::list<SerializedTransaction::pointer>& failedTransactions);
|
CanonicalTXSet& failedTransactions);
|
||||||
|
|
||||||
// manipulating our own position
|
// manipulating our own position
|
||||||
void takeInitialPosition(Ledger::pointer initialLedger);
|
void takeInitialPosition(Ledger::pointer initialLedger);
|
||||||
|
|||||||
Reference in New Issue
Block a user