From 1e7311e36d368d6deaa28012ca57d2ad051eae1e Mon Sep 17 00:00:00 2001 From: Yuta Saito Date: Tue, 15 Oct 2024 02:41:43 +0900 Subject: [PATCH 1/6] [Coverage][WebAssembly] Add initial support for WebAssembly/WASI (#111332) Currently, WebAssembly/WASI target does not provide direct support for code coverage. This patch set fixes several issues to unlock the feature. The main changes are: 1. Port `compiler-rt/lib/profile` to WebAssembly/WASI. 2. Adjust profile metadata sections for Wasm object file format. - [CodeGen] Emit `__llvm_covmap` and `__llvm_covfun` as custom sections instead of data segments. - [lld] Align the interval space of custom sections at link time. - [llvm-cov] Copy misaligned custom section data if the start address is not aligned. - [llvm-cov] Read `__llvm_prf_names` from data segments 3. [clang] Link with profile runtime libraries if requested See each commit message for more details and rationale. This is part of the effort to add code coverage support in Wasm target of Swift toolchain. --- clang/lib/Driver/ToolChains/WebAssembly.cpp | 2 + .../cmake/Modules/AllSupportedArchDefs.cmake | 2 +- compiler-rt/cmake/config-ix.cmake | 2 +- compiler-rt/lib/profile/CMakeLists.txt | 24 +++++ compiler-rt/lib/profile/GCDAProfiling.c | 2 +- .../lib/profile/InstrProfilingPlatformLinux.c | 8 +- .../lib/profile/InstrProfilingPlatformOther.c | 3 +- compiler-rt/lib/profile/InstrProfilingPort.h | 2 +- compiler-rt/lib/profile/InstrProfilingUtil.c | 12 ++- lld/test/wasm/custom-section-align.s | 31 +++++++ lld/wasm/InputChunks.h | 10 +- lld/wasm/InputFiles.cpp | 18 +++- lld/wasm/OutputSections.cpp | 1 + .../Coverage/CoverageMappingReader.h | 13 ++- .../CodeGen/TargetLoweringObjectFileImpl.cpp | 6 +- llvm/lib/MC/MCContext.cpp | 5 + .../Coverage/CoverageMappingReader.cpp | 87 +++++++++++++++--- .../Instrumentation/InstrProfiling.cpp | 5 +- llvm/test/CodeGen/WebAssembly/profile.ll | 47 ++++++++++ .../InstrProfiling/profiling.ll | 7 +- .../llvm-cov/Inputs/binary-formats.v6.wasm32 | Bin 0 -> 87781 bytes .../Inputs/binary-formats.wasm.proftext | 4 + llvm/test/tools/llvm-cov/binary-formats.c | 7 ++ 23 files changed, 253 insertions(+), 45 deletions(-) create mode 100644 lld/test/wasm/custom-section-align.s create mode 100644 llvm/test/CodeGen/WebAssembly/profile.ll create mode 100755 llvm/test/tools/llvm-cov/Inputs/binary-formats.v6.wasm32 create mode 100644 llvm/test/tools/llvm-cov/Inputs/binary-formats.wasm.proftext diff --git a/clang/lib/Driver/ToolChains/WebAssembly.cpp b/clang/lib/Driver/ToolChains/WebAssembly.cpp index 60bd97e0ee987cc..2215495bc6c56c0 100644 --- a/clang/lib/Driver/ToolChains/WebAssembly.cpp +++ b/clang/lib/Driver/ToolChains/WebAssembly.cpp @@ -155,6 +155,8 @@ void wasm::Linker::ConstructJob(Compilation &C, const JobAction &JA, AddRunTimeLibs(ToolChain, ToolChain.getDriver(), CmdArgs, Args); } + ToolChain.addProfileRTLibs(Args, CmdArgs); + CmdArgs.push_back("-o"); CmdArgs.push_back(Output.getFilename()); diff --git a/compiler-rt/cmake/Modules/AllSupportedArchDefs.cmake b/compiler-rt/cmake/Modules/AllSupportedArchDefs.cmake index 37ad48bef818a2e..3323d9aae6f7576 100644 --- a/compiler-rt/cmake/Modules/AllSupportedArchDefs.cmake +++ b/compiler-rt/cmake/Modules/AllSupportedArchDefs.cmake @@ -71,7 +71,7 @@ set(ALL_HWASAN_SUPPORTED_ARCH ${X86_64} ${ARM64} ${RISCV64}) set(ALL_MEMPROF_SUPPORTED_ARCH ${X86_64}) set(ALL_PROFILE_SUPPORTED_ARCH ${X86} ${X86_64} ${ARM32} ${ARM64} ${PPC32} ${PPC64} ${MIPS32} ${MIPS64} ${S390X} ${SPARC} ${SPARCV9} ${HEXAGON} - ${RISCV32} ${RISCV64} ${LOONGARCH64}) + ${RISCV32} ${RISCV64} ${LOONGARCH64} ${WASM32}) set(ALL_CTX_PROFILE_SUPPORTED_ARCH ${X86_64}) set(ALL_TSAN_SUPPORTED_ARCH ${X86_64} ${MIPS64} ${ARM64} ${PPC64} ${S390X} ${LOONGARCH64} ${RISCV64}) diff --git a/compiler-rt/cmake/config-ix.cmake b/compiler-rt/cmake/config-ix.cmake index dad557af2ae8c8d..2542ba6119d5f50 100644 --- a/compiler-rt/cmake/config-ix.cmake +++ b/compiler-rt/cmake/config-ix.cmake @@ -816,7 +816,7 @@ else() endif() if (PROFILE_SUPPORTED_ARCH AND NOT LLVM_USE_SANITIZER AND - OS_NAME MATCHES "Darwin|Linux|FreeBSD|Windows|Android|Fuchsia|SunOS|NetBSD|AIX") + OS_NAME MATCHES "Darwin|Linux|FreeBSD|Windows|Android|Fuchsia|SunOS|NetBSD|AIX|WASI") set(COMPILER_RT_HAS_PROFILE TRUE) else() set(COMPILER_RT_HAS_PROFILE FALSE) diff --git a/compiler-rt/lib/profile/CMakeLists.txt b/compiler-rt/lib/profile/CMakeLists.txt index 45e516489175158..f65d1cf9640206c 100644 --- a/compiler-rt/lib/profile/CMakeLists.txt +++ b/compiler-rt/lib/profile/CMakeLists.txt @@ -38,6 +38,17 @@ int main() { " COMPILER_RT_TARGET_HAS_FCNTL_LCK) +CHECK_CXX_SOURCE_COMPILES(" +#include + +int fd; +int main() { + flock(fd, LOCK_EX); + return 0; +} + +" COMPILER_RT_TARGET_HAS_FLOCK) + CHECK_CXX_SOURCE_COMPILES(" #include int main() { @@ -93,6 +104,13 @@ if(FUCHSIA OR UNIX) -Wno-pedantic) endif() +if(CMAKE_SYSTEM_NAME STREQUAL "WASI") + set(EXTRA_FLAGS + ${EXTRA_FLAGS} + -D_WASI_EMULATED_MMAN + -D_WASI_EMULATED_GETPID) +endif() + if(COMPILER_RT_TARGET_HAS_ATOMICS) set(EXTRA_FLAGS ${EXTRA_FLAGS} @@ -105,6 +123,12 @@ if(COMPILER_RT_TARGET_HAS_FCNTL_LCK) -DCOMPILER_RT_HAS_FCNTL_LCK=1) endif() +if(COMPILER_RT_TARGET_HAS_FLOCK) + set(EXTRA_FLAGS + ${EXTRA_FLAGS} + -DCOMPILER_RT_HAS_FLOCK=1) +endif() + if(COMPILER_RT_TARGET_HAS_UNAME) set(EXTRA_FLAGS ${EXTRA_FLAGS} diff --git a/compiler-rt/lib/profile/GCDAProfiling.c b/compiler-rt/lib/profile/GCDAProfiling.c index 4f46fd2839b9093..46b99b3e3f30e15 100644 --- a/compiler-rt/lib/profile/GCDAProfiling.c +++ b/compiler-rt/lib/profile/GCDAProfiling.c @@ -584,7 +584,7 @@ void llvm_reset_counters(void) { } } -#if !defined(_WIN32) +#if !defined(_WIN32) && !defined(__wasm__) COMPILER_RT_VISIBILITY pid_t __gcov_fork() { pid_t parent_pid = getpid(); diff --git a/compiler-rt/lib/profile/InstrProfilingPlatformLinux.c b/compiler-rt/lib/profile/InstrProfilingPlatformLinux.c index b766436497b741f..02f23379ce98bfe 100644 --- a/compiler-rt/lib/profile/InstrProfilingPlatformLinux.c +++ b/compiler-rt/lib/profile/InstrProfilingPlatformLinux.c @@ -6,11 +6,11 @@ |* \*===----------------------------------------------------------------------===*/ -#if defined(__linux__) || defined(__FreeBSD__) || defined(__Fuchsia__) || \ - (defined(__sun__) && defined(__svr4__)) || defined(__NetBSD__) || \ - defined(_AIX) +#if defined(__linux__) || defined(__FreeBSD__) || defined(__Fuchsia__) || \ + (defined(__sun__) && defined(__svr4__)) || defined(__NetBSD__) || \ + defined(_AIX) || defined(__wasm__) -#if !defined(_AIX) +#if !defined(_AIX) && !defined(__wasm__) #include #include #endif diff --git a/compiler-rt/lib/profile/InstrProfilingPlatformOther.c b/compiler-rt/lib/profile/InstrProfilingPlatformOther.c index aa79a5641ceca61..52e82273f8aade4 100644 --- a/compiler-rt/lib/profile/InstrProfilingPlatformOther.c +++ b/compiler-rt/lib/profile/InstrProfilingPlatformOther.c @@ -8,7 +8,8 @@ #if !defined(__APPLE__) && !defined(__linux__) && !defined(__FreeBSD__) && \ !defined(__Fuchsia__) && !(defined(__sun__) && defined(__svr4__)) && \ - !defined(__NetBSD__) && !defined(_WIN32) && !defined(_AIX) + !defined(__NetBSD__) && !defined(_WIN32) && !defined(_AIX) && \ + !defined(__wasm__) #include #include diff --git a/compiler-rt/lib/profile/InstrProfilingPort.h b/compiler-rt/lib/profile/InstrProfilingPort.h index ed0905cc5f20222..8715a3b0d2a6f00 100644 --- a/compiler-rt/lib/profile/InstrProfilingPort.h +++ b/compiler-rt/lib/profile/InstrProfilingPort.h @@ -54,7 +54,7 @@ #endif #define COMPILER_RT_MAX_HOSTLEN 128 -#ifdef __ORBIS__ +#if defined(__ORBIS__) || defined(__wasi__) #define COMPILER_RT_GETHOSTNAME(Name, Len) ((void)(Name), (void)(Len), (-1)) #else #define COMPILER_RT_GETHOSTNAME(Name, Len) lprofGetHostName(Name, Len) diff --git a/compiler-rt/lib/profile/InstrProfilingUtil.c b/compiler-rt/lib/profile/InstrProfilingUtil.c index 01093e4759a5234..1ef349fa1c82bdd 100644 --- a/compiler-rt/lib/profile/InstrProfilingUtil.c +++ b/compiler-rt/lib/profile/InstrProfilingUtil.c @@ -153,9 +153,11 @@ COMPILER_RT_VISIBILITY int lprofLockFd(int fd) { } } return 0; -#else +#elif defined(COMPILER_RT_HAS_FLOCK) flock(fd, LOCK_EX); return 0; +#else + return 0; #endif } @@ -178,9 +180,11 @@ COMPILER_RT_VISIBILITY int lprofUnlockFd(int fd) { } } return 0; -#else +#elif defined(COMPILER_RT_HAS_FLOCK) flock(fd, LOCK_UN); return 0; +#else + return 0; #endif } @@ -372,8 +376,8 @@ COMPILER_RT_VISIBILITY void lprofRestoreSigKill(void) { COMPILER_RT_VISIBILITY int lprofReleaseMemoryPagesToOS(uintptr_t Begin, uintptr_t End) { -#if defined(__ve__) - // VE doesn't support madvise. +#if defined(__ve__) || defined(__wasi__) + // VE and WASI doesn't support madvise. return 0; #else size_t PageSize = getpagesize(); diff --git a/lld/test/wasm/custom-section-align.s b/lld/test/wasm/custom-section-align.s new file mode 100644 index 000000000000000..0e46177f4cdb798 --- /dev/null +++ b/lld/test/wasm/custom-section-align.s @@ -0,0 +1,31 @@ +# RUN: llvm-mc -filetype=obj -triple=wasm32-unknown-unknown -o %t.o %s +# RUN: wasm-ld --no-entry %t.o -o %t.wasm +# RUN: obj2yaml %t.wasm | FileCheck %s + +# Check that "__llvm_covfun" custom section is aligned to 8 bytes. + + .section .custom_section.__llvm_covfun,"GR",@,__covrec_A + .int32 1 + .int8 2 +# pad .int8 0 +# .int8 0 +# .int8 0 + + .section .custom_section.__llvm_covfun,"GR",@,__covrec_B + .int32 3 + +# CHECK: - Type: CUSTOM +# CHECK-NEXT: Name: __llvm_covfun +# CHECK-NEXT: Payload: '010000000200000003000000' + +# Check that regular custom sections are not aligned. + .section .custom_section.foo,"GR",@,foo_A + .int32 1 + .int8 2 + + .section .custom_section.foo,"GR",@,foo_B + .int32 3 + +# CHECK: - Type: CUSTOM +# CHECK-NEXT: Name: foo +# CHECK-NEXT: Payload: '010000000203000000' diff --git a/lld/wasm/InputChunks.h b/lld/wasm/InputChunks.h index 5174439facc678b..efb5b66899fb5ab 100644 --- a/lld/wasm/InputChunks.h +++ b/lld/wasm/InputChunks.h @@ -177,8 +177,9 @@ class MergeInputChunk : public InputChunk { inputSectionOffset = seg.SectionOffset; } - MergeInputChunk(const WasmSection &s, ObjFile *f) - : InputChunk(f, Merge, s.Name, 0, llvm::wasm::WASM_SEG_FLAG_STRINGS) { + MergeInputChunk(const WasmSection &s, ObjFile *f, uint32_t alignment) + : InputChunk(f, Merge, s.Name, alignment, + llvm::wasm::WASM_SEG_FLAG_STRINGS) { assert(s.Type == llvm::wasm::WASM_SEC_CUSTOM); comdat = s.Comdat; rawData = s.Content; @@ -234,6 +235,7 @@ class SyntheticMergedChunk : public InputChunk { void addMergeChunk(MergeInputChunk *ms) { comdat = ms->getComdat(); + alignment = std::max(alignment, ms->alignment); ms->parent = this; chunks.push_back(ms); } @@ -337,8 +339,8 @@ class SyntheticFunction : public InputFunction { // Represents a single Wasm Section within an input file. class InputSection : public InputChunk { public: - InputSection(const WasmSection &s, ObjFile *f) - : InputChunk(f, InputChunk::Section, s.Name), + InputSection(const WasmSection &s, ObjFile *f, uint32_t alignment) + : InputChunk(f, InputChunk::Section, s.Name, alignment), tombstoneValue(getTombstoneForSection(s.Name)), section(s) { assert(section.Type == llvm::wasm::WASM_SEC_CUSTOM); comdat = section.Comdat; diff --git a/lld/wasm/InputFiles.cpp b/lld/wasm/InputFiles.cpp index f3f0ef9a994973c..ec86c2f359a35e4 100644 --- a/lld/wasm/InputFiles.cpp +++ b/lld/wasm/InputFiles.cpp @@ -18,6 +18,7 @@ #include "llvm/BinaryFormat/Wasm.h" #include "llvm/Object/Binary.h" #include "llvm/Object/Wasm.h" +#include "llvm/ProfileData/InstrProf.h" #include "llvm/Support/Path.h" #include "llvm/Support/TarWriter.h" #include "llvm/Support/raw_ostream.h" @@ -451,6 +452,18 @@ void SharedFile::parse() { } } +// Returns the alignment for a custom section. This is used to concatenate +// custom sections with the same name into a single custom section. +static uint32_t getCustomSectionAlignment(const WasmSection &sec) { + // TODO: Add a section attribute for alignment in the linking spec. + if (sec.Name == getInstrProfSectionName(IPSK_covfun, Triple::Wasm) || + sec.Name == getInstrProfSectionName(IPSK_covmap, Triple::Wasm)) { + // llvm-cov assumes that coverage metadata sections are 8-byte aligned. + return 8; + } + return 1; +} + WasmFileBase::WasmFileBase(Kind k, MemoryBufferRef m) : InputFile(k, m) { // Parse a memory buffer as a wasm file. LLVM_DEBUG(dbgs() << "Reading object: " << toString(this) << "\n"); @@ -520,10 +533,11 @@ void ObjFile::parse(bool ignoreComdats) { dataSection = §ion; } else if (section.Type == WASM_SEC_CUSTOM) { InputChunk *customSec; + uint32_t alignment = getCustomSectionAlignment(section); if (shouldMerge(section)) - customSec = make(section, this); + customSec = make(section, this, alignment); else - customSec = make(section, this); + customSec = make(section, this, alignment); customSec->discarded = isExcludedByComdat(customSec); customSections.emplace_back(customSec); customSections.back()->setRelocations(section.Relocations); diff --git a/lld/wasm/OutputSections.cpp b/lld/wasm/OutputSections.cpp index 3974146ab7270b8..62acc4cf7b381dd 100644 --- a/lld/wasm/OutputSections.cpp +++ b/lld/wasm/OutputSections.cpp @@ -249,6 +249,7 @@ void CustomSection::finalizeContents() { for (InputChunk *section : inputSections) { assert(!section->discarded); + payloadSize = alignTo(payloadSize, section->alignment); section->outSecOff = payloadSize; payloadSize += section->getSize(); } diff --git a/llvm/include/llvm/ProfileData/Coverage/CoverageMappingReader.h b/llvm/include/llvm/ProfileData/Coverage/CoverageMappingReader.h index f05b90114d75a68..886b4d3d6894dce 100644 --- a/llvm/include/llvm/ProfileData/Coverage/CoverageMappingReader.h +++ b/llvm/include/llvm/ProfileData/Coverage/CoverageMappingReader.h @@ -180,6 +180,7 @@ class BinaryCoverageReader : public CoverageMappingReader { }; using FuncRecordsStorage = std::unique_ptr; + using CoverageMapCopyStorage = std::unique_ptr; private: std::vector Filenames; @@ -195,9 +196,16 @@ class BinaryCoverageReader : public CoverageMappingReader { // D69471, which can split up function records into multiple sections on ELF. FuncRecordsStorage FuncRecords; + // Used to tie the lifetimes of an optional copy of the coverage mapping data + // to the lifetime of this BinaryCoverageReader instance. Needed to support + // Wasm object format, which might require realignment of section contents. + CoverageMapCopyStorage CoverageMapCopy; + BinaryCoverageReader(std::unique_ptr Symtab, - FuncRecordsStorage &&FuncRecords) - : ProfileNames(std::move(Symtab)), FuncRecords(std::move(FuncRecords)) {} + FuncRecordsStorage &&FuncRecords, + CoverageMapCopyStorage &&CoverageMapCopy) + : ProfileNames(std::move(Symtab)), FuncRecords(std::move(FuncRecords)), + CoverageMapCopy(std::move(CoverageMapCopy)) {} public: BinaryCoverageReader(const BinaryCoverageReader &) = delete; @@ -212,6 +220,7 @@ class BinaryCoverageReader : public CoverageMappingReader { static Expected> createCoverageReaderFromBuffer( StringRef Coverage, FuncRecordsStorage &&FuncRecords, + CoverageMapCopyStorage &&CoverageMap, std::unique_ptr ProfileNamesPtr, uint8_t BytesInAddress, llvm::endianness Endian, StringRef CompilationDir = ""); diff --git a/llvm/lib/CodeGen/TargetLoweringObjectFileImpl.cpp b/llvm/lib/CodeGen/TargetLoweringObjectFileImpl.cpp index 2a195f5249d259a..2ad4299e1419ef9 100644 --- a/llvm/lib/CodeGen/TargetLoweringObjectFileImpl.cpp +++ b/llvm/lib/CodeGen/TargetLoweringObjectFileImpl.cpp @@ -2173,7 +2173,11 @@ MCSection *TargetLoweringObjectFileWasm::getExplicitSectionGlobal( // This could be avoided if all data segements (the wasm sense) were // represented as their own sections (in the llvm sense). // TODO(sbc): https://github.com/WebAssembly/tool-conventions/issues/138 - if (Name == ".llvmcmd" || Name == ".llvmbc") + if (Name == getInstrProfSectionName(IPSK_covmap, Triple::Wasm, + /*AddSegmentInfo=*/false) || + Name == getInstrProfSectionName(IPSK_covfun, Triple::Wasm, + /*AddSegmentInfo=*/false) || + Name == ".llvmbc" || Name == ".llvmcmd") Kind = SectionKind::getMetadata(); StringRef Group = ""; diff --git a/llvm/lib/MC/MCContext.cpp b/llvm/lib/MC/MCContext.cpp index 228c4fb03a276ed..0b34ad4e814fe5d 100644 --- a/llvm/lib/MC/MCContext.cpp +++ b/llvm/lib/MC/MCContext.cpp @@ -756,6 +756,11 @@ MCSectionWasm *MCContext::getWasmSection(const Twine &Section, SectionKind K, if (!Group.isTriviallyEmpty() && !Group.str().empty()) { GroupSym = cast(getOrCreateSymbol(Group)); GroupSym->setComdat(true); + if (K.isMetadata() && !GroupSym->getType().has_value()) { + // Comdat group symbol associated with a custom section is a section + // symbol (not a data symbol). + GroupSym->setType(wasm::WASM_SYMBOL_TYPE_SECTION); + } } return getWasmSection(Section, K, Flags, GroupSym, UniqueID); diff --git a/llvm/lib/ProfileData/Coverage/CoverageMappingReader.cpp b/llvm/lib/ProfileData/Coverage/CoverageMappingReader.cpp index 445b48067a9755b..982a6f518c2f69b 100644 --- a/llvm/lib/ProfileData/Coverage/CoverageMappingReader.cpp +++ b/llvm/lib/ProfileData/Coverage/CoverageMappingReader.cpp @@ -18,12 +18,14 @@ #include "llvm/ADT/SmallVector.h" #include "llvm/ADT/Statistic.h" #include "llvm/ADT/StringRef.h" +#include "llvm/BinaryFormat/Wasm.h" #include "llvm/Object/Archive.h" #include "llvm/Object/Binary.h" #include "llvm/Object/COFF.h" #include "llvm/Object/Error.h" #include "llvm/Object/MachOUniversal.h" #include "llvm/Object/ObjectFile.h" +#include "llvm/Object/Wasm.h" #include "llvm/ProfileData/InstrProf.h" #include "llvm/Support/Casting.h" #include "llvm/Support/Compression.h" @@ -894,13 +896,15 @@ static Error readCoverageMappingData( Expected> BinaryCoverageReader::createCoverageReaderFromBuffer( StringRef Coverage, FuncRecordsStorage &&FuncRecords, + CoverageMapCopyStorage &&CoverageMap, std::unique_ptr ProfileNamesPtr, uint8_t BytesInAddress, llvm::endianness Endian, StringRef CompilationDir) { if (ProfileNamesPtr == nullptr) return make_error(coveragemap_error::malformed, "Caller must provide ProfileNames"); - std::unique_ptr Reader(new BinaryCoverageReader( - std::move(ProfileNamesPtr), std::move(FuncRecords))); + std::unique_ptr Reader( + new BinaryCoverageReader(std::move(ProfileNamesPtr), + std::move(FuncRecords), std::move(CoverageMap))); InstrProfSymtab &ProfileNames = *Reader->ProfileNames; StringRef FuncRecordsRef = Reader->FuncRecords->getBuffer(); if (BytesInAddress == 4 && Endian == llvm::endianness::little) { @@ -1035,8 +1039,8 @@ loadTestingFormat(StringRef Data, StringRef CompilationDir) { MemoryBuffer::getMemBuffer(Data); return BinaryCoverageReader::createCoverageReaderFromBuffer( - CoverageMapping, std::move(CoverageRecords), std::move(ProfileNames), - BytesInAddress, Endian, CompilationDir); + CoverageMapping, std::move(CoverageRecords), nullptr, + std::move(ProfileNames), BytesInAddress, Endian, CompilationDir); } /// Find all sections that match \p IPSK name. There may be more than one if @@ -1073,6 +1077,53 @@ lookupSections(ObjectFile &OF, InstrProfSectKind IPSK) { return Sections; } +/// Find a section that matches \p Name and is allocatable at runtime. +/// +/// Returns the contents of the section and its start offset in the object file. +static Expected> +lookupAllocatableSection(ObjectFile &OF, InstrProfSectKind IPSK) { + // On Wasm, allocatable sections can live only in data segments. + if (auto *WOF = dyn_cast(&OF)) { + std::vector Segments; + auto ObjFormat = OF.getTripleObjectFormat(); + auto Name = + getInstrProfSectionName(IPSK, ObjFormat, /*AddSegmentInfo=*/false); + for (const auto &DebugName : WOF->debugNames()) { + if (DebugName.Type != wasm::NameType::DATA_SEGMENT || + DebugName.Name != Name) + continue; + if (DebugName.Index >= WOF->dataSegments().size()) + return make_error(coveragemap_error::malformed); + auto &Segment = WOF->dataSegments()[DebugName.Index]; + Segments.push_back(&Segment); + } + if (Segments.empty()) + return make_error(coveragemap_error::no_data_found); + if (Segments.size() != 1) + return make_error(coveragemap_error::malformed); + + const auto &Segment = *Segments.front(); + auto &Data = Segment.Data; + StringRef Content(reinterpret_cast(Data.Content.data()), + Data.Content.size()); + return std::make_pair(Content, Segment.SectionOffset); + } + + // On other object file types, delegate to lookupSections to find the section. + auto Sections = lookupSections(OF, IPSK); + if (!Sections) + return Sections.takeError(); + if (Sections->size() != 1) + return make_error( + coveragemap_error::malformed, + "the size of coverage mapping section is not one"); + auto &Section = Sections->front(); + auto ContentsOrErr = Section.getContents(); + if (!ContentsOrErr) + return ContentsOrErr.takeError(); + return std::make_pair(*ContentsOrErr, Section.getAddress()); +} + static Expected> loadBinaryFormat(std::unique_ptr Bin, StringRef Arch, StringRef CompilationDir = "", @@ -1103,23 +1154,20 @@ loadBinaryFormat(std::unique_ptr Bin, StringRef Arch, // Look for the sections that we are interested in. auto ProfileNames = std::make_unique(); - std::vector NamesSectionRefs; // If IPSK_name is not found, fallback to search for IPK_covname, which is // used when binary correlation is enabled. - auto NamesSection = lookupSections(*OF, IPSK_name); + auto NamesSection = lookupAllocatableSection(*OF, IPSK_name); if (auto E = NamesSection.takeError()) { consumeError(std::move(E)); - NamesSection = lookupSections(*OF, IPSK_covname); + NamesSection = lookupAllocatableSection(*OF, IPSK_covname); if (auto E = NamesSection.takeError()) return std::move(E); } - NamesSectionRefs = *NamesSection; - if (NamesSectionRefs.size() != 1) - return make_error( - coveragemap_error::malformed, - "the size of coverage mapping section is not one"); - if (Error E = ProfileNames->create(NamesSectionRefs.back())) + uint64_t NamesAddress; + StringRef NamesContent; + std::tie(NamesContent, NamesAddress) = *NamesSection; + if (Error E = ProfileNames->create(NamesContent, NamesAddress)) return std::move(E); auto CoverageSection = lookupSections(*OF, IPSK_covmap); @@ -1134,6 +1182,15 @@ loadBinaryFormat(std::unique_ptr Bin, StringRef Arch, return CoverageMappingOrErr.takeError(); StringRef CoverageMapping = CoverageMappingOrErr.get(); + // If the coverage mapping section is not aligned to 8 bytes, copy it to a + // new buffer that is. Wasm format typically has unaligned section contents + // because it doesn't have a good way to insert padding bytes. + std::unique_ptr CoverageMapCopy; + if (!isAddrAligned(Align(8), CoverageMapping.data())) { + CoverageMapCopy = MemoryBuffer::getMemBufferCopy(CoverageMapping); + CoverageMapping = CoverageMapCopy->getBuffer(); + } + // Look for the coverage records section (Version4 only). auto CoverageRecordsSections = lookupSections(*OF, IPSK_covfun); @@ -1182,8 +1239,8 @@ loadBinaryFormat(std::unique_ptr Bin, StringRef Arch, *BinaryID = getBuildID(OF.get()); return BinaryCoverageReader::createCoverageReaderFromBuffer( - CoverageMapping, std::move(FuncRecords), std::move(ProfileNames), - BytesInAddress, Endian, CompilationDir); + CoverageMapping, std::move(FuncRecords), std::move(CoverageMapCopy), + std::move(ProfileNames), BytesInAddress, Endian, CompilationDir); } /// Determine whether \p Arch is invalid or empty, given \p Bin. diff --git a/llvm/lib/Transforms/Instrumentation/InstrProfiling.cpp b/llvm/lib/Transforms/Instrumentation/InstrProfiling.cpp index d1396071c0badec..6c8b0777ec2a1d2 100644 --- a/llvm/lib/Transforms/Instrumentation/InstrProfiling.cpp +++ b/llvm/lib/Transforms/Instrumentation/InstrProfiling.cpp @@ -1426,9 +1426,10 @@ static inline Constant *getFuncAddrForProfData(Function *Fn) { static bool needsRuntimeRegistrationOfSectionRange(const Triple &TT) { // compiler-rt uses linker support to get data/counters/name start/end for - // ELF, COFF, Mach-O and XCOFF. + // ELF, COFF, Mach-O, XCOFF, and Wasm. if (TT.isOSBinFormatELF() || TT.isOSBinFormatCOFF() || - TT.isOSBinFormatMachO() || TT.isOSBinFormatXCOFF()) + TT.isOSBinFormatMachO() || TT.isOSBinFormatXCOFF() || + TT.isOSBinFormatWasm()) return false; return true; diff --git a/llvm/test/CodeGen/WebAssembly/profile.ll b/llvm/test/CodeGen/WebAssembly/profile.ll new file mode 100644 index 000000000000000..27802cc3bf35673 --- /dev/null +++ b/llvm/test/CodeGen/WebAssembly/profile.ll @@ -0,0 +1,47 @@ +; RUN: llc < %s --filetype=obj | obj2yaml | FileCheck %s + +target triple = "wasm32-unknown-unknown" + +$__covrec_A = comdat any +$__covrec_B = comdat any + +@__covrec_A = linkonce_odr hidden constant <{ i64, i32, i64, i64, [4 x i8] }> <{ + i64 -1978722966671112904, + i32 4, + i64 0, + i64 -8102528905418564625, + [4 x i8] c"\01\01\04\11" +}>, section "__llvm_covfun", comdat, align 8 +@__covrec_B = linkonce_odr hidden constant <{ i64, i32, i64, i64, [4 x i8] }> <{ + i64 8006510647218728891, + i32 9, + i64 0, + i64 -8102528905418564625, + [4 x i8] c"\01\01\00\01" +}>, section "__llvm_covfun", comdat, align 8 +@__llvm_coverage_mapping = private constant { { i32, i32, i32, i32 }, [4 x i8] } { + { i32, i32, i32, i32 } { i32 0, i32 87, i32 0, i32 5 }, + [4 x i8] c"\01\01\00\02" +}, section "__llvm_covmap", align 8 + +; CHECK: - Type: CUSTOM +; CHECK-NEXT: Name: __llvm_covfun +; CHECK-NEXT: Payload: 3845A90EF2298AE4040000000000000000000000EF1B31BAE3088E8F01010411 +; CHECK-NEXT: - Type: CUSTOM +; CHECK-NEXT: Name: __llvm_covfun +; CHECK-NEXT: Payload: BBEFDA6903D71C6F090000000000000000000000EF1B31BAE3088E8F01010001 +; CHECK-NEXT: - Type: CUSTOM +; CHECK-NEXT: Name: __llvm_covmap +; CHECK-NEXT: Payload: '0000000057000000000000000500000001010002' +; CHECK-NEXT: - Type: CUSTOM +; CHECK-NEXT: Name: linking +; CHECK-NEXT: Version: 2 +; CHECK-NEXT: Comdats: +; CHECK-NEXT: - Name: __covrec_A +; CHECK-NEXT: Entries: +; CHECK-NEXT: - Kind: SECTION +; CHECK-NEXT: Index: 1 +; CHECK-NEXT: - Name: __covrec_B +; CHECK-NEXT: Entries: +; CHECK-NEXT: - Kind: SECTION +; CHECK-NEXT: Index: 2 diff --git a/llvm/test/Instrumentation/InstrProfiling/profiling.ll b/llvm/test/Instrumentation/InstrProfiling/profiling.ll index e7678a9dce08919..74dd54cef50fb5c 100644 --- a/llvm/test/Instrumentation/InstrProfiling/profiling.ll +++ b/llvm/test/Instrumentation/InstrProfiling/profiling.ll @@ -114,11 +114,6 @@ declare void @llvm.instrprof.increment(ptr, i64, i32, i32) ; PS: %[[REG:.*]] = load i32, ptr @__llvm_profile_runtime ; XCOFF-NOT: define .* __llvm_profile_runtime_user -; WASM: define internal void @__llvm_profile_register_functions() unnamed_addr { -; WASM-NEXT: call void @__llvm_profile_register_function(ptr @__profd_foo) -; WASM-NEXT: call void @__llvm_profile_register_function(ptr @__profd_foo_weak) -; WASM: call void @__llvm_profile_register_names_function(ptr @__llvm_prf_nm -; WASM-NEXT: ret void -; WASM-NEXT: } +; WASM-NOT: internal void @__llvm_profile_register_functions() ; XCOFF-NOT: internal void @__llvm_profile_register_functions() diff --git a/llvm/test/tools/llvm-cov/Inputs/binary-formats.v6.wasm32 b/llvm/test/tools/llvm-cov/Inputs/binary-formats.v6.wasm32 new file mode 100755 index 0000000000000000000000000000000000000000..5a606d5a2f69fd150690bd17ebb9d922cc17c383 GIT binary patch literal 87781 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 V(uIr%G*R2WW4KLte}K5~{{w2iz+3 Date: Tue, 15 Oct 2024 07:04:27 +0900 Subject: [PATCH 2/6] [lld][WebAssembly] Fix build break when building liblldWasm.so (#112275) Fix `BUILD_SHARED_LIBS=ON` build for d4efc3e097f40afbe8ae275150f49bb08fc04572 --- lld/wasm/CMakeLists.txt | 1 + 1 file changed, 1 insertion(+) diff --git a/lld/wasm/CMakeLists.txt b/lld/wasm/CMakeLists.txt index 6033bfbf9a50a30..ba89a6fee3504ed 100644 --- a/lld/wasm/CMakeLists.txt +++ b/lld/wasm/CMakeLists.txt @@ -28,6 +28,7 @@ add_lld_library(lldWasm Object Option Passes + ProfileData Support TargetParser From a1a7a17504f50681f5230690abfa941142e1c286 Mon Sep 17 00:00:00 2001 From: Yuta Saito Date: Tue, 15 Oct 2024 08:04:03 +0000 Subject: [PATCH 3/6] [compiler-rt][profile] Exclude signal.h on WASI WASI doesn't support signal, so we should exclude signal.h on WASI. This patch is only for the swiftlang fork of compiler-rt because those signal usages don't exist in the upstream. --- compiler-rt/lib/profile/InstrProfilingFile.c | 2 ++ compiler-rt/lib/profile/InstrProfilingUtil.c | 4 ++++ 2 files changed, 6 insertions(+) diff --git a/compiler-rt/lib/profile/InstrProfilingFile.c b/compiler-rt/lib/profile/InstrProfilingFile.c index 17a48c4e5c2c7f0..211e76753e96bb1 100644 --- a/compiler-rt/lib/profile/InstrProfilingFile.c +++ b/compiler-rt/lib/profile/InstrProfilingFile.c @@ -13,7 +13,9 @@ #include #include #include +#if !defined(__wasi__) #include +#endif #ifdef _MSC_VER /* For _alloca. */ #include diff --git a/compiler-rt/lib/profile/InstrProfilingUtil.c b/compiler-rt/lib/profile/InstrProfilingUtil.c index 1ef349fa1c82bdd..c0fe0021de550b5 100644 --- a/compiler-rt/lib/profile/InstrProfilingUtil.c +++ b/compiler-rt/lib/profile/InstrProfilingUtil.c @@ -25,7 +25,9 @@ #include #endif +#if !defined(__wasi__) #include +#endif #include #include @@ -336,6 +338,8 @@ COMPILER_RT_VISIBILITY void lprofInstallSignalHandler(int sig, if (err == SIG_ERR) PROF_WARN("Unable to install an exit signal handler for %d (errno = %d).\n", sig, errno); +#elif defined(__wasi__) + // WASI doesn't support signal. #else struct sigaction sigact; memset(&sigact, 0, sizeof(sigact)); From 5dbf8f37687943da0d942899f1d17bf18bdfb486 Mon Sep 17 00:00:00 2001 From: Yuta Saito Date: Wed, 16 Oct 2024 21:42:54 +0900 Subject: [PATCH 4/6] Revert "[llvm-cov][WebAssembly] Read `__llvm_prf_names` from data segments" (#112520) This reverts commit efc9dd4118a7ada7d8c898582f16db64827f7ce0 in order to fix Windows test failure: https://github.com/llvm/llvm-project/pull/111332#issuecomment-2416462512 --- .../Coverage/CoverageMappingReader.cpp | 64 +++--------------- .../llvm-cov/Inputs/binary-formats.v6.wasm32 | Bin 87781 -> 0 bytes .../Inputs/binary-formats.wasm.proftext | 4 -- llvm/test/tools/llvm-cov/binary-formats.c | 7 -- 4 files changed, 9 insertions(+), 66 deletions(-) delete mode 100755 llvm/test/tools/llvm-cov/Inputs/binary-formats.v6.wasm32 delete mode 100644 llvm/test/tools/llvm-cov/Inputs/binary-formats.wasm.proftext diff --git a/llvm/lib/ProfileData/Coverage/CoverageMappingReader.cpp b/llvm/lib/ProfileData/Coverage/CoverageMappingReader.cpp index 982a6f518c2f69b..f10ef3f877b521b 100644 --- a/llvm/lib/ProfileData/Coverage/CoverageMappingReader.cpp +++ b/llvm/lib/ProfileData/Coverage/CoverageMappingReader.cpp @@ -18,14 +18,12 @@ #include "llvm/ADT/SmallVector.h" #include "llvm/ADT/Statistic.h" #include "llvm/ADT/StringRef.h" -#include "llvm/BinaryFormat/Wasm.h" #include "llvm/Object/Archive.h" #include "llvm/Object/Binary.h" #include "llvm/Object/COFF.h" #include "llvm/Object/Error.h" #include "llvm/Object/MachOUniversal.h" #include "llvm/Object/ObjectFile.h" -#include "llvm/Object/Wasm.h" #include "llvm/ProfileData/InstrProf.h" #include "llvm/Support/Casting.h" #include "llvm/Support/Compression.h" @@ -1077,53 +1075,6 @@ lookupSections(ObjectFile &OF, InstrProfSectKind IPSK) { return Sections; } -/// Find a section that matches \p Name and is allocatable at runtime. -/// -/// Returns the contents of the section and its start offset in the object file. -static Expected> -lookupAllocatableSection(ObjectFile &OF, InstrProfSectKind IPSK) { - // On Wasm, allocatable sections can live only in data segments. - if (auto *WOF = dyn_cast(&OF)) { - std::vector Segments; - auto ObjFormat = OF.getTripleObjectFormat(); - auto Name = - getInstrProfSectionName(IPSK, ObjFormat, /*AddSegmentInfo=*/false); - for (const auto &DebugName : WOF->debugNames()) { - if (DebugName.Type != wasm::NameType::DATA_SEGMENT || - DebugName.Name != Name) - continue; - if (DebugName.Index >= WOF->dataSegments().size()) - return make_error(coveragemap_error::malformed); - auto &Segment = WOF->dataSegments()[DebugName.Index]; - Segments.push_back(&Segment); - } - if (Segments.empty()) - return make_error(coveragemap_error::no_data_found); - if (Segments.size() != 1) - return make_error(coveragemap_error::malformed); - - const auto &Segment = *Segments.front(); - auto &Data = Segment.Data; - StringRef Content(reinterpret_cast(Data.Content.data()), - Data.Content.size()); - return std::make_pair(Content, Segment.SectionOffset); - } - - // On other object file types, delegate to lookupSections to find the section. - auto Sections = lookupSections(OF, IPSK); - if (!Sections) - return Sections.takeError(); - if (Sections->size() != 1) - return make_error( - coveragemap_error::malformed, - "the size of coverage mapping section is not one"); - auto &Section = Sections->front(); - auto ContentsOrErr = Section.getContents(); - if (!ContentsOrErr) - return ContentsOrErr.takeError(); - return std::make_pair(*ContentsOrErr, Section.getAddress()); -} - static Expected> loadBinaryFormat(std::unique_ptr Bin, StringRef Arch, StringRef CompilationDir = "", @@ -1154,20 +1105,23 @@ loadBinaryFormat(std::unique_ptr Bin, StringRef Arch, // Look for the sections that we are interested in. auto ProfileNames = std::make_unique(); + std::vector NamesSectionRefs; // If IPSK_name is not found, fallback to search for IPK_covname, which is // used when binary correlation is enabled. - auto NamesSection = lookupAllocatableSection(*OF, IPSK_name); + auto NamesSection = lookupSections(*OF, IPSK_name); if (auto E = NamesSection.takeError()) { consumeError(std::move(E)); - NamesSection = lookupAllocatableSection(*OF, IPSK_covname); + NamesSection = lookupSections(*OF, IPSK_covname); if (auto E = NamesSection.takeError()) return std::move(E); } + NamesSectionRefs = *NamesSection; - uint64_t NamesAddress; - StringRef NamesContent; - std::tie(NamesContent, NamesAddress) = *NamesSection; - if (Error E = ProfileNames->create(NamesContent, NamesAddress)) + if (NamesSectionRefs.size() != 1) + return make_error( + coveragemap_error::malformed, + "the size of coverage mapping section is not one"); + if (Error E = ProfileNames->create(NamesSectionRefs.back())) return std::move(E); auto CoverageSection = lookupSections(*OF, IPSK_covmap); diff --git a/llvm/test/tools/llvm-cov/Inputs/binary-formats.v6.wasm32 b/llvm/test/tools/llvm-cov/Inputs/binary-formats.v6.wasm32 deleted file mode 100755 index 5a606d5a2f69fd150690bd17ebb9d922cc17c383..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 87781 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 V(uIr%G*R2WW4KLte}K5~{{w2iz+3 Date: Tue, 22 Oct 2024 07:09:16 +0900 Subject: [PATCH 5/6] [compiler-rt][profile] Use `flock` shim on Windows even if detection fails (#112695) --- compiler-rt/lib/profile/InstrProfilingUtil.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/compiler-rt/lib/profile/InstrProfilingUtil.c b/compiler-rt/lib/profile/InstrProfilingUtil.c index c0fe0021de550b5..1c1e7b88fca8b4c 100644 --- a/compiler-rt/lib/profile/InstrProfilingUtil.c +++ b/compiler-rt/lib/profile/InstrProfilingUtil.c @@ -155,7 +155,8 @@ COMPILER_RT_VISIBILITY int lprofLockFd(int fd) { } } return 0; -#elif defined(COMPILER_RT_HAS_FLOCK) +#elif defined(COMPILER_RT_HAS_FLOCK) || defined(_WIN32) + // Windows doesn't have flock but WindowsMMap.h provides a shim flock(fd, LOCK_EX); return 0; #else @@ -182,7 +183,8 @@ COMPILER_RT_VISIBILITY int lprofUnlockFd(int fd) { } } return 0; -#elif defined(COMPILER_RT_HAS_FLOCK) +#elif defined(COMPILER_RT_HAS_FLOCK) || defined(_WIN32) + // Windows doesn't have flock but WindowsMMap.h provides a shim flock(fd, LOCK_UN); return 0; #else From 6efc1b4589985df72597b354baf1f22878b9101b Mon Sep 17 00:00:00 2001 From: Yuta Saito Date: Thu, 24 Oct 2024 12:52:50 +0900 Subject: [PATCH 6/6] Reland: [llvm-cov][WebAssembly] Read `__llvm_prf_names` from data segments (#112569) On WebAssembly, most coverage metadata contents read by llvm-cov (like `__llvm_covmap` and `__llvm_covfun`) are stored in custom sections because they are not referenced at runtime. However, `__llvm_prf_names` is referenced at runtime by the profile runtime library and is read by llvm-cov post-processing tools, so it needs to be stored in a data segment, which is allocatable at runtime and accessible by tools as long as "name" section is present in the binary. This patch changes the way llvm-cov reads `__llvm_prf_names` on WebAssembly. Instead of looking for a section, it looks for a data segment with the same name. This reverts commit 157f10ddf2d851125a85a71e530dc9d50cb032a2 and fixes PE/COFF `.lprfn$A` section handling. --- .../Coverage/CoverageMappingReader.cpp | 92 ++++++++++++++---- .../llvm-cov/Inputs/binary-formats.v6.wasm32 | Bin 0 -> 87781 bytes .../Inputs/binary-formats.wasm.proftext | 4 + llvm/test/tools/llvm-cov/binary-formats.c | 7 ++ 4 files changed, 85 insertions(+), 18 deletions(-) create mode 100755 llvm/test/tools/llvm-cov/Inputs/binary-formats.v6.wasm32 create mode 100644 llvm/test/tools/llvm-cov/Inputs/binary-formats.wasm.proftext diff --git a/llvm/lib/ProfileData/Coverage/CoverageMappingReader.cpp b/llvm/lib/ProfileData/Coverage/CoverageMappingReader.cpp index f10ef3f877b521b..5cd40e9710194e1 100644 --- a/llvm/lib/ProfileData/Coverage/CoverageMappingReader.cpp +++ b/llvm/lib/ProfileData/Coverage/CoverageMappingReader.cpp @@ -18,12 +18,14 @@ #include "llvm/ADT/SmallVector.h" #include "llvm/ADT/Statistic.h" #include "llvm/ADT/StringRef.h" +#include "llvm/BinaryFormat/Wasm.h" #include "llvm/Object/Archive.h" #include "llvm/Object/Binary.h" #include "llvm/Object/COFF.h" #include "llvm/Object/Error.h" #include "llvm/Object/MachOUniversal.h" #include "llvm/Object/ObjectFile.h" +#include "llvm/Object/Wasm.h" #include "llvm/ProfileData/InstrProf.h" #include "llvm/Support/Casting.h" #include "llvm/Support/Compression.h" @@ -492,22 +494,29 @@ Expected RawCoverageMappingDummyChecker::isDummy() { return Tag == Counter::Zero; } -Error InstrProfSymtab::create(SectionRef &Section) { - Expected DataOrErr = Section.getContents(); - if (!DataOrErr) - return DataOrErr.takeError(); - Data = *DataOrErr; - Address = Section.getAddress(); - +/// Determine if we should skip the first byte of the section content +static bool shouldSkipSectionFirstByte(SectionRef &Section) { + const ObjectFile *Obj = Section.getObject(); // If this is a linked PE/COFF file, then we have to skip over the null byte // that is allocated in the .lprfn$A section in the LLVM profiling runtime. // If the name section is .lprfcovnames, it doesn't have the null byte at the // beginning. - const ObjectFile *Obj = Section.getObject(); if (isa(Obj) && !Obj->isRelocatableObject()) if (Expected NameOrErr = Section.getName()) if (*NameOrErr != getInstrProfSectionName(IPSK_covname, Triple::COFF)) - Data = Data.drop_front(1); + return true; + return false; +} + +Error InstrProfSymtab::create(SectionRef &Section) { + Expected DataOrErr = Section.getContents(); + if (!DataOrErr) + return DataOrErr.takeError(); + Data = *DataOrErr; + Address = Section.getAddress(); + + if (shouldSkipSectionFirstByte(Section)) + Data = Data.substr(1); return Error::success(); } @@ -1075,6 +1084,56 @@ lookupSections(ObjectFile &OF, InstrProfSectKind IPSK) { return Sections; } +/// Find a section that matches \p Name and is allocatable at runtime. +/// +/// Returns the contents of the section and its start offset in the object file. +static Expected> +lookupAllocatableSection(ObjectFile &OF, InstrProfSectKind IPSK) { + // On Wasm, allocatable sections can live only in data segments. + if (auto *WOF = dyn_cast(&OF)) { + std::vector Segments; + auto ObjFormat = OF.getTripleObjectFormat(); + auto Name = + getInstrProfSectionName(IPSK, ObjFormat, /*AddSegmentInfo=*/false); + for (const auto &DebugName : WOF->debugNames()) { + if (DebugName.Type != wasm::NameType::DATA_SEGMENT || + DebugName.Name != Name) + continue; + if (DebugName.Index >= WOF->dataSegments().size()) + return make_error(coveragemap_error::malformed); + auto &Segment = WOF->dataSegments()[DebugName.Index]; + Segments.push_back(&Segment); + } + if (Segments.empty()) + return make_error(coveragemap_error::no_data_found); + if (Segments.size() != 1) + return make_error(coveragemap_error::malformed); + + const auto &Segment = *Segments.front(); + auto &Data = Segment.Data; + StringRef Content(reinterpret_cast(Data.Content.data()), + Data.Content.size()); + return std::make_pair(Content, Segment.SectionOffset); + } + + // On other object file types, delegate to lookupSections to find the section. + auto Sections = lookupSections(OF, IPSK); + if (!Sections) + return Sections.takeError(); + if (Sections->size() != 1) + return make_error( + coveragemap_error::malformed, + "the size of coverage mapping section is not one"); + auto &Section = Sections->front(); + auto ContentsOrErr = Section.getContents(); + if (!ContentsOrErr) + return ContentsOrErr.takeError(); + auto Content = *ContentsOrErr; + if (shouldSkipSectionFirstByte(Section)) + Content = Content.drop_front(1); + return std::make_pair(Content, Section.getAddress()); +} + static Expected> loadBinaryFormat(std::unique_ptr Bin, StringRef Arch, StringRef CompilationDir = "", @@ -1105,23 +1164,20 @@ loadBinaryFormat(std::unique_ptr Bin, StringRef Arch, // Look for the sections that we are interested in. auto ProfileNames = std::make_unique(); - std::vector NamesSectionRefs; // If IPSK_name is not found, fallback to search for IPK_covname, which is // used when binary correlation is enabled. - auto NamesSection = lookupSections(*OF, IPSK_name); + auto NamesSection = lookupAllocatableSection(*OF, IPSK_name); if (auto E = NamesSection.takeError()) { consumeError(std::move(E)); - NamesSection = lookupSections(*OF, IPSK_covname); + NamesSection = lookupAllocatableSection(*OF, IPSK_covname); if (auto E = NamesSection.takeError()) return std::move(E); } - NamesSectionRefs = *NamesSection; - if (NamesSectionRefs.size() != 1) - return make_error( - coveragemap_error::malformed, - "the size of coverage mapping section is not one"); - if (Error E = ProfileNames->create(NamesSectionRefs.back())) + uint64_t NamesAddress; + StringRef NamesContent; + std::tie(NamesContent, NamesAddress) = *NamesSection; + if (Error E = ProfileNames->create(NamesContent, NamesAddress)) return std::move(E); auto CoverageSection = lookupSections(*OF, IPSK_covmap); diff --git a/llvm/test/tools/llvm-cov/Inputs/binary-formats.v6.wasm32 b/llvm/test/tools/llvm-cov/Inputs/binary-formats.v6.wasm32 new file mode 100755 index 0000000000000000000000000000000000000000..5a606d5a2f69fd150690bd17ebb9d922cc17c383 GIT binary patch literal 87781 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 V(uIr%G*R2WW4KLte}K5~{{w2iz+3