//===-- SBThreadPlan.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 "SBReproducerPrivate.h"
#include "lldb/API/SBThread.h"

#include "lldb/API/SBFileSpec.h"
#include "lldb/API/SBStream.h"
#include "lldb/API/SBStructuredData.h"
#include "lldb/API/SBSymbolContext.h"
#include "lldb/Breakpoint/BreakpointLocation.h"
#include "lldb/Core/Debugger.h"
#include "lldb/Core/StreamFile.h"
#include "lldb/Core/StructuredDataImpl.h"
#include "lldb/Interpreter/CommandInterpreter.h"
#include "lldb/Symbol/CompileUnit.h"
#include "lldb/Symbol/SymbolContext.h"
#include "lldb/Target/Process.h"
#include "lldb/Target/Queue.h"
#include "lldb/Target/StopInfo.h"
#include "lldb/Target/SystemRuntime.h"
#include "lldb/Target/Target.h"
#include "lldb/Target/Thread.h"
#include "lldb/Target/ThreadPlan.h"
#include "lldb/Target/ThreadPlanPython.h"
#include "lldb/Target/ThreadPlanStepInRange.h"
#include "lldb/Target/ThreadPlanStepInstruction.h"
#include "lldb/Target/ThreadPlanStepOut.h"
#include "lldb/Target/ThreadPlanStepRange.h"
#include "lldb/Utility/State.h"
#include "lldb/Utility/Stream.h"
#include "lldb/Utility/StructuredData.h"

#include "lldb/API/SBAddress.h"
#include "lldb/API/SBDebugger.h"
#include "lldb/API/SBEvent.h"
#include "lldb/API/SBFrame.h"
#include "lldb/API/SBProcess.h"
#include "lldb/API/SBThreadPlan.h"
#include "lldb/API/SBValue.h"

#include <memory>

using namespace lldb;
using namespace lldb_private;

// Constructors
SBThreadPlan::SBThreadPlan() { LLDB_RECORD_CONSTRUCTOR_NO_ARGS(SBThreadPlan); }

SBThreadPlan::SBThreadPlan(const ThreadPlanSP &lldb_object_sp)
    : m_opaque_wp(lldb_object_sp) {
  LLDB_RECORD_CONSTRUCTOR(SBThreadPlan, (const lldb::ThreadPlanSP &),
                          lldb_object_sp);
}

SBThreadPlan::SBThreadPlan(const SBThreadPlan &rhs)
    : m_opaque_wp(rhs.m_opaque_wp) {
  LLDB_RECORD_CONSTRUCTOR(SBThreadPlan, (const lldb::SBThreadPlan &), rhs);
}

SBThreadPlan::SBThreadPlan(lldb::SBThread &sb_thread, const char *class_name) {
  LLDB_RECORD_CONSTRUCTOR(SBThreadPlan, (lldb::SBThread &, const char *),
                          sb_thread, class_name);

  Thread *thread = sb_thread.get();
  if (thread)
    m_opaque_wp =
        std::make_shared<ThreadPlanPython>(*thread, class_name, nullptr);
}

SBThreadPlan::SBThreadPlan(lldb::SBThread &sb_thread, const char *class_name,
                           lldb::SBStructuredData &args_data) {
  LLDB_RECORD_CONSTRUCTOR(SBThreadPlan, (lldb::SBThread &, const char *,
                                         SBStructuredData &),
                          sb_thread, class_name, args_data);

  Thread *thread = sb_thread.get();
  if (thread)
    m_opaque_wp = std::make_shared<ThreadPlanPython>(*thread, class_name,
                                                     args_data.m_impl_up.get());
}

// Assignment operator

const lldb::SBThreadPlan &SBThreadPlan::operator=(const SBThreadPlan &rhs) {
  LLDB_RECORD_METHOD(const lldb::SBThreadPlan &,
                     SBThreadPlan, operator=,(const lldb::SBThreadPlan &), rhs);

  if (this != &rhs)
    m_opaque_wp = rhs.m_opaque_wp;
  return LLDB_RECORD_RESULT(*this);
}
// Destructor
SBThreadPlan::~SBThreadPlan() = default;

