[cfe-commits] r149796 - in /cfe/trunk: lib/AST/ExprConstant.cpp test/CXX/expr/expr.const/p2-0x.cpp test/SemaCXX/constant-expression-cxx11.cpp

Richard Smith richard-llvm at metafoo.co.uk
Sat Feb 4 17:23:16 PST 2012


Author: rsmith
Date: Sat Feb  4 19:23:16 2012
New Revision: 149796

URL: http://llvm.org/viewvc/llvm-project?rev=149796&view=rev
Log:
constexpr: Fix implementation of DR1311: check for volatile qualifiers in
lvalue-to-rvalue conversions on the source type of the conversion, not the
target type (which has them removed for non-class types).

Modified:
    cfe/trunk/lib/AST/ExprConstant.cpp
    cfe/trunk/test/CXX/expr/expr.const/p2-0x.cpp
    cfe/trunk/test/SemaCXX/constant-expression-cxx11.cpp

Modified: cfe/trunk/lib/AST/ExprConstant.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/ExprConstant.cpp?rev=149796&r1=149795&r2=149796&view=diff
==============================================================================
--- cfe/trunk/lib/AST/ExprConstant.cpp (original)
+++ cfe/trunk/lib/AST/ExprConstant.cpp Sat Feb  4 19:23:16 2012
@@ -1560,7 +1560,8 @@
 /// \param Info - Information about the ongoing evaluation.
 /// \param Conv - The expression for which we are performing the conversion.
 ///               Used for diagnostics.
-/// \param Type - The type we expect this conversion to produce.
+/// \param Type - The type we expect this conversion to produce, before
+///               stripping cv-qualifiers in the case of a non-clas type.
 /// \param LVal - The glvalue on which we are attempting to perform this action.
 /// \param RVal - The produced value will be placed here.
 static bool HandleLValueToRValueConversion(EvalInfo &Info, const Expr *Conv,
@@ -2536,7 +2537,9 @@
       if (!EvaluateLValue(E->getSubExpr(), LVal, Info))
         return false;
       CCValue RVal;
-      if (!HandleLValueToRValueConversion(Info, E, E->getType(), LVal, RVal))
+      // Note, we use the subexpression's type in order to retain cv-qualifiers.
+      if (!HandleLValueToRValueConversion(Info, E, E->getSubExpr()->getType(),
+                                          LVal, RVal))
         return false;
       return DerivedSuccess(RVal, E);
     }

Modified: cfe/trunk/test/CXX/expr/expr.const/p2-0x.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CXX/expr/expr.const/p2-0x.cpp?rev=149796&r1=149795&r2=149796&view=diff
==============================================================================
--- cfe/trunk/test/CXX/expr/expr.const/p2-0x.cpp (original)
+++ cfe/trunk/test/CXX/expr/expr.const/p2-0x.cpp Sat Feb  4 19:23:16 2012
@@ -268,14 +268,12 @@
   //   non-volatile const object with a preceding initialization, initialized
   //   with a constant expression  [Note: a string literal (2.14.5 [lex.string])
   //   corresponds to an array of such objects. -end note], or
-  volatile const int vi = 1; // expected-note 2{{here}}
+  volatile const int vi = 1; // expected-note {{here}}
   const int ci = 1;
   volatile const int &vrci = ci;
-  static_assert(vi, ""); // expected-error {{constant expression}} expected-note {{read of volatile object 'vi'}}
+  static_assert(vi, ""); // expected-error {{constant expression}} expected-note {{read of volatile-qualified type}}
   static_assert(const_cast<int&>(vi), ""); // expected-error {{constant expression}} expected-note {{read of volatile object 'vi'}}
-  static_assert(vrci, ""); // ok, vrci is converted to a prvalue before
-                           // evaluation and loses its volatility in the
-                           // conversion.
+  static_assert(vrci, ""); // expected-error {{constant expression}} expected-note {{read of volatile-qualified type}}
 
   // - a non-volatile glvalue of literal type that refers to a non-volatile
   //   object defined with constexpr, or that refers to a sub-object of such an
