//===-- TypeSummary.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/DataFormatters/TypeSummary.h"




#include "lldb/lldb-enumerations.h"
#include "lldb/lldb-public.h"

#include "lldb/Core/Debugger.h"
#include "lldb/Core/ValueObject.h"
#include "lldb/DataFormatters/ValueObjectPrinter.h"
#include "lldb/Interpreter/CommandInterpreter.h"
#include "lldb/Symbol/CompilerType.h"
#include "lldb/Target/StackFrame.h"
#include "lldb/Target/Target.h"
#include "lldb/Utility/StreamString.h"

using namespace lldb;
using namespace lldb_private;

TypeSummaryOptions::TypeSummaryOptions() = default;

lldb::LanguageType TypeSummaryOptions::GetLanguage() const { return m_lang; }

lldb::TypeSummaryCapping TypeSummaryOptions::GetCapping() const {
  return m_capping;
}

TypeSummaryOptions &TypeSummaryOptions::SetLanguage(lldb::LanguageType lang) {
  m_lang = lang;
  return *this;
}

TypeSummaryOptions &
TypeSummaryOptions::SetCapping(lldb::TypeSummaryCapping cap) {
  m_capping = cap;
  return *this;
}

TypeSummaryImpl::TypeSummaryImpl(Kind kind, const TypeSummaryImpl::Flags &flags)
    : m_flags(flags), m_kind(kind) {}

StringSummaryFormat::StringSummaryFormat(const TypeSummaryImpl::Flags &flags,
                                         const char *format_cstr)
    : TypeSummaryImpl(Kind::eSummaryString, flags), m_format_str() {
  SetSummaryString(format_cstr);
}

void StringSummaryFormat::SetSummaryString(const char *format_cstr) {
  m_format.Clear();
  if (format_cstr && format_cstr[0]) {
    m_format_str = format_cstr;
    m_error = FormatEntity::Parse(format_cstr, m_format);
  } else {
    m_format_str.clear();
    m_error.Clear();
  }
}

bool StringSummaryFormat::FormatObject(ValueObject *valobj, std::string &retval,
                                       const TypeSummaryOptions &options) {
  if (!valobj) {
    retval.assign("NULL ValueObject");
    return false;
  }

  StreamString s;
  ExecutionContext exe_ctx(valobj->GetExecutionContextRef());
  SymbolContext sc;
  StackFrame *frame = exe_ctx.GetFramePtr();
  if (frame)
    sc = frame->GetSymbolContext(lldb::eSymbolContextEverything);

  if (IsOneLiner()) {
    ValueObjectPrinter printer(valobj, &s, DumpValueObjectOptions());
    printer.PrintChildrenOneLiner(HideNames(valobj));
    retval = std::string(s.GetString());
    return true;
  } else {
    if (FormatEntity::Format(m_format, s, &sc, &exe_ctx,
                             &sc.line_entry.range.GetBaseAddress(), valobj,
                             false, false)) {
      retval.assign(std::string(s.GetString()));
      return true;
    } else {
      retval.assign("error: summary string parsing error");
      return false;
    }
  }
}

std::string StringSummaryFormat::GetDescription() {
  StreamString sstr;

  sstr.Printf("`%s`%s%s%s%s%s%s%s%s%s", m_format_str.c_str(),
              m_error.Fail() ? " error: " : "",
              m_error.Fail() ? m_error.AsCString() : "",
              Cascades() ? "" : " (not cascading)",
              !DoesPrintChildren(nullptr) ? "" : " (show children)",
              !DoesPrintValue(nullptr) ? " (hide value)" : "",
              IsOneLiner() ? " (one-line printout)" : "",
              SkipsPointers() ? " (skip pointers)" : "",
              SkipsReferences() ? " (skip references)" : "",
              HideNames(nullptr) ? " (hide member names)" : "");
  return std::string(sstr.GetString());
}

CXXFunctionSummaryFormat::CXXFunctionSummaryFormat(
    const TypeSummaryImpl::Flags &flags, Callback impl, const char *description)
    : TypeSummaryImpl(Kind::eCallback, flags), m_impl(impl),
      m_description(description ? description : "") {}

bool CXXFunctionSummaryFormat::FormatObject(ValueObject *valobj,
                                            std::string &dest,
                                            const TypeSummaryOptions &options) {
  dest.clear();
  StreamString stream;
  if (!m_impl || !m_impl(*valobj, stream, options))
    return false;
  dest = std::string(stream.GetString());
  return true;
}

std::string CXXFunctionSummaryFormat::GetDescription() {
  StreamString sstr;
  sstr.Printf("%s%s%s%s%s%s%s %s", Cascades() ? "" : " (not cascading)",
              !DoesPrintChildren(nullptr) ? "" : " (show children)",
              !DoesPrintValue(nullptr) ? " (hide value)" : "",
              IsOneLiner() ? " (one-line printout)" : "",
              SkipsPointers() ? " (skip pointers)" : "",
              SkipsReferences() ? " (skip references)" : "",
              HideNames(nullptr) ? " (hide member names)" : "",
              m_description.c_str());
  return std::string(sstr.GetString());
}

ScriptSummaryFormat::ScriptSummaryFormat(const TypeSummaryImpl::Flags &flags,
                                         const char *function_name,
                                         const char *python_script)
    : TypeSummaryImpl(Kind::eScript, flags), m_function_name(),
      m_python_script(), m_script_function_sp() {
  if (function_name)
    m_function_name.assign(function_name);
  if (python_script)
    m_python_script.assign(python_script);
}

bool ScriptSummaryFormat::FormatObject(ValueObject *valobj, std::string &retval,
                                       const TypeSummaryOptions &options) {
  if (!valobj)
    return false;

  TargetSP target_sp(valobj->GetTargetSP());

  if (!target_sp) {
    retval.assign("error: no target");
    return false;
  }

  ScriptInterpreter *script_interpreter =
      target_sp->GetDebugger().GetScriptInterpreter();

  if (!script_interpreter) {
    retval.assign("error: no ScriptInterpreter");
    return false;
  }

  return script_interpreter->GetScriptedSummary(
      m_function_name.c_str(), valobj->GetSP(), m_script_function_sp, options,
      retval);
}

std::string ScriptSummaryFormat::GetDescription() {
  StreamString sstr;
  sstr.Printf("%s%s%s%s%s%s%s\n  ", Cascades() ? "" : " (not cascading)",
              !DoesPrintChildren(nullptr) ? "" : " (show children)",
              !DoesPrintValue(nullptr) ? " (hide value)" : "",
              IsOneLiner() ? " (one-line printout)" : "",
              SkipsPointers() ? " (skip pointers)" : "",
              SkipsReferences() ? " (skip references)" : "",
              HideNames(nullptr) ? " (hide member names)" : "");
  if (m_python_script.empty()) {
    if (m_function_name.empty()) {
      sstr.PutCString("no backing script");
    } else {
      sstr.PutCString(m_function_name);
    }
  } else {
    sstr.PutCString(m_python_script);
  }
  return std::string(sstr.GetString());
}
