llvm.org GIT mirror llvm / b618c82
Revert "Revert "Revert "Revert "Switch external cvtres.exe for llvm's own resource library."""" This reverts commit 147f45ff24456aea59575fa4ac16c8fa554df46a. Revert "Revert "Revert "Revert "Replace trivial use of external rc.exe by writing our own .res file."""" This reverts commit 61a90a67ed54a1f0dfeab457b65abffa129569e4. The patches were intially reverted because they were causing a failure on CrWinClangLLD. Unfortunately, this was done haphazardly and didn't compile, so the revert was reverted again quickly to fix this. One that was done, the revert of the revert was itself reverted. This allowed me to finally fix the actual bug in r307452. This patch re-enables the code path that had originally been causing the bug, now that it (should) be fixed. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@307460 91177308-0d34-0410-b5e6-96231b3b80d8 Eric Beckmann 2 years ago
6 changed file(s) with 60 addition(s) and 31 deletion(s). Raw diff Collapse all Expand all
4343 static const char ClGlObjMagic[] = {
4444 '\x38', '\xfe', '\xb3', '\x0c', '\xa5', '\xd9', '\xab', '\x4d',
4545 '\xac', '\x9b', '\xd6', '\xb6', '\x22', '\x26', '\x53', '\xc2',
46 };
47
48 // The signature bytes that start a .res file.
49 static const char WinResMagic[] = {
50 '\x00', '\x00', '\x00', '\x00', '\x20', '\x00', '\x00', '\x00',
51 '\xff', '\xff', '\x00', '\x00', '\xff', '\xff', '\x00', '\x00',
4652 };
4753
4854 // Sizes in bytes of various things in the COFF format.
4242 #include
4343
4444 namespace llvm {
45
4645 namespace object {
4746
4847 class WindowsResource;
4948
50 enum class Machine { UNKNOWN, ARM, X64, X86 };
49 const size_t WIN_RES_MAGIC_SIZE = 16;
50 const size_t WIN_RES_NULL_ENTRY_SIZE = 16;
51 const uint32_t WIN_RES_HEADER_ALIGNMENT = 4;
52 const uint32_t WIN_RES_DATA_ALIGNMENT = 4;
53 const uint16_t WIN_RES_PURE_MOVEABLE = 0x0030;
54
55 struct WinResHeaderPrefix {
56 support::ulittle32_t DataSize;
57 support::ulittle32_t HeaderSize;
58 };
59
60 // Type and Name may each either be an integer ID or a string. This struct is
61 // only used in the case where they are both IDs.
62 struct WinResIDs {
63 uint16_t TypeFlag;
64 support::ulittle16_t TypeID;
65 uint16_t NameFlag;
66 support::ulittle16_t NameID;
67
68 void setType(uint16_t ID) {
69 TypeFlag = 0xffff;
70 TypeID = ID;
71 }
72
73 void setName(uint16_t ID) {
74 NameFlag = 0xffff;
75 NameID = ID;
76 }
77 };
78
79 struct WinResHeaderSuffix {
80 support::ulittle32_t DataVersion;
81 support::ulittle16_t MemoryFlags;
82 support::ulittle16_t Language;
83 support::ulittle32_t Version;
84 support::ulittle32_t Characteristics;
85 };
5186
5287 class ResourceEntryRef {
5388 public:
72107
73108 Error loadNext();
74109
75 struct HeaderSuffix {
76 support::ulittle32_t DataVersion;
77 support::ulittle16_t MemoryFlags;
78 support::ulittle16_t Language;
79 support::ulittle32_t Version;
80 support::ulittle32_t Characteristics;
81 };
82
83110 BinaryStreamReader Reader;
84111 bool IsStringType;
85112 ArrayRef Type;
87114 bool IsStringName;
88115 ArrayRef Name;
89116 uint16_t NameID;
90 const HeaderSuffix *Suffix = nullptr;
117 const WinResHeaderSuffix *Suffix = nullptr;
91118 ArrayRef Data;
92119 const WindowsResource *OwningRes = nullptr;
93120 };
5050 return file_magic::coff_import_library;
5151 }
5252 // Windows resource file
53 if (startswith(Magic, "\0\0\0\0\x20\0\0\0\xFF"))
53 if (Magic.size() >= sizeof(COFF::WinResMagic) &&
54 memcmp(Magic.data(), COFF::WinResMagic, sizeof(COFF::WinResMagic)) == 0)
5455 return file_magic::windows_resource;
5556 // 0x0000 = COFF unknown machine type
5657 if (Magic[1] == 0)
3535 // 8-byte because it makes everyone happy.
3636 const uint32_t SECTION_ALIGNMENT = sizeof(uint64_t);
3737
38 static const size_t ResourceMagicSize = 16;
39
40 static const size_t NullEntrySize = 16;
41
4238 uint32_t WindowsResourceParser::TreeNode::StringCount = 0;
4339 uint32_t WindowsResourceParser::TreeNode::DataCount = 0;
4440
4541 WindowsResource::WindowsResource(MemoryBufferRef Source)
4642 : Binary(Binary::ID_WinRes, Source) {
47 size_t LeadingSize = ResourceMagicSize + NullEntrySize;
43 size_t LeadingSize = WIN_RES_MAGIC_SIZE + WIN_RES_NULL_ENTRY_SIZE;
4844 BBS = BinaryByteStream(Data.getBuffer().drop_front(LeadingSize),
4945 support::little);
5046 }
5147
5248 Expected>
5349 WindowsResource::createWindowsResource(MemoryBufferRef Source) {
54 if (Source.getBufferSize() < ResourceMagicSize + NullEntrySize)
50 if (Source.getBufferSize() < WIN_RES_MAGIC_SIZE + WIN_RES_NULL_ENTRY_SIZE)
5551 return make_error(
5652 "File too small to be a resource file",
5753 object_error::invalid_file_type);
104100 }
105101
106102 Error ResourceEntryRef::loadNext() {
107 uint32_t DataSize;
108 RETURN_IF_ERROR(Reader.readInteger(DataSize));
109 uint32_t HeaderSize;
110 RETURN_IF_ERROR(Reader.readInteger(HeaderSize));
111
112 if (HeaderSize < MIN_HEADER_SIZE)
103 const WinResHeaderPrefix *Prefix;
104 RETURN_IF_ERROR(Reader.readObject(Prefix));
105
106 if (Prefix->HeaderSize < MIN_HEADER_SIZE)
113107 return make_error("Header size is too small.",
114108 object_error::parse_failed);
115109
117111
118112 RETURN_IF_ERROR(readStringOrId(Reader, NameID, Name, IsStringName));
119113
120 RETURN_IF_ERROR(Reader.padToAlignment(sizeof(uint32_t)));
114 RETURN_IF_ERROR(Reader.padToAlignment(WIN_RES_HEADER_ALIGNMENT));
121115
122116 RETURN_IF_ERROR(Reader.readObject(Suffix));
123117
124 RETURN_IF_ERROR(Reader.readArray(Data, DataSize));
125
126 RETURN_IF_ERROR(Reader.padToAlignment(sizeof(uint32_t)));
118 RETURN_IF_ERROR(Reader.readArray(Data, Prefix->DataSize));
119
120 RETURN_IF_ERROR(Reader.padToAlignment(WIN_RES_DATA_ALIGNMENT));
127121
128122 return Error::success();
129123 }
349343 : MachineType(MachineType), Resources(Parser.getTree()),
350344 Data(Parser.getData()), StringTable(Parser.getStringTable()) {
351345 performFileLayout();
346
352347 OutputBuffer = MemoryBuffer::getNewMemBuffer(FileSize);
353348 }
354349
466461 SectionOneHeader->PointerToLinenumbers = 0;
467462 SectionOneHeader->NumberOfRelocations = Data.size();
468463 SectionOneHeader->NumberOfLinenumbers = 0;
469 SectionOneHeader->Characteristics = COFF::IMAGE_SCN_ALIGN_1BYTES;
470 SectionOneHeader->Characteristics += COFF::IMAGE_SCN_CNT_INITIALIZED_DATA;
471464 SectionOneHeader->Characteristics += COFF::IMAGE_SCN_CNT_INITIALIZED_DATA;
472465 SectionOneHeader->Characteristics += COFF::IMAGE_SCN_MEM_READ;
473466 }
206206 std::copy(OutputBuffer->getBufferStart(), OutputBuffer->getBufferEnd(),
207207 FileBuffer->getBufferStart());
208208 error(FileBuffer->commit());
209
209210 if (Verbose) {
210211 Expected> BinaryOrErr = createBinary(OutputFile);
211212 if (!BinaryOrErr)
7575 "\xfe\xed\xfa\xce........\x00\x00\x00\x0a............";
7676 const char macho_kext_bundle[] =
7777 "\xfe\xed\xfa\xce........\x00\x00\x00\x0b............";
78 const char windows_resource[] = "\x00\x00\x00\x00\x020\x00\x00\x00\xff";
78 const char windows_resource[] =
79 "\x00\x00\x00\x00\x020\x00\x00\x00\xff\xff\x00\x00\xff\xff\x00\x00";
7980 const char macho_dynamically_linked_shared_lib_stub[] =
8081 "\xfe\xed\xfa\xce........\x00\x00\x00\x09............";
8182