diff options
author | Derek Schuff <dschuff@chromium.org> | 2012-09-25 17:30:25 -0700 |
---|---|---|
committer | Derek Schuff <dschuff@chromium.org> | 2012-09-25 18:01:23 -0700 |
commit | a27c28b1427dc2082ab2b31efdbb25f9fde31b61 (patch) | |
tree | 6f3ff025f542ca3f66a1a01cbf239aeef7784511 /lib/MC | |
parent | 0e15ffd8cb1ec642eddb96380660914ff2b007e1 (diff) | |
parent | bc4021f31eaa97ee52655828da3e3de14a39e4a6 (diff) |
Merge commit 'bc4021f31eaa97ee52655828da3e3de14a39e4a6'
Conflicts:
lib/MC/MCAssembler.cpp
lib/Target/ARM/ARMISelDAGToDAG.cpp
lib/Target/Mips/MipsInstrFPU.td
lib/Target/X86/MCTargetDesc/X86AsmBackend.cpp
lib/Target/X86/X86ISelLowering.h
Diffstat (limited to 'lib/MC')
-rw-r--r-- | lib/MC/MCAssembler.cpp | 9 | ||||
-rw-r--r-- | lib/MC/MCContext.cpp | 6 | ||||
-rw-r--r-- | lib/MC/MCDwarf.cpp | 2 | ||||
-rw-r--r-- | lib/MC/MCELFStreamer.cpp | 2 | ||||
-rw-r--r-- | lib/MC/MCExpr.cpp | 2 | ||||
-rw-r--r-- | lib/MC/MCInst.cpp | 4 | ||||
-rw-r--r-- | lib/MC/MCLabel.cpp | 2 | ||||
-rw-r--r-- | lib/MC/MCObjectFileInfo.cpp | 20 | ||||
-rw-r--r-- | lib/MC/MCParser/AsmLexer.cpp | 13 | ||||
-rw-r--r-- | lib/MC/MCParser/AsmParser.cpp | 199 | ||||
-rw-r--r-- | lib/MC/MCParser/MCAsmLexer.cpp | 3 | ||||
-rw-r--r-- | lib/MC/MCParser/MCAsmParser.cpp | 2 | ||||
-rw-r--r-- | lib/MC/MCSubtargetInfo.cpp | 51 | ||||
-rw-r--r-- | lib/MC/MCSymbol.cpp | 4 | ||||
-rw-r--r-- | lib/MC/MCValue.cpp | 2 | ||||
-rw-r--r-- | lib/MC/MachObjectWriter.cpp | 47 | ||||
-rw-r--r-- | lib/MC/SubtargetFeature.cpp | 2 |
17 files changed, 282 insertions, 88 deletions
diff --git a/lib/MC/MCAssembler.cpp b/lib/MC/MCAssembler.cpp index 02bd6deb62..80bf4f9309 100644 --- a/lib/MC/MCAssembler.cpp +++ b/lib/MC/MCAssembler.cpp @@ -330,8 +330,7 @@ MCAssembler::MCAssembler(MCContext &Context_, MCAsmBackend &Backend_, MCCodeEmitter &Emitter_, MCObjectWriter &Writer_, raw_ostream &OS_) : Context(Context_), Backend(Backend_), Emitter(Emitter_), Writer(Writer_), - OS(OS_), RelaxAll(false), NoExecStack(false), SubsectionsViaSymbols(false) -{ + OS(OS_), RelaxAll(false), NoExecStack(false), SubsectionsViaSymbols(false) { } MCAssembler::~MCAssembler() { @@ -631,7 +630,7 @@ static void WriteBundlePadding(const MCAssembler &Asm, } // @LOCALMOD-END -/// WriteFragmentData - Write the \arg F data to the output file. +/// WriteFragmentData - Write the \p F data to the output file. static void WriteFragmentData(const MCAssembler &Asm, const MCAsmLayout &Layout, const MCFragment &F) { MCObjectWriter *OW = &Asm.getWriter(); @@ -810,7 +809,7 @@ void MCAssembler::writeSectionData(const MCSectionData *SD, } uint64_t Start = getWriter().getStream().tell(); - (void) Start; + (void)Start; for (MCSectionData::const_iterator it = SD->begin(), ie = SD->end(); it != ie; ++it) @@ -1107,7 +1106,7 @@ raw_ostream &operator<<(raw_ostream &OS, const MCFixup &AF) { } -#ifndef NDEBUG +#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP) void MCFragment::dump() { raw_ostream &OS = llvm::errs(); diff --git a/lib/MC/MCContext.cpp b/lib/MC/MCContext.cpp index b5b14b95f6..477bd17c0d 100644 --- a/lib/MC/MCContext.cpp +++ b/lib/MC/MCContext.cpp @@ -153,6 +153,12 @@ MCSymbol *MCContext::LookupSymbol(StringRef Name) const { return Symbols.lookup(Name); } +MCSymbol *MCContext::LookupSymbol(const Twine &Name) const { + SmallString<128> NameSV; + Name.toVector(NameSV); + return LookupSymbol(NameSV.str()); +} + //===----------------------------------------------------------------------===// // Section Management //===----------------------------------------------------------------------===// diff --git a/lib/MC/MCDwarf.cpp b/lib/MC/MCDwarf.cpp index ee597cfa21..a1643b2da5 100644 --- a/lib/MC/MCDwarf.cpp +++ b/lib/MC/MCDwarf.cpp @@ -425,7 +425,7 @@ void MCDwarfFile::print(raw_ostream &OS) const { OS << '"' << getName() << '"'; } -#ifndef NDEBUG +#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP) void MCDwarfFile::dump() const { print(dbgs()); } diff --git a/lib/MC/MCELFStreamer.cpp b/lib/MC/MCELFStreamer.cpp index bf35ab7fc3..d1aeaf36c7 100644 --- a/lib/MC/MCELFStreamer.cpp +++ b/lib/MC/MCELFStreamer.cpp @@ -247,7 +247,6 @@ void MCELFStreamer::EmitSymbolAttribute(MCSymbol *Symbol, switch (Attribute) { case MCSA_LazyReference: case MCSA_Reference: - case MCSA_NoDeadStrip: case MCSA_SymbolResolver: case MCSA_PrivateExtern: case MCSA_WeakDefinition: @@ -256,6 +255,7 @@ void MCELFStreamer::EmitSymbolAttribute(MCSymbol *Symbol, case MCSA_IndirectSymbol: llvm_unreachable("Invalid symbol attribute for ELF!"); + case MCSA_NoDeadStrip: case MCSA_ELF_TypeGnuUniqueObject: // Ignore for now. break; diff --git a/lib/MC/MCExpr.cpp b/lib/MC/MCExpr.cpp index b19665949d..8fed48cef2 100644 --- a/lib/MC/MCExpr.cpp +++ b/lib/MC/MCExpr.cpp @@ -136,7 +136,7 @@ void MCExpr::print(raw_ostream &OS) const { llvm_unreachable("Invalid expression kind!"); } -#ifndef NDEBUG +#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP) void MCExpr::dump() const { print(dbgs()); dbgs() << '\n'; diff --git a/lib/MC/MCInst.cpp b/lib/MC/MCInst.cpp index e96010bd5c..124cc149be 100644 --- a/lib/MC/MCInst.cpp +++ b/lib/MC/MCInst.cpp @@ -32,7 +32,7 @@ void MCOperand::print(raw_ostream &OS, const MCAsmInfo *MAI) const { OS << ">"; } -#ifndef NDEBUG +#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP) void MCOperand::dump() const { print(dbgs(), 0); dbgs() << "\n"; @@ -64,7 +64,7 @@ void MCInst::dump_pretty(raw_ostream &OS, const MCAsmInfo *MAI, OS << ">"; } -#ifndef NDEBUG +#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP) void MCInst::dump() const { print(dbgs(), 0); dbgs() << "\n"; diff --git a/lib/MC/MCLabel.cpp b/lib/MC/MCLabel.cpp index 95d7d16a19..1d3022a93e 100644 --- a/lib/MC/MCLabel.cpp +++ b/lib/MC/MCLabel.cpp @@ -16,7 +16,7 @@ void MCLabel::print(raw_ostream &OS) const { OS << '"' << getInstance() << '"'; } -#ifndef NDEBUG +#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP) void MCLabel::dump() const { print(dbgs()); } diff --git a/lib/MC/MCObjectFileInfo.cpp b/lib/MC/MCObjectFileInfo.cpp index 29b4a94653..8053624831 100644 --- a/lib/MC/MCObjectFileInfo.cpp +++ b/lib/MC/MCObjectFileInfo.cpp @@ -430,12 +430,20 @@ void MCObjectFileInfo::InitCOFFMCObjectFileInfo(Triple T) { } - StaticDtorSection = - Ctx->getCOFFSection(".dtors", - COFF::IMAGE_SCN_CNT_INITIALIZED_DATA | - COFF::IMAGE_SCN_MEM_READ | - COFF::IMAGE_SCN_MEM_WRITE, - SectionKind::getDataRel()); + if (T.getOS() == Triple::Win32) { + StaticDtorSection = + Ctx->getCOFFSection(".CRT$XTX", + COFF::IMAGE_SCN_CNT_INITIALIZED_DATA | + COFF::IMAGE_SCN_MEM_READ, + SectionKind::getReadOnly()); + } else { + StaticDtorSection = + Ctx->getCOFFSection(".dtors", + COFF::IMAGE_SCN_CNT_INITIALIZED_DATA | + COFF::IMAGE_SCN_MEM_READ | + COFF::IMAGE_SCN_MEM_WRITE, + SectionKind::getDataRel()); + } // FIXME: We're emitting LSDA info into a readonly section on COFF, even // though it contains relocatable pointers. In PIC mode, this is probably a diff --git a/lib/MC/MCParser/AsmLexer.cpp b/lib/MC/MCParser/AsmLexer.cpp index c76052d66e..f93f685bf5 100644 --- a/lib/MC/MCParser/AsmLexer.cpp +++ b/lib/MC/MCParser/AsmLexer.cpp @@ -396,8 +396,17 @@ AsmToken AsmLexer::LexToken() { case 0: case ' ': case '\t': - // Ignore whitespace. - return LexToken(); + if (SkipSpace) { + // Ignore whitespace. + return LexToken(); + } else { + int len = 1; + while (*CurPtr==' ' || *CurPtr=='\t') { + CurPtr++; + len++; + } + return AsmToken(AsmToken::Space, StringRef(TokStart, len)); + } case '\n': // FALL THROUGH. case '\r': isAtStartOfLine = true; diff --git a/lib/MC/MCParser/AsmParser.cpp b/lib/MC/MCParser/AsmParser.cpp index 40e6b92174..fc0bc35347 100644 --- a/lib/MC/MCParser/AsmParser.cpp +++ b/lib/MC/MCParser/AsmParser.cpp @@ -47,7 +47,7 @@ namespace { /// \brief Helper class for tracking macro definitions. typedef std::vector<AsmToken> MacroArgument; typedef std::vector<MacroArgument> MacroArguments; -typedef StringRef MacroParameter; +typedef std::pair<StringRef, MacroArgument> MacroParameter; typedef std::vector<MacroParameter> MacroParameters; struct Macro { @@ -84,8 +84,8 @@ public: class AsmParser : public MCAsmParser { friend class GenericAsmParser; - AsmParser(const AsmParser &); // DO NOT IMPLEMENT - void operator=(const AsmParser &); // DO NOT IMPLEMENT + AsmParser(const AsmParser &) LLVM_DELETED_FUNCTION; + void operator=(const AsmParser &) LLVM_DELETED_FUNCTION; private: AsmLexer Lexer; MCContext &Ctx; @@ -130,6 +130,9 @@ private: /// AssemblerDialect. ~OU means unset value and use value provided by MAI. unsigned AssemblerDialect; + /// IsDarwin - is Darwin compatibility enabled? + bool IsDarwin; + public: AsmParser(SourceMgr &SM, MCContext &Ctx, MCStreamer &Out, const MCAsmInfo &MAI); @@ -202,14 +205,15 @@ private: /// This returns true on failure. bool ProcessIncbinFile(const std::string &Filename); - /// \brief Reset the current lexer position to that given by \arg Loc. The + /// \brief Reset the current lexer position to that given by \p Loc. The /// current token is not set; clients should ensure Lex() is called /// subsequently. void JumpToLoc(SMLoc Loc); virtual void EatToEndOfStatement(); - bool ParseMacroArgument(MacroArgument &MA); + bool ParseMacroArgument(MacroArgument &MA, + AsmToken::TokenKind &ArgumentDelimiter); bool ParseMacroArguments(const Macro *M, MacroArguments &A); /// \brief Parse up to the end of statement and a return the contents from the @@ -221,7 +225,8 @@ private: /// return the contents from the current token up to the end or comma. StringRef ParseStringToComma(); - bool ParseAssignment(StringRef Name, bool allow_redef); + bool ParseAssignment(StringRef Name, bool allow_redef, + bool NoDeadStrip = false); bool ParsePrimaryExpr(const MCExpr *&Res, SMLoc &EndLoc); bool ParseBinOpRHS(unsigned Precedence, const MCExpr *&Res, SMLoc &EndLoc); @@ -229,7 +234,7 @@ private: bool ParseBracketExpr(const MCExpr *&Res, SMLoc &EndLoc); /// ParseIdentifier - Parse an identifier or string (as a quoted identifier) - /// and set \arg Res to the identifier contents. + /// and set \p Res to the identifier contents. virtual bool ParseIdentifier(StringRef &Res); // Directive Parsing. @@ -413,8 +418,8 @@ AsmParser::AsmParser(SourceMgr &_SM, MCContext &_Ctx, MCStreamer &_Out, const MCAsmInfo &_MAI) : Lexer(_MAI), Ctx(_Ctx), Out(_Out), MAI(_MAI), SrcMgr(_SM), GenericParser(new GenericAsmParser), PlatformParser(0), - CurBuffer(0), MacrosEnabled(true), CppHashLineNumber(0), - AssemblerDialect(~0U) { + CurBuffer(0), MacrosEnabled(true), CppHashLineNumber(0), + AssemblerDialect(~0U), IsDarwin(false) { // Save the old handler. SavedDiagHandler = SrcMgr.getDiagHandler(); SavedDiagContext = SrcMgr.getDiagContext(); @@ -435,6 +440,7 @@ AsmParser::AsmParser(SourceMgr &_SM, MCContext &_Ctx, } else if (_MAI.hasSubsectionsViaSymbols()) { PlatformParser = createDarwinAsmParser(); PlatformParser->Initialize(*this); + IsDarwin = true; } else { PlatformParser = createELFAsmParser(); PlatformParser->Initialize(*this); @@ -1495,6 +1501,8 @@ bool AsmParser::expandMacro(raw_svector_ostream &OS, StringRef Body, if (NParameters != 0 && NParameters != A.size()) return Error(L, "Wrong number of arguments"); + // A macro without parameters is handled differently on Darwin: + // gas accepts no arguments and does no substitutions while (!Body.empty()) { // Scan for the next substitution. std::size_t End = Body.size(), Pos = 0; @@ -1558,18 +1566,26 @@ bool AsmParser::expandMacro(raw_svector_ostream &OS, StringRef Body, StringRef Argument(Begin, I - (Pos +1)); unsigned Index = 0; for (; Index < NParameters; ++Index) - if (Parameters[Index] == Argument) + if (Parameters[Index].first == Argument) break; - // FIXME: We should error at the macro definition. - if (Index == NParameters) - return Error(L, "Parameter not found"); - - for (MacroArgument::const_iterator it = A[Index].begin(), - ie = A[Index].end(); it != ie; ++it) - OS << it->getString(); + if (Index == NParameters) { + if (Body[Pos+1] == '(' && Body[Pos+2] == ')') + Pos += 3; + else { + OS << '\\' << Argument; + Pos = I; + } + } else { + for (MacroArgument::const_iterator it = A[Index].begin(), + ie = A[Index].end(); it != ie; ++it) + if (it->getKind() == AsmToken::String) + OS << it->getStringContents(); + else + OS << it->getString(); - Pos += 1 + Argument.size(); + Pos += 1 + Argument.size(); + } } // Update the scan point. Body = Body.substr(Pos); @@ -1584,22 +1600,97 @@ MacroInstantiation::MacroInstantiation(const Macro *M, SMLoc IL, SMLoc EL, { } +static bool IsOperator(AsmToken::TokenKind kind) +{ + switch (kind) + { + default: + return false; + case AsmToken::Plus: + case AsmToken::Minus: + case AsmToken::Tilde: + case AsmToken::Slash: + case AsmToken::Star: + case AsmToken::Dot: + case AsmToken::Equal: + case AsmToken::EqualEqual: + case AsmToken::Pipe: + case AsmToken::PipePipe: + case AsmToken::Caret: + case AsmToken::Amp: + case AsmToken::AmpAmp: + case AsmToken::Exclaim: + case AsmToken::ExclaimEqual: + case AsmToken::Percent: + case AsmToken::Less: + case AsmToken::LessEqual: + case AsmToken::LessLess: + case AsmToken::LessGreater: + case AsmToken::Greater: + case AsmToken::GreaterEqual: + case AsmToken::GreaterGreater: + return true; + } +} + /// ParseMacroArgument - Extract AsmTokens for a macro argument. /// This is used for both default macro parameter values and the /// arguments in macro invocations -bool AsmParser::ParseMacroArgument(MacroArgument &MA) { +bool AsmParser::ParseMacroArgument(MacroArgument &MA, + AsmToken::TokenKind &ArgumentDelimiter) { unsigned ParenLevel = 0; + unsigned AddTokens = 0; + + // gas accepts arguments separated by whitespace, except on Darwin + if (!IsDarwin) + Lexer.setSkipSpace(false); for (;;) { - if (Lexer.is(AsmToken::Eof) || Lexer.is(AsmToken::Equal)) + if (Lexer.is(AsmToken::Eof) || Lexer.is(AsmToken::Equal)) { + Lexer.setSkipSpace(true); return TokError("unexpected token in macro instantiation"); + } + + if (ParenLevel == 0 && Lexer.is(AsmToken::Comma)) { + // Spaces and commas cannot be mixed to delimit parameters + if (ArgumentDelimiter == AsmToken::Eof) + ArgumentDelimiter = AsmToken::Comma; + else if (ArgumentDelimiter != AsmToken::Comma) { + Lexer.setSkipSpace(true); + return TokError("expected ' ' for macro argument separator"); + } + break; + } + + if (Lexer.is(AsmToken::Space)) { + Lex(); // Eat spaces + + // Spaces can delimit parameters, but could also be part an expression. + // If the token after a space is an operator, add the token and the next + // one into this argument + if (ArgumentDelimiter == AsmToken::Space || + ArgumentDelimiter == AsmToken::Eof) { + if (IsOperator(Lexer.getKind())) { + // Check to see whether the token is used as an operator, + // or part of an identifier + const char *NextChar = getTok().getEndLoc().getPointer() + 1; + if (*NextChar == ' ') + AddTokens = 2; + } + + if (!AddTokens && ParenLevel == 0) { + if (ArgumentDelimiter == AsmToken::Eof && + !IsOperator(Lexer.getKind())) + ArgumentDelimiter = AsmToken::Space; + break; + } + } + } // HandleMacroEntry relies on not advancing the lexer here // to be able to fill in the remaining default parameter values if (Lexer.is(AsmToken::EndOfStatement)) break; - if (ParenLevel == 0 && Lexer.is(AsmToken::Comma)) - break; // Adjust the current parentheses level. if (Lexer.is(AsmToken::LParen)) @@ -1609,8 +1700,12 @@ bool AsmParser::ParseMacroArgument(MacroArgument &MA) { // Append the token to the current argument list. MA.push_back(getTok()); + if (AddTokens) + AddTokens--; Lex(); } + + Lexer.setSkipSpace(true); if (ParenLevel != 0) return TokError("unbalanced parentheses in macro argument"); return false; @@ -1619,6 +1714,9 @@ bool AsmParser::ParseMacroArgument(MacroArgument &MA) { // Parse the macro instantiation arguments. bool AsmParser::ParseMacroArguments(const Macro *M, MacroArguments &A) { const unsigned NParameters = M ? M->Parameters.size() : 0; + // Argument delimiter is initially unknown. It will be set by + // ParseMacroArgument() + AsmToken::TokenKind ArgumentDelimiter = AsmToken::Eof; // Parse two kinds of macro invocations: // - macros defined without any parameters accept an arbitrary number of them @@ -1627,13 +1725,30 @@ bool AsmParser::ParseMacroArguments(const Macro *M, MacroArguments &A) { ++Parameter) { MacroArgument MA; - if (ParseMacroArgument(MA)) + if (ParseMacroArgument(MA, ArgumentDelimiter)) return true; - A.push_back(MA); + if (!MA.empty() || !NParameters) + A.push_back(MA); + else if (NParameters) { + if (!M->Parameters[Parameter].second.empty()) + A.push_back(M->Parameters[Parameter].second); + } - if (Lexer.is(AsmToken::EndOfStatement)) + // At the end of the statement, fill in remaining arguments that have + // default values. If there aren't any, then the next argument is + // required but missing + if (Lexer.is(AsmToken::EndOfStatement)) { + if (NParameters && Parameter < NParameters - 1) { + if (M->Parameters[Parameter + 1].second.empty()) + return TokError("macro argument '" + + Twine(M->Parameters[Parameter + 1].first) + + "' is missing"); + else + continue; + } return false; + } if (Lexer.is(AsmToken::Comma)) Lex(); @@ -1722,7 +1837,8 @@ static bool IsUsedIn(const MCSymbol *Sym, const MCExpr *Value) { llvm_unreachable("Unknown expr kind!"); } -bool AsmParser::ParseAssignment(StringRef Name, bool allow_redef) { +bool AsmParser::ParseAssignment(StringRef Name, bool allow_redef, + bool NoDeadStrip) { // FIXME: Use better location, we should use proper tokens. SMLoc EqualLoc = Lexer.getLoc(); @@ -1777,6 +1893,9 @@ bool AsmParser::ParseAssignment(StringRef Name, bool allow_redef) { // Do the assignment. Out.EmitAssignment(Sym, Value); + if (NoDeadStrip) + Out.EmitSymbolAttribute(Sym, MCSA_NoDeadStrip); + return false; } @@ -1834,7 +1953,7 @@ bool AsmParser::ParseDirectiveSet(StringRef IDVal, bool allow_redef) { return TokError("unexpected token in '" + Twine(IDVal) + "'"); Lex(); - return ParseAssignment(Name, allow_redef); + return ParseAssignment(Name, allow_redef, true); } bool AsmParser::ParseEscapedString(std::string &Data) { @@ -3152,22 +3271,30 @@ bool GenericAsmParser::ParseDirectiveMacro(StringRef Directive, return TokError("expected identifier in '.macro' directive"); MacroParameters Parameters; + // Argument delimiter is initially unknown. It will be set by + // ParseMacroArgument() + AsmToken::TokenKind ArgumentDelimiter = AsmToken::Eof; if (getLexer().isNot(AsmToken::EndOfStatement)) { for (;;) { MacroParameter Parameter; - if (getParser().ParseIdentifier(Parameter)) + if (getParser().ParseIdentifier(Parameter.first)) return TokError("expected identifier in '.macro' directive"); + + if (getLexer().is(AsmToken::Equal)) { + Lex(); + if (getParser().ParseMacroArgument(Parameter.second, ArgumentDelimiter)) + return true; + } + Parameters.push_back(Parameter); - if (getLexer().isNot(AsmToken::Comma)) + if (getLexer().is(AsmToken::Comma)) + Lex(); + else if (getLexer().is(AsmToken::EndOfStatement)) break; - Lex(); } } - if (getLexer().isNot(AsmToken::EndOfStatement)) - return TokError("unexpected token in '.macro' directive"); - // Eat the end of statement. Lex(); @@ -3372,7 +3499,7 @@ bool AsmParser::ParseDirectiveIrp(SMLoc DirectiveLoc) { MacroParameters Parameters; MacroParameter Parameter; - if (ParseIdentifier(Parameter)) + if (ParseIdentifier(Parameter.first)) return TokError("expected identifier in '.irp' directive"); Parameters.push_back(Parameter); @@ -3418,7 +3545,7 @@ bool AsmParser::ParseDirectiveIrpc(SMLoc DirectiveLoc) { MacroParameters Parameters; MacroParameter Parameter; - if (ParseIdentifier(Parameter)) + if (ParseIdentifier(Parameter.first)) return TokError("expected identifier in '.irpc' directive"); Parameters.push_back(Parameter); @@ -3468,7 +3595,7 @@ bool AsmParser::ParseDirectiveIrpc(SMLoc DirectiveLoc) { bool AsmParser::ParseDirectiveEndr(SMLoc DirectiveLoc) { if (ActiveMacros.empty()) - return TokError("unexpected '.endr' directive, no current .rept"); + return TokError("unmatched '.endr' directive"); // The only .repl that should get here are the ones created by // InstantiateMacroLikeBody. diff --git a/lib/MC/MCParser/MCAsmLexer.cpp b/lib/MC/MCParser/MCAsmLexer.cpp index 3a3ff14711..384b341bc7 100644 --- a/lib/MC/MCParser/MCAsmLexer.cpp +++ b/lib/MC/MCParser/MCAsmLexer.cpp @@ -12,7 +12,8 @@ using namespace llvm; -MCAsmLexer::MCAsmLexer() : CurTok(AsmToken::Error, StringRef()), TokStart(0) { +MCAsmLexer::MCAsmLexer() : CurTok(AsmToken::Error, StringRef()), + TokStart(0), SkipSpace(true) { } MCAsmLexer::~MCAsmLexer() { diff --git a/lib/MC/MCParser/MCAsmParser.cpp b/lib/MC/MCParser/MCAsmParser.cpp index 93ee2dd0c0..6967feef24 100644 --- a/lib/MC/MCParser/MCAsmParser.cpp +++ b/lib/MC/MCParser/MCAsmParser.cpp @@ -44,7 +44,7 @@ bool MCAsmParser::ParseExpression(const MCExpr *&Res) { } void MCParsedAsmOperand::dump() const { -#ifndef NDEBUG +#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP) dbgs() << " " << *this; #endif } diff --git a/lib/MC/MCSubtargetInfo.cpp b/lib/MC/MCSubtargetInfo.cpp index cbf853cd8e..8be07eed82 100644 --- a/lib/MC/MCSubtargetInfo.cpp +++ b/lib/MC/MCSubtargetInfo.cpp @@ -19,11 +19,28 @@ using namespace llvm; MCSchedModel MCSchedModel::DefaultSchedModel; // For unknown processors. +/// ReInitMCSubtargetInfo - Set or change the CPU (optionally supplemented +/// with feature string). Recompute feature bits and scheduling model. +void +MCSubtargetInfo::InitMCProcessorInfo(StringRef CPU, StringRef FS) { + SubtargetFeatures Features(FS); + FeatureBits = Features.getFeatureBits(CPU, ProcDesc, NumProcs, + ProcFeatures, NumFeatures); + + if (!CPU.empty()) + CPUSchedModel = getSchedModelForCPU(CPU); + else + CPUSchedModel = &MCSchedModel::DefaultSchedModel; +} + void MCSubtargetInfo::InitMCSubtargetInfo(StringRef TT, StringRef CPU, StringRef FS, const SubtargetFeatureKV *PF, const SubtargetFeatureKV *PD, const SubtargetInfoKV *ProcSched, + const MCWriteProcResEntry *WPR, + const MCWriteLatencyEntry *WL, + const MCReadAdvanceEntry *RA, const InstrStage *IS, const unsigned *OC, const unsigned *FP, @@ -31,26 +48,18 @@ MCSubtargetInfo::InitMCSubtargetInfo(StringRef TT, StringRef CPU, StringRef FS, TargetTriple = TT; ProcFeatures = PF; ProcDesc = PD; - ProcSchedModel = ProcSched; + ProcSchedModels = ProcSched; + WriteProcResTable = WPR; + WriteLatencyTable = WL; + ReadAdvanceTable = RA; + Stages = IS; OperandCycles = OC; ForwardingPaths = FP; NumFeatures = NF; NumProcs = NP; - SubtargetFeatures Features(FS); - FeatureBits = Features.getFeatureBits(CPU, ProcDesc, NumProcs, - ProcFeatures, NumFeatures); -} - - -/// ReInitMCSubtargetInfo - Change CPU (and optionally supplemented with -/// feature string) and recompute feature bits. -uint64_t MCSubtargetInfo::ReInitMCSubtargetInfo(StringRef CPU, StringRef FS) { - SubtargetFeatures Features(FS); - FeatureBits = Features.getFeatureBits(CPU, ProcDesc, NumProcs, - ProcFeatures, NumFeatures); - return FeatureBits; + InitMCProcessorInfo(CPU, FS); } /// ToggleFeature - Toggle a feature and returns the re-computed feature @@ -72,11 +81,11 @@ uint64_t MCSubtargetInfo::ToggleFeature(StringRef FS) { const MCSchedModel * MCSubtargetInfo::getSchedModelForCPU(StringRef CPU) const { - assert(ProcSchedModel && "Processor machine model not available!"); + assert(ProcSchedModels && "Processor machine model not available!"); #ifndef NDEBUG for (size_t i = 1; i < NumProcs; i++) { - assert(strcmp(ProcSchedModel[i - 1].Key, ProcSchedModel[i].Key) < 0 && + assert(strcmp(ProcSchedModels[i - 1].Key, ProcSchedModels[i].Key) < 0 && "Processor machine model table is not sorted"); } #endif @@ -85,8 +94,8 @@ MCSubtargetInfo::getSchedModelForCPU(StringRef CPU) const { SubtargetInfoKV KV; KV.Key = CPU.data(); const SubtargetInfoKV *Found = - std::lower_bound(ProcSchedModel, ProcSchedModel+NumProcs, KV); - if (Found == ProcSchedModel+NumProcs || StringRef(Found->Key) != CPU) { + std::lower_bound(ProcSchedModels, ProcSchedModels+NumProcs, KV); + if (Found == ProcSchedModels+NumProcs || StringRef(Found->Key) != CPU) { errs() << "'" << CPU << "' is not a recognized processor for this target" << " (ignoring processor)\n"; @@ -101,3 +110,9 @@ MCSubtargetInfo::getInstrItineraryForCPU(StringRef CPU) const { const MCSchedModel *SchedModel = getSchedModelForCPU(CPU); return InstrItineraryData(SchedModel, Stages, OperandCycles, ForwardingPaths); } + +/// Initialize an InstrItineraryData instance. +void MCSubtargetInfo::initInstrItins(InstrItineraryData &InstrItins) const { + InstrItins = + InstrItineraryData(CPUSchedModel, Stages, OperandCycles, ForwardingPaths); +} diff --git a/lib/MC/MCSymbol.cpp b/lib/MC/MCSymbol.cpp index f60126b8fa..b973c57f7b 100644 --- a/lib/MC/MCSymbol.cpp +++ b/lib/MC/MCSymbol.cpp @@ -26,7 +26,7 @@ static bool isAcceptableChar(char C) { return true; } -/// NameNeedsQuoting - Return true if the identifier \arg Str needs quotes to be +/// NameNeedsQuoting - Return true if the identifier \p Str needs quotes to be /// syntactically correct. static bool NameNeedsQuoting(StringRef Str) { assert(!Str.empty() && "Cannot create an empty MCSymbol"); @@ -76,7 +76,7 @@ void MCSymbol::print(raw_ostream &OS) const { OS << '"' << getName() << '"'; } -#ifndef NDEBUG +#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP) void MCSymbol::dump() const { print(dbgs()); } diff --git a/lib/MC/MCValue.cpp b/lib/MC/MCValue.cpp index a37149d788..4393777211 100644 --- a/lib/MC/MCValue.cpp +++ b/lib/MC/MCValue.cpp @@ -31,7 +31,7 @@ void MCValue::print(raw_ostream &OS, const MCAsmInfo *MAI) const { OS << " + " << getConstant(); } -#ifndef NDEBUG +#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP) void MCValue::dump() const { print(dbgs(), 0); } diff --git a/lib/MC/MachObjectWriter.cpp b/lib/MC/MachObjectWriter.cpp index c57b0d65c1..a94b214022 100644 --- a/lib/MC/MachObjectWriter.cpp +++ b/lib/MC/MachObjectWriter.cpp @@ -68,6 +68,11 @@ uint64_t MachObjectWriter::getSymbolAddress(const MCSymbolData* SD, // If this is a variable, then recursively evaluate now. if (S.isVariable()) { + if (const MCConstantExpr *C = + dyn_cast<const MCConstantExpr>(S.getVariableValue())) + return C->getValue(); + + MCValue Target; if (!S.getVariableValue()->EvaluateAsRelocatable(Target, Layout)) report_fatal_error("unable to evaluate offset for variable '" + @@ -140,8 +145,8 @@ void MachObjectWriter::WriteHeader(unsigned NumLoadCommands, /// WriteSegmentLoadCommand - Write a segment load command. /// -/// \arg NumSections - The number of sections in this segment. -/// \arg SectionDataSize - The total size of the sections. +/// \param NumSections The number of sections in this segment. +/// \param SectionDataSize The total size of the sections. void MachObjectWriter::WriteSegmentLoadCommand(unsigned NumSections, uint64_t VMSize, uint64_t SectionDataStartOffset, @@ -315,11 +320,7 @@ void MachObjectWriter::WriteNlist(MachSymbolData &MSD, // Compute the symbol address. if (Symbol.isDefined()) { - if (Symbol.isAbsolute()) { - Address = cast<MCConstantExpr>(Symbol.getVariableValue())->getValue(); - } else { - Address = getSymbolAddress(&Data, Layout); - } + Address = getSymbolAddress(&Data, Layout); } else if (Data.isCommon()) { // Common symbols are encoded with the size in the address // field, and their alignment in the flags. @@ -557,6 +558,26 @@ void MachObjectWriter::computeSectionAddresses(const MCAssembler &Asm, } } +void MachObjectWriter::markAbsoluteVariableSymbols(MCAssembler &Asm, + const MCAsmLayout &Layout) { + for (MCAssembler::symbol_iterator i = Asm.symbol_begin(), + e = Asm.symbol_end(); + i != e; ++i) { + MCSymbolData &SD = *i; + if (!SD.getSymbol().isVariable()) + continue; + + // Is the variable is a symbol difference (SA - SB + C) expression, + // and neither symbol is external, mark the variable as absolute. + const MCExpr *Expr = SD.getSymbol().getVariableValue(); + MCValue Value; + if (Expr->EvaluateAsRelocatable(Value, Layout)) { + if (Value.getSymA() && Value.getSymB()) + const_cast<MCSymbol*>(&SD.getSymbol())->setAbsolute(); + } + } +} + void MachObjectWriter::ExecutePostLayoutBinding(MCAssembler &Asm, const MCAsmLayout &Layout) { computeSectionAddresses(Asm, Layout); @@ -564,6 +585,10 @@ void MachObjectWriter::ExecutePostLayoutBinding(MCAssembler &Asm, // Create symbol data for any indirect symbols. BindIndirectSymbols(Asm); + // |