bool SBThreadPlan::IsValid() const {
  LLDB_RECORD_METHOD_CONST_NO_ARGS(bool, SBThreadPlan, IsValid);
  return this->operator bool();
}
SBThreadPlan::operator bool() const {
  LLDB_RECORD_METHOD_CONST_NO_ARGS(bool, SBThreadPlan, operator bool);

  return static_cast<bool>(GetSP());
}

void SBThreadPlan::Clear() {
  LLDB_RECORD_METHOD_NO_ARGS(void, SBThreadPlan, Clear);

  m_opaque_wp.reset();
}

lldb::StopReason SBThreadPlan::GetStopReason() {
  LLDB_RECORD_METHOD_NO_ARGS(lldb::StopReason, SBThreadPlan, GetStopReason);

  return eStopReasonNone;
}

size_t SBThreadPlan::GetStopReasonDataCount() {
  LLDB_RECORD_METHOD_NO_ARGS(size_t, SBThreadPlan, GetStopReasonDataCount);

  return 0;
}

uint64_t SBThreadPlan::GetStopReasonDataAtIndex(uint32_t idx) {
  LLDB_RECORD_METHOD(uint64_t, SBThreadPlan, GetStopReasonDataAtIndex,
                     (uint32_t), idx);

  return 0;
}

SBThread SBThreadPlan::GetThread() const {
  LLDB_RECORD_METHOD_CONST_NO_ARGS(lldb::SBThread, SBThreadPlan, GetThread);

  ThreadPlanSP thread_plan_sp(GetSP());
  if (thread_plan_sp) {
    return LLDB_RECORD_RESULT(
        SBThread(thread_plan_sp->GetThread().shared_from_this()));
  } else
    return LLDB_RECORD_RESULT(SBThread());
}

bool SBThreadPlan::GetDescription(lldb::SBStream &description) const {
  LLDB_RECORD_METHOD_CONST(bool, SBThreadPlan, GetDescription,
                           (lldb::SBStream &), description);

  ThreadPlanSP thread_plan_sp(GetSP());
  if (thread_plan_sp) {
    thread_plan_sp->GetDescription(description.get(), eDescriptionLevelFull);
  } else {
    description.Printf("Empty SBThreadPlan");
  }
  return true;
}

void SBThreadPlan::SetThreadPlan(const ThreadPlanSP &lldb_object_wp) {
  m_opaque_wp = lldb_object_wp;
}

void SBThreadPlan::SetPlanComplete(bool success) {
  LLDB_RECORD_METHOD(void, SBThreadPlan, SetPlanComplete, (bool), success);

  ThreadPlanSP thread_plan_sp(GetSP());
  if (thread_plan_sp)
    thread_plan_sp->SetPlanComplete(success);
}

bool SBThreadPlan::IsPlanComplete() {
  LLDB_RECORD_METHOD_NO_ARGS(bool, SBThreadPlan, IsPlanComplete);

  ThreadPlanSP thread_plan_sp(GetSP());
  if (thread_plan_sp)
    return thread_plan_sp->IsPlanComplete();
  return true;
}

bool SBThreadPlan::IsPlanStale() {
  LLDB_RECORD_METHOD_NO_ARGS(bool, SBThreadPlan, IsPlanStale);

  ThreadPlanSP thread_plan_sp(GetSP());
  if (thread_plan_sp)
    return thread_plan_sp->IsPlanStale();
  return true;
}

bool SBThreadPlan::IsValid() {
  LLDB_RECORD_METHOD_NO_ARGS(bool, SBThreadPlan, IsValid);

  ThreadPlanSP thread_plan_sp(GetSP());
  if (thread_plan_sp)
    return thread_plan_sp->ValidatePlan(nullptr);
  return false;
}

bool SBThreadPlan::GetStopOthers() {
  LLDB_RECORD_METHOD_NO_ARGS(bool, SBThreadPlan, GetStopOthers);

  ThreadPlanSP thread_plan_sp(GetSP());
  if (thread_plan_sp)
    return thread_plan_sp->StopOthers();
  return false;
}

void SBThreadPlan::SetStopOthers(bool stop_others) {
  LLDB_RECORD_METHOD(void, SBThreadPlan, SetStopOthers, (bool), stop_others);

  ThreadPlanSP thread_plan_sp(GetSP());
  if (thread_plan_sp)
    thread_plan_sp->SetStopOthers(stop_others);
}

