[cfe-commits] r158487 - in /cfe/trunk: lib/Lex/Lexer.cpp test/Lexer/c90.c test/Lexer/hexfloat.cpp

Richard Smith richard-llvm at metafoo.co.uk
Thu Jun 14 22:07:49 PDT 2012


Author: rsmith
Date: Fri Jun 15 00:07:49 2012
New Revision: 158487

URL: http://llvm.org/viewvc/llvm-project?rev=158487&view=rev
Log:
PR12717: Clang supports hexadecimal floating-point literals in all language
modes. For languages other than C99/C11, this isn't quite a conforming
extension, and for C++11, it breaks some reasonable code containing
user-defined literals.

In languages which don't officially have hexfloats, pare back this extension
to only apply in cases where the token starts 0x and does not contain an
underscore. The extension is still not quite conforming, but it's a lot closer
now.

Modified:
    cfe/trunk/lib/Lex/Lexer.cpp
    cfe/trunk/test/Lexer/c90.c
    cfe/trunk/test/Lexer/hexfloat.cpp

Modified: cfe/trunk/lib/Lex/Lexer.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Lex/Lexer.cpp?rev=158487&r1=158486&r2=158487&view=diff
==============================================================================
--- cfe/trunk/lib/Lex/Lexer.cpp (original)
+++ cfe/trunk/lib/Lex/Lexer.cpp Fri Jun 15 00:07:49 2012
@@ -1569,8 +1569,20 @@
   }
 
   // If we have a hex FP constant, continue.
-  if ((C == '-' || C == '+') && (PrevCh == 'P' || PrevCh == 'p'))
-    return LexNumericConstant(Result, ConsumeChar(CurPtr, Size, Result));
+  if ((C == '-' || C == '+') && (PrevCh == 'P' || PrevCh == 'p')) {
+    // Outside C99, we accept hexadecimal floating point numbers as a
+    // not-quite-conforming extension. Only do so if this looks like it's
+    // actually meant to be a hexfloat, and not if it has a ud-suffix.
+    bool IsHexFloat = true;
+    if (!LangOpts.C99) {
+      if (!isHexaLiteral(BufferPtr, LangOpts))
+        IsHexFloat = false;
+      else if (std::find(BufferPtr, CurPtr, '_') != CurPtr)
+        IsHexFloat = false;
+    }
+    if (IsHexFloat)
+      return LexNumericConstant(Result, ConsumeChar(CurPtr, Size, Result));
+  }
 
   // Update the location of token as well as BufferPtr.
   const char *TokStart = BufferPtr;

Modified: cfe/trunk/test/Lexer/c90.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Lexer/c90.c?rev=158487&r1=158486&r2=158487&view=diff
==============================================================================
--- cfe/trunk/test/Lexer/c90.c (original)
+++ cfe/trunk/test/Lexer/c90.c Fri Jun 15 00:07:49 2012
@@ -32,3 +32,10 @@
   (void)L"\u1234";  // expected-error {{unicode escape sequences are only valid in C99 or C++}}
   (void)L'\u1234';  // expected-error {{unicode escape sequences are only valid in C99 or C++}}
 }
+
+#define PREFIX(x) foo ## x
+int test4() {
+  int PREFIX(0p) = 0;
+  int *p = &PREFIX(0p+1);
+  return p[-1];
+}

Modified: cfe/trunk/test/Lexer/hexfloat.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Lexer/hexfloat.cpp?rev=158487&r1=158486&r2=158487&view=diff
==============================================================================
--- cfe/trunk/test/Lexer/hexfloat.cpp (original)
+++ cfe/trunk/test/Lexer/hexfloat.cpp Fri Jun 15 00:07:49 2012
@@ -5,3 +5,11 @@
 double d = 0x.2p2; // expected-warning{{hexadecimal floating constants are a C99 feature}}
 float g = 0x1.2p2; // expected-warning{{hexadecimal floating constants are a C99 feature}}
 double h = 0x1.p2; // expected-warning{{hexadecimal floating constants are a C99 feature}}
+
+// PR12717: In order to minimally diverge from the C++ standard, we do not lex
+// 'p[+-]' as part of a pp-number unless the token starts 0x and doesn't contain
+// an underscore.
+double i = 0p+3; // expected-error{{invalid suffix 'p' on integer constant}}
+#define PREFIX(x) foo ## x
+double foo0p = 1, j = PREFIX(0p+3); // ok
+double k = 0x42_amp+3; // expected-error-re{{invalid suffix '_amp' on integer constant|no matching literal operator for call to 'operator "" _amp'}}





More information about the cfe-commits mailing list