File: | tools/lld/ELF/ScriptParser.cpp |
Warning: | line 55, column 3 Potential memory leak |
Press '?' to see keyboard shortcuts
Keyboard shortcuts:
1 | //===- ScriptParser.cpp ---------------------------------------------------===// | |||
2 | // | |||
3 | // The LLVM Linker | |||
4 | // | |||
5 | // This file is distributed under the University of Illinois Open Source | |||
6 | // License. See LICENSE.TXT for details. | |||
7 | // | |||
8 | //===----------------------------------------------------------------------===// | |||
9 | // | |||
10 | // This file contains a recursive-descendent parser for linker scripts. | |||
11 | // Parsed results are stored to Config and Script global objects. | |||
12 | // | |||
13 | //===----------------------------------------------------------------------===// | |||
14 | ||||
15 | #include "ScriptParser.h" | |||
16 | #include "Config.h" | |||
17 | #include "Driver.h" | |||
18 | #include "InputSection.h" | |||
19 | #include "LinkerScript.h" | |||
20 | #include "OutputSections.h" | |||
21 | #include "ScriptLexer.h" | |||
22 | #include "Symbols.h" | |||
23 | #include "Target.h" | |||
24 | #include "lld/Common/Memory.h" | |||
25 | #include "llvm/ADT/SmallString.h" | |||
26 | #include "llvm/ADT/StringRef.h" | |||
27 | #include "llvm/ADT/StringSet.h" | |||
28 | #include "llvm/ADT/StringSwitch.h" | |||
29 | #include "llvm/BinaryFormat/ELF.h" | |||
30 | #include "llvm/Support/Casting.h" | |||
31 | #include "llvm/Support/ErrorHandling.h" | |||
32 | #include "llvm/Support/FileSystem.h" | |||
33 | #include "llvm/Support/Path.h" | |||
34 | #include <cassert> | |||
35 | #include <limits> | |||
36 | #include <vector> | |||
37 | ||||
38 | using namespace llvm; | |||
39 | using namespace llvm::ELF; | |||
40 | using namespace llvm::support::endian; | |||
41 | using namespace lld; | |||
42 | using namespace lld::elf; | |||
43 | ||||
44 | static bool isUnderSysroot(StringRef Path); | |||
45 | ||||
46 | namespace { | |||
47 | class ScriptParser final : ScriptLexer { | |||
48 | public: | |||
49 | ScriptParser(MemoryBufferRef MB) | |||
50 | : ScriptLexer(MB), | |||
51 | IsUnderSysroot(isUnderSysroot(MB.getBufferIdentifier())) {} | |||
52 | ||||
53 | void readLinkerScript(); | |||
54 | void readVersionScript(); | |||
55 | void readDynamicList(); | |||
56 | void readDefsym(StringRef Name); | |||
57 | ||||
58 | private: | |||
59 | void addFile(StringRef Path); | |||
60 | ||||
61 | void readAsNeeded(); | |||
62 | void readEntry(); | |||
63 | void readExtern(); | |||
64 | void readGroup(); | |||
65 | void readInclude(); | |||
66 | void readInput(); | |||
67 | void readMemory(); | |||
68 | void readOutput(); | |||
69 | void readOutputArch(); | |||
70 | void readOutputFormat(); | |||
71 | void readPhdrs(); | |||
72 | void readRegionAlias(); | |||
73 | void readSearchDir(); | |||
74 | void readSections(); | |||
75 | void readVersion(); | |||
76 | void readVersionScriptCommand(); | |||
77 | ||||
78 | SymbolAssignment *readAssignment(StringRef Name); | |||
79 | ByteCommand *readByteCommand(StringRef Tok); | |||
80 | uint32_t readFill(); | |||
81 | uint32_t parseFill(StringRef Tok); | |||
82 | void readSectionAddressType(OutputSection *Cmd); | |||
83 | OutputSection *readOutputSectionDescription(StringRef OutSec); | |||
84 | std::vector<StringRef> readOutputSectionPhdrs(); | |||
85 | InputSectionDescription *readInputSectionDescription(StringRef Tok); | |||
86 | StringMatcher readFilePatterns(); | |||
87 | std::vector<SectionPattern> readInputSectionsList(); | |||
88 | InputSectionDescription *readInputSectionRules(StringRef FilePattern); | |||
89 | unsigned readPhdrType(); | |||
90 | SortSectionPolicy readSortKind(); | |||
91 | SymbolAssignment *readProvideHidden(bool Provide, bool Hidden); | |||
92 | SymbolAssignment *readProvideOrAssignment(StringRef Tok); | |||
93 | void readSort(); | |||
94 | AssertCommand *readAssert(); | |||
95 | Expr readAssertExpr(); | |||
96 | Expr readConstant(); | |||
97 | Expr getPageSize(); | |||
98 | ||||
99 | uint64_t readMemoryAssignment(StringRef, StringRef, StringRef); | |||
100 | std::pair<uint32_t, uint32_t> readMemoryAttributes(); | |||
101 | ||||
102 | Expr combine(StringRef Op, Expr L, Expr R); | |||
103 | Expr readExpr(); | |||
104 | Expr readExpr1(Expr Lhs, int MinPrec); | |||
105 | StringRef readParenLiteral(); | |||
106 | Expr readPrimary(); | |||
107 | Expr readTernary(Expr Cond); | |||
108 | Expr readParenExpr(); | |||
109 | ||||
110 | // For parsing version script. | |||
111 | std::vector<SymbolVersion> readVersionExtern(); | |||
112 | void readAnonymousDeclaration(); | |||
113 | void readVersionDeclaration(StringRef VerStr); | |||
114 | ||||
115 | std::pair<std::vector<SymbolVersion>, std::vector<SymbolVersion>> | |||
116 | readSymbols(); | |||
117 | ||||
118 | // True if a script being read is in a subdirectory specified by -sysroot. | |||
119 | bool IsUnderSysroot; | |||
120 | ||||
121 | // A set to detect an INCLUDE() cycle. | |||
122 | StringSet<> Seen; | |||
123 | }; | |||
124 | } // namespace | |||
125 | ||||
126 | static StringRef unquote(StringRef S) { | |||
127 | if (S.startswith("\"")) | |||
128 | return S.substr(1, S.size() - 2); | |||
129 | return S; | |||
130 | } | |||
131 | ||||
132 | static bool isUnderSysroot(StringRef Path) { | |||
133 | if (Config->Sysroot == "") | |||
134 | return false; | |||
135 | for (; !Path.empty(); Path = sys::path::parent_path(Path)) | |||
136 | if (sys::fs::equivalent(Config->Sysroot, Path)) | |||
137 | return true; | |||
138 | return false; | |||
139 | } | |||
140 | ||||
141 | // Some operations only support one non absolute value. Move the | |||
142 | // absolute one to the right hand side for convenience. | |||
143 | static void moveAbsRight(ExprValue &A, ExprValue &B) { | |||
144 | if (A.Sec == nullptr || (A.ForceAbsolute && !B.isAbsolute())) | |||
145 | std::swap(A, B); | |||
146 | if (!B.isAbsolute()) | |||
147 | error(A.Loc + ": at least one side of the expression must be absolute"); | |||
148 | } | |||
149 | ||||
150 | static ExprValue add(ExprValue A, ExprValue B) { | |||
151 | moveAbsRight(A, B); | |||
152 | return {A.Sec, A.ForceAbsolute, A.getSectionOffset() + B.getValue(), A.Loc}; | |||
153 | } | |||
154 | ||||
155 | static ExprValue sub(ExprValue A, ExprValue B) { | |||
156 | // The distance between two symbols in sections is absolute. | |||
157 | if (!A.isAbsolute() && !B.isAbsolute()) | |||
158 | return A.getValue() - B.getValue(); | |||
159 | return {A.Sec, false, A.getSectionOffset() - B.getValue(), A.Loc}; | |||
160 | } | |||
161 | ||||
162 | static ExprValue bitAnd(ExprValue A, ExprValue B) { | |||
163 | moveAbsRight(A, B); | |||
164 | return {A.Sec, A.ForceAbsolute, | |||
165 | (A.getValue() & B.getValue()) - A.getSecAddr(), A.Loc}; | |||
166 | } | |||
167 | ||||
168 | static ExprValue bitOr(ExprValue A, ExprValue B) { | |||
169 | moveAbsRight(A, B); | |||
170 | return {A.Sec, A.ForceAbsolute, | |||
171 | (A.getValue() | B.getValue()) - A.getSecAddr(), A.Loc}; | |||
172 | } | |||
173 | ||||
174 | void ScriptParser::readDynamicList() { | |||
175 | Config->HasDynamicList = true; | |||
176 | expect("{"); | |||
177 | std::vector<SymbolVersion> Locals; | |||
178 | std::vector<SymbolVersion> Globals; | |||
179 | std::tie(Locals, Globals) = readSymbols(); | |||
180 | expect(";"); | |||
181 | ||||
182 | if (!atEOF()) { | |||
183 | setError("EOF expected, but got " + next()); | |||
184 | return; | |||
185 | } | |||
186 | if (!Locals.empty()) { | |||
187 | setError("\"local:\" scope not supported in --dynamic-list"); | |||
188 | return; | |||
189 | } | |||
190 | ||||
191 | for (SymbolVersion V : Globals) | |||
192 | Config->DynamicList.push_back(V); | |||
193 | } | |||
194 | ||||
195 | void ScriptParser::readVersionScript() { | |||
196 | readVersionScriptCommand(); | |||
197 | if (!atEOF()) | |||
198 | setError("EOF expected, but got " + next()); | |||
199 | } | |||
200 | ||||
201 | void ScriptParser::readVersionScriptCommand() { | |||
202 | if (consume("{")) { | |||
203 | readAnonymousDeclaration(); | |||
204 | return; | |||
205 | } | |||
206 | ||||
207 | while (!atEOF() && !errorCount() && peek() != "}") { | |||
208 | StringRef VerStr = next(); | |||
209 | if (VerStr == "{") { | |||
210 | setError("anonymous version definition is used in " | |||
211 | "combination with other version definitions"); | |||
212 | return; | |||
213 | } | |||
214 | expect("{"); | |||
215 | readVersionDeclaration(VerStr); | |||
216 | } | |||
217 | } | |||
218 | ||||
219 | void ScriptParser::readVersion() { | |||
220 | expect("{"); | |||
221 | readVersionScriptCommand(); | |||
222 | expect("}"); | |||
223 | } | |||
224 | ||||
225 | void ScriptParser::readLinkerScript() { | |||
226 | while (!atEOF()) { | |||
227 | StringRef Tok = next(); | |||
228 | if (Tok == ";") | |||
229 | continue; | |||
230 | ||||
231 | if (Tok == "ASSERT") { | |||
232 | Script->SectionCommands.push_back(readAssert()); | |||
233 | } else if (Tok == "ENTRY") { | |||
234 | readEntry(); | |||
235 | } else if (Tok == "EXTERN") { | |||
236 | readExtern(); | |||
237 | } else if (Tok == "GROUP") { | |||
238 | readGroup(); | |||
239 | } else if (Tok == "INCLUDE") { | |||
240 | readInclude(); | |||
241 | } else if (Tok == "INPUT") { | |||
242 | readInput(); | |||
243 | } else if (Tok == "MEMORY") { | |||
244 | readMemory(); | |||
245 | } else if (Tok == "OUTPUT") { | |||
246 | readOutput(); | |||
247 | } else if (Tok == "OUTPUT_ARCH") { | |||
248 | readOutputArch(); | |||
249 | } else if (Tok == "OUTPUT_FORMAT") { | |||
250 | readOutputFormat(); | |||
251 | } else if (Tok == "PHDRS") { | |||
252 | readPhdrs(); | |||
253 | } else if (Tok == "REGION_ALIAS") { | |||
254 | readRegionAlias(); | |||
255 | } else if (Tok == "SEARCH_DIR") { | |||
256 | readSearchDir(); | |||
257 | } else if (Tok == "SECTIONS") { | |||
258 | readSections(); | |||
259 | } else if (Tok == "VERSION") { | |||
260 | readVersion(); | |||
261 | } else if (SymbolAssignment *Cmd = readProvideOrAssignment(Tok)) { | |||
262 | Script->SectionCommands.push_back(Cmd); | |||
263 | } else { | |||
264 | setError("unknown directive: " + Tok); | |||
265 | } | |||
266 | } | |||
267 | } | |||
268 | ||||
269 | void ScriptParser::readDefsym(StringRef Name) { | |||
270 | Expr E = readExpr(); | |||
271 | if (!atEOF()) | |||
272 | setError("EOF expected, but got " + next()); | |||
273 | SymbolAssignment *Cmd = make<SymbolAssignment>(Name, E, getCurrentLocation()); | |||
274 | Script->SectionCommands.push_back(Cmd); | |||
275 | } | |||
276 | ||||
277 | void ScriptParser::addFile(StringRef S) { | |||
278 | if (IsUnderSysroot && S.startswith("/")) { | |||
279 | SmallString<128> PathData; | |||
280 | StringRef Path = (Config->Sysroot + S).toStringRef(PathData); | |||
281 | if (sys::fs::exists(Path)) { | |||
282 | Driver->addFile(Saver.save(Path), /*WithLOption=*/false); | |||
283 | return; | |||
284 | } | |||
285 | } | |||
286 | ||||
287 | if (S.startswith("/")) { | |||
288 | Driver->addFile(S, /*WithLOption=*/false); | |||
289 | } else if (S.startswith("=")) { | |||
290 | if (Config->Sysroot.empty()) | |||
291 | Driver->addFile(S.substr(1), /*WithLOption=*/false); | |||
292 | else | |||
293 | Driver->addFile(Saver.save(Config->Sysroot + "/" + S.substr(1)), | |||
294 | /*WithLOption=*/false); | |||
295 | } else if (S.startswith("-l")) { | |||
296 | Driver->addLibrary(S.substr(2)); | |||
297 | } else if (sys::fs::exists(S)) { | |||
298 | Driver->addFile(S, /*WithLOption=*/false); | |||
299 | } else { | |||
300 | if (Optional<std::string> Path = findFromSearchPaths(S)) | |||
301 | Driver->addFile(Saver.save(*Path), /*WithLOption=*/true); | |||
302 | else | |||
303 | setError("unable to find " + S); | |||
304 | } | |||
305 | } | |||
306 | ||||
307 | void ScriptParser::readAsNeeded() { | |||
308 | expect("("); | |||
309 | bool Orig = Config->AsNeeded; | |||
310 | Config->AsNeeded = true; | |||
311 | while (!errorCount() && !consume(")")) | |||
312 | addFile(unquote(next())); | |||
313 | Config->AsNeeded = Orig; | |||
314 | } | |||
315 | ||||
316 | void ScriptParser::readEntry() { | |||
317 | // -e <symbol> takes predecence over ENTRY(<symbol>). | |||
318 | expect("("); | |||
319 | StringRef Tok = next(); | |||
320 | if (Config->Entry.empty()) | |||
321 | Config->Entry = Tok; | |||
322 | expect(")"); | |||
323 | } | |||
324 | ||||
325 | void ScriptParser::readExtern() { | |||
326 | expect("("); | |||
327 | while (!errorCount() && !consume(")")) | |||
328 | Config->Undefined.push_back(next()); | |||
329 | } | |||
330 | ||||
331 | void ScriptParser::readGroup() { | |||
332 | bool Orig = InputFile::IsInGroup; | |||
333 | InputFile::IsInGroup = true; | |||
334 | readInput(); | |||
335 | InputFile::IsInGroup = Orig; | |||
336 | } | |||
337 | ||||
338 | void ScriptParser::readInclude() { | |||
339 | StringRef Tok = unquote(next()); | |||
340 | ||||
341 | if (!Seen.insert(Tok).second) { | |||
342 | setError("there is a cycle in linker script INCLUDEs"); | |||
343 | return; | |||
344 | } | |||
345 | ||||
346 | if (Optional<std::string> Path = searchLinkerScript(Tok)) { | |||
347 | if (Optional<MemoryBufferRef> MB = readFile(*Path)) | |||
348 | tokenize(*MB); | |||
349 | return; | |||
350 | } | |||
351 | setError("cannot find linker script " + Tok); | |||
352 | } | |||
353 | ||||
354 | void ScriptParser::readInput() { | |||
355 | expect("("); | |||
356 | while (!errorCount() && !consume(")")) { | |||
357 | if (consume("AS_NEEDED")) | |||
358 | readAsNeeded(); | |||
359 | else | |||
360 | addFile(unquote(next())); | |||
361 | } | |||
362 | } | |||
363 | ||||
364 | void ScriptParser::readOutput() { | |||
365 | // -o <file> takes predecence over OUTPUT(<file>). | |||
366 | expect("("); | |||
367 | StringRef Tok = next(); | |||
368 | if (Config->OutputFile.empty()) | |||
369 | Config->OutputFile = unquote(Tok); | |||
370 | expect(")"); | |||
371 | } | |||
372 | ||||
373 | void ScriptParser::readOutputArch() { | |||
374 | // OUTPUT_ARCH is ignored for now. | |||
375 | expect("("); | |||
376 | while (!errorCount() && !consume(")")) | |||
377 | skip(); | |||
378 | } | |||
379 | ||||
380 | void ScriptParser::readOutputFormat() { | |||
381 | // Error checking only for now. | |||
382 | expect("("); | |||
383 | skip(); | |||
384 | if (consume(")")) | |||
385 | return; | |||
386 | expect(","); | |||
387 | skip(); | |||
388 | expect(","); | |||
389 | skip(); | |||
390 | expect(")"); | |||
391 | } | |||
392 | ||||
393 | void ScriptParser::readPhdrs() { | |||
394 | expect("{"); | |||
395 | ||||
396 | while (!errorCount() && !consume("}")) { | |||
397 | PhdrsCommand Cmd; | |||
398 | Cmd.Name = next(); | |||
399 | Cmd.Type = readPhdrType(); | |||
400 | ||||
401 | while (!errorCount() && !consume(";")) { | |||
402 | if (consume("FILEHDR")) | |||
403 | Cmd.HasFilehdr = true; | |||
404 | else if (consume("PHDRS")) | |||
405 | Cmd.HasPhdrs = true; | |||
406 | else if (consume("AT")) | |||
407 | Cmd.LMAExpr = readParenExpr(); | |||
408 | else if (consume("FLAGS")) | |||
409 | Cmd.Flags = readParenExpr()().getValue(); | |||
410 | else | |||
411 | setError("unexpected header attribute: " + next()); | |||
412 | } | |||
413 | ||||
414 | Script->PhdrsCommands.push_back(Cmd); | |||
415 | } | |||
416 | } | |||
417 | ||||
418 | void ScriptParser::readRegionAlias() { | |||
419 | expect("("); | |||
420 | StringRef Alias = unquote(next()); | |||
421 | expect(","); | |||
422 | StringRef Name = next(); | |||
423 | expect(")"); | |||
424 | ||||
425 | if (Script->MemoryRegions.count(Alias)) | |||
426 | setError("redefinition of memory region '" + Alias + "'"); | |||
427 | if (!Script->MemoryRegions.count(Name)) | |||
428 | setError("memory region '" + Name + "' is not defined"); | |||
429 | Script->MemoryRegions.insert({Alias, Script->MemoryRegions[Name]}); | |||
430 | } | |||
431 | ||||
432 | void ScriptParser::readSearchDir() { | |||
433 | expect("("); | |||
434 | StringRef Tok = next(); | |||
435 | if (!Config->Nostdlib) | |||
436 | Config->SearchPaths.push_back(unquote(Tok)); | |||
437 | expect(")"); | |||
438 | } | |||
439 | ||||
440 | void ScriptParser::readSections() { | |||
441 | Script->HasSectionsCommand = true; | |||
442 | ||||
443 | // -no-rosegment is used to avoid placing read only non-executable sections in | |||
444 | // their own segment. We do the same if SECTIONS command is present in linker | |||
445 | // script. See comment for computeFlags(). | |||
446 | Config->SingleRoRx = true; | |||
447 | ||||
448 | expect("{"); | |||
449 | std::vector<BaseCommand *> V; | |||
450 | while (!errorCount() && !consume("}")) { | |||
451 | StringRef Tok = next(); | |||
452 | BaseCommand *Cmd = readProvideOrAssignment(Tok); | |||
453 | if (!Cmd) { | |||
454 | if (Tok == "ASSERT") | |||
455 | Cmd = readAssert(); | |||
456 | else | |||
457 | Cmd = readOutputSectionDescription(Tok); | |||
458 | } | |||
459 | V.push_back(Cmd); | |||
460 | } | |||
461 | ||||
462 | if (!atEOF() && consume("INSERT")) { | |||
463 | std::vector<BaseCommand *> *Dest = nullptr; | |||
464 | if (consume("AFTER")) | |||
465 | Dest = &Script->InsertAfterCommands[next()]; | |||
466 | else if (consume("BEFORE")) | |||
467 | Dest = &Script->InsertBeforeCommands[next()]; | |||
468 | else | |||
469 | setError("expected AFTER/BEFORE, but got '" + next() + "'"); | |||
470 | if (Dest) | |||
471 | Dest->insert(Dest->end(), V.begin(), V.end()); | |||
472 | return; | |||
473 | } | |||
474 | ||||
475 | Script->SectionCommands.insert(Script->SectionCommands.end(), V.begin(), | |||
476 | V.end()); | |||
477 | } | |||
478 | ||||
479 | static int precedence(StringRef Op) { | |||
480 | return StringSwitch<int>(Op) | |||
481 | .Cases("*", "/", "%", 6) | |||
482 | .Cases("+", "-", 5) | |||
483 | .Cases("<<", ">>", 4) | |||
484 | .Cases("<", "<=", ">", ">=", "==", "!=", 3) | |||
485 | .Case("&", 2) | |||
486 | .Case("|", 1) | |||
487 | .Default(-1); | |||
488 | } | |||
489 | ||||
490 | StringMatcher ScriptParser::readFilePatterns() { | |||
491 | std::vector<StringRef> V; | |||
492 | while (!errorCount() && !consume(")")) | |||
493 | V.push_back(next()); | |||
494 | return StringMatcher(V); | |||
495 | } | |||
496 | ||||
497 | SortSectionPolicy ScriptParser::readSortKind() { | |||
498 | if (consume("SORT") || consume("SORT_BY_NAME")) | |||
499 | return SortSectionPolicy::Name; | |||
500 | if (consume("SORT_BY_ALIGNMENT")) | |||
501 | return SortSectionPolicy::Alignment; | |||
502 | if (consume("SORT_BY_INIT_PRIORITY")) | |||
503 | return SortSectionPolicy::Priority; | |||
504 | if (consume("SORT_NONE")) | |||
505 | return SortSectionPolicy::None; | |||
506 | return SortSectionPolicy::Default; | |||
507 | } | |||
508 | ||||
509 | // Reads SECTIONS command contents in the following form: | |||
510 | // | |||
511 | // <contents> ::= <elem>* | |||
512 | // <elem> ::= <exclude>? <glob-pattern> | |||
513 | // <exclude> ::= "EXCLUDE_FILE" "(" <glob-pattern>+ ")" | |||
514 | // | |||
515 | // For example, | |||
516 | // | |||
517 | // *(.foo EXCLUDE_FILE (a.o) .bar EXCLUDE_FILE (b.o) .baz) | |||
518 | // | |||
519 | // is parsed as ".foo", ".bar" with "a.o", and ".baz" with "b.o". | |||
520 | // The semantics of that is section .foo in any file, section .bar in | |||
521 | // any file but a.o, and section .baz in any file but b.o. | |||
522 | std::vector<SectionPattern> ScriptParser::readInputSectionsList() { | |||
523 | std::vector<SectionPattern> Ret; | |||
524 | while (!errorCount() && peek() != ")") { | |||
525 | StringMatcher ExcludeFilePat; | |||
526 | if (consume("EXCLUDE_FILE")) { | |||
527 | expect("("); | |||
528 | ExcludeFilePat = readFilePatterns(); | |||
529 | } | |||
530 | ||||
531 | std::vector<StringRef> V; | |||
532 | while (!errorCount() && peek() != ")" && peek() != "EXCLUDE_FILE") | |||
533 | V.push_back(next()); | |||
534 | ||||
535 | if (!V.empty()) | |||
536 | Ret.push_back({std::move(ExcludeFilePat), StringMatcher(V)}); | |||
537 | else | |||
538 | setError("section pattern is expected"); | |||
539 | } | |||
540 | return Ret; | |||
541 | } | |||
542 | ||||
543 | // Reads contents of "SECTIONS" directive. That directive contains a | |||
544 | // list of glob patterns for input sections. The grammar is as follows. | |||
545 | // | |||
546 | // <patterns> ::= <section-list> | |||
547 | // | <sort> "(" <section-list> ")" | |||
548 | // | <sort> "(" <sort> "(" <section-list> ")" ")" | |||
549 | // | |||
550 | // <sort> ::= "SORT" | "SORT_BY_NAME" | "SORT_BY_ALIGNMENT" | |||
551 | // | "SORT_BY_INIT_PRIORITY" | "SORT_NONE" | |||
552 | // | |||
553 | // <section-list> is parsed by readInputSectionsList(). | |||
554 | InputSectionDescription * | |||
555 | ScriptParser::readInputSectionRules(StringRef FilePattern) { | |||
556 | auto *Cmd = make<InputSectionDescription>(FilePattern); | |||
557 | expect("("); | |||
558 | ||||
559 | while (!errorCount() && !consume(")")) { | |||
560 | SortSectionPolicy Outer = readSortKind(); | |||
561 | SortSectionPolicy Inner = SortSectionPolicy::Default; | |||
562 | std::vector<SectionPattern> V; | |||
563 | if (Outer != SortSectionPolicy::Default) { | |||
564 | expect("("); | |||
565 | Inner = readSortKind(); | |||
566 | if (Inner != SortSectionPolicy::Default) { | |||
567 | expect("("); | |||
568 | V = readInputSectionsList(); | |||
569 | expect(")"); | |||
570 | } else { | |||
571 | V = readInputSectionsList(); | |||
572 | } | |||
573 | expect(")"); | |||
574 | } else { | |||
575 | V = readInputSectionsList(); | |||
576 | } | |||
577 | ||||
578 | for (SectionPattern &Pat : V) { | |||
579 | Pat.SortInner = Inner; | |||
580 | Pat.SortOuter = Outer; | |||
581 | } | |||
582 | ||||
583 | std::move(V.begin(), V.end(), std::back_inserter(Cmd->SectionPatterns)); | |||
584 | } | |||
585 | return Cmd; | |||
586 | } | |||
587 | ||||
588 | InputSectionDescription * | |||
589 | ScriptParser::readInputSectionDescription(StringRef Tok) { | |||
590 | // Input section wildcard can be surrounded by KEEP. | |||
591 | // https://sourceware.org/binutils/docs/ld/Input-Section-Keep.html#Input-Section-Keep | |||
592 | if (Tok == "KEEP") { | |||
593 | expect("("); | |||
594 | StringRef FilePattern = next(); | |||
595 | InputSectionDescription *Cmd = readInputSectionRules(FilePattern); | |||
596 | expect(")"); | |||
597 | Script->KeptSections.push_back(Cmd); | |||
598 | return Cmd; | |||
599 | } | |||
600 | return readInputSectionRules(Tok); | |||
601 | } | |||
602 | ||||
603 | void ScriptParser::readSort() { | |||
604 | expect("("); | |||
605 | expect("CONSTRUCTORS"); | |||
606 | expect(")"); | |||
607 | } | |||
608 | ||||
609 | AssertCommand *ScriptParser::readAssert() { | |||
610 | return make<AssertCommand>(readAssertExpr()); | |||
| ||||
611 | } | |||
612 | ||||
613 | Expr ScriptParser::readAssertExpr() { | |||
614 | expect("("); | |||
615 | Expr E = readExpr(); | |||
616 | expect(","); | |||
617 | StringRef Msg = unquote(next()); | |||
618 | expect(")"); | |||
619 | ||||
620 | return [=] { | |||
621 | if (!E().getValue()) | |||
622 | error(Msg); | |||
623 | return Script->getDot(); | |||
624 | }; | |||
625 | } | |||
626 | ||||
627 | // Reads a FILL(expr) command. We handle the FILL command as an | |||
628 | // alias for =fillexp section attribute, which is different from | |||
629 | // what GNU linkers do. | |||
630 | // https://sourceware.org/binutils/docs/ld/Output-Section-Data.html | |||
631 | uint32_t ScriptParser::readFill() { | |||
632 | expect("("); | |||
633 | uint32_t V = parseFill(next()); | |||
634 | expect(")"); | |||
635 | return V; | |||
636 | } | |||
637 | ||||
638 | // Reads an expression and/or the special directive for an output | |||
639 | // section definition. Directive is one of following: "(NOLOAD)", | |||
640 | // "(COPY)", "(INFO)" or "(OVERLAY)". | |||
641 | // | |||
642 | // An output section name can be followed by an address expression | |||
643 | // and/or directive. This grammar is not LL(1) because "(" can be | |||
644 | // interpreted as either the beginning of some expression or beginning | |||
645 | // of directive. | |||
646 | // | |||
647 | // https://sourceware.org/binutils/docs/ld/Output-Section-Address.html | |||
648 | // https://sourceware.org/binutils/docs/ld/Output-Section-Type.html | |||
649 | void ScriptParser::readSectionAddressType(OutputSection *Cmd) { | |||
650 | if (consume("(")) { | |||
651 | if (consume("NOLOAD")) { | |||
652 | expect(")"); | |||
653 | Cmd->Noload = true; | |||
654 | return; | |||
655 | } | |||
656 | if (consume("COPY") || consume("INFO") || consume("OVERLAY")) { | |||
657 | expect(")"); | |||
658 | Cmd->NonAlloc = true; | |||
659 | return; | |||
660 | } | |||
661 | Cmd->AddrExpr = readExpr(); | |||
662 | expect(")"); | |||
663 | } else { | |||
664 | Cmd->AddrExpr = readExpr(); | |||
665 | } | |||
666 | ||||
667 | if (consume("(")) { | |||
668 | expect("NOLOAD"); | |||
669 | expect(")"); | |||
670 | Cmd->Noload = true; | |||
671 | } | |||
672 | } | |||
673 | ||||
674 | static Expr checkAlignment(Expr E, std::string &Loc) { | |||
675 | return [=] { | |||
676 | uint64_t Alignment = std::max((uint64_t)1, E().getValue()); | |||
677 | if (!isPowerOf2_64(Alignment)) { | |||
678 | error(Loc + ": alignment must be power of 2"); | |||
679 | return (uint64_t)1; // Return a dummy value. | |||
680 | } | |||
681 | return Alignment; | |||
682 | }; | |||
683 | } | |||
684 | ||||
685 | OutputSection *ScriptParser::readOutputSectionDescription(StringRef OutSec) { | |||
686 | OutputSection *Cmd = | |||
687 | Script->createOutputSection(OutSec, getCurrentLocation()); | |||
688 | ||||
689 | size_t SymbolsReferenced = Script->ReferencedSymbols.size(); | |||
690 | ||||
691 | if (peek() != ":") | |||
692 | readSectionAddressType(Cmd); | |||
693 | expect(":"); | |||
694 | ||||
695 | std::string Location = getCurrentLocation(); | |||
696 | if (consume("AT")) | |||
697 | Cmd->LMAExpr = readParenExpr(); | |||
698 | if (consume("ALIGN")) | |||
699 | Cmd->AlignExpr = checkAlignment(readParenExpr(), Location); | |||
700 | if (consume("SUBALIGN")) | |||
701 | Cmd->SubalignExpr = checkAlignment(readParenExpr(), Location); | |||
702 | ||||
703 | // Parse constraints. | |||
704 | if (consume("ONLY_IF_RO")) | |||
705 | Cmd->Constraint = ConstraintKind::ReadOnly; | |||
706 | if (consume("ONLY_IF_RW")) | |||
707 | Cmd->Constraint = ConstraintKind::ReadWrite; | |||
708 | expect("{"); | |||
709 | ||||
710 | while (!errorCount() && !consume("}")) { | |||
711 | StringRef Tok = next(); | |||
712 | if (Tok == ";") { | |||
713 | // Empty commands are allowed. Do nothing here. | |||
714 | } else if (SymbolAssignment *Assign = readProvideOrAssignment(Tok)) { | |||
715 | Cmd->SectionCommands.push_back(Assign); | |||
716 | } else if (ByteCommand *Data = readByteCommand(Tok)) { | |||
717 | Cmd->SectionCommands.push_back(Data); | |||
718 | } else if (Tok == "ASSERT") { | |||
719 | Cmd->SectionCommands.push_back(readAssert()); | |||
720 | expect(";"); | |||
721 | } else if (Tok == "CONSTRUCTORS") { | |||
722 | // CONSTRUCTORS is a keyword to make the linker recognize C++ ctors/dtors | |||
723 | // by name. This is for very old file formats such as ECOFF/XCOFF. | |||
724 | // For ELF, we should ignore. | |||
725 | } else if (Tok == "FILL") { | |||
726 | Cmd->Filler = readFill(); | |||
727 | } else if (Tok == "SORT") { | |||
728 | readSort(); | |||
729 | } else if (peek() == "(") { | |||
730 | Cmd->SectionCommands.push_back(readInputSectionDescription(Tok)); | |||
731 | } else { | |||
732 | setError("unknown command " + Tok); | |||
733 | } | |||
734 | } | |||
735 | ||||
736 | if (consume(">")) | |||
737 | Cmd->MemoryRegionName = next(); | |||
738 | ||||
739 | if (consume("AT")) { | |||
740 | expect(">"); | |||
741 | Cmd->LMARegionName = next(); | |||
742 | } | |||
743 | ||||
744 | if (Cmd->LMAExpr && !Cmd->LMARegionName.empty()) | |||
745 | error("section can't have both LMA and a load region"); | |||
746 | ||||
747 | Cmd->Phdrs = readOutputSectionPhdrs(); | |||
748 | ||||
749 | if (consume("=")) | |||
750 | Cmd->Filler = parseFill(next()); | |||
751 | else if (peek().startswith("=")) | |||
752 | Cmd->Filler = parseFill(next().drop_front()); | |||
753 | ||||
754 | // Consume optional comma following output section command. | |||
755 | consume(","); | |||
756 | ||||
757 | if (Script->ReferencedSymbols.size() > SymbolsReferenced) | |||
758 | Cmd->ExpressionsUseSymbols = true; | |||
759 | return Cmd; | |||
760 | } | |||
761 | ||||
762 | // Parses a given string as a octal/decimal/hexadecimal number and | |||
763 | // returns it as a big-endian number. Used for `=<fillexp>`. | |||
764 | // https://sourceware.org/binutils/docs/ld/Output-Section-Fill.html | |||
765 | // | |||
766 | // When reading a hexstring, ld.bfd handles it as a blob of arbitrary | |||
767 | // size, while ld.gold always handles it as a 32-bit big-endian number. | |||
768 | // We are compatible with ld.gold because it's easier to implement. | |||
769 | uint32_t ScriptParser::parseFill(StringRef Tok) { | |||
770 | uint32_t V = 0; | |||
771 | if (!to_integer(Tok, V)) | |||
772 | setError("invalid filler expression: " + Tok); | |||
773 | ||||
774 | uint32_t Buf; | |||
775 | write32be(&Buf, V); | |||
776 | return Buf; | |||
777 | } | |||
778 | ||||
779 | SymbolAssignment *ScriptParser::readProvideHidden(bool Provide, bool Hidden) { | |||
780 | expect("("); | |||
781 | SymbolAssignment *Cmd = readAssignment(next()); | |||
782 | Cmd->Provide = Provide; | |||
783 | Cmd->Hidden = Hidden; | |||
784 | expect(")"); | |||
785 | return Cmd; | |||
786 | } | |||
787 | ||||
788 | SymbolAssignment *ScriptParser::readProvideOrAssignment(StringRef Tok) { | |||
789 | size_t OldPos = Pos; | |||
790 | SymbolAssignment *Cmd = nullptr; | |||
791 | if (peek() == "=" || peek() == "+=") | |||
792 | Cmd = readAssignment(Tok); | |||
793 | else if (Tok == "PROVIDE") | |||
794 | Cmd = readProvideHidden(true, false); | |||
795 | else if (Tok == "HIDDEN") | |||
796 | Cmd = readProvideHidden(false, true); | |||
797 | else if (Tok == "PROVIDE_HIDDEN") | |||
798 | Cmd = readProvideHidden(true, true); | |||
799 | ||||
800 | if (Cmd) { | |||
801 | Cmd->CommandString = | |||
802 | Tok.str() + " " + | |||
803 | llvm::join(Tokens.begin() + OldPos, Tokens.begin() + Pos, " "); | |||
804 | expect(";"); | |||
805 | } | |||
806 | return Cmd; | |||
807 | } | |||
808 | ||||
809 | SymbolAssignment *ScriptParser::readAssignment(StringRef Name) { | |||
810 | StringRef Op = next(); | |||
811 | assert(Op == "=" || Op == "+=")(static_cast <bool> (Op == "=" || Op == "+=") ? void (0 ) : __assert_fail ("Op == \"=\" || Op == \"+=\"", "/build/llvm-toolchain-snapshot-7~svn329677/tools/lld/ELF/ScriptParser.cpp" , 811, __extension__ __PRETTY_FUNCTION__)); | |||
812 | Expr E = readExpr(); | |||
813 | if (Op == "+=") { | |||
814 | std::string Loc = getCurrentLocation(); | |||
815 | E = [=] { return add(Script->getSymbolValue(Name, Loc), E()); }; | |||
816 | } | |||
817 | return make<SymbolAssignment>(Name, E, getCurrentLocation()); | |||
818 | } | |||
819 | ||||
820 | // This is an operator-precedence parser to parse a linker | |||
821 | // script expression. | |||
822 | Expr ScriptParser::readExpr() { | |||
823 | // Our lexer is context-aware. Set the in-expression bit so that | |||
824 | // they apply different tokenization rules. | |||
825 | bool Orig = InExpr; | |||
826 | InExpr = true; | |||
827 | Expr E = readExpr1(readPrimary(), 0); | |||
828 | InExpr = Orig; | |||
829 | return E; | |||
830 | } | |||
831 | ||||
832 | Expr ScriptParser::combine(StringRef Op, Expr L, Expr R) { | |||
833 | if (Op == "+") | |||
834 | return [=] { return add(L(), R()); }; | |||
835 | if (Op == "-") | |||
836 | return [=] { return sub(L(), R()); }; | |||
837 | if (Op == "*") | |||
838 | return [=] { return L().getValue() * R().getValue(); }; | |||
839 | if (Op == "/") { | |||
840 | std::string Loc = getCurrentLocation(); | |||
841 | return [=]() -> uint64_t { | |||
842 | if (uint64_t RV = R().getValue()) | |||
843 | return L().getValue() / RV; | |||
844 | error(Loc + ": division by zero"); | |||
845 | return 0; | |||
846 | }; | |||
847 | } | |||
848 | if (Op == "%") { | |||
849 | std::string Loc = getCurrentLocation(); | |||
850 | return [=]() -> uint64_t { | |||
851 | if (uint64_t RV = R().getValue()) | |||
852 | return L().getValue() % RV; | |||
853 | error(Loc + ": modulo by zero"); | |||
854 | return 0; | |||
855 | }; | |||
856 | } | |||
857 | if (Op == "<<") | |||
858 | return [=] { return L().getValue() << R().getValue(); }; | |||
859 | if (Op == ">>") | |||
860 | return [=] { return L().getValue() >> R().getValue(); }; | |||
861 | if (Op == "<") | |||
862 | return [=] { return L().getValue() < R().getValue(); }; | |||
863 | if (Op == ">") | |||
864 | return [=] { return L().getValue() > R().getValue(); }; | |||
865 | if (Op == ">=") | |||
866 | return [=] { return L().getValue() >= R().getValue(); }; | |||
867 | if (Op == "<=") | |||
868 | return [=] { return L().getValue() <= R().getValue(); }; | |||
869 | if (Op == "==") | |||
870 | return [=] { return L().getValue() == R().getValue(); }; | |||
871 | if (Op == "!=") | |||
872 | return [=] { return L().getValue() != R().getValue(); }; | |||
873 | if (Op == "&") | |||
874 | return [=] { return bitAnd(L(), R()); }; | |||
875 | if (Op == "|") | |||
876 | return [=] { return bitOr(L(), R()); }; | |||
877 | llvm_unreachable("invalid operator")::llvm::llvm_unreachable_internal("invalid operator", "/build/llvm-toolchain-snapshot-7~svn329677/tools/lld/ELF/ScriptParser.cpp" , 877); | |||
878 | } | |||
879 | ||||
880 | // This is a part of the operator-precedence parser. This function | |||
881 | // assumes that the remaining token stream starts with an operator. | |||
882 | Expr ScriptParser::readExpr1(Expr Lhs, int MinPrec) { | |||
883 | while (!atEOF() && !errorCount()) { | |||
884 | // Read an operator and an expression. | |||
885 | if (consume("?")) | |||
886 | return readTernary(Lhs); | |||
887 | StringRef Op1 = peek(); | |||
888 | if (precedence(Op1) < MinPrec) | |||
889 | break; | |||
890 | skip(); | |||
891 | Expr Rhs = readPrimary(); | |||
892 | ||||
893 | // Evaluate the remaining part of the expression first if the | |||
894 | // next operator has greater precedence than the previous one. | |||
895 | // For example, if we have read "+" and "3", and if the next | |||
896 | // operator is "*", then we'll evaluate 3 * ... part first. | |||
897 | while (!atEOF()) { | |||
898 | StringRef Op2 = peek(); | |||
899 | if (precedence(Op2) <= precedence(Op1)) | |||
900 | break; | |||
901 | Rhs = readExpr1(Rhs, precedence(Op2)); | |||
902 | } | |||
903 | ||||
904 | Lhs = combine(Op1, Lhs, Rhs); | |||
905 | } | |||
906 | return Lhs; | |||
907 | } | |||
908 | ||||
909 | Expr ScriptParser::getPageSize() { | |||
910 | std::string Location = getCurrentLocation(); | |||
911 | return [=]() -> uint64_t { | |||
912 | if (Target) | |||
913 | return Target->PageSize; | |||
914 | error(Location + ": unable to calculate page size"); | |||
915 | return 4096; // Return a dummy value. | |||
916 | }; | |||
917 | } | |||
918 | ||||
919 | Expr ScriptParser::readConstant() { | |||
920 | StringRef S = readParenLiteral(); | |||
921 | if (S == "COMMONPAGESIZE") | |||
922 | return getPageSize(); | |||
923 | if (S == "MAXPAGESIZE") | |||
924 | return [] { return Config->MaxPageSize; }; | |||
925 | setError("unknown constant: " + S); | |||
926 | return [] { return 0; }; | |||
927 | } | |||
928 | ||||
929 | // Parses Tok as an integer. It recognizes hexadecimal (prefixed with | |||
930 | // "0x" or suffixed with "H") and decimal numbers. Decimal numbers may | |||
931 | // have "K" (Ki) or "M" (Mi) suffixes. | |||
932 | static Optional<uint64_t> parseInt(StringRef Tok) { | |||
933 | // Hexadecimal | |||
934 | uint64_t Val; | |||
935 | if (Tok.startswith_lower("0x")) { | |||
936 | if (!to_integer(Tok.substr(2), Val, 16)) | |||
937 | return None; | |||
938 | return Val; | |||
939 | } | |||
940 | if (Tok.endswith_lower("H")) { | |||
941 | if (!to_integer(Tok.drop_back(), Val, 16)) | |||
942 | return None; | |||
943 | return Val; | |||
944 | } | |||
945 | ||||
946 | // Decimal | |||
947 | if (Tok.endswith_lower("K")) { | |||
948 | if (!to_integer(Tok.drop_back(), Val, 10)) | |||
949 | return None; | |||
950 | return Val * 1024; | |||
951 | } | |||
952 | if (Tok.endswith_lower("M")) { | |||
953 | if (!to_integer(Tok.drop_back(), Val, 10)) | |||
954 | return None; | |||
955 | return Val * 1024 * 1024; | |||
956 | } | |||
957 | if (!to_integer(Tok, Val, 10)) | |||
958 | return None; | |||
959 | return Val; | |||
960 | } | |||
961 | ||||
962 | ByteCommand *ScriptParser::readByteCommand(StringRef Tok) { | |||
963 | int Size = StringSwitch<int>(Tok) | |||
964 | .Case("BYTE", 1) | |||
965 | .Case("SHORT", 2) | |||
966 | .Case("LONG", 4) | |||
967 | .Case("QUAD", 8) | |||
968 | .Default(-1); | |||
969 | if (Size == -1) | |||
970 | return nullptr; | |||
971 | ||||
972 | size_t OldPos = Pos; | |||
973 | Expr E = readParenExpr(); | |||
974 | std::string CommandString = | |||
975 | Tok.str() + " " + | |||
976 | llvm::join(Tokens.begin() + OldPos, Tokens.begin() + Pos, " "); | |||
977 | return make<ByteCommand>(E, Size, CommandString); | |||
978 | } | |||
979 | ||||
980 | StringRef ScriptParser::readParenLiteral() { | |||
981 | expect("("); | |||
982 | bool Orig = InExpr; | |||
983 | InExpr = false; | |||
984 | StringRef Tok = next(); | |||
985 | InExpr = Orig; | |||
986 | expect(")"); | |||
987 | return Tok; | |||
988 | } | |||
989 | ||||
990 | static void checkIfExists(OutputSection *Cmd, StringRef Location) { | |||
991 | if (Cmd->Location.empty() && Script->ErrorOnMissingSection) | |||
992 | error(Location + ": undefined section " + Cmd->Name); | |||
993 | } | |||
994 | ||||
995 | Expr ScriptParser::readPrimary() { | |||
996 | if (peek() == "(") | |||
997 | return readParenExpr(); | |||
998 | ||||
999 | if (consume("~")) { | |||
1000 | Expr E = readPrimary(); | |||
1001 | return [=] { return ~E().getValue(); }; | |||
1002 | } | |||
1003 | if (consume("!")) { | |||
1004 | Expr E = readPrimary(); | |||
1005 | return [=] { return !E().getValue(); }; | |||
1006 | } | |||
1007 | if (consume("-")) { | |||
1008 | Expr E = readPrimary(); | |||
1009 | return [=] { return -E().getValue(); }; | |||
1010 | } | |||
1011 | ||||
1012 | StringRef Tok = next(); | |||
1013 | std::string Location = getCurrentLocation(); | |||
1014 | ||||
1015 | // Built-in functions are parsed here. | |||
1016 | // https://sourceware.org/binutils/docs/ld/Builtin-Functions.html. | |||
1017 | if (Tok == "ABSOLUTE") { | |||
1018 | Expr Inner = readParenExpr(); | |||
1019 | return [=] { | |||
1020 | ExprValue I = Inner(); | |||
1021 | I.ForceAbsolute = true; | |||
1022 | return I; | |||
1023 | }; | |||
1024 | } | |||
1025 | if (Tok == "ADDR") { | |||
1026 | StringRef Name = readParenLiteral(); | |||
1027 | OutputSection *Sec = Script->getOrCreateOutputSection(Name); | |||
1028 | return [=]() -> ExprValue { | |||
1029 | checkIfExists(Sec, Location); | |||
1030 | return {Sec, false, 0, Location}; | |||
1031 | }; | |||
1032 | } | |||
1033 | if (Tok == "ALIGN") { | |||
1034 | expect("("); | |||
1035 | Expr E = readExpr(); | |||
1036 | if (consume(")")) { | |||
1037 | E = checkAlignment(E, Location); | |||
1038 | return [=] { return alignTo(Script->getDot(), E().getValue()); }; | |||
1039 | } | |||
1040 | expect(","); | |||
1041 | Expr E2 = checkAlignment(readExpr(), Location); | |||
1042 | expect(")"); | |||
1043 | return [=] { | |||
1044 | ExprValue V = E(); | |||
1045 | V.Alignment = E2().getValue(); | |||
1046 | return V; | |||
1047 | }; | |||
1048 | } | |||
1049 | if (Tok == "ALIGNOF") { | |||
1050 | StringRef Name = readParenLiteral(); | |||
1051 | OutputSection *Cmd = Script->getOrCreateOutputSection(Name); | |||
1052 | return [=] { | |||
1053 | checkIfExists(Cmd, Location); | |||
1054 | return Cmd->Alignment; | |||
1055 | }; | |||
1056 | } | |||
1057 | if (Tok == "ASSERT") | |||
1058 | return readAssertExpr(); | |||
1059 | if (Tok == "CONSTANT") | |||
1060 | return readConstant(); | |||
1061 | if (Tok == "DATA_SEGMENT_ALIGN") { | |||
1062 | expect("("); | |||
1063 | Expr E = readExpr(); | |||
1064 | expect(","); | |||
1065 | readExpr(); | |||
1066 | expect(")"); | |||
1067 | return [=] { | |||
1068 | return alignTo(Script->getDot(), std::max((uint64_t)1, E().getValue())); | |||
1069 | }; | |||
1070 | } | |||
1071 | if (Tok == "DATA_SEGMENT_END") { | |||
1072 | expect("("); | |||
1073 | expect("."); | |||
1074 | expect(")"); | |||
1075 | return [] { return Script->getDot(); }; | |||
1076 | } | |||
1077 | if (Tok == "DATA_SEGMENT_RELRO_END") { | |||
1078 | // GNU linkers implements more complicated logic to handle | |||
1079 | // DATA_SEGMENT_RELRO_END. We instead ignore the arguments and | |||
1080 | // just align to the next page boundary for simplicity. | |||
1081 | expect("("); | |||
1082 | readExpr(); | |||
1083 | expect(","); | |||
1084 | readExpr(); | |||
1085 | expect(")"); | |||
1086 | Expr E = getPageSize(); | |||
1087 | return [=] { return alignTo(Script->getDot(), E().getValue()); }; | |||
1088 | } | |||
1089 | if (Tok == "DEFINED") { | |||
1090 | StringRef Name = readParenLiteral(); | |||
1091 | return [=] { return Symtab->find(Name) ? 1 : 0; }; | |||
1092 | } | |||
1093 | if (Tok == "LENGTH") { | |||
1094 | StringRef Name = readParenLiteral(); | |||
1095 | if (Script->MemoryRegions.count(Name) == 0) { | |||
1096 | setError("memory region not defined: " + Name); | |||
1097 | return [] { return 0; }; | |||
1098 | } | |||
1099 | return [=] { return Script->MemoryRegions[Name]->Length; }; | |||
1100 | } | |||
1101 | if (Tok == "LOADADDR") { | |||
1102 | StringRef Name = readParenLiteral(); | |||
1103 | OutputSection *Cmd = Script->getOrCreateOutputSection(Name); | |||
1104 | return [=] { | |||
1105 | checkIfExists(Cmd, Location); | |||
1106 | return Cmd->getLMA(); | |||
1107 | }; | |||
1108 | } | |||
1109 | if (Tok == "MAX" || Tok == "MIN") { | |||
1110 | expect("("); | |||
1111 | Expr A = readExpr(); | |||
1112 | expect(","); | |||
1113 | Expr B = readExpr(); | |||
1114 | expect(")"); | |||
1115 | if (Tok == "MIN") | |||
1116 | return [=] { return std::min(A().getValue(), B().getValue()); }; | |||
1117 | return [=] { return std::max(A().getValue(), B().getValue()); }; | |||
1118 | } | |||
1119 | if (Tok == "ORIGIN") { | |||
1120 | StringRef Name = readParenLiteral(); | |||
1121 | if (Script->MemoryRegions.count(Name) == 0) { | |||
1122 | setError("memory region not defined: " + Name); | |||
1123 | return [] { return 0; }; | |||
1124 | } | |||
1125 | return [=] { return Script->MemoryRegions[Name]->Origin; }; | |||
1126 | } | |||
1127 | if (Tok == "SEGMENT_START") { | |||
1128 | expect("("); | |||
1129 | skip(); | |||
1130 | expect(","); | |||
1131 | Expr E = readExpr(); | |||
1132 | expect(")"); | |||
1133 | return [=] { return E(); }; | |||
1134 | } | |||
1135 | if (Tok == "SIZEOF") { | |||
1136 | StringRef Name = readParenLiteral(); | |||
1137 | OutputSection *Cmd = Script->getOrCreateOutputSection(Name); | |||
1138 | // Linker script does not create an output section if its content is empty. | |||
1139 | // We want to allow SIZEOF(.foo) where .foo is a section which happened to | |||
1140 | // be empty. | |||
1141 | return [=] { return Cmd->Size; }; | |||
1142 | } | |||
1143 | if (Tok == "SIZEOF_HEADERS") | |||
1144 | return [=] { return elf::getHeaderSize(); }; | |||
1145 | ||||
1146 | // Tok is the dot. | |||
1147 | if (Tok == ".") | |||
1148 | return [=] { return Script->getSymbolValue(Tok, Location); }; | |||
1149 | ||||
1150 | // Tok is a literal number. | |||
1151 | if (Optional<uint64_t> Val = parseInt(Tok)) | |||
1152 | return [=] { return *Val; }; | |||
1153 | ||||
1154 | // Tok is a symbol name. | |||
1155 | if (!isValidCIdentifier(Tok)) | |||
1156 | setError("malformed number: " + Tok); | |||
1157 | Script->ReferencedSymbols.push_back(Tok); | |||
1158 | return [=] { return Script->getSymbolValue(Tok, Location); }; | |||
1159 | } | |||
1160 | ||||
1161 | Expr ScriptParser::readTernary(Expr Cond) { | |||
1162 | Expr L = readExpr(); | |||
1163 | expect(":"); | |||
1164 | Expr R = readExpr(); | |||
1165 | return [=] { return Cond().getValue() ? L() : R(); }; | |||
1166 | } | |||
1167 | ||||
1168 | Expr ScriptParser::readParenExpr() { | |||
1169 | expect("("); | |||
1170 | Expr E = readExpr(); | |||
1171 | expect(")"); | |||
1172 | return E; | |||
1173 | } | |||
1174 | ||||
1175 | std::vector<StringRef> ScriptParser::readOutputSectionPhdrs() { | |||
1176 | std::vector<StringRef> Phdrs; | |||
1177 | while (!errorCount() && peek().startswith(":")) { | |||
1178 | StringRef Tok = next(); | |||
1179 | Phdrs.push_back((Tok.size() == 1) ? next() : Tok.substr(1)); | |||
1180 | } | |||
1181 | return Phdrs; | |||
1182 | } | |||
1183 | ||||
1184 | // Read a program header type name. The next token must be a | |||
1185 | // name of a program header type or a constant (e.g. "0x3"). | |||
1186 | unsigned ScriptParser::readPhdrType() { | |||
1187 | StringRef Tok = next(); | |||
1188 | if (Optional<uint64_t> Val = parseInt(Tok)) | |||
1189 | return *Val; | |||
1190 | ||||
1191 | unsigned Ret = StringSwitch<unsigned>(Tok) | |||
1192 | .Case("PT_NULL", PT_NULL) | |||
1193 | .Case("PT_LOAD", PT_LOAD) | |||
1194 | .Case("PT_DYNAMIC", PT_DYNAMIC) | |||
1195 | .Case("PT_INTERP", PT_INTERP) | |||
1196 | .Case("PT_NOTE", PT_NOTE) | |||
1197 | .Case("PT_SHLIB", PT_SHLIB) | |||
1198 | .Case("PT_PHDR", PT_PHDR) | |||
1199 | .Case("PT_TLS", PT_TLS) | |||
1200 | .Case("PT_GNU_EH_FRAME", PT_GNU_EH_FRAME) | |||
1201 | .Case("PT_GNU_STACK", PT_GNU_STACK) | |||
1202 | .Case("PT_GNU_RELRO", PT_GNU_RELRO) | |||
1203 | .Case("PT_OPENBSD_RANDOMIZE", PT_OPENBSD_RANDOMIZE) | |||
1204 | .Case("PT_OPENBSD_WXNEEDED", PT_OPENBSD_WXNEEDED) | |||
1205 | .Case("PT_OPENBSD_BOOTDATA", PT_OPENBSD_BOOTDATA) | |||
1206 | .Default(-1); | |||
1207 | ||||
1208 | if (Ret == (unsigned)-1) { | |||
1209 | setError("invalid program header type: " + Tok); | |||
1210 | return PT_NULL; | |||
1211 | } | |||
1212 | return Ret; | |||
1213 | } | |||
1214 | ||||
1215 | // Reads an anonymous version declaration. | |||
1216 | void ScriptParser::readAnonymousDeclaration() { | |||
1217 | std::vector<SymbolVersion> Locals; | |||
1218 | std::vector<SymbolVersion> Globals; | |||
1219 | std::tie(Locals, Globals) = readSymbols(); | |||
1220 | ||||
1221 | for (SymbolVersion V : Locals) { | |||
1222 | if (V.Name == "*") | |||
1223 | Config->DefaultSymbolVersion = VER_NDX_LOCAL; | |||
1224 | else | |||
1225 | Config->VersionScriptLocals.push_back(V); | |||
1226 | } | |||
1227 | ||||
1228 | for (SymbolVersion V : Globals) | |||
1229 | Config->VersionScriptGlobals.push_back(V); | |||
1230 | ||||
1231 | expect(";"); | |||
1232 | } | |||
1233 | ||||
1234 | // Reads a non-anonymous version definition, | |||
1235 | // e.g. "VerStr { global: foo; bar; local: *; };". | |||
1236 | void ScriptParser::readVersionDeclaration(StringRef VerStr) { | |||
1237 | // Read a symbol list. | |||
1238 | std::vector<SymbolVersion> Locals; | |||
1239 | std::vector<SymbolVersion> Globals; | |||
1240 | std::tie(Locals, Globals) = readSymbols(); | |||
1241 | ||||
1242 | for (SymbolVersion V : Locals) { | |||
1243 | if (V.Name == "*") | |||
1244 | Config->DefaultSymbolVersion = VER_NDX_LOCAL; | |||
1245 | else | |||
1246 | Config->VersionScriptLocals.push_back(V); | |||
1247 | } | |||
1248 | ||||
1249 | // Create a new version definition and add that to the global symbols. | |||
1250 | VersionDefinition Ver; | |||
1251 | Ver.Name = VerStr; | |||
1252 | Ver.Globals = Globals; | |||
1253 | ||||
1254 | // User-defined version number starts from 2 because 0 and 1 are | |||
1255 | // reserved for VER_NDX_LOCAL and VER_NDX_GLOBAL, respectively. | |||
1256 | Ver.Id = Config->VersionDefinitions.size() + 2; | |||
1257 | Config->VersionDefinitions.push_back(Ver); | |||
1258 | ||||
1259 | // Each version may have a parent version. For example, "Ver2" | |||
1260 | // defined as "Ver2 { global: foo; local: *; } Ver1;" has "Ver1" | |||
1261 | // as a parent. This version hierarchy is, probably against your | |||
1262 | // instinct, purely for hint; the runtime doesn't care about it | |||
1263 | // at all. In LLD, we simply ignore it. | |||
1264 | if (peek() != ";") | |||
1265 | skip(); | |||
1266 | expect(";"); | |||
1267 | } | |||
1268 | ||||
1269 | static bool hasWildcard(StringRef S) { | |||
1270 | return S.find_first_of("?*[") != StringRef::npos; | |||
1271 | } | |||
1272 | ||||
1273 | // Reads a list of symbols, e.g. "{ global: foo; bar; local: *; };". | |||
1274 | std::pair<std::vector<SymbolVersion>, std::vector<SymbolVersion>> | |||
1275 | ScriptParser::readSymbols() { | |||
1276 | std::vector<SymbolVersion> Locals; | |||
1277 | std::vector<SymbolVersion> Globals; | |||
1278 | std::vector<SymbolVersion> *V = &Globals; | |||
1279 | ||||
1280 | while (!errorCount()) { | |||
1281 | if (consume("}")) | |||
1282 | break; | |||
1283 | if (consumeLabel("local")) { | |||
1284 | V = &Locals; | |||
1285 | continue; | |||
1286 | } | |||
1287 | if (consumeLabel("global")) { | |||
1288 | V = &Globals; | |||
1289 | continue; | |||
1290 | } | |||
1291 | ||||
1292 | if (consume("extern")) { | |||
1293 | std::vector<SymbolVersion> Ext = readVersionExtern(); | |||
1294 | V->insert(V->end(), Ext.begin(), Ext.end()); | |||
1295 | } else { | |||
1296 | StringRef Tok = next(); | |||
1297 | V->push_back({unquote(Tok), false, hasWildcard(Tok)}); | |||
1298 | } | |||
1299 | expect(";"); | |||
1300 | } | |||
1301 | return {Locals, Globals}; | |||
1302 | } | |||
1303 | ||||
1304 | // Reads an "extern C++" directive, e.g., | |||
1305 | // "extern "C++" { ns::*; "f(int, double)"; };" | |||
1306 | // | |||
1307 | // The last semicolon is optional. E.g. this is OK: | |||
1308 | // "extern "C++" { ns::*; "f(int, double)" };" | |||
1309 | std::vector<SymbolVersion> ScriptParser::readVersionExtern() { | |||
1310 | StringRef Tok = next(); | |||
1311 | bool IsCXX = Tok == "\"C++\""; | |||
1312 | if (!IsCXX && Tok != "\"C\"") | |||
1313 | setError("Unknown language"); | |||
1314 | expect("{"); | |||
1315 | ||||
1316 | std::vector<SymbolVersion> Ret; | |||
1317 | while (!errorCount() && peek() != "}") { | |||
1318 | StringRef Tok = next(); | |||
1319 | bool HasWildcard = !Tok.startswith("\"") && hasWildcard(Tok); | |||
1320 | Ret.push_back({unquote(Tok), IsCXX, HasWildcard}); | |||
1321 | if (consume("}")) | |||
1322 | return Ret; | |||
1323 | expect(";"); | |||
1324 | } | |||
1325 | ||||
1326 | expect("}"); | |||
1327 | return Ret; | |||
1328 | } | |||
1329 | ||||
1330 | uint64_t ScriptParser::readMemoryAssignment(StringRef S1, StringRef S2, | |||
1331 | StringRef S3) { | |||
1332 | if (!consume(S1) && !consume(S2) && !consume(S3)) { | |||
1333 | setError("expected one of: " + S1 + ", " + S2 + ", or " + S3); | |||
1334 | return 0; | |||
1335 | } | |||
1336 | expect("="); | |||
1337 | return readExpr()().getValue(); | |||
1338 | } | |||
1339 | ||||
1340 | // Parse the MEMORY command as specified in: | |||
1341 | // https://sourceware.org/binutils/docs/ld/MEMORY.html | |||
1342 | // | |||
1343 | // MEMORY { name [(attr)] : ORIGIN = origin, LENGTH = len ... } | |||
1344 | void ScriptParser::readMemory() { | |||
1345 | expect("{"); | |||
1346 | while (!errorCount() && !consume("}")) { | |||
1347 | StringRef Name = next(); | |||
1348 | ||||
1349 | uint32_t Flags = 0; | |||
1350 | uint32_t NegFlags = 0; | |||
1351 | if (consume("(")) { | |||
1352 | std::tie(Flags, NegFlags) = readMemoryAttributes(); | |||
1353 | expect(")"); | |||
1354 | } | |||
1355 | expect(":"); | |||
1356 | ||||
1357 | uint64_t Origin = readMemoryAssignment("ORIGIN", "org", "o"); | |||
1358 | expect(","); | |||
1359 | uint64_t Length = readMemoryAssignment("LENGTH", "len", "l"); | |||
1360 | ||||
1361 | // Add the memory region to the region map. | |||
1362 | MemoryRegion *MR = | |||
1363 | make<MemoryRegion>(Name, Origin, Length, Flags, NegFlags); | |||
1364 | if (!Script->MemoryRegions.insert({Name, MR}).second) | |||
1365 | setError("region '" + Name + "' already defined"); | |||
1366 | } | |||
1367 | } | |||
1368 | ||||
1369 | // This function parses the attributes used to match against section | |||
1370 | // flags when placing output sections in a memory region. These flags | |||
1371 | // are only used when an explicit memory region name is not used. | |||
1372 | std::pair<uint32_t, uint32_t> ScriptParser::readMemoryAttributes() { | |||
1373 | uint32_t Flags = 0; | |||
1374 | uint32_t NegFlags = 0; | |||
1375 | bool Invert = false; | |||
1376 | ||||
1377 | for (char C : next().lower()) { | |||
1378 | uint32_t Flag = 0; | |||
1379 | if (C == '!') | |||
1380 | Invert = !Invert; | |||
1381 | else if (C == 'w') | |||
1382 | Flag = SHF_WRITE; | |||
1383 | else if (C == 'x') | |||
1384 | Flag = SHF_EXECINSTR; | |||
1385 | else if (C == 'a') | |||
1386 | Flag = SHF_ALLOC; | |||
1387 | else if (C != 'r') | |||
1388 | setError("invalid memory region attribute"); | |||
1389 | ||||
1390 | if (Invert) | |||
1391 | NegFlags |= Flag; | |||
1392 | else | |||
1393 | Flags |= Flag; | |||
1394 | } | |||
1395 | return {Flags, NegFlags}; | |||
1396 | } | |||
1397 | ||||
1398 | void elf::readLinkerScript(MemoryBufferRef MB) { | |||
1399 | ScriptParser(MB).readLinkerScript(); | |||
1400 | } | |||
1401 | ||||
1402 | void elf::readVersionScript(MemoryBufferRef MB) { | |||
1403 | ScriptParser(MB).readVersionScript(); | |||
1404 | } | |||
1405 | ||||
1406 | void elf::readDynamicList(MemoryBufferRef MB) { | |||
1407 | ScriptParser(MB).readDynamicList(); | |||
1408 | } | |||
1409 | ||||
1410 | void elf::readDefsym(StringRef Name, MemoryBufferRef MB) { | |||
1411 | ScriptParser(MB).readDefsym(Name); | |||
1412 | } |
1 | // Implementation of std::function -*- C++ -*- |
2 | |
3 | // Copyright (C) 2004-2017 Free Software Foundation, Inc. |
4 | // |
5 | // This file is part of the GNU ISO C++ Library. This library is free |
6 | // software; you can redistribute it and/or modify it under the |
7 | // terms of the GNU General Public License as published by the |
8 | // Free Software Foundation; either version 3, or (at your option) |
9 | // any later version. |
10 | |
11 | // This library is distributed in the hope that it will be useful, |
12 | // but WITHOUT ANY WARRANTY; without even the implied warranty of |
13 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
14 | // GNU General Public License for more details. |
15 | |
16 | // Under Section 7 of GPL version 3, you are granted additional |
17 | // permissions described in the GCC Runtime Library Exception, version |
18 | // 3.1, as published by the Free Software Foundation. |
19 | |
20 | // You should have received a copy of the GNU General Public License and |
21 | // a copy of the GCC Runtime Library Exception along with this program; |
22 | // see the files COPYING3 and COPYING.RUNTIME respectively. If not, see |
23 | // <http://www.gnu.org/licenses/>. |
24 | |
25 | /** @file include/bits/function.h |
26 | * This is an internal header file, included by other library headers. |
27 | * Do not attempt to use it directly. @headername{functional} |
28 | */ |
29 | |
30 | #ifndef _GLIBCXX_STD_FUNCTION_H1 |
31 | #define _GLIBCXX_STD_FUNCTION_H1 1 |
32 | |
33 | #pragma GCC system_header |
34 | |
35 | #if __cplusplus201103L < 201103L |
36 | # include <bits/c++0x_warning.h> |
37 | #else |
38 | |
39 | #if __cpp_rtti199711 |
40 | # include <typeinfo> |
41 | #endif |
42 | #include <bits/stl_function.h> |
43 | #include <bits/invoke.h> |
44 | #include <bits/refwrap.h> |
45 | #include <bits/functexcept.h> |
46 | |
47 | namespace std _GLIBCXX_VISIBILITY(default)__attribute__ ((__visibility__ ("default"))) |
48 | { |
49 | _GLIBCXX_BEGIN_NAMESPACE_VERSION |
50 | |
51 | /** |
52 | * Derives from @c unary_function or @c binary_function, or perhaps |
53 | * nothing, depending on the number of arguments provided. The |
54 | * primary template is the basis case, which derives nothing. |
55 | */ |
56 | template<typename _Res, typename... _ArgTypes> |
57 | struct _Maybe_unary_or_binary_function { }; |
58 | |
59 | /// Derives from @c unary_function, as appropriate. |
60 | template<typename _Res, typename _T1> |
61 | struct _Maybe_unary_or_binary_function<_Res, _T1> |
62 | : std::unary_function<_T1, _Res> { }; |
63 | |
64 | /// Derives from @c binary_function, as appropriate. |
65 | template<typename _Res, typename _T1, typename _T2> |
66 | struct _Maybe_unary_or_binary_function<_Res, _T1, _T2> |
67 | : std::binary_function<_T1, _T2, _Res> { }; |
68 | |
69 | |
70 | /** |
71 | * @brief Exception class thrown when class template function's |
72 | * operator() is called with an empty target. |
73 | * @ingroup exceptions |
74 | */ |
75 | class bad_function_call : public std::exception |
76 | { |
77 | public: |
78 | virtual ~bad_function_call() noexcept; |
79 | |
80 | const char* what() const noexcept; |
81 | }; |
82 | |
83 | /** |
84 | * Trait identifying "location-invariant" types, meaning that the |
85 | * address of the object (or any of its members) will not escape. |
86 | * Trivially copyable types are location-invariant and users can |
87 | * specialize this trait for other types. |
88 | */ |
89 | template<typename _Tp> |
90 | struct __is_location_invariant |
91 | : is_trivially_copyable<_Tp>::type |
92 | { }; |
93 | |
94 | class _Undefined_class; |
95 | |
96 | union _Nocopy_types |
97 | { |
98 | void* _M_object; |
99 | const void* _M_const_object; |
100 | void (*_M_function_pointer)(); |
101 | void (_Undefined_class::*_M_member_pointer)(); |
102 | }; |
103 | |
104 | union [[gnu::may_alias]] _Any_data |
105 | { |
106 | void* _M_access() { return &_M_pod_data[0]; } |
107 | const void* _M_access() const { return &_M_pod_data[0]; } |
108 | |
109 | template<typename _Tp> |
110 | _Tp& |
111 | _M_access() |
112 | { return *static_cast<_Tp*>(_M_access()); } |
113 | |
114 | template<typename _Tp> |
115 | const _Tp& |
116 | _M_access() const |
117 | { return *static_cast<const _Tp*>(_M_access()); } |
118 | |
119 | _Nocopy_types _M_unused; |
120 | char _M_pod_data[sizeof(_Nocopy_types)]; |
121 | }; |
122 | |
123 | enum _Manager_operation |
124 | { |
125 | __get_type_info, |
126 | __get_functor_ptr, |
127 | __clone_functor, |
128 | __destroy_functor |
129 | }; |
130 | |
131 | // Simple type wrapper that helps avoid annoying const problems |
132 | // when casting between void pointers and pointers-to-pointers. |
133 | template<typename _Tp> |
134 | struct _Simple_type_wrapper |
135 | { |
136 | _Simple_type_wrapper(_Tp __value) : __value(__value) { } |
137 | |
138 | _Tp __value; |
139 | }; |
140 | |
141 | template<typename _Tp> |
142 | struct __is_location_invariant<_Simple_type_wrapper<_Tp> > |
143 | : __is_location_invariant<_Tp> |
144 | { }; |
145 | |
146 | template<typename _Signature> |
147 | class function; |
148 | |
149 | /// Base class of all polymorphic function object wrappers. |
150 | class _Function_base |
151 | { |
152 | public: |
153 | static const std::size_t _M_max_size = sizeof(_Nocopy_types); |
154 | static const std::size_t _M_max_align = __alignof__(_Nocopy_types); |
155 | |
156 | template<typename _Functor> |
157 | class _Base_manager |
158 | { |
159 | protected: |
160 | static const bool __stored_locally = |
161 | (__is_location_invariant<_Functor>::value |
162 | && sizeof(_Functor) <= _M_max_size |
163 | && __alignof__(_Functor) <= _M_max_align |
164 | && (_M_max_align % __alignof__(_Functor) == 0)); |
165 | |
166 | typedef integral_constant<bool, __stored_locally> _Local_storage; |
167 | |
168 | // Retrieve a pointer to the function object |
169 | static _Functor* |
170 | _M_get_pointer(const _Any_data& __source) |
171 | { |
172 | const _Functor* __ptr = |
173 | __stored_locally? std::__addressof(__source._M_access<_Functor>()) |
174 | /* have stored a pointer */ : __source._M_access<_Functor*>(); |
175 | return const_cast<_Functor*>(__ptr); |
176 | } |
177 | |
178 | // Clone a location-invariant function object that fits within |
179 | // an _Any_data structure. |
180 | static void |
181 | _M_clone(_Any_data& __dest, const _Any_data& __source, true_type) |
182 | { |
183 | ::new (__dest._M_access()) _Functor(__source._M_access<_Functor>()); |
184 | } |
185 | |
186 | // Clone a function object that is not location-invariant or |
187 | // that cannot fit into an _Any_data structure. |
188 | static void |
189 | _M_clone(_Any_data& __dest, const _Any_data& __source, false_type) |
190 | { |
191 | __dest._M_access<_Functor*>() = |
192 | new _Functor(*__source._M_access<_Functor*>()); |
193 | } |
194 | |
195 | // Destroying a location-invariant object may still require |
196 | // destruction. |
197 | static void |
198 | _M_destroy(_Any_data& __victim, true_type) |
199 | { |
200 | __victim._M_access<_Functor>().~_Functor(); |
201 | } |
202 | |
203 | // Destroying an object located on the heap. |
204 | static void |
205 | _M_destroy(_Any_data& __victim, false_type) |
206 | { |
207 | delete __victim._M_access<_Functor*>(); |
208 | } |
209 | |
210 | public: |
211 | static bool |
212 | _M_manager(_Any_data& __dest, const _Any_data& __source, |
213 | _Manager_operation __op) |
214 | { |
215 | switch (__op) |
216 | { |
217 | #if __cpp_rtti199711 |
218 | case __get_type_info: |
219 | __dest._M_access<const type_info*>() = &typeid(_Functor); |
220 | break; |
221 | #endif |
222 | case __get_functor_ptr: |
223 | __dest._M_access<_Functor*>() = _M_get_pointer(__source); |
224 | break; |
225 | |
226 | case __clone_functor: |
227 | _M_clone(__dest, __source, _Local_storage()); |
228 | break; |
229 | |
230 | case __destroy_functor: |
231 | _M_destroy(__dest, _Local_storage()); |
232 | break; |
233 | } |
234 | return false; |
235 | } |
236 | |
237 | static void |
238 | _M_init_functor(_Any_data& __functor, _Functor&& __f) |
239 | { _M_init_functor(__functor, std::move(__f), _Local_storage()); } |
240 | |
241 | template<typename _Signature> |
242 | static bool |
243 | _M_not_empty_function(const function<_Signature>& __f) |
244 | { return static_cast<bool>(__f); } |
245 | |
246 | template<typename _Tp> |
247 | static bool |
248 | _M_not_empty_function(_Tp* __fp) |
249 | { return __fp != nullptr; } |
250 | |
251 | template<typename _Class, typename _Tp> |
252 | static bool |
253 | _M_not_empty_function(_Tp _Class::* __mp) |
254 | { return __mp != nullptr; } |
255 | |
256 | template<typename _Tp> |
257 | static bool |
258 | _M_not_empty_function(const _Tp&) |
259 | { return true; } |
260 | |
261 | private: |
262 | static void |
263 | _M_init_functor(_Any_data& __functor, _Functor&& __f, true_type) |
264 | { ::new (__functor._M_access()) _Functor(std::move(__f)); } |
265 | |
266 | static void |
267 | _M_init_functor(_Any_data& __functor, _Functor&& __f, false_type) |
268 | { __functor._M_access<_Functor*>() = new _Functor(std::move(__f)); } |
269 | }; |
270 | |
271 | _Function_base() : _M_manager(nullptr) { } |
272 | |
273 | ~_Function_base() |
274 | { |
275 | if (_M_manager) |
276 | _M_manager(_M_functor, _M_functor, __destroy_functor); |
277 | } |
278 | |
279 | bool _M_empty() const { return !_M_manager; } |
280 | |
281 | typedef bool (*_Manager_type)(_Any_data&, const _Any_data&, |
282 | _Manager_operation); |
283 | |
284 | _Any_data _M_functor; |
285 | _Manager_type _M_manager; |
286 | }; |
287 | |
288 | template<typename _Signature, typename _Functor> |
289 | class _Function_handler; |
290 | |
291 | template<typename _Res, typename _Functor, typename... _ArgTypes> |
292 | class _Function_handler<_Res(_ArgTypes...), _Functor> |
293 | : public _Function_base::_Base_manager<_Functor> |
294 | { |
295 | typedef _Function_base::_Base_manager<_Functor> _Base; |
296 | |
297 | public: |
298 | static _Res |
299 | _M_invoke(const _Any_data& __functor, _ArgTypes&&... __args) |
300 | { |
301 | return (*_Base::_M_get_pointer(__functor))( |
302 | std::forward<_ArgTypes>(__args)...); |
303 | } |
304 | }; |
305 | |
306 | template<typename _Functor, typename... _ArgTypes> |
307 | class _Function_handler<void(_ArgTypes...), _Functor> |
308 | : public _Function_base::_Base_manager<_Functor> |
309 | { |
310 | typedef _Function_base::_Base_manager<_Functor> _Base; |
311 | |
312 | public: |
313 | static void |
314 | _M_invoke(const _Any_data& __functor, _ArgTypes&&... __args) |
315 | { |
316 | (*_Base::_M_get_pointer(__functor))( |
317 | std::forward<_ArgTypes>(__args)...); |
318 | } |
319 | }; |
320 | |
321 | template<typename _Class, typename _Member, typename _Res, |
322 | typename... _ArgTypes> |
323 | class _Function_handler<_Res(_ArgTypes...), _Member _Class::*> |
324 | : public _Function_handler<void(_ArgTypes...), _Member _Class::*> |
325 | { |
326 | typedef _Function_handler<void(_ArgTypes...), _Member _Class::*> |
327 | _Base; |
328 | |
329 | public: |
330 | static _Res |
331 | _M_invoke(const _Any_data& __functor, _ArgTypes&&... __args) |
332 | { |
333 | return std::__invoke(_Base::_M_get_pointer(__functor)->__value, |
334 | std::forward<_ArgTypes>(__args)...); |
335 | } |
336 | }; |
337 | |
338 | template<typename _Class, typename _Member, typename... _ArgTypes> |
339 | class _Function_handler<void(_ArgTypes...), _Member _Class::*> |
340 | : public _Function_base::_Base_manager< |
341 | _Simple_type_wrapper< _Member _Class::* > > |
342 | { |
343 | typedef _Member _Class::* _Functor; |
344 | typedef _Simple_type_wrapper<_Functor> _Wrapper; |
345 | typedef _Function_base::_Base_manager<_Wrapper> _Base; |
346 | |
347 | public: |
348 | static bool |
349 | _M_manager(_Any_data& __dest, const _Any_data& __source, |
350 | _Manager_operation __op) |
351 | { |
352 | switch (__op) |
353 | { |
354 | #if __cpp_rtti199711 |
355 | case __get_type_info: |
356 | __dest._M_access<const type_info*>() = &typeid(_Functor); |
357 | break; |
358 | #endif |
359 | case __get_functor_ptr: |
360 | __dest._M_access<_Functor*>() = |
361 | &_Base::_M_get_pointer(__source)->__value; |
362 | break; |
363 | |
364 | default: |
365 | _Base::_M_manager(__dest, __source, __op); |
366 | } |
367 | return false; |
368 | } |
369 | |
370 | static void |
371 | _M_invoke(const _Any_data& __functor, _ArgTypes&&... __args) |
372 | { |
373 | std::__invoke(_Base::_M_get_pointer(__functor)->__value, |
374 | std::forward<_ArgTypes>(__args)...); |
375 | } |
376 | }; |
377 | |
378 | template<typename _From, typename _To> |
379 | using __check_func_return_type |
380 | = __or_<is_void<_To>, is_same<_From, _To>, is_convertible<_From, _To>>; |
381 | |
382 | /** |
383 | * @brief Primary class template for std::function. |
384 | * @ingroup functors |
385 | * |
386 | * Polymorphic function wrapper. |
387 | */ |
388 | template<typename _Res, typename... _ArgTypes> |
389 | class function<_Res(_ArgTypes...)> |
390 | : public _Maybe_unary_or_binary_function<_Res, _ArgTypes...>, |
391 | private _Function_base |
392 | { |
393 | template<typename _Func, |
394 | typename _Res2 = typename result_of<_Func&(_ArgTypes...)>::type> |
395 | struct _Callable : __check_func_return_type<_Res2, _Res> { }; |
396 | |
397 | // Used so the return type convertibility checks aren't done when |
398 | // performing overload resolution for copy construction/assignment. |
399 | template<typename _Tp> |
400 | struct _Callable<function, _Tp> : false_type { }; |
401 | |
402 | template<typename _Cond, typename _Tp> |
403 | using _Requires = typename enable_if<_Cond::value, _Tp>::type; |
404 | |
405 | public: |
406 | typedef _Res result_type; |
407 | |
408 | // [3.7.2.1] construct/copy/destroy |
409 | |
410 | /** |
411 | * @brief Default construct creates an empty function call wrapper. |
412 | * @post @c !(bool)*this |
413 | */ |
414 | function() noexcept |
415 | : _Function_base() { } |
416 | |
417 | /** |
418 | * @brief Creates an empty function call wrapper. |
419 | * @post @c !(bool)*this |
420 | */ |
421 | function(nullptr_t) noexcept |
422 | : _Function_base() { } |
423 | |
424 | /** |
425 | * @brief %Function copy constructor. |
426 | * @param __x A %function object with identical call signature. |
427 | * @post @c bool(*this) == bool(__x) |
428 | * |
429 | * The newly-created %function contains a copy of the target of @a |
430 | * __x (if it has one). |
431 | */ |
432 | function(const function& __x); |
433 | |
434 | /** |
435 | * @brief %Function move constructor. |
436 | * @param __x A %function object rvalue with identical call signature. |
437 | * |
438 | * The newly-created %function contains the target of @a __x |
439 | * (if it has one). |
440 | */ |
441 | function(function&& __x) noexcept : _Function_base() |
442 | { |
443 | __x.swap(*this); |
444 | } |
445 | |
446 | /** |
447 | * @brief Builds a %function that targets a copy of the incoming |
448 | * function object. |
449 | * @param __f A %function object that is callable with parameters of |
450 | * type @c T1, @c T2, ..., @c TN and returns a value convertible |
451 | * to @c Res. |
452 | * |
453 | * The newly-created %function object will target a copy of |
454 | * @a __f. If @a __f is @c reference_wrapper<F>, then this function |
455 | * object will contain a reference to the function object @c |
456 | * __f.get(). If @a __f is a NULL function pointer or NULL |
457 | * pointer-to-member, the newly-created object will be empty. |
458 | * |
459 | * If @a __f is a non-NULL function pointer or an object of type @c |
460 | * reference_wrapper<F>, this function will not throw. |
461 | */ |
462 | template<typename _Functor, |
463 | typename = _Requires<__not_<is_same<_Functor, function>>, void>, |
464 | typename = _Requires<_Callable<_Functor>, void>> |
465 | function(_Functor); |
466 | |
467 | /** |
468 | * @brief %Function assignment operator. |
469 | * @param __x A %function with identical call signature. |
470 | * @post @c (bool)*this == (bool)x |
471 | * @returns @c *this |
472 | * |
473 | * The target of @a __x is copied to @c *this. If @a __x has no |
474 | * target, then @c *this will be empty. |
475 | * |
476 | * If @a __x targets a function pointer or a reference to a function |
477 | * object, then this operation will not throw an %exception. |
478 | */ |
479 | function& |
480 | operator=(const function& __x) |
481 | { |
482 | function(__x).swap(*this); |
483 | return *this; |
484 | } |
485 | |
486 | /** |
487 | * @brief %Function move-assignment operator. |
488 | * @param __x A %function rvalue with identical call signature. |
489 | * @returns @c *this |
490 | * |
491 | * The target of @a __x is moved to @c *this. If @a __x has no |
492 | * target, then @c *this will be empty. |
493 | * |
494 | * If @a __x targets a function pointer or a reference to a function |
495 | * object, then this operation will not throw an %exception. |
496 | */ |
497 | function& |
498 | operator=(function&& __x) noexcept |
499 | { |
500 | function(std::move(__x)).swap(*this); |
501 | return *this; |
502 | } |
503 | |
504 | /** |
505 | * @brief %Function assignment to zero. |
506 | * @post @c !(bool)*this |
507 | * @returns @c *this |
508 | * |
509 | * The target of @c *this is deallocated, leaving it empty. |
510 | */ |
511 | function& |
512 | operator=(nullptr_t) noexcept |
513 | { |
514 | if (_M_manager) |
515 | { |
516 | _M_manager(_M_functor, _M_functor, __destroy_functor); |
517 | _M_manager = nullptr; |
518 | _M_invoker = nullptr; |
519 | } |
520 | return *this; |
521 | } |
522 | |
523 | /** |
524 | * @brief %Function assignment to a new target. |
525 | * @param __f A %function object that is callable with parameters of |
526 | * type @c T1, @c T2, ..., @c TN and returns a value convertible |
527 | * to @c Res. |
528 | * @return @c *this |
529 | * |
530 | * This %function object wrapper will target a copy of @a |
531 | * __f. If @a __f is @c reference_wrapper<F>, then this function |
532 | * object will contain a reference to the function object @c |
533 | * __f.get(). If @a __f is a NULL function pointer or NULL |
534 | * pointer-to-member, @c this object will be empty. |
535 | * |
536 | * If @a __f is a non-NULL function pointer or an object of type @c |
537 | * reference_wrapper<F>, this function will not throw. |
538 | */ |
539 | template<typename _Functor> |
540 | _Requires<_Callable<typename decay<_Functor>::type>, function&> |
541 | operator=(_Functor&& __f) |
542 | { |
543 | function(std::forward<_Functor>(__f)).swap(*this); |
544 | return *this; |
545 | } |
546 | |
547 | /// @overload |
548 | template<typename _Functor> |
549 | function& |
550 | operator=(reference_wrapper<_Functor> __f) noexcept |
551 | { |
552 | function(__f).swap(*this); |
553 | return *this; |
554 | } |
555 | |
556 | // [3.7.2.2] function modifiers |
557 | |
558 | /** |
559 | * @brief Swap the targets of two %function objects. |
560 | * @param __x A %function with identical call signature. |
561 | * |
562 | * Swap the targets of @c this function object and @a __f. This |
563 | * function will not throw an %exception. |
564 | */ |
565 | void swap(function& __x) noexcept |
566 | { |
567 | std::swap(_M_functor, __x._M_functor); |
568 | std::swap(_M_manager, __x._M_manager); |
569 | std::swap(_M_invoker, __x._M_invoker); |
570 | } |
571 | |
572 | // [3.7.2.3] function capacity |
573 | |
574 | /** |
575 | * @brief Determine if the %function wrapper has a target. |
576 | * |
577 | * @return @c true when this %function object contains a target, |
578 | * or @c false when it is empty. |
579 | * |
580 | * This function will not throw an %exception. |
581 | */ |
582 | explicit operator bool() const noexcept |
583 | { return !_M_empty(); } |
584 | |
585 | // [3.7.2.4] function invocation |
586 | |
587 | /** |
588 | * @brief Invokes the function targeted by @c *this. |
589 | * @returns the result of the target. |
590 | * @throws bad_function_call when @c !(bool)*this |
591 | * |
592 | * The function call operator invokes the target function object |
593 | * stored by @c this. |
594 | */ |
595 | _Res operator()(_ArgTypes... __args) const; |
596 | |
597 | #if __cpp_rtti199711 |
598 | // [3.7.2.5] function target access |
599 | /** |
600 | * @brief Determine the type of the target of this function object |
601 | * wrapper. |
602 | * |
603 | * @returns the type identifier of the target function object, or |
604 | * @c typeid(void) if @c !(bool)*this. |
605 | * |
606 | * This function will not throw an %exception. |
607 | */ |
608 | const type_info& target_type() const noexcept; |
609 | |
610 | /** |
611 | * @brief Access the stored target function object. |
612 | * |
613 | * @return Returns a pointer to the stored target function object, |
614 | * if @c typeid(_Functor).equals(target_type()); otherwise, a NULL |
615 | * pointer. |
616 | * |
617 | * This function does not throw exceptions. |
618 | * |
619 | * @{ |
620 | */ |
621 | template<typename _Functor> _Functor* target() noexcept; |
622 | |
623 | template<typename _Functor> const _Functor* target() const noexcept; |
624 | // @} |
625 | #endif |
626 | |
627 | private: |
628 | using _Invoker_type = _Res (*)(const _Any_data&, _ArgTypes&&...); |
629 | _Invoker_type _M_invoker; |
630 | }; |
631 | |
632 | #if __cpp_deduction_guides >= 201606 |
633 | template<typename> |
634 | struct __function_guide_helper |
635 | { }; |
636 | |
637 | template<typename _Res, typename _Tp, bool _Nx, typename... _Args> |
638 | struct __function_guide_helper< |
639 | _Res (_Tp::*) (_Args...) noexcept(_Nx) |
640 | > |
641 | { using type = _Res(_Args...); }; |
642 | |
643 | template<typename _Res, typename _Tp, bool _Nx, typename... _Args> |
644 | struct __function_guide_helper< |
645 | _Res (_Tp::*) (_Args...) & noexcept(_Nx) |
646 | > |
647 | { using type = _Res(_Args...); }; |
648 | |
649 | template<typename _Res, typename _Tp, bool _Nx, typename... _Args> |
650 | struct __function_guide_helper< |
651 | _Res (_Tp::*) (_Args...) const noexcept(_Nx) |
652 | > |
653 | { using type = _Res(_Args...); }; |
654 | |
655 | template<typename _Res, typename _Tp, bool _Nx, typename... _Args> |
656 | struct __function_guide_helper< |
657 | _Res (_Tp::*) (_Args...) const & noexcept(_Nx) |
658 | > |
659 | { using type = _Res(_Args...); }; |
660 | |
661 | template<typename _Res, typename... _ArgTypes> |
662 | function(_Res(*)(_ArgTypes...)) -> function<_Res(_ArgTypes...)>; |
663 | |
664 | template<typename _Functor, typename _Signature = typename |
665 | __function_guide_helper<decltype(&_Functor::operator())>::type> |
666 | function(_Functor) -> function<_Signature>; |
667 | #endif |
668 | |
669 | // Out-of-line member definitions. |
670 | template<typename _Res, typename... _ArgTypes> |
671 | function<_Res(_ArgTypes...)>:: |
672 | function(const function& __x) |
673 | : _Function_base() |
674 | { |
675 | if (static_cast<bool>(__x)) |
676 | { |
677 | __x._M_manager(_M_functor, __x._M_functor, __clone_functor); |
678 | _M_invoker = __x._M_invoker; |
679 | _M_manager = __x._M_manager; |
680 | } |
681 | } |
682 | |
683 | template<typename _Res, typename... _ArgTypes> |
684 | template<typename _Functor, typename, typename> |
685 | function<_Res(_ArgTypes...)>:: |
686 | function(_Functor __f) |
687 | : _Function_base() |
688 | { |
689 | typedef _Function_handler<_Res(_ArgTypes...), _Functor> _My_handler; |
690 | |
691 | if (_My_handler::_M_not_empty_function(__f)) |
692 | { |
693 | _My_handler::_M_init_functor(_M_functor, std::move(__f)); |
694 | _M_invoker = &_My_handler::_M_invoke; |
695 | _M_manager = &_My_handler::_M_manager; |
696 | } |
697 | } |
698 | |
699 | template<typename _Res, typename... _ArgTypes> |
700 | _Res |
701 | function<_Res(_ArgTypes...)>:: |
702 | operator()(_ArgTypes... __args) const |
703 | { |
704 | if (_M_empty()) |
705 | __throw_bad_function_call(); |
706 | return _M_invoker(_M_functor, std::forward<_ArgTypes>(__args)...); |
707 | } |
708 | |
709 | #if __cpp_rtti199711 |
710 | template<typename _Res, typename... _ArgTypes> |
711 | const type_info& |
712 | function<_Res(_ArgTypes...)>:: |
713 | target_type() const noexcept |
714 | { |
715 | if (_M_manager) |
716 | { |
717 | _Any_data __typeinfo_result; |
718 | _M_manager(__typeinfo_result, _M_functor, __get_type_info); |
719 | return *__typeinfo_result._M_access<const type_info*>(); |
720 | } |
721 | else |
722 | return typeid(void); |
723 | } |
724 | |
725 | template<typename _Res, typename... _ArgTypes> |
726 | template<typename _Functor> |
727 | _Functor* |
728 | function<_Res(_ArgTypes...)>:: |
729 | target() noexcept |
730 | { |
731 | const function* __const_this = this; |
732 | const _Functor* __func = __const_this->template target<_Functor>(); |
733 | return const_cast<_Functor*>(__func); |
734 | } |
735 | |
736 | template<typename _Res, typename... _ArgTypes> |
737 | template<typename _Functor> |
738 | const _Functor* |
739 | function<_Res(_ArgTypes...)>:: |
740 | target() const noexcept |
741 | { |
742 | if (typeid(_Functor) == target_type() && _M_manager) |
743 | { |
744 | _Any_data __ptr; |
745 | _M_manager(__ptr, _M_functor, __get_functor_ptr); |
746 | return __ptr._M_access<const _Functor*>(); |
747 | } |
748 | else |
749 | return nullptr; |
750 | } |
751 | #endif |
752 | |
753 | // [20.7.15.2.6] null pointer comparisons |
754 | |
755 | /** |
756 | * @brief Compares a polymorphic function object wrapper against 0 |
757 | * (the NULL pointer). |
758 | * @returns @c true if the wrapper has no target, @c false otherwise |
759 | * |
760 | * This function will not throw an %exception. |
761 | */ |
762 | template<typename _Res, typename... _Args> |
763 | inline bool |
764 | operator==(const function<_Res(_Args...)>& __f, nullptr_t) noexcept |
765 | { return !static_cast<bool>(__f); } |
766 | |
767 | /// @overload |
768 | template<typename _Res, typename... _Args> |
769 | inline bool |
770 | operator==(nullptr_t, const function<_Res(_Args...)>& __f) noexcept |
771 | { return !static_cast<bool>(__f); } |
772 | |
773 | /** |
774 | * @brief Compares a polymorphic function object wrapper against 0 |
775 | * (the NULL pointer). |
776 | * @returns @c false if the wrapper has no target, @c true otherwise |
777 | * |
778 | * This function will not throw an %exception. |
779 | */ |
780 | template<typename _Res, typename... _Args> |
781 | inline bool |
782 | operator!=(const function<_Res(_Args...)>& __f, nullptr_t) noexcept |
783 | { return static_cast<bool>(__f); } |
784 | |
785 | /// @overload |
786 | template<typename _Res, typename... _Args> |
787 | inline bool |
788 | operator!=(nullptr_t, const function<_Res(_Args...)>& __f) noexcept |
789 | { return static_cast<bool>(__f); } |
790 | |
791 | |
792 | // [20.7.15.2.7] specialized algorithms |
793 | |
794 | /** |
795 | * @brief Swap the targets of two polymorphic function object wrappers. |
796 | * |
797 | * This function will not throw an %exception. |
798 | */ |
799 | // _GLIBCXX_RESOLVE_LIB_DEFECTS |
800 | // 2062. Effect contradictions w/o no-throw guarantee of std::function swaps |
801 | template<typename _Res, typename... _Args> |
802 | inline void |
803 | swap(function<_Res(_Args...)>& __x, function<_Res(_Args...)>& __y) noexcept |
804 | { __x.swap(__y); } |
805 | |
806 | _GLIBCXX_END_NAMESPACE_VERSION |
807 | } // namespace std |
808 | |
809 | #endif // C++11 |
810 | |
811 | #endif // _GLIBCXX_STD_FUNCTION_H |
1 | //===- Memory.h -------------------------------------------------*- C++ -*-===// | |||
2 | // | |||
3 | // The LLVM Linker | |||
4 | // | |||
5 | // This file is distributed under the University of Illinois Open Source | |||
6 | // License. See LICENSE.TXT for details. | |||
7 | // | |||
8 | //===----------------------------------------------------------------------===// | |||
9 | // | |||
10 | // This file defines arena allocators. | |||
11 | // | |||
12 | // Almost all large objects, such as files, sections or symbols, are | |||
13 | // used for the entire lifetime of the linker once they are created. | |||
14 | // This usage characteristic makes arena allocator an attractive choice | |||
15 | // where the entire linker is one arena. With an arena, newly created | |||
16 | // objects belong to the arena and freed all at once when everything is done. | |||
17 | // Arena allocators are efficient and easy to understand. | |||
18 | // Most objects are allocated using the arena allocators defined by this file. | |||
19 | // | |||
20 | //===----------------------------------------------------------------------===// | |||
21 | ||||
22 | #ifndef LLD_COMMON_MEMORY_H | |||
23 | #define LLD_COMMON_MEMORY_H | |||
24 | ||||
25 | #include "llvm/Support/Allocator.h" | |||
26 | #include "llvm/Support/StringSaver.h" | |||
27 | #include <vector> | |||
28 | ||||
29 | namespace lld { | |||
30 | ||||
31 | // Use this arena if your object doesn't have a destructor. | |||
32 | extern llvm::BumpPtrAllocator BAlloc; | |||
33 | extern llvm::StringSaver Saver; | |||
34 | ||||
35 | void freeArena(); | |||
36 | ||||
37 | // These two classes are hack to keep track of all | |||
38 | // SpecificBumpPtrAllocator instances. | |||
39 | struct SpecificAllocBase { | |||
40 | SpecificAllocBase() { Instances.push_back(this); } | |||
41 | virtual ~SpecificAllocBase() = default; | |||
42 | virtual void reset() = 0; | |||
43 | static std::vector<SpecificAllocBase *> Instances; | |||
44 | }; | |||
45 | ||||
46 | template <class T> struct SpecificAlloc : public SpecificAllocBase { | |||
47 | void reset() override { Alloc.DestroyAll(); } | |||
48 | llvm::SpecificBumpPtrAllocator<T> Alloc; | |||
49 | }; | |||
50 | ||||
51 | // Use this arena if your object has a destructor. | |||
52 | // Your destructor will be invoked from freeArena(). | |||
53 | template <typename T, typename... U> T *make(U &&... Args) { | |||
54 | static SpecificAlloc<T> Alloc; | |||
55 | return new (Alloc.Alloc.Allocate()) T(std::forward<U>(Args)...); | |||
| ||||
56 | } | |||
57 | ||||
58 | } // namespace lld | |||
59 | ||||
60 | #endif |