Audit and finish the implementation of C++0x nullptr, fixing two
minor issues along the way:
  - Non-type template parameters of type 'std::nullptr_t' were not
  permitted.
  - We didn't properly introduce built-in operators for nullptr ==,
  !=, <, <=, >=, or > as candidate functions .

To my knowledge, there's only one (minor but annoying) part of nullptr
that hasn't been implemented: catching a thrown 'nullptr' as a pointer
or pointer-to-member, per C++0x [except.handle]p4.



git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@131813 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/test/SemaCXX/nullptr.cpp b/test/SemaCXX/nullptr.cpp
index 84c80aa..d69af58 100644
--- a/test/SemaCXX/nullptr.cpp
+++ b/test/SemaCXX/nullptr.cpp
@@ -60,6 +60,10 @@
 
   // You can reinterpret_cast nullptr to an integer.
   (void)reinterpret_cast<uintptr_t>(nullptr);
+  (void)reinterpret_cast<uintptr_t>(*pn);
+
+  int *ip = *pn;
+  if (*pn) { }
 
   // You can throw nullptr.
   throw nullptr;
@@ -104,3 +108,56 @@
     f("%p", nullptr);
   }
 }
+
+int array0[__is_scalar(nullptr_t)? 1 : -1];
+int array1[__is_pod(nullptr_t)? 1 : -1];
+int array2[sizeof(nullptr_t) == sizeof(void*)? 1 : -1];
+
+// FIXME: when we implement constexpr, this will be testable.
+#if 0
+int relational0[nullptr < nullptr? -1 : 1];
+int relational1[nullptr > nullptr? -1 : 1];
+int relational2[nullptr <= nullptr? 1 : -1];
+int relational3[nullptr >= nullptr? 1 : -1];
+int equality[nullptr == nullptr? 1 : -1];
+int inequality[nullptr != nullptr? -1 : 1];
+#endif
+
+namespace overloading {
+  int &f1(int*);
+  float &f1(bool);
+
+  void test_f1() {
+    int &ir = (f1)(nullptr);
+  }
+
+  struct ConvertsToNullPtr {
+    operator nullptr_t() const;
+  };
+
+  void test_conversion(ConvertsToNullPtr ctn) {
+    (void)(ctn == ctn);
+    (void)(ctn != ctn);
+    (void)(ctn <= ctn);
+    (void)(ctn >= ctn);
+    (void)(ctn < ctn);
+    (void)(ctn > ctn);
+  }
+}
+
+namespace templates {
+  template<typename T, nullptr_t Value>
+  struct X { 
+    X() { ptr = Value; }
+
+    T *ptr;
+  };
+  
+  X<int, nullptr> x;
+
+
+  template<int (*fp)(int), int* p, int A::* pmd, int (A::*pmf)(int)>
+  struct X2 {};
+  
+  X2<nullptr, nullptr, nullptr, nullptr> x2;
+}