//===-- WindowsResource.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
//
//===---------------------------------------------------------------------===//
//
// This file declares the .res file class.  .res files are intermediate
// products of the typical resource-compilation process on Windows.  This
// process is as follows:
//
// .rc file(s) ---(rc.exe)---> .res file(s) ---(cvtres.exe)---> COFF file
//
// .rc files are human-readable scripts that list all resources a program uses.
//
// They are compiled into .res files, which are a list of the resources in
// binary form.
//
// Finally the data stored in the .res is compiled into a COFF file, where it
// is organized in a directory tree structure for optimized access by the
// program during runtime.
//
// Ref: msdn.microsoft.com/en-us/library/windows/desktop/ms648007(v=vs.85).aspx
//
//===---------------------------------------------------------------------===//

#ifndef LLVM_OBJECT_WINDOWSRESOURCE_H
#define LLVM_OBJECT_WINDOWSRESOURCE_H

#include "llvm/ADT/ArrayRef.h"
#include "llvm/BinaryFormat/COFF.h"
#include "llvm/Object/Binary.h"
#include "llvm/Object/COFF.h"
#include "llvm/Object/Error.h"
#include "llvm/Support/BinaryByteStream.h"
#include "llvm/Support/BinaryStreamReader.h"
#include "llvm/Support/ConvertUTF.h"
#include "llvm/Support/Endian.h"
#include "llvm/Support/Error.h"

#include <map>

namespace llvm {

class raw_ostream;
class ScopedPrinter;

namespace object {

class WindowsResource;
class ResourceSectionRef;

const size_t WIN_RES_MAGIC_SIZE = 16;
const size_t WIN_RES_NULL_ENTRY_SIZE = 16;
const uint32_t WIN_RES_HEADER_ALIGNMENT = 4;
const uint32_t WIN_RES_DATA_ALIGNMENT = 4;
const uint16_t WIN_RES_PURE_MOVEABLE = 0x0030;

struct WinResHeaderPrefix {
  support::ulittle32_t DataSize;
  support::ulittle32_t HeaderSize;
};

// Type and Name may each either be an integer ID or a string.  This struct is
// only used in the case where they are both IDs.
struct WinResIDs {
  uint16_t TypeFlag;
  support::ulittle16_t TypeID;
  uint16_t NameFlag;
  support::ulittle16_t NameID;

  void setType(uint16_t ID) {
    TypeFlag = 0xffff;
    TypeID = ID;
  }

  void setName(uint16_t ID) {
    NameFlag = 0xffff;
    NameID = ID;
  }
};

struct WinResHeaderSuffix {
  support::ulittle32_t DataVersion;
  support::ulittle16_t MemoryFlags;
  support::ulittle16_t Language;
  support::ulittle32_t Version;
  support::ulittle32_t Characteristics;
};

class EmptyResError : public GenericBinaryError {
public:
  EmptyResError(Twine Msg, object_error ECOverride)
      : GenericBinaryError(Msg, ECOverride) {}
};

class ResourceEntryRef {
public:
  Error moveNext(bool &End);
  bool checkTypeString() const { return IsStringType; }
  ArrayRef<UTF16> getTypeString() const { return Type; }
  uint16_t getTypeID() const { return TypeID; }
  bool checkNameString() const { return IsStringName; }
  ArrayRef<UTF16> getNameString() const { return Name; }
  uint16_t getNameID() const { return NameID; }
  uint16_t getDataVersion() const { return Suffix->DataVersion; }
  uint16_t getLanguage() const { return Suffix->Language; }
  uint16_t getMemoryFlags() const { return Suffix->MemoryFlags; }
  uint16_t getMajorVersion() const { return Suffix->Version >> 16; }
  uint16_t getMinorVersion() const { return Suffix->Version; }
  uint32_t getCharacteristics() const { return Suffix->Characteristics; }
  ArrayRef<uint8_t> getData() const { return Data; }

private:
  friend class WindowsResource;

  ResourceEntryRef(BinaryStreamRef Ref, const WindowsResource *Owner);
  Error loadNext();

  static Expected<ResourceEntryRef> create(BinaryStreamRef Ref,
                                           const WindowsResource *Owner);

  BinaryStreamReader Reader;
  const WindowsResource *Owner;
  bool IsStringType;
  ArrayRef<UTF16> Type;
  uint16_t TypeID;
  bool IsStringName;
  ArrayRef<UTF16> Name;
  uint16_t NameID;
  const WinResHeaderSuffix *Suffix = nullptr;
  ArrayRef<uint8_t> Data;
};

class WindowsResource : public Binary {
public:
  Expected<ResourceEntryRef> getHeadEntry();

  static bool classof(const Binary *V) { return V->isWinRes(); }

  static Expected<std::unique_ptr<WindowsResource>>
  createWindowsResource(MemoryBufferRef Source);

private:
  friend class ResourceEntryRef;

  WindowsResource(MemoryBufferRef Source);

