
#ifndef PLS_SWMR_SPIN_LOCK_LOCK_H_
#define PLS_SWMR_SPIN_LOCK_LOCK_H_

#include <atomic>

#include "pls/internal/helpers/profiler.h"

namespace pls {
namespace internal {
namespace base {

/**
 * Single writer, multiple reader spin lock.
 * The writer is required to be the same thread all the time (single writer),
 * while multiple threads can read.
 * Readers fail to lock when the writer requests the lock,
 * the acquires the lock after all remaining readers left the critical section.
 */
class swmr_spin_lock {
  std::atomic<int> readers_;
  std::atomic<int> write_request_;

 public:
  explicit swmr_spin_lock() : readers_{0}, write_request_{0} {}

  bool reader_try_lock();
  void reader_unlock();

  void writer_lock();
  void writer_unlock();
};

}
}
}

#endif //PLS_SWMR_SPIN_LOCK_LOCK_H_
