//===-- RegisterContextThreadMemory.cpp -----------------------------------===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//

#include "lldb/Target/OperatingSystem.h"
#include "lldb/Target/Process.h"
#include "lldb/Target/Thread.h"
#include "lldb/Utility/Status.h"
#include "lldb/lldb-private.h"

#include "RegisterContextThreadMemory.h"

using namespace lldb;
using namespace lldb_private;

RegisterContextThreadMemory::RegisterContextThreadMemory(
    Thread &thread, lldb::addr_t register_data_addr)
    : RegisterContext(thread, 0), m_thread_wp(thread.shared_from_this()),
      m_reg_ctx_sp(), m_register_data_addr(register_data_addr), m_stop_id(0) {}

RegisterContextThreadMemory::~RegisterContextThreadMemory() = default;

void RegisterContextThreadMemory::UpdateRegisterContext() {
  ThreadSP thread_sp(m_thread_wp.lock());
  if (thread_sp) {
    ProcessSP process_sp(thread_sp->GetProcess());

    if (process_sp) {
      const uint32_t stop_id = process_sp->GetModID().GetStopID();
      if (m_stop_id != stop_id) {
        m_stop_id = stop_id;
        m_reg_ctx_sp.reset();
      }
      if (!m_reg_ctx_sp) {
        ThreadSP backing_thread_sp(thread_sp->GetBackingThread());
        if (backing_thread_sp) {
          m_reg_ctx_sp = backing_thread_sp->GetRegisterContext();
        } else {
          OperatingSystem *os = process_sp->GetOperatingSystem();
          if (os->IsOperatingSystemPluginThread(thread_sp))
            m_reg_ctx_sp = os->CreateRegisterContextForThread(
                thread_sp.get(), m_register_data_addr);
        }
      }
    } else {
      m_reg_ctx_sp.reset();
    }
  } else {
    m_reg_ctx_sp.reset();
  }
}

// Subclasses must override these functions
void RegisterContextThreadMemory::InvalidateAllRegisters() {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    m_reg_ctx_sp->InvalidateAllRegisters();
}

size_t RegisterContextThreadMemory::GetRegisterCount() {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->GetRegisterCount();
  return 0;
}

const RegisterInfo *
RegisterContextThreadMemory::GetRegisterInfoAtIndex(size_t reg) {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->GetRegisterInfoAtIndex(reg);
  return nullptr;
}

size_t RegisterContextThreadMemory::GetRegisterSetCount() {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->GetRegisterSetCount();
  return 0;
}

const RegisterSet *RegisterContextThreadMemory::GetRegisterSet(size_t reg_set) {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->GetRegisterSet(reg_set);
  return nullptr;
}

bool RegisterContextThreadMemory::ReadRegister(const RegisterInfo *reg_info,
                                               RegisterValue &reg_value) {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->ReadRegister(reg_info, reg_value);
  return false;
}

bool RegisterContextThreadMemory::WriteRegister(
    const RegisterInfo *reg_info, const RegisterValue &reg_value) {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->WriteRegister(reg_info, reg_value);
  return false;
}

bool RegisterContextThreadMemory::ReadAllRegisterValues(
    lldb::WritableDataBufferSP &data_sp) {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->ReadAllRegisterValues(data_sp);
  return false;
}

bool RegisterContextThreadMemory::ReadAllRegisterValues(
    lldb_private::RegisterCheckpoint &reg_checkpoint) {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->ReadAllRegisterValues(reg_checkpoint);
  return false;
}

bool RegisterContextThreadMemory::WriteAllRegisterValues(
    const lldb::DataBufferSP &data_sp) {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->WriteAllRegisterValues(data_sp);
  return false;
}

bool RegisterContextThreadMemory::WriteAllRegisterValues(
    const lldb_private::RegisterCheckpoint &reg_checkpoint) {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->WriteAllRegisterValues(reg_checkpoint);
  return false;
}

bool RegisterContextThreadMemory::CopyFromRegisterContext(
    lldb::RegisterContextSP reg_ctx_sp) {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->CopyFromRegisterContext(reg_ctx_sp);
  return false;
}

uint32_t RegisterContextThreadMemory::ConvertRegisterKindToRegisterNumber(
    lldb::RegisterKind kind, uint32_t num) {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->ConvertRegisterKindToRegisterNumber(kind, num);
  return false;
}

uint32_t RegisterContextThreadMemory::NumSupportedHardwareBreakpoints() {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->NumSupportedHardwareBreakpoints();
  return false;
}

uint32_t RegisterContextThreadMemory::SetHardwareBreakpoint(lldb::addr_t addr,
                                                            size_t size) {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->SetHardwareBreakpoint(addr, size);
  return 0;
}

bool RegisterContextThreadMemory::ClearHardwareBreakpoint(uint32_t hw_idx) {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->ClearHardwareBreakpoint(hw_idx);
  return false;
}

uint32_t RegisterContextThreadMemory::NumSupportedHardwareWatchpoints() {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->NumSupportedHardwareWatchpoints();
  return 0;
}

uint32_t RegisterContextThreadMemory::SetHardwareWatchpoint(lldb::addr_t addr,
                                                            size_t size,
                                                            bool read,
                                                            bool write) {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->SetHardwareWatchpoint(addr, size, read, write);
  return 0;
}

bool RegisterContextThreadMemory::ClearHardwareWatchpoint(uint32_t hw_index) {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->ClearHardwareWatchpoint(hw_index);
  return false;
}

bool RegisterContextThreadMemory::HardwareSingleStep(bool enable) {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->HardwareSingleStep(enable);
  return false;
}

Status RegisterContextThreadMemory::ReadRegisterValueFromMemory(
    const lldb_private::RegisterInfo *reg_info, lldb::addr_t src_addr,
    uint32_t src_len, RegisterValue &reg_value) {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->ReadRegisterValueFromMemory(reg_info, src_addr,
                                                     src_len, reg_value);
  return Status::FromErrorString("invalid register context");
}

Status RegisterContextThreadMemory::WriteRegisterValueToMemory(
    const lldb_private::RegisterInfo *reg_info, lldb::addr_t dst_addr,
    uint32_t dst_len, const RegisterValue &reg_value) {
  UpdateRegisterContext();
  if (m_reg_ctx_sp)
    return m_reg_ctx_sp->WriteRegisterValueToMemory(reg_info, dst_addr, dst_len,
                                                    reg_value);
  return Status::FromErrorString("invalid register context");
}
