Index: test/tools/llvm-objcopy/ELF/compress-debug-sections-zlib-header.test =================================================================== --- /dev/null +++ test/tools/llvm-objcopy/ELF/compress-debug-sections-zlib-header.test @@ -0,0 +1,44 @@ +# REQUIRES: zlib + +# RUN: yaml2obj %s -o %t1.o +# RUN: llvm-objcopy --compress-debug-sections %t1.o %t2.o +# RUN: llvm-readobj -s %t2.o | FileCheck %s + +# We had a bug when llvm-objcopy did not compress normally named sections +# that had data which started from "ZLIB". Such header is used in zlib-gnu +# compression format, but the sign of using is not the header, but section name, +# first of all. The name of the compressed section should start from .z* (e.g .zdebug_info). +# If it does not start from that bytes, it is not a zlib-gnu format. + +# In this test we have 2 normal sections, one of them starts from "ZLIB", +# another starts from "ZZZZ". Check we compress both as expected. + +# CHECK: Name: .debug_foo +# CHECK-NEXT: Type: SHT_PROGBITS +# CHECK-NEXT: Flags [ +# CHECK-NEXT: SHF_COMPRESSED +# CHECK-NEXT: ] + +# CHECK: Name: .debug_bar +# CHECK-NEXT: Type: SHT_PROGBITS +# CHECK-NEXT: Flags [ +# CHECK-NEXT: SHF_COMPRESSED +# CHECK-NEXT: ] + +--- !ELF +FileHeader: + Class: ELFCLASS64 + Data: ELFDATA2LSB + Type: ET_REL + Machine: EM_X86_64 +Sections: + - Name: .debug_foo + Type: SHT_PROGBITS + AddressAlign: 0x0000000000000001 + # "ZLIB" + Content: 5A4C49420000000000000000 + - Name: .debug_bar + Type: SHT_PROGBITS + AddressAlign: 0x0000000000000001 + # "ZZZZ" + Content: 5A5A5A5A0000000000000000 Index: tools/llvm-objcopy/ELF/ELFObjcopy.cpp =================================================================== --- tools/llvm-objcopy/ELF/ELFObjcopy.cpp +++ tools/llvm-objcopy/ELF/ELFObjcopy.cpp @@ -223,18 +223,11 @@ return createStringError(object_error::parse_failed, "Section not found"); } -static bool isCompressed(const SectionBase &Section) { - const char *Magic = "ZLIB"; - return StringRef(Section.Name).startswith(".zdebug") || - (Section.OriginalData.size() > strlen(Magic) && - !strncmp(reinterpret_cast(Section.OriginalData.data()), - Magic, strlen(Magic))) || - (Section.Flags & ELF::SHF_COMPRESSED); -} - static bool isCompressable(const SectionBase &Section) { - return !isCompressed(Section) && isDebugSection(Section) && - Section.Name != ".gdb_index"; + if ((Section.Flags & ELF::SHF_COMPRESSED) || + StringRef(Section.Name).startswith(".zdebug")) + return false; + return isDebugSection(Section) && Section.Name != ".gdb_index"; } static void replaceDebugSections(