LLVM  10.0.0svn
WindowsResource.h
Go to the documentation of this file.
1 //===-- WindowsResource.h ---------------------------------------*- C++-*-===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===---------------------------------------------------------------------===//
8 //
9 // This file declares the .res file class. .res files are intermediate
10 // products of the typical resource-compilation process on Windows. This
11 // process is as follows:
12 //
13 // .rc file(s) ---(rc.exe)---> .res file(s) ---(cvtres.exe)---> COFF file
14 //
15 // .rc files are human-readable scripts that list all resources a program uses.
16 //
17 // They are compiled into .res files, which are a list of the resources in
18 // binary form.
19 //
20 // Finally the data stored in the .res is compiled into a COFF file, where it
21 // is organized in a directory tree structure for optimized access by the
22 // program during runtime.
23 //
24 // Ref: msdn.microsoft.com/en-us/library/windows/desktop/ms648007(v=vs.85).aspx
25 //
26 //===---------------------------------------------------------------------===//
27 
28 #ifndef LLVM_INCLUDE_LLVM_OBJECT_RESFILE_H
29 #define LLVM_INCLUDE_LLVM_OBJECT_RESFILE_H
30 
31 #include "llvm/ADT/ArrayRef.h"
32 #include "llvm/BinaryFormat/COFF.h"
33 #include "llvm/Object/Binary.h"
34 #include "llvm/Object/COFF.h"
35 #include "llvm/Object/Error.h"
39 #include "llvm/Support/Endian.h"
40 #include "llvm/Support/Error.h"
41 
42 #include <map>
43 
44 namespace llvm {
45 
46 class raw_ostream;
47 class ScopedPrinter;
48 
49 namespace object {
50 
51 class WindowsResource;
52 class ResourceSectionRef;
53 
54 const size_t WIN_RES_MAGIC_SIZE = 16;
55 const size_t WIN_RES_NULL_ENTRY_SIZE = 16;
58 const uint16_t WIN_RES_PURE_MOVEABLE = 0x0030;
59 
63 };
64 
65 // Type and Name may each either be an integer ID or a string. This struct is
66 // only used in the case where they are both IDs.
67 struct WinResIDs {
68  uint16_t TypeFlag;
70  uint16_t NameFlag;
72 
73  void setType(uint16_t ID) {
74  TypeFlag = 0xffff;
75  TypeID = ID;
76  }
77 
78  void setName(uint16_t ID) {
79  NameFlag = 0xffff;
80  NameID = ID;
81  }
82 };
83 
90 };
91 
93 public:
94  EmptyResError(Twine Msg, object_error ECOverride)
95  : GenericBinaryError(Msg, ECOverride) {}
96 };
97 
99 public:
100  Error moveNext(bool &End);
101  bool checkTypeString() const { return IsStringType; }
102  ArrayRef<UTF16> getTypeString() const { return Type; }
103  uint16_t getTypeID() const { return TypeID; }
104  bool checkNameString() const { return IsStringName; }
105  ArrayRef<UTF16> getNameString() const { return Name; }
106  uint16_t getNameID() const { return NameID; }
107  uint16_t getDataVersion() const { return Suffix->DataVersion; }
108  uint16_t getLanguage() const { return Suffix->Language; }
109  uint16_t getMemoryFlags() const { return Suffix->MemoryFlags; }
110  uint16_t getMajorVersion() const { return Suffix->Version >> 16; }
111  uint16_t getMinorVersion() const { return Suffix->Version; }
112  uint32_t getCharacteristics() const { return Suffix->Characteristics; }
113  ArrayRef<uint8_t> getData() const { return Data; }
114 
115 private:
116  friend class WindowsResource;
117 
119  Error loadNext();
120 
122  const WindowsResource *Owner);
123 
124  BinaryStreamReader Reader;
125  const WindowsResource *Owner;
126  bool IsStringType;
128  uint16_t TypeID;
129  bool IsStringName;
131  uint16_t NameID;
132  const WinResHeaderSuffix *Suffix = nullptr;
134 };
135 
136 class WindowsResource : public Binary {
137 public:
138  Expected<ResourceEntryRef> getHeadEntry();
139 
140  static bool classof(const Binary *V) { return V->isWinRes(); }
141 
143  createWindowsResource(MemoryBufferRef Source);
144 
145 private:
146  friend class ResourceEntryRef;
147 
149 
150  BinaryByteStream BBS;
151 };
152 
154 public:
155  class TreeNode;
156  WindowsResourceParser(bool MinGW = false);
157  Error parse(WindowsResource *WR, std::vector<std::string> &Duplicates);
158  Error parse(ResourceSectionRef &RSR, StringRef Filename,
159  std::vector<std::string> &Duplicates);
160  void cleanUpManifests(std::vector<std::string> &Duplicates);
161  void printTree(raw_ostream &OS) const;
162  const TreeNode &getTree() const { return Root; }
163  const ArrayRef<std::vector<uint8_t>> getData() const { return Data; }
165  return StringTable;
166  }
167 
168  class TreeNode {
169  public:
170  template <typename T>
171  using Children = std::map<T, std::unique_ptr<TreeNode>>;
172 
173  void print(ScopedPrinter &Writer, StringRef Name) const;
174  uint32_t getTreeSize() const;
175  uint32_t getStringIndex() const { return StringIndex; }
176  uint32_t getDataIndex() const { return DataIndex; }
177  uint16_t getMajorVersion() const { return MajorVersion; }
178  uint16_t getMinorVersion() const { return MinorVersion; }
180  bool checkIsDataNode() const { return IsDataNode; }
181  const Children<uint32_t> &getIDChildren() const { return IDChildren; }
183  return StringChildren;
184  }
185 
186  private:
187  friend class WindowsResourceParser;
188 
189  // Index is the StringTable vector index for this node's name.
190  static std::unique_ptr<TreeNode> createStringNode(uint32_t Index);
191  static std::unique_ptr<TreeNode> createIDNode();
192  // DataIndex is the Data vector index that the data node points at.
193  static std::unique_ptr<TreeNode> createDataNode(uint16_t MajorVersion,
194  uint16_t MinorVersion,
196  uint32_t Origin,
197  uint32_t DataIndex);
198 
199  explicit TreeNode(uint32_t StringIndex);
200  TreeNode(uint16_t MajorVersion, uint16_t MinorVersion,
201  uint32_t Characteristics, uint32_t Origin, uint32_t DataIndex);
202 
203  bool addEntry(const ResourceEntryRef &Entry, uint32_t Origin,
204  std::vector<std::vector<uint8_t>> &Data,
205  std::vector<std::vector<UTF16>> &StringTable,
206  TreeNode *&Result);
207  TreeNode &addTypeNode(const ResourceEntryRef &Entry,
208  std::vector<std::vector<UTF16>> &StringTable);
209  TreeNode &addNameNode(const ResourceEntryRef &Entry,
210  std::vector<std::vector<UTF16>> &StringTable);
211  bool addLanguageNode(const ResourceEntryRef &Entry, uint32_t Origin,
212  std::vector<std::vector<uint8_t>> &Data,
213  TreeNode *&Result);
214  bool addDataChild(uint32_t ID, uint16_t MajorVersion, uint16_t MinorVersion,
216  uint32_t DataIndex, TreeNode *&Result);
217  TreeNode &addIDChild(uint32_t ID);
218  TreeNode &addNameChild(ArrayRef<UTF16> NameRef,
219  std::vector<std::vector<UTF16>> &StringTable);
220  void shiftDataIndexDown(uint32_t Index);
221 
222  bool IsDataNode = false;
223  uint32_t StringIndex;
224  uint32_t DataIndex;
225  Children<uint32_t> IDChildren;
226  Children<std::string> StringChildren;
227  uint16_t MajorVersion = 0;
228  uint16_t MinorVersion = 0;
230 
231  // The .res file that defined this TreeNode, for diagnostics.
232  // Index into InputFilenames.
233  uint32_t Origin;
234  };
235 
236  struct StringOrID {
237  bool IsString;
240 
241  StringOrID(uint32_t ID) : IsString(false), ID(ID) {}
242  StringOrID(ArrayRef<UTF16> String) : IsString(true), String(String) {}
243  };
244 
245 private:
246  Error addChildren(TreeNode &Node, ResourceSectionRef &RSR,
247  const coff_resource_dir_table &Table, uint32_t Origin,
248  std::vector<StringOrID> &Context,
249  std::vector<std::string> &Duplicates);
250  bool shouldIgnoreDuplicate(const ResourceEntryRef &Entry) const;
251  bool shouldIgnoreDuplicate(const std::vector<StringOrID> &Context) const;
252 
253  TreeNode Root;
254  std::vector<std::vector<uint8_t>> Data;
255  std::vector<std::vector<UTF16>> StringTable;
256 
257  std::vector<std::string> InputFilenames;
258 
259  bool MinGW;
260 };
261 
265  uint32_t TimeDateStamp);
266 
267 void printResourceTypeName(uint16_t TypeID, raw_ostream &OS);
268 } // namespace object
269 } // namespace llvm
270 
271 #endif
const size_t WIN_RES_NULL_ENTRY_SIZE
LLVMContext & Context
An implementation of BinaryStream which holds its entire data set in a single contiguous buffer...
This class represents lattice values for constants.
Definition: AllocatorList.h:23
amdgpu Simplify well known AMD library false FunctionCallee Value const Twine & Name
Expected< std::unique_ptr< MemoryBuffer > > writeWindowsResourceCOFF(llvm::COFF::MachineTypes MachineType, const WindowsResourceParser &Parser, uint32_t TimeDateStamp)
support::ulittle32_t HeaderSize
block Block Frequency true
support::ulittle16_t NameID
void setName(uint16_t ID)
C::iterator addEntry(C &Container, StringRef InstallName)
support::ulittle16_t TypeID
MachineTypes
Definition: COFF.h:93
Twine - A lightweight data structure for efficiently representing the concatenation of temporary valu...
Definition: Twine.h:80
std::map< T, std::unique_ptr< TreeNode > > Children
const Children< uint32_t > & getIDChildren() const
Tagged union holding either a T or a Error.
Definition: yaml2obj.h:21
static bool classof(const Binary *V)
The instances of the Type class are immutable: once they are created, they are never changed...
Definition: Type.h:45
object_error
Definition: Error.h:27
ArrayRef< uint8_t > getData() const
Type::TypeID TypeID
ArrayRef< UTF16 > getTypeString() const
static void print(raw_ostream &Out, object::Archive::Kind Kind, T Val)
const uint16_t WIN_RES_PURE_MOVEABLE
bool isWinRes() const
Definition: Binary.h:151
const ArrayRef< std::vector< UTF16 > > getStringTable() const
const uint32_t WIN_RES_HEADER_ALIGNMENT
const ArrayRef< std::vector< uint8_t > > getData() const
void setType(uint16_t ID)
BinaryStreamRef is to BinaryStream what ArrayRef is to an Array.
support::ulittle32_t DataVersion
support::ulittle16_t MemoryFlags
const size_t WIN_RES_MAGIC_SIZE
EmptyResError(Twine Msg, object_error ECOverride)
COFFYAML::WeakExternalCharacteristics Characteristics
Definition: COFFYAML.cpp:325
ArrayRef< UTF16 > getNameString() const
Generic binary error.
Definition: Error.h:65
void printResourceTypeName(uint16_t TypeID, raw_ostream &OS)
const uint32_t WIN_RES_DATA_ALIGNMENT
Lightweight error class with error context and mandatory checking.
Definition: Error.h:157
This class implements an extremely fast bulk output stream that can only output to a stream...
Definition: raw_ostream.h:45
Provides read only access to a subclass of BinaryStream.
StringRef - Represent a constant reference to a string, i.e.
Definition: StringRef.h:48
static llvm::Error parse(DataExtractor &Data, uint64_t BaseAddr, LineEntryCallback const &Callback)
Definition: LineTable.cpp:54
const TreeNode & getTree() const
support::ulittle32_t Characteristics
const Children< std::string > & getStringChildren() const