Implement ranking of standard conversion sequences by their qualification
conversions (e.g., comparing int* -> const int* against 
int* -> const volatile int*); see C++ 13.3.3.2p3 bullet 3.

Add Sema::UnwrapSimilarPointerTypes to simplify the control flow of
IsQualificationConversion and CompareQualificationConversion (and fix
the handling of the int* -> volatile int* conversion in the former).
 


git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@57978 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/Sema/SemaType.cpp b/lib/Sema/SemaType.cpp
index f1edabf..82e16cf 100644
--- a/lib/Sema/SemaType.cpp
+++ b/lib/Sema/SemaType.cpp
@@ -535,6 +535,29 @@
   return T;
 }
 
+/// UnwrapSimilarPointerTypes - If T1 and T2 are pointer types (FIXME:
+/// or pointer-to-member types) that may be similar (C++ 4.4),
+/// replaces T1 and T2 with the type that they point to and return
+/// true. If T1 and T2 aren't pointer types or pointer-to-member
+/// types, or if they are not similar at this level, returns false and
+/// leaves T1 and T2 unchanged. Top-level qualifiers on T1 and T2 are
+/// ignord. This function will typically be called in a loop that
+/// successively "unwraps" pointer and pointer-to-member types to
+/// compare them at each level.
+bool Sema::UnwrapSimilarPointerTypes(QualType& T1, QualType& T2)
+{
+  const PointerType *T1PtrType = T1->getAsPointerType(),
+                    *T2PtrType = T2->getAsPointerType();
+  if (T1PtrType && T2PtrType) {
+    T1 = T1PtrType->getPointeeType();
+    T2 = T2PtrType->getPointeeType();
+    return true;
+  }
+
+  // FIXME: pointer-to-member types
+  return false;
+}
+
 Sema::TypeResult Sema::ActOnTypeName(Scope *S, Declarator &D) {
   // C99 6.7.6: Type names have no identifier.  This is already validated by
   // the parser.