diff options
author | Shih-wei Liao <sliao@google.com> | 2010-04-28 01:47:00 -0700 |
---|---|---|
committer | Shih-wei Liao <sliao@google.com> | 2010-04-28 01:47:00 -0700 |
commit | 7abe37e4aee38cc79d91dd069a37d7e91d5bef53 (patch) | |
tree | c13b26fc3d8909240f981988535c0b82dd9bf37c /lib/Target/X86/AsmParser | |
parent | 6037a7c3c97b651dd70e48ebe5453134713971ed (diff) | |
download | external_llvm-7abe37e4aee38cc79d91dd069a37d7e91d5bef53.zip external_llvm-7abe37e4aee38cc79d91dd069a37d7e91d5bef53.tar.gz external_llvm-7abe37e4aee38cc79d91dd069a37d7e91d5bef53.tar.bz2 |
Sync upstream to r102410.
Re-turn on sdk.
Change-Id: I91a890863989a67243b4d2dfd1ae09b843ebaeaf
Diffstat (limited to 'lib/Target/X86/AsmParser')
-rw-r--r-- | lib/Target/X86/AsmParser/Makefile | 2 | ||||
-rw-r--r-- | lib/Target/X86/AsmParser/X86AsmParser.cpp | 85 |
2 files changed, 71 insertions, 16 deletions
diff --git a/lib/Target/X86/AsmParser/Makefile b/lib/Target/X86/AsmParser/Makefile index 25fb0a2..fb97607 100644 --- a/lib/Target/X86/AsmParser/Makefile +++ b/lib/Target/X86/AsmParser/Makefile @@ -10,6 +10,6 @@ LEVEL = ../../../.. LIBRARYNAME = LLVMX86AsmParser # Hack: we need to include 'main' x86 target directory to grab private headers -CPPFLAGS = -I$(PROJ_OBJ_DIR)/.. -I$(PROJ_SRC_DIR)/.. +CPP.Flags += -I$(PROJ_OBJ_DIR)/.. -I$(PROJ_SRC_DIR)/.. include $(LEVEL)/Makefile.common diff --git a/lib/Target/X86/AsmParser/X86AsmParser.cpp b/lib/Target/X86/AsmParser/X86AsmParser.cpp index 84d7bb7..da01350 100644 --- a/lib/Target/X86/AsmParser/X86AsmParser.cpp +++ b/lib/Target/X86/AsmParser/X86AsmParser.cpp @@ -29,6 +29,9 @@ struct X86Operand; class X86ATTAsmParser : public TargetAsmParser { MCAsmParser &Parser; +protected: + unsigned Is64Bit : 1; + private: MCAsmParser &getParser() const { return Parser; } @@ -41,10 +44,12 @@ private: bool ParseRegister(unsigned &RegNo, SMLoc &StartLoc, SMLoc &EndLoc); X86Operand *ParseOperand(); - X86Operand *ParseMemOperand(); + X86Operand *ParseMemOperand(unsigned SegReg, SMLoc StartLoc); bool ParseDirectiveWord(unsigned Size, SMLoc L); + void InstructionCleanup(MCInst &Inst); + /// @name Auto-generated Match Functions /// { @@ -62,7 +67,23 @@ public: virtual bool ParseDirective(AsmToken DirectiveID); }; - + +class X86_32ATTAsmParser : public X86ATTAsmParser { +public: + X86_32ATTAsmParser(const Target &T, MCAsmParser &_Parser) + : X86ATTAsmParser(T, _Parser) { + Is64Bit = false; + } +}; + +class X86_64ATTAsmParser : public X86ATTAsmParser { +public: + X86_64ATTAsmParser(const Target &T, MCAsmParser &_Parser) + : X86ATTAsmParser(T, _Parser) { + Is64Bit = true; + } +}; + } // end anonymous namespace /// @name Auto-generated Match Functions @@ -347,14 +368,22 @@ bool X86ATTAsmParser::ParseRegister(unsigned &RegNo, X86Operand *X86ATTAsmParser::ParseOperand() { switch (getLexer().getKind()) { default: - return ParseMemOperand(); + // Parse a memory operand with no segment register. + return ParseMemOperand(0, Parser.getTok().getLoc()); case AsmToken::Percent: { - // FIXME: if a segment register, this could either be just the seg reg, or - // the start of a memory operand. + // Read the register. unsigned RegNo; SMLoc Start, End; if (ParseRegister(RegNo, Start, End)) return 0; - return X86Operand::CreateReg(RegNo, Start, End); + + // If this is a segment register followed by a ':', then this is the start + // of a memory reference, otherwise this is a normal register reference. + if (getLexer().isNot(AsmToken::Colon)) + return X86Operand::CreateReg(RegNo, Start, End); + + + getParser().Lex(); // Eat the colon. + return ParseMemOperand(RegNo, Start); } case AsmToken::Dollar: { // $42 -> immediate. @@ -368,13 +397,10 @@ X86Operand *X86ATTAsmParser::ParseOperand() { } } -/// ParseMemOperand: segment: disp(basereg, indexreg, scale) -X86Operand *X86ATTAsmParser::ParseMemOperand() { - SMLoc MemStart = Parser.getTok().getLoc(); - - // FIXME: If SegReg ':' (e.g. %gs:), eat and remember. - unsigned SegReg = 0; - +/// ParseMemOperand: segment: disp(basereg, indexreg, scale). The '%ds:' prefix +/// has already been parsed if present. +X86Operand *X86ATTAsmParser::ParseMemOperand(unsigned SegReg, SMLoc MemStart) { + // We have to disambiguate a parenthesized expression "(4+5)" from the start // of a memory operand with a missing displacement "(%ebx)" or "(,%eax)". The // only way to do this without lookahead is to eat the '(' and see what is @@ -542,6 +568,17 @@ ParseInstruction(const StringRef &Name, SMLoc NameLoc, } } + // FIXME: Hack to handle recognizing s{hr,ar,hl}? $1. + if ((Name.startswith("shr") || Name.startswith("sar") || + Name.startswith("shl")) && + Operands.size() == 3 && + static_cast<X86Operand*>(Operands[1])->isImm() && + isa<MCConstantExpr>(static_cast<X86Operand*>(Operands[1])->getImm()) && + cast<MCConstantExpr>(static_cast<X86Operand*>(Operands[1])->getImm())->getValue() == 1) { + delete Operands[1]; + Operands.erase(Operands.begin() + 1); + } + return false; } @@ -577,12 +614,30 @@ bool X86ATTAsmParser::ParseDirectiveWord(unsigned Size, SMLoc L) { return false; } +// FIXME: Custom X86 cleanup function to implement a temporary hack to handle +// matching INCL/DECL correctly for x86_64. This needs to be replaced by a +// proper mechanism for supporting (ambiguous) feature dependent instructions. +void X86ATTAsmParser::InstructionCleanup(MCInst &Inst) { + if (!Is64Bit) return; + + switch (Inst.getOpcode()) { + case X86::DEC16r: Inst.setOpcode(X86::DEC64_16r); break; + case X86::DEC16m: Inst.setOpcode(X86::DEC64_16m); break; + case X86::DEC32r: Inst.setOpcode(X86::DEC64_32r); break; + case X86::DEC32m: Inst.setOpcode(X86::DEC64_32m); break; + case X86::INC16r: Inst.setOpcode(X86::INC64_16r); break; + case X86::INC16m: Inst.setOpcode(X86::INC64_16m); break; + case X86::INC32r: Inst.setOpcode(X86::INC64_32r); break; + case X86::INC32m: Inst.setOpcode(X86::INC64_32m); break; + } +} + extern "C" void LLVMInitializeX86AsmLexer(); // Force static initialization. extern "C" void LLVMInitializeX86AsmParser() { - RegisterAsmParser<X86ATTAsmParser> X(TheX86_32Target); - RegisterAsmParser<X86ATTAsmParser> Y(TheX86_64Target); + RegisterAsmParser<X86_32ATTAsmParser> X(TheX86_32Target); + RegisterAsmParser<X86_64ATTAsmParser> Y(TheX86_64Target); LLVMInitializeX86AsmLexer(); } |