20#include <xrpld/app/paths/Credit.h> 
   21#include <xrpld/app/paths/detail/AmountSpec.h> 
   22#include <xrpld/app/paths/detail/StepChecks.h> 
   23#include <xrpld/app/paths/detail/Steps.h> 
   25#include <xrpl/basics/Log.h> 
   26#include <xrpl/ledger/PaymentSandbox.h> 
   27#include <xrpl/protocol/Feature.h> 
   28#include <xrpl/protocol/IOUAmount.h> 
   29#include <xrpl/protocol/Quality.h> 
   30#include <xrpl/protocol/XRPAmount.h> 
   32#include <boost/container/flat_set.hpp> 
   38template <
class TDerived>
 
   40    : 
public StepImp<XRPAmount, XRPAmount, XRPEndpointStep<TDerived>>
 
  106        boost::container::flat_set<uint256>& ofrsToRm,
 
  113        boost::container::flat_set<uint256>& ofrsToRm,
 
  136             << 
"\nAcc: " << 
acc_;
 
 
  148        return !(lhs == rhs);
 
 
  235template <
class TDerived>
 
  244template <
class TDerived>
 
  255template <
class TDerived>
 
  260    boost::container::flat_set<uint256>& ofrsToRm,
 
  263    auto const balance = 
static_cast<TDerived const*
>(
this)->
xrpLiquid(sb);
 
  268    auto& receiver = isLast_ ? acc_ : 
xrpAccount();
 
  273    cache_.emplace(result);
 
  274    return {result, result};
 
 
  277template <
class TDerived>
 
  282    boost::container::flat_set<uint256>& ofrsToRm,
 
  285    XRPL_ASSERT(cache_, 
"ripple::XRPEndpointStep::fwdImp : cache is set");
 
  286    auto const balance = 
static_cast<TDerived const*
>(
this)->
xrpLiquid(sb);
 
  288    auto const result = isLast_ ? 
in : 
std::min(balance, 
in);
 
  291    auto& receiver = isLast_ ? acc_ : 
xrpAccount();
 
  296    cache_.emplace(result);
 
  297    return {result, result};
 
 
  300template <
class TDerived>
 
  309        JLOG(j_.
error()) << 
"Expected valid cache in validFwd";
 
  313    XRPL_ASSERT(
in.native, 
"ripple::XRPEndpointStep::validFwd : input is XRP");
 
  315    auto const& xrpIn = 
in.xrp;
 
  316    auto const balance = 
static_cast<TDerived const*
>(
this)->
xrpLiquid(sb);
 
  318    if (!isLast_ && balance < xrpIn)
 
  320        JLOG(j_.
warn()) << 
"XRPEndpointStep: Strand re-execute check failed." 
  321                        << 
" Insufficient balance: " << 
to_string(balance)
 
  326    if (xrpIn != *cache_)
 
  328        JLOG(j_.
warn()) << 
"XRPEndpointStep: Strand re-execute check failed." 
 
  335template <
class TDerived>
 
  341        JLOG(j_.
debug()) << 
"XRPEndpointStep: specified bad account.";
 
  348        JLOG(j_.
warn()) << 
"XRPEndpointStep: can't send or receive XRP from " 
  349                           "non-existent account: " 
  365    auto const issuesIndex = isLast_ ? 0 : 1;
 
  368        JLOG(j_.
debug()) << 
"XRPEndpointStep: loop detected: Index: " 
 
 
  386        return xs->acc() == acc;
 
 
  401        auto offerCrossingStep =
 
  403        ter = offerCrossingStep->check(ctx);
 
  404        r = std::move(offerCrossingStep);
 
  409        ter = paymentStep->check(ctx);
 
  410        r = std::move(paymentStep);
 
  413        return {ter, 
nullptr};
 
 
 
 
 
 
 
A generic endpoint for log messages.
 
Writeable view to a ledger, for applying a transaction.
 
A wrapper which makes credits unavailable to balances.
 
virtual std::shared_ptr< SLE const > read(Keylet const &k) const =0
Return the state item associated with a key.
 
static std::uint64_t const uRateOne
 
A step in a payment path.
 