// This section allows an SBThreadPlan to push another of the common types of
// plans...
//
// FIXME, you should only be able to queue thread plans from inside the methods
// of a Scripted Thread Plan.  Need a way to enforce that.

SBThreadPlan
SBThreadPlan::QueueThreadPlanForStepOverRange(SBAddress &sb_start_address,
                                              lldb::addr_t size) {
  LLDB_RECORD_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                     QueueThreadPlanForStepOverRange,
                     (lldb::SBAddress &, lldb::addr_t), sb_start_address, size);

  SBError error;
  return LLDB_RECORD_RESULT(
      QueueThreadPlanForStepOverRange(sb_start_address, size, error));
}

SBThreadPlan SBThreadPlan::QueueThreadPlanForStepOverRange(
    SBAddress &sb_start_address, lldb::addr_t size, SBError &error) {
  LLDB_RECORD_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                     QueueThreadPlanForStepOverRange,
                     (lldb::SBAddress &, lldb::addr_t, lldb::SBError &),
                     sb_start_address, size, error);

  ThreadPlanSP thread_plan_sp(GetSP());
  if (thread_plan_sp) {
    Address *start_address = sb_start_address.get();
    if (!start_address) {
      return LLDB_RECORD_RESULT(SBThreadPlan());
    }

    AddressRange range(*start_address, size);
    SymbolContext sc;
    start_address->CalculateSymbolContext(&sc);
    Status plan_status;

    SBThreadPlan plan = SBThreadPlan(
        thread_plan_sp->GetThread().QueueThreadPlanForStepOverRange(
            false, range, sc, eAllThreads, plan_status));

    if (plan_status.Fail())
      error.SetErrorString(plan_status.AsCString());
    else
      plan.GetSP()->SetPrivate(true);

    return LLDB_RECORD_RESULT(plan);
  }
  return LLDB_RECORD_RESULT(SBThreadPlan());
}

SBThreadPlan
SBThreadPlan::QueueThreadPlanForStepInRange(SBAddress &sb_start_address,
                                            lldb::addr_t size) {
  LLDB_RECORD_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                     QueueThreadPlanForStepInRange,
                     (lldb::SBAddress &, lldb::addr_t), sb_start_address, size);

  SBError error;
  return LLDB_RECORD_RESULT(
      QueueThreadPlanForStepInRange(sb_start_address, size, error));
}

SBThreadPlan
SBThreadPlan::QueueThreadPlanForStepInRange(SBAddress &sb_start_address,
                                            lldb::addr_t size, SBError &error) {
  LLDB_RECORD_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                     QueueThreadPlanForStepInRange,
                     (lldb::SBAddress &, lldb::addr_t, lldb::SBError &),
                     sb_start_address, size, error);

  ThreadPlanSP thread_plan_sp(GetSP());
  if (thread_plan_sp) {
    Address *start_address = sb_start_address.get();
    if (!start_address) {
      return LLDB_RECORD_RESULT(SBThreadPlan());
    }

    AddressRange range(*start_address, size);
    SymbolContext sc;
    start_address->CalculateSymbolContext(&sc);

    Status plan_status;
    SBThreadPlan plan =
        SBThreadPlan(thread_plan_sp->GetThread().QueueThreadPlanForStepInRange(
            false, range, sc, nullptr, eAllThreads, plan_status));

    if (plan_status.Fail())
      error.SetErrorString(plan_status.AsCString());
    else
      plan.GetSP()->SetPrivate(true);

    return LLDB_RECORD_RESULT(plan);
  }
  return LLDB_RECORD_RESULT(SBThreadPlan());
}

SBThreadPlan
SBThreadPlan::QueueThreadPlanForStepOut(uint32_t frame_idx_to_step_to,
                                        bool first_insn) {
  LLDB_RECORD_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                     QueueThreadPlanForStepOut, (uint32_t, bool),
                     frame_idx_to_step_to, first_insn);

  SBError error;
  return LLDB_RECORD_RESULT(
      QueueThreadPlanForStepOut(frame_idx_to_step_to, first_insn, error));
}

