aboutsummaryrefslogtreecommitdiff
path: root/clang/test
diff options
context:
space:
mode:
Diffstat (limited to 'clang/test')
-rw-r--r--clang/test/AST/ByteCode/cxx11.cpp13
-rw-r--r--clang/test/Analysis/store-to-immutable-basic.c121
-rw-r--r--clang/test/Analysis/store-to-immutable-basic.cpp72
-rw-r--r--clang/test/Analysis/store-to-immutable-lambda-init.cpp13
-rw-r--r--clang/test/CodeGenCXX/debug-info-class.cpp46
-rw-r--r--clang/test/CodeGenCXX/mangle-concept.cpp3
-rw-r--r--clang/test/CodeGenCXX/vtable-debug-info-inheritance-simple.cpp11
-rw-r--r--clang/test/CodeGenOpenCL/preserve_vec3.cl22
-rw-r--r--clang/test/Frontend/dump-minimization-hints-cpp20-modules.cpp117
-rw-r--r--clang/test/Modules/ExtDebugInfo.cpp15
-rw-r--r--clang/test/Parser/cxx-template-template-recovery.cpp12
-rw-r--r--clang/test/Parser/cxx2a-concept-declaration.cpp5
-rw-r--r--clang/test/Parser/cxx2c-template-template-param.cpp79
-rw-r--r--clang/test/Sema/riscv-interrupt-attr-rnmi.c28
-rw-r--r--clang/test/SemaCXX/cxx2c-template-template-param.cpp352
15 files changed, 861 insertions, 48 deletions
diff --git a/clang/test/AST/ByteCode/cxx11.cpp b/clang/test/AST/ByteCode/cxx11.cpp
index 378702f..8a125a4 100644
--- a/clang/test/AST/ByteCode/cxx11.cpp
+++ b/clang/test/AST/ByteCode/cxx11.cpp
@@ -289,3 +289,16 @@ namespace OverlappingStrings {
}
+
+namespace NonConstLocal {
+ int a() {
+ const int t=t; // both-note {{declared here}}
+
+ switch(1) {
+ case t:; // both-note {{initializer of 't' is not a constant expression}} \
+ // both-error {{case value is not a constant expression}}
+ }
+ }
+}
+
+
diff --git a/clang/test/Analysis/store-to-immutable-basic.c b/clang/test/Analysis/store-to-immutable-basic.c
new file mode 100644
index 0000000..f7d8878
--- /dev/null
+++ b/clang/test/Analysis/store-to-immutable-basic.c
@@ -0,0 +1,121 @@
+// RUN: %clang_analyze_cc1 -analyzer-checker=alpha.core.StoreToImmutable -verify %s
+
+// Test basic functionality of StoreToImmutable checker for the C programming language.
+
+const int tentative_global_const; // expected-note {{Memory region is declared as immutable here}}
+
+void test_direct_write_to_tentative_const_global() {
+ *(int*)&tentative_global_const = 100; // expected-warning {{Trying to write to immutable memory in global read-only storage}}
+}
+
+const int global_const = 42; // expected-note {{Memory region is declared as immutable here}}
+
+void test_direct_write_to_const_global() {
+ // This should trigger a warning about writing to immutable memory
+ *(int*)&global_const = 100; // expected-warning {{Trying to write to immutable memory in global read-only storage}}
+}
+
+void test_write_through_const_pointer() {
+ const int local_const = 10; // expected-note {{Memory region is declared as immutable here}}
+ int *ptr = (int*)&local_const;
+ *ptr = 20; // expected-warning {{Trying to write to immutable memory}}
+}
+
+void test_write_to_const_array() {
+ const int arr[5] = {1, 2, 3, 4, 5}; // expected-note {{Enclosing memory region is declared as immutable here}}
+ int *ptr = (int*)arr;
+ ptr[0] = 10; // expected-warning {{Trying to write to immutable memory}}
+}
+
+struct TestStruct {
+ const int x; // expected-note 2 {{Memory region is declared as immutable here}}
+ int y;
+};
+
+void test_write_to_const_struct_member() {
+ struct TestStruct s = {1, 2};
+ int *ptr = (int*)&s.x;
+ *ptr = 10; // expected-warning {{Trying to write to immutable memory}}
+}
+
+const int global_array[3] = {1, 2, 3}; // expected-note {{Enclosing memory region is declared as immutable here}}
+
+void test_write_to_const_global_array() {
+ int *ptr = (int*)global_array;
+ ptr[0] = 10; // expected-warning {{Trying to write to immutable memory in global read-only storage}}
+}
+
+const struct TestStruct global_struct = {1, 2};
+
+void test_write_to_const_global_struct() {
+ int *ptr = (int*)&global_struct.x;
+ *ptr = 10; // expected-warning {{Trying to write to immutable memory in global read-only storage}}
+}
+
+
+void test_write_to_const_param(const int param) { // expected-note {{Memory region is declared as immutable here}}
+ *(int*)&param = 100; // expected-warning {{Trying to write to immutable memory}}
+}
+
+void test_write_to_const_ptr_param(const int *param) {
+ *(int*)param = 100; // expected-warning {{Trying to write to immutable memory}}
+}
+
+void test_write_to_const_array_param(const int arr[5]) {
+ *(int*)arr = 100; // expected-warning {{Trying to write to immutable memory}}
+}
+
+struct ParamStruct {
+ const int z; // expected-note 2 {{Memory region is declared as immutable here}}
+ int w;
+};
+
+void test_write_to_const_struct_param(const struct ParamStruct s) {
+ *(int*)&s.z = 100; // expected-warning {{Trying to write to immutable memory}}
+}
+
+void test_write_to_const_struct_ptr_param(const struct ParamStruct *s) {
+ *(int*)&s->z = 100; // expected-warning {{Trying to write to immutable memory}}
+}
+
+void test_write_to_nonconst() {
+ int non_const = 42;
+ *(int*)&non_const = 100; // No warning expected
+}
+
+int global_non_const = 42;
+
+void test_write_to_nonconst_global() {
+ *(int*)&global_non_const = 100; // No warning expected
+}
+
+struct NonConstStruct {
+ int x;
+ int y;
+};
+
+void test_write_to_nonconst_struct_member() {
+ struct NonConstStruct s = {1, 2};
+ *(int*)&s.x = 100; // No warning expected
+}
+
+void test_write_to_nonconst_param(int param) {
+ *(int*)&param = 100; // No warning expected
+}
+
+void test_normal_assignment() {
+ int x = 42;
+ x = 100; // No warning expected
+}
+
+void test_const_ptr_to_nonconst_data() {
+ int data = 42;
+ const int *ptr = &data;
+ *(int*)ptr = 100; // No warning expected
+}
+
+void test_const_ptr_to_const_data() {
+ const int data = 42; // expected-note {{Memory region is declared as immutable here}}
+ const int *ptr = &data;
+ *(int*)ptr = 100; // expected-warning {{Trying to write to immutable memory}}
+}
diff --git a/clang/test/Analysis/store-to-immutable-basic.cpp b/clang/test/Analysis/store-to-immutable-basic.cpp
new file mode 100644
index 0000000..63319d9
--- /dev/null
+++ b/clang/test/Analysis/store-to-immutable-basic.cpp
@@ -0,0 +1,72 @@
+// RUN: %clang_analyze_cc1 -analyzer-checker=alpha.core.StoreToImmutable -std=c++17 -verify %s
+
+void test_write_to_const_ref_param(const int &param) {
+ *(int*)&param = 100; // expected-warning {{Trying to write to immutable memory}}
+}
+
+// FIXME: This should warn in C mode too.
+void test_write_to_string_literal() {
+ char *str = (char*)"hello";
+ str[0] = 'H'; // expected-warning {{Trying to write to immutable memory}}
+}
+
+struct ParamStruct {
+ const int z; // expected-note {{Memory region is declared as immutable here}}
+ int w;
+};
+
+void test_write_to_const_struct_ref_param(const ParamStruct &s) {
+ *(int*)&s.z = 100; // expected-warning {{Trying to write to immutable memory}}
+}
+
+void test_const_ref_to_nonconst_data() {
+ int data = 42;
+ const int &ref = data;
+ *(int*)&ref = 100; // No warning expected
+}
+
+void test_const_ref_to_const_data() {
+ const int data = 42; // expected-note {{Memory region is declared as immutable here}}
+ const int &ref = data;
+ *(int*)&ref = 100; // expected-warning {{Trying to write to immutable memory}}
+}
+
+void test_ref_to_nonconst_data() {
+ int data = 42;
+ int &ref = data;
+ ref = 100; // No warning expected
+}
+
+void test_ref_to_const_data() {
+ const int data = 42; // expected-note {{Memory region is declared as immutable here}}
+ int &ref = *(int*)&data;
+ ref = 100; // expected-warning {{Trying to write to immutable memory}}
+}
+
+struct MultipleLayerStruct {
+ MultipleLayerStruct();
+ const int data; // expected-note {{Memory region is declared as immutable here}}
+ const int buf[10]; // expected-note {{Enclosing memory region is declared as immutable here}}
+};
+
+MultipleLayerStruct MLS[10];
+
+void test_multiple_layer_struct_array_member() {
+ int *p = (int*)&MLS[2].data;
+ *p = 4; // expected-warning {{Trying to write to immutable memory}}
+}
+
+void test_multiple_layer_struct_array_array_member() {
+ int *p = (int*)&MLS[2].buf[3];
+ *p = 4; // expected-warning {{Trying to write to immutable memory}}
+}
+
+struct StructWithNonConstMember {
+ int x;
+};
+
+const StructWithNonConstMember SWNCM{0}; // expected-note {{Enclosing memory region is declared as immutable here}}
+
+void test_write_to_non_const_member_of_const_struct() {
+ *(int*)&SWNCM.x = 100; // expected-warning {{Trying to write to immutable memory in global read-only storage}}
+}
diff --git a/clang/test/Analysis/store-to-immutable-lambda-init.cpp b/clang/test/Analysis/store-to-immutable-lambda-init.cpp
new file mode 100644
index 0000000..764ce3f
--- /dev/null
+++ b/clang/test/Analysis/store-to-immutable-lambda-init.cpp
@@ -0,0 +1,13 @@
+// RUN: %clang_analyze_cc1 -analyzer-checker=alpha.core.StoreToImmutable -std=c++11 -verify %s
+// RUN: %clang_analyze_cc1 -analyzer-checker=alpha.core.StoreToImmutable -std=c++14 -verify %s
+// RUN: %clang_analyze_cc1 -analyzer-checker=alpha.core.StoreToImmutable -std=c++17 -verify %s
+// RUN: %clang_analyze_cc1 -analyzer-checker=alpha.core.StoreToImmutable -std=c++20 -verify %s
+
+// expected-no-diagnostics
+
+// In C++14 and before, when initializing a lambda, the statement given in the checkBind callback is not the whole DeclExpr, but the CXXConstructExpr of the lambda object.
+// FIXME: Once the API of checkBind provides more information about the statement, the checker should be simplified, and this test case will no longer be a cornercase in the checker.
+
+void test_const_lambda_initialization_pre_cpp17() {
+ const auto lambda = [](){}; // No warning expected
+}
diff --git a/clang/test/CodeGenCXX/debug-info-class.cpp b/clang/test/CodeGenCXX/debug-info-class.cpp
index 0bc4fdaa..aa24a63 100644
--- a/clang/test/CodeGenCXX/debug-info-class.cpp
+++ b/clang/test/CodeGenCXX/debug-info-class.cpp
@@ -99,12 +99,12 @@ int main(int argc, char **argv) {
return 0;
}
-// RUN: %clang_cc1 -triple x86_64-unknown_unknown -emit-llvm -debug-info-kind=limited -fexceptions -std=c++98 %s -o - | FileCheck -check-prefix=CHECK98 -check-prefix=CHECK %s
-// RUN: %clang_cc1 -triple i686-cygwin -emit-llvm -debug-info-kind=limited -fexceptions -std=c++98 %s -o - | FileCheck -check-prefix=CHECK98 -check-prefix=CHECK %s
-// RUN: %clang_cc1 -triple armv7l-unknown-linux-gnueabihf -emit-llvm -debug-info-kind=limited -fexceptions -std=c++98 %s -o - | FileCheck -check-prefix=CHECK98 -check-prefix=CHECK %s
-// RUN: %clang_cc1 -triple x86_64-unknown_unknown -emit-llvm -debug-info-kind=limited -fexceptions -std=c++11 %s -o - | FileCheck -check-prefix=CHECK11 -check-prefix=CHECK %s
-// RUN: %clang_cc1 -triple i686-cygwin -emit-llvm -debug-info-kind=limited -fexceptions -std=c++11 %s -o - | FileCheck -check-prefix=CHECK11 -check-prefix=CHECK %s
-// RUN: %clang_cc1 -triple armv7l-unknown-linux-gnueabihf -emit-llvm -debug-info-kind=limited -fexceptions -std=c++11 %s -o - | FileCheck -check-prefix=CHECK11 -check-prefix=CHECK %s
+// RUN: %clang_cc1 -triple x86_64-unknown_unknown -emit-llvm -debug-info-kind=limited -fexceptions -std=c++98 %s -o - | FileCheck -check-prefix=CHECK98 -check-prefix=CHECK -check-prefix=CHECKELF %s
+// RUN: %clang_cc1 -triple i686-cygwin -emit-llvm -debug-info-kind=limited -fexceptions -std=c++98 %s -o - | FileCheck -check-prefix=CHECK98 -check-prefix=CHECK -check-prefix=CHECKCOFF %s
+// RUN: %clang_cc1 -triple armv7l-unknown-linux-gnueabihf -emit-llvm -debug-info-kind=limited -fexceptions -std=c++98 %s -o - | FileCheck -check-prefix=CHECK98 -check-prefix=CHECK -check-prefix=CHECKELF %s
+// RUN: %clang_cc1 -triple x86_64-unknown_unknown -emit-llvm -debug-info-kind=limited -fexceptions -std=c++11 %s -o - | FileCheck -check-prefix=CHECK11 -check-prefix=CHECK -check-prefix=CHECKELF %s
+// RUN: %clang_cc1 -triple i686-cygwin -emit-llvm -debug-info-kind=limited -fexceptions -std=c++11 %s -o - | FileCheck -check-prefix=CHECK11 -check-prefix=CHECK -check-prefix=CHECKCOFF %s
+// RUN: %clang_cc1 -triple armv7l-unknown-linux-gnueabihf -emit-llvm -debug-info-kind=limited -fexceptions -std=c++11 %s -o - | FileCheck -check-prefix=CHECK11 -check-prefix=CHECK -check-prefix=CHECKELF %s
// CHECK98: invoke {{.+}} @_ZN1BD1Ev(ptr {{[^,]*}} %b)
// CHECK98-NEXT: unwind label %{{.+}}, !dbg ![[EXCEPTLOC:.*]]
@@ -122,6 +122,14 @@ int main(int argc, char **argv) {
// CHECK-SAME: ){{$}}
// CHECK: ![[INT:[0-9]+]] = !DIBasicType(name: "int"
+// CHECKCOFF: !DICompositeType(tag: DW_TAG_structure_type, name: "foo"
+// CHECKCOFF: !DICompositeType(tag: DW_TAG_class_type, name: "bar"
+// CHECKCOFF: !DICompositeType(tag: DW_TAG_union_type, name: "baz"
+// CHECKCOFF: !DICompositeType(tag: DW_TAG_class_type, name: "B"
+// CHECKCOFF-NOT: DIFlagFwdDecl
+// CHECKCOFF-SAME: ){{$}}
+// CHECKCOFF: !DIDerivedType(tag: DW_TAG_member, name: "_vptr$B",
+// CHECKCOFF-SAME: DIFlagArtificial
// CHECK: [[C:![0-9]*]] = distinct !DICompositeType(tag: DW_TAG_structure_type, name: "C",
// CHECK-NOT: DIFlagFwdDecl
@@ -137,19 +145,19 @@ int main(int argc, char **argv) {
// CHECK-SAME: DIFlagStaticMember
// CHECK: [[C_DTOR]] = !DISubprogram(name: "~C"
-// CHECK: !DICompositeType(tag: DW_TAG_structure_type, name: "K"
-// CHECK-SAME: identifier: "_ZTS1K"
-// CHECK-SAME: ){{$}}
+// CHECKELF: !DICompositeType(tag: DW_TAG_structure_type, name: "K"
+// CHECKELF-SAME: identifier: "_ZTS1K"
+// CHECKELF-SAME: ){{$}}
-// CHECK: !DICompositeType(tag: DW_TAG_class_type, name: "B"
-// CHECK-NOT: DIFlagFwdDecl
-// CHECK-SAME: ){{$}}
-// CHECK: !DIDerivedType(tag: DW_TAG_member, name: "_vptr$B",
-// CHECK-SAME: DIFlagArtificial
+// CHECKELF: !DICompositeType(tag: DW_TAG_class_type, name: "B"
+// CHECKELF-NOT: DIFlagFwdDecl
+// CHECKELF-SAME: ){{$}}
+// CHECKELF: !DIDerivedType(tag: DW_TAG_member, name: "_vptr$B",
+// CHECKELF-SAME: DIFlagArtificial
-// CHECK: !DICompositeType(tag: DW_TAG_structure_type, name: "foo"
-// CHECK: !DICompositeType(tag: DW_TAG_class_type, name: "bar"
-// CHECK: !DICompositeType(tag: DW_TAG_union_type, name: "baz"
+// CHECKELF: !DICompositeType(tag: DW_TAG_structure_type, name: "foo"
+// CHECKELF: !DICompositeType(tag: DW_TAG_class_type, name: "bar"
+// CHECKELF: !DICompositeType(tag: DW_TAG_union_type, name: "baz"
// CHECK: [[D:![0-9]+]] = !DICompositeType(tag: DW_TAG_structure_type, name: "D"
// CHECK-SAME: size:
@@ -162,6 +170,10 @@ int main(int argc, char **argv) {
// CHECK-NOT: identifier:
// CHECK-SAME: ){{$}}
+// CHECKCOFF: !DICompositeType(tag: DW_TAG_structure_type, name: "K"
+// CHECKCOFF-SAME: identifier: "_ZTS1K"
+// CHECKCOFF-SAME: ){{$}}
+
// CHECK: [[L:![0-9]+]] = distinct !DICompositeType(tag: DW_TAG_structure_type, name: "L"
// CHECK-SAME: ){{$}}
// CHECK: [[L_FUNC_DECL:![0-9]*]] = !DISubprogram(name: "func",{{.*}} scope: [[L]]
diff --git a/clang/test/CodeGenCXX/mangle-concept.cpp b/clang/test/CodeGenCXX/mangle-concept.cpp
index aa0940c..63e819b 100644
--- a/clang/test/CodeGenCXX/mangle-concept.cpp
+++ b/clang/test/CodeGenCXX/mangle-concept.cpp
@@ -6,7 +6,8 @@
namespace test1 {
template <bool> struct S {};
template <typename> concept C = true;
-template <typename T = int> S<C<T>> f0() { return S<C<T>>{}; }
+template <typename T = int>
+S<C<T>> f0() { return S<C<T>>{}; }
template S<C<int>> f0<>();
// CHECK: @_ZN5test12f0IiEENS_1SIX1CIT_EEEEv(
// CLANG17: @_ZN5test12f0IiEENS_1SIL_ZNS_1CIT_EEEEEv(
diff --git a/clang/test/CodeGenCXX/vtable-debug-info-inheritance-simple.cpp b/clang/test/CodeGenCXX/vtable-debug-info-inheritance-simple.cpp
index 249586f..b24ece1 100644
--- a/clang/test/CodeGenCXX/vtable-debug-info-inheritance-simple.cpp
+++ b/clang/test/CodeGenCXX/vtable-debug-info-inheritance-simple.cpp
@@ -1,5 +1,3 @@
-// REQUIRES: target={{x86_64.*-linux.*}}
-
// Simple inheritance case:
// For CBase and CDerived we check:
// - Generation of their vtables (including attributes).
@@ -30,13 +28,20 @@ int main() {
return 0;
}
-// RUN: %clang --target=x86_64-linux -Xclang -disable-O0-optnone -Xclang -disable-llvm-passes -emit-llvm -S -g %s -o - | FileCheck %s
+// RUN: %clang_cc1 -triple x86_64-linux -emit-llvm -mrelocation-model pic -pic-is-pie -debug-info-kind=limited -dwarf-version=5 -disable-O0-optnone -disable-llvm-passes %s -o - | FileCheck %s
+// RUN: %clang_cc1 -triple x86_64-windows-gnu -emit-llvm -mrelocation-model pic -pic-is-pie -debug-info-kind=limited -dwarf-version=5 -disable-O0-optnone -disable-llvm-passes %s -o - | FileCheck %s --check-prefix=COFF
// CHECK: $_ZTVN3NSP5CBaseE = comdat any
// CHECK: $_ZTV8CDerived = comdat any
// CHECK: @_ZTVN3NSP5CBaseE = linkonce_odr {{dso_local|hidden}} unnamed_addr constant {{.*}}, comdat, align 8, !dbg [[BASE_VTABLE_VAR:![0-9]*]]
// CHECK: @_ZTV8CDerived = linkonce_odr {{dso_local|hidden}} unnamed_addr constant {{.*}}, comdat, align 8, !dbg [[DERIVED_VTABLE_VAR:![0-9]*]]
+// COFF: @_ZTVN3NSP5CBaseE = linkonce_odr {{dso_local|hidden}} unnamed_addr constant {{.*}}, comdat, align 8
+// COFF-NOT: !dbg
+// COFF-SAME: {{$}}
+// COFF: @_ZTV8CDerived = linkonce_odr {{dso_local|hidden}} unnamed_addr constant {{.*}}, comdat, align 8
+// COFF-NOT: !dbg
+// COFF-SAME: {{$}}
// CHECK: [[BASE_VTABLE_VAR]] = !DIGlobalVariableExpression(var: [[BASE_VTABLE:![0-9]*]], expr: !DIExpression())
// CHECK-NEXT: [[BASE_VTABLE]] = distinct !DIGlobalVariable(name: "_vtable$", linkageName: "_ZTVN3NSP5CBaseE"
diff --git a/clang/test/CodeGenOpenCL/preserve_vec3.cl b/clang/test/CodeGenOpenCL/preserve_vec3.cl
index 49ebae6..e73657e 100644
--- a/clang/test/CodeGenOpenCL/preserve_vec3.cl
+++ b/clang/test/CodeGenOpenCL/preserve_vec3.cl
@@ -11,8 +11,8 @@ typedef float float4 __attribute__((ext_vector_type(4)));
// CHECK-LABEL: define dso_local spir_kernel void @foo(
// CHECK-SAME: ptr addrspace(1) noundef readonly align 16 captures(none) [[A:%.*]], ptr addrspace(1) noundef writeonly align 16 captures(none) initializes((0, 16)) [[B:%.*]]) local_unnamed_addr #[[ATTR0:[0-9]+]] !kernel_arg_addr_space [[META3:![0-9]+]] !kernel_arg_access_qual [[META4:![0-9]+]] !kernel_arg_type [[META5:![0-9]+]] !kernel_arg_base_type [[META6:![0-9]+]] !kernel_arg_type_qual [[META7:![0-9]+]] {
// CHECK-NEXT: [[ENTRY:.*:]]
-// CHECK-NEXT: [[LOADVECN:%.*]] = load <4 x float>, ptr addrspace(1) [[A]], align 16
-// CHECK-NEXT: [[EXTRACTVEC1:%.*]] = shufflevector <4 x float> [[LOADVECN]], <4 x float> poison, <4 x i32> <i32 0, i32 1, i32 2, i32 poison>
+// CHECK-NEXT: [[TMP0:%.*]] = load <3 x float>, ptr addrspace(1) [[A]], align 16
+// CHECK-NEXT: [[EXTRACTVEC1:%.*]] = shufflevector <3 x float> [[TMP0]], <3 x float> poison, <4 x i32> <i32 0, i32 1, i32 2, i32 poison>
// CHECK-NEXT: store <4 x float> [[EXTRACTVEC1]], ptr addrspace(1) [[B]], align 16, !tbaa [[TBAA8:![0-9]+]]
// CHECK-NEXT: ret void
//
@@ -23,8 +23,8 @@ void kernel foo(global float3 *a, global float3 *b) {
// CHECK-LABEL: define dso_local spir_kernel void @float4_to_float3(
// CHECK-SAME: ptr addrspace(1) noundef writeonly align 16 captures(none) initializes((0, 16)) [[A:%.*]], ptr addrspace(1) noundef readonly align 16 captures(none) [[B:%.*]]) local_unnamed_addr #[[ATTR0]] !kernel_arg_addr_space [[META3]] !kernel_arg_access_qual [[META4]] !kernel_arg_type [[META11:![0-9]+]] !kernel_arg_base_type [[META12:![0-9]+]] !kernel_arg_type_qual [[META7]] {
// CHECK-NEXT: [[ENTRY:.*:]]
-// CHECK-NEXT: [[TMP0:%.*]] = load <4 x float>, ptr addrspace(1) [[B]], align 16, !tbaa [[TBAA8]]
-// CHECK-NEXT: [[EXTRACTVEC:%.*]] = shufflevector <4 x float> [[TMP0]], <4 x float> poison, <4 x i32> <i32 0, i32 1, i32 2, i32 poison>
+// CHECK-NEXT: [[TMP0:%.*]] = load <3 x float>, ptr addrspace(1) [[B]], align 16, !tbaa [[TBAA8]]
+// CHECK-NEXT: [[EXTRACTVEC:%.*]] = shufflevector <3 x float> [[TMP0]], <3 x float> poison, <4 x i32> <i32 0, i32 1, i32 2, i32 poison>
// CHECK-NEXT: store <4 x float> [[EXTRACTVEC]], ptr addrspace(1) [[A]], align 16, !tbaa [[TBAA8]]
// CHECK-NEXT: ret void
//
@@ -35,8 +35,8 @@ void kernel float4_to_float3(global float3 *a, global float4 *b) {
// CHECK-LABEL: define dso_local spir_kernel void @float3_to_float4(
// CHECK-SAME: ptr addrspace(1) noundef readonly align 16 captures(none) [[A:%.*]], ptr addrspace(1) noundef writeonly align 16 captures(none) initializes((0, 16)) [[B:%.*]]) local_unnamed_addr #[[ATTR0]] !kernel_arg_addr_space [[META3]] !kernel_arg_access_qual [[META4]] !kernel_arg_type [[META11]] !kernel_arg_base_type [[META12]] !kernel_arg_type_qual [[META7]] {
// CHECK-NEXT: [[ENTRY:.*:]]
-// CHECK-NEXT: [[LOADVECN:%.*]] = load <4 x float>, ptr addrspace(1) [[A]], align 16
-// CHECK-NEXT: [[ASTYPE:%.*]] = shufflevector <4 x float> [[LOADVECN]], <4 x float> poison, <4 x i32> <i32 0, i32 1, i32 2, i32 poison>
+// CHECK-NEXT: [[TMP0:%.*]] = load <3 x float>, ptr addrspace(1) [[A]], align 16
+// CHECK-NEXT: [[ASTYPE:%.*]] = shufflevector <3 x float> [[TMP0]], <3 x float> poison, <4 x i32> <i32 0, i32 1, i32 2, i32 poison>
// CHECK-NEXT: store <4 x float> [[ASTYPE]], ptr addrspace(1) [[B]], align 16, !tbaa [[TBAA8]]
// CHECK-NEXT: ret void
//
@@ -47,9 +47,9 @@ void kernel float3_to_float4(global float3 *a, global float4 *b) {
// CHECK-LABEL: define dso_local spir_kernel void @float3_to_double2(
// CHECK-SAME: ptr addrspace(1) noundef readonly align 16 captures(none) [[A:%.*]], ptr addrspace(1) noundef writeonly align 16 captures(none) initializes((0, 16)) [[B:%.*]]) local_unnamed_addr #[[ATTR0]] !kernel_arg_addr_space [[META3]] !kernel_arg_access_qual [[META4]] !kernel_arg_type [[META13:![0-9]+]] !kernel_arg_base_type [[META14:![0-9]+]] !kernel_arg_type_qual [[META7]] {
// CHECK-NEXT: [[ENTRY:.*:]]
-// CHECK-NEXT: [[LOADVECN:%.*]] = load <4 x float>, ptr addrspace(1) [[A]], align 16
-// CHECK-NEXT: [[TMP0:%.*]] = shufflevector <4 x float> [[LOADVECN]], <4 x float> poison, <4 x i32> <i32 0, i32 1, i32 2, i32 poison>
-// CHECK-NEXT: store <4 x float> [[TMP0]], ptr addrspace(1) [[B]], align 16, !tbaa [[TBAA8]]
+// CHECK-NEXT: [[TMP0:%.*]] = load <3 x float>, ptr addrspace(1) [[A]], align 16
+// CHECK-NEXT: [[TMP1:%.*]] = shufflevector <3 x float> [[TMP0]], <3 x float> poison, <4 x i32> <i32 0, i32 1, i32 2, i32 poison>
+// CHECK-NEXT: store <4 x float> [[TMP1]], ptr addrspace(1) [[B]], align 16, !tbaa [[TBAA8]]
// CHECK-NEXT: ret void
//
void kernel float3_to_double2(global float3 *a, global double2 *b) {
@@ -59,8 +59,8 @@ void kernel float3_to_double2(global float3 *a, global double2 *b) {
// CHECK-LABEL: define dso_local spir_kernel void @char8_to_short3(
// CHECK-SAME: ptr addrspace(1) noundef writeonly align 8 captures(none) initializes((0, 8)) [[A:%.*]], ptr addrspace(1) noundef readonly align 8 captures(none) [[B:%.*]]) local_unnamed_addr #[[ATTR0]] !kernel_arg_addr_space [[META3]] !kernel_arg_access_qual [[META4]] !kernel_arg_type [[META15:![0-9]+]] !kernel_arg_base_type [[META16:![0-9]+]] !kernel_arg_type_qual [[META7]] {
// CHECK-NEXT: [[ENTRY:.*:]]
-// CHECK-NEXT: [[TMP0:%.*]] = load <4 x i16>, ptr addrspace(1) [[B]], align 8, !tbaa [[TBAA8]]
-// CHECK-NEXT: [[EXTRACTVEC:%.*]] = shufflevector <4 x i16> [[TMP0]], <4 x i16> poison, <4 x i32> <i32 0, i32 1, i32 2, i32 poison>
+// CHECK-NEXT: [[TMP0:%.*]] = load <3 x i16>, ptr addrspace(1) [[B]], align 8, !tbaa [[TBAA8]]
+// CHECK-NEXT: [[EXTRACTVEC:%.*]] = shufflevector <3 x i16> [[TMP0]], <3 x i16> poison, <4 x i32> <i32 0, i32 1, i32 2, i32 poison>
// CHECK-NEXT: store <4 x i16> [[EXTRACTVEC]], ptr addrspace(1) [[A]], align 8, !tbaa [[TBAA8]]
// CHECK-NEXT: ret void
//
diff --git a/clang/test/Frontend/dump-minimization-hints-cpp20-modules.cpp b/clang/test/Frontend/dump-minimization-hints-cpp20-modules.cpp
new file mode 100644
index 0000000..a28acba
--- /dev/null
+++ b/clang/test/Frontend/dump-minimization-hints-cpp20-modules.cpp
@@ -0,0 +1,117 @@
+// RUN: rm -rf %t
+// RUN: mkdir -p %t
+// RUN: split-file %s %t
+// RUN: %clang_cc1 -std=c++20 %t/foo.cppm -emit-module-interface -o %t/foo.pcm
+// RUN: %clang_cc1 -std=c++20 -fprebuilt-module-path=%t %t/use.cpp -dump-minimization-hints=%t/decls
+// RUN: cat %t/decls
+// RUN: cat %t/decls | FileCheck -check-prefix=RANGE %s
+// RANGE:{
+// RANGE-NEXT:"required_ranges": [
+// RANGE-NEXT: {
+// RANGE-NEXT: "file": "{{.+}}foo.cppm",
+// RANGE-NEXT: "range": [
+// RANGE-NEXT: {
+// RANGE-NEXT: "from": {
+// RANGE-NEXT: "line": 3,
+// RANGE-NEXT: "column": 1
+// RANGE-NEXT: },
+// RANGE-NEXT: "to": {
+// RANGE-NEXT: "line": 3,
+// RANGE-NEXT: "column": 22
+// RANGE-NEXT: }
+// RANGE-NEXT: },
+// RANGE-NEXT: {
+// RANGE-NEXT: "from": {
+// RANGE-NEXT: "line": 4,
+// RANGE-NEXT: "column": 3
+// RANGE-NEXT: },
+// RANGE-NEXT: "to": {
+// RANGE-NEXT: "line": 4,
+// RANGE-NEXT: "column": 9
+// RANGE-NEXT: }
+// RANGE-NEXT: },
+// RANGE-NEXT: {
+// RANGE-NEXT: "from": {
+// RANGE-NEXT: "line": 4,
+// RANGE-NEXT: "column": 10
+// RANGE-NEXT: },
+// RANGE-NEXT: "to": {
+// RANGE-NEXT: "line": 4,
+// RANGE-NEXT: "column": 43
+// RANGE-NEXT: }
+// RANGE-NEXT: },
+// RANGE-NEXT: {
+// RANGE-NEXT: "from": {
+// RANGE-NEXT: "line": 6,
+// RANGE-NEXT: "column": 1
+// RANGE-NEXT: },
+// RANGE-NEXT: "to": {
+// RANGE-NEXT: "line": 6,
+// RANGE-NEXT: "column": 2
+// RANGE-NEXT: }
+// RANGE-NEXT: },
+// RANGE-NEXT: {
+// RANGE-NEXT: "from": {
+// RANGE-NEXT: "line": 8,
+// RANGE-NEXT: "column": 1
+// RANGE-NEXT: },
+// RANGE-NEXT: "to": {
+// RANGE-NEXT: "line": 8,
+// RANGE-NEXT: "column": 7
+// RANGE-NEXT: }
+// RANGE-NEXT: },
+// RANGE-NEXT: {
+// RANGE-NEXT: "from": {
+// RANGE-NEXT: "line": 8,
+// RANGE-NEXT: "column": 8
+// RANGE-NEXT: },
+// RANGE-NEXT: "to": {
+// RANGE-NEXT: "line": 8,
+// RANGE-NEXT: "column": 25
+// RANGE-NEXT: }
+// RANGE-NEXT: },
+// RANGE-NEXT: {
+// RANGE-NEXT: "from": {
+// RANGE-NEXT: "line": 9,
+// RANGE-NEXT: "column": 3
+// RANGE-NEXT: },
+// RANGE-NEXT: "to": {
+// RANGE-NEXT: "line": 9,
+// RANGE-NEXT: "column": 36
+// RANGE-NEXT: }
+// RANGE-NEXT: },
+// RANGE-NEXT: {
+// RANGE-NEXT: "from": {
+// RANGE-NEXT: "line": 11,
+// RANGE-NEXT: "column": 1
+// RANGE-NEXT: },
+// RANGE-NEXT: "to": {
+// RANGE-NEXT: "line": 11,
+// RANGE-NEXT: "column": 2
+// RANGE-NEXT: }
+// RANGE-NEXT: }
+// RANGE-NEXT: ]
+// RANGE-NEXT: }
+// RANGE-NEXT:]
+// RANGE-NEXT:}
+
+//--- foo.cppm
+export module foo;
+
+namespace piecemeal { // line 3
+ export int used(int n) { return n + 1; }
+ export int unused(int n) { return n + 2; }
+}
+
+export namespace whole { // line 8
+ int used(int n) { return n + 1; }
+ int unused(int n) { return n + 3; }
+} // line 11
+
+//--- use.cpp
+import foo;
+
+int main() {
+ piecemeal::used(4); // only one of the functions used from each namespace.
+ whole::used(4);
+}
diff --git a/clang/test/Modules/ExtDebugInfo.cpp b/clang/test/Modules/ExtDebugInfo.cpp
index 184973b..3e74e22 100644
--- a/clang/test/Modules/ExtDebugInfo.cpp
+++ b/clang/test/Modules/ExtDebugInfo.cpp
@@ -8,7 +8,7 @@
// RUN: -fmodule-format=obj -fimplicit-module-maps -DMODULES \
// RUN: -triple %itanium_abi_triple \
// RUN: -fmodules-cache-path=%t %s -I %S/Inputs -I %t -emit-llvm -o %t-mod.ll
-// RUN: cat %t-mod.ll | FileCheck %s
+// RUN: cat %t-mod.ll | FileCheck %s --check-prefix=CHECK %if target={{.*-(win|mingw|cyg).*}} %{--check-prefix=CHECKCOFF%} %else %{--check-prefix=CHECKELF%}
// PCH:
// RUN: %clang_cc1 -x c++ -std=c++11 -fmodule-format=obj -emit-pch -I%S/Inputs \
@@ -18,7 +18,7 @@
// RUN: -dwarf-ext-refs -fmodule-format=obj \
// RUN: -triple %itanium_abi_triple \
// RUN: -include-pch %t.pch %s -emit-llvm -o %t-pch.ll
-// RUN: cat %t-pch.ll | FileCheck %s
+// RUN: cat %t-pch.ll | FileCheck %s --check-prefix=CHECK %if target={{.*-(win|mingw|cyg).*}} %{--check-prefix=CHECKCOFF%} %else %{--check-prefix=CHECKELF%}
// RUN: cat %t-pch.ll | FileCheck %s --check-prefix=CHECK-PCH
#ifdef MODULES
@@ -208,9 +208,9 @@ void foo() {
// CHECK-SAME: name: "InAnonymousNamespace", {{.*}}DIFlagFwdDecl)
// There is a full definition of the type available in the module.
-// CHECK: !DICompositeType(tag: DW_TAG_structure_type, name: "Virtual",
-// CHECK-SAME: DIFlagFwdDecl
-// CHECK-SAME: identifier: "_ZTS7Virtual")
+// CHECKELF: !DICompositeType(tag: DW_TAG_structure_type, name: "Virtual",
+// CHECKELF-SAME: DIFlagFwdDecl
+// CHECKELF-SAME: identifier: "_ZTS7Virtual")
// CHECK: !DIImportedEntity(tag: DW_TAG_imported_declaration, scope: !{{[0-9]+}}, entity: ![[STRUCT]], file: ![[CPP]], line: 50)
@@ -222,3 +222,8 @@ void foo() {
// CHECK: !DICompositeType(tag: DW_TAG_class_type, name: "A",
// CHECK-SAME: DIFlagFwdDecl
+
+// There is a full definition of the type available in the module.
+// CHECKCOFF: !DICompositeType(tag: DW_TAG_structure_type, name: "Virtual",
+// CHECKCOFF-SAME: DIFlagFwdDecl
+// CHECKCOFF-SAME: identifier: "_ZTS7Virtual")
diff --git a/clang/test/Parser/cxx-template-template-recovery.cpp b/clang/test/Parser/cxx-template-template-recovery.cpp
index 5700b16..61ef82d 100644
--- a/clang/test/Parser/cxx-template-template-recovery.cpp
+++ b/clang/test/Parser/cxx-template-template-recovery.cpp
@@ -22,18 +22,18 @@ auto V3 = true; // #V3
template <template <typename T> typename C>
constexpr bool test = true;
-static_assert(test<a::C1>); // expected-error {{too few template arguments for concept 'C1'}} \
+static_assert(test<a::C1>); // expected-error {{template argument does not refer to a class or alias template, or template template parameter}} \
// expected-note@#C1 {{here}}
-static_assert(test<a::b::C2>); // expected-error {{too few template arguments for concept 'C2'}} \
+static_assert(test<a::b::C2>); // expected-error {{template argument does not refer to a class or alias template, or template template parameter}} \
// expected-note@#C2 {{here}}
-static_assert(test<C3>); // expected-error {{too few template arguments for concept 'C3'}} \
+static_assert(test<C3>); // expected-error {{template argument does not refer to a class or alias template, or template template parameter}} \
// expected-note@#C3 {{here}}
-static_assert(test<a::V1>); // expected-error {{use of variable template 'a::V1' requires template arguments}} \
+static_assert(test<a::V1>); // expected-error {{template argument does not refer to a class or alias template, or template template parameter}} \
// expected-note@#V1 {{here}}
-static_assert(test<a::b::V2>); // expected-error {{use of variable template 'a::b::V2' requires template arguments}} \
+static_assert(test<a::b::V2>); // expected-error {{template argument does not refer to a class or alias template, or template template parameter}} \
// expected-note@#V2 {{here}}
-static_assert(test<V3>); // expected-error {{use of variable template 'V3' requires template arguments}} \
+static_assert(test<V3>); // expected-error {{template argument does not refer to a class or alias template, or template template parameter}} \
// expected-note@#V3 {{here}}
diff --git a/clang/test/Parser/cxx2a-concept-declaration.cpp b/clang/test/Parser/cxx2a-concept-declaration.cpp
index 0a7af84..fea6084 100644
--- a/clang/test/Parser/cxx2a-concept-declaration.cpp
+++ b/clang/test/Parser/cxx2a-concept-declaration.cpp
@@ -9,11 +9,6 @@ template<concept T> concept D1 = true;
// expected-error@-1{{expected template parameter}}
// expected-error@-2{{concept template parameter list must have at least one parameter; explicit specialization of concepts is not allowed}}
-template<template<typename> concept T> concept D2 = true;
-// expected-error@-1{{expected identifier}}
-// expected-error@-2{{template template parameter requires 'class' or 'typename' after the parameter list}}
-// expected-error@-3{{concept template parameter list must have at least one parameter; explicit specialization of concepts is not allowed}}
-
struct S1 {
template<typename T> concept C1 = true; // expected-error {{concept declarations may only appear in global or namespace scope}}
};
diff --git a/clang/test/Parser/cxx2c-template-template-param.cpp b/clang/test/Parser/cxx2c-template-template-param.cpp
new file mode 100644
index 0000000..e8c7621
--- /dev/null
+++ b/clang/test/Parser/cxx2c-template-template-param.cpp
@@ -0,0 +1,79 @@
+// RUN: %clang_cc1 -std=c++2c -verify %s
+
+template<template<typename> auto Var>
+struct A{};
+template<template<auto> auto Var>
+struct B{};
+template<template<typename> auto Var>
+struct C{};
+template<template<typename> concept C>
+struct D{};
+template<template<auto> concept C>
+struct E{};
+
+template<template<typename> auto Var>
+int V1;
+template<template<auto> auto Var>
+int V2;
+template<template<typename> auto Var>
+int V3;
+template<template<typename> concept C>
+int V4;
+template<template<auto> concept C>
+int V5;
+
+namespace packs {
+
+template<template<typename> auto... Var>
+struct A{};
+template<template<auto> auto... Var>
+struct B{};
+template<template<typename> auto... Var>
+struct C{};
+template<template<typename> concept... C>
+struct D{};
+template<template<auto> concept... C>
+struct E{};
+
+template<template<typename> auto... Var>
+int V1;
+template<template<auto> auto... Var>
+int V2;
+template<template<typename> auto... Var>
+int V3;
+template<template<typename> concept... C>
+int V4;
+template<template<auto> concept... C>
+int V5;
+
+}
+
+namespace concepts {
+template<template<auto> concept...>
+struct A{};
+template<template<auto> concept... C>
+struct B{};
+template<template<auto> concept& C> // expected-error{{expected identifier}} \
+ // expected-error {{in declaration of struct 'C'}}
+struct C{};
+}
+
+namespace vars {
+template<template<auto> auto...>
+struct A{};
+template<template<auto> auto & C> // expected-error {{expected identifier}} \
+ // expected-error {{extraneous 'template<>'}}
+struct B{};
+template<template<auto> const auto> // expected-error {{expected identifier}} \
+ // expected-error {{extraneous 'template<>'}}
+struct C{};
+}
+
+namespace errors {
+template<concept> // expected-error {{expected template parameter}} \
+ // expected-error {{extraneous 'template<>' in declaration of struct 'A'}}
+struct A{};
+template<template<concept> auto> // expected-error {{expected template parameter}} \
+ // expected-error {{template template parameter must have its own template parameters}}
+struct B{};
+}
diff --git a/clang/test/Sema/riscv-interrupt-attr-rnmi.c b/clang/test/Sema/riscv-interrupt-attr-rnmi.c
new file mode 100644
index 0000000..964bae5
--- /dev/null
+++ b/clang/test/Sema/riscv-interrupt-attr-rnmi.c
@@ -0,0 +1,28 @@
+// RUN: %clang_cc1 -triple riscv32-unknown-elf -target-feature +smrnmi -emit-llvm -DCHECK_IR < %s | FileCheck %s
+// RUN: %clang_cc1 %s -triple riscv32-unknown-elf -target-feature +smrnmi -verify=enabled,both -fsyntax-only
+// RUN: %clang_cc1 %s -triple riscv32-unknown-elf -verify=disabled,both -fsyntax-only
+// RUN: %clang_cc1 %s -triple riscv32-unknown-elf -target-feature -srnmi -verify=disabled,both -fsyntax-only
+
+#if defined(CHECK_IR)
+// CHECK-LABEL: foo_rnmi_interrupt() #0
+// CHECK: ret void
+__attribute__((interrupt("rnmi")))
+void foo_rnmi_interrupt(void) {}
+
+// CHECK-LABEL: @foo_rnmi_rnmi_interrupt() #0
+// CHECK: ret void
+__attribute__((interrupt("rnmi", "rnmi")))
+void foo_rnmi_rnmi_interrupt(void) {}
+
+// CHECK: attributes #0
+// CHECK: "interrupt"="rnmi"
+#else
+
+__attribute__((interrupt("rnmi"))) void test_rnmi(void) {} // disabled-error {{RISC-V 'interrupt' attribute 'rnmi' requires extension 'Smrnmi'}}
+__attribute__((interrupt("rnmi", "rnmi"))) void test_rnmi_rnmi(void) {} // disabled-error {{RISC-V 'interrupt' attribute 'rnmi' requires extension 'Smrnmi'}}
+
+__attribute__((interrupt("rnmi", "supervisor"))) void foo_rnmi_supervisor(void) {} // both-error {{RISC-V 'interrupt' attribute contains invalid combination of interrupt types}}
+__attribute__((interrupt("rnmi", "machine"))) void foo_rnmi_machine(void) {} // both-error {{RISC-V 'interrupt' attribute contains invalid combination of interrupt types}}
+
+__attribute__((interrupt("RNMI"))) void test_RNMI(void) {} // both-warning {{'interrupt' attribute argument not supported: "RNMI"}}
+#endif
diff --git a/clang/test/SemaCXX/cxx2c-template-template-param.cpp b/clang/test/SemaCXX/cxx2c-template-template-param.cpp
new file mode 100644
index 0000000..ed55a059
--- /dev/null
+++ b/clang/test/SemaCXX/cxx2c-template-template-param.cpp
@@ -0,0 +1,352 @@
+// RUN: %clang_cc1 -std=c++2c -verify %s
+
+namespace Errors {
+
+template <template<typename T> auto>
+struct S1;
+template <template<auto T> auto>
+struct S2;
+template <template<typename T> concept>
+struct S3;
+template <template<auto T> concept>
+struct S4;
+int a;
+
+template <typename T>
+concept C = true; // expected-note 2{{template argument refers to a concept 'C', here}}
+template <typename T>
+auto Var = 0; // expected-note 2{{template argument refers to a variable template 'Var', here}}
+
+S1<1> t1; // expected-error {{template argument for template template parameter must be a variable template}}
+S1<a> t2; // expected-error {{template argument for template template parameter must be a variable template}}
+S1<int> t3; // expected-error {{template argument for template template parameter must be a variable template}}
+S1<C> t4; // expected-error {{template argument does not refer to a variable template, or template template parameter}}
+S2<1> t5; // expected-error {{template argument for template template parameter must be a variable template}}
+S2<a> t6; // expected-error {{template argument for template template parameter must be a variable template}}
+S2<int> t7; // expected-error {{template argument for template template parameter must be a variable template}}
+S2<C> t8; // expected-error {{template argument does not refer to a variable template, or template template parameter}}
+S3<1> t9; // expected-error {{template argument for template template parameter must be a concept}}
+S3<a> t10; // expected-error {{template argument for template template parameter must be a concept}}
+S3<int> t11; // expected-error {{template argument for template template parameter must be a concept}}
+S3<Var> t12; // expected-error {{template argument does not refer to a concept, or template template parameter}}
+S4<1> t13; // expected-error {{template argument for template template parameter must be a concept}}
+S4<a> t14; // expected-error {{template argument for template template parameter must be a concept}}
+S4<int> t15; // expected-error {{template argument for template template parameter must be a concept}}
+S4<Var> t16; // expected-error {{template argument does not refer to a concept, or template template parameter}}
+
+}
+
+template <template<typename T> auto V> // expected-note {{previous template template parameter is here}} \
+ // expected-error{{template argument for non-type template parameter must be an expression}}
+struct S1 {
+ static_assert(V<int> == 42);
+ static_assert(V<const int> == 84);
+ static_assert(V<double> == 0);
+};
+template <template<auto T> auto V> // expected-error {{template argument for template type parameter must be a type}} \
+ // expected-note {{previous template template parameter is here}}
+struct S2 {
+ static_assert(V<0> == 1);
+ static_assert(V<1> == 0);
+};
+template <template<typename T> concept C > // expected-error {{template argument for non-type template parameter must be an expression}} \
+ // expected-note {{previous template template parameter is here}}
+struct S3 {
+ static_assert(C<int>);
+};
+template <template<auto> concept C> // expected-error {{template argument for template type parameter must be a type}} \
+ // expected-note {{previous template template parameter is here}}
+struct S4 {
+ static_assert(C<0>);
+};
+
+template <typename T> // expected-note {{template parameter is declared here}}
+concept C = true;
+
+template <auto I> // expected-note {{template parameter is declared here}}
+concept CI = true;
+
+template <typename T> // expected-note {{template parameter is declared here}}
+constexpr auto Var = 42;
+template <typename T>
+constexpr auto Var<const T> = 84;
+template <>
+constexpr auto Var<double> = 0;
+
+template <auto N> // expected-note {{template parameter is declared here}}
+constexpr auto Var2 = 0;
+template <auto N>
+requires (N%2 == 0)
+constexpr auto Var2<N> = 1;
+
+void test () {
+ S1<Var2> sE; // expected-note {{template template argument has different template parameters than its corresponding template template parameter}}
+ S2<Var> sE; // expected-note {{template template argument has different template parameters than its corresponding template template parameter}}
+ S1<Var> s1;
+ S2<Var2> s2;
+ S3<C> s3;
+ S4<C> sE; // expected-note {{template template argument has different template parameters than its corresponding template template parameter}}
+ S4<CI> s4;
+ S3<CI> sE; // expected-note {{template template argument has different template parameters than its corresponding template template parameter}}
+}
+
+
+namespace template_type_constraints {
+
+
+template <typename T>
+concept Unary = true;
+template <typename T, typename = int>
+concept BinaryDefaulted = true;
+
+template <typename T>
+concept UnaryFalse = false; // expected-note 3{{because 'false' evaluated to false}}
+template <typename T, typename = int>
+concept BinaryDefaultedFalse = false;
+
+template <template <typename...> concept C, typename T>
+struct S {
+ template <C TT> // expected-note {{because 'int' does not satisfy 'UnaryFalse'}}
+ void f(TT); // expected-note {{ignored}}
+ void g(C auto); // expected-note {{ignored}} \
+ // expected-note {{because 'int' does not satisfy 'UnaryFalse'}}
+
+ auto h() -> C auto { // expected-error {{deduced type 'int' does not satisfy 'UnaryFalse'}}
+ return 0;
+ };
+
+ void test() {
+ C auto a = 0;
+ }
+};
+
+template <template <typename...> concept C, typename T>
+struct SArg {
+ template <C<int> TT>
+ void f(TT);
+ void g(C<int> auto);
+
+ auto h() -> C<int> auto {
+ return 0;
+ };
+ void test() {
+ C<int> auto a = 0;
+ }
+};
+
+void test() {
+ S<Unary, int> s;
+ s.f(0);
+ s.g(0);
+ s.h();
+ S<BinaryDefaulted, int> s2;
+ s2.f(0);
+ s2.g(0);
+ s2.h();
+
+ SArg<BinaryDefaulted, int> s3;
+ s3.f(0);
+ s3.g(0);
+ s3.h();
+}
+
+void test_errors() {
+ S<UnaryFalse, int> s;
+ s.f(0); // expected-error {{no matching member function for call to 'f'}}
+ s.g(0); // expected-error {{no matching member function for call to 'g'}}
+ s.h(); // expected-note {{in instantiation of member function 'template_type_constraints::S<template_type_constraints::UnaryFalse, int>::h'}}
+}
+
+}
+
+template <typename T>
+concept Unary = true;
+template <typename T, typename = int>
+concept BinaryDefaulted = true;
+
+template <typename T>
+concept UnaryFalse = false; // expected-note 3{{because 'false' evaluated to false}}
+template <typename T, typename = int>
+concept BinaryDefaultedFalse = false;
+
+template <template <typename...> concept C, typename T>
+struct S {
+ template <C TT> // expected-note {{because 'int' does not satisfy 'UnaryFalse'}}
+ void f(TT); // expected-note {{ignored}}
+ void g(C auto); // expected-note {{ignored}} \
+ // expected-note {{because 'int' does not satisfy 'UnaryFalse'}}
+
+ auto h() -> C auto { // expected-error {{deduced type 'int' does not satisfy 'UnaryFalse'}}
+ return 0;
+ };
+
+ void test() {
+ C auto a = 0;
+ }
+};
+
+template <template <typename...> concept C, typename T>
+struct SArg {
+ template <C<int> TT>
+ void f(TT);
+ void g(C<int> auto);
+
+ auto h() -> C<int> auto {
+ return 0;
+ };
+ void test() {
+ C<int> auto a = 0;
+ }
+};
+
+void test_args() {
+ S<Unary, int> s;
+ s.f(0);
+ s.g(0);
+ s.h();
+ S<BinaryDefaulted, int> s2;
+ s2.f(0);
+ s2.g(0);
+ s2.h();
+
+ SArg<BinaryDefaulted, int> s3;
+ s3.f(0);
+ s3.g(0);
+ s3.h();
+}
+
+void test_errors() {
+ S<UnaryFalse, int> s;
+ s.f(0); // expected-error {{no matching member function for call to 'f'}}
+ s.g(0); // expected-error {{no matching member function for call to 'g'}}
+ s.h(); // expected-note {{in instantiation of member function 'S<UnaryFalse, int>::h'}}
+}
+
+namespace non_type {
+
+template <auto>
+concept Unary = true;
+
+template <template <auto> concept C>
+struct S {
+ template <C Foo> // expected-error {{concept named in type constraint is not a type concept}}
+ void f();
+ // FIXME, bad diagnostic
+ void g(C auto); // expected-error{{concept named in type constraint is not a type concept}}
+ auto h() -> C auto { // expected-error{{concept named in type constraint is not a type concept}}
+ }
+ void i() {
+ C auto a = 0; // expected-error{{concept named in type constraint is not a type concept}}
+ }
+};
+
+}
+
+namespace default_args {
+
+template <typename T>
+concept Concept = false; // expected-note 2{{template argument refers to a concept 'Concept', here}} \
+ // expected-note 2{{because 'false' evaluated to false}}
+
+template <typename T>
+constexpr auto Var = false; // expected-note 2{{template argument refers to a variable template 'Var', here}}
+
+template <typename T>
+struct Type; // expected-note 2{{template argument refers to a class template 'Type', here}}
+
+
+template <template <typename> auto = Concept> // expected-error {{template argument does not refer to a variable template, or template template parameter}}
+struct E1;
+
+template <template <typename> auto = Type> // expected-error {{template argument does not refer to a variable template, or template template parameter}}
+struct E2;
+
+template <template <typename> typename = Concept> // expected-error {{template argument does not refer to a class or alias template, or template template parameter}}
+struct E3;
+
+template <template <typename> typename = Var> // expected-error {{template argument does not refer to a class or alias template, or template template parameter}}
+struct E4;
+
+template <template <typename> concept = Var> // expected-error {{template argument does not refer to a concept, or template template parameter}}
+struct E4;
+
+template <template <typename> concept = Type> // expected-error {{template argument does not refer to a concept, or template template parameter}}
+struct E4;
+
+template <
+ template <typename> concept TConcept, // expected-note 2{{template argument refers to a concept 'TConcept', here}}
+ template <typename> auto TVar, // expected-note 2{{template argument refers to a variable template 'TVar', here}}
+ template <typename> typename TType // expected-note 2{{template argument refers to a class template 'TType', here}}
+>
+struct Nested {
+ template <template <typename> auto = TConcept> // expected-error {{template argument does not refer to a variable template, or template template parameter}}
+ struct E1;
+
+ template <template <typename> auto = TType> // expected-error {{template argument does not refer to a variable template, or template template parameter}}
+ struct E2;
+
+ template <template <typename> typename = TConcept> // expected-error {{template argument does not refer to a class or alias template, or template template parameter}}
+ struct E3;
+
+ template <template <typename> typename = TVar> // expected-error {{template argument does not refer to a class or alias template, or template template parameter}}
+ struct E4;
+
+ template <template <typename> concept = TVar> // expected-error {{template argument does not refer to a concept, or template template parameter}}
+ struct E4;
+
+ template <template <typename> concept = TType> // expected-error {{template argument does not refer to a concept, or template template parameter}}
+ struct E4;
+};
+
+
+template <template <typename> concept C = Concept>
+struct TestDefaultConcept {
+ template <template <typename> concept CC = C>
+ void f() {
+ static_assert(C<int>); // expected-error {{static assertion failed}} \
+ // expected-note {{because 'int' does not satisfy 'Concept'}}
+ static_assert(CC<int>); // expected-error {{static assertion failed}} \
+ // expected-note {{because 'int' does not satisfy 'Concept'}}
+ }
+};
+void do_test_concept() {
+ TestDefaultConcept<>{}.f(); // expected-note {{in instantiation}}
+}
+
+template <template <typename> auto V = Var>
+struct TestDefaultVar {
+ template <template <typename> auto VV = V>
+ void f() {
+ static_assert(V<int>); // expected-error {{static assertion failed}}
+ static_assert(VV<int>); // expected-error {{static assertion failed}}
+ }
+};
+void do_test_var() {
+ TestDefaultVar<>{}.f(); // expected-note {{in instantiation}}
+}
+
+}
+
+namespace TTPDependence {
+template <template <typename... > concept C>
+concept A = C<>;
+template <template <typename... > concept C>
+concept B = C<int>;
+
+template <template <typename... > auto Var>
+concept C = Var<>;
+template <template <typename... > auto Var>
+concept D = Var<int>;
+
+}
+
+namespace InvalidName {
+template <typename T, template <typename> concept C>
+concept A = C<T>; // expected-note {{here}}
+
+template <A<concept missing<int>> T> // expected-error {{expected expression}} \
+ // expected-error {{too few template arguments for concept 'A'}} \
+ // expected-error {{unknown type name 'T'}} \
+ // expected-error {{expected unqualified-id}}
+auto f();
+}