1db17bf38SDimitry Andric //===- llvm/lib/CodeGen/AsmPrinter/CodeViewDebug.cpp ----------------------===//
23ca95b02SDimitry Andric //
33ca95b02SDimitry Andric //                     The LLVM Compiler Infrastructure
43ca95b02SDimitry Andric //
53ca95b02SDimitry Andric // This file is distributed under the University of Illinois Open Source
63ca95b02SDimitry Andric // License. See LICENSE.TXT for details.
73ca95b02SDimitry Andric //
83ca95b02SDimitry Andric //===----------------------------------------------------------------------===//
93ca95b02SDimitry Andric //
103ca95b02SDimitry Andric // This file contains support for writing Microsoft CodeView debug info.
113ca95b02SDimitry Andric //
123ca95b02SDimitry Andric //===----------------------------------------------------------------------===//
133ca95b02SDimitry Andric 
143ca95b02SDimitry Andric #include "CodeViewDebug.h"
152cab237bSDimitry Andric #include "DwarfExpression.h"
16db17bf38SDimitry Andric #include "llvm/ADT/APSInt.h"
17db17bf38SDimitry Andric #include "llvm/ADT/ArrayRef.h"
18db17bf38SDimitry Andric #include "llvm/ADT/DenseMap.h"
19db17bf38SDimitry Andric #include "llvm/ADT/DenseSet.h"
20db17bf38SDimitry Andric #include "llvm/ADT/MapVector.h"
21db17bf38SDimitry Andric #include "llvm/ADT/None.h"
22db17bf38SDimitry Andric #include "llvm/ADT/Optional.h"
232cab237bSDimitry Andric #include "llvm/ADT/STLExtras.h"
24db17bf38SDimitry Andric #include "llvm/ADT/SmallString.h"
25db17bf38SDimitry Andric #include "llvm/ADT/SmallVector.h"
26db17bf38SDimitry Andric #include "llvm/ADT/StringRef.h"
273ca95b02SDimitry Andric #include "llvm/ADT/TinyPtrVector.h"
28db17bf38SDimitry Andric #include "llvm/ADT/Triple.h"
29db17bf38SDimitry Andric #include "llvm/ADT/Twine.h"
30db17bf38SDimitry Andric #include "llvm/BinaryFormat/COFF.h"
31db17bf38SDimitry Andric #include "llvm/BinaryFormat/Dwarf.h"
32db17bf38SDimitry Andric #include "llvm/CodeGen/AsmPrinter.h"
33db17bf38SDimitry Andric #include "llvm/CodeGen/LexicalScopes.h"
34*b5893f02SDimitry Andric #include "llvm/CodeGen/MachineFrameInfo.h"
35db17bf38SDimitry Andric #include "llvm/CodeGen/MachineFunction.h"
36db17bf38SDimitry Andric #include "llvm/CodeGen/MachineInstr.h"
37db17bf38SDimitry Andric #include "llvm/CodeGen/MachineModuleInfo.h"
38db17bf38SDimitry Andric #include "llvm/CodeGen/MachineOperand.h"
392cab237bSDimitry Andric #include "llvm/CodeGen/TargetFrameLowering.h"
402cab237bSDimitry Andric #include "llvm/CodeGen/TargetRegisterInfo.h"
412cab237bSDimitry Andric #include "llvm/CodeGen/TargetSubtargetInfo.h"
42db17bf38SDimitry Andric #include "llvm/Config/llvm-config.h"
433ca95b02SDimitry Andric #include "llvm/DebugInfo/CodeView/CVTypeVisitor.h"
443ca95b02SDimitry Andric #include "llvm/DebugInfo/CodeView/CodeView.h"
452cab237bSDimitry Andric #include "llvm/DebugInfo/CodeView/ContinuationRecordBuilder.h"
4689cb50c9SDimitry Andric #include "llvm/DebugInfo/CodeView/DebugInlineeLinesSubsection.h"
47*b5893f02SDimitry Andric #include "llvm/DebugInfo/CodeView/EnumTables.h"
483ca95b02SDimitry Andric #include "llvm/DebugInfo/CodeView/Line.h"
493ca95b02SDimitry Andric #include "llvm/DebugInfo/CodeView/SymbolRecord.h"
50f1a29dd3SDimitry Andric #include "llvm/DebugInfo/CodeView/TypeDumpVisitor.h"
513ca95b02SDimitry Andric #include "llvm/DebugInfo/CodeView/TypeIndex.h"
523ca95b02SDimitry Andric #include "llvm/DebugInfo/CodeView/TypeRecord.h"
53d8866befSDimitry Andric #include "llvm/DebugInfo/CodeView/TypeTableCollection.h"
543ca95b02SDimitry Andric #include "llvm/IR/Constants.h"
55db17bf38SDimitry Andric #include "llvm/IR/DataLayout.h"
56db17bf38SDimitry Andric #include "llvm/IR/DebugInfoMetadata.h"
57db17bf38SDimitry Andric #include "llvm/IR/DebugLoc.h"
58db17bf38SDimitry Andric #include "llvm/IR/Function.h"
59db17bf38SDimitry Andric #include "llvm/IR/GlobalValue.h"
60db17bf38SDimitry Andric #include "llvm/IR/GlobalVariable.h"
61db17bf38SDimitry Andric #include "llvm/IR/Metadata.h"
62db17bf38SDimitry Andric #include "llvm/IR/Module.h"
63d88c1a5aSDimitry Andric #include "llvm/MC/MCAsmInfo.h"
64db17bf38SDimitry Andric #include "llvm/MC/MCContext.h"
653ca95b02SDimitry Andric #include "llvm/MC/MCSectionCOFF.h"
66db17bf38SDimitry Andric #include "llvm/MC/MCStreamer.h"
673ca95b02SDimitry Andric #include "llvm/MC/MCSymbol.h"
687a7e6055SDimitry Andric #include "llvm/Support/BinaryByteStream.h"
697a7e6055SDimitry Andric #include "llvm/Support/BinaryStreamReader.h"
70db17bf38SDimitry Andric #include "llvm/Support/Casting.h"
712cab237bSDimitry Andric #include "llvm/Support/CommandLine.h"
72db17bf38SDimitry Andric #include "llvm/Support/Compiler.h"
73db17bf38SDimitry Andric #include "llvm/Support/Endian.h"
74db17bf38SDimitry Andric #include "llvm/Support/Error.h"
75db17bf38SDimitry Andric #include "llvm/Support/ErrorHandling.h"
762cab237bSDimitry Andric #include "llvm/Support/FormatVariadic.h"
77*b5893f02SDimitry Andric #include "llvm/Support/Path.h"
78db17bf38SDimitry Andric #include "llvm/Support/SMLoc.h"
792cab237bSDimitry Andric #include "llvm/Support/ScopedPrinter.h"
804ba319b5SDimitry Andric #include "llvm/Target/TargetLoweringObjectFile.h"
81db17bf38SDimitry Andric #include "llvm/Target/TargetMachine.h"
82db17bf38SDimitry Andric #include <algorithm>
83db17bf38SDimitry Andric #include <cassert>
84db17bf38SDimitry Andric #include <cctype>
85db17bf38SDimitry Andric #include <cstddef>
86db17bf38SDimitry Andric #include <cstdint>
87db17bf38SDimitry Andric #include <iterator>
88db17bf38SDimitry Andric #include <limits>
89db17bf38SDimitry Andric #include <string>
90db17bf38SDimitry Andric #include <utility>
91db17bf38SDimitry Andric #include <vector>
923ca95b02SDimitry Andric 
933ca95b02SDimitry Andric using namespace llvm;
943ca95b02SDimitry Andric using namespace llvm::codeview;
953ca95b02SDimitry Andric 
mapArchToCVCPUType(Triple::ArchType Type)96*b5893f02SDimitry Andric static CPUType mapArchToCVCPUType(Triple::ArchType Type) {
97*b5893f02SDimitry Andric   switch (Type) {
98*b5893f02SDimitry Andric   case Triple::ArchType::x86:
99*b5893f02SDimitry Andric     return CPUType::Pentium3;
100*b5893f02SDimitry Andric   case Triple::ArchType::x86_64:
101*b5893f02SDimitry Andric     return CPUType::X64;
102*b5893f02SDimitry Andric   case Triple::ArchType::thumb:
103*b5893f02SDimitry Andric     return CPUType::Thumb;
104*b5893f02SDimitry Andric   case Triple::ArchType::aarch64:
105*b5893f02SDimitry Andric     return CPUType::ARM64;
106*b5893f02SDimitry Andric   default:
107*b5893f02SDimitry Andric     report_fatal_error("target architecture doesn't map to a CodeView CPUType");
108*b5893f02SDimitry Andric   }
109*b5893f02SDimitry Andric }
1102cab237bSDimitry Andric 
CodeViewDebug(AsmPrinter * AP)1113ca95b02SDimitry Andric CodeViewDebug::CodeViewDebug(AsmPrinter *AP)
112db17bf38SDimitry Andric     : DebugHandlerBase(AP), OS(*Asm->OutStreamer), TypeTable(Allocator) {
1133ca95b02SDimitry Andric   // If module doesn't have named metadata anchors or COFF debug section
1143ca95b02SDimitry Andric   // is not available, skip any debug info related stuff.
1153ca95b02SDimitry Andric   if (!MMI->getModule()->getNamedMetadata("llvm.dbg.cu") ||
1163ca95b02SDimitry Andric       !AP->getObjFileLowering().getCOFFDebugSymbolsSection()) {
1173ca95b02SDimitry Andric     Asm = nullptr;
118*b5893f02SDimitry Andric     MMI->setDebugInfoAvailability(false);
1193ca95b02SDimitry Andric     return;
1203ca95b02SDimitry Andric   }
1213ca95b02SDimitry Andric   // Tell MMI that we have debug info.
1223ca95b02SDimitry Andric   MMI->setDebugInfoAvailability(true);
123*b5893f02SDimitry Andric 
124*b5893f02SDimitry Andric   TheCPU =
125*b5893f02SDimitry Andric       mapArchToCVCPUType(Triple(MMI->getModule()->getTargetTriple()).getArch());
126*b5893f02SDimitry Andric 
127*b5893f02SDimitry Andric   collectGlobalVariableInfo();
128*b5893f02SDimitry Andric 
129*b5893f02SDimitry Andric   // Check if we should emit type record hashes.
130*b5893f02SDimitry Andric   ConstantInt *GH = mdconst::extract_or_null<ConstantInt>(
131*b5893f02SDimitry Andric       MMI->getModule()->getModuleFlag("CodeViewGHash"));
132*b5893f02SDimitry Andric   EmitDebugGlobalHashes = GH && !GH->isZero();
1333ca95b02SDimitry Andric }
1343ca95b02SDimitry Andric 
getFullFilepath(const DIFile * File)1353ca95b02SDimitry Andric StringRef CodeViewDebug::getFullFilepath(const DIFile *File) {
1363ca95b02SDimitry Andric   std::string &Filepath = FileToFilepathMap[File];
1373ca95b02SDimitry Andric   if (!Filepath.empty())
1383ca95b02SDimitry Andric     return Filepath;
1393ca95b02SDimitry Andric 
1403ca95b02SDimitry Andric   StringRef Dir = File->getDirectory(), Filename = File->getFilename();
1413ca95b02SDimitry Andric 
1424ba319b5SDimitry Andric   // If this is a Unix-style path, just use it as is. Don't try to canonicalize
1434ba319b5SDimitry Andric   // it textually because one of the path components could be a symlink.
144*b5893f02SDimitry Andric   if (Dir.startswith("/") || Filename.startswith("/")) {
145*b5893f02SDimitry Andric     if (llvm::sys::path::is_absolute(Filename, llvm::sys::path::Style::posix))
146*b5893f02SDimitry Andric       return Filename;
1474ba319b5SDimitry Andric     Filepath = Dir;
1484ba319b5SDimitry Andric     if (Dir.back() != '/')
1494ba319b5SDimitry Andric       Filepath += '/';
1504ba319b5SDimitry Andric     Filepath += Filename;
1514ba319b5SDimitry Andric     return Filepath;
1524ba319b5SDimitry Andric   }
1534ba319b5SDimitry Andric 
1543ca95b02SDimitry Andric   // Clang emits directory and relative filename info into the IR, but CodeView
1553ca95b02SDimitry Andric   // operates on full paths.  We could change Clang to emit full paths too, but
1563ca95b02SDimitry Andric   // that would increase the IR size and probably not needed for other users.
1573ca95b02SDimitry Andric   // For now, just concatenate and canonicalize the path here.
1583ca95b02SDimitry Andric   if (Filename.find(':') == 1)
1593ca95b02SDimitry Andric     Filepath = Filename;
1603ca95b02SDimitry Andric   else
1613ca95b02SDimitry Andric     Filepath = (Dir + "\\" + Filename).str();
1623ca95b02SDimitry Andric 
1633ca95b02SDimitry Andric   // Canonicalize the path.  We have to do it textually because we may no longer
1643ca95b02SDimitry Andric   // have access the file in the filesystem.
1653ca95b02SDimitry Andric   // First, replace all slashes with backslashes.
1663ca95b02SDimitry Andric   std::replace(Filepath.begin(), Filepath.end(), '/', '\\');
1673ca95b02SDimitry Andric 
1683ca95b02SDimitry Andric   // Remove all "\.\" with "\".
1693ca95b02SDimitry Andric   size_t Cursor = 0;
1703ca95b02SDimitry Andric   while ((Cursor = Filepath.find("\\.\\", Cursor)) != std::string::npos)
1713ca95b02SDimitry Andric     Filepath.erase(Cursor, 2);
1723ca95b02SDimitry Andric 
1733ca95b02SDimitry Andric   // Replace all "\XXX\..\" with "\".  Don't try too hard though as the original
1743ca95b02SDimitry Andric   // path should be well-formatted, e.g. start with a drive letter, etc.
1753ca95b02SDimitry Andric   Cursor = 0;
1763ca95b02SDimitry Andric   while ((Cursor = Filepath.find("\\..\\", Cursor)) != std::string::npos) {
1773ca95b02SDimitry Andric     // Something's wrong if the path starts with "\..\", abort.
1783ca95b02SDimitry Andric     if (Cursor == 0)
1793ca95b02SDimitry Andric       break;
1803ca95b02SDimitry Andric 
1813ca95b02SDimitry Andric     size_t PrevSlash = Filepath.rfind('\\', Cursor - 1);
1823ca95b02SDimitry Andric     if (PrevSlash == std::string::npos)
1833ca95b02SDimitry Andric       // Something's wrong, abort.
1843ca95b02SDimitry Andric       break;
1853ca95b02SDimitry Andric 
1863ca95b02SDimitry Andric     Filepath.erase(PrevSlash, Cursor + 3 - PrevSlash);
1873ca95b02SDimitry Andric     // The next ".." might be following the one we've just erased.
1883ca95b02SDimitry Andric     Cursor = PrevSlash;
1893ca95b02SDimitry Andric   }
1903ca95b02SDimitry Andric 
1913ca95b02SDimitry Andric   // Remove all duplicate backslashes.
1923ca95b02SDimitry Andric   Cursor = 0;
1933ca95b02SDimitry Andric   while ((Cursor = Filepath.find("\\\\", Cursor)) != std::string::npos)
1943ca95b02SDimitry Andric     Filepath.erase(Cursor, 1);
1953ca95b02SDimitry Andric 
1963ca95b02SDimitry Andric   return Filepath;
1973ca95b02SDimitry Andric }
1983ca95b02SDimitry Andric 
maybeRecordFile(const DIFile * F)1993ca95b02SDimitry Andric unsigned CodeViewDebug::maybeRecordFile(const DIFile *F) {
2002cab237bSDimitry Andric   StringRef FullPath = getFullFilepath(F);
2013ca95b02SDimitry Andric   unsigned NextId = FileIdMap.size() + 1;
2022cab237bSDimitry Andric   auto Insertion = FileIdMap.insert(std::make_pair(FullPath, NextId));
2033ca95b02SDimitry Andric   if (Insertion.second) {
2043ca95b02SDimitry Andric     // We have to compute the full filepath and emit a .cv_file directive.
2054ba319b5SDimitry Andric     ArrayRef<uint8_t> ChecksumAsBytes;
2064ba319b5SDimitry Andric     FileChecksumKind CSKind = FileChecksumKind::None;
2074ba319b5SDimitry Andric     if (F->getChecksum()) {
2084ba319b5SDimitry Andric       std::string Checksum = fromHex(F->getChecksum()->Value);
2092cab237bSDimitry Andric       void *CKMem = OS.getContext().allocate(Checksum.size(), 1);
2102cab237bSDimitry Andric       memcpy(CKMem, Checksum.data(), Checksum.size());
2114ba319b5SDimitry Andric       ChecksumAsBytes = ArrayRef<uint8_t>(
2124ba319b5SDimitry Andric           reinterpret_cast<const uint8_t *>(CKMem), Checksum.size());
2134ba319b5SDimitry Andric       switch (F->getChecksum()->Kind) {
2144ba319b5SDimitry Andric       case DIFile::CSK_MD5:  CSKind = FileChecksumKind::MD5; break;
2154ba319b5SDimitry Andric       case DIFile::CSK_SHA1: CSKind = FileChecksumKind::SHA1; break;
2164ba319b5SDimitry Andric       }
2174ba319b5SDimitry Andric     }
2182cab237bSDimitry Andric     bool Success = OS.EmitCVFileDirective(NextId, FullPath, ChecksumAsBytes,
2194ba319b5SDimitry Andric                                           static_cast<unsigned>(CSKind));
220d88c1a5aSDimitry Andric     (void)Success;
221d88c1a5aSDimitry Andric     assert(Success && ".cv_file directive failed");
2223ca95b02SDimitry Andric   }
2233ca95b02SDimitry Andric   return Insertion.first->second;
2243ca95b02SDimitry Andric }
2253ca95b02SDimitry Andric 
2263ca95b02SDimitry Andric CodeViewDebug::InlineSite &
getInlineSite(const DILocation * InlinedAt,const DISubprogram * Inlinee)2273ca95b02SDimitry Andric CodeViewDebug::getInlineSite(const DILocation *InlinedAt,
2283ca95b02SDimitry Andric                              const DISubprogram *Inlinee) {
2293ca95b02SDimitry Andric   auto SiteInsertion = CurFn->InlineSites.insert({InlinedAt, InlineSite()});
2303ca95b02SDimitry Andric   InlineSite *Site = &SiteInsertion.first->second;
2313ca95b02SDimitry Andric   if (SiteInsertion.second) {
232d88c1a5aSDimitry Andric     unsigned ParentFuncId = CurFn->FuncId;
233d88c1a5aSDimitry Andric     if (const DILocation *OuterIA = InlinedAt->getInlinedAt())
234d88c1a5aSDimitry Andric       ParentFuncId =
235d88c1a5aSDimitry Andric           getInlineSite(OuterIA, InlinedAt->getScope()->getSubprogram())
236d88c1a5aSDimitry Andric               .SiteFuncId;
237d88c1a5aSDimitry Andric 
2383ca95b02SDimitry Andric     Site->SiteFuncId = NextFuncId++;
239d88c1a5aSDimitry Andric     OS.EmitCVInlineSiteIdDirective(
240d88c1a5aSDimitry Andric         Site->SiteFuncId, ParentFuncId, maybeRecordFile(InlinedAt->getFile()),
241d88c1a5aSDimitry Andric         InlinedAt->getLine(), InlinedAt->getColumn(), SMLoc());
2423ca95b02SDimitry Andric     Site->Inlinee = Inlinee;
2433ca95b02SDimitry Andric     InlinedSubprograms.insert(Inlinee);
2443ca95b02SDimitry Andric     getFuncIdForSubprogram(Inlinee);
2453ca95b02SDimitry Andric   }
2463ca95b02SDimitry Andric   return *Site;
2473ca95b02SDimitry Andric }
2483ca95b02SDimitry Andric 
getPrettyScopeName(const DIScope * Scope)2493ca95b02SDimitry Andric static StringRef getPrettyScopeName(const DIScope *Scope) {
2503ca95b02SDimitry Andric   StringRef ScopeName = Scope->getName();
2513ca95b02SDimitry Andric   if (!ScopeName.empty())
2523ca95b02SDimitry Andric     return ScopeName;
2533ca95b02SDimitry Andric 
2543ca95b02SDimitry Andric   switch (Scope->getTag()) {
2553ca95b02SDimitry Andric   case dwarf::DW_TAG_enumeration_type:
2563ca95b02SDimitry Andric   case dwarf::DW_TAG_class_type:
2573ca95b02SDimitry Andric   case dwarf::DW_TAG_structure_type:
2583ca95b02SDimitry Andric   case dwarf::DW_TAG_union_type:
2593ca95b02SDimitry Andric     return "<unnamed-tag>";
2603ca95b02SDimitry Andric   case dwarf::DW_TAG_namespace:
2613ca95b02SDimitry Andric     return "`anonymous namespace'";
2623ca95b02SDimitry Andric   }
2633ca95b02SDimitry Andric 
2643ca95b02SDimitry Andric   return StringRef();
2653ca95b02SDimitry Andric }
2663ca95b02SDimitry Andric 
getQualifiedNameComponents(const DIScope * Scope,SmallVectorImpl<StringRef> & QualifiedNameComponents)2673ca95b02SDimitry Andric static const DISubprogram *getQualifiedNameComponents(
2683ca95b02SDimitry Andric     const DIScope *Scope, SmallVectorImpl<StringRef> &QualifiedNameComponents) {
2693ca95b02SDimitry Andric   const DISubprogram *ClosestSubprogram = nullptr;
2703ca95b02SDimitry Andric   while (Scope != nullptr) {
2713ca95b02SDimitry Andric     if (ClosestSubprogram == nullptr)
2723ca95b02SDimitry Andric       ClosestSubprogram = dyn_cast<DISubprogram>(Scope);
2733ca95b02SDimitry Andric     StringRef ScopeName = getPrettyScopeName(Scope);
2743ca95b02SDimitry Andric     if (!ScopeName.empty())
2753ca95b02SDimitry Andric       QualifiedNameComponents.push_back(ScopeName);
2763ca95b02SDimitry Andric     Scope = Scope->getScope().resolve();
2773ca95b02SDimitry Andric   }
2783ca95b02SDimitry Andric   return ClosestSubprogram;
2793ca95b02SDimitry Andric }
2803ca95b02SDimitry Andric 
getQualifiedName(ArrayRef<StringRef> QualifiedNameComponents,StringRef TypeName)2813ca95b02SDimitry Andric static std::string getQualifiedName(ArrayRef<StringRef> QualifiedNameComponents,
2823ca95b02SDimitry Andric                                     StringRef TypeName) {
2833ca95b02SDimitry Andric   std::string FullyQualifiedName;
284db17bf38SDimitry Andric   for (StringRef QualifiedNameComponent :
285db17bf38SDimitry Andric        llvm::reverse(QualifiedNameComponents)) {
2863ca95b02SDimitry Andric     FullyQualifiedName.append(QualifiedNameComponent);
2873ca95b02SDimitry Andric     FullyQualifiedName.append("::");
2883ca95b02SDimitry Andric   }
2893ca95b02SDimitry Andric   FullyQualifiedName.append(TypeName);
2903ca95b02SDimitry Andric   return FullyQualifiedName;
2913ca95b02SDimitry Andric }
2923ca95b02SDimitry Andric 
getFullyQualifiedName(const DIScope * Scope,StringRef Name)2933ca95b02SDimitry Andric static std::string getFullyQualifiedName(const DIScope *Scope, StringRef Name) {
2943ca95b02SDimitry Andric   SmallVector<StringRef, 5> QualifiedNameComponents;
2953ca95b02SDimitry Andric   getQualifiedNameComponents(Scope, QualifiedNameComponents);
2963ca95b02SDimitry Andric   return getQualifiedName(QualifiedNameComponents, Name);
2973ca95b02SDimitry Andric }
2983ca95b02SDimitry Andric 
2993ca95b02SDimitry Andric struct CodeViewDebug::TypeLoweringScope {
TypeLoweringScopeCodeViewDebug::TypeLoweringScope3003ca95b02SDimitry Andric   TypeLoweringScope(CodeViewDebug &CVD) : CVD(CVD) { ++CVD.TypeEmissionLevel; }
~TypeLoweringScopeCodeViewDebug::TypeLoweringScope3013ca95b02SDimitry Andric   ~TypeLoweringScope() {
3023ca95b02SDimitry Andric     // Don't decrement TypeEmissionLevel until after emitting deferred types, so
3033ca95b02SDimitry Andric     // inner TypeLoweringScopes don't attempt to emit deferred types.
3043ca95b02SDimitry Andric     if (CVD.TypeEmissionLevel == 1)
3053ca95b02SDimitry Andric       CVD.emitDeferredCompleteTypes();
3063ca95b02SDimitry Andric     --CVD.TypeEmissionLevel;
3073ca95b02SDimitry Andric   }
3083ca95b02SDimitry Andric   CodeViewDebug &CVD;
3093ca95b02SDimitry Andric };
3103ca95b02SDimitry Andric 
getFullyQualifiedName(const DIScope * Ty)3113ca95b02SDimitry Andric static std::string getFullyQualifiedName(const DIScope *Ty) {
3123ca95b02SDimitry Andric   const DIScope *Scope = Ty->getScope().resolve();
3133ca95b02SDimitry Andric   return getFullyQualifiedName(Scope, getPrettyScopeName(Ty));
3143ca95b02SDimitry Andric }
3153ca95b02SDimitry Andric 
getScopeIndex(const DIScope * Scope)3163ca95b02SDimitry Andric TypeIndex CodeViewDebug::getScopeIndex(const DIScope *Scope) {
3173ca95b02SDimitry Andric   // No scope means global scope and that uses the zero index.
3183ca95b02SDimitry Andric   if (!Scope || isa<DIFile>(Scope))
3193ca95b02SDimitry Andric     return TypeIndex();
3203ca95b02SDimitry Andric 
3213ca95b02SDimitry Andric   assert(!isa<DIType>(Scope) && "shouldn't make a namespace scope for a type");
3223ca95b02SDimitry Andric 
3233ca95b02SDimitry Andric   // Check if we've already translated this scope.
3243ca95b02SDimitry Andric   auto I = TypeIndices.find({Scope, nullptr});
3253ca95b02SDimitry Andric   if (I != TypeIndices.end())
3263ca95b02SDimitry Andric     return I->second;
3273ca95b02SDimitry Andric 
3283ca95b02SDimitry Andric   // Build the fully qualified name of the scope.
3293ca95b02SDimitry Andric   std::string ScopeName = getFullyQualifiedName(Scope);
330d88c1a5aSDimitry Andric   StringIdRecord SID(TypeIndex(), ScopeName);
3312cab237bSDimitry Andric   auto TI = TypeTable.writeLeafType(SID);
3323ca95b02SDimitry Andric   return recordTypeIndexForDINode(Scope, TI);
3333ca95b02SDimitry Andric }
3343ca95b02SDimitry Andric 
getFuncIdForSubprogram(const DISubprogram * SP)3353ca95b02SDimitry Andric TypeIndex CodeViewDebug::getFuncIdForSubprogram(const DISubprogram *SP) {
3366c4bc1bdSDimitry Andric   assert(SP);
3373ca95b02SDimitry Andric 
3383ca95b02SDimitry Andric   // Check if we've already translated this subprogram.
3393ca95b02SDimitry Andric   auto I = TypeIndices.find({SP, nullptr});
3403ca95b02SDimitry Andric   if (I != TypeIndices.end())
3413ca95b02SDimitry Andric     return I->second;
3423ca95b02SDimitry Andric 
3433ca95b02SDimitry Andric   // The display name includes function template arguments. Drop them to match
3443ca95b02SDimitry Andric   // MSVC.
345f37b6182SDimitry Andric   StringRef DisplayName = SP->getName().split('<').first;
3463ca95b02SDimitry Andric 
3473ca95b02SDimitry Andric   const DIScope *Scope = SP->getScope().resolve();
3483ca95b02SDimitry Andric   TypeIndex TI;
3493ca95b02SDimitry Andric   if (const auto *Class = dyn_cast_or_null<DICompositeType>(Scope)) {
3503ca95b02SDimitry Andric     // If the scope is a DICompositeType, then this must be a method. Member
3513ca95b02SDimitry Andric     // function types take some special handling, and require access to the
3523ca95b02SDimitry Andric     // subprogram.
3533ca95b02SDimitry Andric     TypeIndex ClassType = getTypeIndex(Class);
3543ca95b02SDimitry Andric     MemberFuncIdRecord MFuncId(ClassType, getMemberFunctionType(SP, Class),
3553ca95b02SDimitry Andric                                DisplayName);
3562cab237bSDimitry Andric     TI = TypeTable.writeLeafType(MFuncId);
3573ca95b02SDimitry Andric   } else {
3583ca95b02SDimitry Andric     // Otherwise, this must be a free function.
3593ca95b02SDimitry Andric     TypeIndex ParentScope = getScopeIndex(Scope);
3603ca95b02SDimitry Andric     FuncIdRecord FuncId(ParentScope, getTypeIndex(SP->getType()), DisplayName);
3612cab237bSDimitry Andric     TI = TypeTable.writeLeafType(FuncId);
3623ca95b02SDimitry Andric   }
3633ca95b02SDimitry Andric 
3643ca95b02SDimitry Andric   return recordTypeIndexForDINode(SP, TI);
3653ca95b02SDimitry Andric }
3663ca95b02SDimitry Andric 
isTrivial(const DICompositeType * DCTy)367*b5893f02SDimitry Andric static bool isTrivial(const DICompositeType *DCTy) {
368*b5893f02SDimitry Andric   return ((DCTy->getFlags() & DINode::FlagTrivial) == DINode::FlagTrivial);
369*b5893f02SDimitry Andric }
370*b5893f02SDimitry Andric 
371*b5893f02SDimitry Andric static FunctionOptions
getFunctionOptions(const DISubroutineType * Ty,const DICompositeType * ClassTy=nullptr,StringRef SPName=StringRef (""))372*b5893f02SDimitry Andric getFunctionOptions(const DISubroutineType *Ty,
373*b5893f02SDimitry Andric                    const DICompositeType *ClassTy = nullptr,
374*b5893f02SDimitry Andric                    StringRef SPName = StringRef("")) {
375*b5893f02SDimitry Andric   FunctionOptions FO = FunctionOptions::None;
376*b5893f02SDimitry Andric   const DIType *ReturnTy = nullptr;
377*b5893f02SDimitry Andric   if (auto TypeArray = Ty->getTypeArray()) {
378*b5893f02SDimitry Andric     if (TypeArray.size())
379*b5893f02SDimitry Andric       ReturnTy = TypeArray[0].resolve();
380*b5893f02SDimitry Andric   }
381*b5893f02SDimitry Andric 
382*b5893f02SDimitry Andric   if (auto *ReturnDCTy = dyn_cast_or_null<DICompositeType>(ReturnTy)) {
383*b5893f02SDimitry Andric     if (!isTrivial(ReturnDCTy))
384*b5893f02SDimitry Andric       FO |= FunctionOptions::CxxReturnUdt;
385*b5893f02SDimitry Andric   }
386*b5893f02SDimitry Andric 
387*b5893f02SDimitry Andric   // DISubroutineType is unnamed. Use DISubprogram's i.e. SPName in comparison.
388*b5893f02SDimitry Andric   if (ClassTy && !isTrivial(ClassTy) && SPName == ClassTy->getName()) {
389*b5893f02SDimitry Andric     FO |= FunctionOptions::Constructor;
390*b5893f02SDimitry Andric 
391*b5893f02SDimitry Andric   // TODO: put the FunctionOptions::ConstructorWithVirtualBases flag.
392*b5893f02SDimitry Andric 
393*b5893f02SDimitry Andric   }
394*b5893f02SDimitry Andric   return FO;
395*b5893f02SDimitry Andric }
396*b5893f02SDimitry Andric 
getMemberFunctionType(const DISubprogram * SP,const DICompositeType * Class)3973ca95b02SDimitry Andric TypeIndex CodeViewDebug::getMemberFunctionType(const DISubprogram *SP,
3983ca95b02SDimitry Andric                                                const DICompositeType *Class) {
3993ca95b02SDimitry Andric   // Always use the method declaration as the key for the function type. The
4003ca95b02SDimitry Andric   // method declaration contains the this adjustment.
4013ca95b02SDimitry Andric   if (SP->getDeclaration())
4023ca95b02SDimitry Andric     SP = SP->getDeclaration();
4033ca95b02SDimitry Andric   assert(!SP->getDeclaration() && "should use declaration as key");
4043ca95b02SDimitry Andric 
4053ca95b02SDimitry Andric   // Key the MemberFunctionRecord into the map as {SP, Class}. It won't collide
4063ca95b02SDimitry Andric   // with the MemberFuncIdRecord, which is keyed in as {SP, nullptr}.
4073ca95b02SDimitry Andric   auto I = TypeIndices.find({SP, Class});
4083ca95b02SDimitry Andric   if (I != TypeIndices.end())
4093ca95b02SDimitry Andric     return I->second;
4103ca95b02SDimitry Andric 
4113ca95b02SDimitry Andric   // Make sure complete type info for the class is emitted *after* the member
4123ca95b02SDimitry Andric   // function type, as the complete class type is likely to reference this
4133ca95b02SDimitry Andric   // member function type.
4143ca95b02SDimitry Andric   TypeLoweringScope S(*this);
4152cab237bSDimitry Andric   const bool IsStaticMethod = (SP->getFlags() & DINode::FlagStaticMember) != 0;
416*b5893f02SDimitry Andric 
417*b5893f02SDimitry Andric   FunctionOptions FO = getFunctionOptions(SP->getType(), Class, SP->getName());
4182cab237bSDimitry Andric   TypeIndex TI = lowerTypeMemberFunction(
419*b5893f02SDimitry Andric       SP->getType(), Class, SP->getThisAdjustment(), IsStaticMethod, FO);
4203ca95b02SDimitry Andric   return recordTypeIndexForDINode(SP, TI, Class);
4213ca95b02SDimitry Andric }
4223ca95b02SDimitry Andric 
recordTypeIndexForDINode(const DINode * Node,TypeIndex TI,const DIType * ClassTy)4233ca95b02SDimitry Andric TypeIndex CodeViewDebug::recordTypeIndexForDINode(const DINode *Node,
4243ca95b02SDimitry Andric                                                   TypeIndex TI,
4253ca95b02SDimitry Andric                                                   const DIType *ClassTy) {
4263ca95b02SDimitry Andric   auto InsertResult = TypeIndices.insert({{Node, ClassTy}, TI});
4273ca95b02SDimitry Andric   (void)InsertResult;
4283ca95b02SDimitry Andric   assert(InsertResult.second && "DINode was already assigned a type index");
4293ca95b02SDimitry Andric   return TI;
4303ca95b02SDimitry Andric }
4313ca95b02SDimitry Andric 
getPointerSizeInBytes()4323ca95b02SDimitry Andric unsigned CodeViewDebug::getPointerSizeInBytes() {
4333ca95b02SDimitry Andric   return MMI->getModule()->getDataLayout().getPointerSizeInBits() / 8;
4343ca95b02SDimitry Andric }
4353ca95b02SDimitry Andric 
recordLocalVariable(LocalVariable && Var,const LexicalScope * LS)4363ca95b02SDimitry Andric void CodeViewDebug::recordLocalVariable(LocalVariable &&Var,
4374ba319b5SDimitry Andric                                         const LexicalScope *LS) {
4384ba319b5SDimitry Andric   if (const DILocation *InlinedAt = LS->getInlinedAt()) {
4393ca95b02SDimitry Andric     // This variable was inlined. Associate it with the InlineSite.
4403ca95b02SDimitry Andric     const DISubprogram *Inlinee = Var.DIVar->getScope()->getSubprogram();
4413ca95b02SDimitry Andric     InlineSite &Site = getInlineSite(InlinedAt, Inlinee);
4423ca95b02SDimitry Andric     Site.InlinedLocals.emplace_back(Var);
4433ca95b02SDimitry Andric   } else {
4444ba319b5SDimitry Andric     // This variable goes into the corresponding lexical scope.
4454ba319b5SDimitry Andric     ScopeVariables[LS].emplace_back(Var);
4463ca95b02SDimitry Andric   }
4473ca95b02SDimitry Andric }
4483ca95b02SDimitry Andric 
addLocIfNotPresent(SmallVectorImpl<const DILocation * > & Locs,const DILocation * Loc)4493ca95b02SDimitry Andric static void addLocIfNotPresent(SmallVectorImpl<const DILocation *> &Locs,
4503ca95b02SDimitry Andric                                const DILocation *Loc) {
4513ca95b02SDimitry Andric   auto B = Locs.begin(), E = Locs.end();
4523ca95b02SDimitry Andric   if (std::find(B, E, Loc) == E)
4533ca95b02SDimitry Andric     Locs.push_back(Loc);
4543ca95b02SDimitry Andric }
4553ca95b02SDimitry Andric 
maybeRecordLocation(const DebugLoc & DL,const MachineFunction * MF)4563ca95b02SDimitry Andric void CodeViewDebug::maybeRecordLocation(const DebugLoc &DL,
4573ca95b02SDimitry Andric                                         const MachineFunction *MF) {
4583ca95b02SDimitry Andric   // Skip this instruction if it has the same location as the previous one.
459a580b014SDimitry Andric   if (!DL || DL == PrevInstLoc)
4603ca95b02SDimitry Andric     return;
4613ca95b02SDimitry Andric 
4623ca95b02SDimitry Andric   const DIScope *Scope = DL.get()->getScope();
4633ca95b02SDimitry Andric   if (!Scope)
4643ca95b02SDimitry Andric     return;
4653ca95b02SDimitry Andric 
4663ca95b02SDimitry Andric   // Skip this line if it is longer than the maximum we can record.
4673ca95b02SDimitry Andric   LineInfo LI(DL.getLine(), DL.getLine(), /*IsStatement=*/true);
4683ca95b02SDimitry Andric   if (LI.getStartLine() != DL.getLine() || LI.isAlwaysStepInto() ||
4693ca95b02SDimitry Andric       LI.isNeverStepInto())
4703ca95b02SDimitry Andric     return;
4713ca95b02SDimitry Andric 
4723ca95b02SDimitry Andric   ColumnInfo CI(DL.getCol(), /*EndColumn=*/0);
4733ca95b02SDimitry Andric   if (CI.getStartColumn() != DL.getCol())
4743ca95b02SDimitry Andric     return;
4753ca95b02SDimitry Andric 
4763ca95b02SDimitry Andric   if (!CurFn->HaveLineInfo)
4773ca95b02SDimitry Andric     CurFn->HaveLineInfo = true;
4783ca95b02SDimitry Andric   unsigned FileId = 0;
479a580b014SDimitry Andric   if (PrevInstLoc.get() && PrevInstLoc->getFile() == DL->getFile())
4803ca95b02SDimitry Andric     FileId = CurFn->LastFileId;
4813ca95b02SDimitry Andric   else
4823ca95b02SDimitry Andric     FileId = CurFn->LastFileId = maybeRecordFile(DL->getFile());
483a580b014SDimitry Andric   PrevInstLoc = DL;
4843ca95b02SDimitry Andric 
4853ca95b02SDimitry Andric   unsigned FuncId = CurFn->FuncId;
4863ca95b02SDimitry Andric   if (const DILocation *SiteLoc = DL->getInlinedAt()) {
4873ca95b02SDimitry Andric     const DILocation *Loc = DL.get();
4883ca95b02SDimitry Andric 
4893ca95b02SDimitry Andric     // If this location was actually inlined from somewhere else, give it the ID
4903ca95b02SDimitry Andric     // of the inline call site.
4913ca95b02SDimitry Andric     FuncId =
4923ca95b02SDimitry Andric         getInlineSite(SiteLoc, Loc->getScope()->getSubprogram()).SiteFuncId;
4933ca95b02SDimitry Andric 
4943ca95b02SDimitry Andric     // Ensure we have links in the tree of inline call sites.
4953ca95b02SDimitry Andric     bool FirstLoc = true;
4963ca95b02SDimitry Andric     while ((SiteLoc = Loc->getInlinedAt())) {
4973ca95b02SDimitry Andric       InlineSite &Site =
4983ca95b02SDimitry Andric           getInlineSite(SiteLoc, Loc->getScope()->getSubprogram());
4993ca95b02SDimitry Andric       if (!FirstLoc)
5003ca95b02SDimitry Andric         addLocIfNotPresent(Site.ChildSites, Loc);
5013ca95b02SDimitry Andric       FirstLoc = false;
5023ca95b02SDimitry Andric       Loc = SiteLoc;
5033ca95b02SDimitry Andric     }
5043ca95b02SDimitry Andric     addLocIfNotPresent(CurFn->ChildSites, Loc);
5053ca95b02SDimitry Andric   }
5063ca95b02SDimitry Andric 
5073ca95b02SDimitry Andric   OS.EmitCVLocDirective(FuncId, FileId, DL.getLine(), DL.getCol(),
508d88c1a5aSDimitry Andric                         /*PrologueEnd=*/false, /*IsStmt=*/false,
509d88c1a5aSDimitry Andric                         DL->getFilename(), SMLoc());
5103ca95b02SDimitry Andric }
5113ca95b02SDimitry Andric 
emitCodeViewMagicVersion()5123ca95b02SDimitry Andric void CodeViewDebug::emitCodeViewMagicVersion() {
5133ca95b02SDimitry Andric   OS.EmitValueToAlignment(4);
5143ca95b02SDimitry Andric   OS.AddComment("Debug section magic");
5153ca95b02SDimitry Andric   OS.EmitIntValue(COFF::DEBUG_SECTION_MAGIC, 4);
5163ca95b02SDimitry Andric }
5173ca95b02SDimitry Andric 
endModule()5183ca95b02SDimitry Andric void CodeViewDebug::endModule() {
5193ca95b02SDimitry Andric   if (!Asm || !MMI->hasDebugInfo())
5203ca95b02SDimitry Andric     return;
5213ca95b02SDimitry Andric 
5223ca95b02SDimitry Andric   assert(Asm != nullptr);
5233ca95b02SDimitry Andric 
5243ca95b02SDimitry Andric   // The COFF .debug$S section consists of several subsections, each starting
5253ca95b02SDimitry Andric   // with a 4-byte control code (e.g. 0xF1, 0xF2, etc) and then a 4-byte length
5263ca95b02SDimitry Andric   // of the payload followed by the payload itself.  The subsections are 4-byte
5273ca95b02SDimitry Andric   // aligned.
5283ca95b02SDimitry Andric 
5293ca95b02SDimitry Andric   // Use the generic .debug$S section, and make a subsection for all the inlined
5303ca95b02SDimitry Andric   // subprograms.
5313ca95b02SDimitry Andric   switchToDebugSectionForSymbol(nullptr);
532d88c1a5aSDimitry Andric 
53389cb50c9SDimitry Andric   MCSymbol *CompilerInfo = beginCVSubsection(DebugSubsectionKind::Symbols);
534d88c1a5aSDimitry Andric   emitCompilerInformation();
535d88c1a5aSDimitry Andric   endCVSubsection(CompilerInfo);
536d88c1a5aSDimitry Andric 
5373ca95b02SDimitry Andric   emitInlineeLinesSubsection();
5383ca95b02SDimitry Andric 
5393ca95b02SDimitry Andric   // Emit per-function debug information.
5403ca95b02SDimitry Andric   for (auto &P : FnDebugInfo)
5413ca95b02SDimitry Andric     if (!P.first->isDeclarationForLinker())
5424ba319b5SDimitry Andric       emitDebugInfoForFunction(P.first, *P.second);
5433ca95b02SDimitry Andric 
5443ca95b02SDimitry Andric   // Emit global variable debug information.
5453ca95b02SDimitry Andric   setCurrentSubprogram(nullptr);
5463ca95b02SDimitry Andric   emitDebugInfoForGlobals();
5473ca95b02SDimitry Andric 
5483ca95b02SDimitry Andric   // Emit retained types.
5493ca95b02SDimitry Andric   emitDebugInfoForRetainedTypes();
5503ca95b02SDimitry Andric 
5513ca95b02SDimitry Andric   // Switch back to the generic .debug$S section after potentially processing
5523ca95b02SDimitry Andric   // comdat symbol sections.
5533ca95b02SDimitry Andric   switchToDebugSectionForSymbol(nullptr);
5543ca95b02SDimitry Andric 
5553ca95b02SDimitry Andric   // Emit UDT records for any types used by global variables.
5563ca95b02SDimitry Andric   if (!GlobalUDTs.empty()) {
55789cb50c9SDimitry Andric     MCSymbol *SymbolsEnd = beginCVSubsection(DebugSubsectionKind::Symbols);
5583ca95b02SDimitry Andric     emitDebugInfoForUDTs(GlobalUDTs);
5593ca95b02SDimitry Andric     endCVSubsection(SymbolsEnd);
5603ca95b02SDimitry Andric   }
5613ca95b02SDimitry Andric 
5623ca95b02SDimitry Andric   // This subsection holds a file index to offset in string table table.
5633ca95b02SDimitry Andric   OS.AddComment("File index to string table offset subsection");
5643ca95b02SDimitry Andric   OS.EmitCVFileChecksumsDirective();
5653ca95b02SDimitry Andric 
5663ca95b02SDimitry Andric   // This subsection holds the string table.
5673ca95b02SDimitry Andric   OS.AddComment("String table");
5683ca95b02SDimitry Andric   OS.EmitCVStringTableDirective();
5693ca95b02SDimitry Andric 
570*b5893f02SDimitry Andric   // Emit S_BUILDINFO, which points to LF_BUILDINFO. Put this in its own symbol
571*b5893f02SDimitry Andric   // subsection in the generic .debug$S section at the end. There is no
572*b5893f02SDimitry Andric   // particular reason for this ordering other than to match MSVC.
573*b5893f02SDimitry Andric   emitBuildInfo();
574*b5893f02SDimitry Andric 
5752cab237bSDimitry Andric   // Emit type information and hashes last, so that any types we translate while
5762cab237bSDimitry Andric   // emitting function info are included.
5773ca95b02SDimitry Andric   emitTypeInformation();
5783ca95b02SDimitry Andric 
5792cab237bSDimitry Andric   if (EmitDebugGlobalHashes)
5802cab237bSDimitry Andric     emitTypeGlobalHashes();
5812cab237bSDimitry Andric 
5823ca95b02SDimitry Andric   clear();
5833ca95b02SDimitry Andric }
5843ca95b02SDimitry Andric 
emitNullTerminatedSymbolName(MCStreamer & OS,StringRef S,unsigned MaxFixedRecordLength=0xF00)5854ba319b5SDimitry Andric static void emitNullTerminatedSymbolName(MCStreamer &OS, StringRef S,
5864ba319b5SDimitry Andric     unsigned MaxFixedRecordLength = 0xF00) {
587d88c1a5aSDimitry Andric   // The maximum CV record length is 0xFF00. Most of the strings we emit appear
588d88c1a5aSDimitry Andric   // after a fixed length portion of the record. The fixed length portion should
589d88c1a5aSDimitry Andric   // always be less than 0xF00 (3840) bytes, so truncate the string so that the
590d88c1a5aSDimitry Andric   // overall record size is less than the maximum allowed.
591d88c1a5aSDimitry Andric   SmallString<32> NullTerminatedString(
592d88c1a5aSDimitry Andric       S.take_front(MaxRecordLength - MaxFixedRecordLength - 1));
5933ca95b02SDimitry Andric   NullTerminatedString.push_back('\0');
5943ca95b02SDimitry Andric   OS.EmitBytes(NullTerminatedString);
5953ca95b02SDimitry Andric }
5963ca95b02SDimitry Andric 
emitTypeInformation()5973ca95b02SDimitry Andric void CodeViewDebug::emitTypeInformation() {
5983ca95b02SDimitry Andric   if (TypeTable.empty())
5993ca95b02SDimitry Andric     return;
6003ca95b02SDimitry Andric 
6014ba319b5SDimitry Andric   // Start the .debug$T or .debug$P section with 0x4.
6023ca95b02SDimitry Andric   OS.SwitchSection(Asm->getObjFileLowering().getCOFFDebugTypesSection());
6033ca95b02SDimitry Andric   emitCodeViewMagicVersion();
6043ca95b02SDimitry Andric 
6053ca95b02SDimitry Andric   SmallString<8> CommentPrefix;
6063ca95b02SDimitry Andric   if (OS.isVerboseAsm()) {
6073ca95b02SDimitry Andric     CommentPrefix += '\t';
6083ca95b02SDimitry Andric     CommentPrefix += Asm->MAI->getCommentString();
6093ca95b02SDimitry Andric     CommentPrefix += ' ';
6103ca95b02SDimitry Andric   }
6113ca95b02SDimitry Andric 
612d8866befSDimitry Andric   TypeTableCollection Table(TypeTable.records());
613d8866befSDimitry Andric   Optional<TypeIndex> B = Table.getFirst();
614d8866befSDimitry Andric   while (B) {
615d8866befSDimitry Andric     // This will fail if the record data is invalid.
616d8866befSDimitry Andric     CVType Record = Table.getType(*B);
617d8866befSDimitry Andric 
6183ca95b02SDimitry Andric     if (OS.isVerboseAsm()) {
6193ca95b02SDimitry Andric       // Emit a block comment describing the type record for readability.
6203ca95b02SDimitry Andric       SmallString<512> CommentBlock;
6213ca95b02SDimitry Andric       raw_svector_ostream CommentOS(CommentBlock);
6223ca95b02SDimitry Andric       ScopedPrinter SP(CommentOS);
6233ca95b02SDimitry Andric       SP.setPrefix(CommentPrefix);
624d8866befSDimitry Andric       TypeDumpVisitor TDV(Table, &SP, false);
625d8866befSDimitry Andric 
626d8866befSDimitry Andric       Error E = codeview::visitTypeRecord(Record, *B, TDV);
6273ca95b02SDimitry Andric       if (E) {
6283ca95b02SDimitry Andric         logAllUnhandledErrors(std::move(E), errs(), "error: ");
6293ca95b02SDimitry Andric         llvm_unreachable("produced malformed type record");
6303ca95b02SDimitry Andric       }
6313ca95b02SDimitry Andric       // emitRawComment will insert its own tab and comment string before
6323ca95b02SDimitry Andric       // the first line, so strip off our first one. It also prints its own
6333ca95b02SDimitry Andric       // newline.
6343ca95b02SDimitry Andric       OS.emitRawComment(
6353ca95b02SDimitry Andric           CommentOS.str().drop_front(CommentPrefix.size() - 1).rtrim());
6363ca95b02SDimitry Andric     }
637d8866befSDimitry Andric     OS.EmitBinaryData(Record.str_data());
638d8866befSDimitry Andric     B = Table.getNext(*B);
6393ca95b02SDimitry Andric   }
6403ca95b02SDimitry Andric }
6413ca95b02SDimitry Andric 
emitTypeGlobalHashes()6422cab237bSDimitry Andric void CodeViewDebug::emitTypeGlobalHashes() {
6432cab237bSDimitry Andric   if (TypeTable.empty())
6442cab237bSDimitry Andric     return;
6452cab237bSDimitry Andric 
6462cab237bSDimitry Andric   // Start the .debug$H section with the version and hash algorithm, currently
6472cab237bSDimitry Andric   // hardcoded to version 0, SHA1.
6482cab237bSDimitry Andric   OS.SwitchSection(Asm->getObjFileLowering().getCOFFGlobalTypeHashesSection());
6492cab237bSDimitry Andric 
6502cab237bSDimitry Andric   OS.EmitValueToAlignment(4);
6512cab237bSDimitry Andric   OS.AddComment("Magic");
6522cab237bSDimitry Andric   OS.EmitIntValue(COFF::DEBUG_HASHES_SECTION_MAGIC, 4);
6532cab237bSDimitry Andric   OS.AddComment("Section Version");
6542cab237bSDimitry Andric   OS.EmitIntValue(0, 2);
6552cab237bSDimitry Andric   OS.AddComment("Hash Algorithm");
6564ba319b5SDimitry Andric   OS.EmitIntValue(uint16_t(GlobalTypeHashAlg::SHA1_8), 2);
6572cab237bSDimitry Andric 
6582cab237bSDimitry Andric   TypeIndex TI(TypeIndex::FirstNonSimpleIndex);
6592cab237bSDimitry Andric   for (const auto &GHR : TypeTable.hashes()) {
6602cab237bSDimitry Andric     if (OS.isVerboseAsm()) {
6612cab237bSDimitry Andric       // Emit an EOL-comment describing which TypeIndex this hash corresponds
6622cab237bSDimitry Andric       // to, as well as the stringified SHA1 hash.
6632cab237bSDimitry Andric       SmallString<32> Comment;
6642cab237bSDimitry Andric       raw_svector_ostream CommentOS(Comment);
6652cab237bSDimitry Andric       CommentOS << formatv("{0:X+} [{1}]", TI.getIndex(), GHR);
6662cab237bSDimitry Andric       OS.AddComment(Comment);
6672cab237bSDimitry Andric       ++TI;
6682cab237bSDimitry Andric     }
6694ba319b5SDimitry Andric     assert(GHR.Hash.size() == 8);
6702cab237bSDimitry Andric     StringRef S(reinterpret_cast<const char *>(GHR.Hash.data()),
6712cab237bSDimitry Andric                 GHR.Hash.size());
6722cab237bSDimitry Andric     OS.EmitBinaryData(S);
6732cab237bSDimitry Andric   }
6742cab237bSDimitry Andric }
675d88c1a5aSDimitry Andric 
MapDWLangToCVLang(unsigned DWLang)676d88c1a5aSDimitry Andric static SourceLanguage MapDWLangToCVLang(unsigned DWLang) {
677d88c1a5aSDimitry Andric   switch (DWLang) {
678d88c1a5aSDimitry Andric   case dwarf::DW_LANG_C:
679d88c1a5aSDimitry Andric   case dwarf::DW_LANG_C89:
680d88c1a5aSDimitry Andric   case dwarf::DW_LANG_C99:
681d88c1a5aSDimitry Andric   case dwarf::DW_LANG_C11:
682d88c1a5aSDimitry Andric   case dwarf::DW_LANG_ObjC:
683d88c1a5aSDimitry Andric     return SourceLanguage::C;
684d88c1a5aSDimitry Andric   case dwarf::DW_LANG_C_plus_plus:
685d88c1a5aSDimitry Andric   case dwarf::DW_LANG_C_plus_plus_03:
686d88c1a5aSDimitry Andric   case dwarf::DW_LANG_C_plus_plus_11:
687d88c1a5aSDimitry Andric   case dwarf::DW_LANG_C_plus_plus_14:
688d88c1a5aSDimitry Andric     return SourceLanguage::Cpp;
689d88c1a5aSDimitry Andric   case dwarf::DW_LANG_Fortran77:
690d88c1a5aSDimitry Andric   case dwarf::DW_LANG_Fortran90:
691d88c1a5aSDimitry Andric   case dwarf::DW_LANG_Fortran03:
692d88c1a5aSDimitry Andric   case dwarf::DW_LANG_Fortran08:
693d88c1a5aSDimitry Andric     return SourceLanguage::Fortran;
694d88c1a5aSDimitry Andric   case dwarf::DW_LANG_Pascal83:
695d88c1a5aSDimitry Andric     return SourceLanguage::Pascal;
696d88c1a5aSDimitry Andric   case dwarf::DW_LANG_Cobol74:
697d88c1a5aSDimitry Andric   case dwarf::DW_LANG_Cobol85:
698d88c1a5aSDimitry Andric     return SourceLanguage::Cobol;
699d88c1a5aSDimitry Andric   case dwarf::DW_LANG_Java:
700d88c1a5aSDimitry Andric     return SourceLanguage::Java;
7012cab237bSDimitry Andric   case dwarf::DW_LANG_D:
7022cab237bSDimitry Andric     return SourceLanguage::D;
703d88c1a5aSDimitry Andric   default:
704d88c1a5aSDimitry Andric     // There's no CodeView representation for this language, and CV doesn't
705d88c1a5aSDimitry Andric     // have an "unknown" option for the language field, so we'll use MASM,
706d88c1a5aSDimitry Andric     // as it's very low level.
707d88c1a5aSDimitry Andric     return SourceLanguage::Masm;
708d88c1a5aSDimitry Andric   }
709d88c1a5aSDimitry Andric }
710d88c1a5aSDimitry Andric 
7112cab237bSDimitry Andric namespace {
712d88c1a5aSDimitry Andric struct Version {
713d88c1a5aSDimitry Andric   int Part[4];
714d88c1a5aSDimitry Andric };
7152cab237bSDimitry Andric } // end anonymous namespace
716d88c1a5aSDimitry Andric 
717d88c1a5aSDimitry Andric // Takes a StringRef like "clang 4.0.0.0 (other nonsense 123)" and parses out
718d88c1a5aSDimitry Andric // the version number.
parseVersion(StringRef Name)719d88c1a5aSDimitry Andric static Version parseVersion(StringRef Name) {
720d88c1a5aSDimitry Andric   Version V = {{0}};
721d88c1a5aSDimitry Andric   int N = 0;
722d88c1a5aSDimitry Andric   for (const char C : Name) {
723d88c1a5aSDimitry Andric     if (isdigit(C)) {
724d88c1a5aSDimitry Andric       V.Part[N] *= 10;
725d88c1a5aSDimitry Andric       V.Part[N] += C - '0';
726d88c1a5aSDimitry Andric     } else if (C == '.') {
727d88c1a5aSDimitry Andric       ++N;
728d88c1a5aSDimitry Andric       if (N >= 4)
729d88c1a5aSDimitry Andric         return V;
730d88c1a5aSDimitry Andric     } else if (N > 0)
731d88c1a5aSDimitry Andric       return V;
732d88c1a5aSDimitry Andric   }
733d88c1a5aSDimitry Andric   return V;
734d88c1a5aSDimitry Andric }
735d88c1a5aSDimitry Andric 
emitCompilerInformation()736d88c1a5aSDimitry Andric void CodeViewDebug::emitCompilerInformation() {
737*b5893f02SDimitry Andric   MCSymbol *CompilerEnd = beginSymbolRecord(SymbolKind::S_COMPILE3);
738d88c1a5aSDimitry Andric   uint32_t Flags = 0;
739d88c1a5aSDimitry Andric 
740d88c1a5aSDimitry Andric   NamedMDNode *CUs = MMI->getModule()->getNamedMetadata("llvm.dbg.cu");
741d88c1a5aSDimitry Andric   const MDNode *Node = *CUs->operands().begin();
742d88c1a5aSDimitry Andric   const auto *CU = cast<DICompileUnit>(Node);
743d88c1a5aSDimitry Andric 
744d88c1a5aSDimitry Andric   // The low byte of the flags indicates the source language.
745d88c1a5aSDimitry Andric   Flags = MapDWLangToCVLang(CU->getSourceLanguage());
746d88c1a5aSDimitry Andric   // TODO:  Figure out which other flags need to be set.
747d88c1a5aSDimitry Andric 
748d88c1a5aSDimitry Andric   OS.AddComment("Flags and language");
749d88c1a5aSDimitry Andric   OS.EmitIntValue(Flags, 4);
750d88c1a5aSDimitry Andric 
751d88c1a5aSDimitry Andric   OS.AddComment("CPUType");
752*b5893f02SDimitry Andric   OS.EmitIntValue(static_cast<uint64_t>(TheCPU), 2);
753d88c1a5aSDimitry Andric 
754d88c1a5aSDimitry Andric   StringRef CompilerVersion = CU->getProducer();
755d88c1a5aSDimitry Andric   Version FrontVer = parseVersion(CompilerVersion);
756d88c1a5aSDimitry Andric   OS.AddComment("Frontend version");
757d88c1a5aSDimitry Andric   for (int N = 0; N < 4; ++N)
758d88c1a5aSDimitry Andric     OS.EmitIntValue(FrontVer.Part[N], 2);
759d88c1a5aSDimitry Andric 
760d88c1a5aSDimitry Andric   // Some Microsoft tools, like Binscope, expect a backend version number of at
761d88c1a5aSDimitry Andric   // least 8.something, so we'll coerce the LLVM version into a form that
762d88c1a5aSDimitry Andric   // guarantees it'll be big enough without really lying about the version.
763d88c1a5aSDimitry Andric   int Major = 1000 * LLVM_VERSION_MAJOR +
764d88c1a5aSDimitry Andric               10 * LLVM_VERSION_MINOR +
765d88c1a5aSDimitry Andric               LLVM_VERSION_PATCH;
766d88c1a5aSDimitry Andric   // Clamp it for builds that use unusually large version numbers.
767d88c1a5aSDimitry Andric   Major = std::min<int>(Major, std::numeric_limits<uint16_t>::max());
768d88c1a5aSDimitry Andric   Version BackVer = {{ Major, 0, 0, 0 }};
769d88c1a5aSDimitry Andric   OS.AddComment("Backend version");
770d88c1a5aSDimitry Andric   for (int N = 0; N < 4; ++N)
771d88c1a5aSDimitry Andric     OS.EmitIntValue(BackVer.Part[N], 2);
772d88c1a5aSDimitry Andric 
773d88c1a5aSDimitry Andric   OS.AddComment("Null-terminated compiler version string");
774d88c1a5aSDimitry Andric   emitNullTerminatedSymbolName(OS, CompilerVersion);
775d88c1a5aSDimitry Andric 
776*b5893f02SDimitry Andric   endSymbolRecord(CompilerEnd);
777*b5893f02SDimitry Andric }
778*b5893f02SDimitry Andric 
getStringIdTypeIdx(GlobalTypeTableBuilder & TypeTable,StringRef S)779*b5893f02SDimitry Andric static TypeIndex getStringIdTypeIdx(GlobalTypeTableBuilder &TypeTable,
780*b5893f02SDimitry Andric                                     StringRef S) {
781*b5893f02SDimitry Andric   StringIdRecord SIR(TypeIndex(0x0), S);
782*b5893f02SDimitry Andric   return TypeTable.writeLeafType(SIR);
783*b5893f02SDimitry Andric }
784*b5893f02SDimitry Andric 
emitBuildInfo()785*b5893f02SDimitry Andric void CodeViewDebug::emitBuildInfo() {
786*b5893f02SDimitry Andric   // First, make LF_BUILDINFO. It's a sequence of strings with various bits of
787*b5893f02SDimitry Andric   // build info. The known prefix is:
788*b5893f02SDimitry Andric   // - Absolute path of current directory
789*b5893f02SDimitry Andric   // - Compiler path
790*b5893f02SDimitry Andric   // - Main source file path, relative to CWD or absolute
791*b5893f02SDimitry Andric   // - Type server PDB file
792*b5893f02SDimitry Andric   // - Canonical compiler command line
793*b5893f02SDimitry Andric   // If frontend and backend compilation are separated (think llc or LTO), it's
794*b5893f02SDimitry Andric   // not clear if the compiler path should refer to the executable for the
795*b5893f02SDimitry Andric   // frontend or the backend. Leave it blank for now.
796*b5893f02SDimitry Andric   TypeIndex BuildInfoArgs[BuildInfoRecord::MaxArgs] = {};
797*b5893f02SDimitry Andric   NamedMDNode *CUs = MMI->getModule()->getNamedMetadata("llvm.dbg.cu");
798*b5893f02SDimitry Andric   const MDNode *Node = *CUs->operands().begin(); // FIXME: Multiple CUs.
799*b5893f02SDimitry Andric   const auto *CU = cast<DICompileUnit>(Node);
800*b5893f02SDimitry Andric   const DIFile *MainSourceFile = CU->getFile();
801*b5893f02SDimitry Andric   BuildInfoArgs[BuildInfoRecord::CurrentDirectory] =
802*b5893f02SDimitry Andric       getStringIdTypeIdx(TypeTable, MainSourceFile->getDirectory());
803*b5893f02SDimitry Andric   BuildInfoArgs[BuildInfoRecord::SourceFile] =
804*b5893f02SDimitry Andric       getStringIdTypeIdx(TypeTable, MainSourceFile->getFilename());
805*b5893f02SDimitry Andric   // FIXME: Path to compiler and command line. PDB is intentionally blank unless
806*b5893f02SDimitry Andric   // we implement /Zi type servers.
807*b5893f02SDimitry Andric   BuildInfoRecord BIR(BuildInfoArgs);
808*b5893f02SDimitry Andric   TypeIndex BuildInfoIndex = TypeTable.writeLeafType(BIR);
809*b5893f02SDimitry Andric 
810*b5893f02SDimitry Andric   // Make a new .debug$S subsection for the S_BUILDINFO record, which points
811*b5893f02SDimitry Andric   // from the module symbols into the type stream.
812*b5893f02SDimitry Andric   MCSymbol *BISubsecEnd = beginCVSubsection(DebugSubsectionKind::Symbols);
813*b5893f02SDimitry Andric   MCSymbol *BIEnd = beginSymbolRecord(SymbolKind::S_BUILDINFO);
814*b5893f02SDimitry Andric   OS.AddComment("LF_BUILDINFO index");
815*b5893f02SDimitry Andric   OS.EmitIntValue(BuildInfoIndex.getIndex(), 4);
816*b5893f02SDimitry Andric   endSymbolRecord(BIEnd);
817*b5893f02SDimitry Andric   endCVSubsection(BISubsecEnd);
818d88c1a5aSDimitry Andric }
819d88c1a5aSDimitry Andric 
emitInlineeLinesSubsection()8203ca95b02SDimitry Andric void CodeViewDebug::emitInlineeLinesSubsection() {
8213ca95b02SDimitry Andric   if (InlinedSubprograms.empty())
8223ca95b02SDimitry Andric     return;
8233ca95b02SDimitry Andric 
8243ca95b02SDimitry Andric   OS.AddComment("Inlinee lines subsection");
82589cb50c9SDimitry Andric   MCSymbol *InlineEnd = beginCVSubsection(DebugSubsectionKind::InlineeLines);
8263ca95b02SDimitry Andric 
8272cab237bSDimitry Andric   // We emit the checksum info for files.  This is used by debuggers to
8282cab237bSDimitry Andric   // determine if a pdb matches the source before loading it.  Visual Studio,
8292cab237bSDimitry Andric   // for instance, will display a warning that the breakpoints are not valid if
8302cab237bSDimitry Andric   // the pdb does not match the source.
8313ca95b02SDimitry Andric   OS.AddComment("Inlinee lines signature");
8323ca95b02SDimitry Andric   OS.EmitIntValue(unsigned(InlineeLinesSignature::Normal), 4);
8333ca95b02SDimitry Andric 
8343ca95b02SDimitry Andric   for (const DISubprogram *SP : InlinedSubprograms) {
8353ca95b02SDimitry Andric     assert(TypeIndices.count({SP, nullptr}));
8363ca95b02SDimitry Andric     TypeIndex InlineeIdx = TypeIndices[{SP, nullptr}];
8373ca95b02SDimitry Andric 
8383ca95b02SDimitry Andric     OS.AddBlankLine();
8393ca95b02SDimitry Andric     unsigned FileId = maybeRecordFile(SP->getFile());
840f37b6182SDimitry Andric     OS.AddComment("Inlined function " + SP->getName() + " starts at " +
8413ca95b02SDimitry Andric                   SP->getFilename() + Twine(':') + Twine(SP->getLine()));
8423ca95b02SDimitry Andric     OS.AddBlankLine();
8433ca95b02SDimitry Andric     OS.AddComment("Type index of inlined function");
8443ca95b02SDimitry Andric     OS.EmitIntValue(InlineeIdx.getIndex(), 4);
8453ca95b02SDimitry Andric     OS.AddComment("Offset into filechecksum table");
8462cab237bSDimitry Andric     OS.EmitCVFileChecksumOffsetDirective(FileId);
8473ca95b02SDimitry Andric     OS.AddComment("Starting line number");
8483ca95b02SDimitry Andric     OS.EmitIntValue(SP->getLine(), 4);
8493ca95b02SDimitry Andric   }
8503ca95b02SDimitry Andric 
8513ca95b02SDimitry Andric   endCVSubsection(InlineEnd);
8523ca95b02SDimitry Andric }
8533ca95b02SDimitry Andric 
emitInlinedCallSite(const FunctionInfo & FI,const DILocation * InlinedAt,const InlineSite & Site)8543ca95b02SDimitry Andric void CodeViewDebug::emitInlinedCallSite(const FunctionInfo &FI,
8553ca95b02SDimitry Andric                                         const DILocation *InlinedAt,
8563ca95b02SDimitry Andric                                         const InlineSite &Site) {
8573ca95b02SDimitry Andric   assert(TypeIndices.count({Site.Inlinee, nullptr}));
8583ca95b02SDimitry Andric   TypeIndex InlineeIdx = TypeIndices[{Site.Inlinee, nullptr}];
8593ca95b02SDimitry Andric 
8603ca95b02SDimitry Andric   // SymbolRecord
861*b5893f02SDimitry Andric   MCSymbol *InlineEnd = beginSymbolRecord(SymbolKind::S_INLINESITE);
8623ca95b02SDimitry Andric 
8633ca95b02SDimitry Andric   OS.AddComment("PtrParent");
8643ca95b02SDimitry Andric   OS.EmitIntValue(0, 4);
8653ca95b02SDimitry Andric   OS.AddComment("PtrEnd");
8663ca95b02SDimitry Andric   OS.EmitIntValue(0, 4);
8673ca95b02SDimitry Andric   OS.AddComment("Inlinee type index");
8683ca95b02SDimitry Andric   OS.EmitIntValue(InlineeIdx.getIndex(), 4);
8693ca95b02SDimitry Andric 
8703ca95b02SDimitry Andric   unsigned FileId = maybeRecordFile(Site.Inlinee->getFile());
8713ca95b02SDimitry Andric   unsigned StartLineNum = Site.Inlinee->getLine();
8723ca95b02SDimitry Andric 
8733ca95b02SDimitry Andric   OS.EmitCVInlineLinetableDirective(Site.SiteFuncId, FileId, StartLineNum,
874d88c1a5aSDimitry Andric                                     FI.Begin, FI.End);
8753ca95b02SDimitry Andric 
876*b5893f02SDimitry Andric   endSymbolRecord(InlineEnd);
8773ca95b02SDimitry Andric 
878*b5893f02SDimitry Andric   emitLocalVariableList(FI, Site.InlinedLocals);
8793ca95b02SDimitry Andric 
8803ca95b02SDimitry Andric   // Recurse on child inlined call sites before closing the scope.
8813ca95b02SDimitry Andric   for (const DILocation *ChildSite : Site.ChildSites) {
8823ca95b02SDimitry Andric     auto I = FI.InlineSites.find(ChildSite);
8833ca95b02SDimitry Andric     assert(I != FI.InlineSites.end() &&
8843ca95b02SDimitry Andric            "child site not in function inline site map");
8853ca95b02SDimitry Andric     emitInlinedCallSite(FI, ChildSite, I->second);
8863ca95b02SDimitry Andric   }
8873ca95b02SDimitry Andric 
8883ca95b02SDimitry Andric   // Close the scope.
889*b5893f02SDimitry Andric   emitEndSymbolRecord(SymbolKind::S_INLINESITE_END);
8903ca95b02SDimitry Andric }
8913ca95b02SDimitry Andric 
switchToDebugSectionForSymbol(const MCSymbol * GVSym)8923ca95b02SDimitry Andric void CodeViewDebug::switchToDebugSectionForSymbol(const MCSymbol *GVSym) {
8933ca95b02SDimitry Andric   // If we have a symbol, it may be in a section that is COMDAT. If so, find the
8943ca95b02SDimitry Andric   // comdat key. A section may be comdat because of -ffunction-sections or
8953ca95b02SDimitry Andric   // because it is comdat in the IR.
8963ca95b02SDimitry Andric   MCSectionCOFF *GVSec =
8973ca95b02SDimitry Andric       GVSym ? dyn_cast<MCSectionCOFF>(&GVSym->getSection()) : nullptr;
8983ca95b02SDimitry Andric   const MCSymbol *KeySym = GVSec ? GVSec->getCOMDATSymbol() : nullptr;
8993ca95b02SDimitry Andric 
9003ca95b02SDimitry Andric   MCSectionCOFF *DebugSec = cast<MCSectionCOFF>(
9013ca95b02SDimitry Andric       Asm->getObjFileLowering().getCOFFDebugSymbolsSection());
9023ca95b02SDimitry Andric   DebugSec = OS.getContext().getAssociativeCOFFSection(DebugSec, KeySym);
9033ca95b02SDimitry Andric 
9043ca95b02SDimitry Andric   OS.SwitchSection(DebugSec);
9053ca95b02SDimitry Andric 
9063ca95b02SDimitry Andric   // Emit the magic version number if this is the first time we've switched to
9073ca95b02SDimitry Andric   // this section.
9083ca95b02SDimitry Andric   if (ComdatDebugSections.insert(DebugSec).second)
9093ca95b02SDimitry Andric     emitCodeViewMagicVersion();
9103ca95b02SDimitry Andric }
9113ca95b02SDimitry Andric 
9124ba319b5SDimitry Andric // Emit an S_THUNK32/S_END symbol pair for a thunk routine.
9134ba319b5SDimitry Andric // The only supported thunk ordinal is currently the standard type.
emitDebugInfoForThunk(const Function * GV,FunctionInfo & FI,const MCSymbol * Fn)9144ba319b5SDimitry Andric void CodeViewDebug::emitDebugInfoForThunk(const Function *GV,
9154ba319b5SDimitry Andric                                           FunctionInfo &FI,
9164ba319b5SDimitry Andric                                           const MCSymbol *Fn) {
9174ba319b5SDimitry Andric   std::string FuncName = GlobalValue::dropLLVMManglingEscape(GV->getName());
9184ba319b5SDimitry Andric   const ThunkOrdinal ordinal = ThunkOrdinal::Standard; // Only supported kind.
9194ba319b5SDimitry Andric 
9204ba319b5SDimitry Andric   OS.AddComment("Symbol subsection for " + Twine(FuncName));
9214ba319b5SDimitry Andric   MCSymbol *SymbolsEnd = beginCVSubsection(DebugSubsectionKind::Symbols);
9224ba319b5SDimitry Andric 
9234ba319b5SDimitry Andric   // Emit S_THUNK32
924*b5893f02SDimitry Andric   MCSymbol *ThunkRecordEnd = beginSymbolRecord(SymbolKind::S_THUNK32);
9254ba319b5SDimitry Andric   OS.AddComment("PtrParent");
9264ba319b5SDimitry Andric   OS.EmitIntValue(0, 4);
9274ba319b5SDimitry Andric   OS.AddComment("PtrEnd");
9284ba319b5SDimitry Andric   OS.EmitIntValue(0, 4);
9294ba319b5SDimitry Andric   OS.AddComment("PtrNext");
9304ba319b5SDimitry Andric   OS.EmitIntValue(0, 4);
9314ba319b5SDimitry Andric   OS.AddComment("Thunk section relative address");
9324ba319b5SDimitry Andric   OS.EmitCOFFSecRel32(Fn, /*Offset=*/0);
9334ba319b5SDimitry Andric   OS.AddComment("Thunk section index");
9344ba319b5SDimitry Andric   OS.EmitCOFFSectionIndex(Fn);
9354ba319b5SDimitry Andric   OS.AddComment("Code size");
9364ba319b5SDimitry Andric   OS.emitAbsoluteSymbolDiff(FI.End, Fn, 2);
9374ba319b5SDimitry Andric   OS.AddComment("Ordinal");
9384ba319b5SDimitry Andric   OS.EmitIntValue(unsigned(ordinal), 1);
9394ba319b5SDimitry Andric   OS.AddComment("Function name");
9404ba319b5SDimitry Andric   emitNullTerminatedSymbolName(OS, FuncName);
9414ba319b5SDimitry Andric   // Additional fields specific to the thunk ordinal would go here.
942*b5893f02SDimitry Andric   endSymbolRecord(ThunkRecordEnd);
9434ba319b5SDimitry Andric 
9444ba319b5SDimitry Andric   // Local variables/inlined routines are purposely omitted here.  The point of
9454ba319b5SDimitry Andric   // marking this as a thunk is so Visual Studio will NOT stop in this routine.
9464ba319b5SDimitry Andric 
9474ba319b5SDimitry Andric   // Emit S_PROC_ID_END
948*b5893f02SDimitry Andric   emitEndSymbolRecord(SymbolKind::S_PROC_ID_END);
9494ba319b5SDimitry Andric 
9504ba319b5SDimitry Andric   endCVSubsection(SymbolsEnd);
9514ba319b5SDimitry Andric }
9524ba319b5SDimitry Andric 
emitDebugInfoForFunction(const Function * GV,FunctionInfo & FI)9533ca95b02SDimitry Andric void CodeViewDebug::emitDebugInfoForFunction(const Function *GV,
9543ca95b02SDimitry Andric                                              FunctionInfo &FI) {
9554ba319b5SDimitry Andric   // For each function there is a separate subsection which holds the PC to
9564ba319b5SDimitry Andric   // file:line table.
9573ca95b02SDimitry Andric   const MCSymbol *Fn = Asm->getSymbol(GV);
9583ca95b02SDimitry Andric   assert(Fn);
9593ca95b02SDimitry Andric 
9603ca95b02SDimitry Andric   // Switch to the to a comdat section, if appropriate.
9613ca95b02SDimitry Andric   switchToDebugSectionForSymbol(Fn);
9623ca95b02SDimitry Andric 
9633ca95b02SDimitry Andric   std::string FuncName;
9643ca95b02SDimitry Andric   auto *SP = GV->getSubprogram();
9656c4bc1bdSDimitry Andric   assert(SP);
9663ca95b02SDimitry Andric   setCurrentSubprogram(SP);
9673ca95b02SDimitry Andric 
9684ba319b5SDimitry Andric   if (SP->isThunk()) {
9694ba319b5SDimitry Andric     emitDebugInfoForThunk(GV, FI, Fn);
9704ba319b5SDimitry Andric     return;
9714ba319b5SDimitry Andric   }
9724ba319b5SDimitry Andric 
9733ca95b02SDimitry Andric   // If we have a display name, build the fully qualified name by walking the
9743ca95b02SDimitry Andric   // chain of scopes.
975f37b6182SDimitry Andric   if (!SP->getName().empty())
9763ca95b02SDimitry Andric     FuncName =
977f37b6182SDimitry Andric         getFullyQualifiedName(SP->getScope().resolve(), SP->getName());
9783ca95b02SDimitry Andric 
9793ca95b02SDimitry Andric   // If our DISubprogram name is empty, use the mangled name.
9803ca95b02SDimitry Andric   if (FuncName.empty())
9815517e702SDimitry Andric     FuncName = GlobalValue::dropLLVMManglingEscape(GV->getName());
9823ca95b02SDimitry Andric 
9832cab237bSDimitry Andric   // Emit FPO data, but only on 32-bit x86. No other platforms use it.
9842cab237bSDimitry Andric   if (Triple(MMI->getModule()->getTargetTriple()).getArch() == Triple::x86)
9852cab237bSDimitry Andric     OS.EmitCVFPOData(Fn);
9862cab237bSDimitry Andric 
9873ca95b02SDimitry Andric   // Emit a symbol subsection, required by VS2012+ to find function boundaries.
9883ca95b02SDimitry Andric   OS.AddComment("Symbol subsection for " + Twine(FuncName));
98989cb50c9SDimitry Andric   MCSymbol *SymbolsEnd = beginCVSubsection(DebugSubsectionKind::Symbols);
9903ca95b02SDimitry Andric   {
991*b5893f02SDimitry Andric     SymbolKind ProcKind = GV->hasLocalLinkage() ? SymbolKind::S_LPROC32_ID
992*b5893f02SDimitry Andric                                                 : SymbolKind::S_GPROC32_ID;
993*b5893f02SDimitry Andric     MCSymbol *ProcRecordEnd = beginSymbolRecord(ProcKind);
9943ca95b02SDimitry Andric 
9953ca95b02SDimitry Andric     // These fields are filled in by tools like CVPACK which run after the fact.
9963ca95b02SDimitry Andric     OS.AddComment("PtrParent");
9973ca95b02SDimitry Andric     OS.EmitIntValue(0, 4);
9983ca95b02SDimitry Andric     OS.AddComment("PtrEnd");
9993ca95b02SDimitry Andric     OS.EmitIntValue(0, 4);
10003ca95b02SDimitry Andric     OS.AddComment("PtrNext");
10013ca95b02SDimitry Andric     OS.EmitIntValue(0, 4);
10023ca95b02SDimitry Andric     // This is the important bit that tells the debugger where the function
10033ca95b02SDimitry Andric     // code is located and what's its size:
10043ca95b02SDimitry Andric     OS.AddComment("Code size");
10053ca95b02SDimitry Andric     OS.emitAbsoluteSymbolDiff(FI.End, Fn, 4);
10063ca95b02SDimitry Andric     OS.AddComment("Offset after prologue");
10073ca95b02SDimitry Andric     OS.EmitIntValue(0, 4);
10083ca95b02SDimitry Andric     OS.AddComment("Offset before epilogue");
10093ca95b02SDimitry Andric     OS.EmitIntValue(0, 4);
10103ca95b02SDimitry Andric     OS.AddComment("Function type index");
10113ca95b02SDimitry Andric     OS.EmitIntValue(getFuncIdForSubprogram(GV->getSubprogram()).getIndex(), 4);
10123ca95b02SDimitry Andric     OS.AddComment("Function section relative address");
1013d88c1a5aSDimitry Andric     OS.EmitCOFFSecRel32(Fn, /*Offset=*/0);
10143ca95b02SDimitry Andric     OS.AddComment("Function section index");
10153ca95b02SDimitry Andric     OS.EmitCOFFSectionIndex(Fn);
10163ca95b02SDimitry Andric     OS.AddComment("Flags");
10173ca95b02SDimitry Andric     OS.EmitIntValue(0, 1);
10183ca95b02SDimitry Andric     // Emit the function display name as a null-terminated string.
10193ca95b02SDimitry Andric     OS.AddComment("Function name");
10203ca95b02SDimitry Andric     // Truncate the name so we won't overflow the record length field.
10213ca95b02SDimitry Andric     emitNullTerminatedSymbolName(OS, FuncName);
1022*b5893f02SDimitry Andric     endSymbolRecord(ProcRecordEnd);
10233ca95b02SDimitry Andric 
1024*b5893f02SDimitry Andric     MCSymbol *FrameProcEnd = beginSymbolRecord(SymbolKind::S_FRAMEPROC);
1025*b5893f02SDimitry Andric     // Subtract out the CSR size since MSVC excludes that and we include it.
1026*b5893f02SDimitry Andric     OS.AddComment("FrameSize");
1027*b5893f02SDimitry Andric     OS.EmitIntValue(FI.FrameSize - FI.CSRSize, 4);
1028*b5893f02SDimitry Andric     OS.AddComment("Padding");
1029*b5893f02SDimitry Andric     OS.EmitIntValue(0, 4);
1030*b5893f02SDimitry Andric     OS.AddComment("Offset of padding");
1031*b5893f02SDimitry Andric     OS.EmitIntValue(0, 4);
1032*b5893f02SDimitry Andric     OS.AddComment("Bytes of callee saved registers");
1033*b5893f02SDimitry Andric     OS.EmitIntValue(FI.CSRSize, 4);
1034*b5893f02SDimitry Andric     OS.AddComment("Exception handler offset");
1035*b5893f02SDimitry Andric     OS.EmitIntValue(0, 4);
1036*b5893f02SDimitry Andric     OS.AddComment("Exception handler section");
1037*b5893f02SDimitry Andric     OS.EmitIntValue(0, 2);
1038*b5893f02SDimitry Andric     OS.AddComment("Flags (defines frame register)");
1039*b5893f02SDimitry Andric     OS.EmitIntValue(uint32_t(FI.FrameProcOpts), 4);
1040*b5893f02SDimitry Andric     endSymbolRecord(FrameProcEnd);
1041*b5893f02SDimitry Andric 
1042*b5893f02SDimitry Andric     emitLocalVariableList(FI, FI.Locals);
1043*b5893f02SDimitry Andric     emitGlobalVariableList(FI.Globals);
10444ba319b5SDimitry Andric     emitLexicalBlockList(FI.ChildBlocks, FI);
10453ca95b02SDimitry Andric 
10463ca95b02SDimitry Andric     // Emit inlined call site information. Only emit functions inlined directly
10473ca95b02SDimitry Andric     // into the parent function. We'll emit the other sites recursively as part
10483ca95b02SDimitry Andric     // of their parent inline site.
10493ca95b02SDimitry Andric     for (const DILocation *InlinedAt : FI.ChildSites) {
10503ca95b02SDimitry Andric       auto I = FI.InlineSites.find(InlinedAt);
10513ca95b02SDimitry Andric       assert(I != FI.InlineSites.end() &&
10523ca95b02SDimitry Andric              "child site not in function inline site map");
10533ca95b02SDimitry Andric       emitInlinedCallSite(FI, InlinedAt, I->second);
10543ca95b02SDimitry Andric     }
10553ca95b02SDimitry Andric 
10562cab237bSDimitry Andric     for (auto Annot : FI.Annotations) {
10572cab237bSDimitry Andric       MCSymbol *Label = Annot.first;
10582cab237bSDimitry Andric       MDTuple *Strs = cast<MDTuple>(Annot.second);
1059*b5893f02SDimitry Andric       MCSymbol *AnnotEnd = beginSymbolRecord(SymbolKind::S_ANNOTATION);
10602cab237bSDimitry Andric       OS.EmitCOFFSecRel32(Label, /*Offset=*/0);
10612cab237bSDimitry Andric       // FIXME: Make sure we don't overflow the max record size.
10622cab237bSDimitry Andric       OS.EmitCOFFSectionIndex(Label);
10632cab237bSDimitry Andric       OS.EmitIntValue(Strs->getNumOperands(), 2);
10642cab237bSDimitry Andric       for (Metadata *MD : Strs->operands()) {
10652cab237bSDimitry Andric         // MDStrings are null terminated, so we can do EmitBytes and get the
10662cab237bSDimitry Andric         // nice .asciz directive.
10672cab237bSDimitry Andric         StringRef Str = cast<MDString>(MD)->getString();
10682cab237bSDimitry Andric         assert(Str.data()[Str.size()] == '\0' && "non-nullterminated MDString");
10692cab237bSDimitry Andric         OS.EmitBytes(StringRef(Str.data(), Str.size() + 1));
10702cab237bSDimitry Andric       }
1071*b5893f02SDimitry Andric       endSymbolRecord(AnnotEnd);
10722cab237bSDimitry Andric     }
10732cab237bSDimitry Andric 
10743ca95b02SDimitry Andric     if (SP != nullptr)
10753ca95b02SDimitry Andric       emitDebugInfoForUDTs(LocalUDTs);
10763ca95b02SDimitry Andric 
10773ca95b02SDimitry Andric     // We're done with this function.
1078*b5893f02SDimitry Andric     emitEndSymbolRecord(SymbolKind::S_PROC_ID_END);
10793ca95b02SDimitry Andric   }
10803ca95b02SDimitry Andric   endCVSubsection(SymbolsEnd);
10813ca95b02SDimitry Andric 
10823ca95b02SDimitry Andric   // We have an assembler directive that takes care of the whole line table.
10833ca95b02SDimitry Andric   OS.EmitCVLinetableDirective(FI.FuncId, Fn, FI.End);
10843ca95b02SDimitry Andric }
10853ca95b02SDimitry Andric 
10863ca95b02SDimitry Andric CodeViewDebug::LocalVarDefRange
createDefRangeMem(uint16_t CVRegister,int Offset)10873ca95b02SDimitry Andric CodeViewDebug::createDefRangeMem(uint16_t CVRegister, int Offset) {
10883ca95b02SDimitry Andric   LocalVarDefRange DR;
10893ca95b02SDimitry Andric   DR.InMemory = -1;
10903ca95b02SDimitry Andric   DR.DataOffset = Offset;
10913ca95b02SDimitry Andric   assert(DR.DataOffset == Offset && "truncation");
1092d88c1a5aSDimitry Andric   DR.IsSubfield = 0;
10933ca95b02SDimitry Andric   DR.StructOffset = 0;
10943ca95b02SDimitry Andric   DR.CVRegister = CVRegister;
10953ca95b02SDimitry Andric   return DR;
10963ca95b02SDimitry Andric }
10973ca95b02SDimitry Andric 
collectVariableInfoFromMFTable(DenseSet<InlinedEntity> & Processed)1098d88c1a5aSDimitry Andric void CodeViewDebug::collectVariableInfoFromMFTable(
1099*b5893f02SDimitry Andric     DenseSet<InlinedEntity> &Processed) {
1100d88c1a5aSDimitry Andric   const MachineFunction &MF = *Asm->MF;
1101d88c1a5aSDimitry Andric   const TargetSubtargetInfo &TSI = MF.getSubtarget();
11023ca95b02SDimitry Andric   const TargetFrameLowering *TFI = TSI.getFrameLowering();
11033ca95b02SDimitry Andric   const TargetRegisterInfo *TRI = TSI.getRegisterInfo();
11043ca95b02SDimitry Andric 
1105d88c1a5aSDimitry Andric   for (const MachineFunction::VariableDbgInfo &VI : MF.getVariableDbgInfo()) {
11063ca95b02SDimitry Andric     if (!VI.Var)
11073ca95b02SDimitry Andric       continue;
11083ca95b02SDimitry Andric     assert(VI.Var->isValidLocationForIntrinsic(VI.Loc) &&
11093ca95b02SDimitry Andric            "Expected inlined-at fields to agree");
11103ca95b02SDimitry Andric 
1111*b5893f02SDimitry Andric     Processed.insert(InlinedEntity(VI.Var, VI.Loc->getInlinedAt()));
11123ca95b02SDimitry Andric     LexicalScope *Scope = LScopes.findLexicalScope(VI.Loc);
11133ca95b02SDimitry Andric 
11143ca95b02SDimitry Andric     // If variable scope is not found then skip this variable.
11153ca95b02SDimitry Andric     if (!Scope)
11163ca95b02SDimitry Andric       continue;
11173ca95b02SDimitry Andric 
11185517e702SDimitry Andric     // If the variable has an attached offset expression, extract it.
11195517e702SDimitry Andric     // FIXME: Try to handle DW_OP_deref as well.
11205517e702SDimitry Andric     int64_t ExprOffset = 0;
11215517e702SDimitry Andric     if (VI.Expr)
11225517e702SDimitry Andric       if (!VI.Expr->extractIfOffset(ExprOffset))
11235517e702SDimitry Andric         continue;
11245517e702SDimitry Andric 
11253ca95b02SDimitry Andric     // Get the frame register used and the offset.
11263ca95b02SDimitry Andric     unsigned FrameReg = 0;
11273ca95b02SDimitry Andric     int FrameOffset = TFI->getFrameIndexReference(*Asm->MF, VI.Slot, FrameReg);
11283ca95b02SDimitry Andric     uint16_t CVReg = TRI->getCodeViewRegNum(FrameReg);
11293ca95b02SDimitry Andric 
11303ca95b02SDimitry Andric     // Calculate the label ranges.
11315517e702SDimitry Andric     LocalVarDefRange DefRange =
11325517e702SDimitry Andric         createDefRangeMem(CVReg, FrameOffset + ExprOffset);
11333ca95b02SDimitry Andric     for (const InsnRange &Range : Scope->getRanges()) {
11343ca95b02SDimitry Andric       const MCSymbol *Begin = getLabelBeforeInsn(Range.first);
11353ca95b02SDimitry Andric       const MCSymbol *End = getLabelAfterInsn(Range.second);
11363ca95b02SDimitry Andric       End = End ? End : Asm->getFunctionEnd();
11373ca95b02SDimitry Andric       DefRange.Ranges.emplace_back(Begin, End);
11383ca95b02SDimitry Andric     }
11393ca95b02SDimitry Andric 
11403ca95b02SDimitry Andric     LocalVariable Var;
11413ca95b02SDimitry Andric     Var.DIVar = VI.Var;
11423ca95b02SDimitry Andric     Var.DefRanges.emplace_back(std::move(DefRange));
11434ba319b5SDimitry Andric     recordLocalVariable(std::move(Var), Scope);
11443ca95b02SDimitry Andric   }
11453ca95b02SDimitry Andric }
11463ca95b02SDimitry Andric 
canUseReferenceType(const DbgVariableLocation & Loc)11472cab237bSDimitry Andric static bool canUseReferenceType(const DbgVariableLocation &Loc) {
11482cab237bSDimitry Andric   return !Loc.LoadChain.empty() && Loc.LoadChain.back() == 0;
11492cab237bSDimitry Andric }
11502cab237bSDimitry Andric 
needsReferenceType(const DbgVariableLocation & Loc)11512cab237bSDimitry Andric static bool needsReferenceType(const DbgVariableLocation &Loc) {
11522cab237bSDimitry Andric   return Loc.LoadChain.size() == 2 && Loc.LoadChain.back() == 0;
11532cab237bSDimitry Andric }
11542cab237bSDimitry Andric 
calculateRanges(LocalVariable & Var,const DbgValueHistoryMap::InstrRanges & Ranges)11552cab237bSDimitry Andric void CodeViewDebug::calculateRanges(
11562cab237bSDimitry Andric     LocalVariable &Var, const DbgValueHistoryMap::InstrRanges &Ranges) {
11572cab237bSDimitry Andric   const TargetRegisterInfo *TRI = Asm->MF->getSubtarget().getRegisterInfo();
11582cab237bSDimitry Andric 
11592cab237bSDimitry Andric   // Calculate the definition ranges.
11602cab237bSDimitry Andric   for (auto I = Ranges.begin(), E = Ranges.end(); I != E; ++I) {
11612cab237bSDimitry Andric     const InsnRange &Range = *I;
11622cab237bSDimitry Andric     const MachineInstr *DVInst = Range.first;
11632cab237bSDimitry Andric     assert(DVInst->isDebugValue() && "Invalid History entry");
11642cab237bSDimitry Andric     // FIXME: Find a way to represent constant variables, since they are
11652cab237bSDimitry Andric     // relatively common.
11662cab237bSDimitry Andric     Optional<DbgVariableLocation> Location =
11672cab237bSDimitry Andric         DbgVariableLocation::extractFromMachineInstruction(*DVInst);
11682cab237bSDimitry Andric     if (!Location)
11692cab237bSDimitry Andric       continue;
11702cab237bSDimitry Andric 
11712cab237bSDimitry Andric     // CodeView can only express variables in register and variables in memory
11722cab237bSDimitry Andric     // at a constant offset from a register. However, for variables passed
11732cab237bSDimitry Andric     // indirectly by pointer, it is common for that pointer to be spilled to a
11742cab237bSDimitry Andric     // stack location. For the special case of one offseted load followed by a
11752cab237bSDimitry Andric     // zero offset load (a pointer spilled to the stack), we change the type of
11762cab237bSDimitry Andric     // the local variable from a value type to a reference type. This tricks the
11772cab237bSDimitry Andric     // debugger into doing the load for us.
11782cab237bSDimitry Andric     if (Var.UseReferenceType) {
11792cab237bSDimitry Andric       // We're using a reference type. Drop the last zero offset load.
11802cab237bSDimitry Andric       if (canUseReferenceType(*Location))
11812cab237bSDimitry Andric         Location->LoadChain.pop_back();
11822cab237bSDimitry Andric       else
11832cab237bSDimitry Andric         continue;
11842cab237bSDimitry Andric     } else if (needsReferenceType(*Location)) {
11852cab237bSDimitry Andric       // This location can't be expressed without switching to a reference type.
11862cab237bSDimitry Andric       // Start over using that.
11872cab237bSDimitry Andric       Var.UseReferenceType = true;
11882cab237bSDimitry Andric       Var.DefRanges.clear();
11892cab237bSDimitry Andric       calculateRanges(Var, Ranges);
11902cab237bSDimitry Andric       return;
11912cab237bSDimitry Andric     }
11922cab237bSDimitry Andric 
11932cab237bSDimitry Andric     // We can only handle a register or an offseted load of a register.
11942cab237bSDimitry Andric     if (Location->Register == 0 || Location->LoadChain.size() > 1)
11952cab237bSDimitry Andric       continue;
11962cab237bSDimitry Andric     {
11972cab237bSDimitry Andric       LocalVarDefRange DR;
11982cab237bSDimitry Andric       DR.CVRegister = TRI->getCodeViewRegNum(Location->Register);
11992cab237bSDimitry Andric       DR.InMemory = !Location->LoadChain.empty();
12002cab237bSDimitry Andric       DR.DataOffset =
12012cab237bSDimitry Andric           !Location->LoadChain.empty() ? Location->LoadChain.back() : 0;
12022cab237bSDimitry Andric       if (Location->FragmentInfo) {
12032cab237bSDimitry Andric         DR.IsSubfield = true;
12042cab237bSDimitry Andric         DR.StructOffset = Location->FragmentInfo->OffsetInBits / 8;
12052cab237bSDimitry Andric       } else {
12062cab237bSDimitry Andric         DR.IsSubfield = false;
12072cab237bSDimitry Andric         DR.StructOffset = 0;
12082cab237bSDimitry Andric       }
12092cab237bSDimitry Andric 
12102cab237bSDimitry Andric       if (Var.DefRanges.empty() ||
12112cab237bSDimitry Andric           Var.DefRanges.back().isDifferentLocation(DR)) {
12122cab237bSDimitry Andric         Var.DefRanges.emplace_back(std::move(DR));
12132cab237bSDimitry Andric       }
12142cab237bSDimitry Andric     }
12152cab237bSDimitry Andric 
12162cab237bSDimitry Andric     // Compute the label range.
12172cab237bSDimitry Andric     const MCSymbol *Begin = getLabelBeforeInsn(Range.first);
12182cab237bSDimitry Andric     const MCSymbol *End = getLabelAfterInsn(Range.second);
12192cab237bSDimitry Andric     if (!End) {
12202cab237bSDimitry Andric       // This range is valid until the next overlapping bitpiece. In the
12212cab237bSDimitry Andric       // common case, ranges will not be bitpieces, so they will overlap.
12222cab237bSDimitry Andric       auto J = std::next(I);
12232cab237bSDimitry Andric       const DIExpression *DIExpr = DVInst->getDebugExpression();
12242cab237bSDimitry Andric       while (J != E &&
12254ba319b5SDimitry Andric              !DIExpr->fragmentsOverlap(J->first->getDebugExpression()))
12262cab237bSDimitry Andric         ++J;
12272cab237bSDimitry Andric       if (J != E)
12282cab237bSDimitry Andric         End = getLabelBeforeInsn(J->first);
12292cab237bSDimitry Andric       else
12302cab237bSDimitry Andric         End = Asm->getFunctionEnd();
12312cab237bSDimitry Andric     }
12322cab237bSDimitry Andric 
12332cab237bSDimitry Andric     // If the last range end is our begin, just extend the last range.
12342cab237bSDimitry Andric     // Otherwise make a new range.
12352cab237bSDimitry Andric     SmallVectorImpl<std::pair<const MCSymbol *, const MCSymbol *>> &R =
12362cab237bSDimitry Andric         Var.DefRanges.back().Ranges;
12372cab237bSDimitry Andric     if (!R.empty() && R.back().second == Begin)
12382cab237bSDimitry Andric       R.back().second = End;
12392cab237bSDimitry Andric     else
12402cab237bSDimitry Andric       R.emplace_back(Begin, End);
12412cab237bSDimitry Andric 
12422cab237bSDimitry Andric     // FIXME: Do more range combining.
12432cab237bSDimitry Andric   }
12442cab237bSDimitry Andric }
12452cab237bSDimitry Andric 
collectVariableInfo(const DISubprogram * SP)12463ca95b02SDimitry Andric void CodeViewDebug::collectVariableInfo(const DISubprogram *SP) {
1247*b5893f02SDimitry Andric   DenseSet<InlinedEntity> Processed;
12483ca95b02SDimitry Andric   // Grab the variable info that was squirreled away in the MMI side-table.
1249d88c1a5aSDimitry Andric   collectVariableInfoFromMFTable(Processed);
12503ca95b02SDimitry Andric 
12513ca95b02SDimitry Andric   for (const auto &I : DbgValues) {
1252*b5893f02SDimitry Andric     InlinedEntity IV = I.first;
12533ca95b02SDimitry Andric     if (Processed.count(IV))
12543ca95b02SDimitry Andric       continue;
1255*b5893f02SDimitry Andric     const DILocalVariable *DIVar = cast<DILocalVariable>(IV.first);
12563ca95b02SDimitry Andric     const DILocation *InlinedAt = IV.second;
12573ca95b02SDimitry Andric 
12583ca95b02SDimitry Andric     // Instruction ranges, specifying where IV is accessible.
12593ca95b02SDimitry Andric     const auto &Ranges = I.second;
12603ca95b02SDimitry Andric 
12613ca95b02SDimitry Andric     LexicalScope *Scope = nullptr;
12623ca95b02SDimitry Andric     if (InlinedAt)
12633ca95b02SDimitry Andric       Scope = LScopes.findInlinedScope(DIVar->getScope(), InlinedAt);
12643ca95b02SDimitry Andric     else
12653ca95b02SDimitry Andric       Scope = LScopes.findLexicalScope(DIVar->getScope());
12663ca95b02SDimitry Andric     // If variable scope is not found then skip this variable.
12673ca95b02SDimitry Andric     if (!Scope)
12683ca95b02SDimitry Andric       continue;
12693ca95b02SDimitry Andric 
12703ca95b02SDimitry Andric     LocalVariable Var;
12713ca95b02SDimitry Andric     Var.DIVar = DIVar;
12723ca95b02SDimitry Andric 
12732cab237bSDimitry Andric     calculateRanges(Var, Ranges);
12744ba319b5SDimitry Andric     recordLocalVariable(std::move(Var), Scope);
12753ca95b02SDimitry Andric   }
12763ca95b02SDimitry Andric }
12773ca95b02SDimitry Andric 
beginFunctionImpl(const MachineFunction * MF)12787a7e6055SDimitry Andric void CodeViewDebug::beginFunctionImpl(const MachineFunction *MF) {
1279*b5893f02SDimitry Andric   const TargetSubtargetInfo &TSI = MF->getSubtarget();
1280*b5893f02SDimitry Andric   const TargetRegisterInfo *TRI = TSI.getRegisterInfo();
1281*b5893f02SDimitry Andric   const MachineFrameInfo &MFI = MF->getFrameInfo();
12822cab237bSDimitry Andric   const Function &GV = MF->getFunction();
12834ba319b5SDimitry Andric   auto Insertion = FnDebugInfo.insert({&GV, llvm::make_unique<FunctionInfo>()});
12844ba319b5SDimitry Andric   assert(Insertion.second && "function already has info");
12854ba319b5SDimitry Andric   CurFn = Insertion.first->second.get();
12863ca95b02SDimitry Andric   CurFn->FuncId = NextFuncId++;
12873ca95b02SDimitry Andric   CurFn->Begin = Asm->getFunctionBegin();
12883ca95b02SDimitry Andric 
1289*b5893f02SDimitry Andric   // The S_FRAMEPROC record reports the stack size, and how many bytes of
1290*b5893f02SDimitry Andric   // callee-saved registers were used. For targets that don't use a PUSH
1291*b5893f02SDimitry Andric   // instruction (AArch64), this will be zero.
1292*b5893f02SDimitry Andric   CurFn->CSRSize = MFI.getCVBytesOfCalleeSavedRegisters();
1293*b5893f02SDimitry Andric   CurFn->FrameSize = MFI.getStackSize();
1294*b5893f02SDimitry Andric   CurFn->OffsetAdjustment = MFI.getOffsetAdjustment();
1295*b5893f02SDimitry Andric   CurFn->HasStackRealignment = TRI->needsStackRealignment(*MF);
1296*b5893f02SDimitry Andric 
1297*b5893f02SDimitry Andric   // For this function S_FRAMEPROC record, figure out which codeview register
1298*b5893f02SDimitry Andric   // will be the frame pointer.
1299*b5893f02SDimitry Andric   CurFn->EncodedParamFramePtrReg = EncodedFramePtrReg::None; // None.
1300*b5893f02SDimitry Andric   CurFn->EncodedLocalFramePtrReg = EncodedFramePtrReg::None; // None.
1301*b5893f02SDimitry Andric   if (CurFn->FrameSize > 0) {
1302*b5893f02SDimitry Andric     if (!TSI.getFrameLowering()->hasFP(*MF)) {
1303*b5893f02SDimitry Andric       CurFn->EncodedLocalFramePtrReg = EncodedFramePtrReg::StackPtr;
1304*b5893f02SDimitry Andric       CurFn->EncodedParamFramePtrReg = EncodedFramePtrReg::StackPtr;
1305*b5893f02SDimitry Andric     } else {
1306*b5893f02SDimitry Andric       // If there is an FP, parameters are always relative to it.
1307*b5893f02SDimitry Andric       CurFn->EncodedParamFramePtrReg = EncodedFramePtrReg::FramePtr;
1308*b5893f02SDimitry Andric       if (CurFn->HasStackRealignment) {
1309*b5893f02SDimitry Andric         // If the stack needs realignment, locals are relative to SP or VFRAME.
1310*b5893f02SDimitry Andric         CurFn->EncodedLocalFramePtrReg = EncodedFramePtrReg::StackPtr;
1311*b5893f02SDimitry Andric       } else {
1312*b5893f02SDimitry Andric         // Otherwise, locals are relative to EBP, and we probably have VLAs or
1313*b5893f02SDimitry Andric         // other stack adjustments.
1314*b5893f02SDimitry Andric         CurFn->EncodedLocalFramePtrReg = EncodedFramePtrReg::FramePtr;
1315*b5893f02SDimitry Andric       }
1316*b5893f02SDimitry Andric     }
1317*b5893f02SDimitry Andric   }
1318*b5893f02SDimitry Andric 
1319*b5893f02SDimitry Andric   // Compute other frame procedure options.
1320*b5893f02SDimitry Andric   FrameProcedureOptions FPO = FrameProcedureOptions::None;
1321*b5893f02SDimitry Andric   if (MFI.hasVarSizedObjects())
1322*b5893f02SDimitry Andric     FPO |= FrameProcedureOptions::HasAlloca;
1323*b5893f02SDimitry Andric   if (MF->exposesReturnsTwice())
1324*b5893f02SDimitry Andric     FPO |= FrameProcedureOptions::HasSetJmp;
1325*b5893f02SDimitry Andric   // FIXME: Set HasLongJmp if we ever track that info.
1326*b5893f02SDimitry Andric   if (MF->hasInlineAsm())
1327*b5893f02SDimitry Andric     FPO |= FrameProcedureOptions::HasInlineAssembly;
1328*b5893f02SDimitry Andric   if (GV.hasPersonalityFn()) {
1329*b5893f02SDimitry Andric     if (isAsynchronousEHPersonality(
1330*b5893f02SDimitry Andric             classifyEHPersonality(GV.getPersonalityFn())))
1331*b5893f02SDimitry Andric       FPO |= FrameProcedureOptions::HasStructuredExceptionHandling;
1332*b5893f02SDimitry Andric     else
1333*b5893f02SDimitry Andric       FPO |= FrameProcedureOptions::HasExceptionHandling;
1334*b5893f02SDimitry Andric   }
1335*b5893f02SDimitry Andric   if (GV.hasFnAttribute(Attribute::InlineHint))
1336*b5893f02SDimitry Andric     FPO |= FrameProcedureOptions::MarkedInline;
1337*b5893f02SDimitry Andric   if (GV.hasFnAttribute(Attribute::Naked))
1338*b5893f02SDimitry Andric     FPO |= FrameProcedureOptions::Naked;
1339*b5893f02SDimitry Andric   if (MFI.hasStackProtectorIndex())
1340*b5893f02SDimitry Andric     FPO |= FrameProcedureOptions::SecurityChecks;
1341*b5893f02SDimitry Andric   FPO |= FrameProcedureOptions(uint32_t(CurFn->EncodedLocalFramePtrReg) << 14U);
1342*b5893f02SDimitry Andric   FPO |= FrameProcedureOptions(uint32_t(CurFn->EncodedParamFramePtrReg) << 16U);
1343*b5893f02SDimitry Andric   if (Asm->TM.getOptLevel() != CodeGenOpt::None && !GV.optForSize() &&
1344*b5893f02SDimitry Andric       !GV.hasFnAttribute(Attribute::OptimizeNone))
1345*b5893f02SDimitry Andric     FPO |= FrameProcedureOptions::OptimizedForSpeed;
1346*b5893f02SDimitry Andric   // FIXME: Set GuardCfg when it is implemented.
1347*b5893f02SDimitry Andric   CurFn->FrameProcOpts = FPO;
1348*b5893f02SDimitry Andric 
1349d88c1a5aSDimitry Andric   OS.EmitCVFuncIdDirective(CurFn->FuncId);
1350d88c1a5aSDimitry Andric 
13513ca95b02SDimitry Andric   // Find the end of the function prolog.  First known non-DBG_VALUE and
13523ca95b02SDimitry Andric   // non-frame setup location marks the beginning of the function body.
13533ca95b02SDimitry Andric   // FIXME: is there a simpler a way to do this? Can we just search
13543ca95b02SDimitry Andric   // for the first instruction of the function, not the last of the prolog?
13553ca95b02SDimitry Andric   DebugLoc PrologEndLoc;
13563ca95b02SDimitry Andric   bool EmptyPrologue = true;
13573ca95b02SDimitry Andric   for (const auto &MBB : *MF) {
13583ca95b02SDimitry Andric     for (const auto &MI : MBB) {
1359302affcbSDimitry Andric       if (!MI.isMetaInstruction() && !MI.getFlag(MachineInstr::FrameSetup) &&
13603ca95b02SDimitry Andric           MI.getDebugLoc()) {
13613ca95b02SDimitry Andric         PrologEndLoc = MI.getDebugLoc();
13623ca95b02SDimitry Andric         break;
1363302affcbSDimitry Andric       } else if (!MI.isMetaInstruction()) {
13643ca95b02SDimitry Andric         EmptyPrologue = false;
13653ca95b02SDimitry Andric       }
13663ca95b02SDimitry Andric     }
13673ca95b02SDimitry Andric   }
13683ca95b02SDimitry Andric 
13693ca95b02SDimitry Andric   // Record beginning of function if we have a non-empty prologue.
13703ca95b02SDimitry Andric   if (PrologEndLoc && !EmptyPrologue) {
13713ca95b02SDimitry Andric     DebugLoc FnStartDL = PrologEndLoc.getFnDebugLoc();
13723ca95b02SDimitry Andric     maybeRecordLocation(FnStartDL, MF);
13733ca95b02SDimitry Andric   }
13743ca95b02SDimitry Andric }
13753ca95b02SDimitry Andric 
shouldEmitUdt(const DIType * T)13762cab237bSDimitry Andric static bool shouldEmitUdt(const DIType *T) {
13772cab237bSDimitry Andric   if (!T)
13782cab237bSDimitry Andric     return false;
13792cab237bSDimitry Andric 
13802cab237bSDimitry Andric   // MSVC does not emit UDTs for typedefs that are scoped to classes.
13812cab237bSDimitry Andric   if (T->getTag() == dwarf::DW_TAG_typedef) {
13822cab237bSDimitry Andric     if (DIScope *Scope = T->getScope().resolve()) {
13832cab237bSDimitry Andric       switch (Scope->getTag()) {
13842cab237bSDimitry Andric       case dwarf::DW_TAG_structure_type:
13852cab237bSDimitry Andric       case dwarf::DW_TAG_class_type:
13862cab237bSDimitry Andric       case dwarf::DW_TAG_union_type:
13872cab237bSDimitry Andric         return false;
13882cab237bSDimitry Andric       }
13892cab237bSDimitry Andric     }
13902cab237bSDimitry Andric   }
13912cab237bSDimitry Andric 
13922cab237bSDimitry Andric   while (true) {
13932cab237bSDimitry Andric     if (!T || T->isForwardDecl())
13942cab237bSDimitry Andric       return false;
13952cab237bSDimitry Andric 
13962cab237bSDimitry Andric     const DIDerivedType *DT = dyn_cast<DIDerivedType>(T);
13972cab237bSDimitry Andric     if (!DT)
13982cab237bSDimitry Andric       return true;
13992cab237bSDimitry Andric     T = DT->getBaseType().resolve();
14002cab237bSDimitry Andric   }
14012cab237bSDimitry Andric   return true;
14022cab237bSDimitry Andric }
14032cab237bSDimitry Andric 
addToUDTs(const DIType * Ty)14042cab237bSDimitry Andric void CodeViewDebug::addToUDTs(const DIType *Ty) {
14053ca95b02SDimitry Andric   // Don't record empty UDTs.
14063ca95b02SDimitry Andric   if (Ty->getName().empty())
14073ca95b02SDimitry Andric     return;
14082cab237bSDimitry Andric   if (!shouldEmitUdt(Ty))
14092cab237bSDimitry Andric     return;
14103ca95b02SDimitry Andric 
14113ca95b02SDimitry Andric   SmallVector<StringRef, 5> QualifiedNameComponents;
14123ca95b02SDimitry Andric   const DISubprogram *ClosestSubprogram = getQualifiedNameComponents(
14133ca95b02SDimitry Andric       Ty->getScope().resolve(), QualifiedNameComponents);
14143ca95b02SDimitry Andric 
14153ca95b02SDimitry Andric   std::string FullyQualifiedName =
14163ca95b02SDimitry Andric       getQualifiedName(QualifiedNameComponents, getPrettyScopeName(Ty));
14173ca95b02SDimitry Andric 
14182cab237bSDimitry Andric   if (ClosestSubprogram == nullptr) {
14192cab237bSDimitry Andric     GlobalUDTs.emplace_back(std::move(FullyQualifiedName), Ty);
14202cab237bSDimitry Andric   } else if (ClosestSubprogram == CurrentSubprogram) {
14212cab237bSDimitry Andric     LocalUDTs.emplace_back(std::move(FullyQualifiedName), Ty);
14222cab237bSDimitry Andric   }
14233ca95b02SDimitry Andric 
14243ca95b02SDimitry Andric   // TODO: What if the ClosestSubprogram is neither null or the current
14253ca95b02SDimitry Andric   // subprogram?  Currently, the UDT just gets dropped on the floor.
14263ca95b02SDimitry Andric   //
14273ca95b02SDimitry Andric   // The current behavior is not desirable.  To get maximal fidelity, we would
14283ca95b02SDimitry Andric   // need to perform all type translation before beginning emission of .debug$S
14293ca95b02SDimitry Andric   // and then make LocalUDTs a member of FunctionInfo
14303ca95b02SDimitry Andric }
14313ca95b02SDimitry Andric 
lowerType(const DIType * Ty,const DIType * ClassTy)14323ca95b02SDimitry Andric TypeIndex CodeViewDebug::lowerType(const DIType *Ty, const DIType *ClassTy) {
14333ca95b02SDimitry Andric   // Generic dispatch for lowering an unknown type.
14343ca95b02SDimitry Andric   switch (Ty->getTag()) {
14353ca95b02SDimitry Andric   case dwarf::DW_TAG_array_type:
14363ca95b02SDimitry Andric     return lowerTypeArray(cast<DICompositeType>(Ty));
14373ca95b02SDimitry Andric   case dwarf::DW_TAG_typedef:
14383ca95b02SDimitry Andric     return lowerTypeAlias(cast<DIDerivedType>(Ty));
14393ca95b02SDimitry Andric   case dwarf::DW_TAG_base_type:
14403ca95b02SDimitry Andric     return lowerTypeBasic(cast<DIBasicType>(Ty));
14413ca95b02SDimitry Andric   case dwarf::DW_TAG_pointer_type:
1442d88c1a5aSDimitry Andric     if (cast<DIDerivedType>(Ty)->getName() == "__vtbl_ptr_type")
1443d88c1a5aSDimitry Andric       return lowerTypeVFTableShape(cast<DIDerivedType>(Ty));
1444d88c1a5aSDimitry Andric     LLVM_FALLTHROUGH;
14453ca95b02SDimitry Andric   case dwarf::DW_TAG_reference_type:
14463ca95b02SDimitry Andric   case dwarf::DW_TAG_rvalue_reference_type:
14473ca95b02SDimitry Andric     return lowerTypePointer(cast<DIDerivedType>(Ty));
14483ca95b02SDimitry Andric   case dwarf::DW_TAG_ptr_to_member_type:
14493ca95b02SDimitry Andric     return lowerTypeMemberPointer(cast<DIDerivedType>(Ty));
14504ba319b5SDimitry Andric   case dwarf::DW_TAG_restrict_type:
14513ca95b02SDimitry Andric   case dwarf::DW_TAG_const_type:
14523ca95b02SDimitry Andric   case dwarf::DW_TAG_volatile_type:
1453d88c1a5aSDimitry Andric   // TODO: add support for DW_TAG_atomic_type here
14543ca95b02SDimitry Andric     return lowerTypeModifier(cast<DIDerivedType>(Ty));
14553ca95b02SDimitry Andric   case dwarf::DW_TAG_subroutine_type:
14563ca95b02SDimitry Andric     if (ClassTy) {
14573ca95b02SDimitry Andric       // The member function type of a member function pointer has no
14583ca95b02SDimitry Andric       // ThisAdjustment.
14593ca95b02SDimitry Andric       return lowerTypeMemberFunction(cast<DISubroutineType>(Ty), ClassTy,
14602cab237bSDimitry Andric                                      /*ThisAdjustment=*/0,
14612cab237bSDimitry Andric                                      /*IsStaticMethod=*/false);
14623ca95b02SDimitry Andric     }
14633ca95b02SDimitry Andric     return lowerTypeFunction(cast<DISubroutineType>(Ty));
14643ca95b02SDimitry Andric   case dwarf::DW_TAG_enumeration_type:
14653ca95b02SDimitry Andric     return lowerTypeEnum(cast<DICompositeType>(Ty));
14663ca95b02SDimitry Andric   case dwarf::DW_TAG_class_type:
14673ca95b02SDimitry Andric   case dwarf::DW_TAG_structure_type:
14683ca95b02SDimitry Andric     return lowerTypeClass(cast<DICompositeType>(Ty));
14693ca95b02SDimitry Andric   case dwarf::DW_TAG_union_type:
14703ca95b02SDimitry Andric     return lowerTypeUnion(cast<DICompositeType>(Ty));
14714ba319b5SDimitry Andric   case dwarf::DW_TAG_unspecified_type:
1472*b5893f02SDimitry Andric     if (Ty->getName() == "decltype(nullptr)")
1473*b5893f02SDimitry Andric       return TypeIndex::NullptrT();
14744ba319b5SDimitry Andric     return TypeIndex::None();
14753ca95b02SDimitry Andric   default:
14763ca95b02SDimitry Andric     // Use the null type index.
14773ca95b02SDimitry Andric     return TypeIndex();
14783ca95b02SDimitry Andric   }
14793ca95b02SDimitry Andric }
14803ca95b02SDimitry Andric 
lowerTypeAlias(const DIDerivedType * Ty)14813ca95b02SDimitry Andric TypeIndex CodeViewDebug::lowerTypeAlias(const DIDerivedType *Ty) {
14823ca95b02SDimitry Andric   DITypeRef UnderlyingTypeRef = Ty->getBaseType();
14833ca95b02SDimitry Andric   TypeIndex UnderlyingTypeIndex = getTypeIndex(UnderlyingTypeRef);
14843ca95b02SDimitry Andric   StringRef TypeName = Ty->getName();
14853ca95b02SDimitry Andric 
14862cab237bSDimitry Andric   addToUDTs(Ty);
14873ca95b02SDimitry Andric 
14883ca95b02SDimitry Andric   if (UnderlyingTypeIndex == TypeIndex(SimpleTypeKind::Int32Long) &&
14893ca95b02SDimitry Andric       TypeName == "HRESULT")
14903ca95b02SDimitry Andric     return TypeIndex(SimpleTypeKind::HResult);
14913ca95b02SDimitry Andric   if (UnderlyingTypeIndex == TypeIndex(SimpleTypeKind::UInt16Short) &&
14923ca95b02SDimitry Andric       TypeName == "wchar_t")
14933ca95b02SDimitry Andric     return TypeIndex(SimpleTypeKind::WideCharacter);
14943ca95b02SDimitry Andric 
14953ca95b02SDimitry Andric   return UnderlyingTypeIndex;
14963ca95b02SDimitry Andric }
14973ca95b02SDimitry Andric 
lowerTypeArray(const DICompositeType * Ty)14983ca95b02SDimitry Andric TypeIndex CodeViewDebug::lowerTypeArray(const DICompositeType *Ty) {
14993ca95b02SDimitry Andric   DITypeRef ElementTypeRef = Ty->getBaseType();
15003ca95b02SDimitry Andric   TypeIndex ElementTypeIndex = getTypeIndex(ElementTypeRef);
15013ca95b02SDimitry Andric   // IndexType is size_t, which depends on the bitness of the target.
15024ba319b5SDimitry Andric   TypeIndex IndexType = getPointerSizeInBytes() == 8
15033ca95b02SDimitry Andric                             ? TypeIndex(SimpleTypeKind::UInt64Quad)
15043ca95b02SDimitry Andric                             : TypeIndex(SimpleTypeKind::UInt32Long);
15053ca95b02SDimitry Andric 
15063ca95b02SDimitry Andric   uint64_t ElementSize = getBaseTypeSize(ElementTypeRef) / 8;
15073ca95b02SDimitry Andric 
15083ca95b02SDimitry Andric   // Add subranges to array type.
15093ca95b02SDimitry Andric   DINodeArray Elements = Ty->getElements();
15103ca95b02SDimitry Andric   for (int i = Elements.size() - 1; i >= 0; --i) {
15113ca95b02SDimitry Andric     const DINode *Element = Elements[i];
15123ca95b02SDimitry Andric     assert(Element->getTag() == dwarf::DW_TAG_subrange_type);
15133ca95b02SDimitry Andric 
15143ca95b02SDimitry Andric     const DISubrange *Subrange = cast<DISubrange>(Element);
15153ca95b02SDimitry Andric     assert(Subrange->getLowerBound() == 0 &&
15163ca95b02SDimitry Andric            "codeview doesn't support subranges with lower bounds");
15174ba319b5SDimitry Andric     int64_t Count = -1;
15184ba319b5SDimitry Andric     if (auto *CI = Subrange->getCount().dyn_cast<ConstantInt*>())
15194ba319b5SDimitry Andric       Count = CI->getSExtValue();
15203ca95b02SDimitry Andric 
15212cab237bSDimitry Andric     // Forward declarations of arrays without a size and VLAs use a count of -1.
15222cab237bSDimitry Andric     // Emit a count of zero in these cases to match what MSVC does for arrays
15232cab237bSDimitry Andric     // without a size. MSVC doesn't support VLAs, so it's not clear what we
15242cab237bSDimitry Andric     // should do for them even if we could distinguish them.
15257a7e6055SDimitry Andric     if (Count == -1)
15262cab237bSDimitry Andric       Count = 0;
15273ca95b02SDimitry Andric 
15283ca95b02SDimitry Andric     // Update the element size and element type index for subsequent subranges.
15293ca95b02SDimitry Andric     ElementSize *= Count;
1530d88c1a5aSDimitry Andric 
1531d88c1a5aSDimitry Andric     // If this is the outermost array, use the size from the array. It will be
15327a7e6055SDimitry Andric     // more accurate if we had a VLA or an incomplete element type size.
1533d88c1a5aSDimitry Andric     uint64_t ArraySize =
1534d88c1a5aSDimitry Andric         (i == 0 && ElementSize == 0) ? Ty->getSizeInBits() / 8 : ElementSize;
1535d88c1a5aSDimitry Andric 
1536d88c1a5aSDimitry Andric     StringRef Name = (i == 0) ? Ty->getName() : "";
1537d88c1a5aSDimitry Andric     ArrayRecord AR(ElementTypeIndex, IndexType, ArraySize, Name);
15382cab237bSDimitry Andric     ElementTypeIndex = TypeTable.writeLeafType(AR);
15393ca95b02SDimitry Andric   }
15403ca95b02SDimitry Andric 
15413ca95b02SDimitry Andric   return ElementTypeIndex;
15423ca95b02SDimitry Andric }
15433ca95b02SDimitry Andric 
lowerTypeBasic(const DIBasicType * Ty)15443ca95b02SDimitry Andric TypeIndex CodeViewDebug::lowerTypeBasic(const DIBasicType *Ty) {
15453ca95b02SDimitry Andric   TypeIndex Index;
15463ca95b02SDimitry Andric   dwarf::TypeKind Kind;
15473ca95b02SDimitry Andric   uint32_t ByteSize;
15483ca95b02SDimitry Andric 
15493ca95b02SDimitry Andric   Kind = static_cast<dwarf::TypeKind>(Ty->getEncoding());
15503ca95b02SDimitry Andric   ByteSize = Ty->getSizeInBits() / 8;
15513ca95b02SDimitry Andric 
15523ca95b02SDimitry Andric   SimpleTypeKind STK = SimpleTypeKind::None;
15533ca95b02SDimitry Andric   switch (Kind) {
15543ca95b02SDimitry Andric   case dwarf::DW_ATE_address:
15553ca95b02SDimitry Andric     // FIXME: Translate
15563ca95b02SDimitry Andric     break;
15573ca95b02SDimitry Andric   case dwarf::DW_ATE_boolean:
15583ca95b02SDimitry Andric     switch (ByteSize) {
15593ca95b02SDimitry Andric     case 1:  STK = SimpleTypeKind::Boolean8;   break;
15603ca95b02SDimitry Andric     case 2:  STK = SimpleTypeKind::Boolean16;  break;
15613ca95b02SDimitry Andric     case 4:  STK = SimpleTypeKind::Boolean32;  break;
15623ca95b02SDimitry Andric     case 8:  STK = SimpleTypeKind::Boolean64;  break;
15633ca95b02SDimitry Andric     case 16: STK = SimpleTypeKind::Boolean128; break;
15643ca95b02SDimitry Andric     }
15653ca95b02SDimitry Andric     break;
15663ca95b02SDimitry Andric   case dwarf::DW_ATE_complex_float:
15673ca95b02SDimitry Andric     switch (ByteSize) {
15683ca95b02SDimitry Andric     case 2:  STK = SimpleTypeKind::Complex16;  break;
15693ca95b02SDimitry Andric     case 4:  STK = SimpleTypeKind::Complex32;  break;
15703ca95b02SDimitry Andric     case 8:  STK = SimpleTypeKind::Complex64;  break;
15713ca95b02SDimitry Andric     case 10: STK = SimpleTypeKind::Complex80;  break;
15723ca95b02SDimitry Andric     case 16: STK = SimpleTypeKind::Complex128; break;
15733ca95b02SDimitry Andric     }
15743ca95b02SDimitry Andric     break;
15753ca95b02SDimitry Andric   case dwarf::DW_ATE_float:
15763ca95b02SDimitry Andric     switch (ByteSize) {
15773ca95b02SDimitry Andric     case 2:  STK = SimpleTypeKind::Float16;  break;
15783ca95b02SDimitry Andric     case 4:  STK = SimpleTypeKind::Float32;  break;
15793ca95b02SDimitry Andric     case 6:  STK = SimpleTypeKind::Float48;  break;
15803ca95b02SDimitry Andric     case 8:  STK = SimpleTypeKind::Float64;  break;
15813ca95b02SDimitry Andric     case 10: STK = SimpleTypeKind::Float80;  break;
15823ca95b02SDimitry Andric     case 16: STK = SimpleTypeKind::Float128; break;
15833ca95b02SDimitry Andric     }
15843ca95b02SDimitry Andric     break;
15853ca95b02SDimitry Andric   case dwarf::DW_ATE_signed:
15863ca95b02SDimitry Andric     switch (ByteSize) {
1587d88c1a5aSDimitry Andric     case 1:  STK = SimpleTypeKind::SignedCharacter; break;
15883ca95b02SDimitry Andric     case 2:  STK = SimpleTypeKind::Int16Short;      break;
15893ca95b02SDimitry Andric     case 4:  STK = SimpleTypeKind::Int32;           break;
15903ca95b02SDimitry Andric     case 8:  STK = SimpleTypeKind::Int64Quad;       break;
15913ca95b02SDimitry Andric     case 16: STK = SimpleTypeKind::Int128Oct;       break;
15923ca95b02SDimitry Andric     }
15933ca95b02SDimitry Andric     break;
15943ca95b02SDimitry Andric   case dwarf::DW_ATE_unsigned:
15953ca95b02SDimitry Andric     switch (ByteSize) {
1596d88c1a5aSDimitry Andric     case 1:  STK = SimpleTypeKind::UnsignedCharacter; break;
15973ca95b02SDimitry Andric     case 2:  STK = SimpleTypeKind::UInt16Short;       break;
15983ca95b02SDimitry Andric     case 4:  STK = SimpleTypeKind::UInt32;            break;
15993ca95b02SDimitry Andric     case 8:  STK = SimpleTypeKind::UInt64Quad;        break;
16003ca95b02SDimitry Andric     case 16: STK = SimpleTypeKind::UInt128Oct;        break;
16013ca95b02SDimitry Andric     }
16023ca95b02SDimitry Andric     break;
16033ca95b02SDimitry Andric   case dwarf::DW_ATE_UTF:
16043ca95b02SDimitry Andric     switch (ByteSize) {
16053ca95b02SDimitry Andric     case 2: STK = SimpleTypeKind::Character16; break;
16063ca95b02SDimitry Andric     case 4: STK = SimpleTypeKind::Character32; break;
16073ca95b02SDimitry Andric     }
16083ca95b02SDimitry Andric     break;
16093ca95b02SDimitry Andric   case dwarf::DW_ATE_signed_char:
16103ca95b02SDimitry Andric     if (ByteSize == 1)
16113ca95b02SDimitry Andric       STK = SimpleTypeKind::SignedCharacter;
16123ca95b02SDimitry Andric     break;
16133ca95b02SDimitry Andric   case dwarf::DW_ATE_unsigned_char:
16143ca95b02SDimitry Andric     if (ByteSize == 1)
16153ca95b02SDimitry Andric       STK = SimpleTypeKind::UnsignedCharacter;
16163ca95b02SDimitry Andric     break;
16173ca95b02SDimitry Andric   default:
16183ca95b02SDimitry Andric     break;
16193ca95b02SDimitry Andric   }
16203ca95b02SDimitry Andric 
16213ca95b02SDimitry Andric   // Apply some fixups based on the source-level type name.
16223ca95b02SDimitry Andric   if (STK == SimpleTypeKind::Int32 && Ty->getName() == "long int")
16233ca95b02SDimitry Andric     STK = SimpleTypeKind::Int32Long;
16243ca95b02SDimitry Andric   if (STK == SimpleTypeKind::UInt32 && Ty->getName() == "long unsigned int")
16253ca95b02SDimitry Andric     STK = SimpleTypeKind::UInt32Long;
16263ca95b02SDimitry Andric   if (STK == SimpleTypeKind::UInt16Short &&
16273ca95b02SDimitry Andric       (Ty->getName() == "wchar_t" || Ty->getName() == "__wchar_t"))
16283ca95b02SDimitry Andric     STK = SimpleTypeKind::WideCharacter;
16293ca95b02SDimitry Andric   if ((STK == SimpleTypeKind::SignedCharacter ||
16303ca95b02SDimitry Andric        STK == SimpleTypeKind::UnsignedCharacter) &&
16313ca95b02SDimitry Andric       Ty->getName() == "char")
16323ca95b02SDimitry Andric     STK = SimpleTypeKind::NarrowCharacter;
16333ca95b02SDimitry Andric 
16343ca95b02SDimitry Andric   return TypeIndex(STK);
16353ca95b02SDimitry Andric }
16363ca95b02SDimitry Andric 
lowerTypePointer(const DIDerivedType * Ty,PointerOptions PO)16374ba319b5SDimitry Andric TypeIndex CodeViewDebug::lowerTypePointer(const DIDerivedType *Ty,
16384ba319b5SDimitry Andric                                           PointerOptions PO) {
16393ca95b02SDimitry Andric   TypeIndex PointeeTI = getTypeIndex(Ty->getBaseType());
16403ca95b02SDimitry Andric 
16414ba319b5SDimitry Andric   // Pointers to simple types without any options can use SimpleTypeMode, rather
16424ba319b5SDimitry Andric   // than having a dedicated pointer type record.
16434ba319b5SDimitry Andric   if (PointeeTI.isSimple() && PO == PointerOptions::None &&
16443ca95b02SDimitry Andric       PointeeTI.getSimpleMode() == SimpleTypeMode::Direct &&
16453ca95b02SDimitry Andric       Ty->getTag() == dwarf::DW_TAG_pointer_type) {
16463ca95b02SDimitry Andric     SimpleTypeMode Mode = Ty->getSizeInBits() == 64
16473ca95b02SDimitry Andric                               ? SimpleTypeMode::NearPointer64
16483ca95b02SDimitry Andric                               : SimpleTypeMode::NearPointer32;
16493ca95b02SDimitry Andric     return TypeIndex(PointeeTI.getSimpleKind(), Mode);
16503ca95b02SDimitry Andric   }
16513ca95b02SDimitry Andric 
16523ca95b02SDimitry Andric   PointerKind PK =
16533ca95b02SDimitry Andric       Ty->getSizeInBits() == 64 ? PointerKind::Near64 : PointerKind::Near32;
16543ca95b02SDimitry Andric   PointerMode PM = PointerMode::Pointer;
16553ca95b02SDimitry Andric   switch (Ty->getTag()) {
16563ca95b02SDimitry Andric   default: llvm_unreachable("not a pointer tag type");
16573ca95b02SDimitry Andric   case dwarf::DW_TAG_pointer_type:
16583ca95b02SDimitry Andric     PM = PointerMode::Pointer;
16593ca95b02SDimitry Andric     break;
16603ca95b02SDimitry Andric   case dwarf::DW_TAG_reference_type:
16613ca95b02SDimitry Andric     PM = PointerMode::LValueReference;
16623ca95b02SDimitry Andric     break;
16633ca95b02SDimitry Andric   case dwarf::DW_TAG_rvalue_reference_type:
16643ca95b02SDimitry Andric     PM = PointerMode::RValueReference;
16653ca95b02SDimitry Andric     break;
16663ca95b02SDimitry Andric   }
16674ba319b5SDimitry Andric 
1668*b5893f02SDimitry Andric   if (Ty->isObjectPointer())
1669*b5893f02SDimitry Andric     PO |= PointerOptions::Const;
1670*b5893f02SDimitry Andric 
16713ca95b02SDimitry Andric   PointerRecord PR(PointeeTI, PK, PM, PO, Ty->getSizeInBits() / 8);
16722cab237bSDimitry Andric   return TypeTable.writeLeafType(PR);
16733ca95b02SDimitry Andric }
16743ca95b02SDimitry Andric 
16753ca95b02SDimitry Andric static PointerToMemberRepresentation
translatePtrToMemberRep(unsigned SizeInBytes,bool IsPMF,unsigned Flags)16763ca95b02SDimitry Andric translatePtrToMemberRep(unsigned SizeInBytes, bool IsPMF, unsigned Flags) {
16773ca95b02SDimitry Andric   // SizeInBytes being zero generally implies that the member pointer type was
16783ca95b02SDimitry Andric   // incomplete, which can happen if it is part of a function prototype. In this
16793ca95b02SDimitry Andric   // case, use the unknown model instead of the general model.
16803ca95b02SDimitry Andric   if (IsPMF) {
16813ca95b02SDimitry Andric     switch (Flags & DINode::FlagPtrToMemberRep) {
16823ca95b02SDimitry Andric     case 0:
16833ca95b02SDimitry Andric       return SizeInBytes == 0 ? PointerToMemberRepresentation::Unknown
16843ca95b02SDimitry Andric                               : PointerToMemberRepresentation::GeneralFunction;
16853ca95b02SDimitry Andric     case DINode::FlagSingleInheritance:
16863ca95b02SDimitry Andric       return PointerToMemberRepresentation::SingleInheritanceFunction;
16873ca95b02SDimitry Andric     case DINode::FlagMultipleInheritance:
16883ca95b02SDimitry Andric       return PointerToMemberRepresentation::MultipleInheritanceFunction;
16893ca95b02SDimitry Andric     case DINode::FlagVirtualInheritance:
16903ca95b02SDimitry Andric       return PointerToMemberRepresentation::VirtualInheritanceFunction;
16913ca95b02SDimitry Andric     }
16923ca95b02SDimitry Andric   } else {
16933ca95b02SDimitry Andric     switch (Flags & DINode::FlagPtrToMemberRep) {
16943ca95b02SDimitry Andric     case 0:
16953ca95b02SDimitry Andric       return SizeInBytes == 0 ? PointerToMemberRepresentation::Unknown
16963ca95b02SDimitry Andric                               : PointerToMemberRepresentation::GeneralData;
16973ca95b02SDimitry Andric     case DINode::FlagSingleInheritance:
16983ca95b02SDimitry Andric       return PointerToMemberRepresentation::SingleInheritanceData;
16993ca95b02SDimitry Andric     case DINode::FlagMultipleInheritance:
17003ca95b02SDimitry Andric       return PointerToMemberRepresentation::MultipleInheritanceData;
17013ca95b02SDimitry Andric     case DINode::FlagVirtualInheritance:
17023ca95b02SDimitry Andric       return PointerToMemberRepresentation::VirtualInheritanceData;
17033ca95b02SDimitry Andric     }
17043ca95b02SDimitry Andric   }
17053ca95b02SDimitry Andric   llvm_unreachable("invalid ptr to member representation");
17063ca95b02SDimitry Andric }
17073ca95b02SDimitry Andric 
lowerTypeMemberPointer(const DIDerivedType * Ty,PointerOptions PO)17084ba319b5SDimitry Andric TypeIndex CodeViewDebug::lowerTypeMemberPointer(const DIDerivedType *Ty,
17094ba319b5SDimitry Andric                                                 PointerOptions PO) {
17103ca95b02SDimitry Andric   assert(Ty->getTag() == dwarf::DW_TAG_ptr_to_member_type);
17113ca95b02SDimitry Andric   TypeIndex ClassTI = getTypeIndex(Ty->getClassType());
17123ca95b02SDimitry Andric   TypeIndex PointeeTI = getTypeIndex(Ty->getBaseType(), Ty->getClassType());
17134ba319b5SDimitry Andric   PointerKind PK = getPointerSizeInBytes() == 8 ? PointerKind::Near64
17143ca95b02SDimitry Andric                                                 : PointerKind::Near32;
17153ca95b02SDimitry Andric   bool IsPMF = isa<DISubroutineType>(Ty->getBaseType());
17163ca95b02SDimitry Andric   PointerMode PM = IsPMF ? PointerMode::PointerToMemberFunction
17173ca95b02SDimitry Andric                          : PointerMode::PointerToDataMember;
17184ba319b5SDimitry Andric 
17193ca95b02SDimitry Andric   assert(Ty->getSizeInBits() / 8 <= 0xff && "pointer size too big");
17203ca95b02SDimitry Andric   uint8_t SizeInBytes = Ty->getSizeInBits() / 8;
17213ca95b02SDimitry Andric   MemberPointerInfo MPI(
17223ca95b02SDimitry Andric       ClassTI, translatePtrToMemberRep(SizeInBytes, IsPMF, Ty->getFlags()));
17233ca95b02SDimitry Andric   PointerRecord PR(PointeeTI, PK, PM, PO, SizeInBytes, MPI);
17242cab237bSDimitry Andric   return TypeTable.writeLeafType(PR);
17253ca95b02SDimitry Andric }
17263ca95b02SDimitry Andric 
17273ca95b02SDimitry Andric /// Given a DWARF calling convention, get the CodeView equivalent. If we don't
17283ca95b02SDimitry Andric /// have a translation, use the NearC convention.
dwarfCCToCodeView(unsigned DwarfCC)17293ca95b02SDimitry Andric static CallingConvention dwarfCCToCodeView(unsigned DwarfCC) {
17303ca95b02SDimitry Andric   switch (DwarfCC) {
17313ca95b02SDimitry Andric   case dwarf::DW_CC_normal:             return CallingConvention::NearC;
17323ca95b02SDimitry Andric   case dwarf::DW_CC_BORLAND_msfastcall: return CallingConvention::NearFast;
17333ca95b02SDimitry Andric   case dwarf::DW_CC_BORLAND_thiscall:   return CallingConvention::ThisCall;
17343ca95b02SDimitry Andric   case dwarf::DW_CC_BORLAND_stdcall:    return CallingConvention::NearStdCall;
17353ca95b02SDimitry Andric   case dwarf::DW_CC_BORLAND_pascal:     return CallingConvention::NearPascal;
17363ca95b02SDimitry Andric   case dwarf::DW_CC_LLVM_vectorcall:    return CallingConvention::NearVector;
17373ca95b02SDimitry Andric   }
17383ca95b02SDimitry Andric   return CallingConvention::NearC;
17393ca95b02SDimitry Andric }
17403ca95b02SDimitry Andric 
lowerTypeModifier(const DIDerivedType * Ty)17413ca95b02SDimitry Andric TypeIndex CodeViewDebug::lowerTypeModifier(const DIDerivedType *Ty) {
17423ca95b02SDimitry Andric   ModifierOptions Mods = ModifierOptions::None;
17434ba319b5SDimitry Andric   PointerOptions PO = PointerOptions::None;
17443ca95b02SDimitry Andric   bool IsModifier = true;
17453ca95b02SDimitry Andric   const DIType *BaseTy = Ty;
17463ca95b02SDimitry Andric   while (IsModifier && BaseTy) {
1747d88c1a5aSDimitry Andric     // FIXME: Need to add DWARF tags for __unaligned and _Atomic
17483ca95b02SDimitry Andric     switch (BaseTy->getTag()) {
17493ca95b02SDimitry Andric     case dwarf::DW_TAG_const_type:
17503ca95b02SDimitry Andric       Mods |= ModifierOptions::Const;
17514ba319b5SDimitry Andric       PO |= PointerOptions::Const;
17523ca95b02SDimitry Andric       break;
17533ca95b02SDimitry Andric     case dwarf::DW_TAG_volatile_type:
17543ca95b02SDimitry Andric       Mods |= ModifierOptions::Volatile;
17554ba319b5SDimitry Andric       PO |= PointerOptions::Volatile;
17564ba319b5SDimitry Andric       break;
17574ba319b5SDimitry Andric     case dwarf::DW_TAG_restrict_type:
17584ba319b5SDimitry Andric       // Only pointer types be marked with __restrict. There is no known flag
17594ba319b5SDimitry Andric       // for __restrict in LF_MODIFIER records.
17604ba319b5SDimitry Andric       PO |= PointerOptions::Restrict;
17613ca95b02SDimitry Andric       break;
17623ca95b02SDimitry Andric     default:
17633ca95b02SDimitry Andric       IsModifier = false;
17643ca95b02SDimitry Andric       break;
17653ca95b02SDimitry Andric     }
17663ca95b02SDimitry Andric     if (IsModifier)
17673ca95b02SDimitry Andric       BaseTy = cast<DIDerivedType>(BaseTy)->getBaseType().resolve();
17683ca95b02SDimitry Andric   }
17694ba319b5SDimitry Andric 
17704ba319b5SDimitry Andric   // Check if the inner type will use an LF_POINTER record. If so, the
17714ba319b5SDimitry Andric   // qualifiers will go in the LF_POINTER record. This comes up for types like
17724ba319b5SDimitry Andric   // 'int *const' and 'int *__restrict', not the more common cases like 'const
17734ba319b5SDimitry Andric   // char *'.
17744ba319b5SDimitry Andric   if (BaseTy) {
17754ba319b5SDimitry Andric     switch (BaseTy->getTag()) {
17764ba319b5SDimitry Andric     case dwarf::DW_TAG_pointer_type:
17774ba319b5SDimitry Andric     case dwarf::DW_TAG_reference_type:
17784ba319b5SDimitry Andric     case dwarf::DW_TAG_rvalue_reference_type:
17794ba319b5SDimitry Andric       return lowerTypePointer(cast<DIDerivedType>(BaseTy), PO);
17804ba319b5SDimitry Andric     case dwarf::DW_TAG_ptr_to_member_type:
17814ba319b5SDimitry Andric       return lowerTypeMemberPointer(cast<DIDerivedType>(BaseTy), PO);
17824ba319b5SDimitry Andric     default:
17834ba319b5SDimitry Andric       break;
17844ba319b5SDimitry Andric     }
17854ba319b5SDimitry Andric   }
17864ba319b5SDimitry Andric 
17873ca95b02SDimitry Andric   TypeIndex ModifiedTI = getTypeIndex(BaseTy);
17884ba319b5SDimitry Andric 
17894ba319b5SDimitry Andric   // Return the base type index if there aren't any modifiers. For example, the
17904ba319b5SDimitry Andric   // metadata could contain restrict wrappers around non-pointer types.
17914ba319b5SDimitry Andric   if (Mods == ModifierOptions::None)
17924ba319b5SDimitry Andric     return ModifiedTI;
17934ba319b5SDimitry Andric 
17943ca95b02SDimitry Andric   ModifierRecord MR(ModifiedTI, Mods);
17952cab237bSDimitry Andric   return TypeTable.writeLeafType(MR);
17963ca95b02SDimitry Andric }
17973ca95b02SDimitry Andric 
lowerTypeFunction(const DISubroutineType * Ty)17983ca95b02SDimitry Andric TypeIndex CodeViewDebug::lowerTypeFunction(const DISubroutineType *Ty) {
17993ca95b02SDimitry Andric   SmallVector<TypeIndex, 8> ReturnAndArgTypeIndices;
18003ca95b02SDimitry Andric   for (DITypeRef ArgTypeRef : Ty->getTypeArray())
18013ca95b02SDimitry Andric     ReturnAndArgTypeIndices.push_back(getTypeIndex(ArgTypeRef));
18023ca95b02SDimitry Andric 
18034ba319b5SDimitry Andric   // MSVC uses type none for variadic argument.
18044ba319b5SDimitry Andric   if (ReturnAndArgTypeIndices.size() > 1 &&
18054ba319b5SDimitry Andric       ReturnAndArgTypeIndices.back() == TypeIndex::Void()) {
18064ba319b5SDimitry Andric     ReturnAndArgTypeIndices.back() = TypeIndex::None();
18074ba319b5SDimitry Andric   }
18083ca95b02SDimitry Andric   TypeIndex ReturnTypeIndex = TypeIndex::Void();
18093ca95b02SDimitry Andric   ArrayRef<TypeIndex> ArgTypeIndices = None;
18103ca95b02SDimitry Andric   if (!ReturnAndArgTypeIndices.empty()) {
18113ca95b02SDimitry Andric     auto ReturnAndArgTypesRef = makeArrayRef(ReturnAndArgTypeIndices);
18123ca95b02SDimitry Andric     ReturnTypeIndex = ReturnAndArgTypesRef.front();
18133ca95b02SDimitry Andric     ArgTypeIndices = ReturnAndArgTypesRef.drop_front();
18143ca95b02SDimitry Andric   }
18153ca95b02SDimitry Andric 
18163ca95b02SDimitry Andric   ArgListRecord ArgListRec(TypeRecordKind::ArgList, ArgTypeIndices);
18172cab237bSDimitry Andric   TypeIndex ArgListIndex = TypeTable.writeLeafType(ArgListRec);
18183ca95b02SDimitry Andric 
18193ca95b02SDimitry Andric   CallingConvention CC = dwarfCCToCodeView(Ty->getCC());
18203ca95b02SDimitry Andric 
1821*b5893f02SDimitry Andric   FunctionOptions FO = getFunctionOptions(Ty);
1822*b5893f02SDimitry Andric   ProcedureRecord Procedure(ReturnTypeIndex, CC, FO, ArgTypeIndices.size(),
1823*b5893f02SDimitry Andric                             ArgListIndex);
18242cab237bSDimitry Andric   return TypeTable.writeLeafType(Procedure);
18253ca95b02SDimitry Andric }
18263ca95b02SDimitry Andric 
lowerTypeMemberFunction(const DISubroutineType * Ty,const DIType * ClassTy,int ThisAdjustment,bool IsStaticMethod,FunctionOptions FO)18273ca95b02SDimitry Andric TypeIndex CodeViewDebug::lowerTypeMemberFunction(const DISubroutineType *Ty,
18283ca95b02SDimitry Andric                                                  const DIType *ClassTy,
18292cab237bSDimitry Andric                                                  int ThisAdjustment,
1830*b5893f02SDimitry Andric                                                  bool IsStaticMethod,
1831*b5893f02SDimitry Andric                                                  FunctionOptions FO) {
18323ca95b02SDimitry Andric   // Lower the containing class type.
18333ca95b02SDimitry Andric   TypeIndex ClassType = getTypeIndex(ClassTy);
18343ca95b02SDimitry Andric 
1835*b5893f02SDimitry Andric   DITypeRefArray ReturnAndArgs = Ty->getTypeArray();
1836*b5893f02SDimitry Andric 
1837*b5893f02SDimitry Andric   unsigned Index = 0;
1838*b5893f02SDimitry Andric   SmallVector<TypeIndex, 8> ArgTypeIndices;
1839*b5893f02SDimitry Andric   TypeIndex ReturnTypeIndex = TypeIndex::Void();
1840*b5893f02SDimitry Andric   if (ReturnAndArgs.size() > Index) {
1841*b5893f02SDimitry Andric     ReturnTypeIndex = getTypeIndex(ReturnAndArgs[Index++]);
1842*b5893f02SDimitry Andric   }
1843*b5893f02SDimitry Andric 
1844*b5893f02SDimitry Andric   // If the first argument is a pointer type and this isn't a static method,
1845*b5893f02SDimitry Andric   // treat it as the special 'this' parameter, which is encoded separately from
1846*b5893f02SDimitry Andric   // the arguments.
1847*b5893f02SDimitry Andric   TypeIndex ThisTypeIndex;
1848*b5893f02SDimitry Andric   if (!IsStaticMethod && ReturnAndArgs.size() > Index) {
1849*b5893f02SDimitry Andric     if (const DIDerivedType *PtrTy =
1850*b5893f02SDimitry Andric             dyn_cast_or_null<DIDerivedType>(ReturnAndArgs[Index].resolve())) {
1851*b5893f02SDimitry Andric       if (PtrTy->getTag() == dwarf::DW_TAG_pointer_type) {
1852*b5893f02SDimitry Andric         ThisTypeIndex = getTypeIndexForThisPtr(PtrTy, Ty);
1853*b5893f02SDimitry Andric         Index++;
1854*b5893f02SDimitry Andric       }
1855*b5893f02SDimitry Andric     }
1856*b5893f02SDimitry Andric   }
1857*b5893f02SDimitry Andric 
1858*b5893f02SDimitry Andric   while (Index < ReturnAndArgs.size())
1859*b5893f02SDimitry Andric     ArgTypeIndices.push_back(getTypeIndex(ReturnAndArgs[Index++]));
18603ca95b02SDimitry Andric 
18614ba319b5SDimitry Andric   // MSVC uses type none for variadic argument.
1862*b5893f02SDimitry Andric   if (!ArgTypeIndices.empty() && ArgTypeIndices.back() == TypeIndex::Void())
1863*b5893f02SDimitry Andric     ArgTypeIndices.back() = TypeIndex::None();
18643ca95b02SDimitry Andric 
18653ca95b02SDimitry Andric   ArgListRecord ArgListRec(TypeRecordKind::ArgList, ArgTypeIndices);
18662cab237bSDimitry Andric   TypeIndex ArgListIndex = TypeTable.writeLeafType(ArgListRec);
18673ca95b02SDimitry Andric 
18683ca95b02SDimitry Andric   CallingConvention CC = dwarfCCToCodeView(Ty->getCC());
18693ca95b02SDimitry Andric 
1870*b5893f02SDimitry Andric   MemberFunctionRecord MFR(ReturnTypeIndex, ClassType, ThisTypeIndex, CC, FO,
1871*b5893f02SDimitry Andric                            ArgTypeIndices.size(), ArgListIndex, ThisAdjustment);
18722cab237bSDimitry Andric   return TypeTable.writeLeafType(MFR);
18733ca95b02SDimitry Andric }
18743ca95b02SDimitry Andric 
lowerTypeVFTableShape(const DIDerivedType * Ty)1875d88c1a5aSDimitry Andric TypeIndex CodeViewDebug::lowerTypeVFTableShape(const DIDerivedType *Ty) {
18766bc11b14SDimitry Andric   unsigned VSlotCount =
18776bc11b14SDimitry Andric       Ty->getSizeInBits() / (8 * Asm->MAI->getCodePointerSize());
1878d88c1a5aSDimitry Andric   SmallVector<VFTableSlotKind, 4> Slots(VSlotCount, VFTableSlotKind::Near);
1879d88c1a5aSDimitry Andric 
1880d88c1a5aSDimitry Andric   VFTableShapeRecord VFTSR(Slots);
18812cab237bSDimitry Andric   return TypeTable.writeLeafType(VFTSR);
1882d88c1a5aSDimitry Andric }
1883d88c1a5aSDimitry Andric 
translateAccessFlags(unsigned RecordTag,unsigned Flags)18843ca95b02SDimitry Andric static MemberAccess translateAccessFlags(unsigned RecordTag, unsigned Flags) {
18853ca95b02SDimitry Andric   switch (Flags & DINode::FlagAccessibility) {
18863ca95b02SDimitry Andric   case DINode::FlagPrivate:   return MemberAccess::Private;
18873ca95b02SDimitry Andric   case DINode::FlagPublic:    return MemberAccess::Public;
18883ca95b02SDimitry Andric   case DINode::FlagProtected: return MemberAccess::Protected;
18893ca95b02SDimitry Andric   case 0:
18903ca95b02SDimitry Andric     // If there was no explicit access control, provide the default for the tag.
18913ca95b02SDimitry Andric     return RecordTag == dwarf::DW_TAG_class_type ? MemberAccess::Private
18923ca95b02SDimitry Andric                                                  : MemberAccess::Public;
18933ca95b02SDimitry Andric   }
18943ca95b02SDimitry Andric   llvm_unreachable("access flags are exclusive");
18953ca95b02SDimitry Andric }
18963ca95b02SDimitry Andric 
translateMethodOptionFlags(const DISubprogram * SP)18973ca95b02SDimitry Andric static MethodOptions translateMethodOptionFlags(const DISubprogram *SP) {
18983ca95b02SDimitry Andric   if (SP->isArtificial())
18993ca95b02SDimitry Andric     return MethodOptions::CompilerGenerated;
19003ca95b02SDimitry Andric 
19013ca95b02SDimitry Andric   // FIXME: Handle other MethodOptions.
19023ca95b02SDimitry Andric 
19033ca95b02SDimitry Andric   return MethodOptions::None;
19043ca95b02SDimitry Andric }
19053ca95b02SDimitry Andric 
translateMethodKindFlags(const DISubprogram * SP,bool Introduced)19063ca95b02SDimitry Andric static MethodKind translateMethodKindFlags(const DISubprogram *SP,
19073ca95b02SDimitry Andric                                            bool Introduced) {
19082cab237bSDimitry Andric   if (SP->getFlags() & DINode::FlagStaticMember)
19092cab237bSDimitry Andric     return MethodKind::Static;
19102cab237bSDimitry Andric 
19113ca95b02SDimitry Andric   switch (SP->getVirtuality()) {
19123ca95b02SDimitry Andric   case dwarf::DW_VIRTUALITY_none:
19133ca95b02SDimitry Andric     break;
19143ca95b02SDimitry Andric   case dwarf::DW_VIRTUALITY_virtual:
19153ca95b02SDimitry Andric     return Introduced ? MethodKind::IntroducingVirtual : MethodKind::Virtual;
19163ca95b02SDimitry Andric   case dwarf::DW_VIRTUALITY_pure_virtual:
19173ca95b02SDimitry Andric     return Introduced ? MethodKind::PureIntroducingVirtual
19183ca95b02SDimitry Andric                       : MethodKind::PureVirtual;
19193ca95b02SDimitry Andric   default:
19203ca95b02SDimitry Andric     llvm_unreachable("unhandled virtuality case");
19213ca95b02SDimitry Andric   }
19223ca95b02SDimitry Andric 
19233ca95b02SDimitry Andric   return MethodKind::Vanilla;
19243ca95b02SDimitry Andric }
19253ca95b02SDimitry Andric 
getRecordKind(const DICompositeType * Ty)19263ca95b02SDimitry Andric static TypeRecordKind getRecordKind(const DICompositeType *Ty) {
19273ca95b02SDimitry Andric   switch (Ty->getTag()) {
19283ca95b02SDimitry Andric   case dwarf::DW_TAG_class_type:     return TypeRecordKind::Class;
19293ca95b02SDimitry Andric   case dwarf::DW_TAG_structure_type: return TypeRecordKind::Struct;
19303ca95b02SDimitry Andric   }
19313ca95b02SDimitry Andric   llvm_unreachable("unexpected tag");
19323ca95b02SDimitry Andric }
19333ca95b02SDimitry Andric 
19343ca95b02SDimitry Andric /// Return ClassOptions that should be present on both the forward declaration
19353ca95b02SDimitry Andric /// and the defintion of a tag type.
getCommonClassOptions(const DICompositeType * Ty)19363ca95b02SDimitry Andric static ClassOptions getCommonClassOptions(const DICompositeType *Ty) {
19373ca95b02SDimitry Andric   ClassOptions CO = ClassOptions::None;
19383ca95b02SDimitry Andric 
19393ca95b02SDimitry Andric   // MSVC always sets this flag, even for local types. Clang doesn't always
19403ca95b02SDimitry Andric   // appear to give every type a linkage name, which may be problematic for us.
19413ca95b02SDimitry Andric   // FIXME: Investigate the consequences of not following them here.
19423ca95b02SDimitry Andric   if (!Ty->getIdentifier().empty())
19433ca95b02SDimitry Andric     CO |= ClassOptions::HasUniqueName;
19443ca95b02SDimitry Andric 
19453ca95b02SDimitry Andric   // Put the Nested flag on a type if it appears immediately inside a tag type.
19463ca95b02SDimitry Andric   // Do not walk the scope chain. Do not attempt to compute ContainsNestedClass
19473ca95b02SDimitry Andric   // here. That flag is only set on definitions, and not forward declarations.
19483ca95b02SDimitry Andric   const DIScope *ImmediateScope = Ty->getScope().resolve();
19493ca95b02SDimitry Andric   if (ImmediateScope && isa<DICompositeType>(ImmediateScope))
19503ca95b02SDimitry Andric     CO |= ClassOptions::Nested;
19513ca95b02SDimitry Andric 
1952*b5893f02SDimitry Andric   // Put the Scoped flag on function-local types. MSVC puts this flag for enum
1953*b5893f02SDimitry Andric   // type only when it has an immediate function scope. Clang never puts enums
1954*b5893f02SDimitry Andric   // inside DILexicalBlock scopes. Enum types, as generated by clang, are
1955*b5893f02SDimitry Andric   // always in function, class, or file scopes.
1956*b5893f02SDimitry Andric   if (Ty->getTag() == dwarf::DW_TAG_enumeration_type) {
1957*b5893f02SDimitry Andric     if (ImmediateScope && isa<DISubprogram>(ImmediateScope))
1958*b5893f02SDimitry Andric       CO |= ClassOptions::Scoped;
1959*b5893f02SDimitry Andric   } else {
19603ca95b02SDimitry Andric     for (const DIScope *Scope = ImmediateScope; Scope != nullptr;
19613ca95b02SDimitry Andric          Scope = Scope->getScope().resolve()) {
19623ca95b02SDimitry Andric       if (isa<DISubprogram>(Scope)) {
19633ca95b02SDimitry Andric         CO |= ClassOptions::Scoped;
19643ca95b02SDimitry Andric         break;
19653ca95b02SDimitry Andric       }
19663ca95b02SDimitry Andric     }
1967*b5893f02SDimitry Andric   }
19683ca95b02SDimitry Andric 
19693ca95b02SDimitry Andric   return CO;
19703ca95b02SDimitry Andric }
19713ca95b02SDimitry Andric 
addUDTSrcLine(const DIType * Ty,TypeIndex TI)19724ba319b5SDimitry Andric void CodeViewDebug::addUDTSrcLine(const DIType *Ty, TypeIndex TI) {
19734ba319b5SDimitry Andric   switch (Ty->getTag()) {
19744ba319b5SDimitry Andric   case dwarf::DW_TAG_class_type:
19754ba319b5SDimitry Andric   case dwarf::DW_TAG_structure_type:
19764ba319b5SDimitry Andric   case dwarf::DW_TAG_union_type:
19774ba319b5SDimitry Andric   case dwarf::DW_TAG_enumeration_type:
19784ba319b5SDimitry Andric     break;
19794ba319b5SDimitry Andric   default:
19804ba319b5SDimitry Andric     return;
19814ba319b5SDimitry Andric   }
19824ba319b5SDimitry Andric 
19834ba319b5SDimitry Andric   if (const auto *File = Ty->getFile()) {
19844ba319b5SDimitry Andric     StringIdRecord SIDR(TypeIndex(0x0), getFullFilepath(File));
19854ba319b5SDimitry Andric     TypeIndex SIDI = TypeTable.writeLeafType(SIDR);
19864ba319b5SDimitry Andric 
19874ba319b5SDimitry Andric     UdtSourceLineRecord USLR(TI, SIDI, Ty->getLine());
19884ba319b5SDimitry Andric     TypeTable.writeLeafType(USLR);
19894ba319b5SDimitry Andric   }
19904ba319b5SDimitry Andric }
19914ba319b5SDimitry Andric 
lowerTypeEnum(const DICompositeType * Ty)19923ca95b02SDimitry Andric TypeIndex CodeViewDebug::lowerTypeEnum(const DICompositeType *Ty) {
19933ca95b02SDimitry Andric   ClassOptions CO = getCommonClassOptions(Ty);
19943ca95b02SDimitry Andric   TypeIndex FTI;
19953ca95b02SDimitry Andric   unsigned EnumeratorCount = 0;
19963ca95b02SDimitry Andric 
19973ca95b02SDimitry Andric   if (Ty->isForwardDecl()) {
19983ca95b02SDimitry Andric     CO |= ClassOptions::ForwardReference;
19993ca95b02SDimitry Andric   } else {
20002cab237bSDimitry Andric     ContinuationRecordBuilder ContinuationBuilder;
20012cab237bSDimitry Andric     ContinuationBuilder.begin(ContinuationRecordKind::FieldList);
20023ca95b02SDimitry Andric     for (const DINode *Element : Ty->getElements()) {
20033ca95b02SDimitry Andric       // We assume that the frontend provides all members in source declaration
20043ca95b02SDimitry Andric       // order, which is what MSVC does.
20053ca95b02SDimitry Andric       if (auto *Enumerator = dyn_cast_or_null<DIEnumerator>(Element)) {
2006d88c1a5aSDimitry Andric         EnumeratorRecord ER(MemberAccess::Public,
2007d88c1a5aSDimitry Andric                             APSInt::getUnsigned(Enumerator->getValue()),
2008d88c1a5aSDimitry Andric                             Enumerator->getName());
20092cab237bSDimitry Andric         ContinuationBuilder.writeMemberType(ER);
20103ca95b02SDimitry Andric         EnumeratorCount++;
20113ca95b02SDimitry Andric       }
20123ca95b02SDimitry Andric     }
20132cab237bSDimitry Andric     FTI = TypeTable.insertRecord(ContinuationBuilder);
20143ca95b02SDimitry Andric   }
20153ca95b02SDimitry Andric 
20163ca95b02SDimitry Andric   std::string FullName = getFullyQualifiedName(Ty);
20173ca95b02SDimitry Andric 
2018d88c1a5aSDimitry Andric   EnumRecord ER(EnumeratorCount, CO, FTI, FullName, Ty->getIdentifier(),
2019d88c1a5aSDimitry Andric                 getTypeIndex(Ty->getBaseType()));
20204ba319b5SDimitry Andric   TypeIndex EnumTI = TypeTable.writeLeafType(ER);
20214ba319b5SDimitry Andric 
20224ba319b5SDimitry Andric   addUDTSrcLine(Ty, EnumTI);
20234ba319b5SDimitry Andric 
20244ba319b5SDimitry Andric   return EnumTI;
20253ca95b02SDimitry Andric }
20263ca95b02SDimitry Andric 
20273ca95b02SDimitry Andric //===----------------------------------------------------------------------===//
20283ca95b02SDimitry Andric // ClassInfo
20293ca95b02SDimitry Andric //===----------------------------------------------------------------------===//
20303ca95b02SDimitry Andric 
20313ca95b02SDimitry Andric struct llvm::ClassInfo {
20323ca95b02SDimitry Andric   struct MemberInfo {
20333ca95b02SDimitry Andric     const DIDerivedType *MemberTypeNode;
20343ca95b02SDimitry Andric     uint64_t BaseOffset;
20353ca95b02SDimitry Andric   };
20363ca95b02SDimitry Andric   // [MemberInfo]
2037db17bf38SDimitry Andric   using MemberList = std::vector<MemberInfo>;
20383ca95b02SDimitry Andric 
2039db17bf38SDimitry Andric   using MethodsList = TinyPtrVector<const DISubprogram *>;
20403ca95b02SDimitry Andric   // MethodName -> MethodsList
2041db17bf38SDimitry Andric   using MethodsMap = MapVector<MDString *, MethodsList>;
20423ca95b02SDimitry Andric 
20433ca95b02SDimitry Andric   /// Base classes.
20443ca95b02SDimitry Andric   std::vector<const DIDerivedType *> Inheritance;
20453ca95b02SDimitry Andric 
20463ca95b02SDimitry Andric   /// Direct members.
20473ca95b02SDimitry Andric   MemberList Members;
20483ca95b02SDimitry Andric   // Direct overloaded methods gathered by name.
20493ca95b02SDimitry Andric   MethodsMap Methods;
20503ca95b02SDimitry Andric 
2051d88c1a5aSDimitry Andric   TypeIndex VShapeTI;
2052d88c1a5aSDimitry Andric 
20532cab237bSDimitry Andric   std::vector<const DIType *> NestedTypes;
20543ca95b02SDimitry Andric };
20553ca95b02SDimitry Andric 
clear()20563ca95b02SDimitry Andric void CodeViewDebug::clear() {
20573ca95b02SDimitry Andric   assert(CurFn == nullptr);
20583ca95b02SDimitry Andric   FileIdMap.clear();
20593ca95b02SDimitry Andric   FnDebugInfo.clear();
20603ca95b02SDimitry Andric   FileToFilepathMap.clear();
20613ca95b02SDimitry Andric   LocalUDTs.clear();
20623ca95b02SDimitry Andric   GlobalUDTs.clear();
20633ca95b02SDimitry Andric   TypeIndices.clear();
20643ca95b02SDimitry Andric   CompleteTypeIndices.clear();
2065*b5893f02SDimitry Andric   ScopeGlobals.clear();
20663ca95b02SDimitry Andric }
20673ca95b02SDimitry Andric 
collectMemberInfo(ClassInfo & Info,const DIDerivedType * DDTy)20683ca95b02SDimitry Andric void CodeViewDebug::collectMemberInfo(ClassInfo &Info,
20693ca95b02SDimitry Andric                                       const DIDerivedType *DDTy) {
20703ca95b02SDimitry Andric   if (!DDTy->getName().empty()) {
20713ca95b02SDimitry Andric     Info.Members.push_back({DDTy, 0});
20723ca95b02SDimitry Andric     return;
20733ca95b02SDimitry Andric   }
20744ba319b5SDimitry Andric 
20754ba319b5SDimitry Andric   // An unnamed member may represent a nested struct or union. Attempt to
20764ba319b5SDimitry Andric   // interpret the unnamed member as a DICompositeType possibly wrapped in
20774ba319b5SDimitry Andric   // qualifier types. Add all the indirect fields to the current record if that
20784ba319b5SDimitry Andric   // succeeds, and drop the member if that fails.
20793ca95b02SDimitry Andric   assert((DDTy->getOffsetInBits() % 8) == 0 && "Unnamed bitfield member!");
20803ca95b02SDimitry Andric   uint64_t Offset = DDTy->getOffsetInBits();
20813ca95b02SDimitry Andric   const DIType *Ty = DDTy->getBaseType().resolve();
20824ba319b5SDimitry Andric   bool FullyResolved = false;
20834ba319b5SDimitry Andric   while (!FullyResolved) {
20844ba319b5SDimitry Andric     switch (Ty->getTag()) {
20854ba319b5SDimitry Andric     case dwarf::DW_TAG_const_type:
20864ba319b5SDimitry Andric     case dwarf::DW_TAG_volatile_type:
20874ba319b5SDimitry Andric       // FIXME: we should apply the qualifier types to the indirect fields
20884ba319b5SDimitry Andric       // rather than dropping them.
20894ba319b5SDimitry Andric       Ty = cast<DIDerivedType>(Ty)->getBaseType().resolve();
20904ba319b5SDimitry Andric       break;
20914ba319b5SDimitry Andric     default:
20924ba319b5SDimitry Andric       FullyResolved = true;
20934ba319b5SDimitry Andric       break;
20944ba319b5SDimitry Andric     }
20954ba319b5SDimitry Andric   }
20964ba319b5SDimitry Andric 
20974ba319b5SDimitry Andric   const DICompositeType *DCTy = dyn_cast<DICompositeType>(Ty);
20984ba319b5SDimitry Andric   if (!DCTy)
20994ba319b5SDimitry Andric     return;
21004ba319b5SDimitry Andric 
21013ca95b02SDimitry Andric   ClassInfo NestedInfo = collectClassInfo(DCTy);
21023ca95b02SDimitry Andric   for (const ClassInfo::MemberInfo &IndirectField : NestedInfo.Members)
21033ca95b02SDimitry Andric     Info.Members.push_back(
21043ca95b02SDimitry Andric         {IndirectField.MemberTypeNode, IndirectField.BaseOffset + Offset});
21053ca95b02SDimitry Andric }
21063ca95b02SDimitry Andric 
collectClassInfo(const DICompositeType * Ty)21073ca95b02SDimitry Andric ClassInfo CodeViewDebug::collectClassInfo(const DICompositeType *Ty) {
21083ca95b02SDimitry Andric   ClassInfo Info;
21093ca95b02SDimitry Andric   // Add elements to structure type.
21103ca95b02SDimitry Andric   DINodeArray Elements = Ty->getElements();
21113ca95b02SDimitry Andric   for (auto *Element : Elements) {
21123ca95b02SDimitry Andric     // We assume that the frontend provides all members in source declaration
21133ca95b02SDimitry Andric     // order, which is what MSVC does.
21143ca95b02SDimitry Andric     if (!Element)
21153ca95b02SDimitry Andric       continue;
21163ca95b02SDimitry Andric     if (auto *SP = dyn_cast<DISubprogram>(Element)) {
21173ca95b02SDimitry Andric       Info.Methods[SP->getRawName()].push_back(SP);
21183ca95b02SDimitry Andric     } else if (auto *DDTy = dyn_cast<DIDerivedType>(Element)) {
21193ca95b02SDimitry Andric       if (DDTy->getTag() == dwarf::DW_TAG_member) {
21203ca95b02SDimitry Andric         collectMemberInfo(Info, DDTy);
21213ca95b02SDimitry Andric       } else if (DDTy->getTag() == dwarf::DW_TAG_inheritance) {
21223ca95b02SDimitry Andric         Info.Inheritance.push_back(DDTy);
2123d88c1a5aSDimitry Andric       } else if (DDTy->getTag() == dwarf::DW_TAG_pointer_type &&
2124d88c1a5aSDimitry Andric                  DDTy->getName() == "__vtbl_ptr_type") {
2125d88c1a5aSDimitry Andric         Info.VShapeTI = getTypeIndex(DDTy);
21262cab237bSDimitry Andric       } else if (DDTy->getTag() == dwarf::DW_TAG_typedef) {
21272cab237bSDimitry Andric         Info.NestedTypes.push_back(DDTy);
21283ca95b02SDimitry Andric       } else if (DDTy->getTag() == dwarf::DW_TAG_friend) {
21293ca95b02SDimitry Andric         // Ignore friend members. It appears that MSVC emitted info about
21303ca95b02SDimitry Andric         // friends in the past, but modern versions do not.
21313ca95b02SDimitry Andric       }
21323ca95b02SDimitry Andric     } else if (auto *Composite = dyn_cast<DICompositeType>(Element)) {
21332cab237bSDimitry Andric       Info.NestedTypes.push_back(Composite);
21343ca95b02SDimitry Andric     }
21353ca95b02SDimitry Andric     // Skip other unrecognized kinds of elements.
21363ca95b02SDimitry Andric   }
21373ca95b02SDimitry Andric   return Info;
21383ca95b02SDimitry Andric }
21393ca95b02SDimitry Andric 
shouldAlwaysEmitCompleteClassType(const DICompositeType * Ty)21404ba319b5SDimitry Andric static bool shouldAlwaysEmitCompleteClassType(const DICompositeType *Ty) {
21414ba319b5SDimitry Andric   // This routine is used by lowerTypeClass and lowerTypeUnion to determine
21424ba319b5SDimitry Andric   // if a complete type should be emitted instead of a forward reference.
21434ba319b5SDimitry Andric   return Ty->getName().empty() && Ty->getIdentifier().empty() &&
21444ba319b5SDimitry Andric       !Ty->isForwardDecl();
21454ba319b5SDimitry Andric }
21464ba319b5SDimitry Andric 
lowerTypeClass(const DICompositeType * Ty)21473ca95b02SDimitry Andric TypeIndex CodeViewDebug::lowerTypeClass(const DICompositeType *Ty) {
21484ba319b5SDimitry Andric   // Emit the complete type for unnamed structs.  C++ classes with methods
21494ba319b5SDimitry Andric   // which have a circular reference back to the class type are expected to
21504ba319b5SDimitry Andric   // be named by the front-end and should not be "unnamed".  C unnamed
21514ba319b5SDimitry Andric   // structs should not have circular references.
21524ba319b5SDimitry Andric   if (shouldAlwaysEmitCompleteClassType(Ty)) {
21534ba319b5SDimitry Andric     // If this unnamed complete type is already in the process of being defined
21544ba319b5SDimitry Andric     // then the description of the type is malformed and cannot be emitted
21554ba319b5SDimitry Andric     // into CodeView correctly so report a fatal error.
21564ba319b5SDimitry Andric     auto I = CompleteTypeIndices.find(Ty);
21574ba319b5SDimitry Andric     if (I != CompleteTypeIndices.end() && I->second == TypeIndex())
21584ba319b5SDimitry Andric       report_fatal_error("cannot debug circular reference to unnamed type");
21594ba319b5SDimitry Andric     return getCompleteTypeIndex(Ty);
21604ba319b5SDimitry Andric   }
21614ba319b5SDimitry Andric 
21623ca95b02SDimitry Andric   // First, construct the forward decl.  Don't look into Ty to compute the
21633ca95b02SDimitry Andric   // forward decl options, since it might not be available in all TUs.
21643ca95b02SDimitry Andric   TypeRecordKind Kind = getRecordKind(Ty);
21653ca95b02SDimitry Andric   ClassOptions CO =
21663ca95b02SDimitry Andric       ClassOptions::ForwardReference | getCommonClassOptions(Ty);
21673ca95b02SDimitry Andric   std::string FullName = getFullyQualifiedName(Ty);
2168d88c1a5aSDimitry Andric   ClassRecord CR(Kind, 0, CO, TypeIndex(), TypeIndex(), TypeIndex(), 0,
2169d88c1a5aSDimitry Andric                  FullName, Ty->getIdentifier());
21702cab237bSDimitry Andric   TypeIndex FwdDeclTI = TypeTable.writeLeafType(CR);
21713ca95b02SDimitry Andric   if (!Ty->isForwardDecl())
21723ca95b02SDimitry Andric     DeferredCompleteTypes.push_back(Ty);
21733ca95b02SDimitry Andric   return FwdDeclTI;
21743ca95b02SDimitry Andric }
21753ca95b02SDimitry Andric 
lowerCompleteTypeClass(const DICompositeType * Ty)21763ca95b02SDimitry Andric TypeIndex CodeViewDebug::lowerCompleteTypeClass(const DICompositeType *Ty) {
21773ca95b02SDimitry Andric   // Construct the field list and complete type record.
21783ca95b02SDimitry Andric   TypeRecordKind Kind = getRecordKind(Ty);
21793ca95b02SDimitry Andric   ClassOptions CO = getCommonClassOptions(Ty);
21803ca95b02SDimitry Andric   TypeIndex FieldTI;
21813ca95b02SDimitry Andric   TypeIndex VShapeTI;
21823ca95b02SDimitry Andric   unsigned FieldCount;
21833ca95b02SDimitry Andric   bool ContainsNestedClass;
21843ca95b02SDimitry Andric   std::tie(FieldTI, VShapeTI, FieldCount, ContainsNestedClass) =
21853ca95b02SDimitry Andric       lowerRecordFieldList(Ty);
21863ca95b02SDimitry Andric 
21873ca95b02SDimitry Andric   if (ContainsNestedClass)
21883ca95b02SDimitry Andric     CO |= ClassOptions::ContainsNestedClass;
21893ca95b02SDimitry Andric 
21903ca95b02SDimitry Andric   std::string FullName = getFullyQualifiedName(Ty);
21913ca95b02SDimitry Andric 
21923ca95b02SDimitry Andric   uint64_t SizeInBytes = Ty->getSizeInBits() / 8;
21933ca95b02SDimitry Andric 
2194d88c1a5aSDimitry Andric   ClassRecord CR(Kind, FieldCount, CO, FieldTI, TypeIndex(), VShapeTI,
2195d88c1a5aSDimitry Andric                  SizeInBytes, FullName, Ty->getIdentifier());
21962cab237bSDimitry Andric   TypeIndex ClassTI = TypeTable.writeLeafType(CR);
21973ca95b02SDimitry Andric 
21984ba319b5SDimitry Andric   addUDTSrcLine(Ty, ClassTI);
21993ca95b02SDimitry Andric 
22002cab237bSDimitry Andric   addToUDTs(Ty);
22013ca95b02SDimitry Andric 
22023ca95b02SDimitry Andric   return ClassTI;
22033ca95b02SDimitry Andric }
22043ca95b02SDimitry Andric 
lowerTypeUnion(const DICompositeType * Ty)22053ca95b02SDimitry Andric TypeIndex CodeViewDebug::lowerTypeUnion(const DICompositeType *Ty) {
22064ba319b5SDimitry Andric   // Emit the complete type for unnamed unions.
22074ba319b5SDimitry Andric   if (shouldAlwaysEmitCompleteClassType(Ty))
22084ba319b5SDimitry Andric     return getCompleteTypeIndex(Ty);
22094ba319b5SDimitry Andric 
22103ca95b02SDimitry Andric   ClassOptions CO =
22113ca95b02SDimitry Andric       ClassOptions::ForwardReference | getCommonClassOptions(Ty);
22123ca95b02SDimitry Andric   std::string FullName = getFullyQualifiedName(Ty);
2213d88c1a5aSDimitry Andric   UnionRecord UR(0, CO, TypeIndex(), 0, FullName, Ty->getIdentifier());
22142cab237bSDimitry Andric   TypeIndex FwdDeclTI = TypeTable.writeLeafType(UR);
22153ca95b02SDimitry Andric   if (!Ty->isForwardDecl())
22163ca95b02SDimitry Andric     DeferredCompleteTypes.push_back(Ty);
22173ca95b02SDimitry Andric   return FwdDeclTI;
22183ca95b02SDimitry Andric }
22193ca95b02SDimitry Andric 
lowerCompleteTypeUnion(const DICompositeType * Ty)22203ca95b02SDimitry Andric TypeIndex CodeViewDebug::lowerCompleteTypeUnion(const DICompositeType *Ty) {
22213ca95b02SDimitry Andric   ClassOptions CO = ClassOptions::Sealed | getCommonClassOptions(Ty);
22223ca95b02SDimitry Andric   TypeIndex FieldTI;
22233ca95b02SDimitry Andric   unsigned FieldCount;
22243ca95b02SDimitry Andric   bool ContainsNestedClass;
22253ca95b02SDimitry Andric   std::tie(FieldTI, std::ignore, FieldCount, ContainsNestedClass) =
22263ca95b02SDimitry Andric       lowerRecordFieldList(Ty);
22273ca95b02SDimitry Andric 
22283ca95b02SDimitry Andric   if (ContainsNestedClass)
22293ca95b02SDimitry Andric     CO |= ClassOptions::ContainsNestedClass;
22303ca95b02SDimitry Andric 
22313ca95b02SDimitry Andric   uint64_t SizeInBytes = Ty->getSizeInBits() / 8;
22323ca95b02SDimitry Andric   std::string FullName = getFullyQualifiedName(Ty);
22333ca95b02SDimitry Andric 
2234d88c1a5aSDimitry Andric   UnionRecord UR(FieldCount, CO, FieldTI, SizeInBytes, FullName,
2235d88c1a5aSDimitry Andric                  Ty->getIdentifier());
22362cab237bSDimitry Andric   TypeIndex UnionTI = TypeTable.writeLeafType(UR);
22373ca95b02SDimitry Andric 
22384ba319b5SDimitry Andric   addUDTSrcLine(Ty, UnionTI);
22392cab237bSDimitry Andric 
22402cab237bSDimitry Andric   addToUDTs(Ty);
22413ca95b02SDimitry Andric 
22423ca95b02SDimitry Andric   return UnionTI;
22433ca95b02SDimitry Andric }
22443ca95b02SDimitry Andric 
22453ca95b02SDimitry Andric std::tuple<TypeIndex, TypeIndex, unsigned, bool>
lowerRecordFieldList(const DICompositeType * Ty)22463ca95b02SDimitry Andric CodeViewDebug::lowerRecordFieldList(const DICompositeType *Ty) {
22473ca95b02SDimitry Andric   // Manually count members. MSVC appears to count everything that generates a
22483ca95b02SDimitry Andric   // field list record. Each individual overload in a method overload group
22493ca95b02SDimitry Andric   // contributes to this count, even though the overload group is a single field
22503ca95b02SDimitry Andric   // list record.
22513ca95b02SDimitry Andric   unsigned MemberCount = 0;
22523ca95b02SDimitry Andric   ClassInfo Info = collectClassInfo(Ty);
22532cab237bSDimitry Andric   ContinuationRecordBuilder ContinuationBuilder;
22542cab237bSDimitry Andric   ContinuationBuilder.begin(ContinuationRecordKind::FieldList);
22553ca95b02SDimitry Andric 
22563ca95b02SDimitry Andric   // Create base classes.
22573ca95b02SDimitry Andric   for (const DIDerivedType *I : Info.Inheritance) {
22583ca95b02SDimitry Andric     if (I->getFlags() & DINode::FlagVirtual) {
22593ca95b02SDimitry Andric       // Virtual base.
22604ba319b5SDimitry Andric       unsigned VBPtrOffset = I->getVBPtrOffset();
22613ca95b02SDimitry Andric       // FIXME: Despite the accessor name, the offset is really in bytes.
22623ca95b02SDimitry Andric       unsigned VBTableIndex = I->getOffsetInBits() / 4;
2263d88c1a5aSDimitry Andric       auto RecordKind = (I->getFlags() & DINode::FlagIndirectVirtualBase) == DINode::FlagIndirectVirtualBase
2264d88c1a5aSDimitry Andric                             ? TypeRecordKind::IndirectVirtualBaseClass
2265d88c1a5aSDimitry Andric                             : TypeRecordKind::VirtualBaseClass;
2266d88c1a5aSDimitry Andric       VirtualBaseClassRecord VBCR(
2267d88c1a5aSDimitry Andric           RecordKind, translateAccessFlags(Ty->getTag(), I->getFlags()),
22683ca95b02SDimitry Andric           getTypeIndex(I->getBaseType()), getVBPTypeIndex(), VBPtrOffset,
2269d88c1a5aSDimitry Andric           VBTableIndex);
2270d88c1a5aSDimitry Andric 
22712cab237bSDimitry Andric       ContinuationBuilder.writeMemberType(VBCR);
22724ba319b5SDimitry Andric       MemberCount++;
22733ca95b02SDimitry Andric     } else {
22743ca95b02SDimitry Andric       assert(I->getOffsetInBits() % 8 == 0 &&
22753ca95b02SDimitry Andric              "bases must be on byte boundaries");
2276d88c1a5aSDimitry Andric       BaseClassRecord BCR(translateAccessFlags(Ty->getTag(), I->getFlags()),
2277d88c1a5aSDimitry Andric                           getTypeIndex(I->getBaseType()),
2278d88c1a5aSDimitry Andric                           I->getOffsetInBits() / 8);
22792cab237bSDimitry Andric       ContinuationBuilder.writeMemberType(BCR);
22804ba319b5SDimitry Andric       MemberCount++;
22813ca95b02SDimitry Andric     }
22823ca95b02SDimitry Andric   }
22833ca95b02SDimitry Andric 
22843ca95b02SDimitry Andric   // Create members.
22853ca95b02SDimitry Andric   for (ClassInfo::MemberInfo &MemberInfo : Info.Members) {
22863ca95b02SDimitry Andric     const DIDerivedType *Member = MemberInfo.MemberTypeNode;
22873ca95b02SDimitry Andric     TypeIndex MemberBaseType = getTypeIndex(Member->getBaseType());
22883ca95b02SDimitry Andric     StringRef MemberName = Member->getName();
22893ca95b02SDimitry Andric     MemberAccess Access =
22903ca95b02SDimitry Andric         translateAccessFlags(Ty->getTag(), Member->getFlags());
22913ca95b02SDimitry Andric 
22923ca95b02SDimitry Andric     if (Member->isStaticMember()) {
2293d88c1a5aSDimitry Andric       StaticDataMemberRecord SDMR(Access, MemberBaseType, MemberName);
22942cab237bSDimitry Andric       ContinuationBuilder.writeMemberType(SDMR);
2295d88c1a5aSDimitry Andric       MemberCount++;
2296d88c1a5aSDimitry Andric       continue;
2297d88c1a5aSDimitry Andric     }
2298d88c1a5aSDimitry Andric 
2299d88c1a5aSDimitry Andric     // Virtual function pointer member.
2300d88c1a5aSDimitry Andric     if ((Member->getFlags() & DINode::FlagArtificial) &&
2301d88c1a5aSDimitry Andric         Member->getName().startswith("_vptr$")) {
2302d88c1a5aSDimitry Andric       VFPtrRecord VFPR(getTypeIndex(Member->getBaseType()));
23032cab237bSDimitry Andric       ContinuationBuilder.writeMemberType(VFPR);
23043ca95b02SDimitry Andric       MemberCount++;
23053ca95b02SDimitry Andric       continue;
23063ca95b02SDimitry Andric     }
23073ca95b02SDimitry Andric 
23083ca95b02SDimitry Andric     // Data member.
23093ca95b02SDimitry Andric     uint64_t MemberOffsetInBits =
23103ca95b02SDimitry Andric         Member->getOffsetInBits() + MemberInfo.BaseOffset;
23113ca95b02SDimitry Andric     if (Member->isBitField()) {
23123ca95b02SDimitry Andric       uint64_t StartBitOffset = MemberOffsetInBits;
23133ca95b02SDimitry Andric       if (const auto *CI =
23143ca95b02SDimitry Andric               dyn_cast_or_null<ConstantInt>(Member->getStorageOffsetInBits())) {
23153ca95b02SDimitry Andric         MemberOffsetInBits = CI->getZExtValue() + MemberInfo.BaseOffset;
23163ca95b02SDimitry Andric       }
23173ca95b02SDimitry Andric       StartBitOffset -= MemberOffsetInBits;
2318d88c1a5aSDimitry Andric       BitFieldRecord BFR(MemberBaseType, Member->getSizeInBits(),
2319d88c1a5aSDimitry Andric                          StartBitOffset);
23202cab237bSDimitry Andric       MemberBaseType = TypeTable.writeLeafType(BFR);
23213ca95b02SDimitry Andric     }
23223ca95b02SDimitry Andric     uint64_t MemberOffsetInBytes = MemberOffsetInBits / 8;
2323d88c1a5aSDimitry Andric     DataMemberRecord DMR(Access, MemberBaseType, MemberOffsetInBytes,
2324d88c1a5aSDimitry Andric                          MemberName);
23252cab237bSDimitry Andric     ContinuationBuilder.writeMemberType(DMR);
23263ca95b02SDimitry Andric     MemberCount++;
23273ca95b02SDimitry Andric   }
23283ca95b02SDimitry Andric 
23293ca95b02SDimitry Andric   // Create methods
23303ca95b02SDimitry Andric   for (auto &MethodItr : Info.Methods) {
23313ca95b02SDimitry Andric     StringRef Name = MethodItr.first->getString();
23323ca95b02SDimitry Andric 
23333ca95b02SDimitry Andric     std::vector<OneMethodRecord> Methods;
23343ca95b02SDimitry Andric     for (const DISubprogram *SP : MethodItr.second) {
23353ca95b02SDimitry Andric       TypeIndex MethodType = getMemberFunctionType(SP, Ty);
23363ca95b02SDimitry Andric       bool Introduced = SP->getFlags() & DINode::FlagIntroducedVirtual;
23373ca95b02SDimitry Andric 
23383ca95b02SDimitry Andric       unsigned VFTableOffset = -1;
23393ca95b02SDimitry Andric       if (Introduced)
23403ca95b02SDimitry Andric         VFTableOffset = SP->getVirtualIndex() * getPointerSizeInBytes();
23413ca95b02SDimitry Andric 
2342d88c1a5aSDimitry Andric       Methods.push_back(OneMethodRecord(
2343d88c1a5aSDimitry Andric           MethodType, translateAccessFlags(Ty->getTag(), SP->getFlags()),
2344d88c1a5aSDimitry Andric           translateMethodKindFlags(SP, Introduced),
2345d88c1a5aSDimitry Andric           translateMethodOptionFlags(SP), VFTableOffset, Name));
23463ca95b02SDimitry Andric       MemberCount++;
23473ca95b02SDimitry Andric     }
2348db17bf38SDimitry Andric     assert(!Methods.empty() && "Empty methods map entry");
23493ca95b02SDimitry Andric     if (Methods.size() == 1)
23502cab237bSDimitry Andric       ContinuationBuilder.writeMemberType(Methods[0]);
23513ca95b02SDimitry Andric     else {
23522cab237bSDimitry Andric       // FIXME: Make this use its own ContinuationBuilder so that
23532cab237bSDimitry Andric       // MethodOverloadList can be split correctly.
2354d88c1a5aSDimitry Andric       MethodOverloadListRecord MOLR(Methods);
23552cab237bSDimitry Andric       TypeIndex MethodList = TypeTable.writeLeafType(MOLR);
23562cab237bSDimitry Andric 
2357d88c1a5aSDimitry Andric       OverloadedMethodRecord OMR(Methods.size(), MethodList, Name);
23582cab237bSDimitry Andric       ContinuationBuilder.writeMemberType(OMR);
23593ca95b02SDimitry Andric     }
23603ca95b02SDimitry Andric   }
23613ca95b02SDimitry Andric 
23623ca95b02SDimitry Andric   // Create nested classes.
23632cab237bSDimitry Andric   for (const DIType *Nested : Info.NestedTypes) {
23643ca95b02SDimitry Andric     NestedTypeRecord R(getTypeIndex(DITypeRef(Nested)), Nested->getName());
23652cab237bSDimitry Andric     ContinuationBuilder.writeMemberType(R);
23663ca95b02SDimitry Andric     MemberCount++;
23673ca95b02SDimitry Andric   }
23683ca95b02SDimitry Andric 
23692cab237bSDimitry Andric   TypeIndex FieldTI = TypeTable.insertRecord(ContinuationBuilder);
2370d88c1a5aSDimitry Andric   return std::make_tuple(FieldTI, Info.VShapeTI, MemberCount,
23712cab237bSDimitry Andric                          !Info.NestedTypes.empty());
23723ca95b02SDimitry Andric }
23733ca95b02SDimitry Andric 
getVBPTypeIndex()23743ca95b02SDimitry Andric TypeIndex CodeViewDebug::getVBPTypeIndex() {
23753ca95b02SDimitry Andric   if (!VBPType.getIndex()) {
23763ca95b02SDimitry Andric     // Make a 'const int *' type.
23773ca95b02SDimitry Andric     ModifierRecord MR(TypeIndex::Int32(), ModifierOptions::Const);
23782cab237bSDimitry Andric     TypeIndex ModifiedTI = TypeTable.writeLeafType(MR);
23793ca95b02SDimitry Andric 
23803ca95b02SDimitry Andric     PointerKind PK = getPointerSizeInBytes() == 8 ? PointerKind::Near64
23813ca95b02SDimitry Andric                                                   : PointerKind::Near32;
23823ca95b02SDimitry Andric     PointerMode PM = PointerMode::Pointer;
23833ca95b02SDimitry Andric     PointerOptions PO = PointerOptions::None;
23843ca95b02SDimitry Andric     PointerRecord PR(ModifiedTI, PK, PM, PO, getPointerSizeInBytes());
23852cab237bSDimitry Andric     VBPType = TypeTable.writeLeafType(PR);
23863ca95b02SDimitry Andric   }
23873ca95b02SDimitry Andric 
23883ca95b02SDimitry Andric   return VBPType;
23893ca95b02SDimitry Andric }
23903ca95b02SDimitry Andric 
getTypeIndex(DITypeRef TypeRef,DITypeRef ClassTyRef)23913ca95b02SDimitry Andric TypeIndex CodeViewDebug::getTypeIndex(DITypeRef TypeRef, DITypeRef ClassTyRef) {
23923ca95b02SDimitry Andric   const DIType *Ty = TypeRef.resolve();
23933ca95b02SDimitry Andric   const DIType *ClassTy = ClassTyRef.resolve();
23943ca95b02SDimitry Andric 
23953ca95b02SDimitry Andric   // The null DIType is the void type. Don't try to hash it.
23963ca95b02SDimitry Andric   if (!Ty)
23973ca95b02SDimitry Andric     return TypeIndex::Void();
23983ca95b02SDimitry Andric 
23993ca95b02SDimitry Andric   // Check if we've already translated this type. Don't try to do a
24003ca95b02SDimitry Andric   // get-or-create style insertion that caches the hash lookup across the
24013ca95b02SDimitry Andric   // lowerType call. It will update the TypeIndices map.
24023ca95b02SDimitry Andric   auto I = TypeIndices.find({Ty, ClassTy});
24033ca95b02SDimitry Andric   if (I != TypeIndices.end())
24043ca95b02SDimitry Andric     return I->second;
24053ca95b02SDimitry Andric 
24063ca95b02SDimitry Andric   TypeLoweringScope S(*this);
24073ca95b02SDimitry Andric   TypeIndex TI = lowerType(Ty, ClassTy);
24083ca95b02SDimitry Andric   return recordTypeIndexForDINode(Ty, TI, ClassTy);
24093ca95b02SDimitry Andric }
24103ca95b02SDimitry Andric 
2411*b5893f02SDimitry Andric codeview::TypeIndex
getTypeIndexForThisPtr(const DIDerivedType * PtrTy,const DISubroutineType * SubroutineTy)2412*b5893f02SDimitry Andric CodeViewDebug::getTypeIndexForThisPtr(const DIDerivedType *PtrTy,
2413*b5893f02SDimitry Andric                                       const DISubroutineType *SubroutineTy) {
2414*b5893f02SDimitry Andric   assert(PtrTy->getTag() == dwarf::DW_TAG_pointer_type &&
2415*b5893f02SDimitry Andric          "this type must be a pointer type");
2416*b5893f02SDimitry Andric 
2417*b5893f02SDimitry Andric   PointerOptions Options = PointerOptions::None;
2418*b5893f02SDimitry Andric   if (SubroutineTy->getFlags() & DINode::DIFlags::FlagLValueReference)
2419*b5893f02SDimitry Andric     Options = PointerOptions::LValueRefThisPointer;
2420*b5893f02SDimitry Andric   else if (SubroutineTy->getFlags() & DINode::DIFlags::FlagRValueReference)
2421*b5893f02SDimitry Andric     Options = PointerOptions::RValueRefThisPointer;
2422*b5893f02SDimitry Andric 
2423*b5893f02SDimitry Andric   // Check if we've already translated this type.  If there is no ref qualifier
2424*b5893f02SDimitry Andric   // on the function then we look up this pointer type with no associated class
2425*b5893f02SDimitry Andric   // so that the TypeIndex for the this pointer can be shared with the type
2426*b5893f02SDimitry Andric   // index for other pointers to this class type.  If there is a ref qualifier
2427*b5893f02SDimitry Andric   // then we lookup the pointer using the subroutine as the parent type.
2428*b5893f02SDimitry Andric   auto I = TypeIndices.find({PtrTy, SubroutineTy});
2429*b5893f02SDimitry Andric   if (I != TypeIndices.end())
2430*b5893f02SDimitry Andric     return I->second;
2431*b5893f02SDimitry Andric 
2432*b5893f02SDimitry Andric   TypeLoweringScope S(*this);
2433*b5893f02SDimitry Andric   TypeIndex TI = lowerTypePointer(PtrTy, Options);
2434*b5893f02SDimitry Andric   return recordTypeIndexForDINode(PtrTy, TI, SubroutineTy);
2435*b5893f02SDimitry Andric }
2436*b5893f02SDimitry Andric 
getTypeIndexForReferenceTo(DITypeRef TypeRef)24372cab237bSDimitry Andric TypeIndex CodeViewDebug::getTypeIndexForReferenceTo(DITypeRef TypeRef) {
24382cab237bSDimitry Andric   DIType *Ty = TypeRef.resolve();
24392cab237bSDimitry Andric   PointerRecord PR(getTypeIndex(Ty),
24402cab237bSDimitry Andric                    getPointerSizeInBytes() == 8 ? PointerKind::Near64
24412cab237bSDimitry Andric                                                 : PointerKind::Near32,
24422cab237bSDimitry Andric                    PointerMode::LValueReference, PointerOptions::None,
24432cab237bSDimitry Andric                    Ty->getSizeInBits() / 8);
24442cab237bSDimitry Andric   return TypeTable.writeLeafType(PR);
24452cab237bSDimitry Andric }
24462cab237bSDimitry Andric 
getCompleteTypeIndex(DITypeRef TypeRef)24473ca95b02SDimitry Andric TypeIndex CodeViewDebug::getCompleteTypeIndex(DITypeRef TypeRef) {
24483ca95b02SDimitry Andric   const DIType *Ty = TypeRef.resolve();
24493ca95b02SDimitry Andric 
24503ca95b02SDimitry Andric   // The null DIType is the void type. Don't try to hash it.
24513ca95b02SDimitry Andric   if (!Ty)
24523ca95b02SDimitry Andric     return TypeIndex::Void();
24533ca95b02SDimitry Andric 
2454*b5893f02SDimitry Andric   // Look through typedefs when getting the complete type index. Call
2455*b5893f02SDimitry Andric   // getTypeIndex on the typdef to ensure that any UDTs are accumulated and are
2456*b5893f02SDimitry Andric   // emitted only once.
2457*b5893f02SDimitry Andric   if (Ty->getTag() == dwarf::DW_TAG_typedef)
2458*b5893f02SDimitry Andric     (void)getTypeIndex(Ty);
2459*b5893f02SDimitry Andric   while (Ty->getTag() == dwarf::DW_TAG_typedef)
2460*b5893f02SDimitry Andric     Ty = cast<DIDerivedType>(Ty)->getBaseType().resolve();
2461*b5893f02SDimitry Andric 
24623ca95b02SDimitry Andric   // If this is a non-record type, the complete type index is the same as the
24633ca95b02SDimitry Andric   // normal type index. Just call getTypeIndex.
24643ca95b02SDimitry Andric   switch (Ty->getTag()) {
24653ca95b02SDimitry Andric   case dwarf::DW_TAG_class_type:
24663ca95b02SDimitry Andric   case dwarf::DW_TAG_structure_type:
24673ca95b02SDimitry Andric   case dwarf::DW_TAG_union_type:
24683ca95b02SDimitry Andric     break;
24693ca95b02SDimitry Andric   default:
24703ca95b02SDimitry Andric     return getTypeIndex(Ty);
24713ca95b02SDimitry Andric   }
24723ca95b02SDimitry Andric 
24734ba319b5SDimitry Andric   // Check if we've already translated the complete record type.
24743ca95b02SDimitry Andric   const auto *CTy = cast<DICompositeType>(Ty);
24753ca95b02SDimitry Andric   auto InsertResult = CompleteTypeIndices.insert({CTy, TypeIndex()});
24763ca95b02SDimitry Andric   if (!InsertResult.second)
24773ca95b02SDimitry Andric     return InsertResult.first->second;
24783ca95b02SDimitry Andric 
24793ca95b02SDimitry Andric   TypeLoweringScope S(*this);
24803ca95b02SDimitry Andric 
24813ca95b02SDimitry Andric   // Make sure the forward declaration is emitted first. It's unclear if this
24823ca95b02SDimitry Andric   // is necessary, but MSVC does it, and we should follow suit until we can show
24833ca95b02SDimitry Andric   // otherwise.
24844ba319b5SDimitry Andric   // We only emit a forward declaration for named types.
24854ba319b5SDimitry Andric   if (!CTy->getName().empty() || !CTy->getIdentifier().empty()) {
24863ca95b02SDimitry Andric     TypeIndex FwdDeclTI = getTypeIndex(CTy);
24873ca95b02SDimitry Andric 
24884ba319b5SDimitry Andric     // Just use the forward decl if we don't have complete type info. This
24894ba319b5SDimitry Andric     // might happen if the frontend is using modules and expects the complete
24904ba319b5SDimitry Andric     // definition to be emitted elsewhere.
24913ca95b02SDimitry Andric     if (CTy->isForwardDecl())
24923ca95b02SDimitry Andric       return FwdDeclTI;
24934ba319b5SDimitry Andric   }
24943ca95b02SDimitry Andric 
24953ca95b02SDimitry Andric   TypeIndex TI;
24963ca95b02SDimitry Andric   switch (CTy->getTag()) {
24973ca95b02SDimitry Andric   case dwarf::DW_TAG_class_type:
24983ca95b02SDimitry Andric   case dwarf::DW_TAG_structure_type:
24993ca95b02SDimitry Andric     TI = lowerCompleteTypeClass(CTy);
25003ca95b02SDimitry Andric     break;
25013ca95b02SDimitry Andric   case dwarf::DW_TAG_union_type:
25023ca95b02SDimitry Andric     TI = lowerCompleteTypeUnion(CTy);
25033ca95b02SDimitry Andric     break;
25043ca95b02SDimitry Andric   default:
25053ca95b02SDimitry Andric     llvm_unreachable("not a record");
25063ca95b02SDimitry Andric   }
25073ca95b02SDimitry Andric 
25084ba319b5SDimitry Andric   // Update the type index associated with this CompositeType.  This cannot
25094ba319b5SDimitry Andric   // use the 'InsertResult' iterator above because it is potentially
25104ba319b5SDimitry Andric   // invalidated by map insertions which can occur while lowering the class
25114ba319b5SDimitry Andric   // type above.
25124ba319b5SDimitry Andric   CompleteTypeIndices[CTy] = TI;
25133ca95b02SDimitry Andric   return TI;
25143ca95b02SDimitry Andric }
25153ca95b02SDimitry Andric 
25163ca95b02SDimitry Andric /// Emit all the deferred complete record types. Try to do this in FIFO order,
25173ca95b02SDimitry Andric /// and do this until fixpoint, as each complete record type typically
25183ca95b02SDimitry Andric /// references
25193ca95b02SDimitry Andric /// many other record types.
emitDeferredCompleteTypes()25203ca95b02SDimitry Andric void CodeViewDebug::emitDeferredCompleteTypes() {
25213ca95b02SDimitry Andric   SmallVector<const DICompositeType *, 4> TypesToEmit;
25223ca95b02SDimitry Andric   while (!DeferredCompleteTypes.empty()) {
25233ca95b02SDimitry Andric     std::swap(DeferredCompleteTypes, TypesToEmit);
25243ca95b02SDimitry Andric     for (const DICompositeType *RecordTy : TypesToEmit)
25253ca95b02SDimitry Andric       getCompleteTypeIndex(RecordTy);
25263ca95b02SDimitry Andric     TypesToEmit.clear();
25273ca95b02SDimitry Andric   }
25283ca95b02SDimitry Andric }
25293ca95b02SDimitry Andric 
emitLocalVariableList(const FunctionInfo & FI,ArrayRef<LocalVariable> Locals)2530*b5893f02SDimitry Andric void CodeViewDebug::emitLocalVariableList(const FunctionInfo &FI,
2531*b5893f02SDimitry Andric                                           ArrayRef<LocalVariable> Locals) {
25323ca95b02SDimitry Andric   // Get the sorted list of parameters and emit them first.
25333ca95b02SDimitry Andric   SmallVector<const LocalVariable *, 6> Params;
25343ca95b02SDimitry Andric   for (const LocalVariable &L : Locals)
25353ca95b02SDimitry Andric     if (L.DIVar->isParameter())
25363ca95b02SDimitry Andric       Params.push_back(&L);
2537*b5893f02SDimitry Andric   llvm::sort(Params, [](const LocalVariable *L, const LocalVariable *R) {
25383ca95b02SDimitry Andric     return L->DIVar->getArg() < R->DIVar->getArg();
25393ca95b02SDimitry Andric   });
25403ca95b02SDimitry Andric   for (const LocalVariable *L : Params)
2541*b5893f02SDimitry Andric     emitLocalVariable(FI, *L);
25423ca95b02SDimitry Andric 
25433ca95b02SDimitry Andric   // Next emit all non-parameters in the order that we found them.
25443ca95b02SDimitry Andric   for (const LocalVariable &L : Locals)
25453ca95b02SDimitry Andric     if (!L.DIVar->isParameter())
2546*b5893f02SDimitry Andric       emitLocalVariable(FI, L);
25473ca95b02SDimitry Andric }
25483ca95b02SDimitry Andric 
2549*b5893f02SDimitry Andric /// Only call this on endian-specific types like ulittle16_t and little32_t, or
2550*b5893f02SDimitry Andric /// structs composed of them.
2551*b5893f02SDimitry Andric template <typename T>
copyBytesForDefRange(SmallString<20> & BytePrefix,SymbolKind SymKind,const T & DefRangeHeader)2552*b5893f02SDimitry Andric static void copyBytesForDefRange(SmallString<20> &BytePrefix,
2553*b5893f02SDimitry Andric                                  SymbolKind SymKind, const T &DefRangeHeader) {
2554*b5893f02SDimitry Andric   BytePrefix.resize(2 + sizeof(T));
2555*b5893f02SDimitry Andric   ulittle16_t SymKindLE = ulittle16_t(SymKind);
2556*b5893f02SDimitry Andric   memcpy(&BytePrefix[0], &SymKindLE, 2);
2557*b5893f02SDimitry Andric   memcpy(&BytePrefix[2], &DefRangeHeader, sizeof(T));
2558*b5893f02SDimitry Andric }
25593ca95b02SDimitry Andric 
emitLocalVariable(const FunctionInfo & FI,const LocalVariable & Var)2560*b5893f02SDimitry Andric void CodeViewDebug::emitLocalVariable(const FunctionInfo &FI,
2561*b5893f02SDimitry Andric                                       const LocalVariable &Var) {
2562*b5893f02SDimitry Andric   // LocalSym record, see SymbolRecord.h for more info.
2563*b5893f02SDimitry Andric   MCSymbol *LocalEnd = beginSymbolRecord(SymbolKind::S_LOCAL);
25643ca95b02SDimitry Andric 
25653ca95b02SDimitry Andric   LocalSymFlags Flags = LocalSymFlags::None;
25663ca95b02SDimitry Andric   if (Var.DIVar->isParameter())
25673ca95b02SDimitry Andric     Flags |= LocalSymFlags::IsParameter;
25683ca95b02SDimitry Andric   if (Var.DefRanges.empty())
25693ca95b02SDimitry Andric     Flags |= LocalSymFlags::IsOptimizedOut;
25703ca95b02SDimitry Andric 
25713ca95b02SDimitry Andric   OS.AddComment("TypeIndex");
25722cab237bSDimitry Andric   TypeIndex TI = Var.UseReferenceType
25732cab237bSDimitry Andric                      ? getTypeIndexForReferenceTo(Var.DIVar->getType())
25742cab237bSDimitry Andric                      : getCompleteTypeIndex(Var.DIVar->getType());
25753ca95b02SDimitry Andric   OS.EmitIntValue(TI.getIndex(), 4);
25763ca95b02SDimitry Andric   OS.AddComment("Flags");
25773ca95b02SDimitry Andric   OS.EmitIntValue(static_cast<uint16_t>(Flags), 2);
25783ca95b02SDimitry Andric   // Truncate the name so we won't overflow the record length field.
25793ca95b02SDimitry Andric   emitNullTerminatedSymbolName(OS, Var.DIVar->getName());
2580*b5893f02SDimitry Andric   endSymbolRecord(LocalEnd);
25813ca95b02SDimitry Andric 
25823ca95b02SDimitry Andric   // Calculate the on disk prefix of the appropriate def range record. The
25833ca95b02SDimitry Andric   // records and on disk formats are described in SymbolRecords.h. BytePrefix
25843ca95b02SDimitry Andric   // should be big enough to hold all forms without memory allocation.
25853ca95b02SDimitry Andric   SmallString<20> BytePrefix;
25863ca95b02SDimitry Andric   for (const LocalVarDefRange &DefRange : Var.DefRanges) {
25873ca95b02SDimitry Andric     BytePrefix.clear();
25883ca95b02SDimitry Andric     if (DefRange.InMemory) {
2589*b5893f02SDimitry Andric       int Offset = DefRange.DataOffset;
2590*b5893f02SDimitry Andric       unsigned Reg = DefRange.CVRegister;
2591*b5893f02SDimitry Andric 
2592*b5893f02SDimitry Andric       // 32-bit x86 call sequences often use PUSH instructions, which disrupt
2593*b5893f02SDimitry Andric       // ESP-relative offsets. Use the virtual frame pointer, VFRAME or $T0,
2594*b5893f02SDimitry Andric       // instead. In frames without stack realignment, $T0 will be the CFA.
2595*b5893f02SDimitry Andric       if (RegisterId(Reg) == RegisterId::ESP) {
2596*b5893f02SDimitry Andric         Reg = unsigned(RegisterId::VFRAME);
2597*b5893f02SDimitry Andric         Offset += FI.OffsetAdjustment;
2598*b5893f02SDimitry Andric       }
2599*b5893f02SDimitry Andric 
2600*b5893f02SDimitry Andric       // If we can use the chosen frame pointer for the frame and this isn't a
2601*b5893f02SDimitry Andric       // sliced aggregate, use the smaller S_DEFRANGE_FRAMEPOINTER_REL record.
2602*b5893f02SDimitry Andric       // Otherwise, use S_DEFRANGE_REGISTER_REL.
2603*b5893f02SDimitry Andric       EncodedFramePtrReg EncFP = encodeFramePtrReg(RegisterId(Reg), TheCPU);
2604*b5893f02SDimitry Andric       if (!DefRange.IsSubfield && EncFP != EncodedFramePtrReg::None &&
2605*b5893f02SDimitry Andric           (bool(Flags & LocalSymFlags::IsParameter)
2606*b5893f02SDimitry Andric                ? (EncFP == FI.EncodedParamFramePtrReg)
2607*b5893f02SDimitry Andric                : (EncFP == FI.EncodedLocalFramePtrReg))) {
2608*b5893f02SDimitry Andric         little32_t FPOffset = little32_t(Offset);
2609*b5893f02SDimitry Andric         copyBytesForDefRange(BytePrefix, S_DEFRANGE_FRAMEPOINTER_REL, FPOffset);
2610*b5893f02SDimitry Andric       } else {
2611d88c1a5aSDimitry Andric         uint16_t RegRelFlags = 0;
2612d88c1a5aSDimitry Andric         if (DefRange.IsSubfield) {
2613d88c1a5aSDimitry Andric           RegRelFlags = DefRangeRegisterRelSym::IsSubfieldFlag |
2614d88c1a5aSDimitry Andric                         (DefRange.StructOffset
2615d88c1a5aSDimitry Andric                          << DefRangeRegisterRelSym::OffsetInParentShift);
2616d88c1a5aSDimitry Andric         }
2617*b5893f02SDimitry Andric         DefRangeRegisterRelSym::Header DRHdr;
2618*b5893f02SDimitry Andric         DRHdr.Register = Reg;
2619*b5893f02SDimitry Andric         DRHdr.Flags = RegRelFlags;
2620*b5893f02SDimitry Andric         DRHdr.BasePointerOffset = Offset;
2621*b5893f02SDimitry Andric         copyBytesForDefRange(BytePrefix, S_DEFRANGE_REGISTER_REL, DRHdr);
2622*b5893f02SDimitry Andric       }
26233ca95b02SDimitry Andric     } else {
26243ca95b02SDimitry Andric       assert(DefRange.DataOffset == 0 && "unexpected offset into register");
2625d88c1a5aSDimitry Andric       if (DefRange.IsSubfield) {
2626*b5893f02SDimitry Andric         DefRangeSubfieldRegisterSym::Header DRHdr;
2627*b5893f02SDimitry Andric         DRHdr.Register = DefRange.CVRegister;
2628*b5893f02SDimitry Andric         DRHdr.MayHaveNoName = 0;
2629*b5893f02SDimitry Andric         DRHdr.OffsetInParent = DefRange.StructOffset;
2630*b5893f02SDimitry Andric         copyBytesForDefRange(BytePrefix, S_DEFRANGE_SUBFIELD_REGISTER, DRHdr);
2631d88c1a5aSDimitry Andric       } else {
2632*b5893f02SDimitry Andric         DefRangeRegisterSym::Header DRHdr;
2633*b5893f02SDimitry Andric         DRHdr.Register = DefRange.CVRegister;
2634*b5893f02SDimitry Andric         DRHdr.MayHaveNoName = 0;
2635*b5893f02SDimitry Andric         copyBytesForDefRange(BytePrefix, S_DEFRANGE_REGISTER, DRHdr);
2636d88c1a5aSDimitry Andric       }
26373ca95b02SDimitry Andric     }
26383ca95b02SDimitry Andric     OS.EmitCVDefRangeDirective(DefRange.Ranges, BytePrefix);
26393ca95b02SDimitry Andric   }
26403ca95b02SDimitry Andric }
26413ca95b02SDimitry Andric 
emitLexicalBlockList(ArrayRef<LexicalBlock * > Blocks,const FunctionInfo & FI)26424ba319b5SDimitry Andric void CodeViewDebug::emitLexicalBlockList(ArrayRef<LexicalBlock *> Blocks,
26434ba319b5SDimitry Andric                                          const FunctionInfo& FI) {
26444ba319b5SDimitry Andric   for (LexicalBlock *Block : Blocks)
26454ba319b5SDimitry Andric     emitLexicalBlock(*Block, FI);
26464ba319b5SDimitry Andric }
26474ba319b5SDimitry Andric 
26484ba319b5SDimitry Andric /// Emit an S_BLOCK32 and S_END record pair delimiting the contents of a
26494ba319b5SDimitry Andric /// lexical block scope.
emitLexicalBlock(const LexicalBlock & Block,const FunctionInfo & FI)26504ba319b5SDimitry Andric void CodeViewDebug::emitLexicalBlock(const LexicalBlock &Block,
26514ba319b5SDimitry Andric                                      const FunctionInfo& FI) {
2652*b5893f02SDimitry Andric   MCSymbol *RecordEnd = beginSymbolRecord(SymbolKind::S_BLOCK32);
26534ba319b5SDimitry Andric   OS.AddComment("PtrParent");
26544ba319b5SDimitry Andric   OS.EmitIntValue(0, 4);                                  // PtrParent
26554ba319b5SDimitry Andric   OS.AddComment("PtrEnd");
26564ba319b5SDimitry Andric   OS.EmitIntValue(0, 4);                                  // PtrEnd
26574ba319b5SDimitry Andric   OS.AddComment("Code size");
26584ba319b5SDimitry Andric   OS.emitAbsoluteSymbolDiff(Block.End, Block.Begin, 4);   // Code Size
26594ba319b5SDimitry Andric   OS.AddComment("Function section relative address");
26604ba319b5SDimitry Andric   OS.EmitCOFFSecRel32(Block.Begin, /*Offset=*/0);         // Func Offset
26614ba319b5SDimitry Andric   OS.AddComment("Function section index");
26624ba319b5SDimitry Andric   OS.EmitCOFFSectionIndex(FI.Begin);                      // Func Symbol
26634ba319b5SDimitry Andric   OS.AddComment("Lexical block name");
26644ba319b5SDimitry Andric   emitNullTerminatedSymbolName(OS, Block.Name);           // Name
2665*b5893f02SDimitry Andric   endSymbolRecord(RecordEnd);
26664ba319b5SDimitry Andric 
26674ba319b5SDimitry Andric   // Emit variables local to this lexical block.
2668*b5893f02SDimitry Andric   emitLocalVariableList(FI, Block.Locals);
2669*b5893f02SDimitry Andric   emitGlobalVariableList(Block.Globals);
26704ba319b5SDimitry Andric 
26714ba319b5SDimitry Andric   // Emit lexical blocks contained within this block.
26724ba319b5SDimitry Andric   emitLexicalBlockList(Block.Children, FI);
26734ba319b5SDimitry Andric 
26744ba319b5SDimitry Andric   // Close the lexical block scope.
2675*b5893f02SDimitry Andric   emitEndSymbolRecord(SymbolKind::S_END);
26764ba319b5SDimitry Andric }
26774ba319b5SDimitry Andric 
26784ba319b5SDimitry Andric /// Convenience routine for collecting lexical block information for a list
26794ba319b5SDimitry Andric /// of lexical scopes.
collectLexicalBlockInfo(SmallVectorImpl<LexicalScope * > & Scopes,SmallVectorImpl<LexicalBlock * > & Blocks,SmallVectorImpl<LocalVariable> & Locals,SmallVectorImpl<CVGlobalVariable> & Globals)26804ba319b5SDimitry Andric void CodeViewDebug::collectLexicalBlockInfo(
26814ba319b5SDimitry Andric         SmallVectorImpl<LexicalScope *> &Scopes,
26824ba319b5SDimitry Andric         SmallVectorImpl<LexicalBlock *> &Blocks,
2683*b5893f02SDimitry Andric         SmallVectorImpl<LocalVariable> &Locals,
2684*b5893f02SDimitry Andric         SmallVectorImpl<CVGlobalVariable> &Globals) {
26854ba319b5SDimitry Andric   for (LexicalScope *Scope : Scopes)
2686*b5893f02SDimitry Andric     collectLexicalBlockInfo(*Scope, Blocks, Locals, Globals);
26874ba319b5SDimitry Andric }
26884ba319b5SDimitry Andric 
26894ba319b5SDimitry Andric /// Populate the lexical blocks and local variable lists of the parent with
26904ba319b5SDimitry Andric /// information about the specified lexical scope.
collectLexicalBlockInfo(LexicalScope & Scope,SmallVectorImpl<LexicalBlock * > & ParentBlocks,SmallVectorImpl<LocalVariable> & ParentLocals,SmallVectorImpl<CVGlobalVariable> & ParentGlobals)26914ba319b5SDimitry Andric void CodeViewDebug::collectLexicalBlockInfo(
26924ba319b5SDimitry Andric     LexicalScope &Scope,
26934ba319b5SDimitry Andric     SmallVectorImpl<LexicalBlock *> &ParentBlocks,
2694*b5893f02SDimitry Andric     SmallVectorImpl<LocalVariable> &ParentLocals,
2695*b5893f02SDimitry Andric     SmallVectorImpl<CVGlobalVariable> &ParentGlobals) {
26964ba319b5SDimitry Andric   if (Scope.isAbstractScope())
26974ba319b5SDimitry Andric     return;
26984ba319b5SDimitry Andric 
2699*b5893f02SDimitry Andric   // Gather information about the lexical scope including local variables,
2700*b5893f02SDimitry Andric   // global variables, and address ranges.
2701*b5893f02SDimitry Andric   bool IgnoreScope = false;
2702*b5893f02SDimitry Andric   auto LI = ScopeVariables.find(&Scope);
2703*b5893f02SDimitry Andric   SmallVectorImpl<LocalVariable> *Locals =
2704*b5893f02SDimitry Andric       LI != ScopeVariables.end() ? &LI->second : nullptr;
2705*b5893f02SDimitry Andric   auto GI = ScopeGlobals.find(Scope.getScopeNode());
2706*b5893f02SDimitry Andric   SmallVectorImpl<CVGlobalVariable> *Globals =
2707*b5893f02SDimitry Andric       GI != ScopeGlobals.end() ? GI->second.get() : nullptr;
27084ba319b5SDimitry Andric   const DILexicalBlock *DILB = dyn_cast<DILexicalBlock>(Scope.getScopeNode());
27094ba319b5SDimitry Andric   const SmallVectorImpl<InsnRange> &Ranges = Scope.getRanges();
2710*b5893f02SDimitry Andric 
2711*b5893f02SDimitry Andric   // Ignore lexical scopes which do not contain variables.
2712*b5893f02SDimitry Andric   if (!Locals && !Globals)
2713*b5893f02SDimitry Andric     IgnoreScope = true;
2714*b5893f02SDimitry Andric 
2715*b5893f02SDimitry Andric   // Ignore lexical scopes which are not lexical blocks.
2716*b5893f02SDimitry Andric   if (!DILB)
2717*b5893f02SDimitry Andric     IgnoreScope = true;
2718*b5893f02SDimitry Andric 
2719*b5893f02SDimitry Andric   // Ignore scopes which have too many address ranges to represent in the
2720*b5893f02SDimitry Andric   // current CodeView format or do not have a valid address range.
27214ba319b5SDimitry Andric   //
27224ba319b5SDimitry Andric   // For lexical scopes with multiple address ranges you may be tempted to
27234ba319b5SDimitry Andric   // construct a single range covering every instruction where the block is
27244ba319b5SDimitry Andric   // live and everything in between.  Unfortunately, Visual Studio only
27254ba319b5SDimitry Andric   // displays variables from the first matching lexical block scope.  If the
27264ba319b5SDimitry Andric   // first lexical block contains exception handling code or cold code which
27274ba319b5SDimitry Andric   // is moved to the bottom of the routine creating a single range covering
27284ba319b5SDimitry Andric   // nearly the entire routine, then it will hide all other lexical blocks
27294ba319b5SDimitry Andric   // and the variables they contain.
2730*b5893f02SDimitry Andric   if (Ranges.size() != 1 || !getLabelAfterInsn(Ranges.front().second))
2731*b5893f02SDimitry Andric     IgnoreScope = true;
2732*b5893f02SDimitry Andric 
2733*b5893f02SDimitry Andric   if (IgnoreScope) {
2734*b5893f02SDimitry Andric     // This scope can be safely ignored and eliminating it will reduce the
2735*b5893f02SDimitry Andric     // size of the debug information. Be sure to collect any variable and scope
2736*b5893f02SDimitry Andric     // information from the this scope or any of its children and collapse them
2737*b5893f02SDimitry Andric     // into the parent scope.
2738*b5893f02SDimitry Andric     if (Locals)
2739*b5893f02SDimitry Andric       ParentLocals.append(Locals->begin(), Locals->end());
2740*b5893f02SDimitry Andric     if (Globals)
2741*b5893f02SDimitry Andric       ParentGlobals.append(Globals->begin(), Globals->end());
2742*b5893f02SDimitry Andric     collectLexicalBlockInfo(Scope.getChildren(),
2743*b5893f02SDimitry Andric                             ParentBlocks,
2744*b5893f02SDimitry Andric                             ParentLocals,
2745*b5893f02SDimitry Andric                             ParentGlobals);
27464ba319b5SDimitry Andric     return;
27474ba319b5SDimitry Andric   }
27484ba319b5SDimitry Andric 
27494ba319b5SDimitry Andric   // Create a new CodeView lexical block for this lexical scope.  If we've
27504ba319b5SDimitry Andric   // seen this DILexicalBlock before then the scope tree is malformed and
27514ba319b5SDimitry Andric   // we can handle this gracefully by not processing it a second time.
27524ba319b5SDimitry Andric   auto BlockInsertion = CurFn->LexicalBlocks.insert({DILB, LexicalBlock()});
27534ba319b5SDimitry Andric   if (!BlockInsertion.second)
27544ba319b5SDimitry Andric     return;
27554ba319b5SDimitry Andric 
2756*b5893f02SDimitry Andric   // Create a lexical block containing the variables and collect the the
2757*b5893f02SDimitry Andric   // lexical block information for the children.
27584ba319b5SDimitry Andric   const InsnRange &Range = Ranges.front();
27594ba319b5SDimitry Andric   assert(Range.first && Range.second);
27604ba319b5SDimitry Andric   LexicalBlock &Block = BlockInsertion.first->second;
27614ba319b5SDimitry Andric   Block.Begin = getLabelBeforeInsn(Range.first);
27624ba319b5SDimitry Andric   Block.End = getLabelAfterInsn(Range.second);
27634ba319b5SDimitry Andric   assert(Block.Begin && "missing label for scope begin");
27644ba319b5SDimitry Andric   assert(Block.End && "missing label for scope end");
27654ba319b5SDimitry Andric   Block.Name = DILB->getName();
2766*b5893f02SDimitry Andric   if (Locals)
2767*b5893f02SDimitry Andric     Block.Locals = std::move(*Locals);
2768*b5893f02SDimitry Andric   if (Globals)
2769*b5893f02SDimitry Andric     Block.Globals = std::move(*Globals);
27704ba319b5SDimitry Andric   ParentBlocks.push_back(&Block);
2771*b5893f02SDimitry Andric   collectLexicalBlockInfo(Scope.getChildren(),
2772*b5893f02SDimitry Andric                           Block.Children,
2773*b5893f02SDimitry Andric                           Block.Locals,
2774*b5893f02SDimitry Andric                           Block.Globals);
27754ba319b5SDimitry Andric }
27764ba319b5SDimitry Andric 
endFunctionImpl(const MachineFunction * MF)27777a7e6055SDimitry Andric void CodeViewDebug::endFunctionImpl(const MachineFunction *MF) {
27782cab237bSDimitry Andric   const Function &GV = MF->getFunction();
27792cab237bSDimitry Andric   assert(FnDebugInfo.count(&GV));
27804ba319b5SDimitry Andric   assert(CurFn == FnDebugInfo[&GV].get());
27813ca95b02SDimitry Andric 
27822cab237bSDimitry Andric   collectVariableInfo(GV.getSubprogram());
27833ca95b02SDimitry Andric 
27844ba319b5SDimitry Andric   // Build the lexical block structure to emit for this routine.
27854ba319b5SDimitry Andric   if (LexicalScope *CFS = LScopes.getCurrentFunctionScope())
2786*b5893f02SDimitry Andric     collectLexicalBlockInfo(*CFS,
2787*b5893f02SDimitry Andric                             CurFn->ChildBlocks,
2788*b5893f02SDimitry Andric                             CurFn->Locals,
2789*b5893f02SDimitry Andric                             CurFn->Globals);
27904ba319b5SDimitry Andric 
27914ba319b5SDimitry Andric   // Clear the scope and variable information from the map which will not be
27924ba319b5SDimitry Andric   // valid after we have finished processing this routine.  This also prepares
27934ba319b5SDimitry Andric   // the map for the subsequent routine.
27944ba319b5SDimitry Andric   ScopeVariables.clear();
27954ba319b5SDimitry Andric 
27963ca95b02SDimitry Andric   // Don't emit anything if we don't have any line tables.
27974ba319b5SDimitry Andric   // Thunks are compiler-generated and probably won't have source correlation.
27984ba319b5SDimitry Andric   if (!CurFn->HaveLineInfo && !GV.getSubprogram()->isThunk()) {
27992cab237bSDimitry Andric     FnDebugInfo.erase(&GV);
28003ca95b02SDimitry Andric     CurFn = nullptr;
28013ca95b02SDimitry Andric     return;
28023ca95b02SDimitry Andric   }
28033ca95b02SDimitry Andric 
28042cab237bSDimitry Andric   CurFn->Annotations = MF->getCodeViewAnnotations();
28052cab237bSDimitry Andric 
28063ca95b02SDimitry Andric   CurFn->End = Asm->getFunctionEnd();
28073ca95b02SDimitry Andric 
28083ca95b02SDimitry Andric   CurFn = nullptr;
28093ca95b02SDimitry Andric }
28103ca95b02SDimitry Andric 
beginInstruction(const MachineInstr * MI)28113ca95b02SDimitry Andric void CodeViewDebug::beginInstruction(const MachineInstr *MI) {
28123ca95b02SDimitry Andric   DebugHandlerBase::beginInstruction(MI);
28133ca95b02SDimitry Andric 
28144ba319b5SDimitry Andric   // Ignore DBG_VALUE and DBG_LABEL locations and function prologue.
28154ba319b5SDimitry Andric   if (!Asm || !CurFn || MI->isDebugInstr() ||
28166c4bc1bdSDimitry Andric       MI->getFlag(MachineInstr::FrameSetup))
28173ca95b02SDimitry Andric     return;
2818a580b014SDimitry Andric 
2819a580b014SDimitry Andric   // If the first instruction of a new MBB has no location, find the first
2820a580b014SDimitry Andric   // instruction with a location and use that.
28213ca95b02SDimitry Andric   DebugLoc DL = MI->getDebugLoc();
2822a580b014SDimitry Andric   if (!DL && MI->getParent() != PrevInstBB) {
2823a580b014SDimitry Andric     for (const auto &NextMI : *MI->getParent()) {
28244ba319b5SDimitry Andric       if (NextMI.isDebugInstr())
28252cab237bSDimitry Andric         continue;
2826a580b014SDimitry Andric       DL = NextMI.getDebugLoc();
2827a580b014SDimitry Andric       if (DL)
2828a580b014SDimitry Andric         break;
2829a580b014SDimitry Andric     }
2830a580b014SDimitry Andric   }
2831a580b014SDimitry Andric   PrevInstBB = MI->getParent();
2832a580b014SDimitry Andric 
2833a580b014SDimitry Andric   // If we still don't have a debug location, don't record a location.
2834a580b014SDimitry Andric   if (!DL)
28353ca95b02SDimitry Andric     return;
2836a580b014SDimitry Andric 
28373ca95b02SDimitry Andric   maybeRecordLocation(DL, Asm->MF);
28383ca95b02SDimitry Andric }
28393ca95b02SDimitry Andric 
beginCVSubsection(DebugSubsectionKind Kind)284089cb50c9SDimitry Andric MCSymbol *CodeViewDebug::beginCVSubsection(DebugSubsectionKind Kind) {
28413ca95b02SDimitry Andric   MCSymbol *BeginLabel = MMI->getContext().createTempSymbol(),
28423ca95b02SDimitry Andric            *EndLabel = MMI->getContext().createTempSymbol();
28433ca95b02SDimitry Andric   OS.EmitIntValue(unsigned(Kind), 4);
28443ca95b02SDimitry Andric   OS.AddComment("Subsection size");
28453ca95b02SDimitry Andric   OS.emitAbsoluteSymbolDiff(EndLabel, BeginLabel, 4);
28463ca95b02SDimitry Andric   OS.EmitLabel(BeginLabel);
28473ca95b02SDimitry Andric   return EndLabel;
28483ca95b02SDimitry Andric }
28493ca95b02SDimitry Andric 
endCVSubsection(MCSymbol * EndLabel)28503ca95b02SDimitry Andric void CodeViewDebug::endCVSubsection(MCSymbol *EndLabel) {
28513ca95b02SDimitry Andric   OS.EmitLabel(EndLabel);
28523ca95b02SDimitry Andric   // Every subsection must be aligned to a 4-byte boundary.
28533ca95b02SDimitry Andric   OS.EmitValueToAlignment(4);
28543ca95b02SDimitry Andric }
28553ca95b02SDimitry Andric 
getSymbolName(SymbolKind SymKind)2856*b5893f02SDimitry Andric static StringRef getSymbolName(SymbolKind SymKind) {
2857*b5893f02SDimitry Andric   for (const EnumEntry<SymbolKind> &EE : getSymbolTypeNames())
2858*b5893f02SDimitry Andric     if (EE.Value == SymKind)
2859*b5893f02SDimitry Andric       return EE.Name;
2860*b5893f02SDimitry Andric   return "";
2861*b5893f02SDimitry Andric }
2862*b5893f02SDimitry Andric 
beginSymbolRecord(SymbolKind SymKind)2863*b5893f02SDimitry Andric MCSymbol *CodeViewDebug::beginSymbolRecord(SymbolKind SymKind) {
2864*b5893f02SDimitry Andric   MCSymbol *BeginLabel = MMI->getContext().createTempSymbol(),
2865*b5893f02SDimitry Andric            *EndLabel = MMI->getContext().createTempSymbol();
2866*b5893f02SDimitry Andric   OS.AddComment("Record length");
2867*b5893f02SDimitry Andric   OS.emitAbsoluteSymbolDiff(EndLabel, BeginLabel, 2);
2868*b5893f02SDimitry Andric   OS.EmitLabel(BeginLabel);
2869*b5893f02SDimitry Andric   if (OS.isVerboseAsm())
2870*b5893f02SDimitry Andric     OS.AddComment("Record kind: " + getSymbolName(SymKind));
2871*b5893f02SDimitry Andric   OS.EmitIntValue(unsigned(SymKind), 2);
2872*b5893f02SDimitry Andric   return EndLabel;
2873*b5893f02SDimitry Andric }
2874*b5893f02SDimitry Andric 
endSymbolRecord(MCSymbol * SymEnd)2875*b5893f02SDimitry Andric void CodeViewDebug::endSymbolRecord(MCSymbol *SymEnd) {
2876*b5893f02SDimitry Andric   // MSVC does not pad out symbol records to four bytes, but LLVM does to avoid
2877*b5893f02SDimitry Andric   // an extra copy of every symbol record in LLD. This increases object file
2878*b5893f02SDimitry Andric   // size by less than 1% in the clang build, and is compatible with the Visual
2879*b5893f02SDimitry Andric   // C++ linker.
2880*b5893f02SDimitry Andric   OS.EmitValueToAlignment(4);
2881*b5893f02SDimitry Andric   OS.EmitLabel(SymEnd);
2882*b5893f02SDimitry Andric }
2883*b5893f02SDimitry Andric 
emitEndSymbolRecord(SymbolKind EndKind)2884*b5893f02SDimitry Andric void CodeViewDebug::emitEndSymbolRecord(SymbolKind EndKind) {
2885*b5893f02SDimitry Andric   OS.AddComment("Record length");
2886*b5893f02SDimitry Andric   OS.EmitIntValue(2, 2);
2887*b5893f02SDimitry Andric   if (OS.isVerboseAsm())
2888*b5893f02SDimitry Andric     OS.AddComment("Record kind: " + getSymbolName(EndKind));
2889*b5893f02SDimitry Andric   OS.EmitIntValue(unsigned(EndKind), 2); // Record Kind
2890*b5893f02SDimitry Andric }
2891*b5893f02SDimitry Andric 
emitDebugInfoForUDTs(ArrayRef<std::pair<std::string,const DIType * >> UDTs)28923ca95b02SDimitry Andric void CodeViewDebug::emitDebugInfoForUDTs(
28932cab237bSDimitry Andric     ArrayRef<std::pair<std::string, const DIType *>> UDTs) {
28942cab237bSDimitry Andric   for (const auto &UDT : UDTs) {
28952cab237bSDimitry Andric     const DIType *T = UDT.second;
28962cab237bSDimitry Andric     assert(shouldEmitUdt(T));
28972cab237bSDimitry Andric 
2898*b5893f02SDimitry Andric     MCSymbol *UDTRecordEnd = beginSymbolRecord(SymbolKind::S_UDT);
28993ca95b02SDimitry Andric     OS.AddComment("Type");
29002cab237bSDimitry Andric     OS.EmitIntValue(getCompleteTypeIndex(T).getIndex(), 4);
29013ca95b02SDimitry Andric     emitNullTerminatedSymbolName(OS, UDT.first);
2902*b5893f02SDimitry Andric     endSymbolRecord(UDTRecordEnd);
29033ca95b02SDimitry Andric   }
29043ca95b02SDimitry Andric }
29053ca95b02SDimitry Andric 
collectGlobalVariableInfo()2906*b5893f02SDimitry Andric void CodeViewDebug::collectGlobalVariableInfo() {
2907d88c1a5aSDimitry Andric   DenseMap<const DIGlobalVariableExpression *, const GlobalVariable *>
2908d88c1a5aSDimitry Andric       GlobalMap;
2909d88c1a5aSDimitry Andric   for (const GlobalVariable &GV : MMI->getModule()->globals()) {
2910d88c1a5aSDimitry Andric     SmallVector<DIGlobalVariableExpression *, 1> GVEs;
2911d88c1a5aSDimitry Andric     GV.getDebugInfo(GVEs);
2912d88c1a5aSDimitry Andric     for (const auto *GVE : GVEs)
2913d88c1a5aSDimitry Andric       GlobalMap[GVE] = &GV;
2914d88c1a5aSDimitry Andric   }
2915d88c1a5aSDimitry Andric 
29163ca95b02SDimitry Andric   NamedMDNode *CUs = MMI->getModule()->getNamedMetadata("llvm.dbg.cu");
29173ca95b02SDimitry Andric   for (const MDNode *Node : CUs->operands()) {
29183ca95b02SDimitry Andric     const auto *CU = cast<DICompileUnit>(Node);
2919*b5893f02SDimitry Andric     for (const auto *GVE : CU->getGlobalVariables()) {
2920*b5893f02SDimitry Andric       const auto *GV = GlobalMap.lookup(GVE);
2921*b5893f02SDimitry Andric       if (!GV || GV->isDeclarationForLinker())
2922*b5893f02SDimitry Andric         continue;
2923*b5893f02SDimitry Andric       const DIGlobalVariable *DIGV = GVE->getVariable();
2924*b5893f02SDimitry Andric       DIScope *Scope = DIGV->getScope();
2925*b5893f02SDimitry Andric       SmallVector<CVGlobalVariable, 1> *VariableList;
2926*b5893f02SDimitry Andric       if (Scope && isa<DILocalScope>(Scope)) {
2927*b5893f02SDimitry Andric         // Locate a global variable list for this scope, creating one if
2928*b5893f02SDimitry Andric         // necessary.
2929*b5893f02SDimitry Andric         auto Insertion = ScopeGlobals.insert(
2930*b5893f02SDimitry Andric             {Scope, std::unique_ptr<GlobalVariableList>()});
2931*b5893f02SDimitry Andric         if (Insertion.second)
2932*b5893f02SDimitry Andric           Insertion.first->second = llvm::make_unique<GlobalVariableList>();
2933*b5893f02SDimitry Andric         VariableList = Insertion.first->second.get();
2934*b5893f02SDimitry Andric       } else if (GV->hasComdat())
2935*b5893f02SDimitry Andric         // Emit this global variable into a COMDAT section.
2936*b5893f02SDimitry Andric         VariableList = &ComdatVariables;
2937*b5893f02SDimitry Andric       else
2938*b5893f02SDimitry Andric         // Emit this globla variable in a single global symbol section.
2939*b5893f02SDimitry Andric         VariableList = &GlobalVariables;
2940*b5893f02SDimitry Andric       CVGlobalVariable CVGV = {DIGV, GV};
2941*b5893f02SDimitry Andric       VariableList->emplace_back(std::move(CVGV));
2942*b5893f02SDimitry Andric     }
2943*b5893f02SDimitry Andric   }
2944*b5893f02SDimitry Andric }
29453ca95b02SDimitry Andric 
emitDebugInfoForGlobals()2946*b5893f02SDimitry Andric void CodeViewDebug::emitDebugInfoForGlobals() {
29473ca95b02SDimitry Andric   // First, emit all globals that are not in a comdat in a single symbol
29483ca95b02SDimitry Andric   // substream. MSVC doesn't like it if the substream is empty, so only open
29493ca95b02SDimitry Andric   // it if we have at least one global to emit.
29503ca95b02SDimitry Andric   switchToDebugSectionForSymbol(nullptr);
2951*b5893f02SDimitry Andric   if (!GlobalVariables.empty()) {
29523ca95b02SDimitry Andric     OS.AddComment("Symbol subsection for globals");
2953*b5893f02SDimitry Andric     MCSymbol *EndLabel = beginCVSubsection(DebugSubsectionKind::Symbols);
2954*b5893f02SDimitry Andric     emitGlobalVariableList(GlobalVariables);
29553ca95b02SDimitry Andric     endCVSubsection(EndLabel);
2956*b5893f02SDimitry Andric   }
29573ca95b02SDimitry Andric 
29583ca95b02SDimitry Andric   // Second, emit each global that is in a comdat into its own .debug$S
29593ca95b02SDimitry Andric   // section along with its own symbol substream.
2960*b5893f02SDimitry Andric   for (const CVGlobalVariable &CVGV : ComdatVariables) {
2961*b5893f02SDimitry Andric     MCSymbol *GVSym = Asm->getSymbol(CVGV.GV);
29623ca95b02SDimitry Andric     OS.AddComment("Symbol subsection for " +
2963*b5893f02SDimitry Andric             Twine(GlobalValue::dropLLVMManglingEscape(CVGV.GV->getName())));
29643ca95b02SDimitry Andric     switchToDebugSectionForSymbol(GVSym);
2965*b5893f02SDimitry Andric     MCSymbol *EndLabel = beginCVSubsection(DebugSubsectionKind::Symbols);
2966d88c1a5aSDimitry Andric     // FIXME: emitDebugInfoForGlobal() doesn't handle DIExpressions.
2967*b5893f02SDimitry Andric     emitDebugInfoForGlobal(CVGV.DIGV, CVGV.GV, GVSym);
29683ca95b02SDimitry Andric     endCVSubsection(EndLabel);
29693ca95b02SDimitry Andric   }
29703ca95b02SDimitry Andric }
29713ca95b02SDimitry Andric 
emitDebugInfoForRetainedTypes()29723ca95b02SDimitry Andric void CodeViewDebug::emitDebugInfoForRetainedTypes() {
29733ca95b02SDimitry Andric   NamedMDNode *CUs = MMI->getModule()->getNamedMetadata("llvm.dbg.cu");
29743ca95b02SDimitry Andric   for (const MDNode *Node : CUs->operands()) {
29753ca95b02SDimitry Andric     for (auto *Ty : cast<DICompileUnit>(Node)->getRetainedTypes()) {
29763ca95b02SDimitry Andric       if (DIType *RT = dyn_cast<DIType>(Ty)) {
29773ca95b02SDimitry Andric         getTypeIndex(RT);
29783ca95b02SDimitry Andric         // FIXME: Add to global/local DTU list.
29793ca95b02SDimitry Andric       }
29803ca95b02SDimitry Andric     }
29813ca95b02SDimitry Andric   }
29823ca95b02SDimitry Andric }
29833ca95b02SDimitry Andric 
2984*b5893f02SDimitry Andric // Emit each global variable in the specified array.
emitGlobalVariableList(ArrayRef<CVGlobalVariable> Globals)2985*b5893f02SDimitry Andric void CodeViewDebug::emitGlobalVariableList(ArrayRef<CVGlobalVariable> Globals) {
2986*b5893f02SDimitry Andric   for (const CVGlobalVariable &CVGV : Globals) {
2987*b5893f02SDimitry Andric     MCSymbol *GVSym = Asm->getSymbol(CVGV.GV);
2988*b5893f02SDimitry Andric     // FIXME: emitDebugInfoForGlobal() doesn't handle DIExpressions.
2989*b5893f02SDimitry Andric     emitDebugInfoForGlobal(CVGV.DIGV, CVGV.GV, GVSym);
2990*b5893f02SDimitry Andric   }
2991*b5893f02SDimitry Andric }
2992*b5893f02SDimitry Andric 
emitDebugInfoForGlobal(const DIGlobalVariable * DIGV,const GlobalVariable * GV,MCSymbol * GVSym)29933ca95b02SDimitry Andric void CodeViewDebug::emitDebugInfoForGlobal(const DIGlobalVariable *DIGV,
2994d88c1a5aSDimitry Andric                                            const GlobalVariable *GV,
29953ca95b02SDimitry Andric                                            MCSymbol *GVSym) {
2996*b5893f02SDimitry Andric   // DataSym record, see SymbolRecord.h for more info. Thread local data
2997*b5893f02SDimitry Andric   // happens to have the same format as global data.
2998*b5893f02SDimitry Andric   SymbolKind DataSym = GV->isThreadLocal()
2999*b5893f02SDimitry Andric                            ? (DIGV->isLocalToUnit() ? SymbolKind::S_LTHREAD32
3000*b5893f02SDimitry Andric                                                     : SymbolKind::S_GTHREAD32)
3001*b5893f02SDimitry Andric                            : (DIGV->isLocalToUnit() ? SymbolKind::S_LDATA32
3002*b5893f02SDimitry Andric                                                     : SymbolKind::S_GDATA32);
3003*b5893f02SDimitry Andric   MCSymbol *DataEnd = beginSymbolRecord(DataSym);
30043ca95b02SDimitry Andric   OS.AddComment("Type");
30053ca95b02SDimitry Andric   OS.EmitIntValue(getCompleteTypeIndex(DIGV->getType()).getIndex(), 4);
30063ca95b02SDimitry Andric   OS.AddComment("DataOffset");
3007d88c1a5aSDimitry Andric   OS.EmitCOFFSecRel32(GVSym, /*Offset=*/0);
30083ca95b02SDimitry Andric   OS.AddComment("Segment");
30093ca95b02SDimitry Andric   OS.EmitCOFFSectionIndex(GVSym);
30103ca95b02SDimitry Andric   OS.AddComment("Name");
3011*b5893f02SDimitry Andric   const unsigned LengthOfDataRecord = 12;
3012*b5893f02SDimitry Andric   emitNullTerminatedSymbolName(OS, DIGV->getName(), LengthOfDataRecord);
3013*b5893f02SDimitry Andric   endSymbolRecord(DataEnd);
30143ca95b02SDimitry Andric }
3015