7
7
#pragma once
8
8
9
9
#include < AK/Assertions.h>
10
- #include < AK/Atomic.h>
11
10
#include < AK/RefCounted.h>
12
11
#include < AK/RefPtr.h>
13
12
#include < AK/StdLibExtras.h>
14
- #include < sched.h>
15
13
16
14
namespace AK {
17
15
@@ -31,59 +29,27 @@ class WeakLink : public RefCounted<WeakLink> {
31
29
RefPtr<T> strong_ref () const
32
30
requires(IsBaseOf<RefCountedBase, T>)
33
31
{
34
- RefPtr<T> ref;
35
-
36
- {
37
- if (!(m_consumers.fetch_add (1u << 1 , AK::MemoryOrder::memory_order_acquire) & 1u )) {
38
- T* ptr = (T*)m_ptr.load (AK::MemoryOrder::memory_order_acquire);
39
- if (ptr && ptr->try_ref ())
40
- ref = adopt_ref (*ptr);
41
- }
42
- m_consumers.fetch_sub (1u << 1 , AK::MemoryOrder::memory_order_release);
43
- }
44
-
45
- return ref;
32
+ return static_cast <T*>(m_ptr);
46
33
}
47
34
48
35
template <typename T>
49
36
T* unsafe_ptr () const
50
37
{
51
- if (m_consumers.load (AK::MemoryOrder::memory_order_relaxed) & 1u )
52
- return nullptr ;
53
- // NOTE: This may return a non-null pointer even if revocation
54
- // has been triggered as there is a possible race! But it's "unsafe"
55
- // anyway because we return a raw pointer without ensuring a
56
- // reference...
57
- return (T*)m_ptr.load (AK::MemoryOrder::memory_order_acquire);
38
+ return static_cast <T*>(m_ptr);
58
39
}
59
40
60
- bool is_null () const
61
- {
62
- return unsafe_ptr<void >() == nullptr ;
63
- }
41
+ bool is_null () const { return m_ptr == nullptr ; }
64
42
65
- void revoke ()
66
- {
67
- auto current_consumers = m_consumers.fetch_or (1u , AK::MemoryOrder::memory_order_relaxed);
68
- VERIFY (!(current_consumers & 1u ));
69
- // We flagged revocation, now wait until everyone trying to obtain
70
- // a strong reference is done
71
- while (current_consumers > 0 ) {
72
- sched_yield ();
73
- current_consumers = m_consumers.load (AK::MemoryOrder::memory_order_acquire) & ~1u ;
74
- }
75
- // No one is trying to use it (anymore)
76
- m_ptr.store (nullptr , AK::MemoryOrder::memory_order_release);
77
- }
43
+ void revoke () { m_ptr = nullptr ; }
78
44
79
45
private:
80
46
template <typename T>
81
47
explicit WeakLink (T& weakable)
82
48
: m_ptr(&weakable)
83
49
{
84
50
}
85
- mutable Atomic< void *> m_ptr;
86
- mutable Atomic< unsigned > m_consumers; // LSB indicates revocation in progress
51
+
52
+ mutable void * m_ptr { nullptr };
87
53
};
88
54
89
55
template <typename T>
0 commit comments