mirror of
https://github.com/Xahau/xahaud.git
synced 2025-12-06 17:27:52 +00:00
Cleanup and simplifications to SHAMap:
SHAMapTreeNode * Remove SHAMapTreeNode::pointer and SHAMapTreeNode::ref. * Add std includes necessary to make the header standalone. * Remove implementation from the SHAMapTreeNode declaration. * Make clear what part of SHAMapTreeNode is: 1) Truly public. 2) Used only by SHAMap. 3) Truly private to SHAMapTreeNode. SHAMapItem * Remove SHAMapItem::pointer and SHAMapItem::ref. * Add std includes necessary to make the header standalone. * Remove implementation from the SHAMapItem declaration. * Make clear what part of SHAMapItem is: 1) Truly public. 2) Used only by SHAMapTreeNode. 3) Truly private to SHAMapItem. SHAMapSyncFilter * Add override for SHAMapSyncFilter-derived functions. * Add missing header. * Default the destructor and delete the SHAMapSyncFilter copy members. SHAMapNodeID * Remove unused mHash member. * Remove unused std::hash and boost::hash specializations. * Remove unused constructor. * Remove unused comparison with uint256. * Remove unused getNodeID (int depth, uint256 const& hash). * Remove virtual specifier from getString(). * Fix operator<= and operator>=. * Document what API is used outside of SHAMap. * Move inline definitions outside of the class declaration. SHAMapMissingNode * Make SHAMapType a enum class to prevent unwanted conversions. * Remove needless ~SHAMapMissingNode() declaration/definition. * Add referenced std includes. SHAMapAddNode * Make SHAMapAddNode (int good, int bad, int duplicate) ctor private. * Move all member function definitions out of the class declaration. * Remove dependence on beast::lexicalCastThrow. * Make getGood() const. * Make get() const. * Add #include <string>. SHAMap * Remove unused enum STATE_MAP_BUCKETS. * Remove unused getCountedObjectName(). * Remove SHAMap::pointer * Remove SHAMap::ref * Remove unused fetchPackEntry_t. * Remove inline member function definitions from class declaration. * Remove unused getTrustedPath. * Remove unused getPath. * Remove unused visitLeavesInternal. * Make SHAMapState an enum class. * Explicitly delete SHAMap copy members. * Reduce access to nested types as much as possible. * Normalize member data names to one style. * Change last of the typedefs to usings under shamap. * Reorder some includes ripple-first, beast-second. * Declare a few constructions from make_shared with auto. * Mark those SHAMap member functions which can be, with const. * Add missing includes
This commit is contained in:
committed by
Vinnie Falco
parent
315a8b6b60
commit
ec1e6b9385
@@ -18,6 +18,7 @@
|
||||
//==============================================================================
|
||||
|
||||
#include <BeastConfig.h>
|
||||
#include <beast/module/core/text/LexicalCast.h>
|
||||
#include <ripple/app/consensus/DisputedTx.h>
|
||||
#include <ripple/app/consensus/LedgerConsensus.h>
|
||||
#include <ripple/app/ledger/InboundLedgers.h>
|
||||
@@ -319,7 +320,8 @@ public:
|
||||
@return Pointer to the transaction tree if we got it, else
|
||||
nullptr.
|
||||
*/
|
||||
SHAMap::pointer getTransactionTree (uint256 const& hash, bool doAcquire)
|
||||
std::shared_ptr<SHAMap>
|
||||
getTransactionTree (uint256 const& hash, bool doAcquire)
|
||||
{
|
||||
auto it = mAcquired.find (hash);
|
||||
|
||||
@@ -328,7 +330,7 @@ public:
|
||||
|
||||
if (mState == lcsPRE_CLOSE)
|
||||
{
|
||||
SHAMap::pointer currentMap
|
||||
std::shared_ptr<SHAMap> currentMap
|
||||
= getApp().getLedgerMaster ().getCurrentLedger ()
|
||||
->peekTransactionMap ();
|
||||
|
||||
@@ -350,8 +352,8 @@ public:
|
||||
{
|
||||
if (hash.isZero ())
|
||||
{
|
||||
SHAMap::pointer empty = std::make_shared<SHAMap> (
|
||||
smtTRANSACTION, getApp().family(),
|
||||
auto empty = std::make_shared<SHAMap> (
|
||||
SHAMapType::TRANSACTION, getApp().family(),
|
||||
deprecatedLogs().journal("SHAMap"));
|
||||
mapCompleteInternal (hash, empty, false);
|
||||
return empty;
|
||||
@@ -362,7 +364,7 @@ public:
|
||||
}
|
||||
}
|
||||
|
||||
return SHAMap::pointer ();
|
||||
return std::shared_ptr<SHAMap> ();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -372,7 +374,8 @@ public:
|
||||
@param map the transaction set.
|
||||
@param acquired true if we have acquired the transaction set.
|
||||
*/
|
||||
void mapComplete (uint256 const& hash, SHAMap::ref map, bool acquired)
|
||||
void mapComplete (uint256 const& hash, std::shared_ptr<SHAMap> const& map,
|
||||
bool acquired)
|
||||
{
|
||||
try
|
||||
{
|
||||
@@ -387,7 +390,8 @@ public:
|
||||
}
|
||||
}
|
||||
|
||||
void mapCompleteInternal (uint256 const& hash, SHAMap::ref map, bool acquired)
|
||||
void mapCompleteInternal (uint256 const& hash,
|
||||
std::shared_ptr<SHAMap> const& map, bool acquired)
|
||||
{
|
||||
CondLog (acquired, lsINFO, LedgerConsensus)
|
||||
<< "We have acquired TXS " << hash;
|
||||
@@ -904,7 +908,7 @@ public:
|
||||
<< newPosition->getCurrentHash ();
|
||||
currentPosition = newPosition;
|
||||
|
||||
SHAMap::pointer set
|
||||
std::shared_ptr<SHAMap> set
|
||||
= getTransactionTree (newPosition->getCurrentHash (), true);
|
||||
|
||||
if (set)
|
||||
@@ -998,7 +1002,7 @@ private:
|
||||
|
||||
@param set Our consensus set
|
||||
*/
|
||||
void accept (SHAMap::pointer set)
|
||||
void accept (std::shared_ptr<SHAMap> set)
|
||||
{
|
||||
|
||||
{
|
||||
@@ -1282,7 +1286,8 @@ private:
|
||||
@param m1 One transaction set
|
||||
@param m2 The other transaction set
|
||||
*/
|
||||
void createDisputes (SHAMap::ref m1, SHAMap::ref m2)
|
||||
void createDisputes (std::shared_ptr<SHAMap> const& m1,
|
||||
std::shared_ptr<SHAMap> const& m2)
|
||||
{
|
||||
if (m1->getHash() == m2->getHash())
|
||||
return;
|
||||
@@ -1381,7 +1386,8 @@ private:
|
||||
@param map A disputed position
|
||||
@param peers peers which are taking the position map
|
||||
*/
|
||||
void adjustCount (SHAMap::ref map, const std::vector<NodeID>& peers)
|
||||
void adjustCount (std::shared_ptr<SHAMap> const& map,
|
||||
const std::vector<NodeID>& peers)
|
||||
{
|
||||
for (auto& it : mDisputes)
|
||||
{
|
||||
@@ -1512,13 +1518,13 @@ private:
|
||||
*/
|
||||
void takeInitialPosition (Ledger& initialLedger)
|
||||
{
|
||||
SHAMap::pointer initialSet;
|
||||
std::shared_ptr<SHAMap> initialSet;
|
||||
|
||||
if ((getConfig ().RUN_STANDALONE || (mProposing && mHaveCorrectLCL))
|
||||
&& ((mPreviousLedger->getLedgerSeq () % 256) == 0))
|
||||
{
|
||||
// previous ledger was flag ledger
|
||||
SHAMap::pointer preSet
|
||||
std::shared_ptr<SHAMap> preSet
|
||||
= initialLedger.peekTransactionMap ()->snapShot (true);
|
||||
m_feeVote.doVoting (mPreviousLedger, preSet);
|
||||
getApp().getAmendmentTable ().doVoting (mPreviousLedger, preSet);
|
||||
@@ -1604,7 +1610,7 @@ private:
|
||||
peerCutoff -= boost::posix_time::seconds (PROPOSE_FRESHNESS);
|
||||
|
||||
bool changes = false;
|
||||
SHAMap::pointer ourPosition;
|
||||
std::shared_ptr<SHAMap> ourPosition;
|
||||
// std::vector<uint256> addedTx, removedTx;
|
||||
|
||||
// Verify freshness of peer positions and compute close times
|
||||
@@ -1889,7 +1895,7 @@ private:
|
||||
*/
|
||||
void beginAccept (bool synchronous)
|
||||
{
|
||||
SHAMap::pointer consensusSet
|
||||
std::shared_ptr<SHAMap> consensusSet
|
||||
= mAcquired[mOurPosition->getCurrentHash ()];
|
||||
|
||||
if (!consensusSet)
|
||||
@@ -1963,7 +1969,7 @@ private:
|
||||
hash_map<NodeID, LedgerProposal::pointer> mPeerPositions;
|
||||
|
||||
// Transaction Sets, indexed by hash of transaction tree
|
||||
hash_map<uint256, SHAMap::pointer> mAcquired;
|
||||
hash_map<uint256, std::shared_ptr<SHAMap>> mAcquired;
|
||||
hash_map<uint256, TransactionAcquire::pointer> mAcquiring;
|
||||
|
||||
// Peer sets
|
||||
@@ -2069,15 +2075,15 @@ int applyTransaction (TransactionEngine& engine
|
||||
@param retriableTransactions collect failed transactions in this set
|
||||
@param openLgr true if applyLedger is open, else false.
|
||||
*/
|
||||
void applyTransactions (SHAMap::ref set, Ledger::ref applyLedger,
|
||||
Ledger::ref checkLedger, CanonicalTXSet& retriableTransactions,
|
||||
bool openLgr)
|
||||
void applyTransactions (std::shared_ptr<SHAMap> const& set,
|
||||
Ledger::ref applyLedger, Ledger::ref checkLedger,
|
||||
CanonicalTXSet& retriableTransactions, bool openLgr)
|
||||
{
|
||||
TransactionEngine engine (applyLedger);
|
||||
|
||||
if (set)
|
||||
{
|
||||
for (SHAMapItem::pointer item = set->peekFirstItem (); !!item;
|
||||
for (std::shared_ptr<SHAMapItem> item = set->peekFirstItem (); !!item;
|
||||
item = set->peekNextItem (item->getTag ()))
|
||||
{
|
||||
// If the checkLedger doesn't have the transaction
|
||||
|
||||
@@ -53,11 +53,11 @@ public:
|
||||
|
||||
virtual uint256 getLCL () = 0;
|
||||
|
||||
virtual SHAMap::pointer getTransactionTree (uint256 const& hash,
|
||||
virtual std::shared_ptr<SHAMap> getTransactionTree (uint256 const& hash,
|
||||
bool doAcquire) = 0;
|
||||
|
||||
virtual void mapComplete (uint256 const& hash, SHAMap::ref map,
|
||||
bool acquired) = 0;
|
||||
virtual void mapComplete (uint256 const& hash,
|
||||
std::shared_ptr<SHAMap> const& map, bool acquired) = 0;
|
||||
|
||||
virtual bool stillNeedTXSet (uint256 const& hash) = 0;
|
||||
|
||||
@@ -97,7 +97,7 @@ make_LedgerConsensus (LedgerConsensus::clock_type& clock, LocalTxs& localtx,
|
||||
std::uint32_t closeTime, FeeVote& feeVote);
|
||||
|
||||
void
|
||||
applyTransactions(SHAMap::ref set, Ledger::ref applyLedger,
|
||||
applyTransactions(std::shared_ptr<SHAMap> const& set, Ledger::ref applyLedger,
|
||||
Ledger::ref checkLedger,
|
||||
CanonicalTXSet& retriableTransactions, bool openLgr);
|
||||
|
||||
|
||||
@@ -35,7 +35,7 @@ AcceptedLedger::AcceptedLedger (Ledger::ref ledger) : mLedger (ledger)
|
||||
{
|
||||
SHAMap& txSet = *ledger->peekTransactionMap ();
|
||||
|
||||
for (SHAMapItem::pointer item = txSet.peekFirstItem (); item;
|
||||
for (std::shared_ptr<SHAMapItem> item = txSet.peekFirstItem (); item;
|
||||
item = txSet.peekNextItem (item->getTag ()))
|
||||
{
|
||||
SerialIter sit (item->peekSerializer ());
|
||||
|
||||
@@ -36,11 +36,11 @@ public:
|
||||
SHAMapNodeID const& id,
|
||||
uint256 const& nodeHash,
|
||||
Blob& nodeData,
|
||||
SHAMapTreeNode::TNType);
|
||||
SHAMapTreeNode::TNType) override;
|
||||
|
||||
bool haveNode (SHAMapNodeID const& id,
|
||||
uint256 const& nodeHash,
|
||||
Blob& nodeData);
|
||||
Blob& nodeData) override;
|
||||
};
|
||||
|
||||
} // ripple
|
||||
|
||||
@@ -43,11 +43,11 @@ public:
|
||||
SHAMapNodeID const& id,
|
||||
uint256 const& nodeHash,
|
||||
Blob& nodeData,
|
||||
SHAMapTreeNode::TNType);
|
||||
SHAMapTreeNode::TNType) override;
|
||||
|
||||
bool haveNode (SHAMapNodeID const& id,
|
||||
uint256 const& nodeHash,
|
||||
Blob& nodeData);
|
||||
Blob& nodeData) override;
|
||||
|
||||
private:
|
||||
NodeCache& m_nodeCache;
|
||||
|
||||
@@ -20,6 +20,7 @@
|
||||
#include <BeastConfig.h>
|
||||
#include <ripple/app/ledger/DirectoryEntryIterator.h>
|
||||
#include <ripple/basics/Log.h>
|
||||
#include <ripple/protocol/JsonFields.h>
|
||||
|
||||
namespace ripple {
|
||||
|
||||
|
||||
@@ -24,6 +24,7 @@
|
||||
#include <ripple/basics/Log.h>
|
||||
#include <ripple/core/JobQueue.h>
|
||||
#include <beast/cxx14/memory.h> // <memory>
|
||||
#include <beast/module/core/text/LexicalCast.h>
|
||||
|
||||
namespace ripple {
|
||||
|
||||
|
||||
@@ -42,6 +42,7 @@
|
||||
#include <ripple/json/to_string.h>
|
||||
#include <ripple/nodestore/Database.h>
|
||||
#include <ripple/protocol/HashPrefix.h>
|
||||
#include <beast/module/core/text/LexicalCast.h>
|
||||
#include <beast/unit_test/suite.h>
|
||||
|
||||
namespace ripple {
|
||||
@@ -58,9 +59,9 @@ Ledger::Ledger (RippleAddress const& masterID, std::uint64_t startAmount)
|
||||
, mValidHash (false)
|
||||
, mAccepted (false)
|
||||
, mImmutable (false)
|
||||
, mTransactionMap (std::make_shared <SHAMap> (smtTRANSACTION,
|
||||
, mTransactionMap (std::make_shared <SHAMap> (SHAMapType::TRANSACTION,
|
||||
getApp().family(), deprecatedLogs().journal("SHAMap")))
|
||||
, mAccountStateMap (std::make_shared <SHAMap> (smtSTATE,
|
||||
, mAccountStateMap (std::make_shared <SHAMap> (SHAMapType::STATE,
|
||||
getApp().family(), deprecatedLogs().journal("SHAMap")))
|
||||
{
|
||||
// special case: put coins in root account
|
||||
@@ -104,9 +105,9 @@ Ledger::Ledger (uint256 const& parentHash,
|
||||
, mAccepted (false)
|
||||
, mImmutable (true)
|
||||
, mTransactionMap (std::make_shared <SHAMap> (
|
||||
smtTRANSACTION, transHash, getApp().family(),
|
||||
SHAMapType::TRANSACTION, transHash, getApp().family(),
|
||||
deprecatedLogs().journal("SHAMap")))
|
||||
, mAccountStateMap (std::make_shared <SHAMap> (smtSTATE, accountHash,
|
||||
, mAccountStateMap (std::make_shared <SHAMap> (SHAMapType::STATE, accountHash,
|
||||
getApp().family(), deprecatedLogs().journal("SHAMap")))
|
||||
{
|
||||
updateHash ();
|
||||
@@ -167,7 +168,7 @@ Ledger::Ledger (bool /* dummy */,
|
||||
, mValidHash (false)
|
||||
, mAccepted (false)
|
||||
, mImmutable (false)
|
||||
, mTransactionMap (std::make_shared <SHAMap> (smtTRANSACTION,
|
||||
, mTransactionMap (std::make_shared <SHAMap> (SHAMapType::TRANSACTION,
|
||||
getApp().family(), deprecatedLogs().journal("SHAMap")))
|
||||
, mAccountStateMap (prevLedger.mAccountStateMap->snapShot (true))
|
||||
{
|
||||
@@ -236,10 +237,10 @@ Ledger::Ledger (std::uint32_t ledgerSeq, std::uint32_t closeTime)
|
||||
mAccepted (false),
|
||||
mImmutable (false),
|
||||
mTransactionMap (std::make_shared <SHAMap> (
|
||||
smtTRANSACTION, getApp().family(),
|
||||
SHAMapType::TRANSACTION, getApp().family(),
|
||||
deprecatedLogs().journal("SHAMap"))),
|
||||
mAccountStateMap (std::make_shared <SHAMap> (
|
||||
smtSTATE, getApp().family(),
|
||||
SHAMapType::STATE, getApp().family(),
|
||||
deprecatedLogs().journal("SHAMap")))
|
||||
{
|
||||
initializeFees ();
|
||||
@@ -340,9 +341,9 @@ void Ledger::setRaw (Serializer& s, bool hasPrefix)
|
||||
|
||||
if (mValidHash)
|
||||
{
|
||||
mTransactionMap = std::make_shared<SHAMap> (smtTRANSACTION, mTransHash,
|
||||
mTransactionMap = std::make_shared<SHAMap> (SHAMapType::TRANSACTION, mTransHash,
|
||||
getApp().family(), deprecatedLogs().journal("SHAMap"));
|
||||
mAccountStateMap = std::make_shared<SHAMap> (smtSTATE, mAccountHash,
|
||||
mAccountStateMap = std::make_shared<SHAMap> (SHAMapType::STATE, mAccountHash,
|
||||
getApp().family(), deprecatedLogs().journal("SHAMap"));
|
||||
}
|
||||
}
|
||||
@@ -454,7 +455,7 @@ bool Ledger::addTransaction (
|
||||
Transaction::pointer Ledger::getTransaction (uint256 const& transID) const
|
||||
{
|
||||
SHAMapTreeNode::TNType type;
|
||||
SHAMapItem::pointer item = mTransactionMap->peekItem (transID, type);
|
||||
std::shared_ptr<SHAMapItem> item = mTransactionMap->peekItem (transID, type);
|
||||
|
||||
if (!item)
|
||||
return Transaction::pointer ();
|
||||
@@ -490,7 +491,7 @@ Transaction::pointer Ledger::getTransaction (uint256 const& transID) const
|
||||
}
|
||||
|
||||
STTx::pointer Ledger::getSTransaction (
|
||||
SHAMapItem::ref item, SHAMapTreeNode::TNType type)
|
||||
std::shared_ptr<SHAMapItem> const& item, SHAMapTreeNode::TNType type)
|
||||
{
|
||||
SerialIter sit (item->peekSerializer ());
|
||||
|
||||
@@ -508,7 +509,7 @@ STTx::pointer Ledger::getSTransaction (
|
||||
}
|
||||
|
||||
STTx::pointer Ledger::getSMTransaction (
|
||||
SHAMapItem::ref item, SHAMapTreeNode::TNType type,
|
||||
std::shared_ptr<SHAMapItem> const& item, SHAMapTreeNode::TNType type,
|
||||
TransactionMetaSet::pointer& txMeta) const
|
||||
{
|
||||
SerialIter sit (item->peekSerializer ());
|
||||
@@ -537,7 +538,7 @@ bool Ledger::getTransaction (
|
||||
TransactionMetaSet::pointer& meta) const
|
||||
{
|
||||
SHAMapTreeNode::TNType type;
|
||||
SHAMapItem::pointer item = mTransactionMap->peekItem (txID, type);
|
||||
std::shared_ptr<SHAMapItem> item = mTransactionMap->peekItem (txID, type);
|
||||
|
||||
if (!item)
|
||||
return false;
|
||||
@@ -582,7 +583,7 @@ bool Ledger::getTransactionMeta (
|
||||
uint256 const& txID, TransactionMetaSet::pointer& meta) const
|
||||
{
|
||||
SHAMapTreeNode::TNType type;
|
||||
SHAMapItem::pointer item = mTransactionMap->peekItem (txID, type);
|
||||
std::shared_ptr<SHAMapItem> item = mTransactionMap->peekItem (txID, type);
|
||||
|
||||
if (!item)
|
||||
return false;
|
||||
@@ -600,7 +601,7 @@ bool Ledger::getTransactionMeta (
|
||||
bool Ledger::getMetaHex (uint256 const& transID, std::string& hex) const
|
||||
{
|
||||
SHAMapTreeNode::TNType type;
|
||||
SHAMapItem::pointer item = mTransactionMap->peekItem (transID, type);
|
||||
std::shared_ptr<SHAMapItem> item = mTransactionMap->peekItem (transID, type);
|
||||
|
||||
if (!item)
|
||||
return false;
|
||||
@@ -1204,7 +1205,7 @@ LedgerStateParms Ledger::writeBack (LedgerStateParms parms, SLE::ref entry)
|
||||
|
||||
SLE::pointer Ledger::getSLE (uint256 const& uHash) const
|
||||
{
|
||||
SHAMapItem::pointer node = mAccountStateMap->peekItem (uHash);
|
||||
std::shared_ptr<SHAMapItem> node = mAccountStateMap->peekItem (uHash);
|
||||
|
||||
if (!node)
|
||||
return SLE::pointer ();
|
||||
@@ -1216,7 +1217,7 @@ SLE::pointer Ledger::getSLEi (uint256 const& uId) const
|
||||
{
|
||||
uint256 hash;
|
||||
|
||||
SHAMapItem::pointer node = mAccountStateMap->peekItem (uId, hash);
|
||||
std::shared_ptr<SHAMapItem> node = mAccountStateMap->peekItem (uId, hash);
|
||||
|
||||
if (!node)
|
||||
return SLE::pointer ();
|
||||
@@ -1346,7 +1347,7 @@ bool Ledger::visitAccountItems (
|
||||
}
|
||||
|
||||
static void visitHelper (
|
||||
std::function<void (SLE::ref)>& function, SHAMapItem::ref item)
|
||||
std::function<void (SLE::ref)>& function, std::shared_ptr<SHAMapItem> const& item)
|
||||
{
|
||||
function (std::make_shared<SLE> (item->peekSerializer (), item->getTag ()));
|
||||
}
|
||||
@@ -1375,25 +1376,25 @@ void Ledger::visitStateItems (std::function<void (SLE::ref)> function) const
|
||||
|
||||
uint256 Ledger::getFirstLedgerIndex () const
|
||||
{
|
||||
SHAMapItem::pointer node = mAccountStateMap->peekFirstItem ();
|
||||
std::shared_ptr<SHAMapItem> node = mAccountStateMap->peekFirstItem ();
|
||||
return node ? node->getTag () : uint256 ();
|
||||
}
|
||||
|
||||
uint256 Ledger::getLastLedgerIndex () const
|
||||
{
|
||||
SHAMapItem::pointer node = mAccountStateMap->peekLastItem ();
|
||||
std::shared_ptr<SHAMapItem> node = mAccountStateMap->peekLastItem ();
|
||||
return node ? node->getTag () : uint256 ();
|
||||
}
|
||||
|
||||
uint256 Ledger::getNextLedgerIndex (uint256 const& uHash) const
|
||||
{
|
||||
SHAMapItem::pointer node = mAccountStateMap->peekNextItem (uHash);
|
||||
std::shared_ptr<SHAMapItem> node = mAccountStateMap->peekNextItem (uHash);
|
||||
return node ? node->getTag () : uint256 ();
|
||||
}
|
||||
|
||||
uint256 Ledger::getNextLedgerIndex (uint256 const& uHash, uint256 const& uEnd) const
|
||||
{
|
||||
SHAMapItem::pointer node = mAccountStateMap->peekNextItem (uHash);
|
||||
std::shared_ptr<SHAMapItem> node = mAccountStateMap->peekNextItem (uHash);
|
||||
|
||||
if ((!node) || (node->getTag () > uEnd))
|
||||
return uint256 ();
|
||||
@@ -1403,13 +1404,13 @@ uint256 Ledger::getNextLedgerIndex (uint256 const& uHash, uint256 const& uEnd) c
|
||||
|
||||
uint256 Ledger::getPrevLedgerIndex (uint256 const& uHash) const
|
||||
{
|
||||
SHAMapItem::pointer node = mAccountStateMap->peekPrevItem (uHash);
|
||||
std::shared_ptr<SHAMapItem> node = mAccountStateMap->peekPrevItem (uHash);
|
||||
return node ? node->getTag () : uint256 ();
|
||||
}
|
||||
|
||||
uint256 Ledger::getPrevLedgerIndex (uint256 const& uHash, uint256 const& uBegin) const
|
||||
{
|
||||
SHAMapItem::pointer node = mAccountStateMap->peekNextItem (uHash);
|
||||
std::shared_ptr<SHAMapItem> node = mAccountStateMap->peekNextItem (uHash);
|
||||
|
||||
if ((!node) || (node->getTag () < uBegin))
|
||||
return uint256 ();
|
||||
@@ -1430,7 +1431,7 @@ SLE::pointer Ledger::getASNodeI (uint256 const& nodeID, LedgerEntryType let) con
|
||||
SLE::pointer Ledger::getASNode (
|
||||
LedgerStateParms& parms, uint256 const& nodeID, LedgerEntryType let) const
|
||||
{
|
||||
SHAMapItem::pointer account = mAccountStateMap->peekItem (nodeID);
|
||||
std::shared_ptr<SHAMapItem> account = mAccountStateMap->peekItem (nodeID);
|
||||
|
||||
if (!account)
|
||||
{
|
||||
|
||||
@@ -251,11 +251,11 @@ public:
|
||||
boost::posix_time::ptime getCloseTime () const;
|
||||
|
||||
// low level functions
|
||||
SHAMap::ref peekTransactionMap () const
|
||||
std::shared_ptr<SHAMap> const& peekTransactionMap () const
|
||||
{
|
||||
return mTransactionMap;
|
||||
}
|
||||
SHAMap::ref peekAccountStateMap () const
|
||||
std::shared_ptr<SHAMap> const& peekAccountStateMap () const
|
||||
{
|
||||
return mAccountStateMap;
|
||||
}
|
||||
@@ -286,9 +286,9 @@ public:
|
||||
bool getMetaHex (uint256 const& transID, std::string & hex) const;
|
||||
|
||||
static STTx::pointer getSTransaction (
|
||||
SHAMapItem::ref, SHAMapTreeNode::TNType);
|
||||
std::shared_ptr<SHAMapItem> const&, SHAMapTreeNode::TNType);
|
||||
STTx::pointer getSMTransaction (
|
||||
SHAMapItem::ref, SHAMapTreeNode::TNType,
|
||||
std::shared_ptr<SHAMapItem> const&, SHAMapTreeNode::TNType,
|
||||
TransactionMetaSet::pointer & txMeta) const;
|
||||
|
||||
// high-level functions
|
||||
@@ -486,8 +486,8 @@ private:
|
||||
// Ripple cost of the reference transaction
|
||||
std::uint64_t mBaseFee;
|
||||
|
||||
SHAMap::pointer mTransactionMap;
|
||||
SHAMap::pointer mAccountStateMap;
|
||||
std::shared_ptr<SHAMap> mTransactionMap;
|
||||
std::shared_ptr<SHAMap> mAccountStateMap;
|
||||
|
||||
typedef RippleMutex StaticLockType;
|
||||
typedef std::lock_guard <StaticLockType> StaticScopedLockType;
|
||||
|
||||
@@ -1,330 +0,0 @@
|
||||
//------------------------------------------------------------------------------
|
||||
/*
|
||||
This file is part of rippled: https://github.com/ripple/rippled
|
||||
Copyright (c) 2012, 2013 Ripple Labs Inc.
|
||||
|
||||
Permission to use, copy, modify, and/or distribute this software for any
|
||||
purpose with or without fee is hereby granted, provided that the above
|
||||
copyright notice and this permission notice appear in all copies.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||
WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||
MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||
ANY SPECIAL , DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||
WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
||||
ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
||||
OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
*/
|
||||
//==============================================================================
|
||||
|
||||
#include <ripple/app/ledger/Ledger.h>
|
||||
#include <ripple/app/consensus/LedgerConsensus.h>
|
||||
#include <ripple/app/ledger/LedgerTiming.h>
|
||||
#include <ripple/app/misc/CanonicalTXSet.h>
|
||||
#include <ripple/app/transactors/Transactor.h>
|
||||
#include <ripple/basics/seconds_clock.h>
|
||||
#include <ripple/protocol/Indexes.h>
|
||||
#include <ripple/protocol/RippleAddress.h>
|
||||
#include <ripple/protocol/STParsedJSON.h>
|
||||
#include <ripple/protocol/TxFlags.h>
|
||||
#include <beast/unit_test/suite.h>
|
||||
|
||||
namespace ripple {
|
||||
|
||||
class Ledger_test : public beast::unit_test::suite
|
||||
{
|
||||
using TestAccount = std::pair<RippleAddress, unsigned>;
|
||||
|
||||
struct Amount
|
||||
{
|
||||
Amount (double value_, std::string currency_, TestAccount issuer_)
|
||||
: value(value_)
|
||||
, currency(currency_)
|
||||
, issuer(issuer_)
|
||||
{
|
||||
}
|
||||
|
||||
double value;
|
||||
std::string currency;
|
||||
TestAccount issuer;
|
||||
|
||||
Json::Value
|
||||
getJson() const
|
||||
{
|
||||
Json::Value tx_json;
|
||||
tx_json[jss::currency] = currency;
|
||||
tx_json[jss::issuer] = issuer.first.humanAccountID();
|
||||
tx_json[jss::value] = std::to_string(value);
|
||||
return tx_json;
|
||||
}
|
||||
};
|
||||
|
||||
// Helper function to parse a transaction in Json, sign it with account,
|
||||
// and return it as a STTx
|
||||
STTx
|
||||
parseTransaction(TestAccount& account, Json::Value const& tx_json)
|
||||
{
|
||||
STParsedJSONObject parsed (std::string (jss::tx_json), tx_json);
|
||||
std::unique_ptr<STObject> sopTrans = std::move(parsed.object);
|
||||
expect(sopTrans != nullptr);
|
||||
sopTrans->setFieldVL(sfSigningPubKey, account.first.getAccountPublic());
|
||||
return STTx(*sopTrans);
|
||||
}
|
||||
|
||||
// Helper function to apply a transaction to a ledger
|
||||
void
|
||||
applyTransaction(Ledger::pointer const& ledger, STTx const& tx)
|
||||
{
|
||||
TransactionEngine engine(ledger);
|
||||
bool didApply = false;
|
||||
auto r = engine.applyTransaction(tx, tapOPEN_LEDGER | tapNO_CHECK_SIGN,
|
||||
didApply);
|
||||
expect(r == tesSUCCESS);
|
||||
expect(didApply);
|
||||
}
|
||||
|
||||
// Create genesis ledger from a start amount in drops, and the public
|
||||
// master RippleAddress
|
||||
Ledger::pointer
|
||||
createGenesisLedger(std::uint64_t start_amount_drops, TestAccount const& master)
|
||||
{
|
||||
Ledger::pointer ledger = std::make_shared<Ledger>(master.first,
|
||||
start_amount_drops);
|
||||
ledger->updateHash();
|
||||
ledger->setClosed();
|
||||
expect(ledger->assertSane());
|
||||
return ledger;
|
||||
}
|
||||
|
||||
// Create an account represented by public RippleAddress and private
|
||||
// RippleAddress
|
||||
TestAccount
|
||||
createAccount()
|
||||
{
|
||||
static RippleAddress const seed
|
||||
= RippleAddress::createSeedGeneric ("masterpassphrase");
|
||||
static RippleAddress const generator
|
||||
= RippleAddress::createGeneratorPublic (seed);
|
||||
static int iSeq = -1;
|
||||
++iSeq;
|
||||
return std::make_pair(RippleAddress::createAccountPublic(generator, iSeq),
|
||||
std::uint64_t(0));
|
||||
}
|
||||
|
||||
void
|
||||
freezeAccount(TestAccount& account, Ledger::pointer const& ledger)
|
||||
{
|
||||
Json::Value tx_json;
|
||||
tx_json[jss::TransactionType] = "AccountSet";
|
||||
tx_json[jss::Fee] = std::to_string(10);
|
||||
tx_json[jss::Account] = account.first.humanAccountID();
|
||||
tx_json[jss::SetFlag] = asfGlobalFreeze;
|
||||
tx_json[jss::Sequence] = ++account.second;
|
||||
STTx tx = parseTransaction(account, tx_json);
|
||||
applyTransaction(ledger, tx);
|
||||
}
|
||||
|
||||
void
|
||||
unfreezeAccount(TestAccount& account, Ledger::pointer const& ledger)
|
||||
{
|
||||
Json::Value tx_json;
|
||||
tx_json[jss::TransactionType] = "AccountSet";
|
||||
tx_json[jss::Fee] = std::to_string(10);
|
||||
tx_json[jss::Account] = account.first.humanAccountID();
|
||||
tx_json[jss::ClearFlag] = asfGlobalFreeze;
|
||||
tx_json[jss::Sequence] = ++account.second;
|
||||
STTx tx = parseTransaction(account, tx_json);
|
||||
applyTransaction(ledger, tx);
|
||||
}
|
||||
|
||||
void
|
||||
makePayment(TestAccount& from, TestAccount const& to,
|
||||
std::uint64_t amountDrops,
|
||||
Ledger::pointer const& ledger)
|
||||
{
|
||||
Json::Value tx_json;
|
||||
tx_json[jss::Account] = from.first.humanAccountID();
|
||||
tx_json[jss::Amount] = std::to_string(amountDrops);
|
||||
tx_json[jss::Destination] = to.first.humanAccountID();
|
||||
tx_json[jss::TransactionType] = "Payment";
|
||||
tx_json[jss::Fee] = std::to_string(10);
|
||||
tx_json[jss::Sequence] = ++from.second;
|
||||
tx_json[jss::Flags] = tfUniversal;
|
||||
STTx tx = parseTransaction(from, tx_json);
|
||||
applyTransaction(ledger, tx);
|
||||
}
|
||||
|
||||
void
|
||||
makePayment(TestAccount& from, TestAccount const& to,
|
||||
std::string const& currency, std::string const& amount,
|
||||
Ledger::pointer const& ledger)
|
||||
{
|
||||
Json::Value tx_json;
|
||||
tx_json[jss::Account] = from.first.humanAccountID();
|
||||
tx_json[jss::Amount] = Amount(std::stod(amount), currency, to).getJson();
|
||||
tx_json[jss::Destination] = to.first.humanAccountID();
|
||||
tx_json[jss::TransactionType] = "Payment";
|
||||
tx_json[jss::Fee] = std::to_string(10);
|
||||
tx_json[jss::Sequence] = ++from.second;
|
||||
tx_json[jss::Flags] = tfUniversal;
|
||||
STTx tx = parseTransaction(from, tx_json);
|
||||
applyTransaction(ledger, tx);
|
||||
}
|
||||
|
||||
void
|
||||
createOffer(TestAccount& from, Amount const& in, Amount const& out,
|
||||
Ledger::pointer ledger)
|
||||
{
|
||||
Json::Value tx_json;
|
||||
tx_json[jss::TransactionType] = "OfferCreate";
|
||||
tx_json[jss::Fee] = std::to_string(10);
|
||||
tx_json[jss::Account] = from.first.humanAccountID();
|
||||
tx_json[jss::TakerPays] = in.getJson();
|
||||
tx_json[jss::TakerGets] = out.getJson();
|
||||
tx_json[jss::Sequence] = ++from.second;
|
||||
STTx tx = parseTransaction(from, tx_json);
|
||||
applyTransaction(ledger, tx);
|
||||
}
|
||||
|
||||
// As currently implemented, this will cancel only the last offer made
|
||||
// from this account.
|
||||
void
|
||||
cancelOffer(TestAccount& from, Ledger::pointer ledger)
|
||||
{
|
||||
Json::Value tx_json;
|
||||
tx_json[jss::TransactionType] = "OfferCancel";
|
||||
tx_json[jss::Fee] = std::to_string(10);
|
||||
tx_json[jss::Account] = from.first.humanAccountID();
|
||||
tx_json[jss::OfferSequence] = from.second;
|
||||
tx_json[jss::Sequence] = ++from.second;
|
||||
STTx tx = parseTransaction(from, tx_json);
|
||||
applyTransaction(ledger, tx);
|
||||
}
|
||||
|
||||
void
|
||||
makeTrustSet(TestAccount& from, TestAccount const& issuer,
|
||||
std::string const& currency, double amount,
|
||||
Ledger::pointer const& ledger)
|
||||
{
|
||||
Json::Value tx_json;
|
||||
tx_json[jss::Account] = from.first.humanAccountID();
|
||||
Json::Value& limitAmount = tx_json[jss::LimitAmount];
|
||||
limitAmount[jss::currency] = currency;
|
||||
limitAmount[jss::issuer] = issuer.first.humanAccountID();
|
||||
limitAmount[jss::value] = std::to_string(amount);
|
||||
tx_json[jss::TransactionType] = "TrustSet";
|
||||
tx_json[jss::Fee] = std::to_string(10);
|
||||
tx_json[jss::Sequence] = ++from.second;
|
||||
tx_json[jss::Flags] = tfClearNoRipple;
|
||||
STTx tx = parseTransaction(from, tx_json);
|
||||
applyTransaction(ledger, tx);
|
||||
}
|
||||
|
||||
Ledger::pointer
|
||||
close_and_advance(Ledger::pointer ledger, Ledger::pointer LCL)
|
||||
{
|
||||
SHAMap::pointer set = ledger->peekTransactionMap();
|
||||
CanonicalTXSet retriableTransactions(set->getHash());
|
||||
Ledger::pointer newLCL = std::make_shared<Ledger>(false, *LCL);
|
||||
// Set up to write SHAMap changes to our database,
|
||||
// perform updates, extract changes
|
||||
applyTransactions(set, newLCL, newLCL, retriableTransactions, false);
|
||||
newLCL->updateSkipList();
|
||||
newLCL->setClosed();
|
||||
newLCL->peekAccountStateMap()->flushDirty(
|
||||
hotACCOUNT_NODE, newLCL->getLedgerSeq());
|
||||
newLCL->peekTransactionMap()->flushDirty(
|
||||
hotTRANSACTION_NODE, newLCL->getLedgerSeq());
|
||||
using namespace std::chrono;
|
||||
auto const epoch_offset = days(10957); // 2000-01-01
|
||||
std::uint32_t closeTime = time_point_cast<seconds> // now
|
||||
(system_clock::now()-epoch_offset).
|
||||
time_since_epoch().count();
|
||||
int CloseResolution = seconds(LEDGER_TIME_ACCURACY).count();
|
||||
bool closeTimeCorrect = true;
|
||||
newLCL->setAccepted(closeTime, CloseResolution, closeTimeCorrect);
|
||||
return newLCL;
|
||||
}
|
||||
|
||||
void test_genesisLedger ()
|
||||
{
|
||||
std::uint64_t const xrp = std::mega::num;
|
||||
|
||||
// Create master account
|
||||
auto master = createAccount();
|
||||
|
||||
// Create genesis ledger
|
||||
Ledger::pointer LCL = createGenesisLedger(100000*xrp, master);
|
||||
|
||||
// Create open scratch ledger
|
||||
Ledger::pointer ledger = std::make_shared<Ledger>(false, *LCL);
|
||||
|
||||
// Create user accounts
|
||||
auto gw1 = createAccount();
|
||||
auto gw2 = createAccount();
|
||||
auto gw3 = createAccount();
|
||||
auto alice = createAccount();
|
||||
auto mark = createAccount();
|
||||
|
||||
// Fund gw1, gw2, gw3, alice, mark from master
|
||||
makePayment(master, gw1, 5000*xrp, ledger);
|
||||
makePayment(master, gw2, 4000*xrp, ledger);
|
||||
makePayment(master, gw3, 3000*xrp, ledger);
|
||||
makePayment(master, alice, 2000*xrp, ledger);
|
||||
makePayment(master, mark, 1000*xrp, ledger);
|
||||
|
||||
LCL = close_and_advance(ledger, LCL);
|
||||
ledger = std::make_shared<Ledger>(false, *LCL);
|
||||
|
||||
// alice trusts FOO/gw1
|
||||
makeTrustSet(alice, gw1, "FOO", 1, ledger);
|
||||
|
||||
// mark trusts FOO/gw2
|
||||
makeTrustSet(mark, gw2, "FOO", 1, ledger);
|
||||
|
||||
// mark trusts FOO/gw3
|
||||
makeTrustSet(mark, gw3, "FOO", 1, ledger);
|
||||
|
||||
// gw2 pays mark with FOO
|
||||
makePayment(gw2, mark, "FOO", ".1", ledger);
|
||||
|
||||
// gw3 pays mark with FOO
|
||||
makePayment(gw3, mark, "FOO", ".2", ledger);
|
||||
|
||||
// gw1 pays alice with FOO
|
||||
makePayment(gw1, alice, "FOO", ".3", ledger);
|
||||
|
||||
LCL = close_and_advance(ledger, LCL);
|
||||
ledger = std::make_shared<Ledger>(false, *LCL);
|
||||
|
||||
createOffer(mark, Amount(1, "FOO", gw1), Amount(1, "FOO", gw2), ledger);
|
||||
createOffer(mark, Amount(1, "FOO", gw2), Amount(1, "FOO", gw3), ledger);
|
||||
cancelOffer(mark, ledger);
|
||||
freezeAccount(alice, ledger);
|
||||
|
||||
LCL = close_and_advance(ledger, LCL);
|
||||
ledger = std::make_shared<Ledger>(false, *LCL);
|
||||
|
||||
makePayment(alice, mark, 1*xrp, ledger);
|
||||
|
||||
LCL = close_and_advance(ledger, LCL);
|
||||
ledger = std::make_shared<Ledger>(false, *LCL);
|
||||
}
|
||||
|
||||
void test_getQuality ()
|
||||
{
|
||||
uint256 uBig (
|
||||
"D2DC44E5DC189318DB36EF87D2104CDF0A0FE3A4B698BEEE55038D7EA4C68000");
|
||||
expect (6125895493223874560 == getQuality (uBig));
|
||||
}
|
||||
public:
|
||||
void run ()
|
||||
{
|
||||
test_genesisLedger ();
|
||||
test_getQuality ();
|
||||
}
|
||||
};
|
||||
|
||||
BEAST_DEFINE_TESTSUITE(Ledger,ripple_app,ripple);
|
||||
|
||||
} // ripple
|
||||
@@ -24,6 +24,7 @@
|
||||
#include <ripple/app/ledger/LedgerMaster.h>
|
||||
#include <ripple/app/main/Application.h>
|
||||
#include <ripple/core/LoadFeeTrack.h>
|
||||
#include <ripple/protocol/JsonFields.h>
|
||||
#include <ripple/protocol/Protocol.h>
|
||||
#include <ripple/protocol/RippleLedgerHash.h>
|
||||
#include <beast/threads/Thread.h>
|
||||
|
||||
@@ -213,13 +213,13 @@ void LedgerHistory::handleMismatch (LedgerHash const& built, LedgerHash const& v
|
||||
std::vector <SHAMapItemInfo> builtTx, validTx;
|
||||
// Get built ledger hashes and metadata
|
||||
builtLedger->peekTransactionMap()->visitLeaves(
|
||||
[&builtTx](SHAMapItem::ref item)
|
||||
[&builtTx](std::shared_ptr<SHAMapItem> const& item)
|
||||
{
|
||||
builtTx.push_back({item->getTag(), item->peekData()});
|
||||
});
|
||||
// Get valid ledger hashes and metadata
|
||||
validLedger->peekTransactionMap()->visitLeaves(
|
||||
[&validTx](SHAMapItem::ref item)
|
||||
[&validTx](std::shared_ptr<SHAMapItem> const& item)
|
||||
{
|
||||
validTx.push_back({item->getTag(), item->peekData()});
|
||||
});
|
||||
|
||||
@@ -176,7 +176,7 @@ void fillJson (Object& json, LedgerFill const& fill)
|
||||
else
|
||||
{
|
||||
accountStateMap->visitLeaves(
|
||||
[&array, &count] (SHAMapItem::ref smi)
|
||||
[&array, &count] (std::shared_ptr<SHAMapItem> const& smi)
|
||||
{
|
||||
count.yield();
|
||||
array.append (to_string(smi->getTag ()));
|
||||
|
||||
@@ -63,6 +63,7 @@
|
||||
#include <ripple/validators/make_Manager.h>
|
||||
#include <ripple/unity/git_id.h>
|
||||
#include <beast/asio/io_latency_probe.h>
|
||||
#include <beast/module/core/text/LexicalCast.h>
|
||||
#include <beast/module/core/thread/DeadlineTimer.h>
|
||||
#include <boost/asio/signal_set.hpp>
|
||||
#include <fstream>
|
||||
@@ -1254,7 +1255,7 @@ bool ApplicationImp::loadOldLedger (
|
||||
if (replay)
|
||||
{
|
||||
// inject transaction(s) from the replayLedger into our open ledger
|
||||
SHAMap::ref txns = replayLedger->peekTransactionMap();
|
||||
std::shared_ptr<SHAMap> const& txns = replayLedger->peekTransactionMap();
|
||||
|
||||
// Get a mutable snapshot of the open ledger
|
||||
Ledger::pointer cur = getLedgerMaster().getCurrentLedger();
|
||||
|
||||
@@ -23,6 +23,7 @@
|
||||
#include <ripple/basics/StringUtilities.h>
|
||||
#include <ripple/json/to_string.h>
|
||||
#include <ripple/protocol/Indexes.h>
|
||||
#include <ripple/protocol/JsonFields.h>
|
||||
#include <boost/algorithm/string.hpp>
|
||||
#include <boost/format.hpp>
|
||||
|
||||
|
||||
@@ -208,7 +208,8 @@ public:
|
||||
virtual void
|
||||
doValidation (Ledger::ref lastClosedLedger, STObject& baseValidation) = 0;
|
||||
virtual void
|
||||
doVoting (Ledger::ref lastClosedLedger, SHAMap::ref initialPosition) = 0;
|
||||
doVoting (Ledger::ref lastClosedLedger,
|
||||
std::shared_ptr<SHAMap> const& initialPosition) = 0;
|
||||
};
|
||||
|
||||
std::unique_ptr<AmendmentTable> make_AmendmentTable (
|
||||
|
||||
@@ -23,6 +23,7 @@
|
||||
#include <ripple/app/misc/Validations.h>
|
||||
#include <ripple/app/data/DatabaseCon.h>
|
||||
#include <ripple/core/ConfigSections.h>
|
||||
#include <ripple/protocol/JsonFields.h>
|
||||
#include <boost/format.hpp>
|
||||
#include <boost/tokenizer.hpp>
|
||||
#include <algorithm>
|
||||
@@ -95,7 +96,8 @@ public:
|
||||
Json::Value getJson (uint256 const&) override;
|
||||
|
||||
void doValidation (Ledger::ref lastClosedLedger, STObject& baseValidation) override;
|
||||
void doVoting (Ledger::ref lastClosedLedger, SHAMap::ref initialPosition) override;
|
||||
void doVoting (Ledger::ref lastClosedLedger,
|
||||
std::shared_ptr<SHAMap> const& initialPosition) override;
|
||||
|
||||
amendmentList_t getVetoed();
|
||||
amendmentList_t getEnabled();
|
||||
@@ -518,7 +520,7 @@ AmendmentTableImpl<AppApiFacade>::doValidation (Ledger::ref lastClosedLedger,
|
||||
template<class AppApiFacade>
|
||||
void
|
||||
AmendmentTableImpl<AppApiFacade>::doVoting (Ledger::ref lastClosedLedger,
|
||||
SHAMap::ref initialPosition)
|
||||
std::shared_ptr<SHAMap> const& initialPosition)
|
||||
{
|
||||
|
||||
// LCL must be flag ledger
|
||||
@@ -566,7 +568,7 @@ AmendmentTableImpl<AppApiFacade>::doVoting (Ledger::ref lastClosedLedger,
|
||||
Serializer s;
|
||||
trans.add (s, true);
|
||||
#if RIPPLE_PROPOSE_AMENDMENTS
|
||||
SHAMapItem::pointer tItem = std::make_shared<SHAMapItem> (txID, s.peekData ());
|
||||
auto tItem = std::make_shared<SHAMapItem> (txID, s.peekData ());
|
||||
if (!initialPosition->addGiveItem (tItem, true, false))
|
||||
{
|
||||
if (m_journal.warning) m_journal.warning <<
|
||||
|
||||
@@ -67,7 +67,7 @@ public:
|
||||
virtual
|
||||
void
|
||||
doVoting (Ledger::ref lastClosedLedger,
|
||||
SHAMap::ref initialPosition) = 0;
|
||||
std::shared_ptr<SHAMap> const& initialPosition) = 0;
|
||||
};
|
||||
|
||||
/** Build FeeVote::Setup from a config section. */
|
||||
|
||||
@@ -102,7 +102,7 @@ public:
|
||||
|
||||
void
|
||||
doVoting (Ledger::ref lastClosedLedger,
|
||||
SHAMap::ref initialPosition) override;
|
||||
std::shared_ptr<SHAMap> const& initialPosition) override;
|
||||
};
|
||||
|
||||
//--------------------------------------------------------------------------
|
||||
@@ -145,7 +145,7 @@ FeeVoteImpl::doValidation (Ledger::ref lastClosedLedger,
|
||||
|
||||
void
|
||||
FeeVoteImpl::doVoting (Ledger::ref lastClosedLedger,
|
||||
SHAMap::ref initialPosition)
|
||||
std::shared_ptr<SHAMap> const& initialPosition)
|
||||
{
|
||||
// LCL must be flag ledger
|
||||
assert ((lastClosedLedger->getLedgerSeq () % 256) == 0);
|
||||
@@ -228,8 +228,7 @@ FeeVoteImpl::doVoting (Ledger::ref lastClosedLedger,
|
||||
Serializer s;
|
||||
trans.add (s, true);
|
||||
|
||||
SHAMapItem::pointer tItem = std::make_shared<SHAMapItem> (
|
||||
txID, s.peekData ());
|
||||
auto tItem = std::make_shared<SHAMapItem> (txID, s.peekData ());
|
||||
|
||||
if (!initialPosition->addGiveItem (tItem, true, false))
|
||||
{
|
||||
|
||||
@@ -56,6 +56,7 @@
|
||||
#include <ripple/resource/Fees.h>
|
||||
#include <ripple/resource/Gossip.h>
|
||||
#include <ripple/resource/Manager.h>
|
||||
#include <beast/module/core/text/LexicalCast.h>
|
||||
#include <beast/module/core/thread/DeadlineTimer.h>
|
||||
#include <beast/module/core/system/SystemStats.h>
|
||||
#include <beast/cxx14/memory.h> // <memory>
|
||||
@@ -292,13 +293,13 @@ public:
|
||||
|
||||
bool recvValidation (
|
||||
STValidation::ref val, std::string const& source);
|
||||
void takePosition (int seq, SHAMap::ref position);
|
||||
SHAMap::pointer getTXMap (uint256 const& hash);
|
||||
void takePosition (int seq, std::shared_ptr<SHAMap> const& position);
|
||||
std::shared_ptr<SHAMap> getTXMap (uint256 const& hash);
|
||||
bool hasTXSet (
|
||||
const std::shared_ptr<Peer>& peer, uint256 const& set,
|
||||
protocol::TxSetStatus status);
|
||||
|
||||
void mapComplete (uint256 const& hash, SHAMap::ref map);
|
||||
void mapComplete (uint256 const& hash, std::shared_ptr<SHAMap> const& map);
|
||||
bool stillNeedTXSet (uint256 const& hash);
|
||||
void makeFetchPack (
|
||||
Job&, std::weak_ptr<Peer> peer,
|
||||
@@ -577,7 +578,7 @@ private:
|
||||
STValidation::pointer mLastValidation;
|
||||
|
||||
// Recent positions taken
|
||||
std::map<uint256, std::pair<int, SHAMap::pointer> > mRecentPositions;
|
||||
std::map<uint256, std::pair<int, std::shared_ptr<SHAMap>>> mRecentPositions;
|
||||
|
||||
SubInfoMapType mSubAccount;
|
||||
SubInfoMapType mSubRTAccount;
|
||||
@@ -1657,7 +1658,8 @@ void NetworkOPsImp::processTrustedProposal (
|
||||
}
|
||||
|
||||
// Must be called while holding the master lock
|
||||
SHAMap::pointer NetworkOPsImp::getTXMap (uint256 const& hash)
|
||||
std::shared_ptr<SHAMap>
|
||||
NetworkOPsImp::getTXMap (uint256 const& hash)
|
||||
{
|
||||
auto it = mRecentPositions.find (hash);
|
||||
|
||||
@@ -1665,13 +1667,14 @@ SHAMap::pointer NetworkOPsImp::getTXMap (uint256 const& hash)
|
||||
return it->second.second;
|
||||
|
||||
if (!haveConsensusObject ())
|
||||
return SHAMap::pointer ();
|
||||
return std::shared_ptr<SHAMap> ();
|
||||
|
||||
return mConsensus->getTransactionTree (hash, false);
|
||||
}
|
||||
|
||||
// Must be called while holding the master lock
|
||||
void NetworkOPsImp::takePosition (int seq, SHAMap::ref position)
|
||||
void
|
||||
NetworkOPsImp::takePosition (int seq, std::shared_ptr<SHAMap> const& position)
|
||||
{
|
||||
mRecentPositions[position->getHash ()] = std::make_pair (seq, position);
|
||||
|
||||
@@ -1726,7 +1729,9 @@ bool NetworkOPsImp::stillNeedTXSet (uint256 const& hash)
|
||||
return mConsensus->stillNeedTXSet (hash);
|
||||
}
|
||||
|
||||
void NetworkOPsImp::mapComplete (uint256 const& hash, SHAMap::ref map)
|
||||
void
|
||||
NetworkOPsImp::mapComplete (uint256 const& hash,
|
||||
std::shared_ptr<SHAMap> const& map)
|
||||
{
|
||||
if (haveConsensusObject ())
|
||||
mConsensus->mapComplete (hash, map, true);
|
||||
|
||||
@@ -217,14 +217,16 @@ public:
|
||||
virtual bool recvValidation (STValidation::ref val,
|
||||
std::string const& source) = 0;
|
||||
|
||||
virtual void takePosition (int seq, SHAMap::ref position) = 0;
|
||||
virtual void takePosition (int seq,
|
||||
std::shared_ptr<SHAMap> const& position) = 0;
|
||||
|
||||
virtual SHAMap::pointer getTXMap (uint256 const& hash) = 0;
|
||||
virtual std::shared_ptr<SHAMap> getTXMap (uint256 const& hash) = 0;
|
||||
|
||||
virtual bool hasTXSet (const std::shared_ptr<Peer>& peer,
|
||||
uint256 const& set, protocol::TxSetStatus status) = 0;
|
||||
|
||||
virtual void mapComplete (uint256 const& hash, SHAMap::ref map) = 0;
|
||||
virtual void mapComplete (uint256 const& hash,
|
||||
std::shared_ptr<SHAMap> const& map) = 0;
|
||||
|
||||
virtual bool stillNeedTXSet (uint256 const& hash) = 0;
|
||||
|
||||
|
||||
@@ -31,6 +31,7 @@
|
||||
#include <ripple/net/RPCErr.h>
|
||||
#include <ripple/protocol/ErrorCodes.h>
|
||||
#include <ripple/protocol/UintTypes.h>
|
||||
#include <beast/module/core/text/LexicalCast.h>
|
||||
#include <boost/log/trivial.hpp>
|
||||
#include <tuple>
|
||||
|
||||
|
||||
@@ -22,6 +22,7 @@
|
||||
#include <ripple/app/ledger/LedgerMaster.h>
|
||||
#include <ripple/app/main/Application.h>
|
||||
#include <ripple/core/JobQueue.h>
|
||||
#include <ripple/protocol/JsonFields.h>
|
||||
#include <ripple/resource/Fees.h>
|
||||
|
||||
namespace ripple {
|
||||
|
||||
@@ -23,6 +23,7 @@
|
||||
#include <ripple/basics/Log.h>
|
||||
#include <ripple/json/to_string.h>
|
||||
#include <ripple/protocol/Indexes.h>
|
||||
#include <ripple/protocol/JsonFields.h>
|
||||
#include <boost/lexical_cast.hpp>
|
||||
|
||||
namespace ripple {
|
||||
|
||||
@@ -31,6 +31,7 @@
|
||||
#include <ripple/core/Config.h>
|
||||
#include <ripple/core/LoadFeeTrack.h>
|
||||
#include <ripple/net/HTTPClient.h>
|
||||
#include <ripple/protocol/JsonFields.h>
|
||||
#include <beast/module/core/thread/DeadlineTimer.h>
|
||||
#include <beast/cxx14/memory.h> // <memory>
|
||||
#include <boost/algorithm/string.hpp>
|
||||
|
||||
@@ -234,7 +234,7 @@ makeTrustSet(TestAccount& from, TestAccount const& issuer,
|
||||
Ledger::pointer
|
||||
close_and_advance(Ledger::pointer ledger, Ledger::pointer LCL)
|
||||
{
|
||||
SHAMap::pointer set = ledger->peekTransactionMap();
|
||||
std::shared_ptr<SHAMap> set = ledger->peekTransactionMap();
|
||||
CanonicalTXSet retriableTransactions(set->getHash());
|
||||
Ledger::pointer newLCL = std::make_shared<Ledger>(false, *LCL);
|
||||
// Set up to write SHAMap changes to our database,
|
||||
|
||||
@@ -40,7 +40,7 @@ TransactionAcquire::TransactionAcquire (uint256 const& hash, clock_type& clock)
|
||||
deprecatedLogs().journal("TransactionAcquire"))
|
||||
, mHaveRoot (false)
|
||||
{
|
||||
mMap = std::make_shared<SHAMap> (smtTRANSACTION, hash,
|
||||
mMap = std::make_shared<SHAMap> (SHAMapType::TRANSACTION, hash,
|
||||
getApp().family(), deprecatedLogs().journal("SHAMap"));
|
||||
mMap->setUnbacked ();
|
||||
}
|
||||
@@ -49,7 +49,7 @@ TransactionAcquire::~TransactionAcquire ()
|
||||
{
|
||||
}
|
||||
|
||||
static void TACompletionHandler (uint256 hash, SHAMap::pointer map)
|
||||
static void TACompletionHandler (uint256 hash, std::shared_ptr<SHAMap> map)
|
||||
{
|
||||
{
|
||||
Application::ScopedLockType lock (getApp ().getMasterLock ());
|
||||
@@ -63,7 +63,7 @@ static void TACompletionHandler (uint256 hash, SHAMap::pointer map)
|
||||
void TransactionAcquire::done ()
|
||||
{
|
||||
// We hold a PeerSet lock and so cannot acquire the master lock here
|
||||
SHAMap::pointer map;
|
||||
std::shared_ptr<SHAMap> map;
|
||||
|
||||
if (mFailed)
|
||||
{
|
||||
|
||||
@@ -41,7 +41,7 @@ public:
|
||||
TransactionAcquire (uint256 const& hash, clock_type& clock);
|
||||
~TransactionAcquire ();
|
||||
|
||||
SHAMap::ref getMap ()
|
||||
std::shared_ptr<SHAMap> const& getMap ()
|
||||
{
|
||||
return mMap;
|
||||
}
|
||||
@@ -50,7 +50,7 @@ public:
|
||||
const std::list< Blob >& data, Peer::ptr const&);
|
||||
|
||||
private:
|
||||
SHAMap::pointer mMap;
|
||||
std::shared_ptr<SHAMap> mMap;
|
||||
bool mHaveRoot;
|
||||
|
||||
void onTimer (bool progress, ScopedLockType& peerSetLock);
|
||||
|
||||
@@ -59,7 +59,7 @@ Transaction::pointer TransactionMaster::fetch (uint256 const& txnID, bool checkD
|
||||
return txn;
|
||||
}
|
||||
|
||||
STTx::pointer TransactionMaster::fetch (SHAMapItem::ref item,
|
||||
STTx::pointer TransactionMaster::fetch (std::shared_ptr<SHAMapItem> const& item,
|
||||
SHAMapTreeNode::TNType type,
|
||||
bool checkDisk, std::uint32_t uCommitLedger)
|
||||
{
|
||||
|
||||
@@ -34,7 +34,7 @@ public:
|
||||
TransactionMaster ();
|
||||
|
||||
Transaction::pointer fetch (uint256 const& , bool checkDisk);
|
||||
STTx::pointer fetch (SHAMapItem::ref item, SHAMapTreeNode:: TNType type,
|
||||
STTx::pointer fetch (std::shared_ptr<SHAMapItem> const& item, SHAMapTreeNode:: TNType type,
|
||||
bool checkDisk, std::uint32_t uCommitLedger);
|
||||
|
||||
// return value: true = we had the transaction already
|
||||
|
||||
@@ -34,6 +34,7 @@
|
||||
#include <ripple/resource/Fees.h>
|
||||
#include <ripple/server/ServerHandler.h>
|
||||
#include <ripple/protocol/BuildInfo.h>
|
||||
#include <ripple/protocol/JsonFields.h>
|
||||
#include <beast/streams/debug_ostream.h>
|
||||
#include <beast/weak_fn.h>
|
||||
#include <boost/asio/io_service.hpp>
|
||||
@@ -1719,7 +1720,7 @@ void
|
||||
PeerImp::getLedger (std::shared_ptr<protocol::TMGetLedger> const& m)
|
||||
{
|
||||
protocol::TMGetLedger& packet = *m;
|
||||
SHAMap::pointer map;
|
||||
std::shared_ptr<SHAMap> map;
|
||||
protocol::TMLedgerData reply;
|
||||
bool fatLeaves = true, fatRoot = false;
|
||||
|
||||
@@ -1949,7 +1950,7 @@ PeerImp::getLedger (std::shared_ptr<protocol::TMGetLedger> const& m)
|
||||
reply.add_nodes ()->set_nodedata (
|
||||
nData.getDataPtr (), nData.getLength ());
|
||||
|
||||
SHAMap::pointer map = ledger->peekAccountStateMap ();
|
||||
std::shared_ptr<SHAMap> map = ledger->peekAccountStateMap ();
|
||||
|
||||
if (map && map->getHash ().isNonZero ())
|
||||
{
|
||||
|
||||
@@ -21,6 +21,7 @@
|
||||
#include <ripple/basics/Log.h>
|
||||
#include <ripple/json/to_string.h>
|
||||
#include <ripple/protocol/Indexes.h>
|
||||
#include <ripple/protocol/JsonFields.h>
|
||||
#include <ripple/protocol/STAccount.h>
|
||||
#include <ripple/protocol/STLedgerEntry.h>
|
||||
#include <boost/format.hpp>
|
||||
|
||||
@@ -20,6 +20,7 @@
|
||||
#include <BeastConfig.h>
|
||||
#include <ripple/basics/Log.h>
|
||||
#include <ripple/protocol/HashPrefix.h>
|
||||
#include <ripple/protocol/JsonFields.h>
|
||||
#include <ripple/protocol/Protocol.h>
|
||||
#include <ripple/protocol/STAccount.h>
|
||||
#include <ripple/protocol/STArray.h>
|
||||
|
||||
@@ -19,6 +19,7 @@
|
||||
|
||||
#include <BeastConfig.h>
|
||||
#include <ripple/app/misc/SHAMapStore.h>
|
||||
#include <beast/module/core/text/LexicalCast.h>
|
||||
#include <boost/algorithm/string/case_conv.hpp>
|
||||
#include <boost/format.hpp>
|
||||
|
||||
|
||||
@@ -19,6 +19,7 @@
|
||||
|
||||
#include <BeastConfig.h>
|
||||
#include <ripple/app/misc/AmendmentTable.h>
|
||||
#include <beast/module/core/text/LexicalCast.h>
|
||||
|
||||
namespace ripple {
|
||||
|
||||
|
||||
@@ -79,7 +79,7 @@ Json::Value doLedgerData (RPC::Context& context)
|
||||
|
||||
for (;;)
|
||||
{
|
||||
SHAMapItem::pointer item = map.peekNextItem (resumePoint);
|
||||
std::shared_ptr<SHAMapItem> item = map.peekNextItem (resumePoint);
|
||||
if (!item)
|
||||
break;
|
||||
resumePoint = item->getTag();
|
||||
|
||||
@@ -37,7 +37,7 @@ template <class Key>
|
||||
class BasicFullBelowCache
|
||||
{
|
||||
private:
|
||||
typedef KeyCache <Key> CacheType;
|
||||
using CacheType = KeyCache <Key>;
|
||||
|
||||
public:
|
||||
enum
|
||||
@@ -46,9 +46,9 @@ public:
|
||||
,defaultCacheExpirationSeconds = 120
|
||||
};
|
||||
|
||||
typedef Key key_type;
|
||||
typedef typename CacheType::size_type size_type;
|
||||
typedef typename CacheType::clock_type clock_type;
|
||||
using key_type = Key;
|
||||
using size_type = typename CacheType::size_type;
|
||||
using clock_type = typename CacheType::clock_type ;
|
||||
|
||||
/** Construct the cache.
|
||||
|
||||
|
||||
@@ -114,10 +114,10 @@ The `fetchNodeExternalNT()` method goes through three phases:
|
||||
in the historic data stored by the data base. The call to
|
||||
to `fetch(hash)` does that work for us.
|
||||
|
||||
3. Finally, if mLedgerSeq is non-zero and we did't locate the node in the
|
||||
3. Finally, if ledgerSeq_ is non-zero and we did't locate the node in the
|
||||
historic data, then we call a MissingNodeHandler.
|
||||
|
||||
The non-zero mLedgerSeq indicates that the SHAMap is a complete map that
|
||||
The non-zero ledgerSeq_ indicates that the SHAMap is a complete map that
|
||||
belongs to a historic ledger with the given (non-zero) sequence number.
|
||||
So, if all expected data is always present, the MissingNodeHandler should
|
||||
never be executed.
|
||||
|
||||
@@ -28,6 +28,7 @@
|
||||
#include <ripple/shamap/SHAMapNodeID.h>
|
||||
#include <ripple/shamap/SHAMapSyncFilter.h>
|
||||
#include <ripple/shamap/SHAMapTreeNode.h>
|
||||
#include <ripple/shamap/TreeNodeCache.h>
|
||||
#include <ripple/basics/UnorderedContainers.h>
|
||||
#include <ripple/nodestore/Database.h>
|
||||
#include <ripple/nodestore/NodeObject.h>
|
||||
@@ -37,41 +38,15 @@
|
||||
#include <boost/thread/shared_mutex.hpp>
|
||||
#include <stack>
|
||||
|
||||
namespace std {
|
||||
|
||||
template <>
|
||||
struct hash <ripple::SHAMapNodeID>
|
||||
{
|
||||
std::size_t operator() (ripple::SHAMapNodeID const& value) const
|
||||
{
|
||||
return value.getMHash ();
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
namespace boost {
|
||||
|
||||
template <>
|
||||
struct hash <ripple::SHAMapNodeID> : std::hash <ripple::SHAMapNodeID>
|
||||
{
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
namespace ripple {
|
||||
|
||||
enum SHAMapState
|
||||
enum class SHAMapState
|
||||
{
|
||||
smsModifying = 0, // Objects can be added and removed (like an open ledger)
|
||||
smsImmutable = 1, // Map cannot be changed (like a closed ledger)
|
||||
smsSynching = 2, // Map's hash is locked in, valid nodes can be added (like a peer's closing ledger)
|
||||
smsFloating = 3, // Map is free to change hash (like a synching open ledger)
|
||||
smsInvalid = 4, // Map is known not to be valid (usually synching a corrupt ledger)
|
||||
Modifying = 0, // Objects can be added and removed (like an open ledger)
|
||||
Immutable = 1, // Map cannot be changed (like a closed ledger)
|
||||
Synching = 2, // Map's hash is locked in, valid nodes can be added (like a peer's closing ledger)
|
||||
Floating = 3, // Map is free to change hash (like a synching open ledger)
|
||||
Invalid = 4, // Map is known not to be valid (usually synching a corrupt ledger)
|
||||
};
|
||||
|
||||
/** Function object which handles missing nodes. */
|
||||
@@ -106,31 +81,22 @@ private:
|
||||
|
||||
Family& f_;
|
||||
beast::Journal journal_;
|
||||
std::uint32_t mSeq;
|
||||
std::uint32_t mLedgerSeq; // sequence number of ledger this is part of
|
||||
SHAMapTreeNode::pointer root;
|
||||
SHAMapState mState;
|
||||
SHAMapType mType;
|
||||
bool mBacked = true; // Map is backed by the database
|
||||
std::uint32_t seq_;
|
||||
std::uint32_t ledgerSeq_; // sequence number of ledger this is part of
|
||||
std::shared_ptr<SHAMapTreeNode> root_;
|
||||
SHAMapState state_;
|
||||
SHAMapType type_;
|
||||
bool backed_ = true; // Map is backed by the database
|
||||
|
||||
public:
|
||||
enum
|
||||
{
|
||||
STATE_MAP_BUCKETS = 1024
|
||||
};
|
||||
using DeltaItem = std::pair<std::shared_ptr<SHAMapItem>,
|
||||
std::shared_ptr<SHAMapItem>>;
|
||||
using Delta = std::map<uint256, DeltaItem>;
|
||||
|
||||
static char const* getCountedObjectName () { return "SHAMap"; }
|
||||
~SHAMap ();
|
||||
SHAMap(SHAMap const&) = delete;
|
||||
SHAMap& operator=(SHAMap const&) = delete;
|
||||
|
||||
typedef std::shared_ptr<SHAMap> pointer;
|
||||
typedef const std::shared_ptr<SHAMap>& ref;
|
||||
|
||||
typedef std::pair<SHAMapItem::pointer, SHAMapItem::pointer> DeltaItem;
|
||||
typedef std::pair<SHAMapItem::ref, SHAMapItem::ref> DeltaRef;
|
||||
typedef std::map<uint256, DeltaItem> Delta;
|
||||
|
||||
typedef std::stack<std::pair<SHAMapTreeNode::pointer, SHAMapNodeID>> SharedPtrNodeStack;
|
||||
|
||||
public:
|
||||
// build new map
|
||||
SHAMap (
|
||||
SHAMapType t,
|
||||
@@ -145,55 +111,44 @@ public:
|
||||
Family& f,
|
||||
beast::Journal journal);
|
||||
|
||||
~SHAMap ();
|
||||
|
||||
// Returns a new map that's a snapshot of this one.
|
||||
// Handles copy on write for mutable snapshots.
|
||||
SHAMap::pointer snapShot (bool isMutable);
|
||||
|
||||
void setLedgerSeq (std::uint32_t lseq)
|
||||
{
|
||||
mLedgerSeq = lseq;
|
||||
}
|
||||
|
||||
std::shared_ptr<SHAMap> snapShot (bool isMutable) const;
|
||||
void setLedgerSeq (std::uint32_t lseq);
|
||||
bool fetchRoot (uint256 const& hash, SHAMapSyncFilter * filter);
|
||||
|
||||
// normal hash access functions
|
||||
bool hasItem (uint256 const& id);
|
||||
bool delItem (uint256 const& id);
|
||||
bool addItem (SHAMapItem const& i, bool isTransaction, bool hasMeta);
|
||||
|
||||
uint256 getHash () const
|
||||
{
|
||||
return root->getNodeHash ();
|
||||
}
|
||||
uint256 getHash () const;
|
||||
|
||||
// save a copy if you have a temporary anyway
|
||||
bool updateGiveItem (SHAMapItem::ref, bool isTransaction, bool hasMeta);
|
||||
bool addGiveItem (SHAMapItem::ref, bool isTransaction, bool hasMeta);
|
||||
bool updateGiveItem (std::shared_ptr<SHAMapItem> const&, bool isTransaction, bool hasMeta);
|
||||
bool addGiveItem (std::shared_ptr<SHAMapItem> const&, bool isTransaction, bool hasMeta);
|
||||
|
||||
// save a copy if you only need a temporary
|
||||
SHAMapItem::pointer peekItem (uint256 const& id);
|
||||
SHAMapItem::pointer peekItem (uint256 const& id, uint256 & hash);
|
||||
SHAMapItem::pointer peekItem (uint256 const& id, SHAMapTreeNode::TNType & type);
|
||||
std::shared_ptr<SHAMapItem> peekItem (uint256 const& id);
|
||||
std::shared_ptr<SHAMapItem> peekItem (uint256 const& id, uint256 & hash);
|
||||
std::shared_ptr<SHAMapItem> peekItem (uint256 const& id, SHAMapTreeNode::TNType & type);
|
||||
|
||||
// traverse functions
|
||||
SHAMapItem::pointer peekFirstItem ();
|
||||
SHAMapItem::pointer peekFirstItem (SHAMapTreeNode::TNType & type);
|
||||
SHAMapItem::pointer peekLastItem ();
|
||||
SHAMapItem::pointer peekNextItem (uint256 const& );
|
||||
SHAMapItem::pointer peekNextItem (uint256 const& , SHAMapTreeNode::TNType & type);
|
||||
SHAMapItem::pointer peekPrevItem (uint256 const& );
|
||||
std::shared_ptr<SHAMapItem> peekFirstItem ();
|
||||
std::shared_ptr<SHAMapItem> peekFirstItem (SHAMapTreeNode::TNType & type);
|
||||
std::shared_ptr<SHAMapItem> peekLastItem ();
|
||||
std::shared_ptr<SHAMapItem> peekNextItem (uint256 const& );
|
||||
std::shared_ptr<SHAMapItem> peekNextItem (uint256 const& , SHAMapTreeNode::TNType & type);
|
||||
std::shared_ptr<SHAMapItem> peekPrevItem (uint256 const& );
|
||||
|
||||
void visitNodes (std::function<bool (SHAMapTreeNode&)> const&);
|
||||
void visitLeaves(std::function<void (SHAMapItem::ref)> const&);
|
||||
void visitLeaves(std::function<void (std::shared_ptr<SHAMapItem> const&)> const&);
|
||||
|
||||
// comparison/sync functions
|
||||
void getMissingNodes (std::vector<SHAMapNodeID>& nodeIDs, std::vector<uint256>& hashes, int max,
|
||||
SHAMapSyncFilter * filter);
|
||||
bool getNodeFat (SHAMapNodeID node, std::vector<SHAMapNodeID>& nodeIDs,
|
||||
std::list<Blob >& rawNode, bool fatRoot, bool fatLeaves);
|
||||
bool getRootNode (Serializer & s, SHANodeFormat format);
|
||||
bool getRootNode (Serializer & s, SHANodeFormat format) const;
|
||||
std::vector<uint256> getNeededHashes (int max, SHAMapSyncFilter * filter);
|
||||
SHAMapAddNode addRootNode (uint256 const& hash, Blob const& rootNode, SHANodeFormat format,
|
||||
SHAMapSyncFilter * filter);
|
||||
@@ -203,37 +158,19 @@ public:
|
||||
SHAMapSyncFilter * filter);
|
||||
|
||||
// status functions
|
||||
void setImmutable ()
|
||||
{
|
||||
assert (mState != smsInvalid);
|
||||
mState = smsImmutable;
|
||||
}
|
||||
bool isSynching () const
|
||||
{
|
||||
return (mState == smsFloating) || (mState == smsSynching);
|
||||
}
|
||||
void setSynching ()
|
||||
{
|
||||
mState = smsSynching;
|
||||
}
|
||||
void clearSynching ()
|
||||
{
|
||||
mState = smsModifying;
|
||||
}
|
||||
bool isValid ()
|
||||
{
|
||||
return mState != smsInvalid;
|
||||
}
|
||||
void setImmutable ();
|
||||
bool isSynching () const;
|
||||
void setSynching ();
|
||||
void clearSynching ();
|
||||
bool isValid () const;
|
||||
|
||||
// caution: otherMap must be accessed only by this function
|
||||
// return value: true=successfully completed, false=too different
|
||||
bool compare (SHAMap::ref otherMap, Delta & differences, int maxCount);
|
||||
bool compare (std::shared_ptr<SHAMap> const& otherMap,
|
||||
Delta& differences, int maxCount); // HINNANT should be const
|
||||
|
||||
int flushDirty (NodeObjectType t, std::uint32_t seq);
|
||||
int unshare ();
|
||||
|
||||
void walkMap (std::vector<SHAMapMissingNode>& missingNodes, int maxMissing);
|
||||
|
||||
bool deepCompare (SHAMap & other);
|
||||
|
||||
typedef std::pair <uint256, Blob> fetchPackEntry_t;
|
||||
@@ -243,41 +180,36 @@ public:
|
||||
void getFetchPack (SHAMap * have, bool includeLeaves, int max,
|
||||
std::function<void (uint256 const&, const Blob&)>);
|
||||
|
||||
void setUnbacked ()
|
||||
{
|
||||
mBacked = false;
|
||||
}
|
||||
void setUnbacked ();
|
||||
|
||||
void dump (bool withHashes = false);
|
||||
void dump (bool withHashes = false) const;
|
||||
|
||||
private:
|
||||
// trusted path operations - prove a particular node is in a particular ledger
|
||||
std::list<Blob > getTrustedPath (uint256 const& index);
|
||||
using SharedPtrNodeStack =
|
||||
std::stack<std::pair<std::shared_ptr<SHAMapTreeNode>, SHAMapNodeID>>;
|
||||
using DeltaRef = std::pair<std::shared_ptr<SHAMapItem> const&,
|
||||
std::shared_ptr<SHAMapItem> const&> ;
|
||||
|
||||
bool getPath (uint256 const& index, std::vector< Blob >& nodes, SHANodeFormat format);
|
||||
int unshare ();
|
||||
|
||||
// tree node cache operations
|
||||
SHAMapTreeNode::pointer getCache (uint256 const& hash);
|
||||
void canonicalize (uint256 const& hash, SHAMapTreeNode::pointer&);
|
||||
std::shared_ptr<SHAMapTreeNode> getCache (uint256 const& hash) const;
|
||||
void canonicalize (uint256 const& hash, std::shared_ptr<SHAMapTreeNode>&) const;
|
||||
|
||||
// database operations
|
||||
SHAMapTreeNode::pointer fetchNodeFromDB (uint256 const& hash);
|
||||
|
||||
SHAMapTreeNode::pointer fetchNodeNT (uint256 const& hash);
|
||||
|
||||
SHAMapTreeNode::pointer fetchNodeNT (
|
||||
std::shared_ptr<SHAMapTreeNode> fetchNodeFromDB (uint256 const& hash);
|
||||
std::shared_ptr<SHAMapTreeNode> fetchNodeNT (uint256 const& hash);
|
||||
std::shared_ptr<SHAMapTreeNode> fetchNodeNT (
|
||||
SHAMapNodeID const& id,
|
||||
uint256 const& hash,
|
||||
SHAMapSyncFilter *filter);
|
||||
|
||||
SHAMapTreeNode::pointer fetchNode (uint256 const& hash);
|
||||
|
||||
SHAMapTreeNode::pointer checkFilter (uint256 const& hash, SHAMapNodeID const& id,
|
||||
SHAMapSyncFilter* filter);
|
||||
std::shared_ptr<SHAMapTreeNode> fetchNode (uint256 const& hash);
|
||||
std::shared_ptr<SHAMapTreeNode> checkFilter (uint256 const& hash, SHAMapNodeID const& id,
|
||||
SHAMapSyncFilter* filter) const;
|
||||
|
||||
/** Update hashes up to the root */
|
||||
void dirtyUp (SharedPtrNodeStack& stack,
|
||||
uint256 const& target, SHAMapTreeNode::pointer terminal);
|
||||
uint256 const& target, std::shared_ptr<SHAMapTreeNode> terminal);
|
||||
|
||||
/** Get the path from the root to the specified node */
|
||||
SharedPtrNodeStack
|
||||
@@ -287,14 +219,14 @@ private:
|
||||
SHAMapTreeNode* walkToPointer (uint256 const& id);
|
||||
|
||||
/** Unshare the node, allowing it to be modified */
|
||||
void unshareNode (SHAMapTreeNode::pointer&, SHAMapNodeID const& nodeID);
|
||||
void unshareNode (std::shared_ptr<SHAMapTreeNode>&, SHAMapNodeID const& nodeID);
|
||||
|
||||
/** prepare a node to be modified before flushing */
|
||||
void preFlushNode (SHAMapTreeNode::pointer& node);
|
||||
void preFlushNode (std::shared_ptr<SHAMapTreeNode>& node) const;
|
||||
|
||||
/** write and canonicalize modified node */
|
||||
void writeNode (NodeObjectType t, std::uint32_t seq,
|
||||
SHAMapTreeNode::pointer& node);
|
||||
std::shared_ptr<SHAMapTreeNode>& node) const;
|
||||
|
||||
SHAMapTreeNode* firstBelow (SHAMapTreeNode*);
|
||||
SHAMapTreeNode* lastBelow (SHAMapTreeNode*);
|
||||
@@ -303,12 +235,12 @@ private:
|
||||
// Get a child of the specified node
|
||||
SHAMapTreeNode* descend (SHAMapTreeNode*, int branch);
|
||||
SHAMapTreeNode* descendThrow (SHAMapTreeNode*, int branch);
|
||||
SHAMapTreeNode::pointer descend (SHAMapTreeNode::ref, int branch);
|
||||
SHAMapTreeNode::pointer descendThrow (SHAMapTreeNode::ref, int branch);
|
||||
std::shared_ptr<SHAMapTreeNode> descend (std::shared_ptr<SHAMapTreeNode> const&, int branch);
|
||||
std::shared_ptr<SHAMapTreeNode> descendThrow (std::shared_ptr<SHAMapTreeNode> const&, int branch);
|
||||
|
||||
// Descend with filter
|
||||
SHAMapTreeNode* descendAsync (SHAMapTreeNode* parent, int branch,
|
||||
SHAMapNodeID const& childID, SHAMapSyncFilter* filter, bool& pending);
|
||||
SHAMapNodeID const& childID, SHAMapSyncFilter* filter, bool& pending) const;
|
||||
|
||||
std::pair <SHAMapTreeNode*, SHAMapNodeID>
|
||||
descend (SHAMapTreeNode* parent, SHAMapNodeID const& parentID,
|
||||
@@ -316,23 +248,77 @@ private:
|
||||
|
||||
// Non-storing
|
||||
// Does not hook the returned node to its parent
|
||||
SHAMapTreeNode::pointer descendNoStore (SHAMapTreeNode::ref, int branch);
|
||||
std::shared_ptr<SHAMapTreeNode> descendNoStore (std::shared_ptr<SHAMapTreeNode> const&, int branch);
|
||||
|
||||
/** If there is only one leaf below this node, get its contents */
|
||||
SHAMapItem::pointer onlyBelow (SHAMapTreeNode*);
|
||||
std::shared_ptr<SHAMapItem> onlyBelow (SHAMapTreeNode*);
|
||||
|
||||
bool hasInnerNode (SHAMapNodeID const& nodeID, uint256 const& hash);
|
||||
bool hasLeafNode (uint256 const& tag, uint256 const& hash);
|
||||
|
||||
bool walkBranch (SHAMapTreeNode* node,
|
||||
SHAMapItem::ref otherMapItem, bool isFirstMap,
|
||||
std::shared_ptr<SHAMapItem> const& otherMapItem, bool isFirstMap,
|
||||
Delta & differences, int & maxCount);
|
||||
|
||||
void visitLeavesInternal (std::function<void (SHAMapItem::ref item)>& function);
|
||||
|
||||
int walkSubTree (bool doWrite, NodeObjectType t, std::uint32_t seq);
|
||||
};
|
||||
|
||||
inline
|
||||
void
|
||||
SHAMap::setLedgerSeq (std::uint32_t lseq)
|
||||
{
|
||||
ledgerSeq_ = lseq;
|
||||
}
|
||||
|
||||
inline
|
||||
uint256
|
||||
SHAMap::getHash () const
|
||||
{
|
||||
return root_->getNodeHash ();
|
||||
}
|
||||
|
||||
inline
|
||||
void
|
||||
SHAMap::setImmutable ()
|
||||
{
|
||||
assert (state_ != SHAMapState::Invalid);
|
||||
state_ = SHAMapState::Immutable;
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMap::isSynching () const
|
||||
{
|
||||
return (state_ == SHAMapState::Floating) || (state_ == SHAMapState::Synching);
|
||||
}
|
||||
|
||||
inline
|
||||
void
|
||||
SHAMap::setSynching ()
|
||||
{
|
||||
state_ = SHAMapState::Synching;
|
||||
}
|
||||
|
||||
inline
|
||||
void
|
||||
SHAMap::clearSynching ()
|
||||
{
|
||||
state_ = SHAMapState::Modifying;
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMap::isValid () const
|
||||
{
|
||||
return state_ != SHAMapState::Invalid;
|
||||
}
|
||||
|
||||
inline
|
||||
void
|
||||
SHAMap::setUnbacked ()
|
||||
{
|
||||
backed_ = false;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
@@ -20,120 +20,172 @@
|
||||
#ifndef RIPPLE_SHAMAP_SHAMAPADDNODE_H_INCLUDED
|
||||
#define RIPPLE_SHAMAP_SHAMAPADDNODE_H_INCLUDED
|
||||
|
||||
#include <beast/module/core/text/LexicalCast.h>
|
||||
#include <string>
|
||||
|
||||
namespace ripple {
|
||||
|
||||
// results of adding nodes
|
||||
class SHAMapAddNode
|
||||
{
|
||||
private:
|
||||
int mGood;
|
||||
int mBad;
|
||||
int mDuplicate;
|
||||
|
||||
public:
|
||||
SHAMapAddNode ()
|
||||
SHAMapAddNode ();
|
||||
void incInvalid ();
|
||||
void incUseful ();
|
||||
void incDuplicate ();
|
||||
void reset ();
|
||||
int getGood () const;
|
||||
bool isGood () const;
|
||||
bool isInvalid () const;
|
||||
bool isUseful () const;
|
||||
std::string get () const;
|
||||
|
||||
SHAMapAddNode& operator+= (SHAMapAddNode const& n);
|
||||
|
||||
static SHAMapAddNode duplicate ();
|
||||
static SHAMapAddNode useful ();
|
||||
static SHAMapAddNode invalid ();
|
||||
|
||||
private:
|
||||
SHAMapAddNode (int good, int bad, int duplicate);
|
||||
};
|
||||
|
||||
inline
|
||||
SHAMapAddNode::SHAMapAddNode ()
|
||||
: mGood (0)
|
||||
, mBad (0)
|
||||
, mDuplicate (0)
|
||||
{
|
||||
}
|
||||
{
|
||||
}
|
||||
|
||||
SHAMapAddNode (int good, int bad, int duplicate)
|
||||
: mGood(good)
|
||||
, mBad(bad)
|
||||
, mDuplicate(duplicate)
|
||||
{
|
||||
}
|
||||
inline
|
||||
SHAMapAddNode::SHAMapAddNode (int good, int bad, int duplicate)
|
||||
: mGood (good)
|
||||
, mBad (bad)
|
||||
, mDuplicate (duplicate)
|
||||
{
|
||||
}
|
||||
|
||||
void incInvalid ()
|
||||
{
|
||||
inline
|
||||
void
|
||||
SHAMapAddNode::incInvalid ()
|
||||
{
|
||||
++mBad;
|
||||
}
|
||||
void incUseful ()
|
||||
{
|
||||
}
|
||||
|
||||
inline
|
||||
void
|
||||
SHAMapAddNode::incUseful ()
|
||||
{
|
||||
++mGood;
|
||||
}
|
||||
void incDuplicate ()
|
||||
{
|
||||
}
|
||||
|
||||
inline
|
||||
void
|
||||
SHAMapAddNode::incDuplicate ()
|
||||
{
|
||||
++mDuplicate;
|
||||
}
|
||||
}
|
||||
|
||||
void reset ()
|
||||
{
|
||||
inline
|
||||
void
|
||||
SHAMapAddNode::reset ()
|
||||
{
|
||||
mGood = mBad = mDuplicate = 0;
|
||||
}
|
||||
}
|
||||
|
||||
int getGood ()
|
||||
{
|
||||
inline
|
||||
int
|
||||
SHAMapAddNode::getGood () const
|
||||
{
|
||||
return mGood;
|
||||
}
|
||||
}
|
||||
|
||||
bool isInvalid () const
|
||||
{
|
||||
inline
|
||||
bool
|
||||
SHAMapAddNode::isInvalid () const
|
||||
{
|
||||
return mBad > 0;
|
||||
}
|
||||
bool isUseful () const
|
||||
{
|
||||
return mGood > 0;
|
||||
}
|
||||
}
|
||||
|
||||
SHAMapAddNode& operator+= (SHAMapAddNode const& n)
|
||||
{
|
||||
inline
|
||||
bool
|
||||
SHAMapAddNode::isUseful () const
|
||||
{
|
||||
return mGood > 0;
|
||||
}
|
||||
|
||||
inline
|
||||
SHAMapAddNode&
|
||||
SHAMapAddNode::operator+= (SHAMapAddNode const& n)
|
||||
{
|
||||
mGood += n.mGood;
|
||||
mBad += n.mBad;
|
||||
mDuplicate += n.mDuplicate;
|
||||
|
||||
return *this;
|
||||
}
|
||||
}
|
||||
|
||||
bool isGood () const
|
||||
{
|
||||
inline
|
||||
bool
|
||||
SHAMapAddNode::isGood () const
|
||||
{
|
||||
return (mGood + mDuplicate) > mBad;
|
||||
}
|
||||
}
|
||||
|
||||
static SHAMapAddNode duplicate ()
|
||||
{
|
||||
inline
|
||||
SHAMapAddNode
|
||||
SHAMapAddNode::duplicate ()
|
||||
{
|
||||
return SHAMapAddNode (0, 0, 1);
|
||||
}
|
||||
static SHAMapAddNode useful ()
|
||||
{
|
||||
return SHAMapAddNode (1, 0, 0);
|
||||
}
|
||||
static SHAMapAddNode invalid ()
|
||||
{
|
||||
return SHAMapAddNode (0, 1, 0);
|
||||
}
|
||||
}
|
||||
|
||||
std::string get ()
|
||||
{
|
||||
inline
|
||||
SHAMapAddNode
|
||||
SHAMapAddNode::useful ()
|
||||
{
|
||||
return SHAMapAddNode (1, 0, 0);
|
||||
}
|
||||
|
||||
inline
|
||||
SHAMapAddNode
|
||||
SHAMapAddNode::invalid ()
|
||||
{
|
||||
return SHAMapAddNode (0, 1, 0);
|
||||
}
|
||||
|
||||
inline
|
||||
std::string
|
||||
SHAMapAddNode::get () const
|
||||
{
|
||||
std::string ret;
|
||||
if (mGood > 0)
|
||||
{
|
||||
ret.append("good:");
|
||||
ret.append(beast::lexicalCastThrow<std::string>(mGood));
|
||||
ret.append(std::to_string(mGood));
|
||||
}
|
||||
if (mBad > 0)
|
||||
{
|
||||
if (!ret.empty())
|
||||
ret.append(" ");
|
||||
ret.append("bad:");
|
||||
ret.append(beast::lexicalCastThrow<std::string>(mBad));
|
||||
ret.append(std::to_string(mBad));
|
||||
}
|
||||
if (mDuplicate > 0)
|
||||
{
|
||||
if (!ret.empty())
|
||||
ret.append(" ");
|
||||
ret.append("dupe:");
|
||||
ret.append(beast::lexicalCastThrow<std::string>(mDuplicate));
|
||||
ret.append(std::to_string(mDuplicate));
|
||||
}
|
||||
if (ret.empty ())
|
||||
ret = "no nodes processed";
|
||||
return ret;
|
||||
}
|
||||
|
||||
private:
|
||||
|
||||
int mGood;
|
||||
int mBad;
|
||||
int mDuplicate;
|
||||
};
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -20,77 +20,89 @@
|
||||
#ifndef RIPPLE_SHAMAP_SHAMAPITEM_H_INCLUDED
|
||||
#define RIPPLE_SHAMAP_SHAMAPITEM_H_INCLUDED
|
||||
|
||||
#include <ripple/basics/CountedObject.h>
|
||||
#include <ripple/protocol/Serializer.h>
|
||||
#include <ripple/basics/base_uint.h>
|
||||
#include <beast/utility/Journal.h>
|
||||
#include <memory>
|
||||
|
||||
#include <cstddef>
|
||||
|
||||
namespace ripple {
|
||||
|
||||
// an item stored in a SHAMap
|
||||
class SHAMapItem
|
||||
: public CountedObject <SHAMapItem>
|
||||
{
|
||||
public:
|
||||
static char const* getCountedObjectName () { return "SHAMapItem"; }
|
||||
|
||||
typedef std::shared_ptr<SHAMapItem> pointer;
|
||||
typedef const std::shared_ptr<SHAMapItem>& ref;
|
||||
|
||||
public:
|
||||
explicit SHAMapItem (uint256 const& tag)
|
||||
: mTag (tag)
|
||||
{
|
||||
}
|
||||
|
||||
// tag computed from hash of data
|
||||
explicit SHAMapItem (Blob const& data);
|
||||
|
||||
SHAMapItem (uint256 const& tag, Blob const & data);
|
||||
|
||||
SHAMapItem (uint256 const& tag, Serializer const& s);
|
||||
|
||||
std::size_t
|
||||
size() const
|
||||
{
|
||||
return mData.peekData().size();
|
||||
}
|
||||
|
||||
void const*
|
||||
data() const
|
||||
{
|
||||
return mData.peekData().data();
|
||||
}
|
||||
|
||||
uint256 const& getTag() const
|
||||
{
|
||||
return mTag;
|
||||
}
|
||||
|
||||
Blob const& peekData() const
|
||||
{
|
||||
return mData.peekData();
|
||||
}
|
||||
|
||||
Serializer& peekSerializer()
|
||||
{
|
||||
return mData;
|
||||
}
|
||||
|
||||
void addRaw (Blob& s) const
|
||||
{
|
||||
s.insert (s.end (), mData.begin (), mData.end ());
|
||||
}
|
||||
|
||||
// VFALCO Why is this virtual?
|
||||
virtual void dump (beast::Journal journal);
|
||||
|
||||
private:
|
||||
uint256 mTag;
|
||||
Serializer mData;
|
||||
|
||||
public:
|
||||
explicit SHAMapItem (uint256 const& tag);
|
||||
SHAMapItem (uint256 const& tag, Blob const & data);
|
||||
SHAMapItem (uint256 const& tag, Serializer const& s);
|
||||
|
||||
uint256 const& getTag() const;
|
||||
Blob const& peekData() const;
|
||||
Serializer& peekSerializer();
|
||||
|
||||
public: // public only to SHAMapTreeNode
|
||||
std::size_t size() const;
|
||||
|
||||
private:
|
||||
explicit SHAMapItem (Blob const& data);
|
||||
|
||||
void const* data() const;
|
||||
void addRaw (Blob& s) const;
|
||||
void dump (beast::Journal journal);
|
||||
};
|
||||
|
||||
inline
|
||||
SHAMapItem::SHAMapItem (uint256 const& tag)
|
||||
: mTag (tag)
|
||||
{
|
||||
}
|
||||
|
||||
inline
|
||||
std::size_t
|
||||
SHAMapItem::size() const
|
||||
{
|
||||
return mData.peekData().size();
|
||||
}
|
||||
|
||||
inline
|
||||
void const*
|
||||
SHAMapItem::data() const
|
||||
{
|
||||
return mData.peekData().data();
|
||||
}
|
||||
|
||||
inline
|
||||
uint256 const&
|
||||
SHAMapItem::getTag() const
|
||||
{
|
||||
return mTag;
|
||||
}
|
||||
|
||||
inline
|
||||
Blob const&
|
||||
SHAMapItem::peekData() const
|
||||
{
|
||||
return mData.peekData();
|
||||
}
|
||||
|
||||
inline
|
||||
Serializer&
|
||||
SHAMapItem::peekSerializer()
|
||||
{
|
||||
return mData;
|
||||
}
|
||||
|
||||
inline
|
||||
void
|
||||
SHAMapItem::addRaw (Blob& s) const
|
||||
{
|
||||
s.insert (s.end (), mData.begin (), mData.end ());
|
||||
}
|
||||
|
||||
} // ripple
|
||||
|
||||
#endif
|
||||
|
||||
@@ -21,18 +21,24 @@
|
||||
#define RIPPLE_SHAMAP_SHAMAPMISSINGNODE_H_INCLUDED
|
||||
|
||||
#include <ripple/basics/base_uint.h>
|
||||
#include <iosfwd>
|
||||
#include <stdexcept>
|
||||
|
||||
namespace ripple {
|
||||
|
||||
enum SHAMapType
|
||||
enum class SHAMapType
|
||||
{
|
||||
smtTRANSACTION = 1, // A tree of transactions
|
||||
smtSTATE = 2, // A tree of state nodes
|
||||
smtFREE = 3, // A tree not part of a ledger
|
||||
TRANSACTION = 1, // A tree of transactions
|
||||
STATE = 2, // A tree of state nodes
|
||||
FREE = 3, // A tree not part of a ledger
|
||||
};
|
||||
|
||||
class SHAMapMissingNode : public std::runtime_error
|
||||
class SHAMapMissingNode
|
||||
: public std::runtime_error
|
||||
{
|
||||
private:
|
||||
SHAMapType mType;
|
||||
uint256 mNodeHash;
|
||||
public:
|
||||
SHAMapMissingNode (SHAMapType t,
|
||||
uint256 const& nodeHash)
|
||||
@@ -42,10 +48,6 @@ public:
|
||||
{
|
||||
}
|
||||
|
||||
virtual ~SHAMapMissingNode () throw ()
|
||||
{
|
||||
}
|
||||
|
||||
SHAMapType getMapType () const
|
||||
{
|
||||
return mType;
|
||||
@@ -55,10 +57,6 @@ public:
|
||||
{
|
||||
return mNodeHash;
|
||||
}
|
||||
|
||||
private:
|
||||
SHAMapType mType;
|
||||
uint256 mNodeHash;
|
||||
};
|
||||
|
||||
extern std::ostream& operator<< (std::ostream&, SHAMapMissingNode const&);
|
||||
|
||||
@@ -35,104 +35,133 @@ class SHAMapNodeID
|
||||
private:
|
||||
uint256 mNodeID;
|
||||
int mDepth;
|
||||
mutable size_t mHash;
|
||||
|
||||
public:
|
||||
SHAMapNodeID () : mDepth (0), mHash (0)
|
||||
{
|
||||
}
|
||||
|
||||
SHAMapNodeID (int depth, uint256 const& hash);
|
||||
SHAMapNodeID ();
|
||||
SHAMapNodeID (void const* ptr, int len);
|
||||
|
||||
protected:
|
||||
SHAMapNodeID (int depth, uint256 const& id, bool)
|
||||
: mNodeID (id), mDepth (depth), mHash (0)
|
||||
{
|
||||
}
|
||||
|
||||
public:
|
||||
int getDepth () const
|
||||
{
|
||||
return mDepth;
|
||||
}
|
||||
|
||||
uint256 const& getNodeID () const
|
||||
{
|
||||
return mNodeID;
|
||||
}
|
||||
|
||||
bool isValid () const
|
||||
{
|
||||
return (mDepth >= 0) && (mDepth < 64);
|
||||
}
|
||||
|
||||
bool isRoot () const
|
||||
{
|
||||
return mDepth == 0;
|
||||
}
|
||||
|
||||
size_t getMHash () const
|
||||
{
|
||||
if (mHash == 0)
|
||||
mHash = calculate_hash (mNodeID, mDepth);
|
||||
return mHash;
|
||||
}
|
||||
|
||||
SHAMapNodeID getParentNodeID () const
|
||||
{
|
||||
assert (mDepth);
|
||||
return SHAMapNodeID (mDepth - 1, mNodeID);
|
||||
}
|
||||
|
||||
SHAMapNodeID getChildNodeID (int m) const;
|
||||
int selectBranch (uint256 const& hash) const;
|
||||
|
||||
bool operator< (const SHAMapNodeID& n) const
|
||||
{
|
||||
return std::tie(mDepth, mNodeID) < std::tie(n.mDepth, n.mNodeID);
|
||||
}
|
||||
bool operator> (const SHAMapNodeID& n) const {return n < *this;}
|
||||
bool operator<= (const SHAMapNodeID& n) const {return !(*this < n);}
|
||||
bool operator>= (const SHAMapNodeID& n) const {return !(n < *this);}
|
||||
|
||||
bool operator== (const SHAMapNodeID& n) const
|
||||
{
|
||||
return (mDepth == n.mDepth) && (mNodeID == n.mNodeID);
|
||||
}
|
||||
bool operator!= (const SHAMapNodeID& n) const {return !(*this == n);}
|
||||
|
||||
bool operator== (uint256 const& n) const
|
||||
{
|
||||
return n == mNodeID;
|
||||
}
|
||||
bool operator!= (uint256 const& n) const {return !(*this == n);}
|
||||
|
||||
virtual std::string getString () const;
|
||||
void dump (beast::Journal journal) const;
|
||||
|
||||
static uint256 getNodeID (int depth, uint256 const& hash);
|
||||
bool isValid () const;
|
||||
bool isRoot () const;
|
||||
|
||||
// Convert to/from wire format (256-bit nodeID, 1-byte depth)
|
||||
void addIDRaw (Serializer& s) const;
|
||||
std::string getRawString () const;
|
||||
static int getRawIDLength (void)
|
||||
{
|
||||
return 33;
|
||||
}
|
||||
|
||||
bool operator== (const SHAMapNodeID& n) const;
|
||||
bool operator!= (const SHAMapNodeID& n) const;
|
||||
|
||||
bool operator< (const SHAMapNodeID& n) const;
|
||||
bool operator> (const SHAMapNodeID& n) const;
|
||||
bool operator<= (const SHAMapNodeID& n) const;
|
||||
bool operator>= (const SHAMapNodeID& n) const;
|
||||
|
||||
std::string getString () const;
|
||||
void dump (beast::Journal journal) const;
|
||||
|
||||
// Only used by SHAMap and SHAMapTreeNode
|
||||
|
||||
uint256 const& getNodeID () const;
|
||||
SHAMapNodeID getChildNodeID (int m) const;
|
||||
int selectBranch (uint256 const& hash) const;
|
||||
int getDepth () const;
|
||||
|
||||
private:
|
||||
static
|
||||
uint256 const&
|
||||
Masks (int depth);
|
||||
SHAMapNodeID (int depth, uint256 const& hash);
|
||||
|
||||
static
|
||||
std::size_t
|
||||
calculate_hash (uint256 const& node, int depth);
|
||||
static uint256 const& Masks (int depth);
|
||||
|
||||
friend std::ostream& operator<< (std::ostream& out, SHAMapNodeID const& node);
|
||||
|
||||
private: // Currently unused
|
||||
SHAMapNodeID getParentNodeID () const;
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
inline
|
||||
SHAMapNodeID::SHAMapNodeID ()
|
||||
: mDepth (0)
|
||||
{
|
||||
}
|
||||
|
||||
inline
|
||||
int
|
||||
SHAMapNodeID::getDepth () const
|
||||
{
|
||||
return mDepth;
|
||||
}
|
||||
|
||||
inline
|
||||
uint256 const&
|
||||
SHAMapNodeID::getNodeID () const
|
||||
{
|
||||
return mNodeID;
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapNodeID::isValid () const
|
||||
{
|
||||
return (mDepth >= 0) && (mDepth < 64);
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapNodeID::isRoot () const
|
||||
{
|
||||
return mDepth == 0;
|
||||
}
|
||||
|
||||
inline
|
||||
SHAMapNodeID
|
||||
SHAMapNodeID::getParentNodeID () const
|
||||
{
|
||||
assert (mDepth);
|
||||
return SHAMapNodeID (mDepth - 1, mNodeID);
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapNodeID::operator< (const SHAMapNodeID& n) const
|
||||
{
|
||||
return std::tie(mDepth, mNodeID) < std::tie(n.mDepth, n.mNodeID);
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapNodeID::operator> (const SHAMapNodeID& n) const
|
||||
{
|
||||
return n < *this;
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapNodeID::operator<= (const SHAMapNodeID& n) const
|
||||
{
|
||||
return !(n < *this);
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapNodeID::operator>= (const SHAMapNodeID& n) const
|
||||
{
|
||||
return !(*this < n);
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapNodeID::operator== (const SHAMapNodeID& n) const
|
||||
{
|
||||
return (mDepth == n.mDepth) && (mNodeID == n.mNodeID);
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapNodeID::operator!= (const SHAMapNodeID& n) const
|
||||
{
|
||||
return !(*this == n);
|
||||
}
|
||||
|
||||
inline std::ostream& operator<< (std::ostream& out, SHAMapNodeID const& node)
|
||||
{
|
||||
return out << node.getString ();
|
||||
|
||||
@@ -20,6 +20,7 @@
|
||||
#ifndef RIPPLE_SHAMAP_SHAMAPSYNCFILTER_H_INCLUDED
|
||||
#define RIPPLE_SHAMAP_SHAMAPSYNCFILTER_H_INCLUDED
|
||||
|
||||
#include <ripple/shamap/SHAMapNodeID.h>
|
||||
#include <ripple/shamap/SHAMapTreeNode.h>
|
||||
|
||||
/** Callback for filtering SHAMap during sync. */
|
||||
@@ -28,7 +29,10 @@ namespace ripple {
|
||||
class SHAMapSyncFilter
|
||||
{
|
||||
public:
|
||||
virtual ~SHAMapSyncFilter () { }
|
||||
virtual ~SHAMapSyncFilter () = default;
|
||||
SHAMapSyncFilter() = default;
|
||||
SHAMapSyncFilter(SHAMapSyncFilter const&) = delete;
|
||||
SHAMapSyncFilter& operator=(SHAMapSyncFilter const&) = delete;
|
||||
|
||||
// Note that the nodeData is overwritten by this call
|
||||
virtual void gotNode (bool fromFilter,
|
||||
|
||||
@@ -22,14 +22,15 @@
|
||||
|
||||
#include <ripple/shamap/SHAMapItem.h>
|
||||
#include <ripple/shamap/SHAMapNodeID.h>
|
||||
#include <ripple/shamap/TreeNodeCache.h>
|
||||
#include <ripple/basics/CountedObject.h>
|
||||
#include <ripple/basics/TaggedCache.h>
|
||||
#include <beast/utility/Journal.h>
|
||||
|
||||
namespace ripple {
|
||||
#include <cstdint>
|
||||
#include <memory>
|
||||
#include <mutex>
|
||||
#include <string>
|
||||
|
||||
class SHAMap;
|
||||
namespace ripple {
|
||||
|
||||
enum SHANodeFormat
|
||||
{
|
||||
@@ -39,14 +40,8 @@ enum SHANodeFormat
|
||||
};
|
||||
|
||||
class SHAMapTreeNode
|
||||
: public CountedObject <SHAMapTreeNode>
|
||||
{
|
||||
public:
|
||||
static char const* getCountedObjectName () { return "SHAMapTreeNode"; }
|
||||
|
||||
typedef std::shared_ptr<SHAMapTreeNode> pointer;
|
||||
typedef const std::shared_ptr<SHAMapTreeNode>& ref;
|
||||
|
||||
enum TNType
|
||||
{
|
||||
tnERROR = 0,
|
||||
@@ -56,160 +51,210 @@ public:
|
||||
tnACCOUNT_STATE = 4
|
||||
};
|
||||
|
||||
private:
|
||||
uint256 mHash;
|
||||
uint256 mHashes[16];
|
||||
std::shared_ptr<SHAMapTreeNode> mChildren[16];
|
||||
std::shared_ptr<SHAMapItem> mItem;
|
||||
std::uint32_t mSeq;
|
||||
TNType mType;
|
||||
int mIsBranch;
|
||||
std::uint32_t mFullBelowGen;
|
||||
|
||||
static std::mutex childLock;
|
||||
|
||||
public:
|
||||
SHAMapTreeNode (const SHAMapTreeNode&) = delete;
|
||||
SHAMapTreeNode& operator= (const SHAMapTreeNode&) = delete;
|
||||
|
||||
SHAMapTreeNode (std::uint32_t seq); // empty node
|
||||
SHAMapTreeNode (const SHAMapTreeNode & node, std::uint32_t seq); // copy node from older tree
|
||||
SHAMapTreeNode (SHAMapItem::ref item, TNType type, std::uint32_t seq);
|
||||
|
||||
// raw node functions
|
||||
SHAMapTreeNode (std::shared_ptr<SHAMapItem> const& item, TNType type, std::uint32_t seq);
|
||||
SHAMapTreeNode (Blob const & data, std::uint32_t seq,
|
||||
SHANodeFormat format, uint256 const& hash, bool hashValid);
|
||||
|
||||
void addRaw (Serializer&, SHANodeFormat format);
|
||||
uint256 const& getNodeHash () const;
|
||||
|
||||
// node functions
|
||||
std::uint32_t getSeq () const
|
||||
{
|
||||
return mSeq;
|
||||
}
|
||||
|
||||
void setSeq (std::uint32_t s)
|
||||
{
|
||||
mSeq = s;
|
||||
}
|
||||
|
||||
uint256 const& getNodeHash () const
|
||||
{
|
||||
return mHash;
|
||||
}
|
||||
|
||||
TNType getType () const
|
||||
{
|
||||
return mType;
|
||||
}
|
||||
|
||||
// type functions
|
||||
bool isLeaf () const
|
||||
{
|
||||
return (mType == tnTRANSACTION_NM) || (mType == tnTRANSACTION_MD) ||
|
||||
(mType == tnACCOUNT_STATE);
|
||||
}
|
||||
|
||||
bool isInner () const
|
||||
{
|
||||
return mType == tnINNER;
|
||||
}
|
||||
|
||||
bool isInBounds (SHAMapNodeID const &id) const
|
||||
{
|
||||
// Nodes at depth 64 must be leaves
|
||||
return (!isInner() || (id.getDepth() < 64));
|
||||
}
|
||||
|
||||
bool isValid () const
|
||||
{
|
||||
return mType != tnERROR;
|
||||
}
|
||||
|
||||
bool isTransaction () const
|
||||
{
|
||||
return (mType == tnTRANSACTION_NM) || (mType == tnTRANSACTION_MD);
|
||||
}
|
||||
|
||||
bool hasMetaData () const
|
||||
{
|
||||
return mType == tnTRANSACTION_MD;
|
||||
}
|
||||
|
||||
bool isAccountState () const
|
||||
{
|
||||
return mType == tnACCOUNT_STATE;
|
||||
}
|
||||
|
||||
// inner node functions
|
||||
bool isInnerNode () const
|
||||
{
|
||||
return !mItem;
|
||||
}
|
||||
|
||||
// We are modifying the child hash
|
||||
bool setChild (int m, uint256 const& hash, std::shared_ptr<SHAMapTreeNode> const& child);
|
||||
|
||||
// We are sharing/unsharing the child
|
||||
public: // public only to SHAMap
|
||||
bool setChild (int m, uint256 const& hash,
|
||||
std::shared_ptr<SHAMapTreeNode> const& child);
|
||||
void shareChild (int m, std::shared_ptr<SHAMapTreeNode> const& child);
|
||||
|
||||
bool isEmptyBranch (int m) const
|
||||
{
|
||||
return (mIsBranch & (1 << m)) == 0;
|
||||
}
|
||||
// node functions
|
||||
std::uint32_t getSeq () const;
|
||||
void setSeq (std::uint32_t s);
|
||||
TNType getType () const;
|
||||
|
||||
// type functions
|
||||
bool isLeaf () const;
|
||||
bool isInner () const;
|
||||
bool isInBounds (SHAMapNodeID const &id) const;
|
||||
bool isValid () const;
|
||||
|
||||
// inner node functions
|
||||
bool isInnerNode () const;
|
||||
bool isEmptyBranch (int m) const;
|
||||
bool isEmpty () const;
|
||||
|
||||
int getBranchCount () const;
|
||||
|
||||
void makeInner ();
|
||||
|
||||
uint256 const& getChildHash (int m) const
|
||||
{
|
||||
assert ((m >= 0) && (m < 16) && (mType == tnINNER));
|
||||
return mHashes[m];
|
||||
}
|
||||
uint256 const& getChildHash (int m) const;
|
||||
|
||||
// item node function
|
||||
bool hasItem () const
|
||||
{
|
||||
return bool(mItem);
|
||||
}
|
||||
|
||||
SHAMapItem::ref peekItem () const
|
||||
{
|
||||
return mItem;
|
||||
}
|
||||
|
||||
bool setItem (SHAMapItem::ref i, TNType type);
|
||||
bool hasItem () const;
|
||||
std::shared_ptr<SHAMapItem> const& peekItem () const;
|
||||
bool setItem (std::shared_ptr<SHAMapItem> const& i, TNType type);
|
||||
|
||||
// sync functions
|
||||
bool isFullBelow (std::uint32_t generation) const
|
||||
{
|
||||
return mFullBelowGen == generation;
|
||||
}
|
||||
|
||||
void setFullBelowGen (std::uint32_t gen)
|
||||
{
|
||||
mFullBelowGen = gen;
|
||||
}
|
||||
|
||||
// VFALCO Why are these virtual?
|
||||
virtual void dump (SHAMapNodeID const&, beast::Journal journal);
|
||||
virtual std::string getString (SHAMapNodeID const&) const;
|
||||
bool isFullBelow (std::uint32_t generation) const;
|
||||
void setFullBelowGen (std::uint32_t gen);
|
||||
|
||||
SHAMapTreeNode* getChildPointer (int branch);
|
||||
std::shared_ptr<SHAMapTreeNode> getChild (int branch);
|
||||
void canonicalizeChild (int branch, std::shared_ptr<SHAMapTreeNode>& node);
|
||||
|
||||
SHAMapTreeNode::pointer getChild (int branch);
|
||||
|
||||
void canonicalizeChild (int branch, SHAMapTreeNode::pointer& node);
|
||||
// debugging
|
||||
#ifdef BEAST_DEBUG
|
||||
void dump (SHAMapNodeID const&, beast::Journal journal);
|
||||
#endif
|
||||
std::string getString (SHAMapNodeID const&) const;
|
||||
|
||||
private:
|
||||
|
||||
// VFALCO TODO remove the use of friend
|
||||
friend class SHAMap;
|
||||
|
||||
uint256 mHash;
|
||||
uint256 mHashes[16];
|
||||
SHAMapTreeNode::pointer mChildren[16];
|
||||
SHAMapItem::pointer mItem;
|
||||
std::uint32_t mSeq;
|
||||
TNType mType;
|
||||
int mIsBranch;
|
||||
std::uint32_t mFullBelowGen;
|
||||
|
||||
bool isTransaction () const;
|
||||
bool hasMetaData () const;
|
||||
bool isAccountState () const;
|
||||
bool updateHash ();
|
||||
|
||||
static std::mutex childLock;
|
||||
};
|
||||
|
||||
inline
|
||||
std::uint32_t
|
||||
SHAMapTreeNode::getSeq () const
|
||||
{
|
||||
return mSeq;
|
||||
}
|
||||
|
||||
inline
|
||||
void
|
||||
SHAMapTreeNode::setSeq (std::uint32_t s)
|
||||
{
|
||||
mSeq = s;
|
||||
}
|
||||
|
||||
inline
|
||||
uint256 const&
|
||||
SHAMapTreeNode::getNodeHash () const
|
||||
{
|
||||
return mHash;
|
||||
}
|
||||
|
||||
inline
|
||||
SHAMapTreeNode::TNType
|
||||
SHAMapTreeNode::getType () const
|
||||
{
|
||||
return mType;
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapTreeNode::isLeaf () const
|
||||
{
|
||||
return (mType == tnTRANSACTION_NM) || (mType == tnTRANSACTION_MD) ||
|
||||
(mType == tnACCOUNT_STATE);
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapTreeNode::isInner () const
|
||||
{
|
||||
return mType == tnINNER;
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapTreeNode::isInBounds (SHAMapNodeID const &id) const
|
||||
{
|
||||
// Nodes at depth 64 must be leaves
|
||||
return (!isInner() || (id.getDepth() < 64));
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapTreeNode::isValid () const
|
||||
{
|
||||
return mType != tnERROR;
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapTreeNode::isTransaction () const
|
||||
{
|
||||
return (mType == tnTRANSACTION_NM) || (mType == tnTRANSACTION_MD);
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapTreeNode::hasMetaData () const
|
||||
{
|
||||
return mType == tnTRANSACTION_MD;
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapTreeNode::isAccountState () const
|
||||
{
|
||||
return mType == tnACCOUNT_STATE;
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapTreeNode::isInnerNode () const
|
||||
{
|
||||
return !mItem;
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapTreeNode::isEmptyBranch (int m) const
|
||||
{
|
||||
return (mIsBranch & (1 << m)) == 0;
|
||||
}
|
||||
|
||||
inline
|
||||
uint256 const&
|
||||
SHAMapTreeNode::getChildHash (int m) const
|
||||
{
|
||||
assert ((m >= 0) && (m < 16) && (mType == tnINNER));
|
||||
return mHashes[m];
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapTreeNode::hasItem () const
|
||||
{
|
||||
return bool(mItem);
|
||||
}
|
||||
|
||||
inline
|
||||
std::shared_ptr<SHAMapItem> const&
|
||||
SHAMapTreeNode::peekItem () const
|
||||
{
|
||||
return mItem;
|
||||
}
|
||||
|
||||
inline
|
||||
bool
|
||||
SHAMapTreeNode::isFullBelow (std::uint32_t generation) const
|
||||
{
|
||||
return mFullBelowGen == generation;
|
||||
}
|
||||
|
||||
inline
|
||||
void
|
||||
SHAMapTreeNode::setFullBelowGen (std::uint32_t gen)
|
||||
{
|
||||
mFullBelowGen = gen;
|
||||
}
|
||||
|
||||
} // ripple
|
||||
|
||||
#endif
|
||||
|
||||
@@ -31,15 +31,15 @@ SHAMap::SHAMap (
|
||||
std::uint32_t seq)
|
||||
: f_ (f)
|
||||
, journal_(journal)
|
||||
, mSeq (seq)
|
||||
, mLedgerSeq (0)
|
||||
, mState (smsModifying)
|
||||
, mType (t)
|
||||
, seq_ (seq)
|
||||
, ledgerSeq_ (0)
|
||||
, state_ (SHAMapState::Modifying)
|
||||
, type_ (t)
|
||||
{
|
||||
assert (mSeq != 0);
|
||||
assert (seq_ != 0);
|
||||
|
||||
root = std::make_shared<SHAMapTreeNode> (mSeq);
|
||||
root->makeInner ();
|
||||
root_ = std::make_shared<SHAMapTreeNode> (seq_);
|
||||
root_->makeInner ();
|
||||
}
|
||||
|
||||
SHAMap::SHAMap (
|
||||
@@ -49,33 +49,33 @@ SHAMap::SHAMap (
|
||||
beast::Journal journal)
|
||||
: f_ (f)
|
||||
, journal_(journal)
|
||||
, mSeq (1)
|
||||
, mLedgerSeq (0)
|
||||
, mState (smsSynching)
|
||||
, mType (t)
|
||||
, seq_ (1)
|
||||
, ledgerSeq_ (0)
|
||||
, state_ (SHAMapState::Synching)
|
||||
, type_ (t)
|
||||
{
|
||||
root = std::make_shared<SHAMapTreeNode> (mSeq);
|
||||
root->makeInner ();
|
||||
root_ = std::make_shared<SHAMapTreeNode> (seq_);
|
||||
root_->makeInner ();
|
||||
}
|
||||
|
||||
SHAMap::~SHAMap ()
|
||||
{
|
||||
mState = smsInvalid;
|
||||
state_ = SHAMapState::Invalid;
|
||||
}
|
||||
|
||||
SHAMap::pointer SHAMap::snapShot (bool isMutable)
|
||||
std::shared_ptr<SHAMap>
|
||||
SHAMap::snapShot (bool isMutable) const
|
||||
{
|
||||
SHAMap::pointer ret = std::make_shared<SHAMap> (
|
||||
mType, f_, journal_);
|
||||
auto ret = std::make_shared<SHAMap> (type_, f_, journal_);
|
||||
SHAMap& newMap = *ret;
|
||||
|
||||
if (!isMutable)
|
||||
newMap.mState = smsImmutable;
|
||||
newMap.state_ = SHAMapState::Immutable;
|
||||
|
||||
newMap.mSeq = mSeq + 1;
|
||||
newMap.root = root;
|
||||
newMap.seq_ = seq_ + 1;
|
||||
newMap.root_ = root_;
|
||||
|
||||
if ((mState != smsImmutable) || !isMutable)
|
||||
if ((state_ != SHAMapState::Immutable) || !isMutable)
|
||||
{
|
||||
// If either map may change, they cannot share nodes
|
||||
newMap.unshare ();
|
||||
@@ -91,7 +91,7 @@ SHAMap::getStack (uint256 const& id, bool include_nonmatching_leaf)
|
||||
// produce a stack of nodes along the way, with the terminal node at the top
|
||||
SharedPtrNodeStack stack;
|
||||
|
||||
SHAMapTreeNode::pointer node = root;
|
||||
std::shared_ptr<SHAMapTreeNode> node = root_;
|
||||
SHAMapNodeID nodeID;
|
||||
|
||||
while (!node->isLeaf ())
|
||||
@@ -116,19 +116,19 @@ SHAMap::getStack (uint256 const& id, bool include_nonmatching_leaf)
|
||||
|
||||
void
|
||||
SHAMap::dirtyUp (SharedPtrNodeStack& stack,
|
||||
uint256 const& target, SHAMapTreeNode::pointer child)
|
||||
uint256 const& target, std::shared_ptr<SHAMapTreeNode> child)
|
||||
{
|
||||
// walk the tree up from through the inner nodes to the root
|
||||
// walk the tree up from through the inner nodes to the root_
|
||||
// update hashes and links
|
||||
// stack is a path of inner nodes up to, but not including, child
|
||||
// child can be an inner node or a leaf
|
||||
|
||||
assert ((mState != smsSynching) && (mState != smsImmutable));
|
||||
assert (child && (child->getSeq() == mSeq));
|
||||
assert ((state_ != SHAMapState::Synching) && (state_ != SHAMapState::Immutable));
|
||||
assert (child && (child->getSeq() == seq_));
|
||||
|
||||
while (!stack.empty ())
|
||||
{
|
||||
SHAMapTreeNode::pointer node = stack.top ().first;
|
||||
std::shared_ptr<SHAMapTreeNode> node = stack.top ().first;
|
||||
SHAMapNodeID nodeID = stack.top ().second;
|
||||
stack.pop ();
|
||||
assert (node->isInnerNode ());
|
||||
@@ -156,7 +156,7 @@ SHAMap::dirtyUp (SharedPtrNodeStack& stack,
|
||||
|
||||
SHAMapTreeNode* SHAMap::walkToPointer (uint256 const& id)
|
||||
{
|
||||
SHAMapTreeNode* inNode = root.get ();
|
||||
SHAMapTreeNode* inNode = root_.get ();
|
||||
SHAMapNodeID nodeID;
|
||||
uint256 nodeHash;
|
||||
|
||||
@@ -174,11 +174,12 @@ SHAMapTreeNode* SHAMap::walkToPointer (uint256 const& id)
|
||||
return (inNode->peekItem()->getTag () == id) ? inNode : nullptr;
|
||||
}
|
||||
|
||||
SHAMapTreeNode::pointer SHAMap::fetchNodeFromDB (uint256 const& hash)
|
||||
std::shared_ptr<SHAMapTreeNode>
|
||||
SHAMap::fetchNodeFromDB (uint256 const& hash)
|
||||
{
|
||||
SHAMapTreeNode::pointer node;
|
||||
std::shared_ptr<SHAMapTreeNode> node;
|
||||
|
||||
if (mBacked)
|
||||
if (backed_)
|
||||
{
|
||||
NodeObject::pointer obj = f_.db().fetch (hash);
|
||||
if (obj)
|
||||
@@ -193,13 +194,13 @@ SHAMapTreeNode::pointer SHAMap::fetchNodeFromDB (uint256 const& hash)
|
||||
{
|
||||
if (journal_.warning) journal_.warning <<
|
||||
"Invalid DB node " << hash;
|
||||
return SHAMapTreeNode::pointer ();
|
||||
return std::shared_ptr<SHAMapTreeNode> ();
|
||||
}
|
||||
}
|
||||
else if (mLedgerSeq != 0)
|
||||
else if (ledgerSeq_ != 0)
|
||||
{
|
||||
f_.missing_node(mLedgerSeq);
|
||||
mLedgerSeq = 0;
|
||||
f_.missing_node(ledgerSeq_);
|
||||
ledgerSeq_ = 0;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -207,12 +208,12 @@ SHAMapTreeNode::pointer SHAMap::fetchNodeFromDB (uint256 const& hash)
|
||||
}
|
||||
|
||||
// See if a sync filter has a node
|
||||
SHAMapTreeNode::pointer SHAMap::checkFilter (
|
||||
std::shared_ptr<SHAMapTreeNode> SHAMap::checkFilter (
|
||||
uint256 const& hash,
|
||||
SHAMapNodeID const& id,
|
||||
SHAMapSyncFilter* filter)
|
||||
SHAMapSyncFilter* filter) const
|
||||
{
|
||||
SHAMapTreeNode::pointer node;
|
||||
std::shared_ptr<SHAMapTreeNode> node;
|
||||
Blob nodeData;
|
||||
|
||||
if (filter->haveNode (id, hash, nodeData))
|
||||
@@ -222,7 +223,7 @@ SHAMapTreeNode::pointer SHAMap::checkFilter (
|
||||
|
||||
filter->gotNode (true, id, hash, nodeData, node->getType ());
|
||||
|
||||
if (mBacked)
|
||||
if (backed_)
|
||||
canonicalize (hash, node);
|
||||
}
|
||||
|
||||
@@ -231,16 +232,16 @@ SHAMapTreeNode::pointer SHAMap::checkFilter (
|
||||
|
||||
// Get a node without throwing
|
||||
// Used on maps where missing nodes are expected
|
||||
SHAMapTreeNode::pointer SHAMap::fetchNodeNT(
|
||||
std::shared_ptr<SHAMapTreeNode> SHAMap::fetchNodeNT(
|
||||
SHAMapNodeID const& id,
|
||||
uint256 const& hash,
|
||||
SHAMapSyncFilter* filter)
|
||||
{
|
||||
SHAMapTreeNode::pointer node = getCache (hash);
|
||||
std::shared_ptr<SHAMapTreeNode> node = getCache (hash);
|
||||
if (node)
|
||||
return node;
|
||||
|
||||
if (mBacked)
|
||||
if (backed_)
|
||||
{
|
||||
node = fetchNodeFromDB (hash);
|
||||
if (node)
|
||||
@@ -256,23 +257,23 @@ SHAMapTreeNode::pointer SHAMap::fetchNodeNT(
|
||||
return node;
|
||||
}
|
||||
|
||||
SHAMapTreeNode::pointer SHAMap::fetchNodeNT (uint256 const& hash)
|
||||
std::shared_ptr<SHAMapTreeNode> SHAMap::fetchNodeNT (uint256 const& hash)
|
||||
{
|
||||
SHAMapTreeNode::pointer node = getCache (hash);
|
||||
std::shared_ptr<SHAMapTreeNode> node = getCache (hash);
|
||||
|
||||
if (!node && mBacked)
|
||||
if (!node && backed_)
|
||||
node = fetchNodeFromDB (hash);
|
||||
|
||||
return node;
|
||||
}
|
||||
|
||||
// Throw if the node is missing
|
||||
SHAMapTreeNode::pointer SHAMap::fetchNode (uint256 const& hash)
|
||||
std::shared_ptr<SHAMapTreeNode> SHAMap::fetchNode (uint256 const& hash)
|
||||
{
|
||||
SHAMapTreeNode::pointer node = fetchNodeNT (hash);
|
||||
std::shared_ptr<SHAMapTreeNode> node = fetchNodeNT (hash);
|
||||
|
||||
if (!node)
|
||||
throw SHAMapMissingNode (mType, hash);
|
||||
throw SHAMapMissingNode (type_, hash);
|
||||
|
||||
return node;
|
||||
}
|
||||
@@ -282,17 +283,18 @@ SHAMapTreeNode* SHAMap::descendThrow (SHAMapTreeNode* parent, int branch)
|
||||
SHAMapTreeNode* ret = descend (parent, branch);
|
||||
|
||||
if (! ret && ! parent->isEmptyBranch (branch))
|
||||
throw SHAMapMissingNode (mType, parent->getChildHash (branch));
|
||||
throw SHAMapMissingNode (type_, parent->getChildHash (branch));
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
SHAMapTreeNode::pointer SHAMap::descendThrow (SHAMapTreeNode::ref parent, int branch)
|
||||
std::shared_ptr<SHAMapTreeNode>
|
||||
SHAMap::descendThrow (std::shared_ptr<SHAMapTreeNode> const& parent, int branch)
|
||||
{
|
||||
SHAMapTreeNode::pointer ret = descend (parent, branch);
|
||||
std::shared_ptr<SHAMapTreeNode> ret = descend (parent, branch);
|
||||
|
||||
if (! ret && ! parent->isEmptyBranch (branch))
|
||||
throw SHAMapMissingNode (mType, parent->getChildHash (branch));
|
||||
throw SHAMapMissingNode (type_, parent->getChildHash (branch));
|
||||
|
||||
return ret;
|
||||
}
|
||||
@@ -300,10 +302,10 @@ SHAMapTreeNode::pointer SHAMap::descendThrow (SHAMapTreeNode::ref parent, int br
|
||||
SHAMapTreeNode* SHAMap::descend (SHAMapTreeNode* parent, int branch)
|
||||
{
|
||||
SHAMapTreeNode* ret = parent->getChildPointer (branch);
|
||||
if (ret || !mBacked)
|
||||
if (ret || !backed_)
|
||||
return ret;
|
||||
|
||||
SHAMapTreeNode::pointer node = fetchNodeNT (parent->getChildHash (branch));
|
||||
std::shared_ptr<SHAMapTreeNode> node = fetchNodeNT (parent->getChildHash (branch));
|
||||
if (!node)
|
||||
return nullptr;
|
||||
|
||||
@@ -311,10 +313,11 @@ SHAMapTreeNode* SHAMap::descend (SHAMapTreeNode* parent, int branch)
|
||||
return node.get ();
|
||||
}
|
||||
|
||||
SHAMapTreeNode::pointer SHAMap::descend (SHAMapTreeNode::ref parent, int branch)
|
||||
std::shared_ptr<SHAMapTreeNode>
|
||||
SHAMap::descend (std::shared_ptr<SHAMapTreeNode> const& parent, int branch)
|
||||
{
|
||||
SHAMapTreeNode::pointer node = parent->getChild (branch);
|
||||
if (node || !mBacked)
|
||||
std::shared_ptr<SHAMapTreeNode> node = parent->getChild (branch);
|
||||
if (node || !backed_)
|
||||
return node;
|
||||
|
||||
node = fetchNode (parent->getChildHash (branch));
|
||||
@@ -327,10 +330,11 @@ SHAMapTreeNode::pointer SHAMap::descend (SHAMapTreeNode::ref parent, int branch)
|
||||
|
||||
// Gets the node that would be hooked to this branch,
|
||||
// but doesn't hook it up.
|
||||
SHAMapTreeNode::pointer SHAMap::descendNoStore (SHAMapTreeNode::ref parent, int branch)
|
||||
std::shared_ptr<SHAMapTreeNode>
|
||||
SHAMap::descendNoStore (std::shared_ptr<SHAMapTreeNode> const& parent, int branch)
|
||||
{
|
||||
SHAMapTreeNode::pointer ret = parent->getChild (branch);
|
||||
if (!ret && mBacked)
|
||||
std::shared_ptr<SHAMapTreeNode> ret = parent->getChild (branch);
|
||||
if (!ret && backed_)
|
||||
ret = fetchNode (parent->getChildHash (branch));
|
||||
return ret;
|
||||
}
|
||||
@@ -349,7 +353,7 @@ SHAMap::descend (SHAMapTreeNode * parent, SHAMapNodeID const& parentID,
|
||||
|
||||
if (!child)
|
||||
{
|
||||
SHAMapTreeNode::pointer childNode = fetchNodeNT (childID, childHash, filter);
|
||||
std::shared_ptr<SHAMapTreeNode> childNode = fetchNodeNT (childID, childHash, filter);
|
||||
|
||||
if (childNode)
|
||||
{
|
||||
@@ -362,7 +366,7 @@ SHAMap::descend (SHAMapTreeNode * parent, SHAMapNodeID const& parentID,
|
||||
}
|
||||
|
||||
SHAMapTreeNode* SHAMap::descendAsync (SHAMapTreeNode* parent, int branch,
|
||||
SHAMapNodeID const& childID, SHAMapSyncFilter * filter, bool & pending)
|
||||
SHAMapNodeID const& childID, SHAMapSyncFilter * filter, bool & pending) const
|
||||
{
|
||||
pending = false;
|
||||
|
||||
@@ -372,13 +376,13 @@ SHAMapTreeNode* SHAMap::descendAsync (SHAMapTreeNode* parent, int branch,
|
||||
|
||||
uint256 const& hash = parent->getChildHash (branch);
|
||||
|
||||
SHAMapTreeNode::pointer ptr = getCache (hash);
|
||||
std::shared_ptr<SHAMapTreeNode> ptr = getCache (hash);
|
||||
if (!ptr)
|
||||
{
|
||||
if (filter)
|
||||
ptr = checkFilter (hash, childID, filter);
|
||||
|
||||
if (!ptr && mBacked)
|
||||
if (!ptr && backed_)
|
||||
{
|
||||
NodeObject::pointer obj;
|
||||
if (! f_.db().asyncFetch (hash, obj))
|
||||
@@ -391,7 +395,7 @@ SHAMapTreeNode* SHAMap::descendAsync (SHAMapTreeNode* parent, int branch,
|
||||
|
||||
ptr = std::make_shared <SHAMapTreeNode> (obj->getData(), 0, snfPREFIX, hash, true);
|
||||
|
||||
if (mBacked)
|
||||
if (backed_)
|
||||
canonicalize (hash, ptr);
|
||||
}
|
||||
}
|
||||
@@ -403,22 +407,22 @@ SHAMapTreeNode* SHAMap::descendAsync (SHAMapTreeNode* parent, int branch,
|
||||
}
|
||||
|
||||
void
|
||||
SHAMap::unshareNode (SHAMapTreeNode::pointer& node, SHAMapNodeID const& nodeID)
|
||||
SHAMap::unshareNode (std::shared_ptr<SHAMapTreeNode>& node, SHAMapNodeID const& nodeID)
|
||||
{
|
||||
// make sure the node is suitable for the intended operation (copy on write)
|
||||
assert (node->isValid ());
|
||||
assert (node->getSeq () <= mSeq);
|
||||
assert (node->getSeq () <= seq_);
|
||||
|
||||
if (node->getSeq () != mSeq)
|
||||
if (node->getSeq () != seq_)
|
||||
{
|
||||
// have a CoW
|
||||
assert (mState != smsImmutable);
|
||||
assert (state_ != SHAMapState::Immutable);
|
||||
|
||||
node = std::make_shared<SHAMapTreeNode> (*node, mSeq); // here's to the new node, same as the old node
|
||||
node = std::make_shared<SHAMapTreeNode> (*node, seq_); // here's to the new node, same as the old node
|
||||
assert (node->isValid ());
|
||||
|
||||
if (nodeID.isRoot ())
|
||||
root = node;
|
||||
root_ = node;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -475,7 +479,7 @@ SHAMap::lastBelow (SHAMapTreeNode* node)
|
||||
while (true);
|
||||
}
|
||||
|
||||
SHAMapItem::pointer
|
||||
std::shared_ptr<SHAMapItem>
|
||||
SHAMap::onlyBelow (SHAMapTreeNode* node)
|
||||
{
|
||||
// If there is only one item below this node, return it
|
||||
@@ -488,7 +492,7 @@ SHAMap::onlyBelow (SHAMapTreeNode* node)
|
||||
if (!node->isEmptyBranch (i))
|
||||
{
|
||||
if (nextNode)
|
||||
return SHAMapItem::pointer ();
|
||||
return std::shared_ptr<SHAMapItem> ();
|
||||
|
||||
nextNode = descendThrow (node, i);
|
||||
}
|
||||
@@ -497,24 +501,24 @@ SHAMap::onlyBelow (SHAMapTreeNode* node)
|
||||
if (!nextNode)
|
||||
{
|
||||
assert (false);
|
||||
return SHAMapItem::pointer ();
|
||||
return std::shared_ptr<SHAMapItem> ();
|
||||
}
|
||||
|
||||
node = nextNode;
|
||||
}
|
||||
|
||||
// An inner node must have at least one leaf
|
||||
// below it, unless it's the root
|
||||
assert (node->hasItem () || (node == root.get ()));
|
||||
// below it, unless it's the root_
|
||||
assert (node->hasItem () || (node == root_.get ()));
|
||||
|
||||
return node->peekItem ();
|
||||
}
|
||||
|
||||
static const SHAMapItem::pointer no_item;
|
||||
static const std::shared_ptr<SHAMapItem> no_item;
|
||||
|
||||
SHAMapItem::pointer SHAMap::peekFirstItem ()
|
||||
std::shared_ptr<SHAMapItem> SHAMap::peekFirstItem ()
|
||||
{
|
||||
SHAMapTreeNode* node = firstBelow (root.get ());
|
||||
SHAMapTreeNode* node = firstBelow (root_.get ());
|
||||
|
||||
if (!node)
|
||||
return no_item;
|
||||
@@ -522,9 +526,9 @@ SHAMapItem::pointer SHAMap::peekFirstItem ()
|
||||
return node->peekItem ();
|
||||
}
|
||||
|
||||
SHAMapItem::pointer SHAMap::peekFirstItem (SHAMapTreeNode::TNType& type)
|
||||
std::shared_ptr<SHAMapItem> SHAMap::peekFirstItem (SHAMapTreeNode::TNType& type)
|
||||
{
|
||||
SHAMapTreeNode* node = firstBelow (root.get ());
|
||||
SHAMapTreeNode* node = firstBelow (root_.get ());
|
||||
|
||||
if (!node)
|
||||
return no_item;
|
||||
@@ -533,9 +537,9 @@ SHAMapItem::pointer SHAMap::peekFirstItem (SHAMapTreeNode::TNType& type)
|
||||
return node->peekItem ();
|
||||
}
|
||||
|
||||
SHAMapItem::pointer SHAMap::peekLastItem ()
|
||||
std::shared_ptr<SHAMapItem> SHAMap::peekLastItem ()
|
||||
{
|
||||
SHAMapTreeNode* node = lastBelow (root.get ());
|
||||
SHAMapTreeNode* node = lastBelow (root_.get ());
|
||||
|
||||
if (!node)
|
||||
return no_item;
|
||||
@@ -543,13 +547,13 @@ SHAMapItem::pointer SHAMap::peekLastItem ()
|
||||
return node->peekItem ();
|
||||
}
|
||||
|
||||
SHAMapItem::pointer SHAMap::peekNextItem (uint256 const& id)
|
||||
std::shared_ptr<SHAMapItem> SHAMap::peekNextItem (uint256 const& id)
|
||||
{
|
||||
SHAMapTreeNode::TNType type;
|
||||
return peekNextItem (id, type);
|
||||
}
|
||||
|
||||
SHAMapItem::pointer SHAMap::peekNextItem (uint256 const& id, SHAMapTreeNode::TNType& type)
|
||||
std::shared_ptr<SHAMapItem> SHAMap::peekNextItem (uint256 const& id, SHAMapTreeNode::TNType& type)
|
||||
{
|
||||
// Get a pointer to the next item in the tree after a given item - item need not be in tree
|
||||
|
||||
@@ -592,7 +596,7 @@ SHAMapItem::pointer SHAMap::peekNextItem (uint256 const& id, SHAMapTreeNode::TNT
|
||||
}
|
||||
|
||||
// Get a pointer to the previous item in the tree after a given item - item need not be in tree
|
||||
SHAMapItem::pointer SHAMap::peekPrevItem (uint256 const& id)
|
||||
std::shared_ptr<SHAMapItem> SHAMap::peekPrevItem (uint256 const& id)
|
||||
{
|
||||
auto stack = getStack (id, true);
|
||||
|
||||
@@ -625,7 +629,7 @@ SHAMapItem::pointer SHAMap::peekPrevItem (uint256 const& id)
|
||||
return no_item;
|
||||
}
|
||||
|
||||
SHAMapItem::pointer SHAMap::peekItem (uint256 const& id)
|
||||
std::shared_ptr<SHAMapItem> SHAMap::peekItem (uint256 const& id)
|
||||
{
|
||||
SHAMapTreeNode* leaf = walkToPointer (id);
|
||||
|
||||
@@ -635,7 +639,7 @@ SHAMapItem::pointer SHAMap::peekItem (uint256 const& id)
|
||||
return leaf->peekItem ();
|
||||
}
|
||||
|
||||
SHAMapItem::pointer SHAMap::peekItem (uint256 const& id, SHAMapTreeNode::TNType& type)
|
||||
std::shared_ptr<SHAMapItem> SHAMap::peekItem (uint256 const& id, SHAMapTreeNode::TNType& type)
|
||||
{
|
||||
SHAMapTreeNode* leaf = walkToPointer (id);
|
||||
|
||||
@@ -646,7 +650,7 @@ SHAMapItem::pointer SHAMap::peekItem (uint256 const& id, SHAMapTreeNode::TNType&
|
||||
return leaf->peekItem ();
|
||||
}
|
||||
|
||||
SHAMapItem::pointer SHAMap::peekItem (uint256 const& id, uint256& hash)
|
||||
std::shared_ptr<SHAMapItem> SHAMap::peekItem (uint256 const& id, uint256& hash)
|
||||
{
|
||||
SHAMapTreeNode* leaf = walkToPointer (id);
|
||||
|
||||
@@ -668,14 +672,14 @@ bool SHAMap::hasItem (uint256 const& id)
|
||||
bool SHAMap::delItem (uint256 const& id)
|
||||
{
|
||||
// delete the item with this ID
|
||||
assert (mState != smsImmutable);
|
||||
assert (state_ != SHAMapState::Immutable);
|
||||
|
||||
auto stack = getStack (id, true);
|
||||
|
||||
if (stack.empty ())
|
||||
throw (std::runtime_error ("missing node"));
|
||||
|
||||
SHAMapTreeNode::pointer leaf = stack.top ().first;
|
||||
std::shared_ptr<SHAMapTreeNode> leaf = stack.top ().first;
|
||||
SHAMapNodeID leafID = stack.top ().second;
|
||||
stack.pop ();
|
||||
|
||||
@@ -687,11 +691,11 @@ bool SHAMap::delItem (uint256 const& id)
|
||||
// What gets attached to the end of the chain
|
||||
// (For now, nothing, since we deleted the leaf)
|
||||
uint256 prevHash;
|
||||
SHAMapTreeNode::pointer prevNode;
|
||||
std::shared_ptr<SHAMapTreeNode> prevNode;
|
||||
|
||||
while (!stack.empty ())
|
||||
{
|
||||
SHAMapTreeNode::pointer node = stack.top ().first;
|
||||
std::shared_ptr<SHAMapTreeNode> node = stack.top ().first;
|
||||
SHAMapNodeID nodeID = stack.top ().second;
|
||||
stack.pop ();
|
||||
|
||||
@@ -719,7 +723,7 @@ bool SHAMap::delItem (uint256 const& id)
|
||||
else if (bc == 1)
|
||||
{
|
||||
// If there's only one item, pull up on the thread
|
||||
SHAMapItem::pointer item = onlyBelow (node.get ());
|
||||
std::shared_ptr<SHAMapItem> item = onlyBelow (node.get ());
|
||||
|
||||
if (item)
|
||||
{
|
||||
@@ -754,21 +758,23 @@ bool SHAMap::delItem (uint256 const& id)
|
||||
return true;
|
||||
}
|
||||
|
||||
bool SHAMap::addGiveItem (SHAMapItem::ref item, bool isTransaction, bool hasMeta)
|
||||
bool
|
||||
SHAMap::addGiveItem (std::shared_ptr<SHAMapItem> const& item,
|
||||
bool isTransaction, bool hasMeta)
|
||||
{
|
||||
// add the specified item, does not update
|
||||
uint256 tag = item->getTag ();
|
||||
SHAMapTreeNode::TNType type = !isTransaction ? SHAMapTreeNode::tnACCOUNT_STATE :
|
||||
(hasMeta ? SHAMapTreeNode::tnTRANSACTION_MD : SHAMapTreeNode::tnTRANSACTION_NM);
|
||||
|
||||
assert (mState != smsImmutable);
|
||||
assert (state_ != SHAMapState::Immutable);
|
||||
|
||||
auto stack = getStack (tag, true);
|
||||
|
||||
if (stack.empty ())
|
||||
throw (std::runtime_error ("missing node"));
|
||||
|
||||
SHAMapTreeNode::pointer node = stack.top ().first;
|
||||
std::shared_ptr<SHAMapTreeNode> node = stack.top ().first;
|
||||
SHAMapNodeID nodeID = stack.top ().second;
|
||||
stack.pop ();
|
||||
|
||||
@@ -781,8 +787,7 @@ bool SHAMap::addGiveItem (SHAMapItem::ref item, bool isTransaction, bool hasMeta
|
||||
// easy case, we end on an inner node
|
||||
int branch = nodeID.selectBranch (tag);
|
||||
assert (node->isEmptyBranch (branch));
|
||||
SHAMapTreeNode::pointer newNode =
|
||||
std::make_shared<SHAMapTreeNode> (item, type, mSeq);
|
||||
auto newNode = std::make_shared<SHAMapTreeNode> (item, type, seq_);
|
||||
if (! node->setChild (branch, newNode->getNodeHash (), newNode))
|
||||
{
|
||||
assert (false);
|
||||
@@ -791,7 +796,7 @@ bool SHAMap::addGiveItem (SHAMapItem::ref item, bool isTransaction, bool hasMeta
|
||||
else
|
||||
{
|
||||
// this is a leaf node that has to be made an inner node holding two items
|
||||
SHAMapItem::pointer otherItem = node->peekItem ();
|
||||
std::shared_ptr<SHAMapItem> otherItem = node->peekItem ();
|
||||
assert (otherItem && (tag != otherItem->getTag ()));
|
||||
|
||||
node->makeInner ();
|
||||
@@ -805,22 +810,22 @@ bool SHAMap::addGiveItem (SHAMapItem::ref item, bool isTransaction, bool hasMeta
|
||||
|
||||
// we need a new inner node, since both go on same branch at this level
|
||||
nodeID = nodeID.getChildNodeID (b1);
|
||||
node = std::make_shared<SHAMapTreeNode> (mSeq);
|
||||
node = std::make_shared<SHAMapTreeNode> (seq_);
|
||||
node->makeInner ();
|
||||
}
|
||||
|
||||
// we can add the two leaf nodes here
|
||||
assert (node->isInner ());
|
||||
|
||||
SHAMapTreeNode::pointer newNode =
|
||||
std::make_shared<SHAMapTreeNode> (item, type, mSeq);
|
||||
std::shared_ptr<SHAMapTreeNode> newNode =
|
||||
std::make_shared<SHAMapTreeNode> (item, type, seq_);
|
||||
assert (newNode->isValid () && newNode->isLeaf ());
|
||||
if (!node->setChild (b1, newNode->getNodeHash (), newNode))
|
||||
{
|
||||
assert (false);
|
||||
}
|
||||
|
||||
newNode = std::make_shared<SHAMapTreeNode> (otherItem, type, mSeq);
|
||||
newNode = std::make_shared<SHAMapTreeNode> (otherItem, type, seq_);
|
||||
assert (newNode->isValid () && newNode->isLeaf ());
|
||||
if (!node->setChild (b2, newNode->getNodeHash (), newNode))
|
||||
{
|
||||
@@ -837,19 +842,21 @@ bool SHAMap::addItem (const SHAMapItem& i, bool isTransaction, bool hasMetaData)
|
||||
return addGiveItem (std::make_shared<SHAMapItem> (i), isTransaction, hasMetaData);
|
||||
}
|
||||
|
||||
bool SHAMap::updateGiveItem (SHAMapItem::ref item, bool isTransaction, bool hasMeta)
|
||||
bool
|
||||
SHAMap::updateGiveItem (std::shared_ptr<SHAMapItem> const& item,
|
||||
bool isTransaction, bool hasMeta)
|
||||
{
|
||||
// can't change the tag but can change the hash
|
||||
uint256 tag = item->getTag ();
|
||||
|
||||
assert (mState != smsImmutable);
|
||||
assert (state_ != SHAMapState::Immutable);
|
||||
|
||||
auto stack = getStack (tag, true);
|
||||
|
||||
if (stack.empty ())
|
||||
throw (std::runtime_error ("missing node"));
|
||||
|
||||
SHAMapTreeNode::pointer node = stack.top ().first;
|
||||
std::shared_ptr<SHAMapTreeNode> node = stack.top ().first;
|
||||
SHAMapNodeID nodeID = stack.top ().second;
|
||||
stack.pop ();
|
||||
|
||||
@@ -875,17 +882,17 @@ bool SHAMap::updateGiveItem (SHAMapItem::ref item, bool isTransaction, bool hasM
|
||||
|
||||
bool SHAMap::fetchRoot (uint256 const& hash, SHAMapSyncFilter* filter)
|
||||
{
|
||||
if (hash == root->getNodeHash ())
|
||||
if (hash == root_->getNodeHash ())
|
||||
return true;
|
||||
|
||||
if (journal_.trace)
|
||||
{
|
||||
if (mType == smtTRANSACTION)
|
||||
if (type_ == SHAMapType::TRANSACTION)
|
||||
{
|
||||
journal_.trace
|
||||
<< "Fetch root TXN node " << hash;
|
||||
}
|
||||
else if (mType == smtSTATE)
|
||||
else if (type_ == SHAMapType::STATE)
|
||||
{
|
||||
journal_.trace <<
|
||||
"Fetch root STATE node " << hash;
|
||||
@@ -897,12 +904,12 @@ bool SHAMap::fetchRoot (uint256 const& hash, SHAMapSyncFilter* filter)
|
||||
}
|
||||
}
|
||||
|
||||
SHAMapTreeNode::pointer newRoot = fetchNodeNT (SHAMapNodeID(), hash, filter);
|
||||
std::shared_ptr<SHAMapTreeNode> newRoot = fetchNodeNT (SHAMapNodeID(), hash, filter);
|
||||
|
||||
if (newRoot)
|
||||
{
|
||||
root = newRoot;
|
||||
assert (root->getNodeHash () == hash);
|
||||
root_ = newRoot;
|
||||
assert (root_->getNodeHash () == hash);
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -919,11 +926,11 @@ bool SHAMap::fetchRoot (uint256 const& hash, SHAMapSyncFilter* filter)
|
||||
// 2) An unshareable node is shared. This happens when you make
|
||||
// a mutable snapshot of a mutable SHAMap.
|
||||
void SHAMap::writeNode (
|
||||
NodeObjectType t, std::uint32_t seq, SHAMapTreeNode::pointer& node)
|
||||
NodeObjectType t, std::uint32_t seq, std::shared_ptr<SHAMapTreeNode>& node) const
|
||||
{
|
||||
// Node is ours, so we can just make it shareable
|
||||
assert (node->getSeq() == mSeq);
|
||||
assert (mBacked);
|
||||
assert (node->getSeq() == seq_);
|
||||
assert (backed_);
|
||||
node->setSeq (0);
|
||||
|
||||
canonicalize (node->getNodeHash(), node);
|
||||
@@ -937,17 +944,17 @@ void SHAMap::writeNode (
|
||||
// We can't modify an inner node someone else might have a
|
||||
// pointer to because flushing modifies inner nodes -- it
|
||||
// makes them point to canonical/shared nodes.
|
||||
void SHAMap::preFlushNode (SHAMapTreeNode::pointer& node)
|
||||
void SHAMap::preFlushNode (std::shared_ptr<SHAMapTreeNode>& node) const
|
||||
{
|
||||
// A shared node should never need to be flushed
|
||||
// because that would imply someone modified it
|
||||
assert (node->getSeq() != 0);
|
||||
|
||||
if (node->getSeq() != mSeq)
|
||||
if (node->getSeq() != seq_)
|
||||
{
|
||||
// Node is not uniquely ours, so unshare it before
|
||||
// possibly modifying it
|
||||
node = std::make_shared <SHAMapTreeNode> (*node, mSeq);
|
||||
node = std::make_shared <SHAMapTreeNode> (*node, seq_);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -963,28 +970,29 @@ int SHAMap::flushDirty (NodeObjectType t, std::uint32_t seq)
|
||||
return walkSubTree (true, t, seq);
|
||||
}
|
||||
|
||||
int SHAMap::walkSubTree (bool doWrite, NodeObjectType t, std::uint32_t seq)
|
||||
int
|
||||
SHAMap::walkSubTree (bool doWrite, NodeObjectType t, std::uint32_t seq)
|
||||
{
|
||||
int flushed = 0;
|
||||
Serializer s;
|
||||
|
||||
if (!root || (root->getSeq() == 0) || root->isEmpty ())
|
||||
if (!root_ || (root_->getSeq() == 0) || root_->isEmpty ())
|
||||
return flushed;
|
||||
|
||||
if (root->isLeaf())
|
||||
{ // special case -- root is leaf
|
||||
preFlushNode (root);
|
||||
if (doWrite && mBacked)
|
||||
writeNode (t, seq, root);
|
||||
if (root_->isLeaf())
|
||||
{ // special case -- root_ is leaf
|
||||
preFlushNode (root_);
|
||||
if (doWrite && backed_)
|
||||
writeNode (t, seq, root_);
|
||||
return 1;
|
||||
}
|
||||
|
||||
// Stack of {parent,index,child} pointers representing
|
||||
// inner nodes we are in the process of flushing
|
||||
using StackEntry = std::pair <SHAMapTreeNode::pointer, int>;
|
||||
using StackEntry = std::pair <std::shared_ptr<SHAMapTreeNode>, int>;
|
||||
std::stack <StackEntry, std::vector<StackEntry>> stack;
|
||||
|
||||
SHAMapTreeNode::pointer node = root;
|
||||
std::shared_ptr<SHAMapTreeNode> node = root_;
|
||||
preFlushNode (node);
|
||||
|
||||
int pos = 0;
|
||||
@@ -1003,7 +1011,7 @@ int SHAMap::walkSubTree (bool doWrite, NodeObjectType t, std::uint32_t seq)
|
||||
// No need to do I/O. If the node isn't linked,
|
||||
// it can't need to be flushed
|
||||
int branch = pos;
|
||||
SHAMapTreeNode::pointer child = node->getChild (pos++);
|
||||
std::shared_ptr<SHAMapTreeNode> child = node->getChild (pos++);
|
||||
|
||||
if (child && (child->getSeq() != 0))
|
||||
{
|
||||
@@ -1026,9 +1034,9 @@ int SHAMap::walkSubTree (bool doWrite, NodeObjectType t, std::uint32_t seq)
|
||||
|
||||
preFlushNode (child);
|
||||
|
||||
assert (node->getSeq() == mSeq);
|
||||
assert (node->getSeq() == seq_);
|
||||
|
||||
if (doWrite && mBacked)
|
||||
if (doWrite && backed_)
|
||||
writeNode (t, seq, child);
|
||||
|
||||
node->shareChild (branch, child);
|
||||
@@ -1038,7 +1046,7 @@ int SHAMap::walkSubTree (bool doWrite, NodeObjectType t, std::uint32_t seq)
|
||||
}
|
||||
|
||||
// This inner node can now be shared
|
||||
if (doWrite && mBacked)
|
||||
if (doWrite && backed_)
|
||||
writeNode (t, seq, node);
|
||||
|
||||
++flushed;
|
||||
@@ -1046,12 +1054,12 @@ int SHAMap::walkSubTree (bool doWrite, NodeObjectType t, std::uint32_t seq)
|
||||
if (stack.empty ())
|
||||
break;
|
||||
|
||||
SHAMapTreeNode::pointer parent = std::move (stack.top().first);
|
||||
std::shared_ptr<SHAMapTreeNode> parent = std::move (stack.top().first);
|
||||
pos = stack.top().second;
|
||||
stack.pop();
|
||||
|
||||
// Hook this inner node to its parent
|
||||
assert (parent->getSeq() == mSeq);
|
||||
assert (parent->getSeq() == seq_);
|
||||
parent->shareChild (pos, node);
|
||||
|
||||
// Continue with parent's next child, if any
|
||||
@@ -1059,52 +1067,20 @@ int SHAMap::walkSubTree (bool doWrite, NodeObjectType t, std::uint32_t seq)
|
||||
++pos;
|
||||
}
|
||||
|
||||
// Last inner node is the new root
|
||||
root = std::move (node);
|
||||
// Last inner node is the new root_
|
||||
root_ = std::move (node);
|
||||
|
||||
return flushed;
|
||||
}
|
||||
|
||||
bool SHAMap::getPath (uint256 const& index, std::vector< Blob >& nodes, SHANodeFormat format)
|
||||
{
|
||||
// Return the path of nodes to the specified index in the specified format
|
||||
// Return value: true = node present, false = node not present
|
||||
|
||||
SHAMapTreeNode* inNode = root.get ();
|
||||
SHAMapNodeID nodeID;
|
||||
|
||||
while (inNode->isInner ())
|
||||
{
|
||||
Serializer s;
|
||||
inNode->addRaw (s, format);
|
||||
nodes.push_back (s.peekData ());
|
||||
|
||||
int branch = nodeID.selectBranch (index);
|
||||
if (inNode->isEmptyBranch (branch))
|
||||
return false;
|
||||
|
||||
inNode = descendThrow (inNode, branch);
|
||||
nodeID = nodeID.getChildNodeID (branch);
|
||||
}
|
||||
|
||||
if (inNode->peekItem()->getTag () != index) // path leads to different leaf
|
||||
return false;
|
||||
|
||||
// path leads to the requested leaf
|
||||
Serializer s;
|
||||
inNode->addRaw (s, format);
|
||||
nodes.push_back (std::move(s.peekData ()));
|
||||
return true;
|
||||
}
|
||||
|
||||
void SHAMap::dump (bool hash)
|
||||
void SHAMap::dump (bool hash) const
|
||||
{
|
||||
int leafCount = 0;
|
||||
if (journal_.info) journal_.info <<
|
||||
" MAP Contains";
|
||||
|
||||
std::stack <std::pair <SHAMapTreeNode*, SHAMapNodeID> > stack;
|
||||
stack.push ({root.get (), SHAMapNodeID ()});
|
||||
stack.push ({root_.get (), SHAMapNodeID ()});
|
||||
|
||||
do
|
||||
{
|
||||
@@ -1142,21 +1118,20 @@ void SHAMap::dump (bool hash)
|
||||
leafCount << " resident leaves";
|
||||
}
|
||||
|
||||
SHAMapTreeNode::pointer SHAMap::getCache (uint256 const& hash)
|
||||
std::shared_ptr<SHAMapTreeNode> SHAMap::getCache (uint256 const& hash) const
|
||||
{
|
||||
SHAMapTreeNode::pointer ret = f_.treecache().fetch (hash);
|
||||
std::shared_ptr<SHAMapTreeNode> ret = f_.treecache().fetch (hash);
|
||||
assert (!ret || !ret->getSeq());
|
||||
return ret;
|
||||
}
|
||||
|
||||
void SHAMap::canonicalize (uint256 const& hash, SHAMapTreeNode::pointer& node)
|
||||
void SHAMap::canonicalize (uint256 const& hash, std::shared_ptr<SHAMapTreeNode>& node) const
|
||||
{
|
||||
assert (mBacked);
|
||||
assert (backed_);
|
||||
assert (node->getSeq() == 0);
|
||||
assert (node->getNodeHash() == hash);
|
||||
|
||||
f_.treecache().canonicalize (hash, node);
|
||||
|
||||
}
|
||||
|
||||
} // ripple
|
||||
|
||||
@@ -31,7 +31,7 @@ namespace ripple {
|
||||
// synchronizing matching branches too.)
|
||||
|
||||
bool SHAMap::walkBranch (SHAMapTreeNode* node,
|
||||
SHAMapItem::ref otherMapItem, bool isFirstMap,
|
||||
std::shared_ptr<SHAMapItem> const& otherMapItem, bool isFirstMap,
|
||||
Delta& differences, int& maxCount)
|
||||
{
|
||||
// Walk a branch of a SHAMap that's matched by an empty branch or single item in the other map
|
||||
@@ -55,17 +55,17 @@ bool SHAMap::walkBranch (SHAMapTreeNode* node,
|
||||
else
|
||||
{
|
||||
// This is a leaf node, process its item
|
||||
SHAMapItem::pointer item = node->peekItem ();
|
||||
std::shared_ptr<SHAMapItem> item = node->peekItem ();
|
||||
|
||||
if (emptyBranch || (item->getTag () != otherMapItem->getTag ()))
|
||||
{
|
||||
// unmatched
|
||||
if (isFirstMap)
|
||||
differences.insert (std::make_pair (item->getTag (),
|
||||
DeltaRef (item, SHAMapItem::pointer ())));
|
||||
DeltaRef (item, std::shared_ptr<SHAMapItem> ())));
|
||||
else
|
||||
differences.insert (std::make_pair (item->getTag (),
|
||||
DeltaRef (SHAMapItem::pointer (), item)));
|
||||
DeltaRef (std::shared_ptr<SHAMapItem> (), item)));
|
||||
|
||||
if (--maxCount <= 0)
|
||||
return false;
|
||||
@@ -98,12 +98,12 @@ bool SHAMap::walkBranch (SHAMapTreeNode* node,
|
||||
// otherMapItem was unmatched, must add
|
||||
if (isFirstMap) // this is first map, so other item is from second
|
||||
differences.insert (std::make_pair (otherMapItem->getTag (),
|
||||
DeltaRef (SHAMapItem::pointer(),
|
||||
DeltaRef (std::shared_ptr<SHAMapItem>(),
|
||||
otherMapItem)));
|
||||
else
|
||||
differences.insert (std::make_pair (otherMapItem->getTag (),
|
||||
DeltaRef (otherMapItem,
|
||||
SHAMapItem::pointer ())));
|
||||
std::shared_ptr<SHAMapItem> ())));
|
||||
|
||||
if (--maxCount <= 0)
|
||||
return false;
|
||||
@@ -112,7 +112,9 @@ bool SHAMap::walkBranch (SHAMapTreeNode* node,
|
||||
return true;
|
||||
}
|
||||
|
||||
bool SHAMap::compare (SHAMap::ref otherMap, Delta& differences, int maxCount)
|
||||
bool
|
||||
SHAMap::compare (std::shared_ptr<SHAMap> const& otherMap,
|
||||
Delta& differences, int maxCount)
|
||||
{
|
||||
// compare two hash trees, add up to maxCount differences to the difference table
|
||||
// return value: true=complete table of differences given, false=too many differences
|
||||
@@ -127,7 +129,7 @@ bool SHAMap::compare (SHAMap::ref otherMap, Delta& differences, int maxCount)
|
||||
if (getHash () == otherMap->getHash ())
|
||||
return true;
|
||||
|
||||
nodeStack.push ({root.get(), otherMap->root.get()});
|
||||
nodeStack.push ({root_.get(), otherMap->root_.get()});
|
||||
while (!nodeStack.empty ())
|
||||
{
|
||||
SHAMapTreeNode* ourNode = nodeStack.top().first;
|
||||
@@ -137,7 +139,7 @@ bool SHAMap::compare (SHAMap::ref otherMap, Delta& differences, int maxCount)
|
||||
if (!ourNode || !otherNode)
|
||||
{
|
||||
assert (false);
|
||||
throw SHAMapMissingNode (mType, uint256 ());
|
||||
throw SHAMapMissingNode (type_, uint256 ());
|
||||
}
|
||||
|
||||
if (ourNode->isLeaf () && otherNode->isLeaf ())
|
||||
@@ -158,12 +160,12 @@ bool SHAMap::compare (SHAMap::ref otherMap, Delta& differences, int maxCount)
|
||||
{
|
||||
differences.insert (std::make_pair(ourNode->peekItem()->getTag (),
|
||||
DeltaRef(ourNode->peekItem(),
|
||||
SHAMapItem::pointer ())));
|
||||
std::shared_ptr<SHAMapItem> ())));
|
||||
if (--maxCount <= 0)
|
||||
return false;
|
||||
|
||||
differences.insert(std::make_pair(otherNode->peekItem()->getTag (),
|
||||
DeltaRef(SHAMapItem::pointer(),
|
||||
DeltaRef(std::shared_ptr<SHAMapItem>(),
|
||||
otherNode->peekItem ())));
|
||||
if (--maxCount <= 0)
|
||||
return false;
|
||||
@@ -191,7 +193,7 @@ bool SHAMap::compare (SHAMap::ref otherMap, Delta& differences, int maxCount)
|
||||
// We have a branch, the other tree does not
|
||||
SHAMapTreeNode* iNode = descendThrow (ourNode, i);
|
||||
if (!walkBranch (iNode,
|
||||
SHAMapItem::pointer (), true,
|
||||
std::shared_ptr<SHAMapItem> (), true,
|
||||
differences, maxCount))
|
||||
return false;
|
||||
}
|
||||
@@ -201,7 +203,7 @@ bool SHAMap::compare (SHAMap::ref otherMap, Delta& differences, int maxCount)
|
||||
SHAMapTreeNode* iNode =
|
||||
otherMap->descendThrow(otherNode, i);
|
||||
if (!otherMap->walkBranch (iNode,
|
||||
SHAMapItem::pointer(),
|
||||
std::shared_ptr<SHAMapItem>(),
|
||||
false, differences, maxCount))
|
||||
return false;
|
||||
}
|
||||
@@ -219,24 +221,24 @@ bool SHAMap::compare (SHAMap::ref otherMap, Delta& differences, int maxCount)
|
||||
|
||||
void SHAMap::walkMap (std::vector<SHAMapMissingNode>& missingNodes, int maxMissing)
|
||||
{
|
||||
std::stack <SHAMapTreeNode::pointer,
|
||||
std::vector <SHAMapTreeNode::pointer>> nodeStack;
|
||||
std::stack <std::shared_ptr<SHAMapTreeNode>,
|
||||
std::vector <std::shared_ptr<SHAMapTreeNode>>> nodeStack;
|
||||
|
||||
if (!root->isInner ()) // root is only node, and we have it
|
||||
if (!root_->isInner ()) // root_ is only node, and we have it
|
||||
return;
|
||||
|
||||
nodeStack.push (root);
|
||||
nodeStack.push (root_);
|
||||
|
||||
while (!nodeStack.empty ())
|
||||
{
|
||||
SHAMapTreeNode::pointer node = std::move (nodeStack.top());
|
||||
std::shared_ptr<SHAMapTreeNode> node = std::move (nodeStack.top());
|
||||
nodeStack.pop ();
|
||||
|
||||
for (int i = 0; i < 16; ++i)
|
||||
{
|
||||
if (!node->isEmptyBranch (i))
|
||||
{
|
||||
SHAMapTreeNode::pointer nextNode = descendNoStore (node, i);
|
||||
std::shared_ptr<SHAMapTreeNode> nextNode = descendNoStore (node, i);
|
||||
|
||||
if (nextNode)
|
||||
{
|
||||
@@ -245,7 +247,7 @@ void SHAMap::walkMap (std::vector<SHAMapMissingNode>& missingNodes, int maxMissi
|
||||
}
|
||||
else
|
||||
{
|
||||
missingNodes.emplace_back (mType, node->getChildHash (i));
|
||||
missingNodes.emplace_back (type_, node->getChildHash (i));
|
||||
if (--maxMissing <= 0)
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -28,15 +28,15 @@ operator<< (std::ostream& out, const SHAMapMissingNode& mn)
|
||||
{
|
||||
switch (mn.getMapType ())
|
||||
{
|
||||
case smtTRANSACTION:
|
||||
case SHAMapType::TRANSACTION:
|
||||
out << "Missing/TXN(" << mn.getNodeHash () << ")";
|
||||
break;
|
||||
|
||||
case smtSTATE:
|
||||
case SHAMapType::STATE:
|
||||
out << "Missing/STA(" << mn.getNodeHash () << ")";
|
||||
break;
|
||||
|
||||
case smtFREE:
|
||||
case SHAMapType::FREE:
|
||||
default:
|
||||
out << "Missing/" << mn.getNodeHash ();
|
||||
break;
|
||||
|
||||
@@ -57,43 +57,15 @@ SHAMapNodeID::Masks (int depth)
|
||||
return masks->entry[depth];
|
||||
}
|
||||
|
||||
std::size_t
|
||||
SHAMapNodeID::calculate_hash (uint256 const& node, int depth)
|
||||
{
|
||||
struct HashParams
|
||||
{
|
||||
HashParams ()
|
||||
: golden_ratio (0x9e3779b9)
|
||||
{
|
||||
random_fill (&cookie_value);
|
||||
}
|
||||
|
||||
// The cookie value protects us against algorithmic complexity attacks.
|
||||
std::size_t cookie_value;
|
||||
std::size_t golden_ratio;
|
||||
};
|
||||
|
||||
static beast::static_initializer <HashParams> params;
|
||||
|
||||
std::size_t h = params->cookie_value + (depth * params->golden_ratio);
|
||||
|
||||
auto ptr = reinterpret_cast <const unsigned int*> (node.cbegin ());
|
||||
|
||||
for (int i = (depth + 7) / 8; i != 0; --i)
|
||||
h = (h * params->golden_ratio) ^ *ptr++;
|
||||
|
||||
return h;
|
||||
}
|
||||
|
||||
// canonicalize the hash to a node ID for this depth
|
||||
SHAMapNodeID::SHAMapNodeID (int depth, uint256 const& hash)
|
||||
: mNodeID (hash), mDepth (depth), mHash (0)
|
||||
: mNodeID (hash), mDepth (depth)
|
||||
{
|
||||
assert ((depth >= 0) && (depth < 65));
|
||||
mNodeID &= Masks(depth);
|
||||
}
|
||||
|
||||
SHAMapNodeID::SHAMapNodeID (void const* ptr, int len) : mHash (0)
|
||||
SHAMapNodeID::SHAMapNodeID (void const* ptr, int len)
|
||||
{
|
||||
if (len < 33)
|
||||
mDepth = -1;
|
||||
@@ -113,12 +85,6 @@ std::string SHAMapNodeID::getString () const
|
||||
"," + to_string (mNodeID) + ")";
|
||||
}
|
||||
|
||||
uint256 SHAMapNodeID::getNodeID (int depth, uint256 const& hash)
|
||||
{
|
||||
assert ((depth >= 0) && (depth <= 64));
|
||||
return hash & Masks(depth);
|
||||
}
|
||||
|
||||
void SHAMapNodeID::addIDRaw (Serializer& s) const
|
||||
{
|
||||
s.add256 (mNodeID);
|
||||
@@ -141,7 +107,7 @@ SHAMapNodeID SHAMapNodeID::getChildNodeID (int m) const
|
||||
uint256 child (mNodeID);
|
||||
child.begin ()[mDepth / 2] |= (mDepth & 1) ? m : (m << 4);
|
||||
|
||||
return SHAMapNodeID (mDepth + 1, child, true);
|
||||
return SHAMapNodeID (mDepth + 1, child);
|
||||
}
|
||||
|
||||
// Which branch would contain the specified hash
|
||||
|
||||
@@ -29,7 +29,7 @@ namespace ripple {
|
||||
static const uint256 uZero;
|
||||
|
||||
static bool visitLeavesHelper (
|
||||
std::function <void (SHAMapItem::ref)> const& function,
|
||||
std::function <void (std::shared_ptr<SHAMapItem> const&)> const& function,
|
||||
SHAMapTreeNode& node)
|
||||
{
|
||||
// Adapt visitNodes to visitLeaves
|
||||
@@ -39,7 +39,7 @@ static bool visitLeavesHelper (
|
||||
return false;
|
||||
}
|
||||
|
||||
void SHAMap::visitLeaves (std::function<void (SHAMapItem::ref item)> const& leafFunction)
|
||||
void SHAMap::visitLeaves (std::function<void (std::shared_ptr<SHAMapItem> const& item)> const& leafFunction)
|
||||
{
|
||||
visitNodes (std::bind (visitLeavesHelper,
|
||||
std::cref (leafFunction), std::placeholders::_1));
|
||||
@@ -48,20 +48,20 @@ void SHAMap::visitLeaves (std::function<void (SHAMapItem::ref item)> const& leaf
|
||||
void SHAMap::visitNodes(std::function<bool (SHAMapTreeNode&)> const& function)
|
||||
{
|
||||
// Visit every node in a SHAMap
|
||||
assert (root->isValid ());
|
||||
assert (root_->isValid ());
|
||||
|
||||
if (!root || root->isEmpty ())
|
||||
if (!root_ || root_->isEmpty ())
|
||||
return;
|
||||
|
||||
function (*root);
|
||||
function (*root_);
|
||||
|
||||
if (!root->isInner ())
|
||||
if (!root_->isInner ())
|
||||
return;
|
||||
|
||||
using StackEntry = std::pair <int, SHAMapTreeNode::pointer>;
|
||||
using StackEntry = std::pair <int, std::shared_ptr<SHAMapTreeNode>>;
|
||||
std::stack <StackEntry, std::vector <StackEntry>> stack;
|
||||
|
||||
SHAMapTreeNode::pointer node = root;
|
||||
std::shared_ptr<SHAMapTreeNode> node = root_;
|
||||
int pos = 0;
|
||||
|
||||
while (1)
|
||||
@@ -71,7 +71,7 @@ void SHAMap::visitNodes(std::function<bool (SHAMapTreeNode&)> const& function)
|
||||
uint256 childHash;
|
||||
if (!node->isEmptyBranch (pos))
|
||||
{
|
||||
SHAMapTreeNode::pointer child = descendNoStore (node, pos);
|
||||
std::shared_ptr<SHAMapTreeNode> child = descendNoStore (node, pos);
|
||||
if (function (*child))
|
||||
return;
|
||||
|
||||
@@ -115,17 +115,17 @@ void SHAMap::visitNodes(std::function<bool (SHAMapTreeNode&)> const& function)
|
||||
void SHAMap::getMissingNodes (std::vector<SHAMapNodeID>& nodeIDs, std::vector<uint256>& hashes, int max,
|
||||
SHAMapSyncFilter* filter)
|
||||
{
|
||||
assert (root->isValid ());
|
||||
assert (root->getNodeHash().isNonZero ());
|
||||
assert (root_->isValid ());
|
||||
assert (root_->getNodeHash().isNonZero ());
|
||||
|
||||
std::uint32_t generation = f_.fullbelow().getGeneration();
|
||||
if (root->isFullBelow (generation))
|
||||
if (root_->isFullBelow (generation))
|
||||
{
|
||||
clearSynching ();
|
||||
return;
|
||||
}
|
||||
|
||||
if (!root->isInner ())
|
||||
if (!root_->isInner ())
|
||||
{
|
||||
if (journal_.warning) journal_.warning <<
|
||||
"synching empty tree";
|
||||
@@ -148,7 +148,7 @@ void SHAMap::getMissingNodes (std::vector<SHAMapNodeID>& nodeIDs, std::vector<ui
|
||||
|
||||
// Traverse the map without blocking
|
||||
|
||||
SHAMapTreeNode *node = root.get ();
|
||||
SHAMapTreeNode *node = root_.get ();
|
||||
SHAMapNodeID nodeID;
|
||||
|
||||
// The firstChild value is selected randomly so if multiple threads
|
||||
@@ -169,7 +169,7 @@ void SHAMap::getMissingNodes (std::vector<SHAMapNodeID>& nodeIDs, std::vector<ui
|
||||
{
|
||||
uint256 const& childHash = node->getChildHash (branch);
|
||||
|
||||
if (! mBacked || ! f_.fullbelow().touch_if_exists (childHash))
|
||||
if (! backed_ || ! f_.fullbelow().touch_if_exists (childHash))
|
||||
{
|
||||
SHAMapNodeID childID = nodeID.getChildNodeID (branch);
|
||||
bool pending = false;
|
||||
@@ -217,7 +217,7 @@ void SHAMap::getMissingNodes (std::vector<SHAMapNodeID>& nodeIDs, std::vector<ui
|
||||
if (fullBelow)
|
||||
{ // No partial node encountered below this node
|
||||
node->setFullBelowGen (generation);
|
||||
if (mBacked)
|
||||
if (backed_)
|
||||
f_.fullbelow().insert (node->getNodeHash ());
|
||||
}
|
||||
|
||||
@@ -248,10 +248,10 @@ void SHAMap::getMissingNodes (std::vector<SHAMapNodeID>& nodeIDs, std::vector<ui
|
||||
auto const& nodeID = std::get<2>(node);
|
||||
auto const& nodeHash = parent->getChildHash (branch);
|
||||
|
||||
SHAMapTreeNode::pointer nodePtr = fetchNodeNT (nodeID, nodeHash, filter);
|
||||
std::shared_ptr<SHAMapTreeNode> nodePtr = fetchNodeNT (nodeID, nodeHash, filter);
|
||||
if (nodePtr)
|
||||
{
|
||||
if (mBacked)
|
||||
if (backed_)
|
||||
canonicalize (nodeHash, nodePtr);
|
||||
parent->canonicalizeChild (branch, nodePtr);
|
||||
}
|
||||
@@ -288,7 +288,7 @@ bool SHAMap::getNodeFat (SHAMapNodeID wanted, std::vector<SHAMapNodeID>& nodeIDs
|
||||
{
|
||||
// Gets a node and some of its children
|
||||
|
||||
SHAMapTreeNode* node = root.get ();
|
||||
SHAMapTreeNode* node = root_.get ();
|
||||
|
||||
SHAMapNodeID nodeID;
|
||||
|
||||
@@ -328,7 +328,7 @@ bool SHAMap::getNodeFat (SHAMapNodeID wanted, std::vector<SHAMapNodeID>& nodeIDs
|
||||
rawNodes.push_back (std::move (s.peekData ()));
|
||||
}
|
||||
|
||||
if ((!fatRoot && wanted.isRoot ()) || node->isLeaf ()) // don't get a fat root, can't get a fat leaf
|
||||
if ((!fatRoot && wanted.isRoot ()) || node->isLeaf ()) // don't get a fat root_, can't get a fat leaf
|
||||
return true;
|
||||
|
||||
SHAMapTreeNode* nextNode = nullptr;
|
||||
@@ -362,26 +362,25 @@ bool SHAMap::getNodeFat (SHAMapNodeID wanted, std::vector<SHAMapNodeID>& nodeIDs
|
||||
return true;
|
||||
}
|
||||
|
||||
bool SHAMap::getRootNode (Serializer& s, SHANodeFormat format)
|
||||
bool SHAMap::getRootNode (Serializer& s, SHANodeFormat format) const
|
||||
{
|
||||
root->addRaw (s, format);
|
||||
root_->addRaw (s, format);
|
||||
return true;
|
||||
}
|
||||
|
||||
SHAMapAddNode SHAMap::addRootNode (Blob const& rootNode,
|
||||
SHANodeFormat format, SHAMapSyncFilter* filter)
|
||||
{
|
||||
// we already have a root node
|
||||
if (root->getNodeHash ().isNonZero ())
|
||||
// we already have a root_ node
|
||||
if (root_->getNodeHash ().isNonZero ())
|
||||
{
|
||||
if (journal_.trace) journal_.trace <<
|
||||
"got root node, already have one";
|
||||
return SHAMapAddNode::duplicate ();
|
||||
}
|
||||
|
||||
assert (mSeq >= 1);
|
||||
SHAMapTreeNode::pointer node =
|
||||
std::make_shared<SHAMapTreeNode> (rootNode, 0,
|
||||
assert (seq_ >= 1);
|
||||
auto node = std::make_shared<SHAMapTreeNode> (rootNode, 0,
|
||||
format, uZero, false);
|
||||
|
||||
if (!node)
|
||||
@@ -391,20 +390,20 @@ SHAMapAddNode SHAMap::addRootNode (Blob const& rootNode,
|
||||
node->dump (SHAMapNodeID (), journal_);
|
||||
#endif
|
||||
|
||||
if (mBacked)
|
||||
if (backed_)
|
||||
canonicalize (node->getNodeHash (), node);
|
||||
|
||||
root = node;
|
||||
root_ = node;
|
||||
|
||||
if (root->isLeaf())
|
||||
if (root_->isLeaf())
|
||||
clearSynching ();
|
||||
|
||||
if (filter)
|
||||
{
|
||||
Serializer s;
|
||||
root->addRaw (s, snfPREFIX);
|
||||
filter->gotNode (false, SHAMapNodeID{}, root->getNodeHash (),
|
||||
s.modData (), root->getType ());
|
||||
root_->addRaw (s, snfPREFIX);
|
||||
filter->gotNode (false, SHAMapNodeID{}, root_->getNodeHash (),
|
||||
s.modData (), root_->getType ());
|
||||
}
|
||||
|
||||
return SHAMapAddNode::useful ();
|
||||
@@ -413,37 +412,37 @@ SHAMapAddNode SHAMap::addRootNode (Blob const& rootNode,
|
||||
SHAMapAddNode SHAMap::addRootNode (uint256 const& hash, Blob const& rootNode, SHANodeFormat format,
|
||||
SHAMapSyncFilter* filter)
|
||||
{
|
||||
// we already have a root node
|
||||
if (root->getNodeHash ().isNonZero ())
|
||||
// we already have a root_ node
|
||||
if (root_->getNodeHash ().isNonZero ())
|
||||
{
|
||||
if (journal_.trace) journal_.trace <<
|
||||
"got root node, already have one";
|
||||
assert (root->getNodeHash () == hash);
|
||||
assert (root_->getNodeHash () == hash);
|
||||
return SHAMapAddNode::duplicate ();
|
||||
}
|
||||
|
||||
assert (mSeq >= 1);
|
||||
SHAMapTreeNode::pointer node =
|
||||
assert (seq_ >= 1);
|
||||
std::shared_ptr<SHAMapTreeNode> node =
|
||||
std::make_shared<SHAMapTreeNode> (rootNode, 0,
|
||||
format, uZero, false);
|
||||
|
||||
if (!node || node->getNodeHash () != hash)
|
||||
return SHAMapAddNode::invalid ();
|
||||
|
||||
if (mBacked)
|
||||
if (backed_)
|
||||
canonicalize (hash, node);
|
||||
|
||||
root = node;
|
||||
root_ = node;
|
||||
|
||||
if (root->isLeaf())
|
||||
if (root_->isLeaf())
|
||||
clearSynching ();
|
||||
|
||||
if (filter)
|
||||
{
|
||||
Serializer s;
|
||||
root->addRaw (s, snfPREFIX);
|
||||
filter->gotNode (false, SHAMapNodeID{}, root->getNodeHash (), s.modData (),
|
||||
root->getType ());
|
||||
root_->addRaw (s, snfPREFIX);
|
||||
filter->gotNode (false, SHAMapNodeID{}, root_->getNodeHash (), s.modData (),
|
||||
root_->getType ());
|
||||
}
|
||||
|
||||
return SHAMapAddNode::useful ();
|
||||
@@ -465,7 +464,7 @@ SHAMap::addKnownNode (const SHAMapNodeID& node, Blob const& rawNode,
|
||||
|
||||
std::uint32_t generation = f_.fullbelow().getGeneration();
|
||||
SHAMapNodeID iNodeID;
|
||||
SHAMapTreeNode* iNode = root.get ();
|
||||
SHAMapTreeNode* iNode = root_.get ();
|
||||
|
||||
while (iNode->isInner () && !iNode->isFullBelow (generation) &&
|
||||
(iNodeID.getDepth () < node.getDepth ()))
|
||||
@@ -502,14 +501,13 @@ SHAMap::addKnownNode (const SHAMapNodeID& node, Blob const& rawNode,
|
||||
return SHAMapAddNode::invalid ();
|
||||
}
|
||||
|
||||
SHAMapTreeNode::pointer newNode =
|
||||
std::make_shared<SHAMapTreeNode> (rawNode, 0, snfWIRE,
|
||||
auto newNode = std::make_shared<SHAMapTreeNode>(rawNode, 0, snfWIRE,
|
||||
uZero, false);
|
||||
|
||||
if (!newNode->isInBounds (iNodeID))
|
||||
{
|
||||
// Map is provably invalid
|
||||
mState = smsInvalid;
|
||||
state_ = SHAMapState::Invalid;
|
||||
return SHAMapAddNode::useful ();
|
||||
}
|
||||
|
||||
@@ -520,7 +518,7 @@ SHAMap::addKnownNode (const SHAMapNodeID& node, Blob const& rawNode,
|
||||
return SHAMapAddNode::invalid ();
|
||||
}
|
||||
|
||||
if (mBacked)
|
||||
if (backed_)
|
||||
canonicalize (childHash, newNode);
|
||||
|
||||
prevNode->canonicalizeChild (branch, newNode);
|
||||
@@ -547,7 +545,7 @@ bool SHAMap::deepCompare (SHAMap& other)
|
||||
// Intended for debug/test only
|
||||
std::stack <std::pair <SHAMapTreeNode*, SHAMapTreeNode*> > stack;
|
||||
|
||||
stack.push ({root.get(), other.root.get()});
|
||||
stack.push ({root_.get(), other.root_.get()});
|
||||
|
||||
while (!stack.empty ())
|
||||
{
|
||||
@@ -619,7 +617,7 @@ bool
|
||||
SHAMap::hasInnerNode (SHAMapNodeID const& targetNodeID,
|
||||
uint256 const& targetNodeHash)
|
||||
{
|
||||
SHAMapTreeNode* node = root.get ();
|
||||
SHAMapTreeNode* node = root_.get ();
|
||||
SHAMapNodeID nodeID;
|
||||
|
||||
while (node->isInner () && (nodeID.getDepth () < targetNodeID.getDepth ()))
|
||||
@@ -638,9 +636,10 @@ SHAMap::hasInnerNode (SHAMapNodeID const& targetNodeID,
|
||||
|
||||
/** Does this map have this leaf node?
|
||||
*/
|
||||
bool SHAMap::hasLeafNode (uint256 const& tag, uint256 const& targetNodeHash)
|
||||
bool
|
||||
SHAMap::hasLeafNode (uint256 const& tag, uint256 const& targetNodeHash)
|
||||
{
|
||||
SHAMapTreeNode* node = root.get ();
|
||||
SHAMapTreeNode* node = root_.get ();
|
||||
SHAMapNodeID nodeID;
|
||||
|
||||
if (!node->isInner()) // only one leaf node in the tree
|
||||
@@ -697,16 +696,16 @@ void SHAMap::visitDifferences (SHAMap* have, std::function <bool (SHAMapTreeNode
|
||||
// Visit every node in this SHAMap that is not present
|
||||
// in the specified SHAMap
|
||||
|
||||
if (root->getNodeHash ().isZero ())
|
||||
if (root_->getNodeHash ().isZero ())
|
||||
return;
|
||||
|
||||
if (have && (root->getNodeHash () == have->root->getNodeHash ()))
|
||||
if (have && (root_->getNodeHash () == have->root_->getNodeHash ()))
|
||||
return;
|
||||
|
||||
if (root->isLeaf ())
|
||||
if (root_->isLeaf ())
|
||||
{
|
||||
if (! have || ! have->hasLeafNode (root->peekItem()->getTag (), root->getNodeHash ()))
|
||||
func (*root);
|
||||
if (! have || ! have->hasLeafNode (root_->peekItem()->getTag (), root_->getNodeHash ()))
|
||||
func (*root_);
|
||||
|
||||
return;
|
||||
}
|
||||
@@ -714,7 +713,7 @@ void SHAMap::visitDifferences (SHAMap* have, std::function <bool (SHAMapTreeNode
|
||||
using StackEntry = std::pair <SHAMapTreeNode*, SHAMapNodeID>;
|
||||
std::stack <StackEntry, std::vector<StackEntry>> stack;
|
||||
|
||||
stack.push ({root.get(), SHAMapNodeID{}});
|
||||
stack.push ({root_.get(), SHAMapNodeID{}});
|
||||
|
||||
while (!stack.empty())
|
||||
{
|
||||
@@ -751,24 +750,4 @@ void SHAMap::visitDifferences (SHAMap* have, std::function <bool (SHAMapTreeNode
|
||||
}
|
||||
}
|
||||
|
||||
std::list <Blob> SHAMap::getTrustedPath (uint256 const& index)
|
||||
{
|
||||
auto stack = getStack (index, false);
|
||||
if (stack.empty () || !stack.top ().first->isLeaf ())
|
||||
throw std::runtime_error ("requested leaf not present");
|
||||
|
||||
std::list< Blob > path;
|
||||
Serializer s;
|
||||
|
||||
while (!stack.empty ())
|
||||
{
|
||||
stack.top ().first->addRaw (s, snfWIRE);
|
||||
path.push_back (s.getData ());
|
||||
s.erase ();
|
||||
stack.pop ();
|
||||
}
|
||||
|
||||
return path;
|
||||
}
|
||||
|
||||
} // ripple
|
||||
|
||||
@@ -57,7 +57,7 @@ SHAMapTreeNode::SHAMapTreeNode (const SHAMapTreeNode& node, std::uint32_t seq)
|
||||
}
|
||||
}
|
||||
|
||||
SHAMapTreeNode::SHAMapTreeNode (SHAMapItem::ref item,
|
||||
SHAMapTreeNode::SHAMapTreeNode (std::shared_ptr<SHAMapItem> const& item,
|
||||
TNType type, std::uint32_t seq)
|
||||
: mItem (item)
|
||||
, mSeq (seq)
|
||||
@@ -402,7 +402,7 @@ void SHAMapTreeNode::addRaw (Serializer& s, SHANodeFormat format)
|
||||
assert (false);
|
||||
}
|
||||
|
||||
bool SHAMapTreeNode::setItem (SHAMapItem::ref i, TNType type)
|
||||
bool SHAMapTreeNode::setItem (std::shared_ptr<SHAMapItem> const& i, TNType type)
|
||||
{
|
||||
mType = type;
|
||||
mItem = i;
|
||||
@@ -437,12 +437,16 @@ void SHAMapTreeNode::makeInner ()
|
||||
mHash.zero ();
|
||||
}
|
||||
|
||||
#ifdef BEAST_DEBUG
|
||||
|
||||
void SHAMapTreeNode::dump (const SHAMapNodeID & id, beast::Journal journal)
|
||||
{
|
||||
if (journal.debug) journal.debug <<
|
||||
"SHAMapTreeNode(" << id.getNodeID () << ")";
|
||||
}
|
||||
|
||||
#endif // BEAST_DEBUG
|
||||
|
||||
std::string SHAMapTreeNode::getString (const SHAMapNodeID & id) const
|
||||
{
|
||||
std::string ret = "NodeID(";
|
||||
@@ -486,7 +490,7 @@ std::string SHAMapTreeNode::getString (const SHAMapNodeID & id) const
|
||||
}
|
||||
|
||||
// We are modifying an inner node
|
||||
bool SHAMapTreeNode::setChild (int m, uint256 const& hash, SHAMapTreeNode::ref child)
|
||||
bool SHAMapTreeNode::setChild (int m, uint256 const& hash, std::shared_ptr<SHAMapTreeNode> const& child)
|
||||
{
|
||||
assert ((m >= 0) && (m < 16));
|
||||
assert (mType == tnINNER);
|
||||
@@ -515,7 +519,7 @@ bool SHAMapTreeNode::setChild (int m, uint256 const& hash, SHAMapTreeNode::ref c
|
||||
}
|
||||
|
||||
// finished modifying, now make shareable
|
||||
void SHAMapTreeNode::shareChild (int m, SHAMapTreeNode::ref child)
|
||||
void SHAMapTreeNode::shareChild (int m, std::shared_ptr<SHAMapTreeNode> const& child)
|
||||
{
|
||||
assert ((m >= 0) && (m < 16));
|
||||
assert (mType == tnINNER);
|
||||
@@ -536,7 +540,7 @@ SHAMapTreeNode* SHAMapTreeNode::getChildPointer (int branch)
|
||||
return mChildren[branch].get ();
|
||||
}
|
||||
|
||||
SHAMapTreeNode::pointer SHAMapTreeNode::getChild (int branch)
|
||||
std::shared_ptr<SHAMapTreeNode> SHAMapTreeNode::getChild (int branch)
|
||||
{
|
||||
assert (branch >= 0 && branch < 16);
|
||||
assert (isInnerNode ());
|
||||
@@ -546,7 +550,7 @@ SHAMapTreeNode::pointer SHAMapTreeNode::getChild (int branch)
|
||||
return mChildren[branch];
|
||||
}
|
||||
|
||||
void SHAMapTreeNode::canonicalizeChild (int branch, SHAMapTreeNode::pointer& node)
|
||||
void SHAMapTreeNode::canonicalizeChild (int branch, std::shared_ptr<SHAMapTreeNode>& node)
|
||||
{
|
||||
assert (branch >= 0 && branch < 16);
|
||||
assert (isInnerNode ());
|
||||
|
||||
@@ -117,7 +117,7 @@ public:
|
||||
beast::Journal const j; // debug journal
|
||||
TestFamily f(j);
|
||||
std::shared_ptr <Table> t1 (std::make_shared <Table> (
|
||||
smtFREE, f, beast::Journal()));
|
||||
SHAMapType::FREE, f, beast::Journal()));
|
||||
|
||||
pass ();
|
||||
|
||||
@@ -141,7 +141,7 @@ public:
|
||||
// {
|
||||
// TestFilter filter (map, beast::Journal());
|
||||
//
|
||||
// t3 = std::make_shared <Table> (smtFREE, t2->getHash (),
|
||||
// t3 = std::make_shared <Table> (SHAMapType::FREE, t2->getHash (),
|
||||
// fullBelowCache);
|
||||
//
|
||||
// expect (t3->fetchRoot (t2->getHash (), &filter), "unable to get root");
|
||||
|
||||
@@ -63,12 +63,12 @@ public:
|
||||
h4.SetHex ("b92891fe4ef6cee585fdc6fda2e09eb4d386363158ec3321b8123e5a772c6ca8");
|
||||
h5.SetHex ("a92891fe4ef6cee585fdc6fda0e09eb4d386363158ec3321b8123e5a772c6ca7");
|
||||
|
||||
SHAMap sMap (smtFREE, f, beast::Journal());
|
||||
SHAMap sMap (SHAMapType::FREE, f, beast::Journal());
|
||||
SHAMapItem i1 (h1, IntToVUC (1)), i2 (h2, IntToVUC (2)), i3 (h3, IntToVUC (3)), i4 (h4, IntToVUC (4)), i5 (h5, IntToVUC (5));
|
||||
unexpected (!sMap.addItem (i2, true, false), "no add");
|
||||
unexpected (!sMap.addItem (i1, true, false), "no add");
|
||||
|
||||
SHAMapItem::pointer i;
|
||||
std::shared_ptr<SHAMapItem> i;
|
||||
i = sMap.peekFirstItem ();
|
||||
unexpected (!i || (*i != i1), "bad traverse");
|
||||
i = sMap.peekNextItem (i->getTag ());
|
||||
@@ -89,7 +89,7 @@ public:
|
||||
|
||||
testcase ("snapshot");
|
||||
uint256 mapHash = sMap.getHash ();
|
||||
SHAMap::pointer map2 = sMap.snapShot (false);
|
||||
std::shared_ptr<SHAMap> map2 = sMap.snapShot (false);
|
||||
unexpected (sMap.getHash () != mapHash, "bad snapshot");
|
||||
unexpected (map2->getHash () != mapHash, "bad snapshot");
|
||||
unexpected (!sMap.delItem (sMap.peekFirstItem ()->getTag ()), "bad mod");
|
||||
|
||||
@@ -37,7 +37,7 @@ namespace tests {
|
||||
class sync_test : public beast::unit_test::suite
|
||||
{
|
||||
public:
|
||||
static SHAMapItem::pointer makeRandomAS ()
|
||||
static std::shared_ptr<SHAMapItem> makeRandomAS ()
|
||||
{
|
||||
Serializer s;
|
||||
|
||||
@@ -56,7 +56,7 @@ public:
|
||||
|
||||
for (int i = 0; i < count; ++i)
|
||||
{
|
||||
SHAMapItem::pointer item = makeRandomAS ();
|
||||
std::shared_ptr<SHAMapItem> item = makeRandomAS ();
|
||||
items.push_back (item->getTag ());
|
||||
|
||||
if (!map.addItem (*item, false, false))
|
||||
@@ -101,8 +101,8 @@ public:
|
||||
beast::Journal const j; // debug journal
|
||||
|
||||
TestFamily f(j);
|
||||
SHAMap source (smtFREE, f, j);
|
||||
SHAMap destination (smtFREE, f, j);
|
||||
SHAMap source (SHAMapType::FREE, f, j);
|
||||
SHAMap destination (SHAMapType::FREE, f, j);
|
||||
|
||||
int items = 10000;
|
||||
for (int i = 0; i < items; ++i)
|
||||
|
||||
Reference in New Issue
Block a user