SBThreadPlan
SBThreadPlan::QueueThreadPlanForStepOut(uint32_t frame_idx_to_step_to,
                                        bool first_insn, SBError &error) {
  LLDB_RECORD_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                     QueueThreadPlanForStepOut,
                     (uint32_t, bool, lldb::SBError &), frame_idx_to_step_to,
                     first_insn, error);

  ThreadPlanSP thread_plan_sp(GetSP());
  if (thread_plan_sp) {
    SymbolContext sc;
    sc = thread_plan_sp->GetThread().GetStackFrameAtIndex(0)->GetSymbolContext(
        lldb::eSymbolContextEverything);

    Status plan_status;
    SBThreadPlan plan =
        SBThreadPlan(thread_plan_sp->GetThread().QueueThreadPlanForStepOut(
            false, &sc, first_insn, false, eVoteYes, eVoteNoOpinion,
            frame_idx_to_step_to, plan_status));

    if (plan_status.Fail())
      error.SetErrorString(plan_status.AsCString());
    else
      plan.GetSP()->SetPrivate(true);

    return LLDB_RECORD_RESULT(plan);
  }
  return LLDB_RECORD_RESULT(SBThreadPlan());
}

SBThreadPlan
SBThreadPlan::QueueThreadPlanForRunToAddress(SBAddress sb_address) {
  LLDB_RECORD_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                     QueueThreadPlanForRunToAddress, (lldb::SBAddress),
                     sb_address);

  SBError error;
  return LLDB_RECORD_RESULT(QueueThreadPlanForRunToAddress(sb_address, error));
}

SBThreadPlan SBThreadPlan::QueueThreadPlanForRunToAddress(SBAddress sb_address,
                                                          SBError &error) {
  LLDB_RECORD_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                     QueueThreadPlanForRunToAddress,
                     (lldb::SBAddress, lldb::SBError &), sb_address, error);

  ThreadPlanSP thread_plan_sp(GetSP());
  if (thread_plan_sp) {
    Address *address = sb_address.get();
    if (!address)
      return LLDB_RECORD_RESULT(SBThreadPlan());

    Status plan_status;
    SBThreadPlan plan =
        SBThreadPlan(thread_plan_sp->GetThread().QueueThreadPlanForRunToAddress(
            false, *address, false, plan_status));

    if (plan_status.Fail())
      error.SetErrorString(plan_status.AsCString());
    else
      plan.GetSP()->SetPrivate(true);

    return LLDB_RECORD_RESULT(plan);
  }
  return LLDB_RECORD_RESULT(SBThreadPlan());
}

SBThreadPlan
SBThreadPlan::QueueThreadPlanForStepScripted(const char *script_class_name) {
  LLDB_RECORD_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                     QueueThreadPlanForStepScripted, (const char *),
                     script_class_name);

  SBError error;
  return LLDB_RECORD_RESULT(
      QueueThreadPlanForStepScripted(script_class_name, error));
}

SBThreadPlan
SBThreadPlan::QueueThreadPlanForStepScripted(const char *script_class_name,
                                             SBError &error) {
  LLDB_RECORD_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                     QueueThreadPlanForStepScripted,
                     (const char *, lldb::SBError &), script_class_name, error);

  ThreadPlanSP thread_plan_sp(GetSP());
  if (thread_plan_sp) {
    Status plan_status;
    StructuredData::ObjectSP empty_args;
    SBThreadPlan plan =
        SBThreadPlan(thread_plan_sp->GetThread().QueueThreadPlanForStepScripted(
            false, script_class_name, empty_args, false, plan_status));

    if (plan_status.Fail())
      error.SetErrorString(plan_status.AsCString());
    else
      plan.GetSP()->SetPrivate(true);

    return LLDB_RECORD_RESULT(plan);
  }
  return LLDB_RECORD_RESULT(SBThreadPlan());
}

SBThreadPlan
SBThreadPlan::QueueThreadPlanForStepScripted(const char *script_class_name,
                                             lldb::SBStructuredData &args_data,
                                             SBError &error) {
  LLDB_RECORD_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                     QueueThreadPlanForStepScripted,
                     (const char *, lldb::SBStructuredData &, lldb::SBError &), 
                     script_class_name, args_data, error);

  ThreadPlanSP thread_plan_sp(GetSP());
  if (thread_plan_sp) {
    Status plan_status;
    StructuredData::ObjectSP args_obj = args_data.m_impl_up->GetObjectSP();
    SBThreadPlan plan =
        SBThreadPlan(thread_plan_sp->GetThread().QueueThreadPlanForStepScripted(
            false, script_class_name, args_obj, false, plan_status));

    if (plan_status.Fail())
      error.SetErrorString(plan_status.AsCString());
    else
      plan.GetSP()->SetPrivate(true);

    return LLDB_RECORD_RESULT(plan);
  } else {
    return LLDB_RECORD_RESULT(SBThreadPlan());
  }
}

