//===-- HexagonTargetObjectFile.cpp ---------------------------------------===//
//
//                     The LLVM Compiler Infrastructure
//
// This file is distributed under the University of Illinois Open Source
// License. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
//
// This file contains the declarations of the HexagonTargetAsmInfo properties.
//
//===----------------------------------------------------------------------===//

#define DEBUG_TYPE "hexagon-sdata"

#include "HexagonTargetObjectFile.h"
#include "llvm/ADT/SmallString.h"
#include "llvm/ADT/StringRef.h"
#include "llvm/ADT/Twine.h"
#include "llvm/BinaryFormat/ELF.h"
#include "llvm/IR/DataLayout.h"
#include "llvm/IR/DerivedTypes.h"
#include "llvm/IR/GlobalObject.h"
#include "llvm/IR/GlobalValue.h"
#include "llvm/IR/GlobalVariable.h"
#include "llvm/IR/Type.h"
#include "llvm/MC/MCContext.h"
#include "llvm/MC/SectionKind.h"
#include "llvm/Support/Casting.h"
#include "llvm/Support/CommandLine.h"
#include "llvm/Support/Debug.h"
#include "llvm/Support/raw_ostream.h"
#include "llvm/Target/TargetMachine.h"

using namespace llvm;

static cl::opt<unsigned> SmallDataThreshold("hexagon-small-data-threshold",
  cl::init(8), cl::Hidden,
  cl::desc("The maximum size of an object in the sdata section"));

static cl::opt<bool> NoSmallDataSorting("mno-sort-sda", cl::init(false),
  cl::Hidden, cl::desc("Disable small data sections sorting"));

static cl::opt<bool> StaticsInSData("hexagon-statics-in-small-data",
  cl::init(false), cl::Hidden, cl::ZeroOrMore,
  cl::desc("Allow static variables in .sdata"));

static cl::opt<bool> TraceGVPlacement("trace-gv-placement",
  cl::Hidden, cl::init(false),
  cl::desc("Trace global value placement"));

static cl::opt<bool>
    EmitJtInText("hexagon-emit-jt-text", cl::Hidden, cl::init(false),
                 cl::desc("Emit hexagon jump tables in function section"));

static cl::opt<bool>
    EmitLutInText("hexagon-emit-lut-text", cl::Hidden, cl::init(false),
                 cl::desc("Emit hexagon lookup tables in function section"));

// TraceGVPlacement controls messages for all builds. For builds with assertions
// (debug or release), messages are also controlled by the usual debug flags
// (e.g. -debug and -debug-only=globallayout)
#define TRACE_TO(s, X) s << X
#ifdef NDEBUG
#define TRACE(X)                                                               \
  do {                                                                         \
    if (TraceGVPlacement) {                                                    \
      TRACE_TO(errs(), X);                                                     \
    }                                                                          \
  } while (false)
#else
#define TRACE(X)                                                               \
  do {                                                                         \
    if (TraceGVPlacement) {                                                    \
      TRACE_TO(errs(), X);                                                     \
    } else {                                                                   \
      LLVM_DEBUG(TRACE_TO(dbgs(), X));                                         \
    }                                                                          \
  } while (false)
#endif

// Returns true if the section name is such that the symbol will be put
// in a small data section.
// For instance, global variables with section attributes such as ".sdata"
// ".sdata.*", ".sbss", and ".sbss.*" will go into small data.
static bool isSmallDataSection(StringRef Sec) {
  // sectionName is either ".sdata" or ".sbss". Looking for an exact match
  // obviates the need for checks for section names such as ".sdatafoo".
  if (Sec.equals(".sdata") || Sec.equals(".sbss") || Sec.equals(".scommon"))
    return true;
  // If either ".sdata." or ".sbss." is a substring of the section name
  // then put the symbol in small data.
  return Sec.find(".sdata.") != StringRef::npos ||
         Sec.find(".sbss.") != StringRef::npos ||
         Sec.find(".scommon.") != StringRef::npos;
}

static const char *getSectionSuffixForSize(unsigned Size) {
  switch (Size) {
  default:
    return "";
  case 1:
    return ".1";
  case 2:
    return ".2";
  case 4:
    return ".4";
  case 8:
    return ".8";
  }
}

void HexagonTargetObjectFile::Initialize(MCContext &Ctx,
      const TargetMachine &TM) {
  TargetLoweringObjectFileELF::Initialize(Ctx, TM);
  InitializeELF(TM.Options.UseInitArray);

  SmallDataSection =
    getContext().getELFSection(".sdata", ELF::SHT_PROGBITS,
                               ELF::SHF_WRITE | ELF::SHF_ALLOC |
                               ELF::SHF_HEX_GPREL);
  SmallBSSSection =
    getContext().getELFSection(".sbss", ELF::SHT_NOBITS,
                               ELF::SHF_WRITE | ELF::SHF_ALLOC |
                               ELF::SHF_HEX_GPREL);
}

