brintos

brintos / llvm-project-archived public Read only

0
0
Text · 7.2 KiB · c3810d2 Raw
223 lines · cpp
1//===-- LVLine.cpp --------------------------------------------------------===//2//3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.4// See https://llvm.org/LICENSE.txt for license information.5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception6//7//===----------------------------------------------------------------------===//8//9// This implements the LVLine class.10//11//===----------------------------------------------------------------------===//12 13#include "llvm/DebugInfo/LogicalView/Core/LVLine.h"14#include "llvm/DebugInfo/LogicalView/Core/LVCompare.h"15#include "llvm/DebugInfo/LogicalView/Core/LVReader.h"16 17using namespace llvm;18using namespace llvm::logicalview;19 20#define DEBUG_TYPE "Line"21 22namespace {23const char *const KindBasicBlock = "BasicBlock";24const char *const KindDiscriminator = "Discriminator";25const char *const KindEndSequence = "EndSequence";26const char *const KindEpilogueBegin = "EpilogueBegin";27const char *const KindLineDebug = "Line";28const char *const KindLineSource = "Code";29const char *const KindNewStatement = "NewStatement";30const char *const KindPrologueEnd = "PrologueEnd";31const char *const KindUndefined = "Undefined";32const char *const KindAlwaysStepInto = "AlwaysStepInto"; // CodeView33const char *const KindNeverStepInto = "NeverStepInto";   // CodeView34} // end anonymous namespace35 36//===----------------------------------------------------------------------===//37// Logical line.38//===----------------------------------------------------------------------===//39// Return a string representation for the line kind.40const char *LVLine::kind() const {41  const char *Kind = KindUndefined;42  if (getIsLineDebug())43    Kind = KindLineDebug;44  else if (getIsLineAssembler())45    Kind = KindLineSource;46  return Kind;47}48 49LVLineDispatch LVLine::Dispatch = {50    {LVLineKind::IsBasicBlock, &LVLine::getIsBasicBlock},51    {LVLineKind::IsDiscriminator, &LVLine::getIsDiscriminator},52    {LVLineKind::IsEndSequence, &LVLine::getIsEndSequence},53    {LVLineKind::IsLineDebug, &LVLine::getIsLineDebug},54    {LVLineKind::IsLineAssembler, &LVLine::getIsLineAssembler},55    {LVLineKind::IsNewStatement, &LVLine::getIsNewStatement},56    {LVLineKind::IsEpilogueBegin, &LVLine::getIsEpilogueBegin},57    {LVLineKind::IsPrologueEnd, &LVLine::getIsPrologueEnd},58    {LVLineKind::IsAlwaysStepInto, &LVLine::getIsAlwaysStepInto},59    {LVLineKind::IsNeverStepInto, &LVLine::getIsNeverStepInto}};60 61// String used as padding for printing elements with no line number.62std::string LVLine::noLineAsString(bool ShowZero) const {63  if (options().getInternalNone())64    return LVObject::noLineAsString(ShowZero);65  return (ShowZero || options().getAttributeZero()) ? ("    0   ")66                                                    : ("    -   ");67}68 69void LVLine::markMissingParents(const LVLines *References,70                                const LVLines *Targets) {71  if (!(References && Targets))72    return;73 74  LLVM_DEBUG({75    dbgs() << "\n[LVLine::markMissingParents]\n";76    for (const LVLine *Reference : *References)77      dbgs() << "References: "78             << "Kind = " << formattedKind(Reference->kind()) << ", "79             << "Line = " << Reference->getLineNumber() << "\n";80    for (const LVLine *Target : *Targets)81      dbgs() << "Targets   : "82             << "Kind = " << formattedKind(Target->kind()) << ", "83             << "Line = " << Target->getLineNumber() << "\n";84  });85 86  for (LVLine *Reference : *References) {87    LLVM_DEBUG({88      dbgs() << "Search Reference: Line = " << Reference->getLineNumber()89             << "\n";90    });91    if (!Reference->findIn(Targets))92      Reference->markBranchAsMissing();93  }94}95 96LVLine *LVLine::findIn(const LVLines *Targets) const {97  if (!Targets)98    return nullptr;99 100  LLVM_DEBUG({101    dbgs() << "\n[LVLine::findIn]\n"102           << "Reference: "103           << "Level = " << getLevel() << ", "104           << "Kind = " << formattedKind(kind()) << ", "105           << "Line = " << getLineNumber() << "\n";106    for (const LVLine *Target : *Targets)107      dbgs() << "Target   : "108             << "Level = " << Target->getLevel() << ", "109             << "Kind = " << formattedKind(Target->kind()) << ", "110             << "Line = " << Target->getLineNumber() << "\n";111  });112 113  for (LVLine *Line : *Targets)114    if (equals(Line))115      return Line;116 117  return nullptr;118}119 120bool LVLine::equals(const LVLine *Line) const {121  return LVElement::equals(Line);122}123 124bool LVLine::equals(const LVLines *References, const LVLines *Targets) {125  if (!References && !Targets)126    return true;127  if (References && Targets && References->size() == Targets->size()) {128    for (const LVLine *Reference : *References)129      if (!Reference->findIn(Targets))130        return false;131    return true;132  }133  return false;134}135 136void LVLine::report(LVComparePass Pass) {137  getComparator().printItem(this, Pass);138}139 140void LVLine::print(raw_ostream &OS, bool Full) const {141  if (getReader().doPrintLine(this)) {142    getReaderCompileUnit()->incrementPrintedLines();143    LVElement::print(OS, Full);144    printExtra(OS, Full);145  }146}147 148//===----------------------------------------------------------------------===//149// DWARF line record.150//===----------------------------------------------------------------------===//151std::string LVLineDebug::statesInfo(bool Formatted) const {152  // Returns the DWARF extra qualifiers.153  std::string String;154  raw_string_ostream Stream(String);155 156  std::string Separator = Formatted ? " " : "";157  if (getIsNewStatement()) {158    Stream << Separator << "{" << KindNewStatement << "}";159    Separator = " ";160  }161  if (getIsDiscriminator()) {162    Stream << Separator << "{" << KindDiscriminator << "}";163    Separator = " ";164  }165  if (getIsBasicBlock()) {166    Stream << Separator << "{" << KindBasicBlock << "}";167    Separator = " ";168  }169  if (getIsEndSequence()) {170    Stream << Separator << "{" << KindEndSequence << "}";171    Separator = " ";172  }173  if (getIsEpilogueBegin()) {174    Stream << Separator << "{" << KindEpilogueBegin << "}";175    Separator = " ";176  }177  if (getIsPrologueEnd()) {178    Stream << Separator << "{" << KindPrologueEnd << "}";179    Separator = " ";180  }181  if (getIsAlwaysStepInto()) {182    Stream << Separator << "{" << KindAlwaysStepInto << "}";183    Separator = " ";184  }185  if (getIsNeverStepInto()) {186    Stream << Separator << "{" << KindNeverStepInto << "}";187    Separator = " ";188  }189 190  return String;191}192 193bool LVLineDebug::equals(const LVLine *Line) const {194  if (!LVLine::equals(Line))195    return false;196  return getFilenameIndex() == Line->getFilenameIndex();197}198 199void LVLineDebug::printExtra(raw_ostream &OS, bool Full) const {200  OS << formattedKind(kind());201 202  if (options().getAttributeQualifier()) {203    // The qualifier includes the states information and the source filename204    // that contains the line element.205    OS << statesInfo(/*Formatted=*/true);206    OS << " " << formattedName(getPathname());207  }208  OS << "\n";209}210 211//===----------------------------------------------------------------------===//212// Assembler line extracted from the ELF .text section.213//===----------------------------------------------------------------------===//214bool LVLineAssembler::equals(const LVLine *Line) const {215  return LVLine::equals(Line);216}217 218void LVLineAssembler::printExtra(raw_ostream &OS, bool Full) const {219  OS << formattedKind(kind());220  OS << " " << formattedName(getName());221  OS << "\n";222}223