xref: /llvm-project/clang/test/C/C23/n3033.c (revision 50c81128de8616117118564eff22cf508cba7848)
1 // RUN: %clang_cc1 -std=c23 -E %s | FileCheck %s
2 
3 /* WG14 N3033: Clang 12
4  * Comma ommission and deletion (__VA_OPT__)
5  */
6 
7 #define F(...)           f(0 __VA_OPT__(,) __VA_ARGS__)
8 #define G(X, ...)        f(0, X __VA_OPT__(,) __VA_ARGS__)
9 #define SDEF(sname, ...) S sname __VA_OPT__(= { __VA_ARGS__ })
10 #define EMP
11 
12 F(a, b, c)        // replaced by f(0, a, b, c)
13 // CHECK: f(0 , a, b, c)
14 F()               // replaced by f(0)
15 // CHECK: f(0 )
16 F(EMP)            // replaced by f(0)
17 // CHECK: f(0 )
18 
19 G(a, b, c)        // replaced by f(0, a, b, c)
20 // CHECK: f(0, a , b, c)
21 G(a, )            // replaced by f(0, a)
22 // CHECK: f(0, a )
23 G(a)              // replaced by f(0, a)
24 // CHECK: f(0, a )
25 
26 SDEF(foo);        // replaced by S foo;
27 // CHECK: S foo ;
28 SDEF(bar, 1, 2);  // replaced by S bar = { 1, 2 };
29 // CHECK: S bar = { 1, 2 };
30 
31 //#define H1(X, ...)       X __VA_OPT__(##) __VA_ARGS__  // error: ## may not appear at the beginning of a replacement list (6.10.3.3)
32 
33 #define H2(X, Y, ...)    __VA_OPT__(X ## Y,) __VA_ARGS__
34 H2(a, b, c, d)    // replaced by ab, c, d
35 // CHECK: ab, c, d
36 
37 #define H3(X, ...)       #__VA_OPT__(X##X X##X)
38 H3(, 0)           // replaced by ""
39 // CHECK: ""
40 
41 #define H4(X, ...)       __VA_OPT__(a X ## X) ## b
42 H4(, 1)           // replaced by a b
43 // CHECK: a b
44 
45 #define H5A(...)         __VA_OPT__()/**/__VA_OPT__()
46 #define H5B(X)           a ## X ## b
47 #define H5C(X)           H5B(X)
48 H5C(H5A())        // replaced by ab
49 // CHECK: ab
50 
51