MCSection *HexagonTargetObjectFile::SelectSectionForGlobal(
    const GlobalObject *GO, SectionKind Kind, const TargetMachine &TM) const {
  TRACE("[SelectSectionForGlobal] GO(" << GO->getName() << ") ");
  TRACE("input section(" << GO->getSection() << ") ");

  TRACE((GO->hasPrivateLinkage() ? "private_linkage " : "")
         << (GO->hasLocalLinkage() ? "local_linkage " : "")
         << (GO->hasInternalLinkage() ? "internal " : "")
         << (GO->hasExternalLinkage() ? "external " : "")
         << (GO->hasCommonLinkage() ? "common_linkage " : "")
         << (GO->hasCommonLinkage() ? "common " : "" )
         << (Kind.isCommon() ? "kind_common " : "" )
         << (Kind.isBSS() ? "kind_bss " : "" )
         << (Kind.isBSSLocal() ? "kind_bss_local " : "" ));

  // If the lookup table is used by more than one function, do not place
  // it in text section.
  if (EmitLutInText && GO->getName().startswith("switch.table")) {
    if (const Function *Fn = getLutUsedFunction(GO))
      return selectSectionForLookupTable(GO, TM, Fn);
  }

  if (isGlobalInSmallSection(GO, TM))
    return selectSmallSectionForGlobal(GO, Kind, TM);

  if (Kind.isCommon()) {
    // This is purely for LTO+Linker Script because commons don't really have a
    // section. However, the BitcodeSectionWriter pass will query for the
    // sections of commons (and the linker expects us to know their section) so
    // we'll return one here.
    return BSSSection;
  }

  TRACE("default_ELF_section\n");
  // Otherwise, we work the same as ELF.
  return TargetLoweringObjectFileELF::SelectSectionForGlobal(GO, Kind, TM);
}

MCSection *HexagonTargetObjectFile::getExplicitSectionGlobal(
    const GlobalObject *GO, SectionKind Kind, const TargetMachine &TM) const {
  TRACE("[getExplicitSectionGlobal] GO(" << GO->getName() << ") from("
        << GO->getSection() << ") ");
  TRACE((GO->hasPrivateLinkage() ? "private_linkage " : "")
         << (GO->hasLocalLinkage() ? "local_linkage " : "")
         << (GO->hasInternalLinkage() ? "internal " : "")
         << (GO->hasExternalLinkage() ? "external " : "")
         << (GO->hasCommonLinkage() ? "common_linkage " : "")
         << (GO->hasCommonLinkage() ? "common " : "" )
         << (Kind.isCommon() ? "kind_common " : "" )
         << (Kind.isBSS() ? "kind_bss " : "" )
         << (Kind.isBSSLocal() ? "kind_bss_local " : "" ));

  if (GO->hasSection()) {
    StringRef Section = GO->getSection();
    if (Section.find(".access.text.group") != StringRef::npos)
      return getContext().getELFSection(GO->getSection(), ELF::SHT_PROGBITS,
                                        ELF::SHF_ALLOC | ELF::SHF_EXECINSTR);
    if (Section.find(".access.data.group") != StringRef::npos)
      return getContext().getELFSection(GO->getSection(), ELF::SHT_PROGBITS,
                                        ELF::SHF_WRITE | ELF::SHF_ALLOC);
  }

  if (isGlobalInSmallSection(GO, TM))
    return selectSmallSectionForGlobal(GO, Kind, TM);

  // Otherwise, we work the same as ELF.
  TRACE("default_ELF_section\n");
  return TargetLoweringObjectFileELF::getExplicitSectionGlobal(GO, Kind, TM);
}