@@ -287,13 +285,14 @@
     volatile int v; // expected-note {{here}}
   };
   constexpr S s;
-  constexpr volatile S vs; // expected-note 2{{here}}
+  constexpr volatile S vs; // expected-note {{here}}
   constexpr const volatile S &vrs = s;
   static_assert(s.i, "");
-  static_assert(s.v, ""); // expected-error {{constant expression}} expected-note {{read of volatile member 'v'}}
-  static_assert(vs.i, ""); // expected-error {{constant expression}} expected-note {{read of volatile object 'vs'}}
+  static_assert(s.v, ""); // expected-error {{constant expression}} expected-note {{read of volatile-qualified type}}
+  static_assert(const_cast<int&>(s.v), ""); // expected-error {{constant expression}} expected-note {{read of volatile member 'v'}}
+  static_assert(vs.i, ""); // expected-error {{constant expression}} expected-note {{read of volatile-qualified type}}
   static_assert(const_cast<int&>(vs.i), ""); // expected-error {{constant expression}} expected-note {{read of volatile object 'vs'}}
-  static_assert(vrs.i, ""); // ok
+  static_assert(vrs.i, ""); // expected-error {{constant expression}} expected-note {{read of volatile-qualified type}}
 
   // - a non-volatile glvalue of literal type that refers to a non-volatile
   //   temporary object whose lifetime has not ended, initialized with a

Modified: cfe/trunk/test/SemaCXX/constant-expression-cxx11.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/SemaCXX/constant-expression-cxx11.cpp?rev=149796&r1=149795&r2=149796&view=diff
==============================================================================
--- cfe/trunk/test/SemaCXX/constant-expression-cxx11.cpp (original)
+++ cfe/trunk/test/SemaCXX/constant-expression-cxx11.cpp Sat Feb  4 19:23:16 2012
@@ -1011,17 +1011,23 @@
 volatile const int n2 = 0; // expected-note {{here}}
 int n3 = 37; // expected-note {{declared here}}
 
-constexpr int m1 = n1; // expected-error {{constant expression}} expected-note {{read of volatile object 'n1'}}
-constexpr int m2 = n2; // expected-error {{constant expression}} expected-note {{read of volatile object 'n2'}}
+constexpr int m1 = n1; // expected-error {{constant expression}} expected-note {{read of volatile-qualified type 'const volatile int'}}
+constexpr int m2 = n2; // expected-error {{constant expression}} expected-note {{read of volatile-qualified type 'const volatile int'}}
+constexpr int m1b = const_cast<const int&>(n1); // expected-error {{constant expression}} expected-note {{read of volatile object 'n1'}}
+constexpr int m2b = const_cast<const int&>(n2); // expected-error {{constant expression}} expected-note {{read of volatile object 'n2'}}
 
 struct T { int n; };
 const T t = { 42 }; // expected-note {{declared here}}
 
 constexpr int f(volatile int &&r) {
-  return r; // expected-note {{read of volatile temporary is not allowed in a constant expression}}
+  return r; // expected-note {{read of volatile-qualified type 'volatile int'}}
+}
+constexpr int g(volatile int &&r) {
+  return const_cast<int&>(r); // expected-note {{read of volatile temporary is not allowed in a constant expression}}
 }
 struct S {
-  int k : f(0); // expected-error {{constant expression}} expected-note {{temporary created here}} expected-note {{in call to 'f(0)'}}
+  int j : f(0); // expected-error {{constant expression}} expected-note {{in call to 'f(0)'}}
+  int k : g(0); // expected-error {{constant expression}} expected-note {{temporary created here}} expected-note {{in call to 'g(0)'}}
   int l : n3; // expected-error {{constant expression}} expected-note {{read of non-const variable}}
   int m : t.n; // expected-error {{constant expression}} expected-note {{read of non-constexpr variable}}
 };





More information about the cfe-commits mailing list