llvm.org GIT mirror llvm / b976e40
[ms-inline asm] Maintain a StringRef to reference a symbol in a parsed operand, rather than deriving the StringRef from the Start and End SMLocs. Using the Start and End SMLocs works fine for operands such as [Symbol], but not for operands such as [Symbol + ImmDisp]. All existing test cases that reference a variable exercise this patch. rdar://13602265 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@179109 91177308-0d34-0410-b5e6-96231b3b80d8 Chad Rosier 7 years ago
3 changed file(s) with 47 addition(s) and 38 deletion(s). Raw diff Collapse all Expand all
3636 void setMCOperandNum (unsigned OpNum) { MCOperandNum = OpNum; }
3737 unsigned getMCOperandNum() { return MCOperandNum; }
3838
39 unsigned getNameLen() {
40 assert (getStartLoc().isValid() && "Invalid StartLoc!");
41 assert (getEndLoc().isValid() && "Invalid EndLoc!");
42 return getEndLoc().getPointer() - getStartLoc().getPointer();
43 }
44
45 StringRef getName() {
46 return StringRef(getStartLoc().getPointer(), getNameLen());
47 }
39 virtual StringRef getSymName() { return StringRef(); }
4840
4941 /// isToken - Is this a token operand?
5042 virtual bool isToken() const = 0;
41174117 // Expr/Input or Output.
41184118 bool IsVarDecl;
41194119 unsigned Length, Size, Type;
4120 void *OpDecl = SI.LookupInlineAsmIdentifier(Operand->getName(), AsmLoc,
4120 StringRef SymName = Operand->getSymName();
4121 if (SymName.empty())
4122 continue;
4123
4124 void *OpDecl = SI.LookupInlineAsmIdentifier(SymName, AsmLoc,
41214125 Length, Size, Type,
41224126 IsVarDecl);
41234127 if (!OpDecl)
41244128 continue;
41254129
41264130 bool isOutput = (i == 1) && Desc.mayStore();
4131 SMLoc Start = SMLoc::getFromPointer(SymName.data());
41274132 if (isOutput) {
41284133 ++InputIdx;
41294134 OutputDecls.push_back(OpDecl);
41304135 OutputDeclsAddressOf.push_back(Operand->needAddressOf());
41314136 OutputConstraints.push_back('=' + Operand->getConstraint().str());
4132 AsmStrRewrites.push_back(AsmRewrite(AOK_Output, Operand->getStartLoc(),
4133 Operand->getNameLen()));
4137 AsmStrRewrites.push_back(AsmRewrite(AOK_Output, Start, SymName.size()));
41344138 } else {
41354139 InputDecls.push_back(OpDecl);
41364140 InputDeclsAddressOf.push_back(Operand->needAddressOf());
41374141 InputConstraints.push_back(Operand->getConstraint().str());
4138 AsmStrRewrites.push_back(AsmRewrite(AOK_Input, Operand->getStartLoc(),
4139 Operand->getNameLen()));
4142 AsmStrRewrites.push_back(AsmRewrite(AOK_Input, Start, SymName.size()));
41404143 }
41414144 }
41424145 }
6767 X86Operand *ParseMemOperand(unsigned SegReg, SMLoc StartLoc);
6868
6969 X86Operand *CreateMemForInlineAsm(const MCExpr *Disp, SMLoc Start, SMLoc End,
70 SMLoc SizeDirLoc, unsigned Size);
70 SMLoc SizeDirLoc, unsigned Size,
71 StringRef SymName);
7172
7273 bool ParseIntelDotOperator(const MCExpr *Disp, const MCExpr **NewDisp,
7374 SmallString<64> &Err);
175176
176177 SMLoc StartLoc, EndLoc;
177178 SMLoc OffsetOfLoc;
179 StringRef SymName;
178180 bool AddressOf;
179181
180182 struct TokOp {
208210
209211 X86Operand(KindTy K, SMLoc Start, SMLoc End)
210212 : Kind(K), StartLoc(Start), EndLoc(End) {}
213
214 StringRef getSymName() { return SymName; }
211215
212216 /// getStartLoc - Get the location of the first token of this operand.
213217 SMLoc getStartLoc() const { return StartLoc; }
472476
473477 static X86Operand *CreateReg(unsigned RegNo, SMLoc StartLoc, SMLoc EndLoc,
474478 bool AddressOf = false,
475 SMLoc OffsetOfLoc = SMLoc()) {
479 SMLoc OffsetOfLoc = SMLoc(),
480 StringRef SymName = StringRef()) {
476481 X86Operand *Res = new X86Operand(Register, StartLoc, EndLoc);
477482 Res->Reg.RegNo = RegNo;
478483 Res->AddressOf = AddressOf;
479484 Res->OffsetOfLoc = OffsetOfLoc;
485 Res->SymName = SymName;
480486 return Res;
481487 }
482488
488494
489495 /// Create an absolute memory operand.
490496 static X86Operand *CreateMem(const MCExpr *Disp, SMLoc StartLoc, SMLoc EndLoc,
491 unsigned Size = 0) {
497 unsigned Size = 0,
498 StringRef SymName = StringRef()) {
492499 X86Operand *Res = new X86Operand(Memory, StartLoc, EndLoc);
493500 Res->Mem.SegReg = 0;
494501 Res->Mem.Disp = Disp;
496503 Res->Mem.IndexReg = 0;
497504 Res->Mem.Scale = 1;
498505 Res->Mem.Size = Size;
506 Res->SymName = SymName;
499507 Res->AddressOf = false;
500508 return Res;
501509 }
504512 static X86Operand *CreateMem(unsigned SegReg, const MCExpr *Disp,
505513 unsigned BaseReg, unsigned IndexReg,
506514 unsigned Scale, SMLoc StartLoc, SMLoc EndLoc,
507 unsigned Size = 0) {
515 unsigned Size = 0,
516 StringRef SymName = StringRef()) {
508517 // We should never just have a displacement, that should be parsed as an
509518 // absolute memory operand.
510519 assert((SegReg || BaseReg || IndexReg) && "Invalid memory operand!");
519528 Res->Mem.IndexReg = IndexReg;
520529 Res->Mem.Scale = Scale;
521530 Res->Mem.Size = Size;
531 Res->SymName = SymName;
522532 Res->AddressOf = false;
523533 return Res;
524534 }
10611071
10621072 X86Operand *X86AsmParser::CreateMemForInlineAsm(const MCExpr *Disp, SMLoc Start,
10631073 SMLoc End, SMLoc SizeDirLoc,
1064 unsigned Size) {
1074 unsigned Size, StringRef SymName) {
10651075 bool NeedSizeDir = false;
10661076 bool IsVarDecl = false;
1077
10671078 if (const MCSymbolRefExpr *SymRef = dyn_cast(Disp)) {
10681079 const MCSymbol &Sym = SymRef->getSymbol();
10691080 // FIXME: The SemaLookup will fail if the name is anything other then an
10701081 // identifier.
10711082 // FIXME: Pass a valid SMLoc.
10721083 unsigned tLength, tSize, tType;
1073 SemaCallback->LookupInlineAsmIdentifier(Sym.getName(), NULL, tLength,
1074 tSize, tType, IsVarDecl);
1084 SemaCallback->LookupInlineAsmIdentifier(Sym.getName(), NULL, tLength, tSize,
1085 tType, IsVarDecl);
10751086 if (!Size) {
10761087 Size = tType * 8; // Size is in terms of bits in this context.
10771088 NeedSizeDir = Size > 0;
10841095 // a pointer.
10851096 if (!IsVarDecl) {
10861097 unsigned RegNo = is64BitMode() ? X86::RBX : X86::EBX;
1087 return X86Operand::CreateReg(RegNo, Start, End, /*AddressOf=*/true);
1098 return X86Operand::CreateReg(RegNo, Start, End, /*AddressOf=*/true, SMLoc(),
1099 SymName);
10881100 }
10891101
10901102 if (NeedSizeDir)
10951107 // as we don't know the actual value at this time. This is necessary to
10961108 // get the matching correct in some cases.
10971109 return X86Operand::CreateMem(/*SegReg*/0, Disp, /*BaseReg*/1, /*IndexReg*/0,
1098 /*Scale*/1, Start, End, Size);
1110 /*Scale*/1, Start, End, Size, SymName);
10991111 }
11001112
11011113 X86Operand *X86AsmParser::ParseIntelBracExpression(unsigned SegReg,
11261138 if (getLexer().isNot(AsmToken::RBrac))
11271139 return ErrorOperand(Parser.getTok().getLoc(), "Expected ']' token!");
11281140
1129 // Adjust the EndLoc due to the ']'.
1130 End = SMLoc::getFromPointer(Parser.getTok().getEndLoc().getPointer()-1);
1131 Parser.Lex();
1141 unsigned Len = Tok.getLoc().getPointer() - IdentStart.getPointer();
1142 StringRef SymName(IdentStart.getPointer(), Len);
1143 Parser.Lex(); // Eat ']'
11321144 if (!isParsingInlineAsm())
1133 return X86Operand::CreateMem(Disp, Start, End, Size);
1134 return CreateMemForInlineAsm(Disp, Start, End, SizeDirLoc, Size);
1145 return X86Operand::CreateMem(Disp, Start, End, Size, SymName);
1146 return CreateMemForInlineAsm(Disp, Start, End, SizeDirLoc, Size, SymName);
11351147 }
11361148 }
11371149
12121224 Disp = NewDisp;
12131225 }
12141226
1227 StringRef SymName;
12151228 int BaseReg = SM.getBaseReg();
12161229 int IndexReg = SM.getIndexReg();
12171230
12181231 // handle [-42]
12191232 if (!BaseReg && !IndexReg) {
12201233 if (!SegReg)
1221 return X86Operand::CreateMem(Disp, Start, End);
1234 return X86Operand::CreateMem(Disp, Start, End, Size);
12221235 else
12231236 return X86Operand::CreateMem(SegReg, Disp, 0, 0, 1, Start, End, Size);
12241237 }
12251238
12261239 int Scale = SM.getScale();
1227 return X86Operand::CreateMem(SegReg, Disp, BaseReg, IndexReg, Scale,
1228 Start, End, Size);
1240 return X86Operand::CreateMem(SegReg, Disp, BaseReg, IndexReg, Scale, Start,
1241 End, Size);
12291242 }
12301243
12311244 // Inline assembly may use variable names with namespace alias qualifiers.
12391252 if (getLexer().isNot(AsmToken::Colon))
12401253 return 0;
12411254
1242
12431255 bool Done = false;
12441256 const AsmToken &Tok = Parser.getTok();
1245 SMLoc IdentEnd = Tok.getEndLoc();
12461257 while (!Done) {
12471258 switch (getLexer().getKind()) {
12481259 default:
12571268 return ErrorOperand(Tok.getLoc(), "Expected an identifier token!");
12581269 break;
12591270 case AsmToken::Identifier:
1260 IdentEnd = Tok.getEndLoc();
12611271 getLexer().Lex(); // Consume the identifier.
12621272 break;
12631273 }
12641274 }
1265 size_t Len = IdentEnd.getPointer() - IdentStart.getPointer();
1275 size_t Len = Tok.getLoc().getPointer() - IdentStart.getPointer();
12661276 StringRef Identifier(IdentStart.getPointer(), Len);
12671277 MCSymbol *Sym = getContext().GetOrCreateSymbol(Identifier);
12681278 MCSymbolRefExpr::VariantKind Variant = MCSymbolRefExpr::VK_None;
13111321 return ParseIntelBracExpression(SegReg, Start, ImmDisp, Size);
13121322 }
13131323
1314 const MCExpr *Disp = MCConstantExpr::Create(0, getParser().getContext());
1324 const MCExpr *Disp = 0;
13151325 SMLoc IdentStart = Tok.getLoc();
13161326 if (getParser().parseExpression(Disp, End))
13171327 return 0;
13221332 if (X86Operand *Err = ParseIntelVarWithQualifier(Disp, IdentStart))
13231333 return Err;
13241334
1325 return CreateMemForInlineAsm(Disp, Start, End, Start, Size);
1335 unsigned Len = Tok.getLoc().getPointer() - IdentStart.getPointer();
1336 StringRef SymName(IdentStart.getPointer(), Len);
1337 return CreateMemForInlineAsm(Disp, Start, End, Start, Size, SymName);
13261338 }
13271339
13281340 /// Parse the '.' operator.
13981410 // register operand to ensure proper matching. Just pick a GPR based on
13991411 // the size of a pointer.
14001412 unsigned RegNo = is64BitMode() ? X86::RBX : X86::EBX;
1413 unsigned Len = End.getPointer() - Start.getPointer();
1414 StringRef SymName(Start.getPointer(), Len);
14011415 return X86Operand::CreateReg(RegNo, Start, End, /*GetAddress=*/true,
1402 OffsetOfLoc);
1416 OffsetOfLoc, SymName);
14031417 }
14041418
14051419 enum IntelOperatorKind {