xref: /llvm-project/clang/test/Modules/merge-concepts.cppm (revision a171d248ca34b8b6f8de11d42a83ad981285963a)
1// RUN: rm -rf %t
2// RUN: mkdir %t
3// RUN: split-file %s %t
4//
5// RUN: %clang_cc1 -std=c++20 -emit-module-interface -I%t %t/A.cppm -o %t/A.pcm
6// RUN: %clang_cc1 -std=c++20 -emit-module-interface -I%t %t/B.cppm -o %t/B.pcm
7// RUN: %clang_cc1 -std=c++20 -fprebuilt-module-path=%t %t/Use.cpp -verify -fsyntax-only
8// RUN: %clang_cc1 -std=c++20 -fprebuilt-module-path=%t %t/Use2.cpp -verify -fsyntax-only
9// RUN: %clang_cc1 -std=c++20 -fprebuilt-module-path=%t %t/Use3.cpp -verify -fsyntax-only
10// RUN: %clang_cc1 -std=c++20 -fprebuilt-module-path=%t %t/Use4.cpp -verify -fsyntax-only
11// RUN: %clang_cc1 -std=c++20 -fprebuilt-module-path=%t %t/C.cppm -verify -fsyntax-only
12// RUN: %clang_cc1 -std=c++20 -I%t %t/D.cppm -verify -fsyntax-only
13// RUN: %clang_cc1 -std=c++20 -I%t %t/E.cppm -verify -fsyntax-only
14// RUN: %clang_cc1 -std=c++20 -I%t %t/F.cppm -verify -fsyntax-only
15//
16// Testing header units for coverity.
17// RUN: %clang_cc1 -std=c++20 -emit-header-unit -xc++-user-header %t/foo.h -o %t/foo.pcm
18// RUN: %clang_cc1 -std=c++20 -fprebuilt-module-path=%t -fmodule-file=%t/foo.pcm %t/Use5.cpp -verify -fsyntax-only
19// RUN: %clang_cc1 -std=c++20 -fprebuilt-module-path=%t -fmodule-file=%t/foo.pcm %t/Use6.cpp -verify -fsyntax-only
20//
21// Testing with module map modules. It is unclear about the relation ship between Clang modules and
22// C++20 Named Modules. Will they coexist? Or will they be mutually exclusive?
23// The test here is for primarily coverity.
24//
25// RUN: rm -f %t/foo.pcm
26// RUN: %clang_cc1 -std=c++20 -fmodules -fmodules-cache-path=%t -fprebuilt-module-path=%t \
27// RUN:   -fmodule-map-file=%t/module.modulemap %t/Use7.cpp -verify -fsyntax-only
28// RUN: %clang_cc1 -std=c++20 -fmodules -fmodules-cache-path=%t -fprebuilt-module-path=%t \
29// RUN:   -fmodule-map-file=%t/module.modulemap %t/Use7.cpp -verify -fsyntax-only
30// Testing module map modules with named modules.
31// RUN: %clang_cc1 -std=c++20 -fmodules -fmodules-cache-path=%t -fmodule-map-file=%t/module.modulemap \
32// RUN:   %t/A.cppm -o %t/A.pcm
33// RUN: %clang_cc1 -std=c++20 -fmodules -fmodules-cache-path=%t -fprebuilt-module-path=%t \
34// RUN:   -fmodule-map-file=%t/module.modulemap %t/Use7.cpp -verify -fsyntax-only
35// RUN: %clang_cc1 -std=c++20 -fmodules -fmodules-cache-path=%t -fprebuilt-module-path=%t \
36// RUN:   -fmodule-map-file=%t/module.modulemap %t/Use7.cpp -verify -fsyntax-only
37
38//
39//--- foo.h
40#ifndef FOO_H
41#define FOO_H
42template <class T, class U>
43concept same_as = __is_same(T, U);
44#endif
45
46// The compiler would warn if we include foo_h twice without guard.
47//--- redecl.h
48#ifndef REDECL_H
49#define REDECL_H
50template <class T, class U>
51concept same_as = __is_same(T, U);
52#endif
53
54//--- A.cppm
55module;
56#include "foo.h"
57export module A;
58export using ::same_as;
59
60//--- B.cppm
61module;
62#include "foo.h"
63export module B;
64export using ::same_as;
65
66//--- Use.cpp
67// expected-no-diagnostics
68import A;
69import B;
70
71template <class T> void foo()
72  requires same_as<T, int>
73{}
74
75//--- Use2.cpp
76// expected-no-diagnostics
77#include "foo.h"
78import A;
79
80template <class T> void foo()
81  requires same_as<T, int>
82{}
83
84//--- Use3.cpp
85// expected-no-diagnostics
86import A;
87#include "foo.h"
88
89template <class T> void foo()
90  requires same_as<T, int>
91{}
92
93//--- Use4.cpp
94// expected-no-diagnostics
95import A;
96import B;
97#include "foo.h"
98
99template <class T> void foo()
100  requires same_as<T, int>
101{}
102
103//--- C.cppm
104// expected-no-diagnostics
105module;
106#include "foo.h"
107export module C;
108import A;
109import B;
110
111template <class T> void foo()
112  requires same_as<T, int>
113{}
114
115//--- D.cppm
116module;
117#include "foo.h"
118#include "redecl.h"
119export module D;
120export using ::same_as;
121
122// expected-error@* {{redefinition of 'same_as'}}
123// expected-note@* 1+{{previous definition is here}}
124
125//--- E.cppm
126module;
127#include "foo.h"
128export module E;
129export template <class T, class U>
130concept same_as = __is_same(T, U);
131
132// expected-error@* {{redefinition of 'same_as'}}
133// expected-note@* 1+{{previous definition is here}}
134
135//--- F.cppm
136export module F;
137template <class T, class U>
138concept same_as = __is_same(T, U);
139template <class T, class U>
140concept same_as = __is_same(T, U);
141
142// expected-error@* {{redefinition of 'same_as'}}
143// expected-note@* 1+{{previous definition is here}}
144
145//--- Use5.cpp
146import "foo.h";  // expected-warning {{the implementation of header units is in an experimental phase}}
147import A;
148
149template <class T> void foo()
150  requires same_as<T, int>
151{}
152
153//--- Use6.cpp
154import A;
155import "foo.h"; // expected-warning {{the implementation of header units is in an experimental phase}}
156
157template <class T> void foo()
158  requires same_as<T, int>
159{}
160
161//--- module.modulemap
162module "foo" {
163  export *
164  header "foo.h"
165}
166
167//--- Use7.cpp
168// expected-no-diagnostics
169#include "foo.h"
170import A;
171
172template <class T> void foo()
173  requires same_as<T, int>
174{}
175
176//--- Use8.cpp
177// expected-no-diagnostics
178import A;
179#include "foo.h"
180
181template <class T> void foo()
182  requires same_as<T, int>
183{}
184