//===- llvm/Bitcode/BitcodeWriter.h - Bitcode writers -----------*- 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
//
//===----------------------------------------------------------------------===//
//
// This header defines interfaces to write LLVM bitcode files/streams.
//
//===----------------------------------------------------------------------===//

#ifndef LLVM_BITCODE_BITCODEWRITER_H
#define LLVM_BITCODE_BITCODEWRITER_H

#include "llvm/ADT/StringRef.h"
#include "llvm/IR/ModuleSummaryIndex.h"
#include "llvm/MC/StringTableBuilder.h"
#include "llvm/Support/Allocator.h"
#include "llvm/Support/MemoryBuffer.h"
#include <map>
#include <memory>
#include <string>
#include <vector>

namespace llvm {

class BitstreamWriter;
class Module;
class raw_ostream;

  class BitcodeWriter {
    SmallVectorImpl<char> &Buffer;
    std::unique_ptr<BitstreamWriter> Stream;

    StringTableBuilder StrtabBuilder{StringTableBuilder::RAW};

    // Owns any strings created by the irsymtab writer until we create the
    // string table.
    BumpPtrAllocator Alloc;

    bool WroteStrtab = false, WroteSymtab = false;

    void writeBlob(unsigned Block, unsigned Record, StringRef Blob);

    std::vector<Module *> Mods;

  public:
    /// Create a BitcodeWriter that writes to Buffer.
    BitcodeWriter(SmallVectorImpl<char> &Buffer, raw_fd_stream *FS = nullptr);

    ~BitcodeWriter();

    /// Attempt to write a symbol table to the bitcode file. This must be called
    /// at most once after all modules have been written.
    ///
    /// A reader does not require a symbol table to interpret a bitcode file;
    /// the symbol table is needed only to improve link-time performance. So
    /// this function may decide not to write a symbol table. It may so decide
    /// if, for example, the target is unregistered or the IR is malformed.
    void writeSymtab();

    /// Write the bitcode file's string table. This must be called exactly once
    /// after all modules and the optional symbol table have been written.
    void writeStrtab();

    /// Copy the string table for another module into this bitcode file. This
    /// should be called after copying the module itself into the bitcode file.
    void copyStrtab(StringRef Strtab);

    /// Write the specified module to the buffer specified at construction time.
    ///
    /// If \c ShouldPreserveUseListOrder, encode the use-list order for each \a
    /// Value in \c M.  These will be reconstructed exactly when \a M is
    /// deserialized.
    ///
    /// If \c Index is supplied, the bitcode will contain the summary index
    /// (currently for use in ThinLTO optimization).
    ///
    /// \p GenerateHash enables hashing the Module and including the hash in the
    /// bitcode (currently for use in ThinLTO incremental build).
    ///
    /// If \p ModHash is non-null, when GenerateHash is true, the resulting
    /// hash is written into ModHash. When GenerateHash is false, that value
    /// is used as the hash instead of computing from the generated bitcode.
    /// Can be used to produce the same module hash for a minimized bitcode
    /// used just for the thin link as in the regular full bitcode that will
    /// be used in the backend.
    void writeModule(const Module &M, bool ShouldPreserveUseListOrder = false,
                     const ModuleSummaryIndex *Index = nullptr,
                     bool GenerateHash = false, ModuleHash *ModHash = nullptr);

    /// Write the specified thin link bitcode file (i.e., the minimized bitcode
    /// file) to the buffer specified at construction time. The thin link
    /// bitcode file is used for thin link, and it only contains the necessary
    /// information for thin link.
    ///
    /// ModHash is for use in ThinLTO incremental build, generated while the
    /// IR bitcode file writing.
    void writeThinLinkBitcode(const Module &M, const ModuleSummaryIndex &Index,
                              const ModuleHash &ModHash);

    void writeIndex(
        const ModuleSummaryIndex *Index,
        const std::map<std::string, GVSummaryMapTy> *ModuleToSummariesForIndex);
  };

  /// Write the specified module to the specified raw output stream.
  ///
  /// For streams where it matters, the given stream should be in "binary"
  /// mode.
  ///
  /// If \c ShouldPreserveUseListOrder, encode the use-list order for each \a
  /// Value in \c M.  These will be reconstructed exactly when \a M is
  /// deserialized.
  ///
  /// If \c Index is supplied, the bitcode will contain the summary index
  /// (currently for use in ThinLTO optimization).
  ///
  /// \p GenerateHash enables hashing the Module and including the hash in the
  /// bitcode (currently for use in ThinLTO incremental build).
  ///
  /// If \p ModHash is non-null, when GenerateHash is true, the resulting
  /// hash is written into ModHash. When GenerateHash is false, that value
  /// is used as the hash instead of computing from the generated bitcode.
  /// Can be used to produce the same module hash for a minimized bitcode
  /// used just for the thin link as in the regular full bitcode that will
  /// be used in the backend.
  void WriteBitcodeToFile(const Module &M, raw_ostream &Out,
                          bool ShouldPreserveUseListOrder = false,
                          const ModuleSummaryIndex *Index = nullptr,
                          bool GenerateHash = false,
                          ModuleHash *ModHash = nullptr);

  /// Write the specified thin link bitcode file (i.e., the minimized bitcode
  /// file) to the given raw output stream, where it will be written in a new
  /// bitcode block. The thin link bitcode file is used for thin link, and it
  /// only contains the necessary information for thin link.
  ///
  /// ModHash is for use in ThinLTO incremental build, generated while the IR
  /// bitcode file writing.
  void WriteThinLinkBitcodeToFile(const Module &M, raw_ostream &Out,
                                  const ModuleSummaryIndex &Index,
                                  const ModuleHash &ModHash);

  /// Write the specified module summary index to the given raw output stream,
  /// where it will be written in a new bitcode block. This is used when
  /// writing the combined index file for ThinLTO. When writing a subset of the
  /// index for a distributed backend, provide the \p ModuleToSummariesForIndex
  /// map.
  void WriteIndexToFile(const ModuleSummaryIndex &Index, raw_ostream &Out,
                        const std::map<std::string, GVSummaryMapTy>
                            *ModuleToSummariesForIndex = nullptr);

  /// If EmbedBitcode is set, save a copy of the llvm IR as data in the
  ///  __LLVM,__bitcode section (.llvmbc on non-MacOS).
  /// If available, pass the serialized module via the Buf parameter. If not,
  /// pass an empty (default-initialized) MemoryBufferRef, and the serialization
  /// will be handled by this API. The same behavior happens if the provided Buf
  /// is not bitcode (i.e. if it's invalid data or even textual LLVM assembly).
  /// If EmbedCmdline is set, the command line is also exported in
  /// the corresponding section (__LLVM,_cmdline / .llvmcmd) - even if CmdArgs
  /// were empty.
  void EmbedBitcodeInModule(Module &M, MemoryBufferRef Buf, bool EmbedBitcode,
                            bool EmbedCmdline,
                            const std::vector<uint8_t> &CmdArgs);

} // end namespace llvm

#endif // LLVM_BITCODE_BITCODEWRITER_H
