Skip to content

Commit aeceb2c

Browse files
committed
[runtime] Addressed PR1731 comments and...
- cleaned up private scoping - removed generally unneeded API - fix defect in unit tests causing stuck threads
1 parent 3292124 commit aeceb2c

File tree

2 files changed

+21
-29
lines changed

2 files changed

+21
-29
lines changed

include/swift/Runtime/Mutex.h

+8-20
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,8 @@
1919

2020
#if (defined(__APPLE__) || defined(__linux__) || defined(__CYGWIN__))
2121
#define SWIFT_RUNTIME_MUTEX_HAVE_PHTREADS
22+
#else
23+
#error "Must implement the following if your platform doesn't support phtreads."
2224
#endif
2325

2426
#ifdef SWIFT_RUNTIME_MUTEX_HAVE_PHTREADS
@@ -74,18 +76,15 @@ class MutexImpl {
7476
MutexImpl(MutexImpl &&) = delete;
7577
MutexImpl &operator=(MutexImpl &&) = delete;
7678

77-
protected:
78-
explicit MutexImpl(bool checked);
79-
8079
public:
8180
void lock();
8281
void unlock();
8382
bool try_lock();
84-
85-
public:
8683
void wait(Condition &condition);
8784

8885
private:
86+
explicit MutexImpl(bool checked);
87+
8988
#ifdef SWIFT_RUNTIME_MUTEX_HAVE_PHTREADS
9089
pthread_mutex_t PThreadMutex;
9190
#endif
@@ -95,6 +94,7 @@ class MutexImpl {
9594
/// Use ScopedLock instead (see below).
9695
class ScopedLockImpl {
9796
friend class Mutex;
97+
friend class ScopedLock;
9898

9999
public:
100100
ScopedLockImpl() = delete;
@@ -105,20 +105,16 @@ class ScopedLockImpl {
105105
ScopedLockImpl(ScopedLockImpl &&) = delete;
106106
ScopedLockImpl &operator=(ScopedLockImpl &&) = delete;
107107

108-
protected:
109-
ScopedLockImpl(MutexImpl &impl) : Impl(impl) { Impl.lock(); }
110-
111-
public:
112-
void wait(Condition &condition) { Impl.wait(condition); }
113-
114108
private:
109+
ScopedLockImpl(MutexImpl &impl) : Impl(impl) { Impl.lock(); }
115110
MutexImpl &Impl;
116111
};
117112

118113
/// Internal (private) implementation of scoped unlocking functionality.
119114
/// Use ScopedUnlock instead (see below).
120115
class ScopedUnlockImpl {
121116
friend class Mutex;
117+
friend class ScopedUnlock;
122118

123119
public:
124120
ScopedUnlockImpl() = delete;
@@ -129,10 +125,8 @@ class ScopedUnlockImpl {
129125
ScopedUnlockImpl(ScopedUnlockImpl &&) = delete;
130126
ScopedUnlockImpl &operator=(ScopedUnlockImpl &&) = delete;
131127

132-
protected:
133-
ScopedUnlockImpl(MutexImpl &impl) : Impl(impl) { Impl.unlock(); }
134-
135128
private:
129+
ScopedUnlockImpl(MutexImpl &impl) : Impl(impl) { Impl.unlock(); }
136130
MutexImpl &Impl;
137131
};
138132

@@ -292,12 +286,6 @@ class ScopedLock : ScopedLockImpl {
292286
ScopedLock &operator=(const ScopedLock &) = delete;
293287
ScopedLock(ScopedLock &&) = delete;
294288
ScopedLock &operator=(ScopedLock &&) = delete;
295-
296-
public:
297-
/// Releases lock, waits on supplied condition, and relocks before returning.
298-
///
299-
/// Precondition: Mutex locked by this thread, undefined otherwise.
300-
void wait(Condition &condition) { ScopedLockImpl::wait(condition); }
301289
};
302290

303291
/// A stack based object that unlocks the supplied mutex on construction

unittests/runtime/Mutex.cpp

+13-9
Original file line numberDiff line numberDiff line change
@@ -285,10 +285,12 @@ TEST(MutexTest, ConditionThreaded) {
285285
[&](int index) {
286286
ScopedLock guard(mutex);
287287
while (true) {
288-
if (count - index >= 50) {
289-
count -= index;
290-
mutex.unlock(); // Only to give other consumers a chance.
291-
mutex.lock();
288+
if (count > 50) {
289+
count -= 1;
290+
{
291+
// To give other consumers a chance.
292+
ScopedUnlock unguard(mutex);
293+
}
292294
if (trace)
293295
printf("Consumer[%d] count-%d = %d\n", index, index, count);
294296
continue; // keep trying to consume before waiting again.
@@ -297,7 +299,7 @@ TEST(MutexTest, ConditionThreaded) {
297299
printf("Consumer[%d] count == %d and done!\n", index, count);
298300
break;
299301
}
300-
guard.wait(condition);
302+
mutex.wait(condition);
301303
}
302304
},
303305
[&](int index) {
@@ -328,10 +330,12 @@ TEST(MutexTest, ConditionLockOrWaitLockAndNotifyThreaded) {
328330
[&](int index) {
329331
mutex.lockOrWait(condition, [&, index] {
330332
while (true) {
331-
if (count - index >= 50) {
332-
count -= index;
333-
mutex.unlock(); // Only to give other consumers a chance.
334-
mutex.lock();
333+
if (count > 50) {
334+
count -= 1;
335+
{
336+
// To give other consumers a chance.
337+
ScopedUnlock unguard(mutex);
338+
}
335339
if (trace)
336340
printf("Consumer[%d] count-%d = %d\n", index, index, count);
337341
continue; // keep trying to consume before waiting again.

0 commit comments

Comments
 (0)