Skip to content

Commit a0d71e5

Browse files
authored
Merge pull request ceph#57725 from Matan-B/wip-matanb-crimson-load-exist
crimson/osd/object_context_loader: Fix obc cache existence usage Reviewed-by: Aishwarya Mathuria <[email protected]> Reviewed-by: Samuel Just <[email protected]> Reviewed-by: Xuehan Xu <[email protected]> Reviewed-by: Yingxin Cheng <[email protected]>
2 parents 437060b + 1675ce8 commit a0d71e5

File tree

6 files changed

+198
-53
lines changed

6 files changed

+198
-53
lines changed

src/crimson/common/interruptible_future.h

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1230,6 +1230,17 @@ struct interruptor
12301230
};
12311231
}
12321232

1233+
template <typename Lock, typename Func>
1234+
[[gnu::always_inline]]
1235+
static auto with_lock(Lock& lock, Func&& func) {
1236+
return seastar::with_lock(
1237+
lock,
1238+
[func=std::move(func),
1239+
interrupt_condition=interrupt_cond<InterruptCond>.interrupt_cond]() mutable {
1240+
return call_with_interruption(interrupt_condition, func);
1241+
});
1242+
}
1243+
12331244
template <typename Iterator,
12341245
InvokeReturnsInterruptibleFuture<typename Iterator::reference> AsyncAction>
12351246
[[gnu::always_inline]]

src/crimson/common/tri_mutex.cc

Lines changed: 65 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,11 @@
55

66
#include <seastar/util/later.hh>
77

8-
seastar::future<> read_lock::lock()
8+
SET_SUBSYS(osd);
9+
//TODO: SET_SUBSYS(crimson_tri_mutex);
10+
11+
std::optional<seastar::future<>>
12+
read_lock::lock()
913
{
1014
return static_cast<tri_mutex*>(this)->lock_for_read();
1115
}
@@ -15,7 +19,8 @@ void read_lock::unlock()
1519
static_cast<tri_mutex*>(this)->unlock_for_read();
1620
}
1721

18-
seastar::future<> write_lock::lock()
22+
std::optional<seastar::future<>>
23+
write_lock::lock()
1924
{
2025
return static_cast<tri_mutex*>(this)->lock_for_write();
2126
}
@@ -25,7 +30,8 @@ void write_lock::unlock()
2530
static_cast<tri_mutex*>(this)->unlock_for_write();
2631
}
2732

28-
seastar::future<> excl_lock::lock()
33+
std::optional<seastar::future<>>
34+
excl_lock::lock()
2935
{
3036
return static_cast<tri_mutex*>(this)->lock_for_excl();
3137
}
@@ -57,30 +63,40 @@ void excl_lock_from_write::unlock()
5763

5864
tri_mutex::~tri_mutex()
5965
{
66+
LOG_PREFIX(tri_mutex::~tri_mutex());
67+
DEBUGDPP("", *this);
6068
assert(!is_acquired());
6169
}
6270

63-
seastar::future<> tri_mutex::lock_for_read()
71+
std::optional<seastar::future<>>
72+
tri_mutex::lock_for_read()
6473
{
74+
LOG_PREFIX(tri_mutex::lock_for_read());
75+
DEBUGDPP("", *this);
6576
if (try_lock_for_read()) {
66-
return seastar::now();
77+
DEBUGDPP("lock_for_read successfully", *this);
78+
return std::nullopt;
6779
}
68-
waiters.emplace_back(seastar::promise<>(), type_t::read);
80+
DEBUGDPP("can't lock_for_read, adding to waiters", *this);
81+
waiters.emplace_back(seastar::promise<>(), type_t::read, name);
6982
return waiters.back().pr.get_future();
7083
}
7184

7285
bool tri_mutex::try_lock_for_read() noexcept
7386
{
87+
LOG_PREFIX(tri_mutex::try_lock_for_read());
88+
DEBUGDPP("", *this);
7489
if (!writers && !exclusively_used && waiters.empty()) {
7590
++readers;
7691
return true;
77-
} else {
78-
return false;
7992
}
93+
return false;
8094
}
8195

