]> granicus.if.org Git - clang/commitdiff
Allow lexer to handle string_view literals. Patch from Anton Bikineev.
authorEric Fiselier <eric@efcs.ca>
Fri, 30 Dec 2016 04:51:10 +0000 (04:51 +0000)
committerEric Fiselier <eric@efcs.ca>
Fri, 30 Dec 2016 04:51:10 +0000 (04:51 +0000)
This implements the compiler side of p0403r0. This patch was reviewed as
https://reviews.llvm.org/D26829.

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@290744 91177308-0d34-0410-b5e6-96231b3b80d8

include/clang/Lex/LiteralSupport.h
lib/Lex/Lexer.cpp
lib/Lex/LiteralSupport.cpp
lib/Sema/SemaDeclCXX.cpp
test/SemaCXX/cxx1z-user-defined-literals.cpp [new file with mode: 0644]

index 5f946fc8337e5bf1360277e2a90dcda345b3d47d..b66581b428b1f3289ed760ea40be4b32326f726a 100644 (file)
@@ -259,6 +259,8 @@ public:
     return UDSuffixOffset;
   }
 
+  static bool isValidUDSuffix(const LangOptions &LangOpts, StringRef Suffix);
+
 private:
   void init(ArrayRef<Token> StringToks);
   bool CopyStringFragment(const Token &Tok, const char *TokBegin,
index 37c7aa4c577e47278ce69184b46e97cea6ce748d..6025a6675125443319133eb784b37ddb73a9ab6e 100644 (file)
@@ -1713,9 +1713,9 @@ const char *Lexer::LexUDSuffix(Token &Result, const char *CurPtr,
                                          getLangOpts());
         if (!isIdentifierBody(Next)) {
           // End of suffix. Check whether this is on the whitelist.
-          IsUDSuffix = (Chars == 1 && Buffer[0] == 's') ||
-                       NumericLiteralParser::isValidUDSuffix(
-                           getLangOpts(), StringRef(Buffer, Chars));
+          const StringRef CompleteSuffix(Buffer, Chars);
+          IsUDSuffix = StringLiteralParser::isValidUDSuffix(getLangOpts(),
+                                                            CompleteSuffix);
           break;
         }
 
index 582ed3ff4721603ae591bc46b776274aa5ee509d..fbfd3fe5cce0f620880e31b8763012bc5b9f1665 100644 (file)
@@ -1708,3 +1708,12 @@ unsigned StringLiteralParser::getOffsetOfStringByte(const Token &Tok,
 
   return SpellingPtr-SpellingStart;
 }
+
+/// Determine whether a suffix is a valid ud-suffix. We avoid treating reserved
+/// suffixes as ud-suffixes, because the diagnostic experience is better if we
+/// treat it as an invalid suffix.
+bool StringLiteralParser::isValidUDSuffix(const LangOptions &LangOpts,
+                                          StringRef Suffix) {
+  return NumericLiteralParser::isValidUDSuffix(LangOpts, Suffix) ||
+         Suffix == "sv";
+}
index 21bdd945f06c509ee587210911f92b5557f30164..084bd4c45eda2b94beff8219602a5c0775081bcd 100644 (file)
@@ -12913,7 +12913,7 @@ bool Sema::CheckLiteralOperatorDeclaration(FunctionDecl *FnDecl) {
     //   Literal suffix identifiers that do not start with an underscore
     //   are reserved for future standardization.
     Diag(FnDecl->getLocation(), diag::warn_user_literal_reserved)
-      << NumericLiteralParser::isValidUDSuffix(getLangOpts(), LiteralName);
+      << StringLiteralParser::isValidUDSuffix(getLangOpts(), LiteralName);
   }
 
   return false;
diff --git a/test/SemaCXX/cxx1z-user-defined-literals.cpp b/test/SemaCXX/cxx1z-user-defined-literals.cpp
new file mode 100644 (file)
index 0000000..978fd2f
--- /dev/null
@@ -0,0 +1,21 @@
+// RUN: %clang_cc1 -std=c++1z %s -include %s -verify
+
+#ifndef INCLUDED
+#define INCLUDED
+
+#pragma clang system_header
+namespace std {
+  using size_t = decltype(sizeof(0));
+
+  struct string_view {};
+  string_view operator""sv(const char*, size_t);
+}
+
+#else
+
+using namespace std;
+string_view s = "foo"sv;
+const char* p = "bar"sv; // expected-error {{no viable conversion}}
+char error = 'x'sv; // expected-error {{invalid suffix}} expected-error {{expected ';'}}
+
+#endif