aboutsummaryrefslogtreecommitdiff
path: root/lib/Sema/SemaStmt.cpp
diff options
context:
space:
mode:
authorChad Rosier <mcrosier@apple.com>2012-08-08 19:48:07 +0000
committerChad Rosier <mcrosier@apple.com>2012-08-08 19:48:07 +0000
commit62f22b87801882646418bae85111e565f7a53ddb (patch)
treec6b561e44f60d562e6626405c6ed058ee373099f /lib/Sema/SemaStmt.cpp
parentd24bf90ae72d7df5e0ef0a1d3dd2806462ec15b1 (diff)
[ms-inline asm] Refactor the logic to generate the AsmString into Sema. No
functional change intended. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@161518 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Sema/SemaStmt.cpp')
-rw-r--r--lib/Sema/SemaStmt.cpp36
1 files changed, 31 insertions, 5 deletions
diff --git a/lib/Sema/SemaStmt.cpp b/lib/Sema/SemaStmt.cpp
index 80f58b90c3..a8a06a93fc 100644
--- a/lib/Sema/SemaStmt.cpp
+++ b/lib/Sema/SemaStmt.cpp
@@ -2749,9 +2749,6 @@ StmtResult Sema::ActOnAsmStmt(SourceLocation AsmLoc, bool IsSimple,
// needSpaceAsmToken - This function handles whitespace around asm punctuation.
// Returns true if a space should be emitted.
-//
-// FIXME: This is replicated in ParseStmt.cpp. Maybe we should defer building
-// the AsmString (i.e., non-patched AsmString) until Sema.
static inline bool needSpaceAsmToken(Token currTok) {
static Token prevTok;
@@ -2840,13 +2837,42 @@ static std::string PatchMSAsmString(Sema &SemaRef, bool &IsSimple,
return Res;
}
+// Build the unmodified MSAsmString.
+static std::string buildMSAsmString(Sema &SemaRef,
+ ArrayRef<Token> AsmToks,
+ ArrayRef<unsigned> LineEnds) {
+ // Collect the tokens into a string
+ SmallString<512> Asm;
+ SmallString<512> TokenBuf;
+ TokenBuf.resize(512);
+ unsigned AsmLineNum = 0;
+ for (unsigned i = 0, e = AsmToks.size(); i < e; ++i) {
+ const char *ThisTokBuf = &TokenBuf[0];
+ bool StringInvalid = false;
+ unsigned ThisTokLen =
+ Lexer::getSpelling(AsmToks[i], ThisTokBuf, SemaRef.getSourceManager(),
+ SemaRef.getLangOpts(), &StringInvalid);
+ if (i && (!AsmLineNum || i != LineEnds[AsmLineNum-1]) &&
+ needSpaceAsmToken(AsmToks[i]))
+ Asm += ' ';
+ Asm += StringRef(ThisTokBuf, ThisTokLen);
+ if (i + 1 == LineEnds[AsmLineNum] && i + 1 != AsmToks.size()) {
+ Asm += '\n';
+ ++AsmLineNum;
+ }
+ }
+ return Asm.c_str();
+}
+
StmtResult Sema::ActOnMSAsmStmt(SourceLocation AsmLoc,
ArrayRef<Token> AsmToks,
- std::string &AsmString,
+ ArrayRef<unsigned> LineEnds,
SourceLocation EndLoc) {
// MS-style inline assembly is not fully supported, so emit a warning.
Diag(AsmLoc, diag::warn_unsupported_msasm);
+ std::string AsmString = buildMSAsmString(*this, AsmToks, LineEnds);
+
bool IsSimple;
// Rewrite operands to appease the AsmParser.
std::string PatchedAsmString =
@@ -2858,7 +2884,7 @@ StmtResult Sema::ActOnMSAsmStmt(SourceLocation AsmLoc,
MSAsmStmt *NS =
new (Context) MSAsmStmt(Context, AsmLoc, IsSimple, /* IsVolatile */ true,
- AsmToks, AsmString, EndLoc);
+ AsmToks, LineEnds, AsmString, EndLoc);
return Owned(NS);
}