8296
void tri_mutex::unlock_for_read()
8397
{
98+
LOG_PREFIX(tri_mutex::unlock_for_read());
99+
DEBUGDPP("", *this);
84100
assert(readers > 0);
85101
if (--readers == 0) {
86102
wake();
@@ -89,40 +105,51 @@ void tri_mutex::unlock_for_read()
89105

90106
void tri_mutex::promote_from_read()
91107
{
108+
LOG_PREFIX(tri_mutex::promote_from_read());
109+
DEBUGDPP("", *this);
92110
assert(readers == 1);
93111
--readers;
94112
exclusively_used = true;
95113
}
96114

97115
void tri_mutex::demote_to_read()
98116
{
117+
LOG_PREFIX(tri_mutex::demote_to_read());
118+
DEBUGDPP("", *this);
99119
assert(exclusively_used);
100120
exclusively_used = false;
101121
++readers;
102122
}
103123

104-
seastar::future<> tri_mutex::lock_for_write()
124+
std::optional<seastar::future<>>
125+
tri_mutex::lock_for_write()
105126
{
127+
LOG_PREFIX(tri_mutex::lock_for_write());
128+
DEBUGDPP("", *this);
106129
if (try_lock_for_write()) {
107-
return seastar::now();
130+
DEBUGDPP("lock_for_write successfully", *this);
131+
return std::nullopt;
108132
}
109-
waiters.emplace_back(seastar::promise<>(), type_t::write);
133+
DEBUGDPP("can't lock_for_write, adding to waiters", *this);
134+
waiters.emplace_back(seastar::promise<>(), type_t::write, name);
110135
return waiters.back().pr.get_future();
111136
}
112137

113138
bool tri_mutex::try_lock_for_write() noexcept
114139
{
115-
if (!readers && !exclusively_used) {
116-
if (waiters.empty()) {
117-
++writers;
118-
return true;
119-
}
140+
LOG_PREFIX(tri_mutex::try_lock_for_write());
141+
DEBUGDPP("", *this);
142+
if (!readers && !exclusively_used && waiters.empty()) {
143+
++writers;
144+
return true;
120145
}
121146
return false;
122147
}
123148

124149
void tri_mutex::unlock_for_write()
125150
{
151+
LOG_PREFIX(tri_mutex::unlock_for_write());
152+
DEBUGDPP("", *this);
126153
assert(writers > 0);
127154
if (--writers == 0) {
128155
wake();
@@ -131,30 +158,41 @@ void tri_mutex::unlock_for_write()
131158

132159
void tri_mutex::promote_from_write()
133160
{
161+
LOG_PREFIX(tri_mutex::promote_from_write());
162+
DEBUGDPP("", *this);
134163
assert(writers == 1);
135164
--writers;
136165
exclusively_used = true;
137166
}
138167

139168
void tri_mutex::demote_to_write()
140169
{
170+
LOG_PREFIX(tri_mutex::demote_to_write());
171+
DEBUGDPP("", *this);
141172
assert(exclusively_used);
142173
exclusively_used = false;
143174
++writers;
144175
}
145176

146177
// for exclusive users
147-
seastar::future<> tri_mutex::lock_for_excl()
178+
std::optional<seastar::future<>>
179+
tri_mutex::lock_for_excl()
148180
{
181+
LOG_PREFIX(tri_mutex::lock_for_excl());
182+
DEBUGDPP("", *this);
149183
if (try_lock_for_excl()) {
150-
return seastar::now();
184+
DEBUGDPP("lock_for_excl, successfully", *this);
185+
return std::nullopt;
151186
}
152-
waiters.emplace_back(seastar::promise<>(), type_t::exclusive);
187+
DEBUGDPP("can't lock_for_excl, adding to waiters", *this);
188+
waiters.emplace_back(seastar::promise<>(), type_t::exclusive, name);
153189
return waiters.back().pr.get_future();
154190
}
155191

156192
bool tri_mutex::try_lock_for_excl() noexcept
157193
{
194+
LOG_PREFIX(tri_mutex::try_lock_for_excl());
195+
DEBUGDPP("", *this);
158196
if (readers == 0u && writers == 0u && !exclusively_used) {
159197
exclusively_used = true;
160198
return true;
@@ -165,13 +203,17 @@ bool tri_mutex::try_lock_for_excl() noexcept
165203

166204
void tri_mutex::unlock_for_excl()
167205
{
206+
LOG_PREFIX(tri_mutex::unlock_for_excl());
207+
DEBUGDPP("", *this);
168208
assert(exclusively_used);
169209
exclusively_used = false;
170210
wake();
171211
}
172212

173213
bool tri_mutex::is_acquired() const
174214
{
215+
LOG_PREFIX(tri_mutex::is_acquired());
216+
DEBUGDPP("", *this);
175217
if (readers != 0u) {
176218
return true;
177219
} else if (writers != 0u) {
@@ -185,6 +227,8 @@ bool tri_mutex::is_acquired() const
185227

186228
void tri_mutex::wake()
187229
{
230+
LOG_PREFIX(tri_mutex::wake());
231+
DEBUGDPP("", *this);
188232
assert(!readers && !writers && !exclusively_used);
189233
type_t type = type_t::none;
190234
while (!waiters.empty()) {
@@ -210,7 +254,9 @@ void tri_mutex::wake()
210254
default:
211255
assert(0);
212256
}
257+
DEBUGDPP("waking up {}", *this, waiter.waiter_name);
213258
waiter.pr.set_value();
214259
waiters.pop_front();
215260
}
261+
DEBUGDPP("no waiters", *this);
216262
}

src/crimson/common/tri_mutex.h

Lines changed: 35 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -3,24 +3,27 @@
33

44
#pragma once
55

6+
#include <optional>
7+
68
#include <seastar/core/future.hh>
79
#include <seastar/core/circular_buffer.hh>
10+
#include "crimson/common/log.h"
811

912
class read_lock {
1013
public:
11-
seastar::future<> lock();
14+
std::optional<seastar::future<>> lock();
1215
void unlock();
1316
};
1417

1518
class write_lock {
1619
public:
17-
seastar::future<> lock();
20+
std::optional<seastar::future<>> lock();
1821
void unlock();
1922
};
2023

2124
class excl_lock {
2225
public:
23-
seastar::future<> lock();
26+
std::optional<seastar::future<>> lock();
2427
void unlock();
2528
};
2629

@@ -62,6 +65,11 @@ class tri_mutex : private read_lock,
6265
{
6366
public:
6467
tri_mutex() = default;
68+
#ifdef NDEBUG
69+
tri_mutex(const std::string obj_name) : name() {}
70+
#else
71+
tri_mutex(const std::string obj_name) : name(obj_name) {}
72+
#endif
6573
~tri_mutex();
6674

6775
read_lock& for_read() {
@@ -81,7 +89,7 @@ class tri_mutex : private read_lock,
8189
}
8290

8391
// for shared readers
84-
seastar::future<> lock_for_read();
92+
std::optional<seastar::future<>> lock_for_read();
8593
bool try_lock_for_read() noexcept;
8694
void unlock_for_read();
8795
void promote_from_read();
@@ -91,7 +99,7 @@ class tri_mutex : private read_lock,
9199
}
92100

93101
// for shared writers
94-
seastar::future<> lock_for_write();
102+
std::optional<seastar::future<>> lock_for_write();
95103
bool try_lock_for_write() noexcept;
96104
void unlock_for_write();
97105
void promote_from_write();
@@ -101,7 +109,7 @@ class tri_mutex : private read_lock,
101109
}
102110

103111
// for exclusive users
104-
seastar::future<> lock_for_excl();
112+
std::optional<seastar::future<>> lock_for_excl();
105113
bool try_lock_for_excl() noexcept;
106114
void unlock_for_excl();
107115
bool is_excl_acquired() const {
@@ -120,6 +128,10 @@ class tri_mutex : private read_lock,
120128
}
121129
}
122130

131+
std::string_view get_name() const{
132+
return name;
133+
}
134+
123135
private:
124136
void wake();
125137
unsigned readers = 0;
@@ -132,17 +144,33 @@ class tri_mutex : private read_lock,
132144
none,
133145
};
134146
struct waiter_t {
135-
waiter_t(seastar::promise<>&& pr, type_t type)
147+
waiter_t(seastar::promise<>&& pr, type_t type, std::string_view waiter_name)
136148
: pr(std::move(pr)), type(type)
137149
{}
138150
seastar::promise<> pr;
139151
type_t type;
152+
std::string_view waiter_name;
140153
};
141154
seastar::circular_buffer<waiter_t> waiters;
155+
const std::string name;
142156
friend class read_lock;
143157
friend class write_lock;
144158
friend class excl_lock;
145159
friend class excl_lock_from_read;
146160
friend class excl_lock_from_write;
147161
friend class excl_lock_from_excl;
162+
friend std::ostream& operator<<(std::ostream &lhs, const tri_mutex &rhs);
148163
};
164+
165+
inline std::ostream& operator<<(std::ostream& os, const tri_mutex& tm)
166+
{
167+
os << fmt::format("tri_mutex {} writers {} readers {}"
168+
" exclusively_used {} waiters: {}",
169+
tm.get_name(), tm.get_writers(), tm.get_readers(),
170+
tm.exclusively_used, tm.waiters.size());
171+
return os;
172+
}
173+
174+
#if FMT_VERSION >= 90000
175+
template <> struct fmt::formatter<tri_mutex> : fmt::ostream_formatter {};
176+
#endif

0 commit comments

Comments
 (0)