spin_lock.hpp 1.2 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768
  1. /*
  2. * Copyright (c) 2017-2023 zhllxt
  3. *
  4. * author : zhllxt
  5. * email : 37792738@qq.com
  6. *
  7. * Distributed under the Boost Software License, Version 1.0. (See accompanying
  8. * file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
  9. *
  10. * referenced from boost/smart_ptr/detail/spinlock_std_atomic.hpp
  11. */
  12. #ifndef __ASIO2_SPIN_LOCK_HPP__
  13. #define __ASIO2_SPIN_LOCK_HPP__
  14. #if defined(_MSC_VER) && (_MSC_VER >= 1200)
  15. #pragma once
  16. #endif // defined(_MSC_VER) && (_MSC_VER >= 1200)
  17. #include <atomic>
  18. #include <thread>
  19. namespace asio2
  20. {
  21. class spin_lock
  22. {
  23. public:
  24. spin_lock() noexcept
  25. {
  26. v_.clear();
  27. }
  28. bool try_lock() noexcept
  29. {
  30. return !v_.test_and_set(std::memory_order_acquire);
  31. }
  32. void lock() noexcept
  33. {
  34. for (unsigned k = 0; !try_lock(); ++k)
  35. {
  36. if (k < 16)
  37. {
  38. std::this_thread::yield();
  39. }
  40. else if (k < 32)
  41. {
  42. std::this_thread::sleep_for(std::chrono::milliseconds(0));
  43. }
  44. else
  45. {
  46. std::this_thread::sleep_for(std::chrono::milliseconds(1));
  47. }
  48. }
  49. }
  50. void unlock() noexcept
  51. {
  52. v_.clear(std::memory_order_release);
  53. }
  54. public:
  55. std::atomic_flag v_;
  56. };
  57. }
  58. #endif // !__ASIO2_SPIN_LOCK_HPP__