Files
certmgr/certmgr/Core/Utils/AsyncLock.cs
2025-10-18 10:26:43 +02:00

46 lines
1.1 KiB
C#

namespace CertMgr.Core.Utils;
using System;
using System.Threading;
using System.Threading.Tasks;
public sealed class AsyncLock
{
private readonly SemaphoreSlim _semaphore;
private readonly Task<IDisposable> _disposer;
public AsyncLock()
{
_semaphore = new SemaphoreSlim(1, 1);
_disposer = Task.FromResult((IDisposable)new AsyncLockDisposer(this));
}
public Task<IDisposable> LockAsync(CancellationToken cancellation = default)
{
Task wait = _semaphore.WaitAsync();
if (wait.IsCompleted)
{
return _disposer;
}
else
{
return wait.ContinueWith((_, state) => (IDisposable)state!, _disposer.Result, CancellationToken.None, TaskContinuationOptions.ExecuteSynchronously, TaskScheduler.Default);
}
}
private sealed class AsyncLockDisposer : IDisposable
{
private readonly AsyncLock _owner;
internal AsyncLockDisposer(AsyncLock owner)
{
_owner = owner;
}
public void Dispose()
{
_owner._semaphore.Release();
}
}
}