[llvm] r258931 - [DebugInfo] Support zero-length CIE in the _eh_frame parser

Igor Laevsky via llvm-commits llvm-commits at lists.llvm.org
Wed Jan 27 06:05:35 PST 2016


Author: igor.laevsky
Date: Wed Jan 27 08:05:35 2016
New Revision: 258931

URL: http://llvm.org/viewvc/llvm-project?rev=258931&view=rev
Log:
[DebugInfo] Support zero-length CIE in the _eh_frame parser

MCJIT emits zero-length CIE at the end of the _eh_frame section. This change
ensures that parser inside DebugInfo will not crash and correctly record such cases.
We are now recording DW_EH_PE_omit as a default value for FDE and LSDA encodings.
Also Offset != EndAugmentationOffset assertion check will only happen if augmentation 
string had 'z' letter in it.

Differential Revision: http://reviews.llvm.org/D16588


Added:
    llvm/trunk/test/tools/llvm-objdump/Inputs/eh_frame_zero_cie.o   (with props)
    llvm/trunk/test/tools/llvm-objdump/eh_frame_zero_cie.test
Modified:
    llvm/trunk/lib/DebugInfo/DWARF/DWARFDebugFrame.cpp

Modified: llvm/trunk/lib/DebugInfo/DWARF/DWARFDebugFrame.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/DebugInfo/DWARF/DWARFDebugFrame.cpp?rev=258931&r1=258930&r2=258931&view=diff
==============================================================================
--- llvm/trunk/lib/DebugInfo/DWARF/DWARFDebugFrame.cpp (original)
+++ llvm/trunk/lib/DebugInfo/DWARF/DWARFDebugFrame.cpp Wed Jan 27 08:05:35 2016
@@ -201,8 +201,8 @@ public:
       SmallString<8> Augmentation, uint8_t AddressSize,
       uint8_t SegmentDescriptorSize, uint64_t CodeAlignmentFactor,
       int64_t DataAlignmentFactor, uint64_t ReturnAddressRegister,
-      SmallString<8> AugmentationData, Optional<uint32_t> FDEPointerEncoding,
-      Optional<uint32_t> LSDAPointerEncoding)
+      SmallString<8> AugmentationData, uint32_t FDEPointerEncoding,
+      uint32_t LSDAPointerEncoding)
       : FrameEntry(FK_CIE, Offset, Length), Version(Version),
         Augmentation(std::move(Augmentation)),
         AddressSize(AddressSize),
@@ -219,10 +219,10 @@ public:
   StringRef getAugmentationString() const { return Augmentation; }
   uint64_t getCodeAlignmentFactor() const { return CodeAlignmentFactor; }
   int64_t getDataAlignmentFactor() const { return DataAlignmentFactor; }
