Terraria v1.4.4.9
Terraria source code documentation
Loading...
Searching...
No Matches
AsyncMutex.cs
Go to the documentation of this file.
2
3namespace System.Threading;
4
5internal sealed class AsyncMutex
6{
7 private sealed class Waiter : TaskCompletionSource
8 {
9 public AsyncMutex Owner { get; }
10
12
13 public Waiter Next { get; set; }
14
15 public Waiter Prev { get; set; }
16
17 public Waiter(AsyncMutex owner)
19 {
20 Owner = owner;
21 }
22 }
23
24 private int _gate = 1;
25
26 private bool _lockedSemaphoreFull = true;
27
29
30 private object SyncObj => this;
31
33 {
34 if (!cancellationToken.IsCancellationRequested)
35 {
36 if (Interlocked.Decrement(ref _gate) < 0)
37 {
38 return Contended(cancellationToken);
39 }
40 return Task.CompletedTask;
41 }
44 {
45 Waiter waiter4 = new Waiter(this);
46 waiter4.CancellationRegistration = cancellationToken.UnsafeRegister(delegate(object s, CancellationToken token)
47 {
48 OnCancellation(s, token);
49 }, waiter4);
50 lock (SyncObj)
51 {
53 {
56 return Task.CompletedTask;
57 }
58 if (cancellationToken.IsCancellationRequested)
59 {
61 return waiter4.Task;
62 }
63 if (_waitersTail == null)
64 {
65 Waiter next2 = (waiter4.Prev = waiter4);
66 waiter4.Next = next2;
67 }
68 else
69 {
70 waiter4.Next = _waitersTail;
71 waiter4.Prev = _waitersTail.Prev;
72 Waiter prev = waiter4.Prev;
73 Waiter next2 = (waiter4.Next.Prev = waiter4);
74 prev.Next = next2;
75 }
76 _waitersTail = waiter4;
77 }
78 return waiter4.Task;
79 }
80 static void OnCancellation(object state, CancellationToken cancellationToken)
81 {
82 Waiter waiter = (Waiter)state;
83 AsyncMutex owner = waiter.Owner;
84 lock (owner.SyncObj)
85 {
86 if (waiter.Next != null)
87 {
88 Interlocked.Increment(ref owner._gate);
89 if (waiter.Next == waiter)
90 {
91 owner._waitersTail = null;
92 }
93 else
94 {
95 waiter.Next.Prev = waiter.Prev;
96 waiter.Prev.Next = waiter.Next;
97 if (owner._waitersTail == waiter)
98 {
99 owner._waitersTail = waiter.Next;
100 }
101 }
102 Waiter waiter2 = waiter;
103 Waiter next = (waiter.Prev = null);
104 waiter2.Next = next;
105 }
106 else
107 {
108 waiter = null;
109 }
110 }
112 }
113 }
114
115 public void Exit()
116 {
117 if (Interlocked.Increment(ref _gate) < 1)
118 {
119 Contended();
120 }
121 void Contended()
122 {
123 Waiter waiter;
124 lock (SyncObj)
125 {
126 waiter = _waitersTail;
127 if (waiter == null)
128 {
129 _lockedSemaphoreFull = false;
130 }
131 else
132 {
133 if (waiter.Next == waiter)
134 {
135 _waitersTail = null;
136 }
137 else
138 {
139 waiter = waiter.Prev;
140 waiter.Next.Prev = waiter.Prev;
141 waiter.Prev.Next = waiter.Next;
142 }
143 Waiter waiter2 = waiter;
144 Waiter next = (waiter.Prev = null);
145 waiter2.Next = next;
146 }
147 }
148 if (waiter != null)
149 {
151 waiter.TrySetResult();
152 }
153 }
154 }
155}
CancellationTokenRegistration CancellationRegistration
Definition AsyncMutex.cs:11
Task EnterAsync(CancellationToken cancellationToken)
Definition AsyncMutex.cs:32
static int Decrement(ref int location)
static int Increment(ref int location)
static Task FromCanceled(CancellationToken cancellationToken)
Definition Task.cs:3363
static Task CompletedTask
Definition Task.cs:1120