SpinLock: Add acquire/release() and spinPause()

We're very careful to ensure that we add a cpu_relax hint.
This commit is contained in:
2025-09-18 22:58:09 -04:00
parent ec50526804
commit 596bc1fbd2
+46
View File
@@ -2,6 +2,17 @@
#define SPIN_LOCK_H
#include <atomic>
#ifdef __x86_64__
#include <immintrin.h>
#elif defined(__i386__)
#include <xmmintrin.h>
#elif defined(__arm__)
#include <arm_neon.h>
#elif defined(__aarch64__)
#include <arm_neon.h>
#elif defined(__aarch32__)
#include <arm_neon.h>
#endif
namespace smo {
@@ -21,6 +32,41 @@ public:
return locked.compare_exchange_strong(expected, true);
}
inline void spinPause()
{
#ifdef __x86_64__
_mm_pause();
#elif defined(__i386__)
_mm_pause();
#elif defined(__arm__)
__asm__ volatile("yield");
#elif defined(__aarch64__)
__asm__ volatile("yield");
#elif defined(__aarch32__)
__asm__ volatile("yield");
#else
# error "Unsupported architecture"
#endif
}
void acquire()
{
while (!tryAcquire())
{
/** EXPLANATION:
* Busy-wait: keep trying to acquire the lock
* The CPU will spin here until the lock becomes available
*
* The spinPause() function is architecture-specific and is
* essential because I once fried an older Intel M-class laptop CPU
* when I forgot to include a PAUSE instruction in a for (;;){}
* loop. I'm not interested in frying my RPi or my other testbed
* robot boards.
*/
spinPause();
}
}
void release()
{
locked.store(false);