  BinaryByteStream BBS;
};

class WindowsResourceParser {
public:
  class TreeNode;
  WindowsResourceParser(bool MinGW = false);
  Error parse(WindowsResource *WR, std::vector<std::string> &Duplicates);
  Error parse(ResourceSectionRef &RSR, StringRef Filename,
              std::vector<std::string> &Duplicates);
  void cleanUpManifests(std::vector<std::string> &Duplicates);
  void printTree(raw_ostream &OS) const;
  const TreeNode &getTree() const { return Root; }
  ArrayRef<std::vector<uint8_t>> getData() const { return Data; }
  ArrayRef<std::vector<UTF16>> getStringTable() const { return StringTable; }

  class TreeNode {
  public:
    template <typename T>
    using Children = std::map<T, std::unique_ptr<TreeNode>>;

    void print(ScopedPrinter &Writer, StringRef Name) const;
    uint32_t getTreeSize() const;
    uint32_t getStringIndex() const { return StringIndex; }
    uint32_t getDataIndex() const { return DataIndex; }
    uint16_t getMajorVersion() const { return MajorVersion; }
    uint16_t getMinorVersion() const { return MinorVersion; }
    uint32_t getCharacteristics() const { return Characteristics; }
    bool checkIsDataNode() const { return IsDataNode; }
    const Children<uint32_t> &getIDChildren() const { return IDChildren; }
    const Children<std::string> &getStringChildren() const {
      return StringChildren;
    }

  private:
    friend class WindowsResourceParser;

    // Index is the StringTable vector index for this node's name.
    static std::unique_ptr<TreeNode> createStringNode(uint32_t Index);
    static std::unique_ptr<TreeNode> createIDNode();
    // DataIndex is the Data vector index that the data node points at.
    static std::unique_ptr<TreeNode> createDataNode(uint16_t MajorVersion,
                                                    uint16_t MinorVersion,
                                                    uint32_t Characteristics,
                                                    uint32_t Origin,
                                                    uint32_t DataIndex);

    explicit TreeNode(uint32_t StringIndex);
    TreeNode(uint16_t MajorVersion, uint16_t MinorVersion,
             uint32_t Characteristics, uint32_t Origin, uint32_t DataIndex);

    bool addEntry(const ResourceEntryRef &Entry, uint32_t Origin,
                  std::vector<std::vector<uint8_t>> &Data,
                  std::vector<std::vector<UTF16>> &StringTable,
                  TreeNode *&Result);
    TreeNode &addTypeNode(const ResourceEntryRef &Entry,
                          std::vector<std::vector<UTF16>> &StringTable);
    TreeNode &addNameNode(const ResourceEntryRef &Entry,
                          std::vector<std::vector<UTF16>> &StringTable);
    bool addLanguageNode(const ResourceEntryRef &Entry, uint32_t Origin,
                         std::vector<std::vector<uint8_t>> &Data,
                         TreeNode *&Result);
    bool addDataChild(uint32_t ID, uint16_t MajorVersion, uint16_t MinorVersion,
                      uint32_t Characteristics, uint32_t Origin,
                      uint32_t DataIndex, TreeNode *&Result);
    TreeNode &addIDChild(uint32_t ID);
    TreeNode &addNameChild(ArrayRef<UTF16> NameRef,
                           std::vector<std::vector<UTF16>> &StringTable);
    void shiftDataIndexDown(uint32_t Index);

    bool IsDataNode = false;
    uint32_t StringIndex;
    uint32_t DataIndex;
    Children<uint32_t> IDChildren;
    Children<std::string> StringChildren;
    uint16_t MajorVersion = 0;
    uint16_t MinorVersion = 0;
    uint32_t Characteristics = 0;

    // The .res file that defined this TreeNode, for diagnostics.
    // Index into InputFilenames.
    uint32_t Origin;
  };

  struct StringOrID {
    bool IsString;
    ArrayRef<UTF16> String;
    uint32_t ID;

    StringOrID(uint32_t ID) : IsString(false), ID(ID) {}
    StringOrID(ArrayRef<UTF16> String) : IsString(true), String(String) {}
  };

private:
  Error addChildren(TreeNode &Node, ResourceSectionRef &RSR,
                    const coff_resource_dir_table &Table, uint32_t Origin,
                    std::vector<StringOrID> &Context,
                    std::vector<std::string> &Duplicates);
  bool shouldIgnoreDuplicate(const ResourceEntryRef &Entry) const;
  bool shouldIgnoreDuplicate(const std::vector<StringOrID> &Context) const;

  TreeNode Root;
  std::vector<std::vector<uint8_t>> Data;
  std::vector<std::vector<UTF16>> StringTable;

  std::vector<std::string> InputFilenames;

  bool MinGW;
};

Expected<std::unique_ptr<MemoryBuffer>>
writeWindowsResourceCOFF(llvm::COFF::MachineTypes MachineType,
                         const WindowsResourceParser &Parser,
                         uint32_t TimeDateStamp);

void printResourceTypeName(uint16_t TypeID, raw_ostream &OS);
} // namespace object
} // namespace llvm

#endif