/// Return true if this global value should be placed into small data/bss
/// section.
bool HexagonTargetObjectFile::isGlobalInSmallSection(const GlobalObject *GO,
      const TargetMachine &TM) const {
  bool HaveSData = isSmallDataEnabled(TM);
  if (!HaveSData)
    LLVM_DEBUG(dbgs() << "Small-data allocation is disabled, but symbols "
                         "may have explicit section assignments...\n");
  // Only global variables, not functions.
  LLVM_DEBUG(dbgs() << "Checking if value is in small-data, -G"
                    << SmallDataThreshold << ": \"" << GO->getName() << "\": ");
  const GlobalVariable *GVar = dyn_cast<GlobalVariable>(GO);
  if (!GVar) {
    LLVM_DEBUG(dbgs() << "no, not a global variable\n");
    return false;
  }

  // Globals with external linkage that have an original section set must be
  // emitted to that section, regardless of whether we would put them into
  // small data or not. This is how we can support mixing -G0/-G8 in LTO.
  if (GVar->hasSection()) {
    bool IsSmall = isSmallDataSection(GVar->getSection());
    LLVM_DEBUG(dbgs() << (IsSmall ? "yes" : "no")
                      << ", has section: " << GVar->getSection() << '\n');
    return IsSmall;
  }

  // If sdata is disabled, stop the checks here.
  if (!HaveSData) {
    LLVM_DEBUG(dbgs() << "no, small-data allocation is disabled\n");
    return false;
  }

  if (GVar->isConstant()) {
    LLVM_DEBUG(dbgs() << "no, is a constant\n");
    return false;
  }

  bool IsLocal = GVar->hasLocalLinkage();
  if (!StaticsInSData && IsLocal) {
    LLVM_DEBUG(dbgs() << "no, is static\n");
    return false;
  }

  Type *GType = GVar->getType();
  if (PointerType *PT = dyn_cast<PointerType>(GType))
    GType = PT->getElementType();

  if (isa<ArrayType>(GType)) {
    LLVM_DEBUG(dbgs() << "no, is an array\n");
    return false;
  }

  // If the type is a struct with no body provided, treat is conservatively.
  // There cannot be actual definitions of object of such a type in this CU
  // (only references), so assuming that they are not in sdata is safe. If
  // these objects end up in the sdata, the references will still be valid.
  if (StructType *ST = dyn_cast<StructType>(GType)) {
    if (ST->isOpaque()) {
      LLVM_DEBUG(dbgs() << "no, has opaque type\n");
      return false;
    }
  }

  unsigned Size = GVar->getParent()->getDataLayout().getTypeAllocSize(GType);
  if (Size == 0) {
    LLVM_DEBUG(dbgs() << "no, has size 0\n");
    return false;
  }
  if (Size > SmallDataThreshold) {
    LLVM_DEBUG(dbgs() << "no, size exceeds sdata threshold: " << Size << '\n');
    return false;
  }

  LLVM_DEBUG(dbgs() << "yes\n");
  return true;
}

bool HexagonTargetObjectFile::isSmallDataEnabled(const TargetMachine &TM)
    const {
  return SmallDataThreshold > 0 && !TM.isPositionIndependent();
}

unsigned HexagonTargetObjectFile::getSmallDataSize() const {
  return SmallDataThreshold;
}

bool HexagonTargetObjectFile::shouldPutJumpTableInFunctionSection(
    bool UsesLabelDifference, const Function &F) const {
  return EmitJtInText;
}

/// Descends any type down to "elementary" components,
/// discovering the smallest addressable one.
/// If zero is returned, declaration will not be modified.
unsigned HexagonTargetObjectFile::getSmallestAddressableSize(const Type *Ty,
      const GlobalValue *GV, const TargetMachine &TM) const {
  // Assign the smallest element access size to the highest
  // value which assembler can handle.
  unsigned SmallestElement = 8;

  if (!Ty)
    return 0;
  switch (Ty->getTypeID()) {
  case Type::StructTyID: {
    const StructType *STy = cast<const StructType>(Ty);
    for (auto &E : STy->elements()) {
      unsigned AtomicSize = getSmallestAddressableSize(E, GV, TM);
      if (AtomicSize < SmallestElement)
        SmallestElement = AtomicSize;
    }
    return (STy->getNumElements() == 0) ? 0 : SmallestElement;
  }
  case Type::ArrayTyID: {
    const ArrayType *ATy = cast<const ArrayType>(Ty);
    return getSmallestAddressableSize(ATy->getElementType(), GV, TM);
  }
  case Type::VectorTyID: {
    const VectorType *PTy = cast<const VectorType>(Ty);
    return getSmallestAddressableSize(PTy->getElementType(), GV, TM);
  }
  case Type::PointerTyID:
  case Type::HalfTyID:
  case Type::FloatTyID:
  case Type::DoubleTyID:
  case Type::IntegerTyID: {
    const DataLayout &DL = GV->getParent()->getDataLayout();
    // It is unfortunate that DL's function take non-const Type*.
    return DL.getTypeAllocSize(const_cast<Type*>(Ty));
  }
  case Type::FunctionTyID:
  case Type::VoidTyID:
  case Type::X86_FP80TyID:
  case Type::FP128TyID:
  case Type::PPC_FP128TyID:
  case Type::LabelTyID:
  case Type::MetadataTyID:
  case Type::X86_MMXTyID:
  case Type::TokenTyID:
    return 0;
  }

  return 0;
}