std::int32_t const reserveReduction_
 
std::string logString() const override
 
XRPAmount xrpLiquid(ReadView &sb) const
 
static std::int32_t computeReserveReduction(StrandContext const &ctx, AccountID const &acc)
 
XRPEndpointOfferCrossingStep(StrandContext const &ctx, AccountID const &acc)
 
XRPAmount xrpLiquid(ReadView &sb) const
 
std::string logString() const override
 
std::optional< EitherAmount > cachedIn() const override
 
std::string logStringImpl(char const *name) const
 
TER check(StrandContext const &ctx) const
 
std::optional< XRPAmount > cache_
 
friend bool operator==(XRPEndpointStep< P > const &lhs, XRPEndpointStep< P > const &rhs)
 
std::pair< XRPAmount, XRPAmount > revImp(PaymentSandbox &sb, ApplyView &afView, boost::container::flat_set< uint256 > &ofrsToRm, XRPAmount const &out)
 
std::pair< XRPAmount, XRPAmount > fwdImp(PaymentSandbox &sb, ApplyView &afView, boost::container::flat_set< uint256 > &ofrsToRm, XRPAmount const &in)
 
friend bool operator!=(XRPEndpointStep const &lhs, XRPEndpointStep const &rhs)
 
std::pair< bool, EitherAmount > validFwd(PaymentSandbox &sb, ApplyView &afView, EitherAmount const &in) override
 
std::optional< std::pair< AccountID, AccountID > > directStepAccts() const override
 
std::optional< EitherAmount > cached() const
 
XRPAmount xrpLiquidImpl(ReadView &sb, std::int32_t reserveReduction) const
 
std::optional< EitherAmount > cachedOut() const override
 
XRPEndpointStep(StrandContext const &ctx, AccountID const &acc)
 
DebtDirection debtDirection(ReadView const &sb, StrandDirection dir) const override
 
AccountID const & acc() const
 
bool equal(Step const &rhs) const override
 
std::pair< std::optional< Quality >, DebtDirection > qualityUpperBound(ReadView const &v, DebtDirection prevStepDir) const override
 
Keylet line(AccountID const &id0, AccountID const &id1, Currency const ¤cy) noexcept
The index of a trust line for a given currency.
 
Keylet account(AccountID const &id) noexcept
AccountID root.
 
bool xrpEndpointStepEqual(Step const &step, AccountID const &acc)
 
Use hash_* containers for keys that do not need a cryptographically secure hashing algorithm.
 
Issue const & xrpIssue()
Returns an asset specifier that represents XRP.
 
AccountID const & xrpAccount()
Compute AccountID from public key.
 
std::pair< TER, std::unique_ptr< Step > > make_XRPEndpointStep(StrandContext const &ctx, AccountID const &acc)
 
TER checkFreeze(ReadView const &view, AccountID const &src, AccountID const &dst, Currency const ¤cy)
 
STAmount toSTAmount(IOUAmount const &iou, Issue const &iss)
 
TER accountSend(ApplyView &view, AccountID const &from, AccountID const &to, STAmount const &saAmount, beast::Journal j, WaiveTransferFee waiveFee=WaiveTransferFee::No)
Calls static accountSendIOU if saAmount represents Issue.
 
Currency const & xrpCurrency()
XRP currency.
 
std::string to_string(base_uint< Bits, Tag > const &a)
 
constexpr bool operator==(base_uint< Bits, Tag > const &lhs, base_uint< Bits, Tag > const &rhs)
 
XRPAmount xrpLiquid(ReadView const &view, AccountID const &id, std::int32_t ownerCountAdj, beast::Journal j)
 
Context needed to build Strand Steps and for error checking.
 
size_t const strandSize
Length of Strand.
 
ReadView const  & view
Current ReadView.
 
std::array< boost::container::flat_set< Issue >, 2 > & seenDirectIssues
A strand may not include the same account node more than once in the same currency.
 
OfferCrossing const offerCrossing
Yes/Sell if offer crossing, not payment.
 
bool const isFirst
true if Step is first in Strand
 
bool const isLast
true if Step is last in Strand
 
Issue const strandDeliver
Issue strand delivers.