<div dir="ltr"><br><div class="gmail_extra"><br><div class="gmail_quote">On Thu, Apr 30, 2015 at 2:51 PM, Rafael Espindola <span dir="ltr"><<a href="mailto:rafael.espindola@gmail.com" target="_blank">rafael.espindola@gmail.com</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Author: rafael<br>
Date: Thu Apr 30 16:51:58 2015<br>
New Revision: 236267<br>
<br>
URL: <a href="http://llvm.org/viewvc/llvm-project?rev=236267&view=rev" target="_blank">http://llvm.org/viewvc/llvm-project?rev=236267&view=rev</a><br>
Log:<br>
Simplify the creation of compressed debug sections.<br></blockquote><div><br>Awesome, thanks a bunch!<br><br>It was pretty confusing figuring out how to do this when I implemented it - creating fragments, etc.<br> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
<br>
This is actually fairly simple in the current code layout: Check if we should<br>
compress just before writing out and everything else just works.<br>
<br>
This removes the last case in which the object writer was creating a<br>
fragment.<br>
<br>
Modified:<br>
    llvm/trunk/lib/MC/ELFObjectWriter.cpp<br>
<br>
Modified: llvm/trunk/lib/MC/ELFObjectWriter.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/ELFObjectWriter.cpp?rev=236267&r1=236266&r2=236267&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/ELFObjectWriter.cpp?rev=236267&r1=236266&r2=236267&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/MC/ELFObjectWriter.cpp (original)<br>
+++ llvm/trunk/lib/MC/ELFObjectWriter.cpp Thu Apr 30 16:51:58 2015<br>
@@ -182,8 +182,6 @@ class ELFObjectWriter : public MCObjectW<br>
         support::endian::Writer<support::big>(OS).write(Val);<br>
     }<br>
<br>
-    template <typename T> void write(MCDataFragment &F, T Value);<br>
-<br>
     void writeHeader(const MCAssembler &Asm);<br>
<br>
     void WriteSymbol(SymbolTableWriter &Writer, ELFSymbolData &MSD,<br>
@@ -224,8 +222,6 @@ class ELFObjectWriter : public MCObjectW<br>
     const MCSectionELF *createRelocationSection(MCAssembler &Asm,<br>
                                                 const MCSectionELF &Sec);<br>
<br>
-    void CompressDebugSections(MCAssembler &Asm, MCAsmLayout &Layout);<br>
-<br>
     const MCSectionELF *createSectionHeaderStringTable();<br>
     const MCSectionELF *createStringTable(MCContext &Ctx);<br>
<br>
@@ -236,10 +232,13 @@ class ELFObjectWriter : public MCObjectW<br>
                             const SectionIndexMapTy &SectionIndexMap,<br>
                             const SectionOffsetsTy &SectionOffsets);<br>
<br>
+    void writeSectionData(const MCAssembler &Asm, const MCSectionData &SD,<br>
+                          const MCAsmLayout &Layout);<br>
+<br>
     void WriteSecHdrEntry(uint32_t Name, uint32_t Type, uint64_t Flags,<br>
-                          uint64_t Address, uint64_t Offset,<br>
-                          uint64_t Size, uint32_t Link, uint32_t Info,<br>
-                          uint64_t Alignment, uint64_t EntrySize);<br>
+                          uint64_t Address, uint64_t Offset, uint64_t Size,<br>
+                          uint32_t Link, uint32_t Info, uint64_t Alignment,<br>
+                          uint64_t EntrySize);<br>
<br>
     void writeRelocations(const MCAssembler &Asm, const MCSectionELF &Sec);<br>
<br>
@@ -267,15 +266,6 @@ unsigned ELFObjectWriter::addToSectionTa<br>
   return SectionTable.size();<br>
 }<br>
