//===-- SBInstructionList.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/API/SBInstructionList.h"
#include "lldb/API/SBAddress.h"
#include "lldb/API/SBExecutionContext.h"
#include "lldb/API/SBFile.h"
#include "lldb/API/SBInstruction.h"
#include "lldb/API/SBStream.h"
#include "lldb/Core/Disassembler.h"
#include "lldb/Core/Module.h"
#include "lldb/Host/StreamFile.h"
#include "lldb/Symbol/SymbolContext.h"
#include "lldb/Target/ExecutionContext.h"
#include "lldb/Utility/Instrumentation.h"
#include "lldb/Utility/Stream.h"

using namespace lldb;
using namespace lldb_private;

SBInstructionList::SBInstructionList() { LLDB_INSTRUMENT_VA(this); }

SBInstructionList::SBInstructionList(const SBInstructionList &rhs)
    : m_opaque_sp(rhs.m_opaque_sp) {
  LLDB_INSTRUMENT_VA(this, rhs);
}

const SBInstructionList &SBInstructionList::
operator=(const SBInstructionList &rhs) {
  LLDB_INSTRUMENT_VA(this, rhs);

  if (this != &rhs)
    m_opaque_sp = rhs.m_opaque_sp;
  return *this;
}

SBInstructionList::~SBInstructionList() = default;

bool SBInstructionList::IsValid() const {
  LLDB_INSTRUMENT_VA(this);
  return this->operator bool();
}
SBInstructionList::operator bool() const {
  LLDB_INSTRUMENT_VA(this);

  return m_opaque_sp.get() != nullptr;
}

size_t SBInstructionList::GetSize() {
  LLDB_INSTRUMENT_VA(this);

  if (m_opaque_sp)
    return m_opaque_sp->GetInstructionList().GetSize();
  return 0;
}

SBInstruction SBInstructionList::GetInstructionAtIndex(uint32_t idx) {
  LLDB_INSTRUMENT_VA(this, idx);

  SBInstruction inst;
  if (m_opaque_sp && idx < m_opaque_sp->GetInstructionList().GetSize())
    inst.SetOpaque(
        m_opaque_sp,
        m_opaque_sp->GetInstructionList().GetInstructionAtIndex(idx));
  return inst;
}

size_t SBInstructionList::GetInstructionsCount(const SBAddress &start,
                                               const SBAddress &end,
                                               bool canSetBreakpoint) {
  LLDB_INSTRUMENT_VA(this, start, end, canSetBreakpoint);

  size_t num_instructions = GetSize();
  size_t i = 0;
  SBAddress addr;
  size_t lower_index = 0;
  size_t upper_index = 0;
  size_t instructions_to_skip = 0;
  for (i = 0; i < num_instructions; ++i) {
    addr = GetInstructionAtIndex(i).GetAddress();
    if (start == addr)
      lower_index = i;
    if (end == addr)
      upper_index = i;
  }
  if (canSetBreakpoint)
    for (i = lower_index; i <= upper_index; ++i) {
      SBInstruction insn = GetInstructionAtIndex(i);
      if (!insn.CanSetBreakpoint())
        ++instructions_to_skip;
    }
  return upper_index - lower_index - instructions_to_skip;
}

void SBInstructionList::Clear() {
  LLDB_INSTRUMENT_VA(this);

  m_opaque_sp.reset();
}

void SBInstructionList::AppendInstruction(SBInstruction insn) {
  LLDB_INSTRUMENT_VA(this, insn);
}

void SBInstructionList::SetDisassembler(const lldb::DisassemblerSP &opaque_sp) {
  m_opaque_sp = opaque_sp;
}

void SBInstructionList::Print(FILE *out) {
  LLDB_INSTRUMENT_VA(this, out);
  if (out == nullptr)
    return;
  StreamFile stream(out, false);
  GetDescription(stream);
}

void SBInstructionList::Print(SBFile out) {
  LLDB_INSTRUMENT_VA(this, out);
  if (!out.IsValid())
    return;
  StreamFile stream(out.m_opaque_sp);
  GetDescription(stream);
}

void SBInstructionList::Print(FileSP out_sp) {
  LLDB_INSTRUMENT_VA(this, out_sp);
  if (!out_sp || !out_sp->IsValid())
    return;
  StreamFile stream(out_sp);
  GetDescription(stream);
}

bool SBInstructionList::GetDescription(lldb::SBStream &stream) {
  LLDB_INSTRUMENT_VA(this, stream);
  return GetDescription(stream.ref());
}

bool SBInstructionList::GetDescription(lldb::SBStream &stream,
                                       lldb::SBExecutionContext &exe_ctx) {
  LLDB_INSTRUMENT_VA(this, stream);
  ExecutionContext exe_ctx_wrapper(exe_ctx.get());
  return GetDescription(stream.ref(), &exe_ctx_wrapper);
}

bool SBInstructionList::GetDescription(
    Stream &sref, lldb_private::ExecutionContext *exe_ctx) {

  if (m_opaque_sp) {
    size_t num_instructions = GetSize();
    if (num_instructions) {
      // Call the ref() to make sure a stream is created if one deesn't exist
      // already inside description...
      const uint32_t max_opcode_byte_size =
          m_opaque_sp->GetInstructionList().GetMaxOpcocdeByteSize();
      FormatEntity::Entry format;
      FormatEntity::Parse("${addr-file-or-load}: ", format);
      SymbolContext sc;
      SymbolContext prev_sc;

      // Expected address of the next instruction. Used to print an empty line
      // for non-contiguous blocks of insns.
      std::optional<Address> next_addr;
      for (size_t i = 0; i < num_instructions; ++i) {
        Instruction *inst =
            m_opaque_sp->GetInstructionList().GetInstructionAtIndex(i).get();
        if (inst == nullptr)
          break;

        const Address &addr = inst->GetAddress();
        prev_sc = sc;
        ModuleSP module_sp(addr.GetModule());
        if (module_sp) {
          module_sp->ResolveSymbolContextForAddress(
              addr, eSymbolContextEverything, sc);
        }

        if (next_addr && *next_addr != addr)
          sref.EOL();
        inst->Dump(&sref, max_opcode_byte_size, true, false,
                   /*show_control_flow_kind=*/false, exe_ctx, &sc, &prev_sc,
                   &format, 0);
        sref.EOL();
        next_addr = addr;
        next_addr->Slide(inst->GetOpcode().GetByteSize());
      }
      return true;
    }
  }
  return false;
}

bool SBInstructionList::DumpEmulationForAllInstructions(const char *triple) {
  LLDB_INSTRUMENT_VA(this, triple);

  if (m_opaque_sp) {
    size_t len = GetSize();
    for (size_t i = 0; i < len; ++i) {
      if (!GetInstructionAtIndex((uint32_t)i).DumpEmulation(triple))
        return false;
    }
  }
  return true;
}
