PR15730/PR16986 Allow dependently typed vector_size types.

As listed in the above PRs, vector_size doesn't allow
dependent types/values. This patch introduces a new
DependentVectorType to handle a VectorType that has a dependent
size or type.

In the future, ALL the vector-types should be able to create one
of these to handle dependent types/sizes as well. For example,
DependentSizedExtVectorType could likely be switched to just use
this instead, though that is left as an exercise for the future.


Differential Revision: https://reviews.llvm.org/D49045

llvm-svn: 337036
diff --git a/clang/lib/Sema/TreeTransform.h b/clang/lib/Sema/TreeTransform.h
index 6ee5eca..5ed92ae 100644
--- a/clang/lib/Sema/TreeTransform.h
+++ b/clang/lib/Sema/TreeTransform.h
@@ -818,6 +818,15 @@
   QualType RebuildVectorType(QualType ElementType, unsigned NumElements,
                              VectorType::VectorKind VecKind);
 
+  /// Build a new potentially dependently-sized extended vector type
+  /// given the element type and number of elements.
+  ///
+  /// By default, performs semantic analysis when building the vector type.
+  /// Subclasses may override this routine to provide different behavior.
+  QualType RebuildDependentVectorType(QualType ElementType, Expr *SizeExpr,
+                                           SourceLocation AttributeLoc,
+                                           VectorType::VectorKind);
+
   /// Build a new extended vector type given the element type and
   /// number of elements.
   ///
@@ -4750,6 +4759,44 @@
   return Result;
 }
 
+template <typename Derived>
+QualType TreeTransform<Derived>::TransformDependentVectorType(
+    TypeLocBuilder &TLB, DependentVectorTypeLoc TL) {
+  const DependentVectorType *T = TL.getTypePtr();
+  QualType ElementType = getDerived().TransformType(T->getElementType());
+  if (ElementType.isNull())
+    return QualType();
+
+  EnterExpressionEvaluationContext Unevaluated(
+      SemaRef, Sema::ExpressionEvaluationContext::ConstantEvaluated);
+
+  ExprResult Size = getDerived().TransformExpr(T->getSizeExpr());
+  Size = SemaRef.ActOnConstantExpression(Size);
+  if (Size.isInvalid())
+    return QualType();
+
+  QualType Result = TL.getType();
+  if (getDerived().AlwaysRebuild() || ElementType != T->getElementType() ||
+      Size.get() != T->getSizeExpr()) {
+    Result = getDerived().RebuildDependentVectorType(
+        ElementType, Size.get(), T->getAttributeLoc(), T->getVectorKind());
+    if (Result.isNull())
+      return QualType();
+  }
+
+  // Result might be dependent or not.
+  if (isa<DependentVectorType>(Result)) {
+    DependentVectorTypeLoc NewTL =
+        TLB.push<DependentVectorTypeLoc>(Result);
+    NewTL.setNameLoc(TL.getNameLoc());
+  } else {
+    VectorTypeLoc NewTL = TLB.push<VectorTypeLoc>(Result);
+    NewTL.setNameLoc(TL.getNameLoc());
+  }
+
+  return Result;
+}
+
 template<typename Derived>
 QualType TreeTransform<Derived>::TransformDependentSizedExtVectorType(
                                       TypeLocBuilder &TLB,
@@ -12381,6 +12428,13 @@
   return SemaRef.Context.getVectorType(ElementType, NumElements, VecKind);
 }
 
+template <typename Derived>
+QualType TreeTransform<Derived>::RebuildDependentVectorType(
+    QualType ElementType, Expr *SizeExpr, SourceLocation AttributeLoc,
+    VectorType::VectorKind VecKind) {
+  return SemaRef.BuildVectorType(ElementType, SizeExpr, AttributeLoc);
+}
+
 template<typename Derived>
 QualType TreeTransform<Derived>::RebuildExtVectorType(QualType ElementType,
                                                       unsigned NumElements,