| //===- OutputSections.h -----------------------------------------*- C++ -*-===// | 
 | // | 
 | // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. | 
 | // See https://llvm.org/LICENSE.txt for license information. | 
 | // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception | 
 | // | 
 | //===----------------------------------------------------------------------===// | 
 |  | 
 | #ifndef LLD_WASM_OUTPUT_SECTIONS_H | 
 | #define LLD_WASM_OUTPUT_SECTIONS_H | 
 |  | 
 | #include "InputChunks.h" | 
 | #include "WriterUtils.h" | 
 | #include "lld/Common/ErrorHandler.h" | 
 | #include "lld/Common/LLVM.h" | 
 | #include "llvm/ADT/DenseMap.h" | 
 |  | 
 | namespace lld { | 
 |  | 
 | namespace wasm { | 
 | class OutputSection; | 
 | } | 
 | std::string toString(const wasm::OutputSection §ion); | 
 |  | 
 | namespace wasm { | 
 |  | 
 | class OutputSegment; | 
 |  | 
 | class OutputSection { | 
 | public: | 
 |   OutputSection(uint32_t type, std::string name = "") | 
 |       : type(type), name(name) {} | 
 |   virtual ~OutputSection() = default; | 
 |  | 
 |   StringRef getSectionName() const; | 
 |   void setOffset(size_t newOffset) { offset = newOffset; } | 
 |   void createHeader(size_t bodySize); | 
 |   virtual bool isNeeded() const { return true; } | 
 |   virtual size_t getSize() const = 0; | 
 |   virtual size_t getOffset() { return offset; } | 
 |   virtual void writeTo(uint8_t *buf) = 0; | 
 |   virtual void finalizeContents() = 0; | 
 |   virtual uint32_t getNumRelocations() const { return 0; } | 
 |   virtual uint32_t getNumLiveRelocations() const { return getNumRelocations(); } | 
 |   virtual void writeRelocations(raw_ostream &os) const {} | 
 |  | 
 |   std::string header; | 
 |   uint32_t type; | 
 |   uint32_t sectionIndex = UINT32_MAX; | 
 |   std::string name; | 
 |   OutputSectionSymbol *sectionSym = nullptr; | 
 |  | 
 | protected: | 
 |   size_t offset = 0; | 
 | }; | 
 |  | 
 | class CodeSection : public OutputSection { | 
 | public: | 
 |   explicit CodeSection(ArrayRef<InputFunction *> functions) | 
 |       : OutputSection(llvm::wasm::WASM_SEC_CODE), functions(functions) {} | 
 |  | 
 |   static bool classof(const OutputSection *sec) { | 
 |     return sec->type == llvm::wasm::WASM_SEC_CODE; | 
 |   } | 
 |  | 
 |   size_t getSize() const override { return header.size() + bodySize; } | 
 |   void writeTo(uint8_t *buf) override; | 
 |   uint32_t getNumRelocations() const override; | 
 |   void writeRelocations(raw_ostream &os) const override; | 
 |   bool isNeeded() const override { return functions.size() > 0; } | 
 |   void finalizeContents() override; | 
 |  | 
 |   ArrayRef<InputFunction *> functions; | 
 |  | 
 | protected: | 
 |   std::string codeSectionHeader; | 
 |   size_t bodySize = 0; | 
 | }; | 
 |  | 
 | class DataSection : public OutputSection { | 
 | public: | 
 |   explicit DataSection(ArrayRef<OutputSegment *> segments) | 
 |       : OutputSection(llvm::wasm::WASM_SEC_DATA), segments(segments) {} | 
 |  | 
 |   static bool classof(const OutputSection *sec) { | 
 |     return sec->type == llvm::wasm::WASM_SEC_DATA; | 
 |   } | 
 |  | 
 |   size_t getSize() const override { return header.size() + bodySize; } | 
 |   void writeTo(uint8_t *buf) override; | 
 |   uint32_t getNumRelocations() const override; | 
 |   void writeRelocations(raw_ostream &os) const override; | 
 |   bool isNeeded() const override; | 
 |   void finalizeContents() override; | 
 |  | 
 |   ArrayRef<OutputSegment *> segments; | 
 |  | 
 | protected: | 
 |   std::string dataSectionHeader; | 
 |   size_t bodySize = 0; | 
 | }; | 
 |  | 
 | // Represents a custom section in the output file.  Wasm custom sections are | 
 | // used for storing user-defined metadata.  Unlike the core sections types | 
 | // they are identified by their string name. | 
 | // The linker combines custom sections that have the same name by simply | 
 | // concatenating them. | 
 | // Note that some custom sections such as "name" and "linking" are handled | 
 | // separately and are instead synthesized by the linker. | 
 | class CustomSection : public OutputSection { | 
 | public: | 
 |   CustomSection(std::string name, ArrayRef<InputChunk *> inputSections) | 
 |       : OutputSection(llvm::wasm::WASM_SEC_CUSTOM, name), | 
 |         inputSections(inputSections) {} | 
 |  | 
 |   static bool classof(const OutputSection *sec) { | 
 |     return sec->type == llvm::wasm::WASM_SEC_CUSTOM; | 
 |   } | 
 |  | 
 |   size_t getSize() const override { | 
 |     return header.size() + nameData.size() + payloadSize; | 
 |   } | 
 |   void writeTo(uint8_t *buf) override; | 
 |   uint32_t getNumRelocations() const override; | 
 |   void writeRelocations(raw_ostream &os) const override; | 
 |   void finalizeContents() override; | 
 |  | 
 | protected: | 
 |   void finalizeInputSections(); | 
 |   size_t payloadSize = 0; | 
 |   std::vector<InputChunk *> inputSections; | 
 |   std::string nameData; | 
 | }; | 
 |  | 
 | } // namespace wasm | 
 | } // namespace lld | 
 |  | 
 | #endif // LLD_WASM_OUTPUT_SECTIONS_H |