xref: /llvm-project/clang/test/Parser/builtin_types_compatible.c (revision 7deaeb2a056c1756ce6f2550d2ebb91b81b9ff29)
1 // RUN: %clang_cc1 -fsyntax-only -verify %s
2 
3 extern int funcInt(int);
4 extern float funcFloat(float);
5 extern double funcDouble(double);
6 // figure out why "char *" doesn't work (with gcc, nothing to do with clang)
7 //extern void funcCharPtr(char *);
8 
9 #define func(expr) \
10   do { \
11     typeof(expr) tmp; \
12     if (__builtin_types_compatible_p(typeof(expr), int)) funcInt(tmp); \
13     else if (__builtin_types_compatible_p(typeof(expr), float)) funcFloat(tmp); \
14     else if (__builtin_types_compatible_p(typeof(expr), double)) funcDouble(tmp); \
15   } while (0)
16 #define func_choose(expr) \
17   __builtin_choose_expr(__builtin_types_compatible_p(typeof(expr), int), funcInt(expr), \
18     __builtin_choose_expr(__builtin_types_compatible_p(typeof(expr), float), funcFloat(expr), \
19       __builtin_choose_expr(__builtin_types_compatible_p(typeof(expr), double), funcDouble(expr), (void)0)))
20 
test(void)21 static void test(void)
22 {
23   int a;
24   float b;
25   double d;
26 
27   func(a);
28   func(b);
29   func(d);
30   a = func_choose(a);
31   b = func_choose(b);
32   d = func_choose(d);
33 
34   int c;
35   struct xx { int a; } x, y;
36 
37   c = __builtin_choose_expr(a+3-7, b, x); // expected-error{{'__builtin_choose_expr' requires a constant expression}}
38   c = __builtin_choose_expr(0, b, x); // expected-error{{assigning to 'int' from incompatible type 'struct xx'}}
39   c = __builtin_choose_expr(5+3-7, b, x);
40   y = __builtin_choose_expr(4+3-7, b, x);
41 
42 }
43 
44 enum E1 { E1Foo };
45 enum E2 { E2Foo };
46 
testGccCompatibility(void)47 static void testGccCompatibility(void) {
48   _Static_assert(__builtin_types_compatible_p(const volatile int, int), "");
49   _Static_assert(__builtin_types_compatible_p(int[5], int[]), "");
50   _Static_assert(!__builtin_types_compatible_p(int[5], int[4]), "");
51   _Static_assert(!__builtin_types_compatible_p(int *, int **), "");
52   _Static_assert(!__builtin_types_compatible_p(const int *, int *), "");
53   _Static_assert(!__builtin_types_compatible_p(enum E1, enum E2), "");
54 
55   // GCC's __builtin_types_compatible_p ignores qualifiers on arrays.
56   _Static_assert(__builtin_types_compatible_p(const int[4], int[4]), "");
57   _Static_assert(__builtin_types_compatible_p(int[4], const int[4]), "");
58   _Static_assert(__builtin_types_compatible_p(const int[5][4], int[][4]), "");
59   _Static_assert(!__builtin_types_compatible_p(const int(*)[], int(*)[]), "");
60 }
61