rippled
Loading...
Searching...
No Matches
OpenLedger.h
1//------------------------------------------------------------------------------
2/*
3 This file is part of rippled: https://github.com/ripple/rippled
4 Copyright (c) 2012, 2013 Ripple Labs Inc.
5
6 Permission to use, copy, modify, and/or distribute this software for any
7 purpose with or without fee is hereby granted, provided that the above
8 copyright notice and this permission notice appear in all copies.
9
10 THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
11 WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
12 MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
13 ANY SPECIAL , DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
14 WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
15 ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
16 OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
17*/
18//==============================================================================
19
20#ifndef RIPPLE_APP_LEDGER_OPENLEDGER_H_INCLUDED
21#define RIPPLE_APP_LEDGER_OPENLEDGER_H_INCLUDED
22
23#include <xrpld/app/ledger/Ledger.h>
24#include <xrpld/app/misc/CanonicalTXSet.h>
25#include <xrpld/core/Config.h>
26#include <xrpld/ledger/CachedSLEs.h>
27#include <xrpld/ledger/OpenView.h>
28#include <xrpl/basics/Log.h>
29#include <xrpl/basics/UnorderedContainers.h>
30#include <xrpl/beast/utility/Journal.h>
31#include <xrpl/beast/utility/instrumentation.h>
32
33#include <mutex>
34
35namespace ripple {
36
37// How many total extra passes we make
38// We must ensure we make at least one non-retriable pass
39#define LEDGER_TOTAL_PASSES 3
40
41// How many extra retry passes we
42// make if the previous retry pass made changes
43#define LEDGER_RETRY_PASSES 1
44
46
47//------------------------------------------------------------------------------
48
51{
52private:
58
59public:
72
73 OpenLedger() = delete;
74 OpenLedger(OpenLedger const&) = delete;
76 operator=(OpenLedger const&) = delete;
77
82 explicit OpenLedger(
84 CachedSLEs& cache,
85 beast::Journal journal);
86
100 bool
101 empty() const;
102
114 current() const;
115
126 bool
127 modify(modify_type const& f);
128
162 void
163 accept(
164 Application& app,
165 Rules const& rules,
166 std::shared_ptr<Ledger const> const& ledger,
167 OrderedTxs const& locals,
168 bool retriesFirst,
169 OrderedTxs& retries,
170 ApplyFlags flags,
171 std::string const& suffix = "",
172 modify_type const& f = {});
173
174private:
180 template <class FwdRange>
181 static void
182 apply(
183 Application& app,
184 OpenView& view,
185 ReadView const& check,
186 FwdRange const& txs,
187 OrderedTxs& retries,
188 ApplyFlags flags,
190
192
194 create(Rules const& rules, std::shared_ptr<Ledger const> const& ledger);
195
196 static Result
197 apply_one(
198 Application& app,
199 OpenView& view,
201 bool retry,
202 ApplyFlags flags,
204};
205
206//------------------------------------------------------------------------------
207
208template <class FwdRange>
209void
211 Application& app,
212 OpenView& view,
213 ReadView const& check,
214 FwdRange const& txs,
215 OrderedTxs& retries,
216 ApplyFlags flags,
218{
219 for (auto iter = txs.begin(); iter != txs.end(); ++iter)
220 {
221 try
222 {
223 // Dereferencing the iterator can throw since it may be transformed.
224 auto const tx = *iter;
225 auto const txId = tx->getTransactionID();
226 if (check.txExists(txId))
227 continue;
228 auto const result = apply_one(app, view, tx, true, flags, j);
229 if (result == Result::retry)
230 retries.insert(tx);
231 }
232 catch (std::exception const& e)
233 {
234 JLOG(j.error())
235 << "OpenLedger::apply: Caught exception: " << e.what();
236 }
237 }
238 bool retry = true;
239 for (int pass = 0; pass < LEDGER_TOTAL_PASSES; ++pass)
240 {
241 int changes = 0;
242 auto iter = retries.begin();
243 while (iter != retries.end())
244 {
245 switch (apply_one(app, view, iter->second, retry, flags, j))
246 {
247 case Result::success:
248 ++changes;
249 [[fallthrough]];
250 case Result::failure:
251 iter = retries.erase(iter);
252 break;
253 case Result::retry:
254 ++iter;
255 }
256 }
257 // A non-retry pass made no changes
258 if (!changes && !retry)
259 return;
260 // Stop retriable passes
261 if (!changes || (pass >= LEDGER_RETRY_PASSES))
262 retry = false;
263 }
264
265 // If there are any transactions left, we must have
266 // tried them in at least one final pass
267 XRPL_ASSERT(
268 retries.empty() || !retry, "ripple::OpenLedger::apply : valid retries");
269}
270
271//------------------------------------------------------------------------------
272
273// For debug logging
274
277
279debugTostr(OrderedTxs const& set);
280
282debugTostr(SHAMap const& set);
283
286
287} // namespace ripple
288
289#endif
A generic endpoint for log messages.
Definition: Journal.h:60
Stream error() const
Definition: Journal.h:346
Holds transactions which were deferred to the next pass of consensus.
void insert(std::shared_ptr< STTx const > const &txn)
const_iterator end() const
const_iterator begin() const
const_iterator erase(const_iterator const &it)
Represents the open ledger.
Definition: OpenLedger.h:51
bool modify(modify_type const &f)
Modify the open ledger.
Definition: OpenLedger.cpp:56
void accept(Application &app, Rules const &rules, std::shared_ptr< Ledger const > const &ledger, OrderedTxs const &locals, bool retriesFirst, OrderedTxs &retries, ApplyFlags flags, std::string const &suffix="", modify_type const &f={})
Accept a new ledger.
Definition: OpenLedger.cpp:70
CachedSLEs & cache_
Definition: OpenLedger.h:54
OpenLedger(OpenLedger const &)=delete
std::shared_ptr< OpenView > create(Rules const &rules, std::shared_ptr< Ledger const > const &ledger)
Definition: OpenLedger.cpp:146
bool empty() const
Returns true if there are no transactions.
Definition: OpenLedger.cpp:42
static void apply(Application &app, OpenView &view, ReadView const &check, FwdRange const &txs, OrderedTxs &retries, ApplyFlags flags, beast::Journal j)
Algorithm for applying transactions.
Definition: OpenLedger.h:210
std::mutex modify_mutex_
Definition: OpenLedger.h:55
OpenLedger & operator=(OpenLedger const &)=delete
static Result apply_one(Application &app, OpenView &view, std::shared_ptr< STTx const > const &tx, bool retry, ApplyFlags flags, beast::Journal j)
Definition: OpenLedger.cpp:157
std::shared_ptr< OpenView const > current_
Definition: OpenLedger.h:57
beast::Journal const j_
Definition: OpenLedger.h:53
std::shared_ptr< OpenView const > current() const
Returns a view to the current open ledger.
Definition: OpenLedger.cpp:49
std::mutex current_mutex_
Definition: OpenLedger.h:56
Writable ledger view that accumulates state and tx changes.
Definition: OpenView.h:56
A view into a ledger.
Definition: ReadView.h:51
Rules controlling protocol behavior.
Definition: Rules.h:35
A SHAMap is both a radix tree with a fan-out of 16 and a Merkle tree.
Definition: SHAMap.h:94
Map/cache combination.
Definition: TaggedCache.h:58
Use hash_* containers for keys that do not need a cryptographically secure hashing algorithm.
Definition: algorithm.h:26
boost::outcome_v2::result< T, std::error_code > Result
Definition: b58_utils.h:38
std::string debugTostr(OrderedTxs const &set)
Definition: OpenLedger.cpp:188
ApplyFlags
Definition: ApplyView.h:30
std::string debugTxstr(std::shared_ptr< STTx const > const &tx)
Definition: OpenLedger.cpp:180
T what(T... args)