namespace lldb_private {
namespace repro {

template <>
void RegisterMethods<SBThreadPlan>(Registry &R) {
  LLDB_REGISTER_CONSTRUCTOR(SBThreadPlan, ());
  LLDB_REGISTER_CONSTRUCTOR(SBThreadPlan, (const lldb::ThreadPlanSP &));
  LLDB_REGISTER_CONSTRUCTOR(SBThreadPlan, (const lldb::SBThreadPlan &));
  LLDB_REGISTER_CONSTRUCTOR(SBThreadPlan, (lldb::SBThread &, const char *));
  LLDB_REGISTER_CONSTRUCTOR(SBThreadPlan, (lldb::SBThread &, const char *,
                       lldb::SBStructuredData &));
  LLDB_REGISTER_METHOD(const lldb::SBThreadPlan &,
                       SBThreadPlan, operator=,(const lldb::SBThreadPlan &));
  LLDB_REGISTER_METHOD_CONST(bool, SBThreadPlan, IsValid, ());
  LLDB_REGISTER_METHOD_CONST(bool, SBThreadPlan, operator bool, ());
  LLDB_REGISTER_METHOD(void, SBThreadPlan, Clear, ());
  LLDB_REGISTER_METHOD(lldb::StopReason, SBThreadPlan, GetStopReason, ());
  LLDB_REGISTER_METHOD(size_t, SBThreadPlan, GetStopReasonDataCount, ());
  LLDB_REGISTER_METHOD(uint64_t, SBThreadPlan, GetStopReasonDataAtIndex,
                       (uint32_t));
  LLDB_REGISTER_METHOD_CONST(lldb::SBThread, SBThreadPlan, GetThread, ());
  LLDB_REGISTER_METHOD_CONST(bool, SBThreadPlan, GetDescription,
                             (lldb::SBStream &));
  LLDB_REGISTER_METHOD(void, SBThreadPlan, SetPlanComplete, (bool));
  LLDB_REGISTER_METHOD(bool, SBThreadPlan, IsPlanComplete, ());
  LLDB_REGISTER_METHOD(bool, SBThreadPlan, IsPlanStale, ());
  LLDB_REGISTER_METHOD(bool, SBThreadPlan, IsValid, ());
  LLDB_REGISTER_METHOD(void, SBThreadPlan, SetStopOthers, (bool));
  LLDB_REGISTER_METHOD(bool, SBThreadPlan, GetStopOthers, ());
  LLDB_REGISTER_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                       QueueThreadPlanForStepOverRange,
                       (lldb::SBAddress &, lldb::addr_t));
  LLDB_REGISTER_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                       QueueThreadPlanForStepOverRange,
                       (lldb::SBAddress &, lldb::addr_t, lldb::SBError &));
  LLDB_REGISTER_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                       QueueThreadPlanForStepInRange,
                       (lldb::SBAddress &, lldb::addr_t));
  LLDB_REGISTER_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                       QueueThreadPlanForStepInRange,
                       (lldb::SBAddress &, lldb::addr_t, lldb::SBError &));
  LLDB_REGISTER_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                       QueueThreadPlanForStepOut, (uint32_t, bool));
  LLDB_REGISTER_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                       QueueThreadPlanForStepOut,
                       (uint32_t, bool, lldb::SBError &));
  LLDB_REGISTER_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                       QueueThreadPlanForRunToAddress, (lldb::SBAddress));
  LLDB_REGISTER_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                       QueueThreadPlanForRunToAddress,
                       (lldb::SBAddress, lldb::SBError &));
  LLDB_REGISTER_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                       QueueThreadPlanForStepScripted, (const char *));
  LLDB_REGISTER_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                       QueueThreadPlanForStepScripted,
                       (const char *, lldb::SBError &));
  LLDB_REGISTER_METHOD(lldb::SBThreadPlan, SBThreadPlan,
                       QueueThreadPlanForStepScripted,
                       (const char *, lldb::SBStructuredData &,
                       lldb::SBError &));
}

}
}