-  Optional<uint32_t> getFDEPointerEncoding() const {
+  uint32_t getFDEPointerEncoding() const {
     return FDEPointerEncoding;
   }
-  Optional<uint32_t> getLSDAPointerEncoding() const {
+  uint32_t getLSDAPointerEncoding() const {
     return LSDAPointerEncoding;
   }
 
@@ -265,8 +265,8 @@ private:
 
   // The following are used when the CIE represents an EH frame entry.
   SmallString<8> AugmentationData;
-  Optional<uint32_t> FDEPointerEncoding;
-  Optional<uint32_t> LSDAPointerEncoding;
+  uint32_t FDEPointerEncoding;
+  uint32_t LSDAPointerEncoding;
 };
 
 
@@ -556,16 +556,16 @@ void DWARFDebugFrame::parse(DataExtracto
       uint64_t ReturnAddressRegister = Data.getULEB128(&Offset);
 
       // Parse the augmentation data for EH CIEs
-      StringRef AugmentationData;
-      Optional<uint32_t> FDEPointerEncoding;
-      Optional<uint32_t> LSDAPointerEncoding;
+      StringRef AugmentationData("");
+      uint32_t FDEPointerEncoding = DW_EH_PE_omit;
+      uint32_t LSDAPointerEncoding = DW_EH_PE_omit;
       if (IsEH) {
         Optional<uint32_t> PersonalityEncoding;
         Optional<uint64_t> Personality;
 
-        uint64_t AugmentationLength = 0;
-        uint32_t StartAugmentationOffset = 0;
-        uint32_t EndAugmentationOffset = 0;
+        Optional<uint64_t> AugmentationLength;
+        uint32_t StartAugmentationOffset;
+        uint32_t EndAugmentationOffset;
 
         // Walk the augmentation string to get all the augmentation data.
         for (unsigned i = 0, e = AugmentationString.size(); i != e; ++i) {
@@ -573,8 +573,6 @@ void DWARFDebugFrame::parse(DataExtracto
             default:
               ReportError("Unknown augmentation character in entry at %lx");
             case 'L':
-              if (LSDAPointerEncoding)
-                ReportError("Duplicate LSDA encoding in entry at %lx");
               LSDAPointerEncoding = Data.getU8(&Offset);
               break;
             case 'P': {
@@ -585,8 +583,6 @@ void DWARFDebugFrame::parse(DataExtracto
               break;
             }
             case 'R':
-              if (FDEPointerEncoding)
-                ReportError("Duplicate FDE encoding in entry at %lx");
               FDEPointerEncoding = Data.getU8(&Offset);
               break;
             case 'z':
@@ -596,20 +592,22 @@ void DWARFDebugFrame::parse(DataExtracto
               // the string contains a 'z'.
               AugmentationLength = Data.getULEB128(&Offset);
               StartAugmentationOffset = Offset;
-              EndAugmentationOffset =
-                Offset + static_cast<uint32_t>(AugmentationLength);
+              EndAugmentationOffset = Offset +
+                static_cast<uint32_t>(*AugmentationLength);
           }
         }
 
-        if (Offset != EndAugmentationOffset)
-          ReportError("Parsing augmentation data at %lx failed");
+        if (AugmentationLength.hasValue()) {
+          if (Offset != EndAugmentationOffset)
+            ReportError("Parsing augmentation data at %lx failed");
 
-        AugmentationData = Data.getData().slice(StartAugmentationOffset,
-                                                EndAugmentationOffset);
+          AugmentationData = Data.getData().slice(StartAugmentationOffset,
+                                                  EndAugmentationOffset);
+        }
       }
 
       auto Cie = make_unique<CIE>(StartOffset, Length, Version,
-                                  StringRef(Augmentation), AddressSize,
+                                  AugmentationString, AddressSize,
                                   SegmentDescriptorSize, CodeAlignmentFactor,
                                   DataAlignmentFactor, ReturnAddressRegister,
                                   AugmentationData, FDEPointerEncoding,
@@ -628,12 +626,11 @@ void DWARFDebugFrame::parse(DataExtracto
         if (!Cie)
           ReportError("Parsing FDE data at %lx failed due to missing CIE");
 
-        Optional<uint32_t> FDEPointerEncoding = Cie->getFDEPointerEncoding();
-        if (!FDEPointerEncoding)
-          ReportError("Parsing at %lx failed due to missing pointer encoding");
+        InitialLocation = readPointer(Data, Offset,
+                                      Cie->getFDEPointerEncoding());
+        AddressRange = readPointer(Data, Offset,
+                                   Cie->getFDEPointerEncoding());
 
-        InitialLocation = readPointer(Data, Offset, *FDEPointerEncoding);
-        AddressRange = readPointer(Data, Offset, *FDEPointerEncoding);
         StringRef AugmentationString = Cie->getAugmentationString();
         if (!AugmentationString.empty()) {
           // Parse the augmentation length and data for this FDE.
@@ -644,8 +641,8 @@ void DWARFDebugFrame::parse(DataExtracto
 
           // Decode the LSDA if the CIE augmentation string said we should.
           uint64_t LSDA = 0;
-          if (Optional<uint32_t> Encoding = Cie->getLSDAPointerEncoding())
-            LSDA = readPointer(Data, Offset, *Encoding);
+          if (Cie->getLSDAPointerEncoding() != DW_EH_PE_omit)
+            LSDA = readPointer(Data, Offset, Cie->getLSDAPointerEncoding());
 
           if (Offset != EndAugmentationOffset)
             ReportError("Parsing augmentation data at %lx failed");

Added: llvm/trunk/test/tools/llvm-objdump/Inputs/eh_frame_zero_cie.o
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/llvm-objdump/Inputs/eh_frame_zero_cie.o?rev=258931&view=auto
==============================================================================
Binary file - no diff available.

Propchange: llvm/trunk/test/tools/llvm-objdump/Inputs/eh_frame_zero_cie.o
------------------------------------------------------------------------------
    svn:mime-type = application/octet-stream

Added: llvm/trunk/test/tools/llvm-objdump/eh_frame_zero_cie.test
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/llvm-objdump/eh_frame_zero_cie.test?rev=258931&view=auto
==============================================================================
--- llvm/trunk/test/tools/llvm-objdump/eh_frame_zero_cie.test (added)
+++ llvm/trunk/test/tools/llvm-objdump/eh_frame_zero_cie.test Wed Jan 27 08:05:35 2016
@@ -0,0 +1,10 @@
+# RUN: llvm-objdump -dwarf=frames %p/Inputs/eh_frame_zero_cie.o 2>/dev/null | FileCheck %s
+
+# CHECK: .eh_frame contents:
+
+# CHECK: 00000000 00000000 ffffffff CIE
+# CHECK:   Version:               0
+# CHECK:   Augmentation:          ""
+# CHECK:   Code alignment factor: 0
+# CHECK:   Data alignment factor: 0
+# CHECK:   Return address column: 0




More information about the llvm-commits mailing list