<br>
-template <typename T> void ELFObjectWriter::write(MCDataFragment &F, T Val) {<br>
-  if (IsLittleEndian)<br>
-    Val = support::endian::byte_swap<T, support::little>(Val);<br>
-  else<br>
-    Val = support::endian::byte_swap<T, support::big>(Val);<br>
-  const char *Start = (const char *)&Val;<br>
-  F.getContents().append(Start, Start + sizeof(T));<br>
-}<br>
-<br>
 void SymbolTableWriter::createSymtabShndx() {<br>
   if (!ShndxIndexes.empty())<br>
     return;<br>
@@ -1105,7 +1095,7 @@ ELFObjectWriter::createRelocationSection<br>
<br>
 static SmallVector<char, 128><br>
 getUncompressedData(const MCAsmLayout &Layout,<br>
-                    MCSectionData::FragmentListType &Fragments) {<br>
+                    const MCSectionData::FragmentListType &Fragments) {<br>
   SmallVector<char, 128> UncompressedData;<br>
   for (const MCFragment &F : Fragments) {<br>
     const SmallVectorImpl<char> *Contents;<br>
@@ -1148,104 +1138,43 @@ prependCompressionHeader(uint64_t Size,<br>
   return true;<br>
 }<br>
<br>
-// Return a single fragment containing the compressed contents of the whole<br>
-// section. Null if the section was not compressed for any reason.<br>
-static std::unique_ptr<MCDataFragment><br>
-getCompressedFragment(const MCAsmLayout &Layout,<br>
-                      MCSectionData::FragmentListType &Fragments) {<br>
-  std::unique_ptr<MCDataFragment> CompressedFragment(new MCDataFragment());<br>
+void ELFObjectWriter::writeSectionData(const MCAssembler &Asm,<br>
+                                       const MCSectionData &SD,<br>
+                                       const MCAsmLayout &Layout) {<br>
+  const MCSectionELF &Section =<br>
+      static_cast<const MCSectionELF &>(SD.getSection());<br>
+  StringRef SectionName = Section.getSectionName();<br>
+<br>
+  // Compressing debug_frame requires handling alignment fragments which is<br>
+  // more work (possibly generalizing MCAssembler.cpp:writeFragment to allow<br>
+  // for writing to arbitrary buffers) for little benefit.<br>
+  if (!Asm.getContext().getAsmInfo()->compressDebugSections() ||<br>
+      !SectionName.startswith(".debug_") || SectionName == ".debug_frame") {<br>
+    Asm.writeSectionData(&SD, Layout);<br>
+    return;<br>
+  }<br>
<br>
-  // Gather the uncompressed data from all the fragments, recording the<br>
-  // alignment fragment, if seen, and any fixups.<br>
+  // Gather the uncompressed data from all the fragments.<br>
+  const MCSectionData::FragmentListType &Fragments = SD.getFragmentList();<br>
   SmallVector<char, 128> UncompressedData =<br>
       getUncompressedData(Layout, Fragments);<br>
<br>
-  SmallVectorImpl<char> &CompressedContents = CompressedFragment->getContents();<br>
-<br>
+  SmallVector<char, 128> CompressedContents;<br>
   zlib::Status Success = zlib::compress(<br>
       StringRef(UncompressedData.data(), UncompressedData.size()),<br>
       CompressedContents);<br>
-  if (Success != zlib::StatusOK)<br>
-    return nullptr;<br>
-<br>
-  if (!prependCompressionHeader(UncompressedData.size(), CompressedContents))<br>
-    return nullptr;<br>
-<br>
-  return CompressedFragment;<br>
-}<br>
-<br>
-typedef DenseMap<const MCSectionData *, std::vector<MCSymbolData *>><br>
-DefiningSymbolMap;<br>
-<br>
-static void UpdateSymbols(const MCAsmLayout &Layout,<br>
-                          const std::vector<MCSymbolData *> &Symbols,<br>
-                          MCFragment &NewFragment) {<br>
-  for (MCSymbolData *Sym : Symbols) {<br>
-    Sym->setOffset(Sym->getOffset() +<br>
-                   Layout.getFragmentOffset(Sym->getFragment()));<br>
-    Sym->setFragment(&NewFragment);<br>
+  if (Success != zlib::StatusOK) {<br>
+    Asm.writeSectionData(&SD, Layout);<br>
+    return;<br>
   }<br>
-}<br>
<br>
-static void CompressDebugSection(MCAssembler &Asm, MCAsmLayout &Layout,<br>
-                                 const DefiningSymbolMap &DefiningSymbols,<br>
-                                 const MCSectionELF &Section,<br>
-                                 MCSectionData &SD) {<br>
-  StringRef SectionName = Section.getSectionName();<br>
-  MCSectionData::FragmentListType &Fragments = SD.getFragmentList();<br>
-<br>
-  std::unique_ptr<MCDataFragment> CompressedFragment =<br>
-      getCompressedFragment(Layout, Fragments);<br>
-<br>
-  // Leave the section as-is if the fragments could not be compressed.<br>
-  if (!CompressedFragment)<br>
+  if (!prependCompressionHeader(UncompressedData.size(), CompressedContents)) {<br>
+    Asm.writeSectionData(&SD, Layout);<br>
     return;<br>
-<br>
-  // Update the fragment+offsets of any symbols referring to fragments in this<br>
-  // section to refer to the new fragment.<br>
-  auto I = DefiningSymbols.find(&SD);<br>
-  if (I != DefiningSymbols.end())<br>
-    UpdateSymbols(Layout, I->second, *CompressedFragment);<br>
-<br>
-  // Invalidate the layout for the whole section since it will have new and<br>
-  // different fragments now.<br>
-  Layout.invalidateFragmentsFrom(&Fragments.front());<br>
-  Fragments.clear();<br>
-<br>
-  // Complete the initialization of the new fragment<br>
-  CompressedFragment->setParent(&SD);<br>
-  CompressedFragment->setLayoutOrder(0);<br>
-  Fragments.push_back(CompressedFragment.release());<br>
-<br>
-  // Rename from .debug_* to .zdebug_*<br>
+  }<br>
   Asm.getContext().renameELFSection(&Section,<br>
                                     (".z" + SectionName.drop_front(1)).str());<br>
-}<br>
-<br>
-void ELFObjectWriter::CompressDebugSections(MCAssembler &Asm,<br>
-                                            MCAsmLayout &Layout) {<br>
-  if (!Asm.getContext().getAsmInfo()->compressDebugSections())<br>
-    return;<br>
-<br>
-  DefiningSymbolMap DefiningSymbols;<br>
-<br>
-  for (MCSymbolData &SD : Asm.symbols())<br>
-    if (MCFragment *F = SD.getFragment())<br>
-      DefiningSymbols[F->getParent()].push_back(&SD);<br>
-<br>
-  for (MCSectionData &SD : Asm) {<br>
-    const MCSectionELF &Section =<br>
-        static_cast<const MCSectionELF &>(SD.getSection());<br>
-    StringRef SectionName = Section.getSectionName();<br>
-<br>
-    // Compressing debug_frame requires handling alignment fragments which is<br>
-    // more work (possibly generalizing MCAssembler.cpp:writeFragment to allow<br>
-    // for writing to arbitrary buffers) for little benefit.<br>
-    if (!SectionName.startswith(".debug_") || SectionName == ".debug_frame")<br>
-      continue;<br>
-<br>
-    CompressDebugSection(Asm, Layout, DefiningSymbols, Section, SD);<br>
-  }<br>
+  OS << CompressedContents;<br>
 }<br>
<br>
 void ELFObjectWriter::WriteSecHdrEntry(uint32_t Name, uint32_t Type,<br>
@@ -1408,8 +1337,6 @@ void ELFObjectWriter::writeSectionHeader<br>
<br>
 void ELFObjectWriter::WriteObject(MCAssembler &Asm,<br>
                                   const MCAsmLayout &Layout) {<br>
-  CompressDebugSections(Asm, const_cast<MCAsmLayout &>(Layout));<br>
-<br>
   MCContext &Ctx = Asm.getContext();<br>
   const MCSectionELF *ShstrtabSection =<br>
       Ctx.getELFSection(".shstrtab", ELF::SHT_STRTAB, 0);<br>
@@ -1453,7 +1380,7 @@ void ELFObjectWriter::WriteObject(MCAsse<br>
       }<br>
       writeRelocations(Asm, *Section.getAssociatedSection());<br>
     } else {<br>
-      Asm.writeSectionData(&SD, Layout);<br>
+      writeSectionData(Asm, SD, Layout);<br>
     }<br>
<br>
     uint64_t SecEnd = OS.tell();<br>
<br>
<br>
_______________________________________________<br>
llvm-commits mailing list<br>
<a href="mailto:llvm-commits@cs.uiuc.edu">llvm-commits@cs.uiuc.edu</a><br>
<a href="http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits" target="_blank">http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits</a><br>
</blockquote></div><br></div></div>