stdex Additional custom or not Standard C++ covered algorithms

Loading...
Searching...
No Matches
spinlock.hpp
1/*
2 SPDX-License-Identifier: MIT
3 Copyright © 2023-2024 Amebis
4*/
5
6#pragma once
7
8#ifdef _WIN32
9#include "windows.h"
10#include <intrin.h>
11#endif
12#include <atomic>
13
14 namespace stdex
15{
21 class spinlock
22 {
23 private:
24 std::atomic<bool> m_lock = { false };
25
26 public:
30 void lock() noexcept
31 {
32 for (;;) {
33 // Optimistically assume the lock is free on the first try
34 if (!m_lock.exchange(true, std::memory_order_acquire))
35 return;
36
37 // Wait for lock to be released without generating cache misses
38 while (m_lock.load(std::memory_order_relaxed)) {
39 // Issue X86 PAUSE or ARM YIELD instruction to reduce contention between
40 // hyper-threads
41#if _M_ARM || _M_ARM64
42 __yield();
43#elif _M_IX86 || _M_X64
44 _mm_pause();
45#elif __aarch64__
46 asm volatile("yield");
47#elif __i386__ || __x86_64__
48 __builtin_ia32_pause();
49#endif
50 }
51 }
52 }
53
59 bool try_lock() noexcept
60 {
61 // First do a relaxed load to check if lock is free in order to prevent
62 // unnecessary cache misses if someone does while(!try_lock())
63 return
64 !m_lock.load(std::memory_order_relaxed) &&
65 !m_lock.exchange(true, std::memory_order_acquire);
66 }
67
71 void unlock() noexcept
72 {
73 m_lock.store(false, std::memory_order_release);
74 }
75 };
76}
stdex::spinlock
Spin-lock.
Definition spinlock.hpp:22
stdex::spinlock::try_lock
bool try_lock() noexcept
Attempts to acquire the lock for the current execution agent (thread, process, task) without blocking...
Definition spinlock.hpp:59
stdex::spinlock::lock
void lock() noexcept
Blocks until a lock can be acquired for the current execution agent (thread, process,...
Definition spinlock.hpp:30
stdex::spinlock::unlock
void unlock() noexcept
Releases the non-shared lock held by the execution agent.
Definition spinlock.hpp:71