Common: Implement a basic SpinLock class
This commit is contained in:
		
							parent
							
								
									bfa6193eb9
								
							
						
					
					
						commit
						13ed9438fb
					
				@ -143,6 +143,8 @@ add_library(common STATIC
 | 
			
		||||
    scm_rev.cpp
 | 
			
		||||
    scm_rev.h
 | 
			
		||||
    scope_exit.h
 | 
			
		||||
    spin_lock.cpp
 | 
			
		||||
    spin_lock.h
 | 
			
		||||
    string_util.cpp
 | 
			
		||||
    string_util.h
 | 
			
		||||
    swap.h
 | 
			
		||||
 | 
			
		||||
							
								
								
									
										46
									
								
								src/common/spin_lock.cpp
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										46
									
								
								src/common/spin_lock.cpp
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,46 @@
 | 
			
		||||
// Copyright 2020 yuzu Emulator Project
 | 
			
		||||
// Licensed under GPLv2 or any later version
 | 
			
		||||
// Refer to the license.txt file included.
 | 
			
		||||
 | 
			
		||||
#include "common/spin_lock.h"
 | 
			
		||||
 | 
			
		||||
#if _MSC_VER
 | 
			
		||||
#include <intrin.h>
 | 
			
		||||
#if _M_AMD64
 | 
			
		||||
#define __x86_64__ 1
 | 
			
		||||
#endif
 | 
			
		||||
#if _M_ARM64
 | 
			
		||||
#define __aarch64__ 1
 | 
			
		||||
#endif
 | 
			
		||||
#else
 | 
			
		||||
#if __x86_64__
 | 
			
		||||
#include <xmmintrin.h>
 | 
			
		||||
#endif
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
namespace {
 | 
			
		||||
 | 
			
		||||
void thread_pause() {
 | 
			
		||||
#if __x86_64__
 | 
			
		||||
    _mm_pause();
 | 
			
		||||
#elif __aarch64__ && _MSC_VER
 | 
			
		||||
    __yield();
 | 
			
		||||
#elif __aarch64__
 | 
			
		||||
    asm("yield");
 | 
			
		||||
#endif
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
} // namespace
 | 
			
		||||
 | 
			
		||||
namespace Common {
 | 
			
		||||
 | 
			
		||||
void SpinLock::lock() {
 | 
			
		||||
    while (lck.test_and_set(std::memory_order_acquire))
 | 
			
		||||
        thread_pause();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SpinLock::unlock() {
 | 
			
		||||
    lck.clear(std::memory_order_release);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
} // namespace Common
 | 
			
		||||
							
								
								
									
										20
									
								
								src/common/spin_lock.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										20
									
								
								src/common/spin_lock.h
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,20 @@
 | 
			
		||||
// Copyright 2020 yuzu Emulator Project
 | 
			
		||||
// Licensed under GPLv2 or any later version
 | 
			
		||||
// Refer to the license.txt file included.
 | 
			
		||||
 | 
			
		||||
#pragma once
 | 
			
		||||
 | 
			
		||||
#include <atomic>
 | 
			
		||||
 | 
			
		||||
namespace Common {
 | 
			
		||||
 | 
			
		||||
class SpinLock {
 | 
			
		||||
public:
 | 
			
		||||
    void lock();
 | 
			
		||||
    void unlock();
 | 
			
		||||
 | 
			
		||||
private:
 | 
			
		||||
    std::atomic_flag lck = ATOMIC_FLAG_INIT;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
} // namespace Common
 | 
			
		||||
		Loading…
	
		Reference in New Issue
	
	Block a user