This revision was automatically updated to reflect the committed changes.
Closed by commit rG8518742104ab: Fix type printing of array template args
(authored by reikdas, committed by v.g.vassilev).
Herald added a subscriber: cfe-commits.
Repository:
rG LLVM Github Monorepo
CHANGES SINCE LAST ACTION
https://reviews.llvm.org/D36368/new/
https://reviews.llvm.org/D36368
Files:
clang/lib/AST/TemplateBase.cpp
clang/test/CodeGenCXX/debug-info-codeview-display-name.cpp
clang/test/SemaTemplate/temp_arg_nontype_cxx11.cpp
Index: clang/test/SemaTemplate/temp_arg_nontype_cxx11.cpp
===================================================================
--- clang/test/SemaTemplate/temp_arg_nontype_cxx11.cpp
+++ clang/test/SemaTemplate/temp_arg_nontype_cxx11.cpp
@@ -77,3 +77,40 @@
};
void f(C<a> ca) { ca.f({}, 0); }
}
+
+using FourChars = const char[4];
+constexpr FourChars kEta = "Eta";
+constexpr const char kDes[4] = "Des";
+constexpr const char *kNull = "Phi";
+constexpr const char **kZero[] = {};
+
+template <const char *, typename T> class Column {};
+template <const char[], typename T> class Dolumn {};
+template <const char (*)[4], typename T> class Folumn {};
+template <FourChars *, typename T> class Golumn {};
+template <const char *const *, typename T> class Holumn {};
+template <const char *const *const *, typename T> class Jolumn {};
+template <const char **const (*)[0], typename T> class Iolumn {};
+
+class container {
+public:
+ int a;
+};
+template <int container::*> class Kolumn {};
+
+void lookup() {
+ Column<kEta, double>().ls(); // expected-error {{<kEta,}}
+ Column<kDes, double>().ls(); // expected-error {{<kDes,}}
+ Column<nullptr, double>().ls(); // expected-error {{<nullptr,}}
+ Dolumn<kEta, double>().ls(); // expected-error {{<kEta,}}
+ Dolumn<kDes, double>().ls(); // expected-error {{<kDes,}}
+ Folumn<&kEta, double>().ls(); // expected-error {{<&kEta,}}
+ Folumn<&kDes, double>().ls(); // expected-error {{<&kDes,}}
+ Golumn<&kEta, double>().ls(); // expected-error {{<&kEta,}}
+ Golumn<&kDes, double>().ls(); // expected-error {{<&kDes,}}
+ Holumn<&kNull, double>().ls(); // expected-error {{<&kNull,}}
+ Jolumn<kZero, double>().ls(); // expected-error {{<kZero,}}
+ Iolumn<&kZero, double>().ls(); // expected-error {{<&kZero,}}
+ Kolumn<&container::a>().ls(); // expected-error {{<&container::a}}
+ Kolumn<nullptr>().ls(); // expected-error {{<nullptr}}
+}
Index: clang/test/CodeGenCXX/debug-info-codeview-display-name.cpp
===================================================================
--- clang/test/CodeGenCXX/debug-info-codeview-display-name.cpp
+++ clang/test/CodeGenCXX/debug-info-codeview-display-name.cpp
@@ -86,6 +86,12 @@
template void fn_tmpl<int, freefunc>();
// CHECK-DAG: "fn_tmpl<int,&freefunc>"
+template <typename T, void (*)(void)>
+void fn_tmpl_typecheck() {}
+
+template void fn_tmpl_typecheck<int, &freefunc>();
+// CHECK-DAG: "fn_tmpl_typecheck<int,&freefunc>"
+
template <typename A, typename B, typename C> struct ClassTemplate { A a; B b; C c; };
ClassTemplate<char, short, ClassTemplate<int, int, int> > f;
// This will only show up in normal debug builds. The space in `> >` is
Index: clang/lib/AST/TemplateBase.cpp
===================================================================
--- clang/lib/AST/TemplateBase.cpp
+++ clang/lib/AST/TemplateBase.cpp
@@ -80,6 +80,26 @@
}
}
+static unsigned getArrayDepth(QualType type) {
+ unsigned count = 0;
+ while (const auto *arrayType = type->getAsArrayTypeUnsafe()) {
+ count++;
+ type = arrayType->getElementType();
+ }
+ return count;
+}
+
+static bool needsAmpersandOnTemplateArg(QualType paramType, QualType argType) {
+ // Generally, if the parameter type is a pointer, we must be taking the
+ // address of something and need a &. However, if the argument is an array,
+ // this could be implicit via array-to-pointer decay.
+ if (!paramType->isPointerType())
+ return paramType->isMemberPointerType();
+ if (argType->isArrayType())
+ return getArrayDepth(argType) == getArrayDepth(paramType->getPointeeType());
+ return true;
+}
+
//===----------------------------------------------------------------------===//
// TemplateArgument Implementation
//===----------------------------------------------------------------------===//
@@ -363,8 +383,10 @@
break;
}
}
- if (!getParamTypeForDecl()->isReferenceType())
- Out << '&';
+ if (auto *VD = dyn_cast<ValueDecl>(ND)) {
+ if (needsAmpersandOnTemplateArg(getParamTypeForDecl(), VD->getType()))
+ Out << "&";
+ }
ND->printQualifiedName(Out);
break;
}
_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits