1*2ec34544SRui Ueyama //===- ScriptParser.cpp ---------------------------------------------------===// 2*2ec34544SRui Ueyama // 3*2ec34544SRui Ueyama // The LLVM Linker 4*2ec34544SRui Ueyama // 5*2ec34544SRui Ueyama // This file is distributed under the University of Illinois Open Source 6*2ec34544SRui Ueyama // License. See LICENSE.TXT for details. 7*2ec34544SRui Ueyama // 8*2ec34544SRui Ueyama //===----------------------------------------------------------------------===// 9*2ec34544SRui Ueyama 10*2ec34544SRui Ueyama #include "ScriptParser.h" 11*2ec34544SRui Ueyama #include "Config.h" 12*2ec34544SRui Ueyama #include "Driver.h" 13*2ec34544SRui Ueyama #include "InputSection.h" 14*2ec34544SRui Ueyama #include "LinkerScript.h" 15*2ec34544SRui Ueyama #include "Memory.h" 16*2ec34544SRui Ueyama #include "OutputSections.h" 17*2ec34544SRui Ueyama #include "ScriptLexer.h" 18*2ec34544SRui Ueyama #include "Symbols.h" 19*2ec34544SRui Ueyama #include "Target.h" 20*2ec34544SRui Ueyama #include "llvm/ADT/SmallString.h" 21*2ec34544SRui Ueyama #include "llvm/ADT/StringRef.h" 22*2ec34544SRui Ueyama #include "llvm/ADT/StringSwitch.h" 23*2ec34544SRui Ueyama #include "llvm/Support/Casting.h" 24*2ec34544SRui Ueyama #include "llvm/Support/ELF.h" 25*2ec34544SRui Ueyama #include "llvm/Support/ErrorHandling.h" 26*2ec34544SRui Ueyama #include "llvm/Support/FileSystem.h" 27*2ec34544SRui Ueyama #include "llvm/Support/Path.h" 28*2ec34544SRui Ueyama #include <cassert> 29*2ec34544SRui Ueyama #include <limits> 30*2ec34544SRui Ueyama #include <vector> 31*2ec34544SRui Ueyama 32*2ec34544SRui Ueyama using namespace llvm; 33*2ec34544SRui Ueyama using namespace llvm::ELF; 34*2ec34544SRui Ueyama using namespace lld; 35*2ec34544SRui Ueyama using namespace lld::elf; 36*2ec34544SRui Ueyama 37*2ec34544SRui Ueyama static bool isUnderSysroot(StringRef Path); 38*2ec34544SRui Ueyama 39*2ec34544SRui Ueyama class elf::ScriptParser final : ScriptLexer { 40*2ec34544SRui Ueyama public: 41*2ec34544SRui Ueyama ScriptParser(MemoryBufferRef MB) 42*2ec34544SRui Ueyama : ScriptLexer(MB), 43*2ec34544SRui Ueyama IsUnderSysroot(isUnderSysroot(MB.getBufferIdentifier())) {} 44*2ec34544SRui Ueyama 45*2ec34544SRui Ueyama void readLinkerScript(); 46*2ec34544SRui Ueyama void readVersionScript(); 47*2ec34544SRui Ueyama void readDynamicList(); 48*2ec34544SRui Ueyama 49*2ec34544SRui Ueyama private: 50*2ec34544SRui Ueyama void addFile(StringRef Path); 51*2ec34544SRui Ueyama 52*2ec34544SRui Ueyama void readAsNeeded(); 53*2ec34544SRui Ueyama void readEntry(); 54*2ec34544SRui Ueyama void readExtern(); 55*2ec34544SRui Ueyama void readGroup(); 56*2ec34544SRui Ueyama void readInclude(); 57*2ec34544SRui Ueyama void readMemory(); 58*2ec34544SRui Ueyama void readOutput(); 59*2ec34544SRui Ueyama void readOutputArch(); 60*2ec34544SRui Ueyama void readOutputFormat(); 61*2ec34544SRui Ueyama void readPhdrs(); 62*2ec34544SRui Ueyama void readSearchDir(); 63*2ec34544SRui Ueyama void readSections(); 64*2ec34544SRui Ueyama void readVersion(); 65*2ec34544SRui Ueyama void readVersionScriptCommand(); 66*2ec34544SRui Ueyama 67*2ec34544SRui Ueyama SymbolAssignment *readAssignment(StringRef Name); 68*2ec34544SRui Ueyama BytesDataCommand *readBytesDataCommand(StringRef Tok); 69*2ec34544SRui Ueyama uint32_t readFill(); 70*2ec34544SRui Ueyama OutputSectionCommand *readOutputSectionDescription(StringRef OutSec); 71*2ec34544SRui Ueyama uint32_t readOutputSectionFiller(StringRef Tok); 72*2ec34544SRui Ueyama std::vector<StringRef> readOutputSectionPhdrs(); 73*2ec34544SRui Ueyama InputSectionDescription *readInputSectionDescription(StringRef Tok); 74*2ec34544SRui Ueyama StringMatcher readFilePatterns(); 75*2ec34544SRui Ueyama std::vector<SectionPattern> readInputSectionsList(); 76*2ec34544SRui Ueyama InputSectionDescription *readInputSectionRules(StringRef FilePattern); 77*2ec34544SRui Ueyama unsigned readPhdrType(); 78*2ec34544SRui Ueyama SortSectionPolicy readSortKind(); 79*2ec34544SRui Ueyama SymbolAssignment *readProvideHidden(bool Provide, bool Hidden); 80*2ec34544SRui Ueyama SymbolAssignment *readProvideOrAssignment(StringRef Tok); 81*2ec34544SRui Ueyama void readSort(); 82*2ec34544SRui Ueyama Expr readAssert(); 83*2ec34544SRui Ueyama 84*2ec34544SRui Ueyama uint64_t readMemoryAssignment(StringRef, StringRef, StringRef); 85*2ec34544SRui Ueyama std::pair<uint32_t, uint32_t> readMemoryAttributes(); 86*2ec34544SRui Ueyama 87*2ec34544SRui Ueyama Expr readExpr(); 88*2ec34544SRui Ueyama Expr readExpr1(Expr Lhs, int MinPrec); 89*2ec34544SRui Ueyama StringRef readParenLiteral(); 90*2ec34544SRui Ueyama Expr readPrimary(); 91*2ec34544SRui Ueyama Expr readTernary(Expr Cond); 92*2ec34544SRui Ueyama Expr readParenExpr(); 93*2ec34544SRui Ueyama 94*2ec34544SRui Ueyama // For parsing version script. 95*2ec34544SRui Ueyama std::vector<SymbolVersion> readVersionExtern(); 96*2ec34544SRui Ueyama void readAnonymousDeclaration(); 97*2ec34544SRui Ueyama void readVersionDeclaration(StringRef VerStr); 98*2ec34544SRui Ueyama 99*2ec34544SRui Ueyama std::pair<std::vector<SymbolVersion>, std::vector<SymbolVersion>> 100*2ec34544SRui Ueyama readSymbols(); 101*2ec34544SRui Ueyama 102*2ec34544SRui Ueyama bool IsUnderSysroot; 103*2ec34544SRui Ueyama }; 104*2ec34544SRui Ueyama 105*2ec34544SRui Ueyama static bool isUnderSysroot(StringRef Path) { 106*2ec34544SRui Ueyama if (Config->Sysroot == "") 107*2ec34544SRui Ueyama return false; 108*2ec34544SRui Ueyama for (; !Path.empty(); Path = sys::path::parent_path(Path)) 109*2ec34544SRui Ueyama if (sys::fs::equivalent(Config->Sysroot, Path)) 110*2ec34544SRui Ueyama return true; 111*2ec34544SRui Ueyama return false; 112*2ec34544SRui Ueyama } 113*2ec34544SRui Ueyama 114*2ec34544SRui Ueyama // Some operations only support one non absolute value. Move the 115*2ec34544SRui Ueyama // absolute one to the right hand side for convenience. 116*2ec34544SRui Ueyama static void moveAbsRight(ExprValue &A, ExprValue &B) { 117*2ec34544SRui Ueyama if (A.isAbsolute()) 118*2ec34544SRui Ueyama std::swap(A, B); 119*2ec34544SRui Ueyama if (!B.isAbsolute()) 120*2ec34544SRui Ueyama error("At least one side of the expression must be absolute"); 121*2ec34544SRui Ueyama } 122*2ec34544SRui Ueyama 123*2ec34544SRui Ueyama static ExprValue add(ExprValue A, ExprValue B) { 124*2ec34544SRui Ueyama moveAbsRight(A, B); 125*2ec34544SRui Ueyama return {A.Sec, A.ForceAbsolute, A.Val + B.getValue()}; 126*2ec34544SRui Ueyama } 127*2ec34544SRui Ueyama 128*2ec34544SRui Ueyama static ExprValue sub(ExprValue A, ExprValue B) { 129*2ec34544SRui Ueyama return {A.Sec, A.Val - B.getValue()}; 130*2ec34544SRui Ueyama } 131*2ec34544SRui Ueyama 132*2ec34544SRui Ueyama static ExprValue mul(ExprValue A, ExprValue B) { 133*2ec34544SRui Ueyama return A.getValue() * B.getValue(); 134*2ec34544SRui Ueyama } 135*2ec34544SRui Ueyama 136*2ec34544SRui Ueyama static ExprValue div(ExprValue A, ExprValue B) { 137*2ec34544SRui Ueyama if (uint64_t BV = B.getValue()) 138*2ec34544SRui Ueyama return A.getValue() / BV; 139*2ec34544SRui Ueyama error("division by zero"); 140*2ec34544SRui Ueyama return 0; 141*2ec34544SRui Ueyama } 142*2ec34544SRui Ueyama 143*2ec34544SRui Ueyama static ExprValue leftShift(ExprValue A, ExprValue B) { 144*2ec34544SRui Ueyama return A.getValue() << B.getValue(); 145*2ec34544SRui Ueyama } 146*2ec34544SRui Ueyama 147*2ec34544SRui Ueyama static ExprValue rightShift(ExprValue A, ExprValue B) { 148*2ec34544SRui Ueyama return A.getValue() >> B.getValue(); 149*2ec34544SRui Ueyama } 150*2ec34544SRui Ueyama 151*2ec34544SRui Ueyama static ExprValue bitAnd(ExprValue A, ExprValue B) { 152*2ec34544SRui Ueyama moveAbsRight(A, B); 153*2ec34544SRui Ueyama return {A.Sec, A.ForceAbsolute, 154*2ec34544SRui Ueyama (A.getValue() & B.getValue()) - A.getSecAddr()}; 155*2ec34544SRui Ueyama } 156*2ec34544SRui Ueyama 157*2ec34544SRui Ueyama static ExprValue bitOr(ExprValue A, ExprValue B) { 158*2ec34544SRui Ueyama moveAbsRight(A, B); 159*2ec34544SRui Ueyama return {A.Sec, A.ForceAbsolute, 160*2ec34544SRui Ueyama (A.getValue() | B.getValue()) - A.getSecAddr()}; 161*2ec34544SRui Ueyama } 162*2ec34544SRui Ueyama 163*2ec34544SRui Ueyama static ExprValue bitNot(ExprValue A) { return ~A.getValue(); } 164*2ec34544SRui Ueyama static ExprValue minus(ExprValue A) { return -A.getValue(); } 165*2ec34544SRui Ueyama 166*2ec34544SRui Ueyama void ScriptParser::readDynamicList() { 167*2ec34544SRui Ueyama expect("{"); 168*2ec34544SRui Ueyama readAnonymousDeclaration(); 169*2ec34544SRui Ueyama if (!atEOF()) 170*2ec34544SRui Ueyama setError("EOF expected, but got " + next()); 171*2ec34544SRui Ueyama } 172*2ec34544SRui Ueyama 173*2ec34544SRui Ueyama void ScriptParser::readVersionScript() { 174*2ec34544SRui Ueyama readVersionScriptCommand(); 175*2ec34544SRui Ueyama if (!atEOF()) 176*2ec34544SRui Ueyama setError("EOF expected, but got " + next()); 177*2ec34544SRui Ueyama } 178*2ec34544SRui Ueyama 179*2ec34544SRui Ueyama void ScriptParser::readVersionScriptCommand() { 180*2ec34544SRui Ueyama if (consume("{")) { 181*2ec34544SRui Ueyama readAnonymousDeclaration(); 182*2ec34544SRui Ueyama return; 183*2ec34544SRui Ueyama } 184*2ec34544SRui Ueyama 185*2ec34544SRui Ueyama while (!atEOF() && !Error && peek() != "}") { 186*2ec34544SRui Ueyama StringRef VerStr = next(); 187*2ec34544SRui Ueyama if (VerStr == "{") { 188*2ec34544SRui Ueyama setError("anonymous version definition is used in " 189*2ec34544SRui Ueyama "combination with other version definitions"); 190*2ec34544SRui Ueyama return; 191*2ec34544SRui Ueyama } 192*2ec34544SRui Ueyama expect("{"); 193*2ec34544SRui Ueyama readVersionDeclaration(VerStr); 194*2ec34544SRui Ueyama } 195*2ec34544SRui Ueyama } 196*2ec34544SRui Ueyama 197*2ec34544SRui Ueyama void ScriptParser::readVersion() { 198*2ec34544SRui Ueyama expect("{"); 199*2ec34544SRui Ueyama readVersionScriptCommand(); 200*2ec34544SRui Ueyama expect("}"); 201*2ec34544SRui Ueyama } 202*2ec34544SRui Ueyama 203*2ec34544SRui Ueyama void ScriptParser::readLinkerScript() { 204*2ec34544SRui Ueyama while (!atEOF()) { 205*2ec34544SRui Ueyama StringRef Tok = next(); 206*2ec34544SRui Ueyama if (Tok == ";") 207*2ec34544SRui Ueyama continue; 208*2ec34544SRui Ueyama 209*2ec34544SRui Ueyama if (Tok == "ASSERT") { 210*2ec34544SRui Ueyama Script->Opt.Commands.push_back(make<AssertCommand>(readAssert())); 211*2ec34544SRui Ueyama } else if (Tok == "ENTRY") { 212*2ec34544SRui Ueyama readEntry(); 213*2ec34544SRui Ueyama } else if (Tok == "EXTERN") { 214*2ec34544SRui Ueyama readExtern(); 215*2ec34544SRui Ueyama } else if (Tok == "GROUP" || Tok == "INPUT") { 216*2ec34544SRui Ueyama readGroup(); 217*2ec34544SRui Ueyama } else if (Tok == "INCLUDE") { 218*2ec34544SRui Ueyama readInclude(); 219*2ec34544SRui Ueyama } else if (Tok == "MEMORY") { 220*2ec34544SRui Ueyama readMemory(); 221*2ec34544SRui Ueyama } else if (Tok == "OUTPUT") { 222*2ec34544SRui Ueyama readOutput(); 223*2ec34544SRui Ueyama } else if (Tok == "OUTPUT_ARCH") { 224*2ec34544SRui Ueyama readOutputArch(); 225*2ec34544SRui Ueyama } else if (Tok == "OUTPUT_FORMAT") { 226*2ec34544SRui Ueyama readOutputFormat(); 227*2ec34544SRui Ueyama } else if (Tok == "PHDRS") { 228*2ec34544SRui Ueyama readPhdrs(); 229*2ec34544SRui Ueyama } else if (Tok == "SEARCH_DIR") { 230*2ec34544SRui Ueyama readSearchDir(); 231*2ec34544SRui Ueyama } else if (Tok == "SECTIONS") { 232*2ec34544SRui Ueyama readSections(); 233*2ec34544SRui Ueyama } else if (Tok == "VERSION") { 234*2ec34544SRui Ueyama readVersion(); 235*2ec34544SRui Ueyama } else if (SymbolAssignment *Cmd = readProvideOrAssignment(Tok)) { 236*2ec34544SRui Ueyama Script->Opt.Commands.push_back(Cmd); 237*2ec34544SRui Ueyama } else { 238*2ec34544SRui Ueyama setError("unknown directive: " + Tok); 239*2ec34544SRui Ueyama } 240*2ec34544SRui Ueyama } 241*2ec34544SRui Ueyama } 242*2ec34544SRui Ueyama 243*2ec34544SRui Ueyama void ScriptParser::addFile(StringRef S) { 244*2ec34544SRui Ueyama if (IsUnderSysroot && S.startswith("/")) { 245*2ec34544SRui Ueyama SmallString<128> PathData; 246*2ec34544SRui Ueyama StringRef Path = (Config->Sysroot + S).toStringRef(PathData); 247*2ec34544SRui Ueyama if (sys::fs::exists(Path)) { 248*2ec34544SRui Ueyama Driver->addFile(Saver.save(Path)); 249*2ec34544SRui Ueyama return; 250*2ec34544SRui Ueyama } 251*2ec34544SRui Ueyama } 252*2ec34544SRui Ueyama 253*2ec34544SRui Ueyama if (sys::path::is_absolute(S)) { 254*2ec34544SRui Ueyama Driver->addFile(S); 255*2ec34544SRui Ueyama } else if (S.startswith("=")) { 256*2ec34544SRui Ueyama if (Config->Sysroot.empty()) 257*2ec34544SRui Ueyama Driver->addFile(S.substr(1)); 258*2ec34544SRui Ueyama else 259*2ec34544SRui Ueyama Driver->addFile(Saver.save(Config->Sysroot + "/" + S.substr(1))); 260*2ec34544SRui Ueyama } else if (S.startswith("-l")) { 261*2ec34544SRui Ueyama Driver->addLibrary(S.substr(2)); 262*2ec34544SRui Ueyama } else if (sys::fs::exists(S)) { 263*2ec34544SRui Ueyama Driver->addFile(S); 264*2ec34544SRui Ueyama } else { 265*2ec34544SRui Ueyama if (Optional<std::string> Path = findFromSearchPaths(S)) 266*2ec34544SRui Ueyama Driver->addFile(Saver.save(*Path)); 267*2ec34544SRui Ueyama else 268*2ec34544SRui Ueyama setError("unable to find " + S); 269*2ec34544SRui Ueyama } 270*2ec34544SRui Ueyama } 271*2ec34544SRui Ueyama 272*2ec34544SRui Ueyama void ScriptParser::readAsNeeded() { 273*2ec34544SRui Ueyama expect("("); 274*2ec34544SRui Ueyama bool Orig = Config->AsNeeded; 275*2ec34544SRui Ueyama Config->AsNeeded = true; 276*2ec34544SRui Ueyama while (!Error && !consume(")")) 277*2ec34544SRui Ueyama addFile(unquote(next())); 278*2ec34544SRui Ueyama Config->AsNeeded = Orig; 279*2ec34544SRui Ueyama } 280*2ec34544SRui Ueyama 281*2ec34544SRui Ueyama void ScriptParser::readEntry() { 282*2ec34544SRui Ueyama // -e <symbol> takes predecence over ENTRY(<symbol>). 283*2ec34544SRui Ueyama expect("("); 284*2ec34544SRui Ueyama StringRef Tok = next(); 285*2ec34544SRui Ueyama if (Config->Entry.empty()) 286*2ec34544SRui Ueyama Config->Entry = Tok; 287*2ec34544SRui Ueyama expect(")"); 288*2ec34544SRui Ueyama } 289*2ec34544SRui Ueyama 290*2ec34544SRui Ueyama void ScriptParser::readExtern() { 291*2ec34544SRui Ueyama expect("("); 292*2ec34544SRui Ueyama while (!Error && !consume(")")) 293*2ec34544SRui Ueyama Config->Undefined.push_back(next()); 294*2ec34544SRui Ueyama } 295*2ec34544SRui Ueyama 296*2ec34544SRui Ueyama void ScriptParser::readGroup() { 297*2ec34544SRui Ueyama expect("("); 298*2ec34544SRui Ueyama while (!Error && !consume(")")) { 299*2ec34544SRui Ueyama StringRef Tok = next(); 300*2ec34544SRui Ueyama if (Tok == "AS_NEEDED") 301*2ec34544SRui Ueyama readAsNeeded(); 302*2ec34544SRui Ueyama else 303*2ec34544SRui Ueyama addFile(unquote(Tok)); 304*2ec34544SRui Ueyama } 305*2ec34544SRui Ueyama } 306*2ec34544SRui Ueyama 307*2ec34544SRui Ueyama void ScriptParser::readInclude() { 308*2ec34544SRui Ueyama StringRef Tok = unquote(next()); 309*2ec34544SRui Ueyama 310*2ec34544SRui Ueyama // https://sourceware.org/binutils/docs/ld/File-Commands.html: 311*2ec34544SRui Ueyama // The file will be searched for in the current directory, and in any 312*2ec34544SRui Ueyama // directory specified with the -L option. 313*2ec34544SRui Ueyama if (sys::fs::exists(Tok)) { 314*2ec34544SRui Ueyama if (Optional<MemoryBufferRef> MB = readFile(Tok)) 315*2ec34544SRui Ueyama tokenize(*MB); 316*2ec34544SRui Ueyama return; 317*2ec34544SRui Ueyama } 318*2ec34544SRui Ueyama if (Optional<std::string> Path = findFromSearchPaths(Tok)) { 319*2ec34544SRui Ueyama if (Optional<MemoryBufferRef> MB = readFile(*Path)) 320*2ec34544SRui Ueyama tokenize(*MB); 321*2ec34544SRui Ueyama return; 322*2ec34544SRui Ueyama } 323*2ec34544SRui Ueyama setError("cannot open " + Tok); 324*2ec34544SRui Ueyama } 325*2ec34544SRui Ueyama 326*2ec34544SRui Ueyama void ScriptParser::readOutput() { 327*2ec34544SRui Ueyama // -o <file> takes predecence over OUTPUT(<file>). 328*2ec34544SRui Ueyama expect("("); 329*2ec34544SRui Ueyama StringRef Tok = next(); 330*2ec34544SRui Ueyama if (Config->OutputFile.empty()) 331*2ec34544SRui Ueyama Config->OutputFile = unquote(Tok); 332*2ec34544SRui Ueyama expect(")"); 333*2ec34544SRui Ueyama } 334*2ec34544SRui Ueyama 335*2ec34544SRui Ueyama void ScriptParser::readOutputArch() { 336*2ec34544SRui Ueyama // OUTPUT_ARCH is ignored for now. 337*2ec34544SRui Ueyama expect("("); 338*2ec34544SRui Ueyama while (!Error && !consume(")")) 339*2ec34544SRui Ueyama skip(); 340*2ec34544SRui Ueyama } 341*2ec34544SRui Ueyama 342*2ec34544SRui Ueyama void ScriptParser::readOutputFormat() { 343*2ec34544SRui Ueyama // Error checking only for now. 344*2ec34544SRui Ueyama expect("("); 345*2ec34544SRui Ueyama skip(); 346*2ec34544SRui Ueyama StringRef Tok = next(); 347*2ec34544SRui Ueyama if (Tok == ")") 348*2ec34544SRui Ueyama return; 349*2ec34544SRui Ueyama if (Tok != ",") { 350*2ec34544SRui Ueyama setError("unexpected token: " + Tok); 351*2ec34544SRui Ueyama return; 352*2ec34544SRui Ueyama } 353*2ec34544SRui Ueyama skip(); 354*2ec34544SRui Ueyama expect(","); 355*2ec34544SRui Ueyama skip(); 356*2ec34544SRui Ueyama expect(")"); 357*2ec34544SRui Ueyama } 358*2ec34544SRui Ueyama 359*2ec34544SRui Ueyama void ScriptParser::readPhdrs() { 360*2ec34544SRui Ueyama expect("{"); 361*2ec34544SRui Ueyama while (!Error && !consume("}")) { 362*2ec34544SRui Ueyama StringRef Tok = next(); 363*2ec34544SRui Ueyama Script->Opt.PhdrsCommands.push_back( 364*2ec34544SRui Ueyama {Tok, PT_NULL, false, false, UINT_MAX, nullptr}); 365*2ec34544SRui Ueyama PhdrsCommand &PhdrCmd = Script->Opt.PhdrsCommands.back(); 366*2ec34544SRui Ueyama 367*2ec34544SRui Ueyama PhdrCmd.Type = readPhdrType(); 368*2ec34544SRui Ueyama do { 369*2ec34544SRui Ueyama Tok = next(); 370*2ec34544SRui Ueyama if (Tok == ";") 371*2ec34544SRui Ueyama break; 372*2ec34544SRui Ueyama if (Tok == "FILEHDR") 373*2ec34544SRui Ueyama PhdrCmd.HasFilehdr = true; 374*2ec34544SRui Ueyama else if (Tok == "PHDRS") 375*2ec34544SRui Ueyama PhdrCmd.HasPhdrs = true; 376*2ec34544SRui Ueyama else if (Tok == "AT") 377*2ec34544SRui Ueyama PhdrCmd.LMAExpr = readParenExpr(); 378*2ec34544SRui Ueyama else if (Tok == "FLAGS") { 379*2ec34544SRui Ueyama expect("("); 380*2ec34544SRui Ueyama // Passing 0 for the value of dot is a bit of a hack. It means that 381*2ec34544SRui Ueyama // we accept expressions like ".|1". 382*2ec34544SRui Ueyama PhdrCmd.Flags = readExpr()().getValue(); 383*2ec34544SRui Ueyama expect(")"); 384*2ec34544SRui Ueyama } else 385*2ec34544SRui Ueyama setError("unexpected header attribute: " + Tok); 386*2ec34544SRui Ueyama } while (!Error); 387*2ec34544SRui Ueyama } 388*2ec34544SRui Ueyama } 389*2ec34544SRui Ueyama 390*2ec34544SRui Ueyama void ScriptParser::readSearchDir() { 391*2ec34544SRui Ueyama expect("("); 392*2ec34544SRui Ueyama StringRef Tok = next(); 393*2ec34544SRui Ueyama if (!Config->Nostdlib) 394*2ec34544SRui Ueyama Config->SearchPaths.push_back(unquote(Tok)); 395*2ec34544SRui Ueyama expect(")"); 396*2ec34544SRui Ueyama } 397*2ec34544SRui Ueyama 398*2ec34544SRui Ueyama void ScriptParser::readSections() { 399*2ec34544SRui Ueyama Script->Opt.HasSections = true; 400*2ec34544SRui Ueyama // -no-rosegment is used to avoid placing read only non-executable sections in 401*2ec34544SRui Ueyama // their own segment. We do the same if SECTIONS command is present in linker 402*2ec34544SRui Ueyama // script. See comment for computeFlags(). 403*2ec34544SRui Ueyama Config->SingleRoRx = true; 404*2ec34544SRui Ueyama 405*2ec34544SRui Ueyama expect("{"); 406*2ec34544SRui Ueyama while (!Error && !consume("}")) { 407*2ec34544SRui Ueyama StringRef Tok = next(); 408*2ec34544SRui Ueyama BaseCommand *Cmd = readProvideOrAssignment(Tok); 409*2ec34544SRui Ueyama if (!Cmd) { 410*2ec34544SRui Ueyama if (Tok == "ASSERT") 411*2ec34544SRui Ueyama Cmd = make<AssertCommand>(readAssert()); 412*2ec34544SRui Ueyama else 413*2ec34544SRui Ueyama Cmd = readOutputSectionDescription(Tok); 414*2ec34544SRui Ueyama } 415*2ec34544SRui Ueyama Script->Opt.Commands.push_back(Cmd); 416*2ec34544SRui Ueyama } 417*2ec34544SRui Ueyama } 418*2ec34544SRui Ueyama 419*2ec34544SRui Ueyama static int precedence(StringRef Op) { 420*2ec34544SRui Ueyama return StringSwitch<int>(Op) 421*2ec34544SRui Ueyama .Cases("*", "/", 5) 422*2ec34544SRui Ueyama .Cases("+", "-", 4) 423*2ec34544SRui Ueyama .Cases("<<", ">>", 3) 424*2ec34544SRui Ueyama .Cases("<", "<=", ">", ">=", "==", "!=", 2) 425*2ec34544SRui Ueyama .Cases("&", "|", 1) 426*2ec34544SRui Ueyama .Default(-1); 427*2ec34544SRui Ueyama } 428*2ec34544SRui Ueyama 429*2ec34544SRui Ueyama StringMatcher ScriptParser::readFilePatterns() { 430*2ec34544SRui Ueyama std::vector<StringRef> V; 431*2ec34544SRui Ueyama while (!Error && !consume(")")) 432*2ec34544SRui Ueyama V.push_back(next()); 433*2ec34544SRui Ueyama return StringMatcher(V); 434*2ec34544SRui Ueyama } 435*2ec34544SRui Ueyama 436*2ec34544SRui Ueyama SortSectionPolicy ScriptParser::readSortKind() { 437*2ec34544SRui Ueyama if (consume("SORT") || consume("SORT_BY_NAME")) 438*2ec34544SRui Ueyama return SortSectionPolicy::Name; 439*2ec34544SRui Ueyama if (consume("SORT_BY_ALIGNMENT")) 440*2ec34544SRui Ueyama return SortSectionPolicy::Alignment; 441*2ec34544SRui Ueyama if (consume("SORT_BY_INIT_PRIORITY")) 442*2ec34544SRui Ueyama return SortSectionPolicy::Priority; 443*2ec34544SRui Ueyama if (consume("SORT_NONE")) 444*2ec34544SRui Ueyama return SortSectionPolicy::None; 445*2ec34544SRui Ueyama return SortSectionPolicy::Default; 446*2ec34544SRui Ueyama } 447*2ec34544SRui Ueyama 448*2ec34544SRui Ueyama // Method reads a list of sequence of excluded files and section globs given in 449*2ec34544SRui Ueyama // a following form: ((EXCLUDE_FILE(file_pattern+))? section_pattern+)+ 450*2ec34544SRui Ueyama // Example: *(.foo.1 EXCLUDE_FILE (*a.o) .foo.2 EXCLUDE_FILE (*b.o) .foo.3) 451*2ec34544SRui Ueyama // The semantics of that is next: 452*2ec34544SRui Ueyama // * Include .foo.1 from every file. 453*2ec34544SRui Ueyama // * Include .foo.2 from every file but a.o 454*2ec34544SRui Ueyama // * Include .foo.3 from every file but b.o 455*2ec34544SRui Ueyama std::vector<SectionPattern> ScriptParser::readInputSectionsList() { 456*2ec34544SRui Ueyama std::vector<SectionPattern> Ret; 457*2ec34544SRui Ueyama while (!Error && peek() != ")") { 458*2ec34544SRui Ueyama StringMatcher ExcludeFilePat; 459*2ec34544SRui Ueyama if (consume("EXCLUDE_FILE")) { 460*2ec34544SRui Ueyama expect("("); 461*2ec34544SRui Ueyama ExcludeFilePat = readFilePatterns(); 462*2ec34544SRui Ueyama } 463*2ec34544SRui Ueyama 464*2ec34544SRui Ueyama std::vector<StringRef> V; 465*2ec34544SRui Ueyama while (!Error && peek() != ")" && peek() != "EXCLUDE_FILE") 466*2ec34544SRui Ueyama V.push_back(next()); 467*2ec34544SRui Ueyama 468*2ec34544SRui Ueyama if (!V.empty()) 469*2ec34544SRui Ueyama Ret.push_back({std::move(ExcludeFilePat), StringMatcher(V)}); 470*2ec34544SRui Ueyama else 471*2ec34544SRui Ueyama setError("section pattern is expected"); 472*2ec34544SRui Ueyama } 473*2ec34544SRui Ueyama return Ret; 474*2ec34544SRui Ueyama } 475*2ec34544SRui Ueyama 476*2ec34544SRui Ueyama // Reads contents of "SECTIONS" directive. That directive contains a 477*2ec34544SRui Ueyama // list of glob patterns for input sections. The grammar is as follows. 478*2ec34544SRui Ueyama // 479*2ec34544SRui Ueyama // <patterns> ::= <section-list> 480*2ec34544SRui Ueyama // | <sort> "(" <section-list> ")" 481*2ec34544SRui Ueyama // | <sort> "(" <sort> "(" <section-list> ")" ")" 482*2ec34544SRui Ueyama // 483*2ec34544SRui Ueyama // <sort> ::= "SORT" | "SORT_BY_NAME" | "SORT_BY_ALIGNMENT" 484*2ec34544SRui Ueyama // | "SORT_BY_INIT_PRIORITY" | "SORT_NONE" 485*2ec34544SRui Ueyama // 486*2ec34544SRui Ueyama // <section-list> is parsed by readInputSectionsList(). 487*2ec34544SRui Ueyama InputSectionDescription * 488*2ec34544SRui Ueyama ScriptParser::readInputSectionRules(StringRef FilePattern) { 489*2ec34544SRui Ueyama auto *Cmd = make<InputSectionDescription>(FilePattern); 490*2ec34544SRui Ueyama expect("("); 491*2ec34544SRui Ueyama 492*2ec34544SRui Ueyama while (!Error && !consume(")")) { 493*2ec34544SRui Ueyama SortSectionPolicy Outer = readSortKind(); 494*2ec34544SRui Ueyama SortSectionPolicy Inner = SortSectionPolicy::Default; 495*2ec34544SRui Ueyama std::vector<SectionPattern> V; 496*2ec34544SRui Ueyama if (Outer != SortSectionPolicy::Default) { 497*2ec34544SRui Ueyama expect("("); 498*2ec34544SRui Ueyama Inner = readSortKind(); 499*2ec34544SRui Ueyama if (Inner != SortSectionPolicy::Default) { 500*2ec34544SRui Ueyama expect("("); 501*2ec34544SRui Ueyama V = readInputSectionsList(); 502*2ec34544SRui Ueyama expect(")"); 503*2ec34544SRui Ueyama } else { 504*2ec34544SRui Ueyama V = readInputSectionsList(); 505*2ec34544SRui Ueyama } 506*2ec34544SRui Ueyama expect(")"); 507*2ec34544SRui Ueyama } else { 508*2ec34544SRui Ueyama V = readInputSectionsList(); 509*2ec34544SRui Ueyama } 510*2ec34544SRui Ueyama 511*2ec34544SRui Ueyama for (SectionPattern &Pat : V) { 512*2ec34544SRui Ueyama Pat.SortInner = Inner; 513*2ec34544SRui Ueyama Pat.SortOuter = Outer; 514*2ec34544SRui Ueyama } 515*2ec34544SRui Ueyama 516*2ec34544SRui Ueyama std::move(V.begin(), V.end(), std::back_inserter(Cmd->SectionPatterns)); 517*2ec34544SRui Ueyama } 518*2ec34544SRui Ueyama return Cmd; 519*2ec34544SRui Ueyama } 520*2ec34544SRui Ueyama 521*2ec34544SRui Ueyama InputSectionDescription * 522*2ec34544SRui Ueyama ScriptParser::readInputSectionDescription(StringRef Tok) { 523*2ec34544SRui Ueyama // Input section wildcard can be surrounded by KEEP. 524*2ec34544SRui Ueyama // https://sourceware.org/binutils/docs/ld/Input-Section-Keep.html#Input-Section-Keep 525*2ec34544SRui Ueyama if (Tok == "KEEP") { 526*2ec34544SRui Ueyama expect("("); 527*2ec34544SRui Ueyama StringRef FilePattern = next(); 528*2ec34544SRui Ueyama InputSectionDescription *Cmd = readInputSectionRules(FilePattern); 529*2ec34544SRui Ueyama expect(")"); 530*2ec34544SRui Ueyama Script->Opt.KeptSections.push_back(Cmd); 531*2ec34544SRui Ueyama return Cmd; 532*2ec34544SRui Ueyama } 533*2ec34544SRui Ueyama return readInputSectionRules(Tok); 534*2ec34544SRui Ueyama } 535*2ec34544SRui Ueyama 536*2ec34544SRui Ueyama void ScriptParser::readSort() { 537*2ec34544SRui Ueyama expect("("); 538*2ec34544SRui Ueyama expect("CONSTRUCTORS"); 539*2ec34544SRui Ueyama expect(")"); 540*2ec34544SRui Ueyama } 541*2ec34544SRui Ueyama 542*2ec34544SRui Ueyama Expr ScriptParser::readAssert() { 543*2ec34544SRui Ueyama expect("("); 544*2ec34544SRui Ueyama Expr E = readExpr(); 545*2ec34544SRui Ueyama expect(","); 546*2ec34544SRui Ueyama StringRef Msg = unquote(next()); 547*2ec34544SRui Ueyama expect(")"); 548*2ec34544SRui Ueyama return [=] { 549*2ec34544SRui Ueyama if (!E().getValue()) 550*2ec34544SRui Ueyama error(Msg); 551*2ec34544SRui Ueyama return Script->getDot(); 552*2ec34544SRui Ueyama }; 553*2ec34544SRui Ueyama } 554*2ec34544SRui Ueyama 555*2ec34544SRui Ueyama // Reads a FILL(expr) command. We handle the FILL command as an 556*2ec34544SRui Ueyama // alias for =fillexp section attribute, which is different from 557*2ec34544SRui Ueyama // what GNU linkers do. 558*2ec34544SRui Ueyama // https://sourceware.org/binutils/docs/ld/Output-Section-Data.html 559*2ec34544SRui Ueyama uint32_t ScriptParser::readFill() { 560*2ec34544SRui Ueyama expect("("); 561*2ec34544SRui Ueyama uint32_t V = readOutputSectionFiller(next()); 562*2ec34544SRui Ueyama expect(")"); 563*2ec34544SRui Ueyama expect(";"); 564*2ec34544SRui Ueyama return V; 565*2ec34544SRui Ueyama } 566*2ec34544SRui Ueyama 567*2ec34544SRui Ueyama OutputSectionCommand * 568*2ec34544SRui Ueyama ScriptParser::readOutputSectionDescription(StringRef OutSec) { 569*2ec34544SRui Ueyama OutputSectionCommand *Cmd = make<OutputSectionCommand>(OutSec); 570*2ec34544SRui Ueyama Cmd->Location = getCurrentLocation(); 571*2ec34544SRui Ueyama 572*2ec34544SRui Ueyama // Read an address expression. 573*2ec34544SRui Ueyama // https://sourceware.org/binutils/docs/ld/Output-Section-Address.html#Output-Section-Address 574*2ec34544SRui Ueyama if (peek() != ":") 575*2ec34544SRui Ueyama Cmd->AddrExpr = readExpr(); 576*2ec34544SRui Ueyama 577*2ec34544SRui Ueyama expect(":"); 578*2ec34544SRui Ueyama 579*2ec34544SRui Ueyama if (consume("AT")) 580*2ec34544SRui Ueyama Cmd->LMAExpr = readParenExpr(); 581*2ec34544SRui Ueyama if (consume("ALIGN")) 582*2ec34544SRui Ueyama Cmd->AlignExpr = readParenExpr(); 583*2ec34544SRui Ueyama if (consume("SUBALIGN")) 584*2ec34544SRui Ueyama Cmd->SubalignExpr = readParenExpr(); 585*2ec34544SRui Ueyama 586*2ec34544SRui Ueyama // Parse constraints. 587*2ec34544SRui Ueyama if (consume("ONLY_IF_RO")) 588*2ec34544SRui Ueyama Cmd->Constraint = ConstraintKind::ReadOnly; 589*2ec34544SRui Ueyama if (consume("ONLY_IF_RW")) 590*2ec34544SRui Ueyama Cmd->Constraint = ConstraintKind::ReadWrite; 591*2ec34544SRui Ueyama expect("{"); 592*2ec34544SRui Ueyama 593*2ec34544SRui Ueyama while (!Error && !consume("}")) { 594*2ec34544SRui Ueyama StringRef Tok = next(); 595*2ec34544SRui Ueyama if (Tok == ";") { 596*2ec34544SRui Ueyama // Empty commands are allowed. Do nothing here. 597*2ec34544SRui Ueyama } else if (SymbolAssignment *Assignment = readProvideOrAssignment(Tok)) { 598*2ec34544SRui Ueyama Cmd->Commands.push_back(Assignment); 599*2ec34544SRui Ueyama } else if (BytesDataCommand *Data = readBytesDataCommand(Tok)) { 600*2ec34544SRui Ueyama Cmd->Commands.push_back(Data); 601*2ec34544SRui Ueyama } else if (Tok == "ASSERT") { 602*2ec34544SRui Ueyama Cmd->Commands.push_back(make<AssertCommand>(readAssert())); 603*2ec34544SRui Ueyama expect(";"); 604*2ec34544SRui Ueyama } else if (Tok == "CONSTRUCTORS") { 605*2ec34544SRui Ueyama // CONSTRUCTORS is a keyword to make the linker recognize C++ ctors/dtors 606*2ec34544SRui Ueyama // by name. This is for very old file formats such as ECOFF/XCOFF. 607*2ec34544SRui Ueyama // For ELF, we should ignore. 608*2ec34544SRui Ueyama } else if (Tok == "FILL") { 609*2ec34544SRui Ueyama Cmd->Filler = readFill(); 610*2ec34544SRui Ueyama } else if (Tok == "SORT") { 611*2ec34544SRui Ueyama readSort(); 612*2ec34544SRui Ueyama } else if (peek() == "(") { 613*2ec34544SRui Ueyama Cmd->Commands.push_back(readInputSectionDescription(Tok)); 614*2ec34544SRui Ueyama } else { 615*2ec34544SRui Ueyama setError("unknown command " + Tok); 616*2ec34544SRui Ueyama } 617*2ec34544SRui Ueyama } 618*2ec34544SRui Ueyama 619*2ec34544SRui Ueyama if (consume(">")) 620*2ec34544SRui Ueyama Cmd->MemoryRegionName = next(); 621*2ec34544SRui Ueyama 622*2ec34544SRui Ueyama Cmd->Phdrs = readOutputSectionPhdrs(); 623*2ec34544SRui Ueyama 624*2ec34544SRui Ueyama if (consume("=")) 625*2ec34544SRui Ueyama Cmd->Filler = readOutputSectionFiller(next()); 626*2ec34544SRui Ueyama else if (peek().startswith("=")) 627*2ec34544SRui Ueyama Cmd->Filler = readOutputSectionFiller(next().drop_front()); 628*2ec34544SRui Ueyama 629*2ec34544SRui Ueyama // Consume optional comma following output section command. 630*2ec34544SRui Ueyama consume(","); 631*2ec34544SRui Ueyama 632*2ec34544SRui Ueyama return Cmd; 633*2ec34544SRui Ueyama } 634*2ec34544SRui Ueyama 635*2ec34544SRui Ueyama // Read "=<number>" where <number> is an octal/decimal/hexadecimal number. 636*2ec34544SRui Ueyama // https://sourceware.org/binutils/docs/ld/Output-Section-Fill.html 637*2ec34544SRui Ueyama // 638*2ec34544SRui Ueyama // ld.gold is not fully compatible with ld.bfd. ld.bfd handles 639*2ec34544SRui Ueyama // hexstrings as blobs of arbitrary sizes, while ld.gold handles them 640*2ec34544SRui Ueyama // as 32-bit big-endian values. We will do the same as ld.gold does 641*2ec34544SRui Ueyama // because it's simpler than what ld.bfd does. 642*2ec34544SRui Ueyama uint32_t ScriptParser::readOutputSectionFiller(StringRef Tok) { 643*2ec34544SRui Ueyama uint32_t V; 644*2ec34544SRui Ueyama if (!Tok.getAsInteger(0, V)) 645*2ec34544SRui Ueyama return V; 646*2ec34544SRui Ueyama setError("invalid filler expression: " + Tok); 647*2ec34544SRui Ueyama return 0; 648*2ec34544SRui Ueyama } 649*2ec34544SRui Ueyama 650*2ec34544SRui Ueyama SymbolAssignment *ScriptParser::readProvideHidden(bool Provide, bool Hidden) { 651*2ec34544SRui Ueyama expect("("); 652*2ec34544SRui Ueyama SymbolAssignment *Cmd = readAssignment(next()); 653*2ec34544SRui Ueyama Cmd->Provide = Provide; 654*2ec34544SRui Ueyama Cmd->Hidden = Hidden; 655*2ec34544SRui Ueyama expect(")"); 656*2ec34544SRui Ueyama expect(";"); 657*2ec34544SRui Ueyama return Cmd; 658*2ec34544SRui Ueyama } 659*2ec34544SRui Ueyama 660*2ec34544SRui Ueyama SymbolAssignment *ScriptParser::readProvideOrAssignment(StringRef Tok) { 661*2ec34544SRui Ueyama SymbolAssignment *Cmd = nullptr; 662*2ec34544SRui Ueyama if (peek() == "=" || peek() == "+=") { 663*2ec34544SRui Ueyama Cmd = readAssignment(Tok); 664*2ec34544SRui Ueyama expect(";"); 665*2ec34544SRui Ueyama } else if (Tok == "PROVIDE") { 666*2ec34544SRui Ueyama Cmd = readProvideHidden(true, false); 667*2ec34544SRui Ueyama } else if (Tok == "HIDDEN") { 668*2ec34544SRui Ueyama Cmd = readProvideHidden(false, true); 669*2ec34544SRui Ueyama } else if (Tok == "PROVIDE_HIDDEN") { 670*2ec34544SRui Ueyama Cmd = readProvideHidden(true, true); 671*2ec34544SRui Ueyama } 672*2ec34544SRui Ueyama return Cmd; 673*2ec34544SRui Ueyama } 674*2ec34544SRui Ueyama 675*2ec34544SRui Ueyama SymbolAssignment *ScriptParser::readAssignment(StringRef Name) { 676*2ec34544SRui Ueyama StringRef Op = next(); 677*2ec34544SRui Ueyama assert(Op == "=" || Op == "+="); 678*2ec34544SRui Ueyama Expr E = readExpr(); 679*2ec34544SRui Ueyama if (Op == "+=") { 680*2ec34544SRui Ueyama std::string Loc = getCurrentLocation(); 681*2ec34544SRui Ueyama E = [=] { return add(Script->getSymbolValue(Loc, Name), E()); }; 682*2ec34544SRui Ueyama } 683*2ec34544SRui Ueyama return make<SymbolAssignment>(Name, E, getCurrentLocation()); 684*2ec34544SRui Ueyama } 685*2ec34544SRui Ueyama 686*2ec34544SRui Ueyama // This is an operator-precedence parser to parse a linker 687*2ec34544SRui Ueyama // script expression. 688*2ec34544SRui Ueyama Expr ScriptParser::readExpr() { 689*2ec34544SRui Ueyama // Our lexer is context-aware. Set the in-expression bit so that 690*2ec34544SRui Ueyama // they apply different tokenization rules. 691*2ec34544SRui Ueyama bool Orig = InExpr; 692*2ec34544SRui Ueyama InExpr = true; 693*2ec34544SRui Ueyama Expr E = readExpr1(readPrimary(), 0); 694*2ec34544SRui Ueyama InExpr = Orig; 695*2ec34544SRui Ueyama return E; 696*2ec34544SRui Ueyama } 697*2ec34544SRui Ueyama 698*2ec34544SRui Ueyama static Expr combine(StringRef Op, Expr L, Expr R) { 699*2ec34544SRui Ueyama if (Op == "*") 700*2ec34544SRui Ueyama return [=] { return mul(L(), R()); }; 701*2ec34544SRui Ueyama if (Op == "/") { 702*2ec34544SRui Ueyama return [=] { return div(L(), R()); }; 703*2ec34544SRui Ueyama } 704*2ec34544SRui Ueyama if (Op == "+") 705*2ec34544SRui Ueyama return [=] { return add(L(), R()); }; 706*2ec34544SRui Ueyama if (Op == "-") 707*2ec34544SRui Ueyama return [=] { return sub(L(), R()); }; 708*2ec34544SRui Ueyama if (Op == "<<") 709*2ec34544SRui Ueyama return [=] { return leftShift(L(), R()); }; 710*2ec34544SRui Ueyama if (Op == ">>") 711*2ec34544SRui Ueyama return [=] { return rightShift(L(), R()); }; 712*2ec34544SRui Ueyama if (Op == "<") 713*2ec34544SRui Ueyama return [=] { return L().getValue() < R().getValue(); }; 714*2ec34544SRui Ueyama if (Op == ">") 715*2ec34544SRui Ueyama return [=] { return L().getValue() > R().getValue(); }; 716*2ec34544SRui Ueyama if (Op == ">=") 717*2ec34544SRui Ueyama return [=] { return L().getValue() >= R().getValue(); }; 718*2ec34544SRui Ueyama if (Op == "<=") 719*2ec34544SRui Ueyama return [=] { return L().getValue() <= R().getValue(); }; 720*2ec34544SRui Ueyama if (Op == "==") 721*2ec34544SRui Ueyama return [=] { return L().getValue() == R().getValue(); }; 722*2ec34544SRui Ueyama if (Op == "!=") 723*2ec34544SRui Ueyama return [=] { return L().getValue() != R().getValue(); }; 724*2ec34544SRui Ueyama if (Op == "&") 725*2ec34544SRui Ueyama return [=] { return bitAnd(L(), R()); }; 726*2ec34544SRui Ueyama if (Op == "|") 727*2ec34544SRui Ueyama return [=] { return bitOr(L(), R()); }; 728*2ec34544SRui Ueyama llvm_unreachable("invalid operator"); 729*2ec34544SRui Ueyama } 730*2ec34544SRui Ueyama 731*2ec34544SRui Ueyama // This is a part of the operator-precedence parser. This function 732*2ec34544SRui Ueyama // assumes that the remaining token stream starts with an operator. 733*2ec34544SRui Ueyama Expr ScriptParser::readExpr1(Expr Lhs, int MinPrec) { 734*2ec34544SRui Ueyama while (!atEOF() && !Error) { 735*2ec34544SRui Ueyama // Read an operator and an expression. 736*2ec34544SRui Ueyama if (consume("?")) 737*2ec34544SRui Ueyama return readTernary(Lhs); 738*2ec34544SRui Ueyama StringRef Op1 = peek(); 739*2ec34544SRui Ueyama if (precedence(Op1) < MinPrec) 740*2ec34544SRui Ueyama break; 741*2ec34544SRui Ueyama skip(); 742*2ec34544SRui Ueyama Expr Rhs = readPrimary(); 743*2ec34544SRui Ueyama 744*2ec34544SRui Ueyama // Evaluate the remaining part of the expression first if the 745*2ec34544SRui Ueyama // next operator has greater precedence than the previous one. 746*2ec34544SRui Ueyama // For example, if we have read "+" and "3", and if the next 747*2ec34544SRui Ueyama // operator is "*", then we'll evaluate 3 * ... part first. 748*2ec34544SRui Ueyama while (!atEOF()) { 749*2ec34544SRui Ueyama StringRef Op2 = peek(); 750*2ec34544SRui Ueyama if (precedence(Op2) <= precedence(Op1)) 751*2ec34544SRui Ueyama break; 752*2ec34544SRui Ueyama Rhs = readExpr1(Rhs, precedence(Op2)); 753*2ec34544SRui Ueyama } 754*2ec34544SRui Ueyama 755*2ec34544SRui Ueyama Lhs = combine(Op1, Lhs, Rhs); 756*2ec34544SRui Ueyama } 757*2ec34544SRui Ueyama return Lhs; 758*2ec34544SRui Ueyama } 759*2ec34544SRui Ueyama 760*2ec34544SRui Ueyama uint64_t static getConstant(StringRef S) { 761*2ec34544SRui Ueyama if (S == "COMMONPAGESIZE") 762*2ec34544SRui Ueyama return Target->PageSize; 763*2ec34544SRui Ueyama if (S == "MAXPAGESIZE") 764*2ec34544SRui Ueyama return Config->MaxPageSize; 765*2ec34544SRui Ueyama error("unknown constant: " + S); 766*2ec34544SRui Ueyama return 0; 767*2ec34544SRui Ueyama } 768*2ec34544SRui Ueyama 769*2ec34544SRui Ueyama // Parses Tok as an integer. Returns true if successful. 770*2ec34544SRui Ueyama // It recognizes hexadecimal (prefixed with "0x" or suffixed with "H") 771*2ec34544SRui Ueyama // and decimal numbers. Decimal numbers may have "K" (kilo) or 772*2ec34544SRui Ueyama // "M" (mega) prefixes. 773*2ec34544SRui Ueyama static bool readInteger(StringRef Tok, uint64_t &Result) { 774*2ec34544SRui Ueyama // Negative number 775*2ec34544SRui Ueyama if (Tok.startswith("-")) { 776*2ec34544SRui Ueyama if (!readInteger(Tok.substr(1), Result)) 777*2ec34544SRui Ueyama return false; 778*2ec34544SRui Ueyama Result = -Result; 779*2ec34544SRui Ueyama return true; 780*2ec34544SRui Ueyama } 781*2ec34544SRui Ueyama 782*2ec34544SRui Ueyama // Hexadecimal 783*2ec34544SRui Ueyama if (Tok.startswith_lower("0x")) 784*2ec34544SRui Ueyama return !Tok.substr(2).getAsInteger(16, Result); 785*2ec34544SRui Ueyama if (Tok.endswith_lower("H")) 786*2ec34544SRui Ueyama return !Tok.drop_back().getAsInteger(16, Result); 787*2ec34544SRui Ueyama 788*2ec34544SRui Ueyama // Decimal 789*2ec34544SRui Ueyama int Suffix = 1; 790*2ec34544SRui Ueyama if (Tok.endswith_lower("K")) { 791*2ec34544SRui Ueyama Suffix = 1024; 792*2ec34544SRui Ueyama Tok = Tok.drop_back(); 793*2ec34544SRui Ueyama } else if (Tok.endswith_lower("M")) { 794*2ec34544SRui Ueyama Suffix = 1024 * 1024; 795*2ec34544SRui Ueyama Tok = Tok.drop_back(); 796*2ec34544SRui Ueyama } 797*2ec34544SRui Ueyama if (Tok.getAsInteger(10, Result)) 798*2ec34544SRui Ueyama return false; 799*2ec34544SRui Ueyama Result *= Suffix; 800*2ec34544SRui Ueyama return true; 801*2ec34544SRui Ueyama } 802*2ec34544SRui Ueyama 803*2ec34544SRui Ueyama BytesDataCommand *ScriptParser::readBytesDataCommand(StringRef Tok) { 804*2ec34544SRui Ueyama int Size = StringSwitch<unsigned>(Tok) 805*2ec34544SRui Ueyama .Case("BYTE", 1) 806*2ec34544SRui Ueyama .Case("SHORT", 2) 807*2ec34544SRui Ueyama .Case("LONG", 4) 808*2ec34544SRui Ueyama .Case("QUAD", 8) 809*2ec34544SRui Ueyama .Default(-1); 810*2ec34544SRui Ueyama if (Size == -1) 811*2ec34544SRui Ueyama return nullptr; 812*2ec34544SRui Ueyama 813*2ec34544SRui Ueyama return make<BytesDataCommand>(readParenExpr(), Size); 814*2ec34544SRui Ueyama } 815*2ec34544SRui Ueyama 816*2ec34544SRui Ueyama StringRef ScriptParser::readParenLiteral() { 817*2ec34544SRui Ueyama expect("("); 818*2ec34544SRui Ueyama StringRef Tok = next(); 819*2ec34544SRui Ueyama expect(")"); 820*2ec34544SRui Ueyama return Tok; 821*2ec34544SRui Ueyama } 822*2ec34544SRui Ueyama 823*2ec34544SRui Ueyama Expr ScriptParser::readPrimary() { 824*2ec34544SRui Ueyama if (peek() == "(") 825*2ec34544SRui Ueyama return readParenExpr(); 826*2ec34544SRui Ueyama 827*2ec34544SRui Ueyama StringRef Tok = next(); 828*2ec34544SRui Ueyama std::string Location = getCurrentLocation(); 829*2ec34544SRui Ueyama 830*2ec34544SRui Ueyama if (Tok == "~") { 831*2ec34544SRui Ueyama Expr E = readPrimary(); 832*2ec34544SRui Ueyama return [=] { return bitNot(E()); }; 833*2ec34544SRui Ueyama } 834*2ec34544SRui Ueyama if (Tok == "-") { 835*2ec34544SRui Ueyama Expr E = readPrimary(); 836*2ec34544SRui Ueyama return [=] { return minus(E()); }; 837*2ec34544SRui Ueyama } 838*2ec34544SRui Ueyama 839*2ec34544SRui Ueyama // Built-in functions are parsed here. 840*2ec34544SRui Ueyama // https://sourceware.org/binutils/docs/ld/Builtin-Functions.html. 841*2ec34544SRui Ueyama if (Tok == "ABSOLUTE") { 842*2ec34544SRui Ueyama Expr Inner = readParenExpr(); 843*2ec34544SRui Ueyama return [=] { 844*2ec34544SRui Ueyama ExprValue I = Inner(); 845*2ec34544SRui Ueyama I.ForceAbsolute = true; 846*2ec34544SRui Ueyama return I; 847*2ec34544SRui Ueyama }; 848*2ec34544SRui Ueyama } 849*2ec34544SRui Ueyama if (Tok == "ADDR") { 850*2ec34544SRui Ueyama StringRef Name = readParenLiteral(); 851*2ec34544SRui Ueyama return [=]() -> ExprValue { 852*2ec34544SRui Ueyama return {Script->getOutputSection(Location, Name), 0}; 853*2ec34544SRui Ueyama }; 854*2ec34544SRui Ueyama } 855*2ec34544SRui Ueyama if (Tok == "ALIGN") { 856*2ec34544SRui Ueyama expect("("); 857*2ec34544SRui Ueyama Expr E = readExpr(); 858*2ec34544SRui Ueyama if (consume(",")) { 859*2ec34544SRui Ueyama Expr E2 = readExpr(); 860*2ec34544SRui Ueyama expect(")"); 861*2ec34544SRui Ueyama return [=] { return alignTo(E().getValue(), E2().getValue()); }; 862*2ec34544SRui Ueyama } 863*2ec34544SRui Ueyama expect(")"); 864*2ec34544SRui Ueyama return [=] { return alignTo(Script->getDot(), E().getValue()); }; 865*2ec34544SRui Ueyama } 866*2ec34544SRui Ueyama if (Tok == "ALIGNOF") { 867*2ec34544SRui Ueyama StringRef Name = readParenLiteral(); 868*2ec34544SRui Ueyama return [=] { return Script->getOutputSection(Location, Name)->Alignment; }; 869*2ec34544SRui Ueyama } 870*2ec34544SRui Ueyama if (Tok == "ASSERT") 871*2ec34544SRui Ueyama return readAssert(); 872*2ec34544SRui Ueyama if (Tok == "CONSTANT") { 873*2ec34544SRui Ueyama StringRef Name = readParenLiteral(); 874*2ec34544SRui Ueyama return [=] { return getConstant(Name); }; 875*2ec34544SRui Ueyama } 876*2ec34544SRui Ueyama if (Tok == "DATA_SEGMENT_ALIGN") { 877*2ec34544SRui Ueyama expect("("); 878*2ec34544SRui Ueyama Expr E = readExpr(); 879*2ec34544SRui Ueyama expect(","); 880*2ec34544SRui Ueyama readExpr(); 881*2ec34544SRui Ueyama expect(")"); 882*2ec34544SRui Ueyama return [=] { return alignTo(Script->getDot(), E().getValue()); }; 883*2ec34544SRui Ueyama } 884*2ec34544SRui Ueyama if (Tok == "DATA_SEGMENT_END") { 885*2ec34544SRui Ueyama expect("("); 886*2ec34544SRui Ueyama expect("."); 887*2ec34544SRui Ueyama expect(")"); 888*2ec34544SRui Ueyama return [] { return Script->getDot(); }; 889*2ec34544SRui Ueyama } 890*2ec34544SRui Ueyama if (Tok == "DATA_SEGMENT_RELRO_END") { 891*2ec34544SRui Ueyama // GNU linkers implements more complicated logic to handle 892*2ec34544SRui Ueyama // DATA_SEGMENT_RELRO_END. We instead ignore the arguments and 893*2ec34544SRui Ueyama // just align to the next page boundary for simplicity. 894*2ec34544SRui Ueyama expect("("); 895*2ec34544SRui Ueyama readExpr(); 896*2ec34544SRui Ueyama expect(","); 897*2ec34544SRui Ueyama readExpr(); 898*2ec34544SRui Ueyama expect(")"); 899*2ec34544SRui Ueyama return [] { return alignTo(Script->getDot(), Target->PageSize); }; 900*2ec34544SRui Ueyama } 901*2ec34544SRui Ueyama if (Tok == "DEFINED") { 902*2ec34544SRui Ueyama StringRef Name = readParenLiteral(); 903*2ec34544SRui Ueyama return [=] { return Script->isDefined(Name) ? 1 : 0; }; 904*2ec34544SRui Ueyama } 905*2ec34544SRui Ueyama if (Tok == "LOADADDR") { 906*2ec34544SRui Ueyama StringRef Name = readParenLiteral(); 907*2ec34544SRui Ueyama return [=] { return Script->getOutputSection(Location, Name)->getLMA(); }; 908*2ec34544SRui Ueyama } 909*2ec34544SRui Ueyama if (Tok == "SEGMENT_START") { 910*2ec34544SRui Ueyama expect("("); 911*2ec34544SRui Ueyama skip(); 912*2ec34544SRui Ueyama expect(","); 913*2ec34544SRui Ueyama Expr E = readExpr(); 914*2ec34544SRui Ueyama expect(")"); 915*2ec34544SRui Ueyama return [=] { return E(); }; 916*2ec34544SRui Ueyama } 917*2ec34544SRui Ueyama if (Tok == "SIZEOF") { 918*2ec34544SRui Ueyama StringRef Name = readParenLiteral(); 919*2ec34544SRui Ueyama return [=] { return Script->getOutputSectionSize(Name); }; 920*2ec34544SRui Ueyama } 921*2ec34544SRui Ueyama if (Tok == "SIZEOF_HEADERS") 922*2ec34544SRui Ueyama return [=] { return elf::getHeaderSize(); }; 923*2ec34544SRui Ueyama 924*2ec34544SRui Ueyama // Tok is a literal number. 925*2ec34544SRui Ueyama uint64_t V; 926*2ec34544SRui Ueyama if (readInteger(Tok, V)) 927*2ec34544SRui Ueyama return [=] { return V; }; 928*2ec34544SRui Ueyama 929*2ec34544SRui Ueyama // Tok is a symbol name. 930*2ec34544SRui Ueyama if (Tok != ".") { 931*2ec34544SRui Ueyama if (!isValidCIdentifier(Tok)) 932*2ec34544SRui Ueyama setError("malformed number: " + Tok); 933*2ec34544SRui Ueyama Script->Opt.UndefinedSymbols.push_back(Tok); 934*2ec34544SRui Ueyama } 935*2ec34544SRui Ueyama return [=] { return Script->getSymbolValue(Location, Tok); }; 936*2ec34544SRui Ueyama } 937*2ec34544SRui Ueyama 938*2ec34544SRui Ueyama Expr ScriptParser::readTernary(Expr Cond) { 939*2ec34544SRui Ueyama Expr L = readExpr(); 940*2ec34544SRui Ueyama expect(":"); 941*2ec34544SRui Ueyama Expr R = readExpr(); 942*2ec34544SRui Ueyama return [=] { return Cond().getValue() ? L() : R(); }; 943*2ec34544SRui Ueyama } 944*2ec34544SRui Ueyama 945*2ec34544SRui Ueyama Expr ScriptParser::readParenExpr() { 946*2ec34544SRui Ueyama expect("("); 947*2ec34544SRui Ueyama Expr E = readExpr(); 948*2ec34544SRui Ueyama expect(")"); 949*2ec34544SRui Ueyama return E; 950*2ec34544SRui Ueyama } 951*2ec34544SRui Ueyama 952*2ec34544SRui Ueyama std::vector<StringRef> ScriptParser::readOutputSectionPhdrs() { 953*2ec34544SRui Ueyama std::vector<StringRef> Phdrs; 954*2ec34544SRui Ueyama while (!Error && peek().startswith(":")) { 955*2ec34544SRui Ueyama StringRef Tok = next(); 956*2ec34544SRui Ueyama Phdrs.push_back((Tok.size() == 1) ? next() : Tok.substr(1)); 957*2ec34544SRui Ueyama } 958*2ec34544SRui Ueyama return Phdrs; 959*2ec34544SRui Ueyama } 960*2ec34544SRui Ueyama 961*2ec34544SRui Ueyama // Read a program header type name. The next token must be a 962*2ec34544SRui Ueyama // name of a program header type or a constant (e.g. "0x3"). 963*2ec34544SRui Ueyama unsigned ScriptParser::readPhdrType() { 964*2ec34544SRui Ueyama StringRef Tok = next(); 965*2ec34544SRui Ueyama uint64_t Val; 966*2ec34544SRui Ueyama if (readInteger(Tok, Val)) 967*2ec34544SRui Ueyama return Val; 968*2ec34544SRui Ueyama 969*2ec34544SRui Ueyama unsigned Ret = StringSwitch<unsigned>(Tok) 970*2ec34544SRui Ueyama .Case("PT_NULL", PT_NULL) 971*2ec34544SRui Ueyama .Case("PT_LOAD", PT_LOAD) 972*2ec34544SRui Ueyama .Case("PT_DYNAMIC", PT_DYNAMIC) 973*2ec34544SRui Ueyama .Case("PT_INTERP", PT_INTERP) 974*2ec34544SRui Ueyama .Case("PT_NOTE", PT_NOTE) 975*2ec34544SRui Ueyama .Case("PT_SHLIB", PT_SHLIB) 976*2ec34544SRui Ueyama .Case("PT_PHDR", PT_PHDR) 977*2ec34544SRui Ueyama .Case("PT_TLS", PT_TLS) 978*2ec34544SRui Ueyama .Case("PT_GNU_EH_FRAME", PT_GNU_EH_FRAME) 979*2ec34544SRui Ueyama .Case("PT_GNU_STACK", PT_GNU_STACK) 980*2ec34544SRui Ueyama .Case("PT_GNU_RELRO", PT_GNU_RELRO) 981*2ec34544SRui Ueyama .Case("PT_OPENBSD_RANDOMIZE", PT_OPENBSD_RANDOMIZE) 982*2ec34544SRui Ueyama .Case("PT_OPENBSD_WXNEEDED", PT_OPENBSD_WXNEEDED) 983*2ec34544SRui Ueyama .Case("PT_OPENBSD_BOOTDATA", PT_OPENBSD_BOOTDATA) 984*2ec34544SRui Ueyama .Default(-1); 985*2ec34544SRui Ueyama 986*2ec34544SRui Ueyama if (Ret == (unsigned)-1) { 987*2ec34544SRui Ueyama setError("invalid program header type: " + Tok); 988*2ec34544SRui Ueyama return PT_NULL; 989*2ec34544SRui Ueyama } 990*2ec34544SRui Ueyama return Ret; 991*2ec34544SRui Ueyama } 992*2ec34544SRui Ueyama 993*2ec34544SRui Ueyama // Reads an anonymous version declaration. 994*2ec34544SRui Ueyama void ScriptParser::readAnonymousDeclaration() { 995*2ec34544SRui Ueyama std::vector<SymbolVersion> Locals; 996*2ec34544SRui Ueyama std::vector<SymbolVersion> Globals; 997*2ec34544SRui Ueyama std::tie(Locals, Globals) = readSymbols(); 998*2ec34544SRui Ueyama 999*2ec34544SRui Ueyama for (SymbolVersion V : Locals) { 1000*2ec34544SRui Ueyama if (V.Name == "*") 1001*2ec34544SRui Ueyama Config->DefaultSymbolVersion = VER_NDX_LOCAL; 1002*2ec34544SRui Ueyama else 1003*2ec34544SRui Ueyama Config->VersionScriptLocals.push_back(V); 1004*2ec34544SRui Ueyama } 1005*2ec34544SRui Ueyama 1006*2ec34544SRui Ueyama for (SymbolVersion V : Globals) 1007*2ec34544SRui Ueyama Config->VersionScriptGlobals.push_back(V); 1008*2ec34544SRui Ueyama 1009*2ec34544SRui Ueyama expect(";"); 1010*2ec34544SRui Ueyama } 1011*2ec34544SRui Ueyama 1012*2ec34544SRui Ueyama // Reads a non-anonymous version definition, 1013*2ec34544SRui Ueyama // e.g. "VerStr { global: foo; bar; local: *; };". 1014*2ec34544SRui Ueyama void ScriptParser::readVersionDeclaration(StringRef VerStr) { 1015*2ec34544SRui Ueyama // Read a symbol list. 1016*2ec34544SRui Ueyama std::vector<SymbolVersion> Locals; 1017*2ec34544SRui Ueyama std::vector<SymbolVersion> Globals; 1018*2ec34544SRui Ueyama std::tie(Locals, Globals) = readSymbols(); 1019*2ec34544SRui Ueyama 1020*2ec34544SRui Ueyama for (SymbolVersion V : Locals) { 1021*2ec34544SRui Ueyama if (V.Name == "*") 1022*2ec34544SRui Ueyama Config->DefaultSymbolVersion = VER_NDX_LOCAL; 1023*2ec34544SRui Ueyama else 1024*2ec34544SRui Ueyama Config->VersionScriptLocals.push_back(V); 1025*2ec34544SRui Ueyama } 1026*2ec34544SRui Ueyama 1027*2ec34544SRui Ueyama // Create a new version definition and add that to the global symbols. 1028*2ec34544SRui Ueyama VersionDefinition Ver; 1029*2ec34544SRui Ueyama Ver.Name = VerStr; 1030*2ec34544SRui Ueyama Ver.Globals = Globals; 1031*2ec34544SRui Ueyama 1032*2ec34544SRui Ueyama // User-defined version number starts from 2 because 0 and 1 are 1033*2ec34544SRui Ueyama // reserved for VER_NDX_LOCAL and VER_NDX_GLOBAL, respectively. 1034*2ec34544SRui Ueyama Ver.Id = Config->VersionDefinitions.size() + 2; 1035*2ec34544SRui Ueyama Config->VersionDefinitions.push_back(Ver); 1036*2ec34544SRui Ueyama 1037*2ec34544SRui Ueyama // Each version may have a parent version. For example, "Ver2" 1038*2ec34544SRui Ueyama // defined as "Ver2 { global: foo; local: *; } Ver1;" has "Ver1" 1039*2ec34544SRui Ueyama // as a parent. This version hierarchy is, probably against your 1040*2ec34544SRui Ueyama // instinct, purely for hint; the runtime doesn't care about it 1041*2ec34544SRui Ueyama // at all. In LLD, we simply ignore it. 1042*2ec34544SRui Ueyama if (peek() != ";") 1043*2ec34544SRui Ueyama skip(); 1044*2ec34544SRui Ueyama expect(";"); 1045*2ec34544SRui Ueyama } 1046*2ec34544SRui Ueyama 1047*2ec34544SRui Ueyama // Reads a list of symbols, e.g. "{ global: foo; bar; local: *; };". 1048*2ec34544SRui Ueyama std::pair<std::vector<SymbolVersion>, std::vector<SymbolVersion>> 1049*2ec34544SRui Ueyama ScriptParser::readSymbols() { 1050*2ec34544SRui Ueyama std::vector<SymbolVersion> Locals; 1051*2ec34544SRui Ueyama std::vector<SymbolVersion> Globals; 1052*2ec34544SRui Ueyama std::vector<SymbolVersion> *V = &Globals; 1053*2ec34544SRui Ueyama 1054*2ec34544SRui Ueyama while (!Error) { 1055*2ec34544SRui Ueyama if (consume("}")) 1056*2ec34544SRui Ueyama break; 1057*2ec34544SRui Ueyama if (consumeLabel("local")) { 1058*2ec34544SRui Ueyama V = &Locals; 1059*2ec34544SRui Ueyama continue; 1060*2ec34544SRui Ueyama } 1061*2ec34544SRui Ueyama if (consumeLabel("global")) { 1062*2ec34544SRui Ueyama V = &Globals; 1063*2ec34544SRui Ueyama continue; 1064*2ec34544SRui Ueyama } 1065*2ec34544SRui Ueyama 1066*2ec34544SRui Ueyama if (consume("extern")) { 1067*2ec34544SRui Ueyama std::vector<SymbolVersion> Ext = readVersionExtern(); 1068*2ec34544SRui Ueyama V->insert(V->end(), Ext.begin(), Ext.end()); 1069*2ec34544SRui Ueyama } else { 1070*2ec34544SRui Ueyama StringRef Tok = next(); 1071*2ec34544SRui Ueyama V->push_back({unquote(Tok), false, hasWildcard(Tok)}); 1072*2ec34544SRui Ueyama } 1073*2ec34544SRui Ueyama expect(";"); 1074*2ec34544SRui Ueyama } 1075*2ec34544SRui Ueyama return {Locals, Globals}; 1076*2ec34544SRui Ueyama } 1077*2ec34544SRui Ueyama 1078*2ec34544SRui Ueyama // Reads an "extern C++" directive, e.g., 1079*2ec34544SRui Ueyama // "extern "C++" { ns::*; "f(int, double)"; };" 1080*2ec34544SRui Ueyama std::vector<SymbolVersion> ScriptParser::readVersionExtern() { 1081*2ec34544SRui Ueyama StringRef Tok = next(); 1082*2ec34544SRui Ueyama bool IsCXX = Tok == "\"C++\""; 1083*2ec34544SRui Ueyama if (!IsCXX && Tok != "\"C\"") 1084*2ec34544SRui Ueyama setError("Unknown language"); 1085*2ec34544SRui Ueyama expect("{"); 1086*2ec34544SRui Ueyama 1087*2ec34544SRui Ueyama std::vector<SymbolVersion> Ret; 1088*2ec34544SRui Ueyama while (!Error && peek() != "}") { 1089*2ec34544SRui Ueyama StringRef Tok = next(); 1090*2ec34544SRui Ueyama bool HasWildcard = !Tok.startswith("\"") && hasWildcard(Tok); 1091*2ec34544SRui Ueyama Ret.push_back({unquote(Tok), IsCXX, HasWildcard}); 1092*2ec34544SRui Ueyama expect(";"); 1093*2ec34544SRui Ueyama } 1094*2ec34544SRui Ueyama 1095*2ec34544SRui Ueyama expect("}"); 1096*2ec34544SRui Ueyama return Ret; 1097*2ec34544SRui Ueyama } 1098*2ec34544SRui Ueyama 1099*2ec34544SRui Ueyama uint64_t ScriptParser::readMemoryAssignment(StringRef S1, StringRef S2, 1100*2ec34544SRui Ueyama StringRef S3) { 1101*2ec34544SRui Ueyama if (!(consume(S1) || consume(S2) || consume(S3))) { 1102*2ec34544SRui Ueyama setError("expected one of: " + S1 + ", " + S2 + ", or " + S3); 1103*2ec34544SRui Ueyama return 0; 1104*2ec34544SRui Ueyama } 1105*2ec34544SRui Ueyama expect("="); 1106*2ec34544SRui Ueyama 1107*2ec34544SRui Ueyama // TODO: Fully support constant expressions. 1108*2ec34544SRui Ueyama uint64_t Val; 1109*2ec34544SRui Ueyama if (!readInteger(next(), Val)) 1110*2ec34544SRui Ueyama setError("nonconstant expression for " + S1); 1111*2ec34544SRui Ueyama return Val; 1112*2ec34544SRui Ueyama } 1113*2ec34544SRui Ueyama 1114*2ec34544SRui Ueyama // Parse the MEMORY command as specified in: 1115*2ec34544SRui Ueyama // https://sourceware.org/binutils/docs/ld/MEMORY.html 1116*2ec34544SRui Ueyama // 1117*2ec34544SRui Ueyama // MEMORY { name [(attr)] : ORIGIN = origin, LENGTH = len ... } 1118*2ec34544SRui Ueyama void ScriptParser::readMemory() { 1119*2ec34544SRui Ueyama expect("{"); 1120*2ec34544SRui Ueyama while (!Error && !consume("}")) { 1121*2ec34544SRui Ueyama StringRef Name = next(); 1122*2ec34544SRui Ueyama 1123*2ec34544SRui Ueyama uint32_t Flags = 0; 1124*2ec34544SRui Ueyama uint32_t NegFlags = 0; 1125*2ec34544SRui Ueyama if (consume("(")) { 1126*2ec34544SRui Ueyama std::tie(Flags, NegFlags) = readMemoryAttributes(); 1127*2ec34544SRui Ueyama expect(")"); 1128*2ec34544SRui Ueyama } 1129*2ec34544SRui Ueyama expect(":"); 1130*2ec34544SRui Ueyama 1131*2ec34544SRui Ueyama uint64_t Origin = readMemoryAssignment("ORIGIN", "org", "o"); 1132*2ec34544SRui Ueyama expect(","); 1133*2ec34544SRui Ueyama uint64_t Length = readMemoryAssignment("LENGTH", "len", "l"); 1134*2ec34544SRui Ueyama 1135*2ec34544SRui Ueyama // Add the memory region to the region map (if it doesn't already exist). 1136*2ec34544SRui Ueyama auto It = Script->Opt.MemoryRegions.find(Name); 1137*2ec34544SRui Ueyama if (It != Script->Opt.MemoryRegions.end()) 1138*2ec34544SRui Ueyama setError("region '" + Name + "' already defined"); 1139*2ec34544SRui Ueyama else 1140*2ec34544SRui Ueyama Script->Opt.MemoryRegions[Name] = {Name, Origin, Length, 1141*2ec34544SRui Ueyama Origin, Flags, NegFlags}; 1142*2ec34544SRui Ueyama } 1143*2ec34544SRui Ueyama } 1144*2ec34544SRui Ueyama 1145*2ec34544SRui Ueyama // This function parses the attributes used to match against section 1146*2ec34544SRui Ueyama // flags when placing output sections in a memory region. These flags 1147*2ec34544SRui Ueyama // are only used when an explicit memory region name is not used. 1148*2ec34544SRui Ueyama std::pair<uint32_t, uint32_t> ScriptParser::readMemoryAttributes() { 1149*2ec34544SRui Ueyama uint32_t Flags = 0; 1150*2ec34544SRui Ueyama uint32_t NegFlags = 0; 1151*2ec34544SRui Ueyama bool Invert = false; 1152*2ec34544SRui Ueyama 1153*2ec34544SRui Ueyama for (char C : next().lower()) { 1154*2ec34544SRui Ueyama uint32_t Flag = 0; 1155*2ec34544SRui Ueyama if (C == '!') 1156*2ec34544SRui Ueyama Invert = !Invert; 1157*2ec34544SRui Ueyama else if (C == 'w') 1158*2ec34544SRui Ueyama Flag = SHF_WRITE; 1159*2ec34544SRui Ueyama else if (C == 'x') 1160*2ec34544SRui Ueyama Flag = SHF_EXECINSTR; 1161*2ec34544SRui Ueyama else if (C == 'a') 1162*2ec34544SRui Ueyama Flag = SHF_ALLOC; 1163*2ec34544SRui Ueyama else if (C != 'r') 1164*2ec34544SRui Ueyama setError("invalid memory region attribute"); 1165*2ec34544SRui Ueyama 1166*2ec34544SRui Ueyama if (Invert) 1167*2ec34544SRui Ueyama NegFlags |= Flag; 1168*2ec34544SRui Ueyama else 1169*2ec34544SRui Ueyama Flags |= Flag; 1170*2ec34544SRui Ueyama } 1171*2ec34544SRui Ueyama return {Flags, NegFlags}; 1172*2ec34544SRui Ueyama } 1173*2ec34544SRui Ueyama 1174*2ec34544SRui Ueyama void elf::readLinkerScript(MemoryBufferRef MB) { 1175*2ec34544SRui Ueyama ScriptParser(MB).readLinkerScript(); 1176*2ec34544SRui Ueyama } 1177*2ec34544SRui Ueyama 1178*2ec34544SRui Ueyama void elf::readVersionScript(MemoryBufferRef MB) { 1179*2ec34544SRui Ueyama ScriptParser(MB).readVersionScript(); 1180*2ec34544SRui Ueyama } 1181*2ec34544SRui Ueyama 1182*2ec34544SRui Ueyama void elf::readDynamicList(MemoryBufferRef MB) { 1183*2ec34544SRui Ueyama ScriptParser(MB).readDynamicList(); 1184*2ec34544SRui Ueyama } 1185