git: 82420cc68852 - stable/12 - Apply upstream lld fix for compressed input sections on BE targets

From: Dimitry Andric <dim_at_FreeBSD.org>
Date: Sat, 25 Dec 2021 11:55:39 UTC
The branch stable/12 has been updated by dim:

URL: https://cgit.FreeBSD.org/src/commit/?id=82420cc68852f332874d11b06153589fa7bce502

commit 82420cc68852f332874d11b06153589fa7bce502
Author:     Dimitry Andric <dim@FreeBSD.org>
AuthorDate: 2021-08-07 11:14:11 +0000
Commit:     Dimitry Andric <dim@FreeBSD.org>
CommitDate: 2021-12-25 11:51:14 +0000

    Apply upstream lld fix for compressed input sections on BE targets
    
    Merge commit c6ebc651b6fa from llvm git (by Simon Atanasyan):
    
      [LLD] Support compressed input sections on big-endian targets
    
      This patch enables compressed input sections on big-endian targets by
      checking the target endianness and selecting an appropriate `Chdr`
      structure.
    
      Fixes PR51369
    
      Differential Revision: https://reviews.llvm.org/D107635
    
    Reported by:    emaste
    MFC after:      3 days
    
    (cherry picked from commit d69d07569ee2404705ff4c4abb45dc0b884eeb35)
---
 contrib/llvm-project/lld/ELF/InputSection.cpp | 47 ++++++++++++---------------
 contrib/llvm-project/lld/ELF/InputSection.h   |  1 +
 2 files changed, 21 insertions(+), 27 deletions(-)

diff --git a/contrib/llvm-project/lld/ELF/InputSection.cpp b/contrib/llvm-project/lld/ELF/InputSection.cpp
index 6f16fc7abc48..f9cad7f975a7 100644
--- a/contrib/llvm-project/lld/ELF/InputSection.cpp
+++ b/contrib/llvm-project/lld/ELF/InputSection.cpp
@@ -88,7 +88,22 @@ InputSectionBase::InputSectionBase(InputFile *file, uint64_t flags,
     if (!zlib::isAvailable())
       error(toString(file) + ": contains a compressed section, " +
             "but zlib is not available");
-    parseCompressedHeader();
+    switch (config->ekind) {
+    case ELF32LEKind:
+      parseCompressedHeader<ELF32LE>();
+      break;
+    case ELF32BEKind:
+      parseCompressedHeader<ELF32BE>();
+      break;
+    case ELF64LEKind:
+      parseCompressedHeader<ELF64LE>();
+      break;
+    case ELF64BEKind:
+      parseCompressedHeader<ELF64BE>();
+      break;
+    default:
+      llvm_unreachable("unknown ELFT");
+    }
   }
 }
 
@@ -210,10 +225,7 @@ OutputSection *SectionBase::getOutputSection() {
 // When a section is compressed, `rawData` consists with a header followed
 // by zlib-compressed data. This function parses a header to initialize
 // `uncompressedSize` member and remove the header from `rawData`.
-void InputSectionBase::parseCompressedHeader() {
-  using Chdr64 = typename ELF64LE::Chdr;
-  using Chdr32 = typename ELF32LE::Chdr;
-
+template <typename ELFT> void InputSectionBase::parseCompressedHeader() {
   // Old-style header
   if (name.startswith(".zdebug")) {
     if (!toStringRef(rawData).startswith("ZLIB")) {
@@ -239,32 +251,13 @@ void InputSectionBase::parseCompressedHeader() {
   assert(flags & SHF_COMPRESSED);
   flags &= ~(uint64_t)SHF_COMPRESSED;
 
-  // New-style 64-bit header
-  if (config->is64) {
-    if (rawData.size() < sizeof(Chdr64)) {
-      error(toString(this) + ": corrupted compressed section");
-      return;
-    }
-
-    auto *hdr = reinterpret_cast<const Chdr64 *>(rawData.data());
-    if (hdr->ch_type != ELFCOMPRESS_ZLIB) {
-      error(toString(this) + ": unsupported compression type");
-      return;
-    }
-
-    uncompressedSize = hdr->ch_size;
-    alignment = std::max<uint32_t>(hdr->ch_addralign, 1);
-    rawData = rawData.slice(sizeof(*hdr));
-    return;
-  }
-
-  // New-style 32-bit header
-  if (rawData.size() < sizeof(Chdr32)) {
+  // New-style header
+  if (rawData.size() < sizeof(typename ELFT::Chdr)) {
     error(toString(this) + ": corrupted compressed section");
     return;
   }
 
-  auto *hdr = reinterpret_cast<const Chdr32 *>(rawData.data());
+  auto *hdr = reinterpret_cast<const typename ELFT::Chdr *>(rawData.data());
   if (hdr->ch_type != ELFCOMPRESS_ZLIB) {
     error(toString(this) + ": unsupported compression type");
     return;
diff --git a/contrib/llvm-project/lld/ELF/InputSection.h b/contrib/llvm-project/lld/ELF/InputSection.h
index 5b91c1c90bd2..c914d0b42155 100644
--- a/contrib/llvm-project/lld/ELF/InputSection.h
+++ b/contrib/llvm-project/lld/ELF/InputSection.h
@@ -238,6 +238,7 @@ public:
   }
 
 protected:
+  template <typename ELFT>
   void parseCompressedHeader();
   void uncompress() const;