Skip to content
Draft
Show file tree
Hide file tree
Changes from 8 commits
Commits
Show all changes
18 commits
Select commit Hold shift + click to select a range
e5b21f0
Merge pull request #692 from Xahau/sync-2.4.0-rebased
RichardAH Feb 24, 2026
65837f4
fix: Add AMMv1_3 amendment (#5203)
gregtatcam Jun 2, 2025
ec65e62
Merge fixAMMv1_3 amendment into featureAMM amendment
tequdev Feb 19, 2026
8673599
fixAMMClawbackRounding: adjust last holder's LPToken balance (#5513)
yinyiqian1 Jul 11, 2025
8cfee6c
Merge fixAMMClawbackRounding amendment into featureAMMClawback amendment
tequdev Feb 19, 2026
355c9f9
port mutex fixes from XRPL port of RWDB
shortthefomo Apr 11, 2026
5280e5b
clang-format fixes
shortthefomo Apr 11, 2026
4ff2611
fix: RWDB rotation memory leak - copy only live state nodes instead o…
shortthefomo Apr 11, 2026
b016c19
feat: experiment with in-memory graph retention for null node-store
sublimator Apr 13, 2026
858cc20
feat: improve base ledger selection for priming in InboundLedger
sublimator Apr 13, 2026
c957778
fix: exclude self from priming base selection
sublimator Apr 13, 2026
67e1db7
fix: bound history priming ledger residency
sublimator Apr 13, 2026
e538a80
Fix null-rdwb memory leak, TOCTOU race, and consolidate env vars
shortthefomo Apr 13, 2026
0edae6d
Port fixes from rippled null-rdwb-experiment-mutex
shortthefomo Apr 13, 2026
4772bed
Fix null-mode rotation: use clearCaches to also clear FullBelowCache
shortthefomo Apr 14, 2026
308e89f
RWDB type always implies null backend: use non-rotating Database and …
shortthefomo Apr 15, 2026
3d927b0
Fix getJournal -> logs().journal() in null-mode makeNodeStore
shortthefomo Apr 15, 2026
c079ba0
fix brain fart to set huge mode nudb cache to 64mib
shortthefomo Apr 15, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
106 changes: 106 additions & 0 deletions include/xrpl/basics/ReaderPreferringSharedMutex.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,106 @@
#pragma once

#include <shared_mutex>

// On Linux (glibc), std::shared_mutex wraps pthread_rwlock_t initialised
// with PTHREAD_RWLOCK_PREFER_WRITER_NONRECURSIVE_NP. This means a
// pending exclusive lock() blocks new shared (reader) acquisitions,
// causing reader starvation when writers contend frequently.
//
// On macOS / ARM (libc++), std::shared_mutex is already reader-preferring,
// so the same code behaves differently across platforms.
//
// This header provides reader_preferring_shared_mutex:
// - On Linux it wraps pthread_rwlock_t initialised with
// PTHREAD_RWLOCK_PREFER_READER_NP, matching macOS semantics.
// - On all other platforms it is a type alias for std::shared_mutex.
//
// The interface is identical to std::shared_mutex, so it works with
// std::shared_lock and std::unique_lock.

#if defined(__linux__)

#include <cerrno>
#include <pthread.h>
#include <stdexcept>

namespace ripple {

class reader_preferring_shared_mutex
{
pthread_rwlock_t rwlock_;

public:
reader_preferring_shared_mutex()
{
pthread_rwlockattr_t attr;
pthread_rwlockattr_init(&attr);
pthread_rwlockattr_setkind_np(&attr, PTHREAD_RWLOCK_PREFER_READER_NP);
int rc = pthread_rwlock_init(&rwlock_, &attr);
pthread_rwlockattr_destroy(&attr);
if (rc != 0)
throw std::system_error(
rc, std::system_category(), "pthread_rwlock_init");
}

~reader_preferring_shared_mutex()
{
pthread_rwlock_destroy(&rwlock_);
}

reader_preferring_shared_mutex(reader_preferring_shared_mutex const&) =
delete;
reader_preferring_shared_mutex&
operator=(reader_preferring_shared_mutex const&) = delete;

// Exclusive (writer) locking
void
lock()
{
pthread_rwlock_wrlock(&rwlock_);
}

bool
try_lock()
{
return pthread_rwlock_trywrlock(&rwlock_) == 0;
}

void
unlock()
{
pthread_rwlock_unlock(&rwlock_);
}

// Shared (reader) locking
void
lock_shared()
{
pthread_rwlock_rdlock(&rwlock_);
}

bool
try_lock_shared()
{
return pthread_rwlock_tryrdlock(&rwlock_) == 0;
}

void
unlock_shared()
{
pthread_rwlock_unlock(&rwlock_);
}
};

} // namespace ripple

#else // !__linux__

namespace ripple {

// macOS, Windows, etc. — std::shared_mutex is already reader-preferring.
using reader_preferring_shared_mutex = std::shared_mutex;

} // namespace ripple

#endif
6 changes: 6 additions & 0 deletions include/xrpl/protocol/IOUAmount.h
Original file line number Diff line number Diff line change
Expand Up @@ -97,6 +97,12 @@ class IOUAmount : private boost::totally_ordered<IOUAmount>,

static IOUAmount
minPositiveAmount();

friend std::ostream&
operator<<(std::ostream& os, IOUAmount const& x)
{
return os << to_string(x);
}
};

inline IOUAmount::IOUAmount(beast::Zero)
Expand Down
3 changes: 3 additions & 0 deletions include/xrpl/protocol/Rules.h
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,9 @@

namespace ripple {

bool
isFeatureEnabled(uint256 const& feature);

class DigestAwareReadView;

/** Rules controlling protocol behavior. */
Expand Down
8 changes: 8 additions & 0 deletions src/libxrpl/protocol/Rules.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -153,4 +153,12 @@ Rules::operator!=(Rules const& other) const
{
return !(*this == other);
}

bool
isFeatureEnabled(uint256 const& feature)
{
auto const& rules = getCurrentTransactionRules();
return rules && rules->enabled(feature);
}

} // namespace ripple
Loading
Loading