<div dir="ltr">Looks like you've introduced a dependency from the AsmPrinter library to the DebugInfo/CodeView library & may need to update AsmPrinter's CMakeLists.txt to add that dependency?</div><div class="gmail_extra"><br><div class="gmail_quote">On Thu, Jan 28, 2016 at 4:49 PM, Reid Kleckner via llvm-commits <span dir="ltr"><<a href="mailto:llvm-commits@lists.llvm.org" target="_blank">llvm-commits@lists.llvm.org</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Author: rnk<br>
Date: Thu Jan 28 18:49:42 2016<br>
New Revision: 259130<br>
<br>
URL: <a href="http://llvm.org/viewvc/llvm-project?rev=259130&view=rev" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project?rev=259130&view=rev</a><br>
Log:<br>
Reland "[CodeView] Use assembler directives for line tables"<br>
<br>
This reverts commit r259126 and relands r259117.<br>
<br>
This time with updated library dependencies.<br>
<br>
Added:<br>
    llvm/trunk/include/llvm/MC/MCCodeView.h<br>
    llvm/trunk/lib/MC/MCCodeView.cpp<br>
    llvm/trunk/test/MC/COFF/cv-loc.s<br>
Modified:<br>
    llvm/trunk/include/llvm/DebugInfo/CodeView/Line.h<br>
    llvm/trunk/include/llvm/MC/MCContext.h<br>
    llvm/trunk/include/llvm/MC/MCObjectStreamer.h<br>
    llvm/trunk/include/llvm/MC/MCStreamer.h<br>
    llvm/trunk/include/llvm/MC/StringTableBuilder.h<br>
    llvm/trunk/include/llvm/Support/COFF.h<br>
    llvm/trunk/lib/CodeGen/AsmPrinter/CodeViewDebug.cpp<br>
    llvm/trunk/lib/CodeGen/AsmPrinter/CodeViewDebug.h<br>
    llvm/trunk/lib/CodeGen/AsmPrinter/LLVMBuild.txt<br>
    llvm/trunk/lib/MC/CMakeLists.txt<br>
    llvm/trunk/lib/MC/MCAsmStreamer.cpp<br>
    llvm/trunk/lib/MC/MCContext.cpp<br>
    llvm/trunk/lib/MC/MCObjectStreamer.cpp<br>
    llvm/trunk/lib/MC/MCParser/AsmParser.cpp<br>
    llvm/trunk/lib/MC/MCStreamer.cpp<br>
    llvm/trunk/lib/MC/StringTableBuilder.cpp<br>
    llvm/trunk/test/DebugInfo/COFF/asm.ll<br>
    llvm/trunk/test/DebugInfo/COFF/multifile.ll<br>
    llvm/trunk/test/DebugInfo/COFF/multifunction.ll<br>
    llvm/trunk/test/DebugInfo/COFF/simple.ll<br>
    llvm/trunk/test/DebugInfo/COFF/tail-call-without-lexical-scopes.ll<br>
    llvm/trunk/tools/llvm-readobj/COFFDumper.cpp<br>
    llvm/trunk/unittests/MC/StringTableBuilderTest.cpp<br>
<br>
Modified: llvm/trunk/include/llvm/DebugInfo/CodeView/Line.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/DebugInfo/CodeView/Line.h?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/DebugInfo/CodeView/Line.h?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/include/llvm/DebugInfo/CodeView/Line.h (original)<br>
+++ llvm/trunk/include/llvm/DebugInfo/CodeView/Line.h Thu Jan 28 18:49:42 2016<br>
@@ -21,16 +21,19 @@ using llvm::support::ulittle32_t;<br>
<br>
 class LineInfo {<br>
 public:<br>
-  static const uint32_t AlwaysStepIntoLineNumber = 0xfeefee;<br>
-  static const uint32_t NeverStepIntoLineNumber = 0xf00f00;<br>
+  enum : uint32_t {<br>
+    AlwaysStepIntoLineNumber = 0xfeefee,<br>
+    NeverStepIntoLineNumber = 0xf00f00<br>
+  };<br>
+<br>
+  enum : int { EndLineDeltaShift = 24 };<br>
+<br>
+  enum : uint32_t {<br>
+    StartLineMask = 0x00ffffff,<br>
+    EndLineDeltaMask = 0x7f000000,<br>
+    StatementFlag = 0x80000000u<br>
+  };<br>
<br>
-private:<br>
-  static const uint32_t StartLineMask = 0x00ffffff;<br>
-  static const uint32_t EndLineDeltaMask = 0x7f000000;<br>
-  static const int EndLineDeltaShift = 24;<br>
-  static const uint32_t StatementFlag = 0x80000000u;<br>
-<br>
-public:<br>
   LineInfo(uint32_t StartLine, uint32_t EndLine, bool IsStatement);<br>
<br>
   uint32_t getStartLine() const { return LineData & StartLineMask; }<br>
@@ -151,6 +154,10 @@ struct FileChecksum {<br>
   // Checksum bytes follow.<br>
 };<br>
<br>
+enum LineFlags : uint32_t {<br>
+  HaveColumns = 1, // CV_LINES_HAVE_COLUMNS<br>
+};<br>
+<br>
 } // namespace codeview<br>
 } // namespace llvm<br>
<br>
<br>
Added: llvm/trunk/include/llvm/MC/MCCodeView.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/MC/MCCodeView.h?rev=259130&view=auto" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/MC/MCCodeView.h?rev=259130&view=auto</a><br>
==============================================================================<br>
--- llvm/trunk/include/llvm/MC/MCCodeView.h (added)<br>
+++ llvm/trunk/include/llvm/MC/MCCodeView.h Thu Jan 28 18:49:42 2016<br>
@@ -0,0 +1,162 @@<br>
+//===- MCCodeView.h - Machine Code CodeView support -------------*- C++ -*-===//<br>
+//<br>
+//                     The LLVM Compiler Infrastructure<br>
+//<br>
+// This file is distributed under the University of Illinois Open Source<br>
+// License. See LICENSE.TXT for details.<br>
+//<br>
+//===----------------------------------------------------------------------===//<br>
+//<br>
+// Holds state from .cv_file and .cv_loc directives for later emission.<br>
+//<br>
+//===----------------------------------------------------------------------===//<br>
+<br>
+#ifndef LLVM_MC_MCCODEVIEW_H<br>
+#define LLVM_MC_MCCODEVIEW_H<br>
+<br>
+#include "llvm/ADT/StringRef.h"<br>
+#include "llvm/ADT/StringMap.h"<br>
+#include "llvm/MC/MCObjectStreamer.h"<br>
+#include "llvm/MC/MCFragment.h"<br>
+#include <map><br>
+#include <vector><br>
+<br>
+namespace llvm {<br>
+class MCContext;<br>
+class MCObjectStreamer;<br>
+class MCStreamer;<br>
+<br>
+/// \brief Instances of this class represent the information from a<br>
+/// .cv_loc directive.<br>
+class MCCVLoc {<br>
+  uint32_t FunctionId;<br>
+  uint32_t FileNum;<br>
+  uint32_t Line;<br>
+  uint16_t Column;<br>
+  uint16_t PrologueEnd : 1;<br>
+  uint16_t IsStmt : 1;<br>
+<br>
+private: // MCContext manages these<br>
+  friend class MCContext;<br>
+  MCCVLoc(unsigned functionid, unsigned fileNum, unsigned line, unsigned column,<br>
+          bool prologueend, bool isstmt)<br>
+      : FunctionId(functionid), FileNum(fileNum), Line(line), Column(column),<br>
+        PrologueEnd(prologueend), IsStmt(isstmt) {}<br>
+<br>
+  // Allow the default copy constructor and assignment operator to be used<br>
+  // for an MCCVLoc object.<br>
+<br>
+public:<br>
+  unsigned getFunctionId() const { return FunctionId; }<br>
+<br>
+  /// \brief Get the FileNum of this MCCVLoc.<br>
+  unsigned getFileNum() const { return FileNum; }<br>
+<br>
+  /// \brief Get the Line of this MCCVLoc.<br>
+  unsigned getLine() const { return Line; }<br>
+<br>
+  /// \brief Get the Column of this MCCVLoc.<br>
+  unsigned getColumn() const { return Column; }<br>
+<br>
+  bool isPrologueEnd() const { return PrologueEnd; }<br>
+  bool isStmt() const { return IsStmt; }<br>
+<br>
+  void setFunctionId(unsigned FID) { FunctionId = FID; }<br>
+<br>
+  /// \brief Set the FileNum of this MCCVLoc.<br>
+  void setFileNum(unsigned fileNum) { FileNum = fileNum; }<br>
+<br>
+  /// \brief Set the Line of this MCCVLoc.<br>
+  void setLine(unsigned line) { Line = line; }<br>
+<br>
+  /// \brief Set the Column of this MCCVLoc.<br>
+  void setColumn(unsigned column) {<br>
+    assert(column <= UINT16_MAX);<br>
+    Column = column;<br>
+  }<br>
+<br>
+  void setPrologueEnd(bool PE) { PrologueEnd = PE; }<br>
+  void setIsStmt(bool IS) { IsStmt = IS; }<br>
+};<br>
+<br>
+/// \brief Instances of this class represent the line information for<br>
+/// the CodeView line table entries.  Which is created after a machine<br>
+/// instruction is assembled and uses an address from a temporary label<br>
+/// created at the current address in the current section and the info from<br>
+/// the last .cv_loc directive seen as stored in the context.<br>
+class MCCVLineEntry : public MCCVLoc {<br>
+  MCSymbol *Label;<br>
+<br>
+private:<br>
+  // Allow the default copy constructor and assignment operator to be used<br>
+  // for an MCCVLineEntry object.<br>
+<br>
+public:<br>
+  // Constructor to create an MCCVLineEntry given a symbol and the dwarf loc.<br>
+  MCCVLineEntry(MCSymbol *label, const MCCVLoc loc)<br>
+      : MCCVLoc(loc), Label(label) {}<br>
+<br>
+  MCSymbol *getLabel() const { return Label; }<br>
+<br>
+  // This is called when an instruction is assembled into the specified<br>
+  // section and if there is information from the last .cv_loc directive that<br>
+  // has yet to have a line entry made for it is made.<br>
+  static void Make(MCObjectStreamer *MCOS);<br>
+};<br>
+<br>
+/// Holds state from .cv_file and .cv_loc directives for later emission.<br>
+class CodeViewContext {<br>
+public:<br>
+  CodeViewContext();<br>
+  ~CodeViewContext();<br>
+<br>
+  bool isValidFileNumber(unsigned FileNumber) const;<br>
+  bool addFile(unsigned FileNumber, StringRef Filename);<br>
+  ArrayRef<StringRef> getFilenames() { return Filenames; }<br>
+<br>
+  /// \brief Add a line entry.<br>
+  void addLineEntry(const MCCVLineEntry &LineEntry) {<br>
+    MCCVLines[LineEntry.getFunctionId()].push_back(LineEntry);<br>
+  }<br>
+<br>
+  ArrayRef<MCCVLineEntry> getFunctionLineEntries(unsigned FuncId) {<br>
+    assert(MCCVLines.find(FuncId) != MCCVLines.end());<br>
+    return MCCVLines.find(FuncId)->second;<br>
+  }<br>
+<br>
+  /// Emits a line table substream.<br>
+  void emitLineTableForFunction(MCObjectStreamer &OS, unsigned FuncId,<br>
+                                const MCSymbol *FuncBegin,<br>
+                                const MCSymbol *FuncEnd);<br>
+<br>
+  /// Emits the string table substream.<br>
+  void emitStringTable(MCObjectStreamer &OS);<br>
+<br>
+  /// Emits the file checksum substream.<br>
+  void emitFileChecksums(MCObjectStreamer &OS);<br>
+<br>
+private:<br>
+  /// Map from string to string table offset.<br>
+  StringMap<unsigned> StringTable;<br>
+<br>
+  /// The fragment that ultimately holds our strings.<br>
+  MCDataFragment *StrTabFragment = nullptr;<br>
+  bool InsertedStrTabFragment = false;<br>
+<br>
+  MCDataFragment *getStringTableFragment();<br>
+<br>
+  /// Add something to the string table.<br>
+  StringRef addToStringTable(StringRef S);<br>
+<br>
+  /// Get a string table offset.<br>
+  unsigned getStringTableOffset(StringRef S);<br>
+<br>
+  /// An array of absolute paths. Eventually this may include the file checksum.<br>
+  SmallVector<StringRef, 4> Filenames;<br>
+<br>
+  /// A collection of MCDwarfLineEntry for each section.<br>
+  std::map<int, std::vector<MCCVLineEntry>> MCCVLines;<br>
+};<br>
+<br>
+} // end namespace llvm<br>
+#endif<br>
<br>
Modified: llvm/trunk/include/llvm/MC/MCContext.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/MC/MCContext.h?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/MC/MCContext.h?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/include/llvm/MC/MCContext.h (original)<br>
+++ llvm/trunk/include/llvm/MC/MCContext.h Thu Jan 28 18:49:42 2016<br>
@@ -16,6 +16,7 @@<br>
 #include "llvm/ADT/SmallVector.h"<br>
 #include "llvm/ADT/StringMap.h"<br>
 #include "llvm/ADT/Twine.h"<br>
+#include "llvm/MC/MCCodeView.h"<br>
 #include "llvm/MC/MCDwarf.h"<br>
 #include "llvm/MC/MCSubtargetInfo.h"<br>
 #include "llvm/MC/SectionKind.h"<br>