MCSection *HexagonTargetObjectFile::selectSmallSectionForGlobal(
    const GlobalObject *GO, SectionKind Kind, const TargetMachine &TM) const {
  const Type *GTy = GO->getType()->getElementType();
  unsigned Size = getSmallestAddressableSize(GTy, GO, TM);

  // If we have -ffunction-section or -fdata-section then we should emit the
  // global value to a unique section specifically for it... even for sdata.
  bool EmitUniquedSection = TM.getDataSections();

  TRACE("Small data. Size(" << Size << ")");
  // Handle Small Section classification here.
  if (Kind.isBSS() || Kind.isBSSLocal()) {
    // If -mno-sort-sda is not set, find out smallest accessible entity in
    // declaration and add it to the section name string.
    // Note. It does not track the actual usage of the value, only its de-
    // claration. Also, compiler adds explicit pad fields to some struct
    // declarations - they are currently counted towards smallest addres-
    // sable entity.
    if (NoSmallDataSorting) {
      TRACE(" default sbss\n");
      return SmallBSSSection;
    }

    StringRef Prefix(".sbss");
    SmallString<128> Name(Prefix);
    Name.append(getSectionSuffixForSize(Size));

    if (EmitUniquedSection) {
      Name.append(".");
      Name.append(GO->getName());
    }
    TRACE(" unique sbss(" << Name << ")\n");
    return getContext().getELFSection(Name.str(), ELF::SHT_NOBITS,
                ELF::SHF_WRITE | ELF::SHF_ALLOC | ELF::SHF_HEX_GPREL);
  }

  if (Kind.isCommon()) {
    // This is purely for LTO+Linker Script because commons don't really have a
    // section. However, the BitcodeSectionWriter pass will query for the
    // sections of commons (and the linker expects us to know their section) so
    // we'll return one here.
    if (NoSmallDataSorting)
      return BSSSection;

    Twine Name = Twine(".scommon") + getSectionSuffixForSize(Size);
    TRACE(" small COMMON (" << Name << ")\n");

    return getContext().getELFSection(Name.str(), ELF::SHT_NOBITS,
                                      ELF::SHF_WRITE | ELF::SHF_ALLOC |
                                      ELF::SHF_HEX_GPREL);
  }

  // We could have changed sdata object to a constant... in this
  // case the Kind could be wrong for it.
  if (Kind.isMergeableConst()) {
    TRACE(" const_object_as_data ");
    const GlobalVariable *GVar = dyn_cast<GlobalVariable>(GO);
    if (GVar->hasSection() && isSmallDataSection(GVar->getSection()))
      Kind = SectionKind::getData();
  }

  if (Kind.isData()) {
    if (NoSmallDataSorting) {
      TRACE(" default sdata\n");
      return SmallDataSection;
    }

    StringRef Prefix(".sdata");
    SmallString<128> Name(Prefix);
    Name.append(getSectionSuffixForSize(Size));

    if (EmitUniquedSection) {
      Name.append(".");
      Name.append(GO->getName());
    }
    TRACE(" unique sdata(" << Name << ")\n");
    return getContext().getELFSection(Name.str(), ELF::SHT_PROGBITS,
                ELF::SHF_WRITE | ELF::SHF_ALLOC | ELF::SHF_HEX_GPREL);
  }

  TRACE("default ELF section\n");
  // Otherwise, we work the same as ELF.
  return TargetLoweringObjectFileELF::SelectSectionForGlobal(GO, Kind, TM);
}

// Return the function that uses the lookup table. If there are more
// than one live function that uses this look table, bail out and place
// the lookup table in default section.
const Function *
HexagonTargetObjectFile::getLutUsedFunction(const GlobalObject *GO) const {
  const Function *ReturnFn = nullptr;
  for (auto U : GO->users()) {
    // validate each instance of user to be a live function.
    auto *I = dyn_cast<Instruction>(U);
    if (!I)
      continue;
    auto *Bb = I->getParent();
    if (!Bb)
      continue;
    auto *UserFn = Bb->getParent();
    if (!ReturnFn)
      ReturnFn = UserFn;
    else if (ReturnFn != UserFn)
      return nullptr;
  }
  return ReturnFn;
}

MCSection *HexagonTargetObjectFile::selectSectionForLookupTable(
    const GlobalObject *GO, const TargetMachine &TM, const Function *Fn) const {

  SectionKind Kind = SectionKind::getText();
  // If the function has explicit section, place the lookup table in this
  // explicit section.
  if (Fn->hasSection())
    return getExplicitSectionGlobal(Fn, Kind, TM);

  const auto *FuncObj = dyn_cast<GlobalObject>(Fn);
  return SelectSectionForGlobal(FuncObj, Kind, TM);
}
