summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTom Stellard <thomas.stellard@amd.com>2014-04-11 19:55:07 +0000
committerTom Stellard <thomas.stellard@amd.com>2014-04-11 19:55:07 +0000
commit1c59c2012a317a8690aac3ec997e5aa93cb53871 (patch)
treee78f758c334dfec74a469c4d343801913d835411
parent0e215b0161c1b3d8cbb8bbad8bf63a3061986eb6 (diff)
downloadllvm-1c59c2012a317a8690aac3ec997e5aa93cb53871.tar.gz
llvm-1c59c2012a317a8690aac3ec997e5aa93cb53871.tar.bz2
llvm-1c59c2012a317a8690aac3ec997e5aa93cb53871.tar.xz
Merging r202774:
------------------------------------------------------------------------ r202774 | reid | 2014-03-03 19:33:17 -0500 (Mon, 03 Mar 2014) | 7 lines MC: Fix Intel assembly parser for [global + offset] We were dropping the displacement on the floor if we also had some immediate offset. Should fix PR19033. ------------------------------------------------------------------------ git-svn-id: https://llvm.org/svn/llvm-project/llvm/branches/release_34@206061 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r--lib/Target/X86/AsmParser/X86AsmParser.cpp40
-rw-r--r--test/MC/X86/intel-syntax.s9
2 files changed, 35 insertions, 14 deletions
diff --git a/lib/Target/X86/AsmParser/X86AsmParser.cpp b/lib/Target/X86/AsmParser/X86AsmParser.cpp
index 2afba6b75a..22b79b3b28 100644
--- a/lib/Target/X86/AsmParser/X86AsmParser.cpp
+++ b/lib/Target/X86/AsmParser/X86AsmParser.cpp
@@ -1181,16 +1181,23 @@ X86AsmParser::CreateMemForInlineAsm(unsigned SegReg, const MCExpr *Disp,
unsigned Scale, SMLoc Start, SMLoc End,
unsigned Size, StringRef Identifier,
InlineAsmIdentifierInfo &Info){
- if (isa<MCSymbolRefExpr>(Disp)) {
- // If this is not a VarDecl then assume it is a FuncDecl or some other label
- // reference. We need an 'r' constraint here, so we need to create register
- // operand to ensure proper matching. Just pick a GPR based on the size of
- // a pointer.
- if (!Info.IsVarDecl) {
- unsigned RegNo = is64BitMode() ? X86::RBX : X86::EBX;
- return X86Operand::CreateReg(RegNo, Start, End, /*AddressOf=*/true,
- SMLoc(), Identifier, Info.OpDecl);
- }
+ // If this is not a VarDecl then assume it is a FuncDecl or some other label
+ // reference. We need an 'r' constraint here, so we need to create register
+ // operand to ensure proper matching. Just pick a GPR based on the size of
+ // a pointer.
+ if (isa<MCSymbolRefExpr>(Disp) && !Info.IsVarDecl) {
+ unsigned RegNo = is64BitMode() ? X86::RBX : X86::EBX;
+ return X86Operand::CreateReg(RegNo, Start, End, /*AddressOf=*/true,
+ SMLoc(), Identifier, Info.OpDecl);
+ }
+
+ // We either have a direct symbol reference, or an offset from a symbol. The
+ // parser always puts the symbol on the LHS, so look there for size
+ // calculation purposes.
+ const MCBinaryExpr *BinOp = dyn_cast<MCBinaryExpr>(Disp);
+ bool IsSymRef =
+ isa<MCSymbolRefExpr>(BinOp ? BinOp->getLHS() : Disp);
+ if (IsSymRef) {
if (!Size) {
Size = Info.Type * 8; // Size is in terms of bits in this context.
if (Size)
@@ -1371,7 +1378,7 @@ X86Operand *X86AsmParser::ParseIntelBracExpression(unsigned SegReg, SMLoc Start,
if (ParseIntelExpression(SM, End))
return 0;
- const MCExpr *Disp;
+ const MCExpr *Disp = 0;
if (const MCExpr *Sym = SM.getSym()) {
// A symbolic displacement.
Disp = Sym;
@@ -1379,9 +1386,14 @@ X86Operand *X86AsmParser::ParseIntelBracExpression(unsigned SegReg, SMLoc Start,
RewriteIntelBracExpression(InstInfo->AsmRewrites, SM.getSymName(),
ImmDisp, SM.getImm(), BracLoc, StartInBrac,
End);
- } else {
- // An immediate displacement only.
- Disp = MCConstantExpr::Create(SM.getImm(), getContext());
+ }
+
+ if (SM.getImm() || !Disp) {
+ const MCExpr *Imm = MCConstantExpr::Create(SM.getImm(), getContext());
+ if (Disp)
+ Disp = MCBinaryExpr::CreateAdd(Disp, Imm, getContext());
+ else
+ Disp = Imm; // An immediate displacement only.
}
// Parse struct field access. Intel requires a dot, but MSVC doesn't. MSVC
diff --git a/test/MC/X86/intel-syntax.s b/test/MC/X86/intel-syntax.s
index 9677da731c..50f29e0a64 100644
--- a/test/MC/X86/intel-syntax.s
+++ b/test/MC/X86/intel-syntax.s
@@ -584,3 +584,12 @@ fsub ST(1)
fsubr ST(1)
fdiv ST(1)
fdivr ST(1)
+
+.bss
+.globl _g0
+.text
+
+// CHECK: movq _g0, %rbx
+// CHECK: movq _g0+8, %rcx
+mov rbx, qword ptr [_g0]
+mov rcx, qword ptr [_g0 + 8]