// Copyright 2012 the V8 project authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#ifndef V8_V8THREADS_H_
#define V8_V8THREADS_H_

#include <atomic>

#include "src/isolate.h"

namespace v8 {
namespace internal {

class RootVisitor;
class ThreadLocalTop;

class ThreadState {
 public:
  // Returns nullptr after the last one.
  ThreadState* Next();

  enum List {FREE_LIST, IN_USE_LIST};

  void LinkInto(List list);
  void Unlink();

  // Id of thread.
  void set_id(ThreadId id) { id_ = id; }
  ThreadId id() { return id_; }

  // Get data area for archiving a thread.
  char* data() { return data_; }

 private:
  explicit ThreadState(ThreadManager* thread_manager);
  ~ThreadState();

  void AllocateSpace();

  ThreadId id_;
  char* data_;
  ThreadState* next_;
  ThreadState* previous_;

  ThreadManager* thread_manager_;

  friend class ThreadManager;
};

class ThreadVisitor {
 public:
  // ThreadLocalTop may be only available during this call.
  virtual void VisitThread(Isolate* isolate, ThreadLocalTop* top) = 0;

 protected:
  virtual ~ThreadVisitor() = default;
};

class ThreadManager {
 public:
  void Lock();
  void Unlock();

  void InitThread(const ExecutionAccess&);
  void ArchiveThread();
  bool RestoreThread();
  void FreeThreadResources();
  bool IsArchived();

  void Iterate(RootVisitor* v);
  void IterateArchivedThreads(ThreadVisitor* v);
  bool IsLockedByCurrentThread() const {
    return mutex_owner_.load(std::memory_order_relaxed) == ThreadId::Current();
  }

  ThreadId CurrentId();

  // Iterate over in-use states.
  ThreadState* FirstThreadStateInUse();
  ThreadState* GetFreeThreadState();

 private:
  explicit ThreadManager(Isolate* isolate);
  ~ThreadManager();

  void DeleteThreadStateList(ThreadState* anchor);

  void EagerlyArchiveThread();

  base::Mutex mutex_;
  // {ThreadId} must be trivially copyable to be stored in {std::atomic}.
  ASSERT_TRIVIALLY_COPYABLE(i::ThreadId);
  std::atomic<ThreadId> mutex_owner_;
  ThreadId lazily_archived_thread_;
  ThreadState* lazily_archived_thread_state_;

  // In the following two lists there is always at least one object on the list.
  // The first object is a flying anchor that is only there to simplify linking
  // and unlinking.
  // Head of linked list of free states.
  ThreadState* free_anchor_;
  // Head of linked list of states in use.
  ThreadState* in_use_anchor_;

  Isolate* isolate_;

  friend class Isolate;
  friend class ThreadState;
};


}  // namespace internal
}  // namespace v8

#endif  // V8_V8THREADS_H_