@@ -42,6 +43,7 @@ namespace llvm {<br>
   class MCSectionMachO;<br>
   class MCSectionELF;<br>
   class MCSectionCOFF;<br>
+  class CodeViewContext;<br>
<br>
   /// Context object for machine code objects.  This class owns all of the<br>
   /// sections that it creates.<br>
@@ -66,6 +68,8 @@ namespace llvm {<br>
     /// The MCObjectFileInfo for this target.<br>
     const MCObjectFileInfo *MOFI;<br>
<br>
+    std::unique_ptr<CodeViewContext> CVContext;<br>
+<br>
     /// Allocator object used for creating machine code objects.<br>
     ///<br>
     /// We use a bump pointer allocator to avoid the need to track all allocated<br>
@@ -135,6 +139,10 @@ namespace llvm {<br>
     MCDwarfLoc CurrentDwarfLoc;<br>
     bool DwarfLocSeen;<br>
<br>
+    /// The current CodeView line information from the last .cv_loc directive.<br>
+    MCCVLoc CurrentCVLoc = MCCVLoc(0, 0, 0, 0, false, true);<br>
+    bool CVLocSeen = false;<br>
+<br>
     /// Generate dwarf debugging info for assembly source files.<br>
     bool GenDwarfForAssembly;<br>
<br>
@@ -237,6 +245,8 @@ namespace llvm {<br>
<br>
     const MCObjectFileInfo *getObjectFileInfo() const { return MOFI; }<br>
<br>
+    CodeViewContext &getCVContext();<br>
+<br>
     void setAllowTemporaryLabels(bool Value) { AllowTemporaryLabels = Value; }<br>
     void setUseNamesOnTempLabels(bool Value) { UseNamesOnTempLabels = Value; }<br>
<br>
@@ -505,6 +515,35 @@ namespace llvm {<br>
<br>
     /// @}<br>
<br>
+<br>
+    /// \name CodeView Management<br>
+    /// @{<br>
+<br>
+    /// Creates an entry in the cv file table.<br>
+    unsigned getCVFile(StringRef FileName, unsigned FileNumber);<br>
+<br>
+    /// Saves the information from the currently parsed .cv_loc directive<br>
+    /// and sets CVLocSeen.  When the next instruction is assembled an entry<br>
+    /// in the line number table with this information and the address of the<br>
+    /// instruction will be created.<br>
+    void setCurrentCVLoc(unsigned FunctionId, unsigned FileNo, unsigned Line,<br>
+                         unsigned Column, bool PrologueEnd, bool IsStmt) {<br>
+      CurrentCVLoc.setFunctionId(FunctionId);<br>
+      CurrentCVLoc.setFileNum(FileNo);<br>
+      CurrentCVLoc.setLine(Line);<br>
+      CurrentCVLoc.setColumn(Column);<br>
+      CurrentCVLoc.setPrologueEnd(PrologueEnd);<br>
+      CurrentCVLoc.setIsStmt(IsStmt);<br>
+      CVLocSeen = true;<br>
+    }<br>
+    void clearCVLocSeen() { CVLocSeen = false; }<br>
+<br>
+    bool getCVLocSeen() { return CVLocSeen; }<br>
+    const MCCVLoc &getCurrentCVLoc() { return CurrentCVLoc; }<br>
+<br>
+    bool isValidCVFileNumber(unsigned FileNumber);<br>
+    /// @}<br>
+<br>
     char *getSecureLogFile() { return SecureLogFile; }<br>
     raw_fd_ostream *getSecureLog() { return SecureLog.get(); }<br>
     bool getSecureLogUsed() { return SecureLogUsed; }<br>
<br>
Modified: llvm/trunk/include/llvm/MC/MCObjectStreamer.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/MC/MCObjectStreamer.h?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/MC/MCObjectStreamer.h?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/include/llvm/MC/MCObjectStreamer.h (original)<br>
+++ llvm/trunk/include/llvm/MC/MCObjectStreamer.h Thu Jan 28 18:49:42 2016<br>
@@ -59,7 +59,6 @@ public:<br>
   void EmitFrames(MCAsmBackend *MAB);<br>
   void EmitCFISections(bool EH, bool Debug) override;<br>
<br>
-protected:<br>
   MCFragment *getCurrentFragment() const;<br>
<br>
   void insert(MCFragment *F) {<br>
@@ -73,6 +72,7 @@ protected:<br>
   /// fragment is not a data fragment.<br>
   MCDataFragment *getOrCreateDataFragment();<br>
<br>
+protected:<br>
   bool changeSectionImpl(MCSection *Section, const MCExpr *Subsection);<br>
<br>
   /// If any labels have been emitted but not assigned fragments, ensure that<br>
@@ -122,6 +122,13 @@ public:<br>
                                 unsigned PointerSize);<br>
   void EmitDwarfAdvanceFrameAddr(const MCSymbol *LastLabel,<br>
                                  const MCSymbol *Label);<br>
+  void EmitCVLocDirective(unsigned FunctionId, unsigned FileNo, unsigned Line,<br>
+                          unsigned Column, bool PrologueEnd, bool IsStmt,<br>
+                          StringRef FileName) override;<br>
+  void EmitCVLinetableDirective(unsigned FunctionId, const MCSymbol *Begin,<br>
+                                const MCSymbol *End) override;<br>
+  void EmitCVStringTableDirective() override;<br>
+  void EmitCVFileChecksumsDirective() override;<br>
   void EmitGPRel32Value(const MCExpr *Value) override;<br>
   void EmitGPRel64Value(const MCExpr *Value) override;<br>
   bool EmitRelocDirective(const MCExpr &Offset, StringRef Name,<br>
<br>
Modified: llvm/trunk/include/llvm/MC/MCStreamer.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/MC/MCStreamer.h?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/MC/MCStreamer.h?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/include/llvm/MC/MCStreamer.h (original)<br>
+++ llvm/trunk/include/llvm/MC/MCStreamer.h Thu Jan 28 18:49:42 2016<br>
@@ -640,6 +640,27 @@ public:<br>
                                      unsigned Isa, unsigned Discriminator,<br>
                                      StringRef FileName);<br>
<br>
+  /// \brief Associate a filename with a specified logical file number.  This<br>
+  /// implements the '.cv_file 4 "foo.c"' assembler directive.<br>
+  virtual unsigned EmitCVFileDirective(unsigned FileNo, StringRef Filename);<br>
+<br>
+  /// \brief This implements the CodeView '.cv_loc' assembler directive.<br>
+  virtual void EmitCVLocDirective(unsigned FunctionId, unsigned FileNo,<br>
+                                  unsigned Line, unsigned Column,<br>
+                                  bool PrologueEnd, bool IsStmt,<br>
+                                  StringRef FileName);<br>
+<br>
+  /// \brief This implements the CodeView '.cv_linetable' assembler directive.<br>
+  virtual void EmitCVLinetableDirective(unsigned FunctionId,<br>
+                                        const MCSymbol *FnStart,<br>
+                                        const MCSymbol *FnEnd);<br>
+<br>
+  /// \brief This implements the CodeView '.cv_stringtable' assembler directive.<br>
+  virtual void EmitCVStringTableDirective() {}<br>
+<br>
+  /// \brief This implements the CodeView '.cv_filechecksums' assembler directive.<br>
+  virtual void EmitCVFileChecksumsDirective() {}<br>
+<br>
   /// Emit the absolute difference between two symbols.<br>
   ///<br>
   /// \pre Offset of \c Hi is greater than the offset \c Lo.<br>
<br>
Modified: llvm/trunk/include/llvm/MC/StringTableBuilder.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/MC/StringTableBuilder.h?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/MC/StringTableBuilder.h?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/include/llvm/MC/StringTableBuilder.h (original)<br>
+++ llvm/trunk/include/llvm/MC/StringTableBuilder.h Thu Jan 28 18:49:42 2016<br>
@@ -27,6 +27,8 @@ private:<br>
   size_t Size = 0;<br>
   Kind K;<br>
<br>
+  void finalizeStringTable(bool Optimize);<br>
+<br>
 public:<br>
   StringTableBuilder(Kind K);<br>
<br>
@@ -39,6 +41,10 @@ public:<br>
   /// be added after this point.<br>
   void finalize();<br>
<br>
+  /// Finalize the string table without reording it. In this mode, offsets<br>
+  /// returned by add will still be valid.<br>
+  void finalizeInOrder();<br>
+<br>
   /// \brief Retrieve the string table data. Can only be used after the table<br>
   /// is finalized.<br>
   StringRef data() const {<br>
<br>
Modified: llvm/trunk/include/llvm/Support/COFF.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/Support/COFF.h?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/Support/COFF.h?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/include/llvm/Support/COFF.h (original)<br>
+++ llvm/trunk/include/llvm/Support/COFF.h Thu Jan 28 18:49:42 2016<br>
@@ -656,17 +656,7 @@ namespace COFF {<br>
     }<br>
   };<br>
<br>
-  enum CodeViewLine : unsigned {<br>
-    CVL_LineNumberStartBits = 24,<br>
-    CVL_LineNumberEndDeltaBits = 7,<br>
-    CVL_LineNumberEndDeltaMask = (1U << CVL_LineNumberEndDeltaBits) - 1,<br>
-    CVL_MaxLineNumber = (1U << CVL_LineNumberStartBits) - 1,<br>
-    CVL_IsStatement = 1U << 31,<br>
-    CVL_MaxColumnNumber = UINT16_MAX,<br>
-  };<br>
-<br>
   enum CodeViewIdentifiers {<br>
-    DEBUG_LINE_TABLES_HAVE_COLUMN_RECORDS = 0x1,<br>
     DEBUG_SECTION_MAGIC = 0x4,<br>
   };<br>
<br>
<br>
Modified: llvm/trunk/lib/CodeGen/AsmPrinter/CodeViewDebug.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/AsmPrinter/CodeViewDebug.cpp?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/AsmPrinter/CodeViewDebug.cpp?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/CodeGen/AsmPrinter/CodeViewDebug.cpp (original)<br>
+++ llvm/trunk/lib/CodeGen/AsmPrinter/CodeViewDebug.cpp Thu Jan 28 18:49:42 2016<br>
@@ -13,6 +13,7 @@<br>
<br>
 #include "CodeViewDebug.h"<br>
 #include "llvm/DebugInfo/CodeView/CodeView.h"<br>
+#include "llvm/DebugInfo/CodeView/Line.h"<br>
 #include "llvm/DebugInfo/CodeView/SymbolRecord.h"<br>
 #include "llvm/MC/MCExpr.h"<br>
 #include "llvm/MC/MCSymbol.h"<br>
@@ -74,6 +75,18 @@ StringRef CodeViewDebug::getFullFilepath<br>
   return Filepath;<br>
 }<br>
<br>
+unsigned CodeViewDebug::maybeRecordFile(const DIFile *F) {<br>
+  unsigned NextId = FileIdMap.size() + 1;<br>
+  auto Insertion = FileIdMap.insert(std::make_pair(F, NextId));<br>
+  if (Insertion.second) {<br>
+    // We have to compute the full filepath and emit a .cv_file directive.<br>
+    StringRef FullPath = getFullFilepath(F);<br>
+    NextId = Asm->OutStreamer->EmitCVFileDirective(NextId, FullPath);<br>
+    assert(NextId == FileIdMap.size() && ".cv_file directive failed");<br>
+  }<br>
+  return Insertion.first->second;<br>
+}<br>
+<br>
 void CodeViewDebug::maybeRecordLocation(DebugLoc DL,<br>
                                         const MachineFunction *MF) {<br>
   // Skip this instruction if it has the same location as the previous one.<br>
@@ -85,15 +98,26 @@ void CodeViewDebug::maybeRecordLocation(<br>
     return;<br>
<br>
   // Skip this line if it is longer than the maximum we can record.<br>
-  if (DL.getLine() > COFF::CVL_MaxLineNumber)<br>
+  LineInfo LI(DL.getLine(), DL.getLine(), /*IsStatement=*/true);<br>
+  if (LI.getStartLine() != DL.getLine() || LI.isAlwaysStepInto() ||<br>
+      LI.isNeverStepInto())<br>
     return;<br>
<br>
-  CurFn->LastLoc = DL;<br>
+  ColumnInfo CI(DL.getCol(), /*EndColumn=*/0);<br>
+  if (CI.getStartColumn() != DL.getCol())<br>
+    return;<br>
<br>
-  MCSymbol *MCL = Asm->MMI->getContext().createTempSymbol();<br>
-  Asm->OutStreamer->EmitLabel(MCL);<br>
-  CurFn->Instrs.push_back(MCL);<br>
-  LabelsAndLocs[MCL] = DL;<br>
+  if (!CurFn->HaveLineInfo)<br>
+    CurFn->HaveLineInfo = true;<br>
+  unsigned FileId = 0;<br>
+  if (CurFn->LastLoc.get() && CurFn->LastLoc->getFile() == DL->getFile())<br>
+    FileId = CurFn->LastFileId;<br>
+  else<br>
+    FileId = CurFn->LastFileId = maybeRecordFile(DL->getFile());<br>
+  CurFn->LastLoc = DL;<br>
+  Asm->OutStreamer->EmitCVLocDirective(CurFn->FuncId, FileId, DL.getLine(),<br>
+                                       DL.getCol(), /*PrologueEnd=*/false,<br>
+                                       /*IsStmt=*/false, DL->getFilename());<br>
 }<br>
<br>
 CodeViewDebug::CodeViewDebug(AsmPrinter *AP)<br>
@@ -128,39 +152,17 @@ void CodeViewDebug::endModule() {<br>
   // of the payload followed by the payload itself.  The subsections are 4-byte<br>
   // aligned.<br>
<br>
-  // Emit per-function debug information.  This code is extracted into a<br>
-  // separate function for readability.<br>
-  for (size_t I = 0, E = VisitedFunctions.size(); I != E; ++I)<br>
-    emitDebugInfoForFunction(VisitedFunctions[I]);<br>
+  // Emit per-function debug information.<br>
+  for (auto &P : FnDebugInfo)<br>
+    emitDebugInfoForFunction(P.first, P.second);<br>
<br>
   // This subsection holds a file index to offset in string table table.<br>
   Asm->OutStreamer->AddComment("File index to string table offset subsection");<br>
-  Asm->EmitInt32(unsigned(ModuleSubstreamKind::FileChecksums));<br>
-  size_t NumFilenames = FileNameRegistry.Infos.size();<br>
-  Asm->EmitInt32(8 * NumFilenames);<br>
-  for (size_t I = 0, E = FileNameRegistry.Filenames.size(); I != E; ++I) {<br>
-    StringRef Filename = FileNameRegistry.Filenames[I];<br>
-    // For each unique filename, just write its offset in the string table.<br>
-    Asm->EmitInt32(FileNameRegistry.Infos[Filename].StartOffset);<br>
-    // The function name offset is not followed by any additional data.<br>
-    Asm->EmitInt32(0);<br>
-  }<br>
+  Asm->OutStreamer->EmitCVFileChecksumsDirective();<br>
<br>
   // This subsection holds the string table.<br>
   Asm->OutStreamer->AddComment("String table");<br>
-  Asm->EmitInt32(unsigned(ModuleSubstreamKind::StringTable));<br>
-  Asm->EmitInt32(FileNameRegistry.LastOffset);<br>
-  // The payload starts with a null character.<br>
-  Asm->EmitInt8(0);<br>
-<br>
-  for (size_t I = 0, E = FileNameRegistry.Filenames.size(); I != E; ++I) {<br>
-    // Just emit unique filenames one by one, separated by a null character.<br>
-    Asm->OutStreamer->EmitBytes(FileNameRegistry.Filenames[I]);<br>
-    Asm->EmitInt8(0);<br>
-  }<br>
-<br>
-  // No more subsections. Fill with zeros to align the end of the section by 4.<br>
-  Asm->OutStreamer->EmitFill((-FileNameRegistry.LastOffset) % 4, 0);<br>
+  Asm->OutStreamer->EmitCVStringTableDirective();<br>
<br>
   clear();<br>
 }<br>
@@ -177,21 +179,13 @@ static void EmitLabelDiff(MCStreamer &St<br>
   Streamer.EmitValue(AddrDelta, Size);<br>
 }<br>
<br>
-static const DIFile *getFileFromLoc(DebugLoc DL) {<br>
-  return DL.get()->getScope()->getFile();<br>
-}<br>
-<br>
-void CodeViewDebug::emitDebugInfoForFunction(const Function *GV) {<br>
+void CodeViewDebug::emitDebugInfoForFunction(const Function *GV,<br>
+                                             FunctionInfo &FI) {<br>
   // For each function there is a separate subsection<br>
   // which holds the PC to file:line table.<br>
   const MCSymbol *Fn = Asm->getSymbol(GV);<br>
   assert(Fn);<br>
<br>
-  const FunctionInfo &FI = FnDebugInfo[GV];<br>
-  if (FI.Instrs.empty())<br>
-    return;<br>
-  assert(FI.End && "Don't know where the function ends?");<br>
-<br>
   StringRef FuncName;<br>
   if (auto *SP = getDISubprogram(GV))<br>
     FuncName = SP->getDisplayName();<br>
@@ -238,102 +232,8 @@ void CodeViewDebug::emitDebugInfoForFunc<br>
   // Every subsection must be aligned to a 4-byte boundary.<br>
   Asm->OutStreamer->EmitFill((-FuncName.size()) % 4, 0);<br>
<br>
-  // PCs/Instructions are grouped into segments sharing the same filename.<br>
-  // Pre-calculate the lengths (in instructions) of these segments and store<br>
-  // them in a map for convenience.  Each index in the map is the sequential<br>
-  // number of the respective instruction that starts a new segment.<br>
-  DenseMap<size_t, size_t> FilenameSegmentLengths;<br>
-  size_t LastSegmentEnd = 0;<br>
-  const DIFile *PrevFile = getFileFromLoc(LabelsAndLocs[FI.Instrs[0]]);<br>
-  for (size_t J = 1, F = FI.Instrs.size(); J != F; ++J) {<br>
-    const DIFile *CurFile = getFileFromLoc(LabelsAndLocs[FI.Instrs[J]]);<br>
-    if (PrevFile == CurFile)<br>
-      continue;<br>
-    FilenameSegmentLengths[LastSegmentEnd] = J - LastSegmentEnd;<br>
-    LastSegmentEnd = J;<br>
-    PrevFile = CurFile;<br>
-  }<br>
-  FilenameSegmentLengths[LastSegmentEnd] = FI.Instrs.size() - LastSegmentEnd;<br>
-<br>
-  // Emit a line table subsection, required to do PC-to-file:line lookup.<br>
-  Asm->OutStreamer->AddComment("Line table subsection for " + Twine(FuncName));<br>
-  Asm->EmitInt32(unsigned(ModuleSubstreamKind::Lines));<br>
-  MCSymbol *LineTableBegin = Asm->MMI->getContext().createTempSymbol(),<br>
-           *LineTableEnd = Asm->MMI->getContext().createTempSymbol();<br>
-  EmitLabelDiff(*Asm->OutStreamer, LineTableBegin, LineTableEnd);<br>
-  Asm->OutStreamer->EmitLabel(LineTableBegin);<br>
-<br>
-  // Identify the function this subsection is for.<br>
-  Asm->OutStreamer->EmitCOFFSecRel32(Fn);<br>
-  Asm->OutStreamer->EmitCOFFSectionIndex(Fn);<br>
-  // Insert flags after a 16-bit section index.<br>
-  Asm->EmitInt16(COFF::DEBUG_LINE_TABLES_HAVE_COLUMN_RECORDS);<br>
-<br>
-  // Length of the function's code, in bytes.<br>
-  EmitLabelDiff(*Asm->OutStreamer, Fn, FI.End);<br>
-<br>
-  // PC-to-linenumber lookup table:<br>
-  MCSymbol *FileSegmentEnd = nullptr;<br>
-<br>
-  // The start of the last segment:<br>
-  size_t LastSegmentStart = 0;<br>
-<br>
-  auto FinishPreviousChunk = [&] {<br>
-    if (!FileSegmentEnd)<br>
-      return;<br>
-    for (size_t ColSegI = LastSegmentStart,<br>
-                ColSegEnd = ColSegI + FilenameSegmentLengths[LastSegmentStart];<br>
-         ColSegI != ColSegEnd; ++ColSegI) {<br>
-      unsigned ColumnNumber = LabelsAndLocs[FI.Instrs[ColSegI]].getCol();<br>
-      // Truncate the column number if it is longer than the maximum we can<br>
-      // record.<br>
-      if (ColumnNumber > COFF::CVL_MaxColumnNumber)<br>
-        ColumnNumber = 0;<br>
-      Asm->EmitInt16(ColumnNumber); // Start column<br>
-      Asm->EmitInt16(0);            // End column<br>
-    }<br>
-    Asm->OutStreamer->EmitLabel(FileSegmentEnd);<br>
-  };<br>
-<br>
-  for (size_t J = 0, F = FI.Instrs.size(); J != F; ++J) {<br>
-    MCSymbol *Instr = FI.Instrs[J];<br>
-    assert(LabelsAndLocs.count(Instr));<br>
-<br>
-    if (FilenameSegmentLengths.count(J)) {<br>
-      // We came to a beginning of a new filename segment.<br>
-      FinishPreviousChunk();<br>
-      const DIFile *File = getFileFromLoc(LabelsAndLocs[FI.Instrs[J]]);<br>
-      StringRef CurFilename = getFullFilepath(File);<br>
-      size_t IndexInFileTable = FileNameRegistry.add(CurFilename);<br>
-      // Each segment starts with the offset of the filename<br>
-      // in the string table.<br>
-      Asm->OutStreamer->AddComment(<br>
-          "Segment for file '" + Twine(CurFilename) + "' begins");<br>
-      MCSymbol *FileSegmentBegin = Asm->MMI->getContext().createTempSymbol();<br>
-      Asm->OutStreamer->EmitLabel(FileSegmentBegin);<br>
-      Asm->EmitInt32(8 * IndexInFileTable);<br>
-<br>
-      // Number of PC records in the lookup table.<br>
-      size_t SegmentLength = FilenameSegmentLengths[J];<br>
-      Asm->EmitInt32(SegmentLength);<br>
-<br>
-      // Full size of the segment for this filename, including the prev two<br>
-      // records.<br>
-      FileSegmentEnd = Asm->MMI->getContext().createTempSymbol();<br>
-      EmitLabelDiff(*Asm->OutStreamer, FileSegmentBegin, FileSegmentEnd);<br>
-      LastSegmentStart = J;<br>
-    }<br>
-<br>
-    // The first PC with the given linenumber and the linenumber itself.<br>
-    EmitLabelDiff(*Asm->OutStreamer, Fn, Instr);<br>
-    uint32_t LineNumber = LabelsAndLocs[Instr].getLine();<br>
-    assert(LineNumber <= COFF::CVL_MaxLineNumber);<br>
-    uint32_t LineData = LineNumber | COFF::CVL_IsStatement;<br>
-    Asm->EmitInt32(LineData);<br>
-  }<br>
-<br>
-  FinishPreviousChunk();<br>
-  Asm->OutStreamer->EmitLabel(LineTableEnd);<br>
+  // We have an assembler directive that takes care of the whole line table.<br>
+  Asm->OutStreamer->EmitCVLinetableDirective(FI.FuncId, Fn, FI.End);<br>
 }<br>
<br>
 void CodeViewDebug::beginFunction(const MachineFunction *MF) {<br>
@@ -344,8 +244,8 @@ void CodeViewDebug::beginFunction(const<br>
<br>
   const Function *GV = MF->getFunction();<br>
   assert(FnDebugInfo.count(GV) == false);<br>
-  VisitedFunctions.push_back(GV);<br>
   CurFn = &FnDebugInfo[GV];<br>
+  CurFn->FuncId = NextFuncId++;<br>
<br>
   // Find the end of the function prolog.<br>
   // FIXME: is there a simpler a way to do this? Can we just search<br>
@@ -384,9 +284,9 @@ void CodeViewDebug::endFunction(const Ma<br>
   assert(FnDebugInfo.count(GV));<br>
   assert(CurFn == &FnDebugInfo[GV]);<br>
<br>
-  if (CurFn->Instrs.empty()) {<br>
+  // Don't emit anything if we don't have any line tables.<br>
+  if (!CurFn->HaveLineInfo) {<br>
     FnDebugInfo.erase(GV);<br>
-    VisitedFunctions.pop_back();<br>
   } else {<br>
     CurFn->End = Asm->getFunctionEnd();<br>
   }<br>
<br>
Modified: llvm/trunk/lib/CodeGen/AsmPrinter/CodeViewDebug.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/AsmPrinter/CodeViewDebug.h?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/AsmPrinter/CodeViewDebug.h?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/CodeGen/AsmPrinter/CodeViewDebug.h (original)<br>
+++ llvm/trunk/lib/CodeGen/AsmPrinter/CodeViewDebug.h Thu Jan 28 18:49:42 2016<br>
@@ -37,72 +37,38 @@ class LLVM_LIBRARY_VISIBILITY CodeViewDe<br>
   // to the end of the function.<br>
   struct FunctionInfo {<br>
     DebugLoc LastLoc;<br>
-    SmallVector<MCSymbol *, 10> Instrs;<br>
-    MCSymbol *End;<br>
-    FunctionInfo() : End(nullptr) {}<br>
+    MCSymbol *End = nullptr;<br>
+    unsigned FuncId = 0;<br>
+    unsigned LastFileId;<br>
+    bool HaveLineInfo = false;<br>
   };<br>
   FunctionInfo *CurFn;<br>
<br>
-  typedef DenseMap<const Function *, FunctionInfo> FnDebugInfoTy;<br>
-  FnDebugInfoTy FnDebugInfo;<br>
-  // Store the functions we've visited in a vector so we can maintain a stable<br>
-  // order while emitting subsections.<br>
-  SmallVector<const Function *, 10> VisitedFunctions;<br>
-<br>
-  DenseMap<MCSymbol *, DebugLoc> LabelsAndLocs;<br>
-<br>
-  // FileNameRegistry - Manages filenames observed while generating debug info<br>
-  // by filtering out duplicates and bookkeeping the offsets in the string<br>
-  // table to be generated.<br>
-  struct FileNameRegistryTy {<br>
-    SmallVector<StringRef, 10> Filenames;<br>
-    struct PerFileInfo {<br>
-      size_t FilenameID, StartOffset;<br>
-    };<br>
-    StringMap<PerFileInfo> Infos;<br>
-<br>
-    // The offset in the string table where we'll write the next unique<br>
-    // filename.<br>
-    size_t LastOffset;<br>
-<br>
-    FileNameRegistryTy() {<br>
-      clear();<br>
-    }<br>
-<br>
-    // Add Filename to the registry, if it was not observed before.<br>
-    size_t add(StringRef Filename) {<br>
-      size_t OldSize = Infos.size();<br>
-      bool Inserted;<br>
-      StringMap<PerFileInfo>::iterator It;<br>
-      std::tie(It, Inserted) = Infos.insert(<br>
-          std::make_pair(Filename, PerFileInfo{OldSize, LastOffset}));<br>
-      if (Inserted) {<br>
-        LastOffset += Filename.size() + 1;<br>
-        Filenames.push_back(Filename);<br>
-      }<br>
-      return It->second.FilenameID;<br>
-    }<br>
-<br>
-    void clear() {<br>
-      LastOffset = 1;<br>
-      Infos.clear();<br>
-      Filenames.clear();<br>
-    }<br>
-  } FileNameRegistry;<br>
+  unsigned NextFuncId = 0;<br>
+<br>
+  /// Remember some debug info about each function. Keep it in a stable order to<br>
+  /// emit at the end of the TU.<br>
+  MapVector<const Function *, FunctionInfo> FnDebugInfo;<br>
+<br>
+  /// Map from DIFile to .cv_file id.<br>
+  DenseMap<const DIFile *, unsigned> FileIdMap;<br>
<br>
   typedef std::map<const DIFile *, std::string> FileToFilepathMapTy;<br>
   FileToFilepathMapTy FileToFilepathMap;<br>
   StringRef getFullFilepath(const DIFile *S);<br>
<br>
+  unsigned maybeRecordFile(const DIFile *F);<br>
+<br>
   void maybeRecordLocation(DebugLoc DL, const MachineFunction *MF);<br>
<br>
   void clear() {<br>
     assert(CurFn == nullptr);<br>
-    FileNameRegistry.clear();<br>
-    LabelsAndLocs.clear();<br>
+    FileIdMap.clear();<br>
+    FnDebugInfo.clear();<br>
+    FileToFilepathMap.clear();<br>
   }<br>
<br>
-  void emitDebugInfoForFunction(const Function *GV);<br>
+  void emitDebugInfoForFunction(const Function *GV, FunctionInfo &FI);<br>
<br>
 public:<br>
   CodeViewDebug(AsmPrinter *Asm);<br>
<br>
Modified: llvm/trunk/lib/CodeGen/AsmPrinter/LLVMBuild.txt<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/AsmPrinter/LLVMBuild.txt?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/AsmPrinter/LLVMBuild.txt?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/CodeGen/AsmPrinter/LLVMBuild.txt (original)<br>
+++ llvm/trunk/lib/CodeGen/AsmPrinter/LLVMBuild.txt Thu Jan 28 18:49:42 2016<br>
@@ -19,4 +19,4 @@<br>
 type = Library<br>
 name = AsmPrinter<br>
 parent = Libraries<br>
-required_libraries = Analysis CodeGen Core MC MCParser Support Target TransformUtils<br>
+required_libraries = Analysis CodeGen Core DebugInfoCodeView MC MCParser Support Target TransformUtils<br>
<br>
Modified: llvm/trunk/lib/MC/CMakeLists.txt<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/CMakeLists.txt?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/CMakeLists.txt?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/MC/CMakeLists.txt (original)<br>
+++ llvm/trunk/lib/MC/CMakeLists.txt Thu Jan 28 18:49:42 2016<br>
@@ -10,6 +10,7 @@ add_llvm_library(LLVMMC<br>
   MCAssembler.cpp<br>
   MCCodeEmitter.cpp<br>
   MCCodeGenInfo.cpp<br>
+  MCCodeView.cpp<br>
   MCContext.cpp<br>
   MCDwarf.cpp<br>
   MCELFObjectTargetWriter.cpp<br>
<br>
Modified: llvm/trunk/lib/MC/MCAsmStreamer.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/MCAsmStreamer.cpp?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/MCAsmStreamer.cpp?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/MC/MCAsmStreamer.cpp (original)<br>
+++ llvm/trunk/lib/MC/MCAsmStreamer.cpp Thu Jan 28 18:49:42 2016<br>
@@ -199,6 +199,15 @@ public:<br>
                              StringRef FileName) override;<br>
   MCSymbol *getDwarfLineTableSymbol(unsigned CUID) override;<br>
<br>
+  unsigned EmitCVFileDirective(unsigned FileNo, StringRef Filename) override;<br>
+  void EmitCVLocDirective(unsigned FunctionId, unsigned FileNo, unsigned Line,<br>
+                          unsigned Column, bool PrologueEnd, bool IsStmt,<br>
+                          StringRef FileName) override;<br>
+  void EmitCVLinetableDirective(unsigned FunctionId, const MCSymbol *FnStart,<br>
+                                const MCSymbol *FnEnd) override;<br>
+  void EmitCVStringTableDirective() override;<br>
+  void EmitCVFileChecksumsDirective() override;<br>
+<br>
   void EmitIdent(StringRef IdentString) override;<br>
   void EmitCFISections(bool EH, bool Debug) override;<br>
   void EmitCFIDefCfa(int64_t Register, int64_t Offset) override;<br>
@@ -954,6 +963,69 @@ MCSymbol *MCAsmStreamer::getDwarfLineTab<br>
   return MCStreamer::getDwarfLineTableSymbol(0);<br>
 }<br>
<br>
+unsigned MCAsmStreamer::EmitCVFileDirective(unsigned FileNo,<br>
+                                            StringRef Filename) {<br>
+  if (!getContext().getCVFile(Filename, FileNo))<br>
+    return 0;<br>
+<br>
+  OS << "\t.cv_file\t" << FileNo << ' ';<br>
+<br>
+  PrintQuotedString(Filename, OS);<br>
+  EmitEOL();<br>
+<br>
+  return FileNo;<br>
+}<br>
+<br>
+void MCAsmStreamer::EmitCVLocDirective(unsigned FunctionId, unsigned FileNo,<br>
+                                       unsigned Line, unsigned Column,<br>
+                                       bool PrologueEnd, bool IsStmt,<br>
+                                       StringRef FileName) {<br>
+  OS << "\t.cv_loc\t" << FunctionId << " " << FileNo << " " << Line << " "<br>
+     << Column;<br>
+  if (PrologueEnd)<br>
+    OS << " prologue_end";<br>
+<br>
+  unsigned OldIsStmt = getContext().getCurrentCVLoc().isStmt();<br>
+  if (IsStmt != OldIsStmt) {<br>
+    OS << " is_stmt ";<br>
+<br>
+    if (IsStmt)<br>
+      OS << "1";<br>
+    else<br>
+      OS << "0";<br>
+  }<br>
+<br>
+  if (IsVerboseAsm) {<br>
+    OS.PadToColumn(MAI->getCommentColumn());<br>
+    OS << MAI->getCommentString() << ' ' << FileName << ':'<br>
+       << Line << ':' << Column;<br>
+  }<br>
+  EmitEOL();<br>
+  this->MCStreamer::EmitCVLocDirective(FunctionId, FileNo, Line, Column,<br>
+                                       PrologueEnd, IsStmt, FileName);<br>
+}<br>
+<br>
+void MCAsmStreamer::EmitCVLinetableDirective(unsigned FunctionId,<br>
+                                             const MCSymbol *FnStart,<br>
+                                             const MCSymbol *FnEnd) {<br>
+  OS << "\t.cv_linetable\t" << FunctionId << ", ";<br>
+  FnStart->print(OS, MAI);<br>
+  OS << ", ";<br>
+  FnEnd->print(OS, MAI);<br>
+  EmitEOL();<br>
+  this->MCStreamer::EmitCVLinetableDirective(FunctionId, FnStart, FnEnd);<br>
+}<br>
+<br>
+void MCAsmStreamer::EmitCVStringTableDirective() {<br>
+  OS << "\t.cv_stringtable";<br>
+  EmitEOL();<br>
+}<br>
+<br>
+void MCAsmStreamer::EmitCVFileChecksumsDirective() {<br>
+  OS << "\t.cv_filechecksums";<br>
+  EmitEOL();<br>
+}<br>
+<br>
 void MCAsmStreamer::EmitIdent(StringRef IdentString) {<br>
   assert(MAI->hasIdentDirective() && ".ident directive not supported");<br>
   OS << "\t.ident\t";<br>
<br>
Added: llvm/trunk/lib/MC/MCCodeView.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/MCCodeView.cpp?rev=259130&view=auto" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/MCCodeView.cpp?rev=259130&view=auto</a><br>
==============================================================================<br>
--- llvm/trunk/lib/MC/MCCodeView.cpp (added)<br>
+++ llvm/trunk/lib/MC/MCCodeView.cpp Thu Jan 28 18:49:42 2016<br>
@@ -0,0 +1,222 @@<br>
+//===- MCCodeView.h - Machine Code CodeView support -------------*- C++ -*-===//<br>
+//<br>
+//                     The LLVM Compiler Infrastructure<br>
+//<br>
+// This file is distributed under the University of Illinois Open Source<br>
+// License. See LICENSE.TXT for details.<br>
+//<br>
+//===----------------------------------------------------------------------===//<br>
+//<br>
+// Holds state from .cv_file and .cv_loc directives for later emission.<br>
+//<br>
+//===----------------------------------------------------------------------===//<br>
+<br>
+#include "llvm/MC/MCCodeView.h"<br>
+#include "llvm/ADT/STLExtras.h"<br>
+#include "llvm/DebugInfo/CodeView/CodeView.h"<br>
+#include "llvm/DebugInfo/CodeView/Line.h"<br>
+#include "llvm/MC/MCContext.h"<br>
+#include "llvm/MC/MCObjectStreamer.h"<br>
+#include "llvm/Support/COFF.h"<br>
+<br>
+using namespace llvm;<br>
+using namespace llvm::codeview;<br>
+<br>
+CodeViewContext::CodeViewContext() {}<br>
+<br>
+CodeViewContext::~CodeViewContext() {<br>
+  // If someone inserted strings into the string table but never actually<br>
+  // emitted them somewhere, clean up the fragment.<br>
+  if (!InsertedStrTabFragment)<br>
+    delete StrTabFragment;<br>
+}<br>
+<br>
+/// This is a valid number for use with .cv_loc if we've already seen a .cv_file<br>
+/// for it.<br>
+bool CodeViewContext::isValidFileNumber(unsigned FileNumber) const {<br>
+  unsigned Idx = FileNumber - 1;<br>
+  if (Idx < Filenames.size())<br>
+    return !Filenames[Idx].empty();<br>
+  return false;<br>
+}<br>
+<br>
+bool CodeViewContext::addFile(unsigned FileNumber, StringRef Filename) {<br>
+  assert(FileNumber > 0);<br>
+  Filename = addToStringTable(Filename);<br>
+  unsigned Idx = FileNumber - 1;<br>
+  if (Idx >= Filenames.size())<br>
+    Filenames.resize(Idx + 1);<br>
+<br>
+  if (Filename.empty())<br>
+    Filename = "<stdin>";<br>
+<br>
+  if (!Filenames[Idx].empty())<br>
+    return false;<br>
+<br>
+  // FIXME: We should store the string table offset of the filename, rather than<br>
+  // the filename itself for efficiency.<br>
+  Filename = addToStringTable(Filename);<br>
+<br>
+  Filenames[Idx] = Filename;<br>
+  return true;<br>
+}<br>
+<br>
+MCDataFragment *CodeViewContext::getStringTableFragment() {<br>
+  if (!StrTabFragment) {<br>
+    StrTabFragment = new MCDataFragment();<br>
+    // Start a new string table out with a null byte.<br>
+    StrTabFragment->getContents().push_back('\0');<br>
+  }<br>
+  return StrTabFragment;<br>
+}<br>
+<br>
+StringRef CodeViewContext::addToStringTable(StringRef S) {<br>
+  SmallVectorImpl<char> &Contents = getStringTableFragment()->getContents();<br>
+  auto Insertion =<br>
+      StringTable.insert(std::make_pair(S, unsigned(Contents.size())));<br>
+  // Return the string from the table, since it is stable.<br>
+  S = Insertion.first->first();<br>
+  if (Insertion.second) {<br>
+    // The string map key is always null terminated.<br>
+    Contents.append(S.begin(), S.end() + 1);<br>
+  }<br>
+  return S;<br>
+}<br>
+<br>
+unsigned CodeViewContext::getStringTableOffset(StringRef S) {<br>
+  // A string table offset of zero is always the empty string.<br>
+  if (S.empty())<br>
+    return 0;<br>
+  auto I = StringTable.find(S);<br>
+  assert(I != StringTable.end());<br>
+  return I->second;<br>
+}<br>
+<br>
+void CodeViewContext::emitStringTable(MCObjectStreamer &OS) {<br>
+  MCContext &Ctx = OS.getContext();<br>
+  MCSymbol *StringBegin = Ctx.createTempSymbol("strtab_begin"),<br>
+           *StringEnd = Ctx.createTempSymbol("strtab_end");<br>
+<br>
+  OS.EmitIntValue(unsigned(ModuleSubstreamKind::StringTable), 4);<br>
+  OS.emitAbsoluteSymbolDiff(StringEnd, StringBegin, 4);<br>
+  OS.EmitLabel(StringBegin);<br>
+<br>
+  // Put the string table data fragment here, if we haven't already put it<br>
+  // somewhere else. If somebody wants two string tables in their .s file, one<br>
+  // will just be empty.<br>
+  if (!InsertedStrTabFragment) {<br>
+    OS.insert(getStringTableFragment());<br>
+    InsertedStrTabFragment = true;<br>
+  }<br>
+<br>
+  OS.EmitValueToAlignment(4, 0);<br>
+<br>
+  OS.EmitLabel(StringEnd);<br>
+}<br>
+<br>
+void CodeViewContext::emitFileChecksums(MCObjectStreamer &OS) {<br>
+  MCContext &Ctx = OS.getContext();<br>
+  MCSymbol *FileBegin = Ctx.createTempSymbol("filechecksums_begin"),<br>
+           *FileEnd = Ctx.createTempSymbol("filechecksums_end");<br>
+<br>
+  OS.EmitIntValue(unsigned(ModuleSubstreamKind::FileChecksums), 4);<br>
+  OS.emitAbsoluteSymbolDiff(FileEnd, FileBegin, 4);<br>
+  OS.EmitLabel(FileBegin);<br>
+<br>
+  // Emit an array of FileChecksum entries. We index into this table using the<br>
+  // user-provided file number. Each entry is currently 8 bytes, as we don't<br>
+  // emit checksums.<br>
+  for (StringRef Filename : Filenames) {<br>
+    OS.EmitIntValue(getStringTableOffset(Filename), 4);<br>
+    // Zero the next two fields and align back to 4 bytes. This indicates that<br>
+    // no checksum is present.<br>
+    OS.EmitIntValue(0, 4);<br>
+  }<br>
+<br>
+  OS.EmitLabel(FileEnd);<br>
+}<br>
+<br>
+void CodeViewContext::emitLineTableForFunction(MCObjectStreamer &OS,<br>
+                                               unsigned FuncId,<br>
+                                               const MCSymbol *FuncBegin,<br>
+                                               const MCSymbol *FuncEnd) {<br>
+  MCContext &Ctx = OS.getContext();<br>
+  MCSymbol *LineBegin = Ctx.createTempSymbol("linetable_begin"),<br>
+           *LineEnd = Ctx.createTempSymbol("linetable_end");<br>
+<br>
+  OS.EmitIntValue(unsigned(ModuleSubstreamKind::Lines), 4);<br>
+  OS.emitAbsoluteSymbolDiff(LineEnd, LineBegin, 4);<br>
+  OS.EmitLabel(LineBegin);<br>
+  OS.EmitCOFFSecRel32(FuncBegin);<br>
+  OS.EmitCOFFSectionIndex(FuncBegin);<br>
+<br>
+  // Actual line info.<br>
+  ArrayRef<MCCVLineEntry> Locs = getFunctionLineEntries(FuncId);<br>
+  bool HaveColumns = any_of(Locs, [](const MCCVLineEntry &LineEntry) {<br>
+    return LineEntry.getColumn() != 0;<br>
+  });<br>
+  OS.EmitIntValue(HaveColumns ? int(codeview::LineFlags::HaveColumns) : 0, 2);<br>
+  OS.emitAbsoluteSymbolDiff(FuncEnd, FuncBegin, 4);<br>
+<br>
+  for (auto I = Locs.begin(), E = Locs.end(); I != E;) {<br>
+    // Emit a file segment for the run of locations that share a file id.<br>
+    unsigned CurFileNum = I->getFileNum();<br>
+    auto FileSegEnd =<br>
+        std::find_if(I, E, [CurFileNum](const MCCVLineEntry &Loc) {<br>
+          return Loc.getFileNum() != CurFileNum;<br>
+        });<br>
+    unsigned EntryCount = FileSegEnd - I;<br>
+    OS.AddComment("Segment for file '" + Twine(Filenames[CurFileNum - 1]) +<br>
+                  "' begins");<br>
+    OS.EmitIntValue(8 * (CurFileNum - 1), 4);<br>
+    OS.EmitIntValue(EntryCount, 4);<br>
+    uint32_t SegmentSize = 12;<br>
+    SegmentSize += 8 * EntryCount;<br>
+    if (HaveColumns)<br>
+      SegmentSize += 4 * EntryCount;<br>
+    OS.EmitIntValue(SegmentSize, 4);<br>
+<br>
+    for (auto J = I; J != FileSegEnd; ++J) {<br>
+      OS.emitAbsoluteSymbolDiff(J->getLabel(), FuncBegin, 4);<br>
+      unsigned LineData = J->getLine();<br>
+      if (J->isStmt())<br>
+        LineData |= codeview::LineInfo::StatementFlag;<br>
+      OS.EmitIntValue(LineData, 4);<br>
+    }<br>
+    if (HaveColumns) {<br>
+      for (auto J = I; J != FileSegEnd; ++J) {<br>
+        OS.EmitIntValue(J->getColumn(), 2);<br>
+        OS.EmitIntValue(0, 2);<br>
+      }<br>
+    }<br>
+    I = FileSegEnd;<br>
+  }<br>
+  OS.EmitLabel(LineEnd);<br>
+}<br>
+<br>
+//<br>
+// This is called when an instruction is assembled into the specified section<br>
+// and if there is information from the last .cv_loc directive that has yet to have<br>
+// a line entry made for it is made.<br>
+//<br>
+void MCCVLineEntry::Make(MCObjectStreamer *MCOS) {<br>
+  if (!MCOS->getContext().getCVLocSeen())<br>
+    return;<br>
+<br>
+  // Create a symbol at in the current section for use in the line entry.<br>
+  MCSymbol *LineSym = MCOS->getContext().createTempSymbol();<br>
+  // Set the value of the symbol to use for the MCCVLineEntry.<br>
+  MCOS->EmitLabel(LineSym);<br>
+<br>
+  // Get the current .loc info saved in the context.<br>
+  const MCCVLoc &CVLoc = MCOS->getContext().getCurrentCVLoc();<br>
+<br>
+  // Create a (local) line entry with the symbol and the current .loc info.<br>
+  MCCVLineEntry LineEntry(LineSym, CVLoc);<br>
+<br>
+  // clear CVLocSeen saying the current .loc info is now used.<br>
+  MCOS->getContext().clearCVLocSeen();<br>
+<br>
+  // Add the line entry to this section's entries.<br>
+  MCOS->getContext().getCVContext().addLineEntry(LineEntry);<br>
+}<br>
<br>
Modified: llvm/trunk/lib/MC/MCContext.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/MCContext.cpp?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/MCContext.cpp?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/MC/MCContext.cpp (original)<br>
+++ llvm/trunk/lib/MC/MCContext.cpp Thu Jan 28 18:49:42 2016<br>
@@ -12,6 +12,7 @@<br>
 #include "llvm/ADT/Twine.h"<br>
 #include "llvm/MC/MCAssembler.h"<br>
 #include "llvm/MC/MCAsmInfo.h"<br>
+#include "llvm/MC/MCCodeView.h"<br>
 #include "llvm/MC/MCDwarf.h"<br>
 #include "llvm/MC/MCLabel.h"<br>
 #include "llvm/MC/MCObjectFileInfo.h"<br>
@@ -90,6 +91,8 @@ void MCContext::reset() {<br>
   DwarfCompileUnitID = 0;<br>
   CurrentDwarfLoc = MCDwarfLoc(0, 0, 0, DWARF2_FLAG_IS_STMT, 0, 0);<br>
<br>
+  CVContext.reset();<br>
+<br>
   MachOUniquingMap.clear();<br>
   ELFUniquingMap.clear();<br>
   COFFUniquingMap.clear();<br>
@@ -474,6 +477,20 @@ void MCContext::finalizeDwarfSections(MC<br>
       [&](MCSection *Sec) { return !MCOS.mayHaveInstructions(*Sec); });<br>
 }<br>
<br>
+CodeViewContext &MCContext::getCVContext() {<br>
+  if (!CVContext.get())<br>
+    CVContext.reset(new CodeViewContext);<br>
+  return *CVContext.get();<br>
+}<br>
+<br>
+unsigned MCContext::getCVFile(StringRef FileName, unsigned FileNumber) {<br>
+  return getCVContext().addFile(FileNumber, FileName) ? FileNumber : 0;<br>
+}<br>
+<br>
+bool MCContext::isValidCVFileNumber(unsigned FileNumber) {<br>
+  return getCVContext().isValidFileNumber(FileNumber);<br>
+}<br>
+<br>
 //===----------------------------------------------------------------------===//<br>
 // Error Reporting<br>
 //===----------------------------------------------------------------------===//<br>
<br>
Modified: llvm/trunk/lib/MC/MCObjectStreamer.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/MCObjectStreamer.cpp?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/MCObjectStreamer.cpp?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/MC/MCObjectStreamer.cpp (original)<br>
+++ llvm/trunk/lib/MC/MCObjectStreamer.cpp Thu Jan 28 18:49:42 2016<br>
@@ -125,6 +125,7 @@ void MCObjectStreamer::EmitValueImpl(con<br>
   MCDataFragment *DF = getOrCreateDataFragment();<br>
   flushPendingLabels(DF, DF->getContents().size());<br>
<br>
+  MCCVLineEntry::Make(this);<br>
   MCDwarfLineEntry::Make(this, getCurrentSection().first);<br>
<br>
   // Avoid fixups when possible.<br>
@@ -232,6 +233,7 @@ void MCObjectStreamer::EmitInstruction(c<br>
<br>
   // Now that a machine instruction has been assembled into this section, make<br>
   // a line entry for any .loc directive that has been seen.<br>
+  MCCVLineEntry::Make(this);<br>
   MCDwarfLineEntry::Make(this, getCurrentSection().first);<br>
<br>
   // If this instruction doesn't need relaxation, just emit it as data.<br>
@@ -362,7 +364,36 @@ void MCObjectStreamer::EmitDwarfAdvanceF<br>
   insert(new MCDwarfCallFrameFragment(*AddrDelta));<br>
 }<br>
<br>
+void MCObjectStreamer::EmitCVLocDirective(unsigned FunctionId, unsigned FileNo,<br>
+                                          unsigned Line, unsigned Column,<br>
+                                          bool PrologueEnd, bool IsStmt,<br>
+                                          StringRef FileName) {<br>
+  // In case we see two .cv_loc directives in a row, make sure the<br>
+  // first one gets a line entry.<br>
+  MCCVLineEntry::Make(this);<br>
+<br>
+  this->MCStreamer::EmitCVLocDirective(FunctionId, FileNo, Line, Column,<br>
+                                       PrologueEnd, IsStmt, FileName);<br>
+}<br>
+<br>
+void MCObjectStreamer::EmitCVLinetableDirective(unsigned FunctionId,<br>
+                                                const MCSymbol *Begin,<br>
+                                                const MCSymbol *End) {<br>
+  getContext().getCVContext().emitLineTableForFunction(*this, FunctionId, Begin,<br>
+                                                       End);<br>
+  this->MCStreamer::EmitCVLinetableDirective(FunctionId, Begin, End);<br>
+}<br>
+<br>
+void MCObjectStreamer::EmitCVStringTableDirective() {<br>
+  getContext().getCVContext().emitStringTable(*this);<br>
+}<br>
+void MCObjectStreamer::EmitCVFileChecksumsDirective() {<br>
+  getContext().getCVContext().emitFileChecksums(*this);<br>
+}<br>
+<br>
+<br>
 void MCObjectStreamer::EmitBytes(StringRef Data) {<br>
+  MCCVLineEntry::Make(this);<br>
   MCDwarfLineEntry::Make(this, getCurrentSection().first);<br>
   MCDataFragment *DF = getOrCreateDataFragment();<br>
   flushPendingLabels(DF, DF->getContents().size());<br>
<br>
Modified: llvm/trunk/lib/MC/MCParser/AsmParser.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/MCParser/AsmParser.cpp?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/MCParser/AsmParser.cpp?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/MC/MCParser/AsmParser.cpp (original)<br>
+++ llvm/trunk/lib/MC/MCParser/AsmParser.cpp Thu Jan 28 18:49:42 2016<br>
@@ -357,6 +357,8 @@ private:<br>
     DK_IFNB, DK_IFC, DK_IFEQS, DK_IFNC, DK_IFNES, DK_IFDEF, DK_IFNDEF,<br>
     DK_IFNOTDEF, DK_ELSEIF, DK_ELSE, DK_ENDIF,<br>
     DK_SPACE, DK_SKIP, DK_FILE, DK_LINE, DK_LOC, DK_STABS,<br>
+    DK_CV_FILE, DK_CV_LOC, DK_CV_LINETABLE, DK_CV_STRINGTABLE,<br>
+    DK_CV_FILECHECKSUMS,<br>
     DK_CFI_SECTIONS, DK_CFI_STARTPROC, DK_CFI_ENDPROC, DK_CFI_DEF_CFA,<br>
     DK_CFI_DEF_CFA_OFFSET, DK_CFI_ADJUST_CFA_OFFSET, DK_CFI_DEF_CFA_REGISTER,<br>
     DK_CFI_OFFSET, DK_CFI_REL_OFFSET, DK_CFI_PERSONALITY, DK_CFI_LSDA,<br>
@@ -394,6 +396,13 @@ private:<br>
   bool parseDirectiveLoc();<br>
   bool parseDirectiveStabs();<br>
<br>
+  // ".cv_file", ".cv_loc", ".cv_linetable"<br>
+  bool parseDirectiveCVFile();<br>
+  bool parseDirectiveCVLoc();<br>
+  bool parseDirectiveCVLinetable();<br>
+  bool parseDirectiveCVStringTable();<br>
+  bool parseDirectiveCVFileChecksums();<br>
+<br>
   // .cfi directives<br>
   bool parseDirectiveCFIRegister(SMLoc DirectiveLoc);<br>
   bool parseDirectiveCFIWindowSave();<br>
@@ -1638,6 +1647,16 @@ bool AsmParser::parseStatement(ParseStat<br>
       return parseDirectiveLoc();<br>
     case DK_STABS:<br>
       return parseDirectiveStabs();<br>
+    case DK_CV_FILE:<br>
+      return parseDirectiveCVFile();<br>
+    case DK_CV_LOC:<br>
+      return parseDirectiveCVLoc();<br>
+    case DK_CV_LINETABLE:<br>
+      return parseDirectiveCVLinetable();<br>
+    case DK_CV_STRINGTABLE:<br>
+      return parseDirectiveCVStringTable();<br>
+    case DK_CV_FILECHECKSUMS:<br>
+      return parseDirectiveCVFileChecksums();<br>
     case DK_CFI_SECTIONS:<br>
       return parseDirectiveCFISections();<br>
     case DK_CFI_STARTPROC:<br>
@@ -3070,6 +3089,156 @@ bool AsmParser::parseDirectiveStabs() {<br>
   return TokError("unsupported directive '.stabs'");<br>
 }<br>
<br>
+/// parseDirectiveCVFile<br>
+/// ::= .cv_file number filename<br>
+bool AsmParser::parseDirectiveCVFile() {<br>
+  SMLoc FileNumberLoc = getLexer().getLoc();<br>
+  if (getLexer().isNot(AsmToken::Integer))<br>
+    return TokError("expected file number in '.cv_file' directive");<br>
+<br>
+  int64_t FileNumber = getTok().getIntVal();<br>
+  Lex();<br>
+<br>
+  if (FileNumber < 1)<br>
+    return TokError("file number less than one");<br>
+<br>
+  if (getLexer().isNot(AsmToken::String))<br>
+    return TokError("unexpected token in '.cv_file' directive");<br>
+<br>
+  // Usually the directory and filename together, otherwise just the directory.<br>
+  // Allow the strings to have escaped octal character sequence.<br>
+  std::string Filename;<br>
+  if (parseEscapedString(Filename))<br>
+    return true;<br>
+  Lex();<br>
+<br>
+  if (getLexer().isNot(AsmToken::EndOfStatement))<br>
+    return TokError("unexpected token in '.cv_file' directive");<br>
+<br>
+  if (getStreamer().EmitCVFileDirective(FileNumber, Filename) == 0)<br>
+    Error(FileNumberLoc, "file number already allocated");<br>
+<br>
+  return false;<br>
+}<br>
+<br>
+/// parseDirectiveCVLoc<br>
+/// ::= .cv_loc FunctionId FileNumber [LineNumber] [ColumnPos] [prologue_end]<br>
+///                                [is_stmt VALUE]<br>
+/// The first number is a file number, must have been previously assigned with<br>
+/// a .file directive, the second number is the line number and optionally the<br>
+/// third number is a column position (zero if not specified).  The remaining<br>
+/// optional items are .loc sub-directives.<br>
+bool AsmParser::parseDirectiveCVLoc() {<br>
+  if (getLexer().isNot(AsmToken::Integer))<br>
+    return TokError("unexpected token in '.cv_loc' directive");<br>
+<br>
+  int64_t FunctionId = getTok().getIntVal();<br>
+  if (FunctionId < 0)<br>
+    return TokError("function id less than zero in '.cv_loc' directive");<br>
+  Lex();<br>
+<br>
+  int64_t FileNumber = getTok().getIntVal();<br>
+  if (FileNumber < 1)<br>
+    return TokError("file number less than one in '.cv_loc' directive");<br>
+  if (!getContext().isValidCVFileNumber(FileNumber))<br>
+    return TokError("unassigned file number in '.cv_loc' directive");<br>
+  Lex();<br>
+<br>
+  int64_t LineNumber = 0;<br>
+  if (getLexer().is(AsmToken::Integer)) {<br>
+    LineNumber = getTok().getIntVal();<br>
+    if (LineNumber < 0)<br>
+      return TokError("line number less than zero in '.cv_loc' directive");<br>
+    Lex();<br>
+  }<br>
+<br>
+  int64_t ColumnPos = 0;<br>
+  if (getLexer().is(AsmToken::Integer)) {<br>
+    ColumnPos = getTok().getIntVal();<br>
+    if (ColumnPos < 0)<br>
+      return TokError("column position less than zero in '.cv_loc' directive");<br>
+    Lex();<br>
+  }<br>
+<br>
+  bool PrologueEnd = false;<br>
+  uint64_t IsStmt = 0;<br>
+  while (getLexer().isNot(AsmToken::EndOfStatement)) {<br>
+    StringRef Name;<br>
+    SMLoc Loc = getTok().getLoc();<br>
+    if (parseIdentifier(Name))<br>
+      return TokError("unexpected token in '.cv_loc' directive");<br>
+<br>
+    if (Name == "prologue_end")<br>
+      PrologueEnd = true;<br>
+    else if (Name == "is_stmt") {<br>
+      Loc = getTok().getLoc();<br>
+      const MCExpr *Value;<br>
+      if (parseExpression(Value))<br>
+        return true;<br>
+      // The expression must be the constant 0 or 1.<br>
+      IsStmt = ~0ULL;<br>
+      if (const auto *MCE = dyn_cast<MCConstantExpr>(Value))<br>
+        IsStmt = MCE->getValue();<br>
+<br>
+      if (IsStmt > 1)<br>
+        return Error(Loc, "is_stmt value not 0 or 1");<br>
+    } else {<br>
+      return Error(Loc, "unknown sub-directive in '.cv_loc' directive");<br>
+    }<br>
+  }<br>
+<br>
+  getStreamer().EmitCVLocDirective(FunctionId, FileNumber, LineNumber,<br>
+                                   ColumnPos, PrologueEnd, IsStmt, StringRef());<br>
+  return false;<br>
+}<br>
+<br>
+/// parseDirectiveCVLinetable<br>
+/// ::= .cv_linetable FunctionId, FnStart, FnEnd<br>
+bool AsmParser::parseDirectiveCVLinetable() {<br>
+  int64_t FunctionId = getTok().getIntVal();<br>
+  if (FunctionId < 0)<br>
+    return TokError("function id less than zero in '.cv_linetable' directive");<br>
+  Lex();<br>
+<br>
+  if (Lexer.isNot(AsmToken::Comma))<br>
+    return TokError("unexpected token in '.cv_linetable' directive");<br>
+  Lex();<br>
+<br>
+  SMLoc Loc = getLexer().getLoc();<br>
+  StringRef FnStartName;<br>
+  if (parseIdentifier(FnStartName))<br>
+    return Error(Loc, "expected identifier in directive");<br>
+<br>
+  if (Lexer.isNot(AsmToken::Comma))<br>
+    return TokError("unexpected token in '.cv_linetable' directive");<br>
+  Lex();<br>
+<br>
+  Loc = getLexer().getLoc();<br>
+  StringRef FnEndName;<br>
+  if (parseIdentifier(FnEndName))<br>
+    return Error(Loc, "expected identifier in directive");<br>
+<br>
+  MCSymbol *FnStartSym = getContext().getOrCreateSymbol(FnStartName);<br>
+  MCSymbol *FnEndSym = getContext().getOrCreateSymbol(FnEndName);<br>
+<br>
+  getStreamer().EmitCVLinetableDirective(FunctionId, FnStartSym, FnEndSym);<br>
+  return false;<br>
+}<br>
+<br>
+/// parseDirectiveCVStringTable<br>
+/// ::= .cv_stringtable<br>
+bool AsmParser::parseDirectiveCVStringTable() {<br>
+  getStreamer().EmitCVStringTableDirective();<br>
+  return false;<br>
+}<br>
+<br>
+/// parseDirectiveCVFileChecksums<br>
+/// ::= .cv_filechecksums<br>
+bool AsmParser::parseDirectiveCVFileChecksums() {<br>
+  getStreamer().EmitCVFileChecksumsDirective();<br>
+  return false;<br>
+}<br>
+<br>
 /// parseDirectiveCFISections<br>
 /// ::= .cfi_sections section [, section]<br>
 bool AsmParser::parseDirectiveCFISections() {<br>
@@ -4381,6 +4550,11 @@ void AsmParser::initializeDirectiveKindM<br>
   DirectiveKindMap[".line"] = DK_LINE;<br>
   DirectiveKindMap[".loc"] = DK_LOC;<br>
   DirectiveKindMap[".stabs"] = DK_STABS;<br>
+  DirectiveKindMap[".cv_file"] = DK_CV_FILE;<br>
+  DirectiveKindMap[".cv_loc"] = DK_CV_LOC;<br>
+  DirectiveKindMap[".cv_linetable"] = DK_CV_LINETABLE;<br>
+  DirectiveKindMap[".cv_stringtable"] = DK_CV_STRINGTABLE;<br>
+  DirectiveKindMap[".cv_filechecksums"] = DK_CV_FILECHECKSUMS;<br>
   DirectiveKindMap[".sleb128"] = DK_SLEB128;<br>
   DirectiveKindMap[".uleb128"] = DK_ULEB128;<br>
   DirectiveKindMap[".cfi_sections"] = DK_CFI_SECTIONS;<br>
<br>
Modified: llvm/trunk/lib/MC/MCStreamer.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/MCStreamer.cpp?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/MCStreamer.cpp?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/MC/MCStreamer.cpp (original)<br>
+++ llvm/trunk/lib/MC/MCStreamer.cpp Thu Jan 28 18:49:42 2016<br>
@@ -180,6 +180,22 @@ void MCStreamer::EnsureValidDwarfFrame()<br>
     report_fatal_error("No open frame");<br>
 }<br>
<br>
+unsigned MCStreamer::EmitCVFileDirective(unsigned FileNo, StringRef Filename) {<br>
+  return getContext().getCVFile(Filename, FileNo);<br>
+}<br>
+<br>
+void MCStreamer::EmitCVLocDirective(unsigned FunctionId, unsigned FileNo,<br>
+                                    unsigned Line, unsigned Column,<br>
+                                    bool PrologueEnd, bool IsStmt,<br>
+                                    StringRef FileName) {<br>
+  getContext().setCurrentCVLoc(FunctionId, FileNo, Line, Column, PrologueEnd,<br>
+                               IsStmt);<br>
+}<br>
+<br>
+void MCStreamer::EmitCVLinetableDirective(unsigned FunctionId,<br>
+                                          const MCSymbol *Begin,<br>
+                                          const MCSymbol *End) {}<br>
+<br>
 void MCStreamer::EmitEHSymAttributes(const MCSymbol *Symbol,<br>
                                      MCSymbol *EHSymbol) {<br>
 }<br>
<br>
Modified: llvm/trunk/lib/MC/StringTableBuilder.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/StringTableBuilder.cpp?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/StringTableBuilder.cpp?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/MC/StringTableBuilder.cpp (original)<br>
+++ llvm/trunk/lib/MC/StringTableBuilder.cpp Thu Jan 28 18:49:42 2016<br>
@@ -16,7 +16,22 @@<br>
<br>
 using namespace llvm;<br>
<br>
-StringTableBuilder::StringTableBuilder(Kind K) : K(K) {}<br>
+StringTableBuilder::StringTableBuilder(Kind K) : K(K) {<br>
+  // Account for leading bytes in table so that offsets returned from add are<br>
+  // correct.<br>
+  switch (K) {<br>
+  case RAW:<br>
+    Size = 0;<br>
+    break;<br>
+  case MachO:<br>
+  case ELF:<br>
+    Size = 1;<br>
+    break;<br>
+  case WinCOFF:<br>
+    Size = 4;<br>
+    break;<br>
+  }<br>
+}<br>
<br>
 typedef std::pair<StringRef, size_t> StringPair;<br>
<br>
@@ -62,13 +77,32 @@ tailcall:<br>
 }<br>
<br>
 void StringTableBuilder::finalize() {<br>
-  std::vector<std::pair<StringRef, size_t> *> Strings;<br>
+  finalizeStringTable(/*Optimize=*/true);<br>
+}<br>
+<br>
+void StringTableBuilder::finalizeInOrder() {<br>
+  finalizeStringTable(/*Optimize=*/false);<br>
+}<br>
+<br>
+void StringTableBuilder::finalizeStringTable(bool Optimize) {<br>
+  typedef std::pair<StringRef, size_t> StringOffsetPair;<br>
+  std::vector<StringOffsetPair *> Strings;<br>
   Strings.reserve(StringIndexMap.size());<br>
-  for (std::pair<StringRef, size_t> &P : StringIndexMap)<br>
+  for (StringOffsetPair &P : StringIndexMap)<br>
     Strings.push_back(&P);<br>
<br>
-  if (!Strings.empty())<br>
-    multikey_qsort(&Strings[0], &Strings[0] + Strings.size(), 0);<br>
+  if (!Strings.empty()) {<br>
+    // If we're optimizing, sort by name. If not, sort by previously assigned<br>
+    // offset.<br>
+    if (Optimize) {<br>
+      multikey_qsort(&Strings[0], &Strings[0] + Strings.size(), 0);<br>
+    } else {<br>
+      std::sort(Strings.begin(), Strings.end(),<br>
+                [](const StringOffsetPair *LHS, const StringOffsetPair *RHS) {<br>
+                  return LHS->second < RHS->second;<br>
+                });<br>
+    }<br>
+  }<br>
<br>
   switch (K) {<br>
   case RAW:<br>
@@ -85,17 +119,22 @@ void StringTableBuilder::finalize() {<br>
   }<br>
<br>
   StringRef Previous;<br>
-  for (std::pair<StringRef, size_t> *P : Strings) {<br>
+  for (StringOffsetPair *P : Strings) {<br>
     StringRef S = P->first;<br>
     if (K == WinCOFF)<br>
       assert(S.size() > COFF::NameSize && "Short string in COFF string table!");<br>
<br>
-    if (Previous.endswith(S)) {<br>
+    if (Optimize && Previous.endswith(S)) {<br>
       P->second = StringTable.size() - S.size() - (K != RAW);<br>
       continue;<br>
     }<br>
<br>
-    P->second = StringTable.size();<br>
+    if (Optimize)<br>
+      P->second = StringTable.size();<br>
+    else<br>
+      assert(P->second == StringTable.size() &&<br>
+             "different strtab offset after finalization");<br>
+<br>
     StringTable += S;<br>
     if (K != RAW)<br>
       StringTable += '\x00';<br>
<br>
Modified: llvm/trunk/test/DebugInfo/COFF/asm.ll<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/test/DebugInfo/COFF/asm.ll?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/test/DebugInfo/COFF/asm.ll?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/test/DebugInfo/COFF/asm.ll (original)<br>
+++ llvm/trunk/test/DebugInfo/COFF/asm.ll Thu Jan 28 18:49:42 2016<br>
@@ -13,11 +13,11 @@<br>
 ;  6 }<br>
<br>
 ; X86-LABEL: _f:<br>
-; X86:      # BB<br>
-; X86-NEXT: [[ASM_LINE:^L.*]]:{{$}}<br>
-; X86:      [[CALL_LINE:^L.*]]:{{$}}<br>
+; X86:      .cv_file 1 "D:\\asm.c"<br>
+; X86:      .cv_loc 0 1 4 0 is_stmt 0<br>
+; X86:      .cv_loc 0 1 5 0<br>
 ; X86:      calll   _g<br>
-; X86-NEXT: [[RETURN_STMT:.*]]:<br>
+; X86:      .cv_loc 0 1 6 0<br>
 ; X86:      ret<br>
 ; X86-NEXT: [[END_OF_F:^L.*]]:<br>
 ;<br>
@@ -45,48 +45,15 @@<br>
 ; Padding<br>
 ; X86-NEXT: .zero   3<br>
 ; Line table<br>
-; X86-NEXT: .long   242<br>
-; X86-NEXT: .long [[F2_END:.*]]-[[F2_START:.*]]<br>
-; X86-NEXT: [[F2_START]]:<br>
-; X86-NEXT: .secrel32 _f<br>
-; X86-NEXT: .secidx _f<br>
-; X86-NEXT: .short 1<br>
-; X86-NEXT: .long [[END_OF_F]]-_f<br>
-; X86-NEXT: [[FILE_SEGMENT_START:[^:]*]]:<br>
-; X86-NEXT: .long   0<br>
-; X86-NEXT: .long   3<br>
-; X86-NEXT: .long [[FILE_SEGMENT_END:.*]]-[[FILE_SEGMENT_START]]<br>
-; X86-NEXT: .long [[ASM_LINE]]-_f<br>
-; X86-NEXT: .long   -2147483644<br>
-; X86-NEXT: .long [[CALL_LINE]]-_f<br>
-; X86-NEXT: .long   -2147483643<br>
-; X86-NEXT: .long [[RETURN_STMT]]-_f<br>
-; X86-NEXT: .long   -2147483642<br>
-; X86-NEXT: .short  0<br>
-; X86-NEXT: .short  0<br>
-; X86-NEXT: .short  0<br>
-; X86-NEXT: .short  0<br>
-; X86-NEXT: .short  0<br>
-; X86-NEXT: .short  0<br>
-; X86-NEXT: [[FILE_SEGMENT_END]]:<br>
-; X86-NEXT: [[F2_END]]:<br>
+; X86-NEXT: .cv_linetable 0, _f, [[END_OF_F]]<br>
 ; File index to string table offset subsection<br>
-; X86-NEXT: .long   244<br>
-; X86-NEXT: .long   8<br>
-; X86-NEXT: .long   1<br>
-; X86-NEXT: .long   0<br>
+; X86-NEXT: .cv_filechecksums<br>
 ; String table<br>
-; X86-NEXT: .long   243<br>
-; X86-NEXT: .long   10<br>
-; X86-NEXT: .byte   0<br>
-; X86-NEXT: .ascii  "D:\\asm.c"<br>
-; X86-NEXT: .byte   0<br>
-; Padding<br>
-; X86-NEXT: .zero   2<br>
+; X86-NEXT: .cv_stringtable<br>
<br>
 ; OBJ32:    Section {<br>
 ; OBJ32:      Name: .debug$S (2E 64 65 62 75 67 24 53)<br>
-; OBJ32:      Characteristics [ (0x42100040)<br>
+; OBJ32:      Characteristics [ (0x42300040)<br>
 ; OBJ32:      ]<br>
 ; OBJ32:      Relocations [<br>
 ; OBJ32-NEXT:   0x2C IMAGE_REL_I386_SECREL _f<br>
@@ -107,7 +74,7 @@<br>
 ; OBJ32-NEXT: ]<br>
 ; OBJ32:      FunctionLineTable [<br>
 ; OBJ32-NEXT:   Name: _f<br>
-; OBJ32-NEXT:   Flags: 0x1<br>
+; OBJ32-NEXT:   Flags: 0x0<br>
 ; OBJ32-NEXT:   CodeSize: 0x6<br>
 ; OBJ32-NEXT:   FilenameSegment [<br>
 ; OBJ32-NEXT:   Filename: D:\asm.c<br>
@@ -118,34 +85,27 @@<br>
 ; OBJ32-NEXT:     LineNumberStart: 4<br>
 ; OBJ32-NEXT:     LineNumberEndDelta: 0<br>
 ; OBJ32-NEXT:     IsStatement: Yes<br>
-; OBJ32-NEXT:     ColStart: 0<br>
-; OBJ32-NEXT:     ColEnd: 0<br>
 ; OBJ32-NEXT:   ]<br>
 ; OBJ32-NEXT:   +0x0 [<br>
 ; OBJ32-NEXT:     LineNumberStart: 5<br>
 ; OBJ32-NEXT:     LineNumberEndDelta: 0<br>
 ; OBJ32-NEXT:     IsStatement: Yes<br>
-; OBJ32-NEXT:     ColStart: 0<br>
-; OBJ32-NEXT:     ColEnd: 0<br>
 ; OBJ32-NEXT:   ]<br>
 ; OBJ32-NEXT:   +0x5 [<br>
 ; OBJ32-NEXT:     LineNumberStart: 6<br>
 ; OBJ32-NEXT:     LineNumberEndDelta: 0<br>
 ; OBJ32-NEXT:     IsStatement: Yes<br>
-; OBJ32-NEXT:     ColStart: 0<br>
-; OBJ32-NEXT:     ColEnd: 0<br>
 ; OBJ32-NEXT:   ]<br>
 ; OBJ32-NEXT: ]<br>
<br>
 ; X64-LABEL: f:<br>
-; X64-NEXT: .L{{.*}}:{{$}}<br>
-; X64-NEXT: [[START:.*]]:{{$}}<br>
-; X64:      # BB<br>
+; X64:      .cv_file 1 "D:\\asm.c"<br>
+; X64:      .cv_loc 0 1 3 0 is_stmt 0<br>
 ; X64:      subq    $40, %rsp<br>
-; X64-NEXT: [[ASM_LINE:.*]]:{{$}}<br>
-; X64:      [[CALL_LINE:.*]]:{{$}}<br>
+; X64:      .cv_loc 0 1 4 0<br>
+; X64:      .cv_loc 0 1 5 0<br>
 ; X64:      callq   g<br>
-; X64-NEXT: [[EPILOG_AND_RET:.*]]:<br>
+; X64:      .cv_loc 0 1 6 0<br>
 ; X64:      addq    $40, %rsp<br>
 ; X64-NEXT: ret<br>
 ; X64-NEXT: [[END_OF_F:.*]]:<br>
@@ -174,52 +134,15 @@<br>
 ; Padding<br>
 ; X64-NEXT: .zero   3<br>
 ; Line table<br>
-; X64-NEXT: .long   242<br>
-; X64-NEXT: .long [[F2_END:.*]]-[[F2_START:.*]]<br>
-; X64-NEXT: [[F2_START]]:<br>
-; X64-NEXT: .secrel32 f<br>
-; X64-NEXT: .secidx f<br>
-; X64-NEXT: .short 1<br>
-; X64-NEXT: .long [[END_OF_F]]-f<br>
-; X64-NEXT: [[FILE_SEGMENT_START:[^:]*]]:<br>
-; X64-NEXT: .long   0<br>
-; X64-NEXT: .long   4<br>
-; X64-NEXT: .long [[FILE_SEGMENT_END:.*]]-[[FILE_SEGMENT_START]]<br>
-; X64-NEXT: .long [[START]]-f<br>
-; X64-NEXT: .long   -2147483645<br>
-; X64-NEXT: .long [[ASM_LINE]]-f<br>
-; X64-NEXT: .long   -2147483644<br>
-; X64-NEXT: .long [[CALL_LINE]]-f<br>
-; X64-NEXT: .long   -2147483643<br>
-; X64-NEXT: .long [[EPILOG_AND_RET]]-f<br>
-; X64-NEXT: .long   -2147483642<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: [[FILE_SEGMENT_END]]:<br>
-; X64-NEXT: [[F2_END]]:<br>
+; X64-NEXT: .cv_linetable 0, f, [[END_OF_F]]<br>
 ; File index to string table offset subsection<br>
-; X64-NEXT: .long   244<br>
-; X64-NEXT: .long   8<br>
-; X64-NEXT: .long   1<br>
-; X64-NEXT: .long   0<br>
+; X64-NEXT: .cv_filechecksums<br>
 ; String table<br>
-; X64-NEXT: .long   243<br>
-; X64-NEXT: .long   10<br>
-; X64-NEXT: .byte   0<br>
-; X64-NEXT: .ascii  "D:\\asm.c"<br>
-; X64-NEXT: .byte   0<br>
-; Padding<br>
-; X64-NEXT: .zero   2<br>
+; X64-NEXT: .cv_stringtable<br>
<br>
 ; OBJ64:    Section {<br>
 ; OBJ64:      Name: .debug$S (2E 64 65 62 75 67 24 53)<br>
-; OBJ64:      Characteristics [ (0x42100040)<br>
+; OBJ64:      Characteristics [ (0x42300040)<br>
 ; OBJ64:      ]<br>
 ; OBJ64:      Relocations [<br>
 ; OBJ64-NEXT:   0x2C IMAGE_REL_AMD64_SECREL f<br>
@@ -239,7 +162,7 @@<br>
 ; OBJ64-NEXT: ]<br>
 ; OBJ64:      FunctionLineTable [<br>
 ; OBJ64-NEXT:   Name: f<br>
-; OBJ64-NEXT:   Flags: 0x1<br>
+; OBJ64-NEXT:   Flags: 0x0<br>
 ; OBJ64-NEXT:   CodeSize: 0xE<br>
 ; OBJ64-NEXT:   FilenameSegment [<br>
 ; OBJ64-NEXT:     Filename: D:\asm.c<br>
@@ -249,29 +172,21 @@<br>
 ; OBJ64-NEXT:       LineNumberStart: 3<br>
 ; OBJ64-NEXT:       LineNumberEndDelta: 0<br>
 ; OBJ64-NEXT:       IsStatement: Yes<br>
-; OBJ64-NEXT:       ColStart: 0<br>
-; OBJ64-NEXT:       ColEnd: 0<br>
 ; OBJ64-NEXT:     ]<br>
 ; OBJ64-NEXT:     +0x4 [<br>
 ; OBJ64-NEXT:       LineNumberStart: 4<br>
 ; OBJ64-NEXT:       LineNumberEndDelta: 0<br>
 ; OBJ64-NEXT:       IsStatement: Yes<br>
-; OBJ64-NEXT:       ColStart: 0<br>
-; OBJ64-NEXT:       ColEnd: 0<br>
 ; OBJ64-NEXT:     ]<br>
 ; OBJ64-NEXT:     +0x4 [<br>
 ; OBJ64-NEXT:       LineNumberStart: 5<br>
 ; OBJ64-NEXT:       LineNumberEndDelta: 0<br>
 ; OBJ64-NEXT:       IsStatement: Yes<br>
-; OBJ64-NEXT:       ColStart: 0<br>
-; OBJ64-NEXT:       ColEnd: 0<br>
 ; OBJ64-NEXT:     ]<br>
 ; OBJ64-NEXT:     +0x9 [<br>
 ; OBJ64-NEXT:       LineNumberStart: 6<br>
 ; OBJ64-NEXT:       LineNumberEndDelta: 0<br>
 ; OBJ64-NEXT:       IsStatement: Yes<br>
-; OBJ64-NEXT:       ColStart: 0<br>
-; OBJ64-NEXT:       ColEnd: 0<br>
 ; OBJ64-NEXT:     ]<br>
 ; OBJ64-NEXT:   ]<br>
 ; OBJ64-NEXT: ]<br>
<br>
Modified: llvm/trunk/test/DebugInfo/COFF/multifile.ll<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/test/DebugInfo/COFF/multifile.ll?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/test/DebugInfo/COFF/multifile.ll?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/test/DebugInfo/COFF/multifile.ll (original)<br>
+++ llvm/trunk/test/DebugInfo/COFF/multifile.ll Thu Jan 28 18:49:42 2016<br>
@@ -18,13 +18,15 @@<br>
<br>
 ; X86-LABEL: _f:<br>
 ; X86:      # BB<br>
-; X86-NEXT: [[CALL_LINE_1:.*]]:{{$}}<br>
+; X86:      .cv_file 1 "D:\\one.c"<br>
+; X86:      .cv_loc 0 1 1 0 is_stmt 0 # one.c:1:0<br>
 ; X86:      calll   _g<br>
-; X86-NEXT: [[CALL_LINE_2:.*]]:{{$}}<br>
+; X86:      .cv_file 2 "D:\\two.c"<br>
+; X86:      .cv_loc 0 2 2 0 # two.c:2:0<br>
 ; X86:      calll   _g<br>
-; X86-NEXT: [[CALL_LINE_3:.*]]:{{$}}<br>
+; X86:      .cv_loc 0 1 7 0 # one.c:7:0<br>
 ; X86:      calll   _g<br>
-; X86-NEXT: [[RETURN_STMT:.*]]:<br>
+; X86:      .cv_loc 0 1 8 0 # one.c:8:0<br>
 ; X86:      ret<br>
 ; X86-NEXT: [[END_OF_F:.*]]:<br>
 ;<br>
@@ -52,68 +54,15 @@<br>
 ; Padding<br>
 ; X86-NEXT: .zero   3<br>
 ; Line table<br>
-; X86-NEXT: .long   242<br>
-; X86-NEXT: .long [[F2_END:.*]]-[[F2_START:.*]]<br>
-; X86-NEXT: [[F2_START]]:<br>
-; X86-NEXT: .secrel32 _f<br>
-; X86-NEXT: .secidx _f<br>
-; X86-NEXT: .short 1<br>
-; X86-NEXT: .long [[END_OF_F]]-_f<br>
-; Segment for file 'D:\\one.c' begins<br>
-; X86-NEXT: [[FILE_SEGMENT_START:[^:]*]]:<br>
-; X86-NEXT: .long   0<br>
-; X86-NEXT: .long   1<br>
-; X86-NEXT: .long [[FILE_SEGMENT_END:.*]]-[[FILE_SEGMENT_START]]<br>
-; X86-NEXT: .long [[CALL_LINE_1]]-_f<br>
-; X86-NEXT: .long   -2147483647<br>
-; X86-NEXT: .short  0<br>
-; X86-NEXT: .short  0<br>
-; X86-NEXT: [[FILE_SEGMENT_END]]:<br>
-; Segment for file 'D:\\two.c' begins<br>
-; X86-NEXT: [[FILE_SEGMENT_START:[^:]*]]:<br>
-; X86-NEXT: .long   8<br>
-; X86-NEXT: .long   1<br>
-; X86-NEXT: .long [[FILE_SEGMENT_END:.*]]-[[FILE_SEGMENT_START]]<br>
-; X86-NEXT: .long [[CALL_LINE_2]]-_f<br>
-; X86-NEXT: .long   -2147483646<br>
-; X86-NEXT: .short  0<br>
-; X86-NEXT: .short  0<br>
-; X86-NEXT: [[FILE_SEGMENT_END]]:<br>
-; A new segment for file 'D:\\one.c' begins<br>
-; X86-NEXT: [[FILE_SEGMENT_START:[^:]*]]:<br>
-; X86-NEXT: .long   0<br>
-; X86-NEXT: .long   2<br>
-; X86-NEXT: .long [[FILE_SEGMENT_END:.*]]-[[FILE_SEGMENT_START]]<br>
-; X86-NEXT: .long [[CALL_LINE_3]]-_f<br>
-; X86-NEXT: .long   -2147483641<br>
-; X86-NEXT: .long [[RETURN_STMT]]-_f<br>
-; X86-NEXT: .long   -2147483640<br>
-; X86-NEXT: .short  0<br>
-; X86-NEXT: .short  0<br>
-; X86-NEXT: .short  0<br>
-; X86-NEXT: .short  0<br>
-; X86-NEXT: [[FILE_SEGMENT_END]]:<br>
-; X86-NEXT: [[F2_END]]:<br>
+; X86-NEXT: .cv_linetable 0, _f, [[END_OF_F]]<br>
 ; File index to string table offset subsection<br>
-; X86-NEXT: .long   244<br>
-; X86-NEXT: .long   16<br>
-; X86-NEXT: .long   1<br>
-; X86-NEXT: .long   0<br>
-; X86-NEXT: .long   10<br>
-; X86-NEXT: .long   0<br>
+; X86-NEXT: .cv_filechecksums<br>
 ; String table<br>
-; X86-NEXT: .long   243<br>
-; X86-NEXT: .long   19<br>
-; X86-NEXT: .byte   0<br>
-; X86-NEXT: .ascii  "D:\\one.c"<br>
-; X86-NEXT: .byte   0<br>
-; X86-NEXT: .ascii  "D:\\two.c"<br>
-; X86-NEXT: .byte   0<br>
-; X86-NEXT: .zero   1<br>
+; X86-NEXT: .cv_stringtable<br>
<br>
 ; OBJ32:    Section {<br>
 ; OBJ32:      Name: .debug$S (2E 64 65 62 75 67 24 53)<br>
-; OBJ32:      Characteristics [ (0x42100040)<br>
+; OBJ32:      Characteristics [ (0x42300040)<br>
 ; OBJ32:      ]<br>
 ; OBJ32:      Relocations [<br>
 ; OBJ32-NEXT:   0x2C IMAGE_REL_I386_SECREL _f<br>
@@ -133,7 +82,7 @@<br>
 ; OBJ32-NEXT: ]<br>
 ; OBJ32:      FunctionLineTable [<br>
 ; OBJ32-NEXT:   Name: _f<br>
-; OBJ32-NEXT:   Flags: 0x1<br>
+; OBJ32-NEXT:   Flags: 0x0<br>
 ; OBJ32-NEXT:   CodeSize: 0x10<br>
 ; OBJ32-NEXT:   FilenameSegment [<br>
 ; OBJ32-NEXT:     Filename: D:\one.c<br>
@@ -141,8 +90,6 @@<br>
 ; OBJ32-NEXT:       LineNumberStart: 1<br>
 ; OBJ32-NEXT:       LineNumberEndDelta: 0<br>
 ; OBJ32-NEXT:       IsStatement: Yes<br>
-; OBJ32-NEXT:       ColStart: 0<br>
-; OBJ32-NEXT:       ColEnd: 0<br>
 ; OBJ32-NEXT:     ]<br>
 ; OBJ32-NEXT:   ]<br>
 ; OBJ32-NEXT:   FilenameSegment [<br>
@@ -151,8 +98,6 @@<br>
 ; OBJ32-NEXT:       LineNumberStart: 2<br>
 ; OBJ32-NEXT:       LineNumberEndDelta: 0<br>
 ; OBJ32-NEXT:       IsStatement: Yes<br>
-; OBJ32-NEXT:       ColStart: 0<br>
-; OBJ32-NEXT:       ColEnd: 0<br>
 ; OBJ32-NEXT:     ]<br>
 ; OBJ32-NEXT:   ]<br>
 ; OBJ32-NEXT:   FilenameSegment [<br>
@@ -161,31 +106,30 @@<br>
 ; OBJ32-NEXT:       LineNumberStart: 7<br>
 ; OBJ32-NEXT:       LineNumberEndDelta: 0<br>
 ; OBJ32-NEXT:       IsStatement: Yes<br>
-; OBJ32-NEXT:       ColStart: 0<br>
-; OBJ32-NEXT:       ColEnd: 0<br>
 ; OBJ32-NEXT:     ]<br>
 ; OBJ32-NEXT:     +0xF [<br>
 ; OBJ32-NEXT:       LineNumberStart: 8<br>
 ; OBJ32-NEXT:       LineNumberEndDelta: 0<br>
 ; OBJ32-NEXT:       IsStatement: Yes<br>
-; OBJ32-NEXT:       ColStart: 0<br>
-; OBJ32-NEXT:       ColEnd: 0<br>
 ; OBJ32-NEXT:     ]<br>
 ; OBJ32-NEXT:   ]<br>
 ; OBJ32-NEXT: ]<br>
<br>
 ; X64-LABEL: f:<br>
 ; X64-NEXT: .L{{.*}}:{{$}}<br>
-; X64-NEXT: [[START:.*]]:{{$}}<br>
+; X64:      .cv_file 1 "D:\\input.c"<br>
+; X64:      .cv_loc 0 1 3 0 is_stmt 0 # input.c:3:0<br>
 ; X64:      # BB<br>
 ; X64:      subq    $40, %rsp<br>
-; X64-NEXT: [[CALL_LINE_1:.*]]:{{$}}<br>
+; X64:      .cv_file 2 "D:\\one.c"<br>
+; X64:      .cv_loc 0 2 1 0 # one.c:1:0<br>
 ; X64:      callq   g<br>
-; X64-NEXT: [[CALL_LINE_2:.*]]:{{$}}<br>
+; X64:      .cv_file 3 "D:\\two.c"<br>
+; X64:      .cv_loc 0 3 2 0 # two.c:2:0<br>
 ; X64:      callq   g<br>
-; X64-NEXT: [[CALL_LINE_3:.*]]:{{$}}<br>
+; X64:      .cv_loc 0 2 7 0 # one.c:7:0<br>
 ; X64:      callq   g<br>
-; X64-NEXT: [[EPILOG_AND_RET:.*]]:<br>
+; X64:      .cv_loc 0 2 8 0 # one.c:8:0<br>
 ; X64:      addq    $40, %rsp<br>
 ; X64-NEXT: ret<br>
 ; X64-NEXT: [[END_OF_F:.*]]:<br>
@@ -213,83 +157,13 @@<br>
 ; X64-NEXT: [[F1_END]]:<br>
 ; Padding<br>
 ; X64-NEXT: .zero   3<br>
-; Line table<br>
-; X64-NEXT: .long   242<br>
-; X64-NEXT: .long [[F2_END:.*]]-[[F2_START:.*]]<br>
-; X64-NEXT: [[F2_START]]:<br>
-; X64-NEXT: .secrel32 f<br>
-; X64-NEXT: .secidx f<br>
-; X64-NEXT: .short 1<br>
-; X64-NEXT: .long [[END_OF_F]]-f<br>
-; Segment for file 'D:\\input.c' begins<br>
-; X64-NEXT: [[FILE_SEGMENT_START:[^:]*]]:<br>
-; X64-NEXT: .long   0<br>
-; X64-NEXT: .long   1<br>
-; X64-NEXT: .long [[FILE_SEGMENT_END:.*]]-[[FILE_SEGMENT_START]]<br>
-; X64-NEXT: .long [[START]]-f<br>
-; X64-NEXT: .long   -2147483645<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: [[FILE_SEGMENT_END]]:<br>
-; Segment for file 'D:\\one.c' begins<br>
-; X64-NEXT: [[FILE_SEGMENT_START:[^:]*]]:<br>
-; X64-NEXT: .long   8<br>
-; X64-NEXT: .long   1<br>
-; X64-NEXT: .long [[FILE_SEGMENT_END:.*]]-[[FILE_SEGMENT_START]]<br>
-; X64-NEXT: .long [[CALL_LINE_1]]-f<br>
-; X64-NEXT: .long   -2147483647<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: [[FILE_SEGMENT_END]]:<br>
-; Segment for file 'D:\\two.c' begins<br>
-; X64-NEXT: [[FILE_SEGMENT_START:[^:]*]]:<br>
-; X64-NEXT: .long   16<br>
-; X64-NEXT: .long   1<br>
-; X64-NEXT: .long [[FILE_SEGMENT_END:.*]]-[[FILE_SEGMENT_START]]<br>
-; X64-NEXT: .long [[CALL_LINE_2]]-f<br>
-; X64-NEXT: .long   -2147483646<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: [[FILE_SEGMENT_END]]:<br>
-; A new segment for file 'D:\\one.c' begins<br>
-; X64-NEXT: [[FILE_SEGMENT_START:[^:]*]]:<br>
-; X64-NEXT: .long   8<br>
-; X64-NEXT: .long   2<br>
-; X64-NEXT: .long [[FILE_SEGMENT_END:.*]]-[[FILE_SEGMENT_START]]<br>
-; X64-NEXT: .long [[CALL_LINE_3]]-f<br>
-; X64-NEXT: .long   -2147483641<br>
-; X64-NEXT: .long [[EPILOG_AND_RET]]-f<br>
-; X64-NEXT: .long   -2147483640<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: [[FILE_SEGMENT_END]]:<br>
-; X64-NEXT: [[F2_END]]:<br>
-; File index to string table offset subsection<br>
-; X64-NEXT: .long   244<br>
-; X64-NEXT: .long   24<br>
-; X64-NEXT: .long   1<br>
-; X64-NEXT: .long   0<br>
-; X64-NEXT: .long   12<br>
-; X64-NEXT: .long   0<br>
-; X64-NEXT: .long   21<br>
-; X64-NEXT: .long   0<br>
-; String table<br>
-; X64-NEXT: .long   243<br>
-; X64-NEXT: .long   30<br>
-; X64-NEXT: .byte   0<br>
-; X64-NEXT: .ascii  "D:\\input.c"<br>
-; X64-NEXT: .byte   0<br>
-; X64-NEXT: .ascii  "D:\\one.c"<br>
-; X64-NEXT: .byte   0<br>
-; X64-NEXT: .ascii  "D:\\two.c"<br>
-; X64-NEXT: .byte   0<br>
-; X64-NEXT: .zero   2<br>
+; X64: .cv_linetable 0, f, [[END_OF_F]]<br>
+; X64: .cv_filechecksums<br>
+; X64: .cv_stringtable<br>
<br>
 ; OBJ64:    Section {<br>
 ; OBJ64:      Name: .debug$S (2E 64 65 62 75 67 24 53)<br>
-; OBJ64:      Characteristics [ (0x42100040)<br>
+; OBJ64:      Characteristics [ (0x42300040)<br>
 ; OBJ64:      ]<br>
 ; OBJ64:      Relocations [<br>
 ; OBJ64-NEXT:   0x2C IMAGE_REL_AMD64_SECREL f<br>
@@ -309,7 +183,7 @@<br>
 ; OBJ64-NEXT: ]<br>
 ; OBJ64:      FunctionLineTable [<br>
 ; OBJ64-NEXT:   Name: f<br>
-; OBJ64-NEXT:   Flags: 0x1<br>
+; OBJ64-NEXT:   Flags: 0x0<br>
 ; OBJ64-NEXT:   CodeSize: 0x18<br>
 ; OBJ64-NEXT:   FilenameSegment [<br>
 ; OBJ64-NEXT:     Filename: D:\input.c<br>
@@ -317,8 +191,6 @@<br>
 ; OBJ64-NEXT:       LineNumberStart: 3<br>
 ; OBJ64-NEXT:       LineNumberEndDelta: 0<br>
 ; OBJ64-NEXT:       IsStatement: Yes<br>
-; OBJ64-NEXT:       ColStart: 0<br>
-; OBJ64-NEXT:       ColEnd: 0<br>
 ; OBJ64-NEXT:     ]<br>
 ; OBJ64-NEXT:   ]<br>
 ; OBJ64-NEXT:   FilenameSegment [<br>
@@ -327,8 +199,6 @@<br>
 ; OBJ64-NEXT:       LineNumberStart: 1<br>
 ; OBJ64-NEXT:       LineNumberEndDelta: 0<br>
 ; OBJ64-NEXT:       IsStatement: Yes<br>
-; OBJ64-NEXT:       ColStart: 0<br>
-; OBJ64-NEXT:       ColEnd: 0<br>
 ; OBJ64-NEXT:     ]<br>
 ; OBJ64-NEXT:   ]<br>
 ; OBJ64-NEXT:   FilenameSegment [<br>
@@ -337,8 +207,6 @@<br>
 ; OBJ64-NEXT:       LineNumberStart: 2<br>
 ; OBJ64-NEXT:       LineNumberEndDelta: 0<br>
 ; OBJ64-NEXT:       IsStatement: Yes<br>
-; OBJ64-NEXT:       ColStart: 0<br>
-; OBJ64-NEXT:       ColEnd: 0<br>
 ; OBJ64-NEXT:     ]<br>
 ; OBJ64-NEXT:   ]<br>
 ; OBJ64-NEXT:   FilenameSegment [<br>
@@ -347,15 +215,11 @@<br>
 ; OBJ64-NEXT:       LineNumberStart: 7<br>
 ; OBJ64-NEXT:       LineNumberEndDelta: 0<br>
 ; OBJ64-NEXT:       IsStatement: Yes<br>
-; OBJ64-NEXT:       ColStart: 0<br>
-; OBJ64-NEXT:       ColEnd: 0<br>
 ; OBJ64-NEXT:     ]<br>
 ; OBJ64-NEXT:     +0x13 [<br>
 ; OBJ64-NEXT:       LineNumberStart: 8<br>
 ; OBJ64-NEXT:       LineNumberEndDelta: 0<br>
 ; OBJ64-NEXT:       IsStatement: Yes<br>
-; OBJ64-NEXT:       ColStart: 0<br>
-; OBJ64-NEXT:       ColEnd: 0<br>
 ; OBJ64-NEXT:     ]<br>
 ; OBJ64-NEXT:   ]<br>
 ; OBJ64-NEXT: ]<br>
<br>
Modified: llvm/trunk/test/DebugInfo/COFF/multifunction.ll<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/test/DebugInfo/COFF/multifunction.ll?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/test/DebugInfo/COFF/multifunction.ll?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/test/DebugInfo/COFF/multifunction.ll (original)<br>
+++ llvm/trunk/test/DebugInfo/COFF/multifunction.ll Thu Jan 28 18:49:42 2016<br>
@@ -24,29 +24,30 @@<br>
<br>
 ; X86-LABEL: _x:<br>
 ; X86:      # BB<br>
-; X86-NEXT: [[X_CALL:.*]]:{{$}}<br>
+; X86:      .cv_file 1 "D:\\source.c"<br>
+; X86:      .cv_loc 0 1 4 42 is_stmt 0 # source.c:4:42<br>
 ; X86:      calll   _z<br>
-; X86-NEXT: [[X_RETURN:.*]]:<br>
+; X86:      .cv_loc 0 1 5 43 # source.c:5:43<br>
 ; X86:      ret<br>
 ; X86-NEXT: [[END_OF_X:.*]]:<br>
 ;<br>
 ; X86-LABEL: _y:<br>
 ; X86:      # BB<br>
-; X86-NEXT: [[Y_CALL:.*]]:{{$}}<br>
+; X86:      .cv_loc 1 1 8 52 # source.c:8:52<br>
 ; X86:      calll   _z<br>
-; X86-NEXT: [[Y_RETURN:.*]]:<br>
+; X86:      .cv_loc 1 1 9 53 # source.c:9:53<br>
 ; X86:      ret<br>
 ; X86-NEXT: [[END_OF_Y:.*]]:<br>
 ;<br>
 ; X86-LABEL: _f:<br>
 ; X86:      # BB<br>
-; X86-NEXT: [[F_CALLS_X:.*]]:{{$}}<br>
+; X86:      .cv_loc 2 1 12 62 # source.c:12:62<br>
 ; X86:      calll   _x<br>
-; X86-NEXT: [[F_CALLS_Y:.*]]:<br>
+; X86:      .cv_loc 2 1 13 63 # source.c:13:63<br>
 ; X86:      calll   _y<br>
-; X86-NEXT: [[F_CALLS_Z:.*]]:<br>
+; X86:      .cv_loc 2 1 14 72 # source.c:14:72<br>
 ; X86:      calll   _z<br>
-; X86-NEXT: [[F_RETURN:.*]]:<br>
+; X86:      .cv_loc 2 1 15 73 # source.c:15:73<br>
 ; X86:      ret<br>
 ; X86-NEXT: [[END_OF_F:.*]]:<br>
 ;<br>
@@ -74,27 +75,7 @@<br>
 ; Padding<br>
 ; X86-NEXT: .zero   3<br>
 ; Line table subsection for x<br>
-; X86-NEXT: .long   242<br>
-; X86-NEXT: .long [[F2_END:.*]]-[[F2_START:.*]]<br>
-; X86-NEXT: [[F2_START]]:<br>
-; X86-NEXT: .secrel32       _x<br>
-; X86-NEXT: .secidx _x<br>
-; X86-NEXT: .short 1<br>
-; X86-NEXT: .long [[END_OF_X]]-_x<br>
-; X86-NEXT: [[FILE_SEGMENT_START:[^:]*]]:<br>
-; X86-NEXT: .long   0<br>
-; X86-NEXT: .long   2<br>
-; X86-NEXT: .long [[FILE_SEGMENT_END:.*]]-[[FILE_SEGMENT_START]]<br>
-; X86-NEXT: .long [[X_CALL]]-_x<br>
-; X86-NEXT: .long   -2147483644<br>
-; X86-NEXT: .long [[X_RETURN]]-_x<br>
-; X86-NEXT: .long   -2147483643<br>
-; X86-NEXT: .short 42<br>
-; X86-NEXT: .short 0<br>
-; X86-NEXT: .short 43<br>
-; X86-NEXT: .short 0<br>
-; X86-NEXT: [[FILE_SEGMENT_END]]:<br>
-; X86-NEXT: [[F2_END]]:<br>
+; X86: .cv_linetable 0, _x, [[END_OF_X]]<br>
 ; Symbol subsection for y<br>
 ; X86-NEXT: .long   241<br>
 ; X86-NEXT: .long [[F1_END:.*]]-[[F1_START:.*]]<br>
@@ -117,27 +98,7 @@<br>
 ; Padding<br>
 ; X86-NEXT: .zero   3<br>
 ; Line table subsection for y<br>
-; X86-NEXT: .long   242<br>
-; X86-NEXT: .long [[F2_END:.*]]-[[F2_START:.*]]<br>
-; X86-NEXT: [[F2_START]]:<br>
-; X86-NEXT: .secrel32       _y<br>
-; X86-NEXT: .secidx _y<br>
-; X86-NEXT: .short 1<br>
-; X86-NEXT: .long [[END_OF_Y]]-_y<br>
-; X86-NEXT: [[FILE_SEGMENT_START:[^:]*]]:<br>
-; X86-NEXT: .long   0<br>
-; X86-NEXT: .long   2<br>
-; X86-NEXT: .long [[FILE_SEGMENT_END:.*]]-[[FILE_SEGMENT_START]]<br>
-; X86-NEXT: .long [[Y_CALL]]-_y<br>
-; X86-NEXT: .long   -2147483640<br>
-; X86-NEXT: .long [[Y_RETURN]]-_y<br>
-; X86-NEXT: .long   -2147483639<br>
-; X86-NEXT: .short 52<br>
-; X86-NEXT: .short 0<br>
-; X86-NEXT: .short 53<br>
-; X86-NEXT: .short 0<br>
-; X86-NEXT: [[FILE_SEGMENT_END]]:<br>
-; X86-NEXT: [[F2_END]]:<br>
+; X86: .cv_linetable 1, _y, [[END_OF_Y]]<br>
 ; Symbol subsection for f<br>
 ; X86-NEXT: .long   241<br>
 ; X86-NEXT: .long [[F1_END:.*]]-[[F1_START:.*]]<br>
@@ -160,51 +121,13 @@<br>
 ; Padding<br>
 ; X86-NEXT: .zero   3<br>
 ; Line table subsection for f<br>
-; X86-NEXT: .long   242<br>
-; X86-NEXT: .long [[F2_END:.*]]-[[F2_START:.*]]<br>
-; X86-NEXT: [[F2_START]]:<br>
-; X86-NEXT: .secrel32 _f<br>
-; X86-NEXT: .secidx _f<br>
-; X86-NEXT: .short 1<br>
-; X86-NEXT: .long [[END_OF_F]]-_f<br>
-; X86-NEXT: [[FILE_SEGMENT_START:[^:]*]]:<br>
-; X86-NEXT: .long   0<br>
-; X86-NEXT: .long   4<br>
-; X86-NEXT: .long [[FILE_SEGMENT_END:.*]]-[[FILE_SEGMENT_START]]<br>
-; X86-NEXT: .long [[F_CALLS_X]]-_f<br>
-; X86-NEXT: .long   -2147483636<br>
-; X86-NEXT: .long [[F_CALLS_Y]]-_f<br>
-; X86-NEXT: .long   -2147483635<br>
-; X86-NEXT: .long [[F_CALLS_Z]]-_f<br>
-; X86-NEXT: .long   -2147483634<br>
-; X86-NEXT: .long [[F_RETURN]]-_f<br>
-; X86-NEXT: .long   -2147483633<br>
-; X86-NEXT: .short 62<br>
-; X86-NEXT: .short 0<br>
-; X86-NEXT: .short 63<br>
-; X86-NEXT: .short 0<br>
-; X86-NEXT: .short 72<br>
-; X86-NEXT: .short 0<br>
-; X86-NEXT: .short 73<br>
-; X86-NEXT: .short 0<br>
-; X86-NEXT: [[FILE_SEGMENT_END]]:<br>
-; X86-NEXT: [[F2_END]]:<br>
-; File index to string table offset subsection<br>
-; X86-NEXT: .long   244<br>
-; X86-NEXT: .long   8<br>
-; X86-NEXT: .long   1<br>
-; X86-NEXT: .long   0<br>
-; String table<br>
-; X86-NEXT: .long   243<br>
-; X86-NEXT: .long   13<br>
-; X86-NEXT: .byte   0<br>
-; X86-NEXT: .ascii  "D:\\source.c"<br>
-; X86-NEXT: .byte   0<br>
-; X86-NEXT: .zero   3<br>
+; X86: .cv_linetable 2, _f, [[END_OF_F]]<br>
+; X86: .cv_filechecksums<br>
+; X86: .cv_stringtable<br>
<br>
 ; OBJ32:    Section {<br>
 ; OBJ32:      Name: .debug$S (2E 64 65 62 75 67 24 53)<br>
-; OBJ32:      Characteristics [ (0x42100040)<br>
+; OBJ32:      Characteristics [ (0x42300040)<br>
 ; OBJ32:      ]<br>
 ; OBJ32:      Relocations [<br>
 ; OBJ32-NEXT:   0x2C IMAGE_REL_I386_SECREL _x<br>
@@ -343,40 +266,41 @@<br>
<br>
 ; X64-LABEL: x:<br>
 ; X64-NEXT: .L{{.*}}:<br>
-; X64-NEXT: [[X_START:.*]]:{{$}}<br>
+; X64:      .cv_file 1 "D:\\source.c"<br>
+; X64:      .cv_loc 0 1 3 0 is_stmt 0 # source.c:3:0<br>
 ; X64:      # BB<br>
 ; X64:      subq    $40, %rsp<br>
-; X64-NEXT: [[X_CALL_LINE:.*]]:{{$}}<br>
+; X64:      .cv_loc 0 1 4 42 # source.c:4:42<br>
 ; X64-NEXT: callq   z<br>
-; X64-NEXT: [[X_EPILOG_AND_RET:.*]]:<br>
+; X64:      .cv_loc 0 1 5 43 # source.c:5:43<br>
 ; X64:      addq    $40, %rsp<br>
 ; X64-NEXT: ret<br>
 ; X64-NEXT: [[END_OF_X:.*]]:<br>
 ;<br>
 ; X64-LABEL: y:<br>
 ; X64-NEXT: .L{{.*}}:<br>
-; X64-NEXT: [[Y_START:.*]]:{{$}}<br>
+; X64:      .cv_loc 1 1 7 0 # source.c:7:0<br>
 ; X64:      # BB<br>
 ; X64:      subq    $40, %rsp<br>
-; X64-NEXT: [[Y_CALL_LINE:.*]]:{{$}}<br>
+; X64:      .cv_loc 1 1 8 52 # source.c:8:52<br>
 ; X64-NEXT: callq   z<br>
-; X64-NEXT: [[Y_EPILOG_AND_RET:.*]]:<br>
+; X64:      .cv_loc 1 1 9 53 # source.c:9:53<br>
 ; X64:      addq    $40, %rsp<br>
 ; X64-NEXT: ret<br>
 ; X64-NEXT: [[END_OF_Y:.*]]:<br>
 ;<br>
 ; X64-LABEL: f:<br>
 ; X64-NEXT: .L{{.*}}:<br>
-; X64-NEXT: [[F_START:.*]]:{{$}}<br>
+; X64:      .cv_loc 2 1 11 0 # source.c:11:0<br>
 ; X64:      # BB<br>
 ; X64:      subq    $40, %rsp<br>
-; X64-NEXT: [[F_CALLS_X:.*]]:{{$}}<br>
+; X64:      .cv_loc 2 1 12 62 # source.c:12:62<br>
 ; X64-NEXT: callq   x<br>
-; X64-NEXT: [[F_CALLS_Y:.*]]:<br>
+; X64:      .cv_loc 2 1 13 63 # source.c:13:63<br>
 ; X64:      callq   y<br>
-; X64-NEXT: [[F_CALLS_Z:.*]]:<br>
+; X64:      .cv_loc 2 1 14 72 # source.c:14:72<br>
 ; X64:      callq   z<br>
-; X64-NEXT: [[F_EPILOG_AND_RET:.*]]:<br>
+; X64:      .cv_loc 2 1 15 73 # source.c:15:73<br>
 ; X64:      addq    $40, %rsp<br>
 ; X64-NEXT: ret<br>
 ; X64-NEXT: [[END_OF_F:.*]]:<br>
@@ -405,31 +329,7 @@<br>
 ; Padding<br>
 ; X64-NEXT: .zero   3<br>
 ; Line table subsection for x<br>
-; X64-NEXT: .long   242<br>
-; X64-NEXT: .long [[F2_END:.*]]-[[F2_START:.*]]<br>
-; X64-NEXT: [[F2_START]]:<br>
-; X64-NEXT: .secrel32 x<br>
-; X64-NEXT: .secidx x<br>
-; X64-NEXT: .short 1<br>
-; X64-NEXT: .long [[END_OF_X]]-x<br>
-; X64-NEXT: [[FILE_SEGMENT_START:[^:]*]]:<br>
-; X64-NEXT: .long   0<br>
-; X64-NEXT: .long   3<br>
-; X64-NEXT: .long [[FILE_SEGMENT_END:.*]]-[[FILE_SEGMENT_START]]<br>
-; X64-NEXT: .long [[X_START]]-x<br>
-; X64-NEXT: .long   -2147483645<br>
-; X64-NEXT: .long [[X_CALL_LINE]]-x<br>
-; X64-NEXT: .long   -2147483644<br>
-; X64-NEXT: .long [[X_EPILOG_AND_RET]]-x<br>
-; X64-NEXT: .long   -2147483643<br>
-; X64-NEXT: .short 0<br>
-; X64-NEXT: .short 0<br>
-; X64-NEXT: .short 42<br>
-; X64-NEXT: .short 0<br>
-; X64-NEXT: .short 43<br>
-; X64-NEXT: .short 0<br>
-; X64-NEXT: [[FILE_SEGMENT_END]]:<br>
-; X64-NEXT: [[F2_END]]:<br>
+; X64: .cv_linetable 0, x, [[END_OF_X]]<br>
 ; Symbol subsection for y<br>
 ; X64-NEXT: .long   241<br>
 ; X64-NEXT: .long [[F1_END:.*]]-[[F1_START:.*]]<br>
@@ -452,31 +352,7 @@<br>
 ; Padding<br>
 ; X64-NEXT: .zero   3<br>
 ; Line table subsection for y<br>
-; X64-NEXT: .long   242<br>
-; X64-NEXT: .long [[F2_END:.*]]-[[F2_START:.*]]<br>
-; X64-NEXT: [[F2_START]]:<br>
-; X64-NEXT: .secrel32 y<br>
-; X64-NEXT: .secidx y<br>
-; X64-NEXT: .short 1<br>
-; X64-NEXT: .long [[END_OF_Y]]-y<br>
-; X64-NEXT: [[FILE_SEGMENT_START:[^:]*]]:<br>
-; X64-NEXT: .long   0<br>
-; X64-NEXT: .long   3<br>
-; X64-NEXT: .long [[FILE_SEGMENT_END:.*]]-[[FILE_SEGMENT_START]]<br>
-; X64-NEXT: .long [[Y_START]]-y<br>
-; X64-NEXT: .long   -2147483641<br>
-; X64-NEXT: .long [[Y_CALL_LINE]]-y<br>
-; X64-NEXT: .long   -2147483640<br>
-; X64-NEXT: .long [[Y_EPILOG_AND_RET]]-y<br>
-; X64-NEXT: .long   -2147483639<br>
-; X64-NEXT: .short 0<br>
-; X64-NEXT: .short 0<br>
-; X64-NEXT: .short 52<br>
-; X64-NEXT: .short 0<br>
-; X64-NEXT: .short 53<br>
-; X64-NEXT: .short 0<br>
-; X64-NEXT: [[FILE_SEGMENT_END]]:<br>
-; X64-NEXT: [[F2_END]]:<br>
+; X64: .cv_linetable 1, y, [[END_OF_Y]]<br>
 ; Symbol subsection for f<br>
 ; X64-NEXT: .long   241<br>
 ; X64-NEXT: .long [[F1_END:.*]]-[[F1_START:.*]]<br>
@@ -499,55 +375,15 @@<br>
 ; Padding<br>
 ; X64-NEXT: .zero   3<br>
 ; Line table subsection for f<br>
-; X64-NEXT: .long   242<br>
-; X64-NEXT: .long [[F2_END:.*]]-[[F2_START:.*]]<br>
-; X64-NEXT: [[F2_START]]:<br>
-; X64-NEXT: .secrel32 f<br>
-; X64-NEXT: .secidx f<br>
-; X64-NEXT: .short 1<br>
-; X64-NEXT: .long [[END_OF_F]]-f<br>
-; X64-NEXT: [[FILE_SEGMENT_START:[^:]*]]:<br>
-; X64-NEXT: .long   0<br>
-; X64-NEXT: .long   5<br>
-; X64-NEXT: .long [[FILE_SEGMENT_END:.*]]-[[FILE_SEGMENT_START]]<br>
-; X64-NEXT: .long [[F_START]]-f<br>
-; X64-NEXT: .long   -2147483637<br>
-; X64-NEXT: .long [[F_CALLS_X]]-f<br>
-; X64-NEXT: .long   -2147483636<br>
-; X64-NEXT: .long [[F_CALLS_Y]]-f<br>
-; X64-NEXT: .long   -2147483635<br>
-; X64-NEXT: .long [[F_CALLS_Z]]-f<br>
-; X64-NEXT: .long   -2147483634<br>
-; X64-NEXT: .long [[F_EPILOG_AND_RET]]-f<br>
-; X64-NEXT: .long   -2147483633<br>
-; X64-NEXT: .short 0<br>
-; X64-NEXT: .short 0<br>
-; X64-NEXT: .short 62<br>
-; X64-NEXT: .short 0<br>
-; X64-NEXT: .short 63<br>
-; X64-NEXT: .short 0<br>
-; X64-NEXT: .short 72<br>
-; X64-NEXT: .short 0<br>
-; X64-NEXT: .short 73<br>
-; X64-NEXT: .short 0<br>
-; X64-NEXT: [[FILE_SEGMENT_END]]:<br>
-; X64-NEXT: [[F2_END]]:<br>
+; X64: .cv_linetable 2, f, [[END_OF_F]]<br>
 ; File index to string table offset subsection<br>
-; X64-NEXT: .long   244<br>
-; X64-NEXT: .long   8<br>
-; X64-NEXT: .long   1<br>
-; X64-NEXT: .long   0<br>
+; X64: .cv_filechecksums<br>
 ; String table<br>
-; X64-NEXT: .long   243<br>
-; X64-NEXT: .long   13<br>
-; X64-NEXT: .byte   0<br>
-; X64-NEXT: .ascii  "D:\\source.c"<br>
-; X64-NEXT: .byte   0<br>
-; X64-NEXT: .zero   3<br>
+; X64: .cv_stringtable<br>
<br>
 ; OBJ64:    Section {<br>
 ; OBJ64:      Name: .debug$S (2E 64 65 62 75 67 24 53)<br>
-; OBJ64:      Characteristics [ (0x42100040)<br>
+; OBJ64:      Characteristics [ (0x42300040)<br>
 ; OBJ64:      ]<br>
 ; OBJ64:      Relocations [<br>
 ; OBJ64-NEXT:   0x2C IMAGE_REL_AMD64_SECREL x<br>
<br>
Modified: llvm/trunk/test/DebugInfo/COFF/simple.ll<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/test/DebugInfo/COFF/simple.ll?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/test/DebugInfo/COFF/simple.ll?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/test/DebugInfo/COFF/simple.ll (original)<br>
+++ llvm/trunk/test/DebugInfo/COFF/simple.ll Thu Jan 28 18:49:42 2016<br>
@@ -13,9 +13,10 @@<br>
<br>
 ; X86-LABEL: _f:<br>
 ; X86:      # BB<br>
-; X86-NEXT: [[CALL_LINE:^L.*]]:{{$}}<br>
+; X86:      .cv_file 1 "D:\\test.c"<br>
+; X86:      .cv_loc 0 1 4 2 is_stmt 0 # test.c:4:2<br>
 ; X86:      calll   _g<br>
-; X86-NEXT: [[RETURN_STMT:.*]]:<br>
+; X86:      .cv_loc 0 1 5 0 # test.c:5:0<br>
 ; X86:      ret<br>
 ; X86-NEXT: [[END_OF_F:.*]]:<br>
 ;<br>
@@ -43,44 +44,15 @@<br>
 ; Padding<br>
 ; X86-NEXT: .zero   3<br>
 ; Line table<br>
-; X86-NEXT: .long   242<br>
-; X86-NEXT: .long [[F2_END:.*]]-[[F2_START:.*]]<br>
-; X86-NEXT: [[F2_START]]:<br>
-; X86-NEXT: .secrel32 _f<br>
-; X86-NEXT: .secidx _f<br>
-; X86-NEXT: .short  1<br>
-; X86-NEXT: .long [[END_OF_F]]-_f<br>
-; X86-NEXT: [[FILE_SEGMENT_START:[^:]*]]:<br>
-; X86-NEXT: .long   0<br>
-; X86-NEXT: .long   2<br>
-; X86-NEXT: .long [[FILE_SEGMENT_END:.*]]-[[FILE_SEGMENT_START]]<br>
-; X86-NEXT: .long [[CALL_LINE]]-_f<br>
-; X86-NEXT: .long   -2147483644<br>
-; X86-NEXT: .long [[RETURN_STMT]]-_f<br>
-; X86-NEXT: .long   -2147483643<br>
-; X86-NEXT: .short  0<br>
-; X86-NEXT: .short  0<br>
-; X86-NEXT: .short  0<br>
-; X86-NEXT: .short  0<br>
-; X86-NEXT: [[FILE_SEGMENT_END]]:<br>
-; X86-NEXT: [[F2_END]]:<br>
+; X86-NEXT: .cv_linetable 0, _f, [[END_OF_F]]<br>
 ; File index to string table offset subsection<br>
-; X86-NEXT: .long   244<br>
-; X86-NEXT: .long   8<br>
-; X86-NEXT: .long   1<br>
-; X86-NEXT: .long   0<br>
+; X86-NEXT: .cv_filechecksums<br>
 ; String table<br>
-; X86-NEXT: .long   243<br>
-; X86-NEXT: .long   11<br>
-; X86-NEXT: .byte   0<br>
-; X86-NEXT: .ascii  "D:\\test.c"<br>
-; X86-NEXT: .byte   0<br>
-; Padding<br>
-; X86-NEXT: .zero   1<br>
+; X86-NEXT: .cv_stringtable<br>
<br>
 ; OBJ32:    Section {<br>
 ; OBJ32:      Name: .debug$S (2E 64 65 62 75 67 24 53)<br>
-; OBJ32:      Characteristics [ (0x42100040)<br>
+; OBJ32:      Characteristics [ (0x42300040)<br>
 ; OBJ32:      ]<br>
 ; OBJ32:      Relocations [<br>
 ; OBJ32-NEXT:   0x2C IMAGE_REL_I386_SECREL _f<br>
@@ -108,7 +80,7 @@<br>
 ; OBJ32-NEXT:       LineNumberStart: 4<br>
 ; OBJ32-NEXT:       LineNumberEndDelta: 0<br>
 ; OBJ32-NEXT:       IsStatement: Yes<br>
-; OBJ32-NEXT:       ColStart: 0<br>
+; OBJ32-NEXT:       ColStart: 2<br>
 ; OBJ32-NEXT:       ColEnd: 0<br>
 ; OBJ32-NEXT:     ]<br>
 ; OBJ32-NEXT:     +0x5 [<br>
@@ -123,12 +95,13 @@<br>
<br>
 ; X64-LABEL: f:<br>
 ; X64-NEXT: .L{{.*}}:{{$}}<br>
-; X64-NEXT: [[START:.*]]:{{$}}<br>
+; X64:      .cv_file 1 "D:\\test.c"<br>
+; X64:      .cv_loc 0 1 3 0 is_stmt 0 # test.c:3:0<br>
 ; X64:      # BB<br>
 ; X64:      subq    $40, %rsp<br>
-; X64-NEXT: [[CALL_LINE:.*]]:{{$}}<br>
+; X64:      .cv_loc 0 1 4 2 # test.c:4:2<br>
 ; X64-NEXT: callq   g<br>
-; X64-NEXT: [[EPILOG_AND_RET:.*]]:<br>
+; X64:      .cv_loc 0 1 5 0 # test.c:5:0<br>
 ; X64:      addq    $40, %rsp<br>
 ; X64-NEXT: ret<br>
 ; X64-NEXT: [[END_OF_F:.*]]:<br>
@@ -157,48 +130,15 @@<br>
 ; Padding<br>
 ; X64-NEXT: .zero   3<br>
 ; Line table<br>
-; X64-NEXT: .long   242<br>
-; X64-NEXT: .long [[F2_END:.*]]-[[F2_START:.*]]<br>
-; X64-NEXT: [[F2_START]]:<br>
-; X64-NEXT: .secrel32 f<br>
-; X64-NEXT: .secidx f<br>
-; X64-NEXT: .short  1<br>
-; X64-NEXT: .long [[END_OF_F]]-f<br>
-; X64-NEXT: [[FILE_SEGMENT_START:[^:]*]]:<br>
-; X64-NEXT: .long   0<br>
-; X64-NEXT: .long   3<br>
-; X64-NEXT: .long [[FILE_SEGMENT_END:.*]]-[[FILE_SEGMENT_START]]<br>
-; X64-NEXT: .long [[START]]-f<br>
-; X64-NEXT: .long   -2147483645<br>
-; X64-NEXT: .long [[CALL_LINE]]-f<br>
-; X64-NEXT: .long   -2147483644<br>
-; X64-NEXT: .long [[EPILOG_AND_RET]]-f<br>
-; X64-NEXT: .long   -2147483643<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: .short  0<br>
-; X64-NEXT: [[FILE_SEGMENT_END]]:<br>
-; X64-NEXT: [[F2_END]]:<br>
+; X64-NEXT: .cv_linetable 0, f, [[END_OF_F]]<br>
 ; File index to string table offset subsection<br>
-; X64-NEXT: .long   244<br>
-; X64-NEXT: .long   8<br>
-; X64-NEXT: .long   1<br>
-; X64-NEXT: .long   0<br>
+; X64-NEXT: .cv_filechecksums<br>
 ; String table<br>
-; X64-NEXT: .long   243<br>
-; X64-NEXT: .long   11<br>
-; X64-NEXT: .byte   0<br>
-; X64-NEXT: .ascii  "D:\\test.c"<br>
-; X64-NEXT: .byte   0<br>
-; Padding<br>
-; X64-NEXT: .zero   1<br>
+; X64-NEXT: .cv_stringtable<br>
<br>
 ; OBJ64:    Section {<br>
 ; OBJ64:      Name: .debug$S (2E 64 65 62 75 67 24 53)<br>
-; OBJ64:      Characteristics [ (0x42100040)<br>
+; OBJ64:      Characteristics [ (0x42300040)<br>
 ; OBJ64:      ]<br>
 ; OBJ64:      Relocations [<br>
 ; OBJ64-NEXT:   0x2C IMAGE_REL_AMD64_SECREL f<br>
@@ -233,7 +173,7 @@<br>
 ; OBJ64-NEXT:       LineNumberStart: 4<br>
 ; OBJ64-NEXT:       LineNumberEndDelta: 0<br>
 ; OBJ64-NEXT:       IsStatement: Yes<br>
-; OBJ64-NEXT:       ColStart: 0<br>
+; OBJ64-NEXT:       ColStart: 2<br>
 ; OBJ64-NEXT:       ColEnd: 0<br>
 ; OBJ64-NEXT:     ]<br>
 ; OBJ64-NEXT:     +0x9 [<br>
@@ -274,5 +214,5 @@ attributes #1 = { "less-precise-fpmad"="<br>
 !9 = !{i32 2, !"CodeView", i32 1}<br>
 !10 = !{i32 1, !"Debug Info Version", i32 3}<br>
 !11 = !{!"clang version 3.5 "}<br>
-!12 = !DILocation(line: 4, scope: !4)<br>
+!12 = !DILocation(line: 4, column: 2, scope: !4)<br>
 !13 = !DILocation(line: 5, scope: !4)<br>
<br>
Modified: llvm/trunk/test/DebugInfo/COFF/tail-call-without-lexical-scopes.ll<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/test/DebugInfo/COFF/tail-call-without-lexical-scopes.ll?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/test/DebugInfo/COFF/tail-call-without-lexical-scopes.ll?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/test/DebugInfo/COFF/tail-call-without-lexical-scopes.ll (original)<br>
+++ llvm/trunk/test/DebugInfo/COFF/tail-call-without-lexical-scopes.ll Thu Jan 28 18:49:42 2016<br>
@@ -15,10 +15,10 @@<br>
 ; The bar function happens to have no lexical scopes, yet it has one instruction<br>
 ; with debug information available.  This used to be PR19239.<br>
<br>
+; X86:      .cv_file 1 "D:\\test.cpp"<br>
+<br>
 ; X86-LABEL: {{^}}"?bar@@YAXHZZ":<br>
-; X86-NEXT: L{{.*}}:<br>
-; X86-NEXT: # BB<br>
-; X86-NEXT: [[JMP_LINE:^L.*]]:{{$}}<br>
+; X86:      .cv_loc  1 1 4 0<br>
 ; X86:      jmp "?foo@@YAXXZ"<br>
 ; X86-NEXT: [[END_OF_BAR:^L.*]]:{{$}}<br>
 ; X86-NOT:  ret<br>
@@ -26,13 +26,9 @@<br>
 ; X86-LABEL: .section        .debug$S,"dr"<br>
 ; X86:       .secrel32 "?bar@@YAXHZZ"<br>
 ; X86-NEXT:  .secidx   "?bar@@YAXHZZ"<br>
-; X86:       .long   0<br>
-; X86-NEXT:  .long   1<br>
-; X86-NEXT:  .long {{.*}}<br>
-; X86-NEXT:  .long [[JMP_LINE]]-"?bar@@YAXHZZ"<br>
-; X86-NEXT:  .long   -2147483644<br>
-<br>
-; X86-LABEL: .long   244<br>
+; X86:       .cv_linetable 1, "?bar@@YAXHZZ", [[END_OF_BAR]]<br>
+; X86:       .cv_filechecksums<br>
+; X86:       .cv_stringtable<br>
<br>
 ; ModuleID = 'test.cpp'<br>
 target datalayout = "e-m:w-p:32:32-i64:64-f80:32-n8:16:32-S32"<br>
<br>
Added: llvm/trunk/test/MC/COFF/cv-loc.s<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/test/MC/COFF/cv-loc.s?rev=259130&view=auto" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/test/MC/COFF/cv-loc.s?rev=259130&view=auto</a><br>
==============================================================================<br>
--- llvm/trunk/test/MC/COFF/cv-loc.s (added)<br>
+++ llvm/trunk/test/MC/COFF/cv-loc.s Thu Jan 28 18:49:42 2016<br>
@@ -0,0 +1,85 @@<br>
+# RUN: llvm-mc < %s -triple=x86_64-pc-win32 -filetype=obj | llvm-readobj - -codeview | FileCheck %s<br>
+<br>
+.section .debug$S<br>
+.long 4<br>
+.cv_stringtable<br>
+<br>
+.cv_file 1 "a.c"<br>
+.cv_file 2 "t.inc"<br>
+<br>
+# Implements this C:<br>
+# void f(volatile int *x) {<br>
+#   ++*x;<br>
+# #include "t.h" // contains two ++*x; statements<br>
+#   ++*x;<br>
+# }<br>
+<br>
+.text<br>
+.def     f;<br>
+        .scl    2;<br>
+        .type   32;<br>
+        .endef<br>
+        .text<br>
+        .globl  f<br>
+        .align  16, 0x90<br>
+f:<br>
+.Lfunc_begin0:<br>
+  .cv_loc 0 1 5 2<br>
+  incl (%rdi)<br>
+  # #include "t.h" start<br>
+  .cv_loc 0 2 0 0<br>
+  incl (%rdi)<br>
+  .cv_loc 0 2 1 0<br>
+  incl (%rdi)<br>
+  # #include "t.h" end<br>
+  .cv_loc 0 1 6 2<br>
+  incl (%rdi)<br>
+  retq<br>
+.Lfunc_end0:<br>
+<br>
+.section .debug$S<br>
+.cv_filechecksums<br>
+.cv_linetable 0, f, .Lfunc_end0<br>
+<br>
+# CHECK: FunctionLineTable [<br>
+# CHECK:   LinkageName: f<br>
+# CHECK:   Flags: 0x1<br>
+# CHECK:   CodeSize: 0x9<br>
+# CHECK:   FilenameSegment [<br>
+# CHECK:     Filename: a.c (0x0)<br>
+# CHECK:     +0x0 [<br>
+# CHECK:       LineNumberStart: 5<br>
+# CHECK:       LineNumberEndDelta: 0<br>
+# CHECK:       IsStatement: Yes<br>
+# CHECK:       ColStart: 2<br>
+# CHECK:       ColEnd: 0<br>
+# CHECK:     ]<br>
+# CHECK:   ]<br>
+# CHECK:   FilenameSegment [<br>
+# CHECK:     Filename: t.inc (0x8)<br>
+# CHECK:     +0x2 [<br>
+# CHECK:       LineNumberStart: 0<br>
+# CHECK:       LineNumberEndDelta: 0<br>
+# CHECK:       IsStatement: Yes<br>
+# CHECK:       ColStart: 0<br>
+# CHECK:       ColEnd: 0<br>
+# CHECK:     ]<br>
+# CHECK:     +0x4 [<br>
+# CHECK:       LineNumberStart: 1<br>
+# CHECK:       LineNumberEndDelta: 0<br>
+# CHECK:       IsStatement: Yes<br>
+# CHECK:       ColStart: 0<br>
+# CHECK:       ColEnd: 0<br>
+# CHECK:     ]<br>
+# CHECK:   ]<br>
+# CHECK:   FilenameSegment [<br>
+# CHECK:     Filename: a.c (0x0)<br>
+# CHECK:     +0x6 [<br>
+# CHECK:       LineNumberStart: 6<br>
+# CHECK:       LineNumberEndDelta: 0<br>
+# CHECK:       IsStatement: Yes<br>
+# CHECK:       ColStart: 2<br>
+# CHECK:       ColEnd: 0<br>
+# CHECK:     ]<br>
+# CHECK:   ]<br>
+# CHECK: ]<br>
<br>
Modified: llvm/trunk/tools/llvm-readobj/COFFDumper.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/tools/llvm-readobj/COFFDumper.cpp?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/tools/llvm-readobj/COFFDumper.cpp?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/tools/llvm-readobj/COFFDumper.cpp (original)<br>
+++ llvm/trunk/tools/llvm-readobj/COFFDumper.cpp Thu Jan 28 18:49:42 2016<br>
@@ -1116,8 +1116,7 @@ void COFFDumper::printCodeViewSymbolSect<br>
     uint32_t Offset = 6;  // Skip relocations.<br>
     uint16_t Flags = DE.getU16(&Offset);<br>
     W.printHex("Flags", Flags);<br>
-    bool HasColumnInformation =<br>
-        Flags & COFF::DEBUG_LINE_TABLES_HAVE_COLUMN_RECORDS;<br>
+    bool HasColumnInformation = Flags & codeview::LineFlags::HaveColumns;<br>
     uint32_t FunctionSize = DE.getU32(&Offset);<br>
     W.printHex("CodeSize", FunctionSize);<br>
     while (DE.isValidOffset(Offset)) {<br>
@@ -1151,11 +1150,11 @@ void COFFDumper::printCodeViewSymbolSect<br>
         char Buffer[32];<br>
         format("+0x%X", PC).snprint(Buffer, 32);<br>
         ListScope PCScope(W, Buffer);<br>
-        uint32_t LineNumberStart = LineData & COFF::CVL_MaxLineNumber;<br>
+        uint32_t LineNumberStart = LineData & codeview::LineInfo::StartLineMask;<br>
         uint32_t LineNumberEndDelta =<br>
-            (LineData >> COFF::CVL_LineNumberStartBits) &<br>
-            COFF::CVL_LineNumberEndDeltaMask;<br>
-        bool IsStatement = LineData & COFF::CVL_IsStatement;<br>
+            (LineData & codeview::LineInfo::EndLineDeltaMask) >><br>
+            codeview::LineInfo::EndLineDeltaShift;<br>
+        bool IsStatement = codeview::LineInfo::StatementFlag;<br>
         W.printNumber("LineNumberStart", LineNumberStart);<br>
         W.printNumber("LineNumberEndDelta", LineNumberEndDelta);<br>
         W.printBoolean("IsStatement", IsStatement);<br>
<br>
Modified: llvm/trunk/unittests/MC/StringTableBuilderTest.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/unittests/MC/StringTableBuilderTest.cpp?rev=259130&r1=259129&r2=259130&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/unittests/MC/StringTableBuilderTest.cpp?rev=259130&r1=259129&r2=259130&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/unittests/MC/StringTableBuilderTest.cpp (original)<br>
+++ llvm/trunk/unittests/MC/StringTableBuilderTest.cpp Thu Jan 28 18:49:42 2016<br>
@@ -68,4 +68,27 @@ TEST(StringTableBuilderTest, BasicWinCOF<br>
   EXPECT_EQ(23U, B.getOffset("river horse"));<br>
 }<br>
<br>
+TEST(StringTableBuilderTest, ELFInOrder) {<br>
+  StringTableBuilder B(StringTableBuilder::ELF);<br>
+  EXPECT_EQ(1U, B.add("foo"));<br>
+  EXPECT_EQ(5U, B.add("bar"));<br>
+  EXPECT_EQ(9U, B.add("foobar"));<br>
+<br>
+  B.finalizeInOrder();<br>
+<br>
+  std::string Expected;<br>
+  Expected += '\x00';<br>
+  Expected += "foo";<br>
+  Expected += '\x00';<br>
+  Expected += "bar";<br>
+  Expected += '\x00';<br>
+  Expected += "foobar";<br>
+  Expected += '\x00';<br>
+<br>
+  EXPECT_EQ(Expected, B.data());<br>
+  EXPECT_EQ(1U, B.getOffset("foo"));<br>
+  EXPECT_EQ(5U, B.getOffset("bar"));<br>
+  EXPECT_EQ(9U, B.getOffset("foobar"));<br>
+}<br>
+<br>
 }<br>
<br>
<br>
_______________________________________________<br>
llvm-commits mailing list<br>
<a href="mailto:llvm-commits@lists.llvm.org">llvm-commits@lists.llvm.org</a><br>
<a href="http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits" rel="noreferrer" target="_blank">http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits</a><br>
</blockquote></div><br></div>