1 /* PR middle-end/10138 - warn for uninitialized arrays passed as const arguments
2    Verify that -Wuninitialized and -Wmaybe-uninitialized trigger (or don't)
3    when passing uninitialized variables by reference to functions declared
4    with or without attribute access and with (or without) const qualified
5    arguments of array, VLA, or pointer types.
6    { dg-do compile }
7    { dg-options "-O2 -Wall -ftrack-macro-expansion=0 -ftrivial-auto-var-init=zero" } */
8 /* -ftrivial-auto-var-init will make the uninitialized warning for address
9    taken auto var going away, FIXME later.  */
10 
11 #define NONE    /* none */
12 #define RO(...) __attribute__ ((access (read_only, __VA_ARGS__)))
13 #define RW(...) __attribute__ ((access (read_write, __VA_ARGS__)))
14 #define WO(...) __attribute__ ((access (write_only, __VA_ARGS__)))
15 #define X(...)  __attribute__ ((access (none, __VA_ARGS__)))
16 
17 #define CONCAT(x, y) x ## y
18 #define CAT(x, y)    CONCAT (x, y)
19 #define UNIQ(pfx)    CAT (pfx, __LINE__)
20 
21 extern void sink (void*);
22 
23 
24 #define T1(attr, name, type)			\
25   void UNIQ (CAT (test_, name))(void) {		\
26     extern attr void UNIQ (name)(type);		\
27     int x;					\
28     UNIQ (name)(&x);				\
29     sink (&x);					\
30   }
31 
32 #define T2(attr, name, types)			\
33   void UNIQ (CAT (test_, name))(void) {		\
34     extern attr void UNIQ (name)(types);	\
35     int x;					\
36     UNIQ (name)(1, &x);				\
37     sink (&x);					\
38   }
39 
40 
41 typedef int IA_[];
42 typedef const int CIA_[];
43 
44 T1 (NONE,   fia_,   IA_);
45 T1 (NONE,   fcia_,  CIA_);    // { dg-warning "\\\[-Wmaybe-uninitialized" "" { xfail *-*-* } }
46 T1 (RO (1), froia_, IA_);     // { dg-warning "\\\[-Wuninitialized" "" { xfail *-*-* } }
47 T1 (RW (1), frwia_, IA_);     // { dg-warning "\\\[-Wmaybe-uninitialized" "" { xfail *-*-* } }
48 T1 (WO (1), fwoia_, IA_);
49 T1 (X (1),  fxia_,  IA_);
50 
51 
52 typedef int IA1[1];
53 typedef const int CIA1[1];
54 
55 T1 (NONE,   fia1,   IA1);
56 T1 (NONE,   fcia1,  CIA1);    // { dg-warning "\\\[-Wmaybe-uninitialized" "" { xfail *-*-* } }
57 T1 (RO (1), froia1, IA1);     // { dg-warning "\\\[-Wuninitialized" "" { xfail *-*-* } }
58 T1 (RW (1), frwia1, IA1);     // { dg-warning "\\\[-Wmaybe-uninitialized" "" { xfail *-*-* } }
59 T1 (WO (1), fwoia1, IA1);
60 T1 (X (1),  fxia1,  IA1);
61 
62 
63 #define IARS1  int[restrict static 1]
64 #define CIARS1 const int[restrict static 1]
65 
66 T1 (NONE,   fiars1,   IARS1);
67 T1 (NONE,   fciars1,  CIARS1);// { dg-warning "\\\[-Wmaybe-uninitialized" "" { xfail *-*-* } }
68 T1 (RO (1), froiars1, IARS1); // { dg-warning "\\\[-Wuninitialized" "" { xfail *-*-* } }
69 T1 (RW (1), frwiars1, IARS1); // { dg-warning "\\\[-Wmaybe-uninitialized" "" { xfail *-*-* } }
70 T1 (WO (1), fwoiars1, IARS1);
71 T1 (X (1),  fxiars1,  IARS1);
72 
73 
74 #define IAS1  int[static 1]
75 #define CIAS1 const int[static 1]
76 
77 T1 (NONE,   fias1,   IAS1);
78 T1 (NONE,   fcias1,  CIAS1);   // { dg-warning "\\\[-Wmaybe-uninitialized" "" { xfail *-*-* } }
79 T1 (RO (1), froias1, IAS1);    // { dg-warning "\\\[-Wuninitialized" "" { xfail *-*-* } }
80 T1 (RW (1), frwias1, IAS1);    // { dg-warning "\\\[-Wmaybe-uninitialized" "" { xfail *-*-* } }
81 T1 (WO (1), fwoias1, IAS1);
82 T1 (X (1),  fxias1,  IAS1);
83 
84 
85 #define IAX  int[*]
86 #define CIAX const int[*]
87 
88 T1 (NONE,   fiax,   IAX);
89 T1 (NONE,   fciax,  CIAX);    // { dg-warning "\\\[-Wmaybe-uninitialized" "" { xfail *-*-* } }
90 T1 (RO (1), froiax, IAX);     // { dg-warning "\\\[-Wuninitialized" "" { xfail *-*-* } }
91 T1 (RW (1), frwiax, IAX);     // { dg-warning "\\\[-Wmaybe-uninitialized" "" { xfail *-*-* } }
92 T1 (WO (1), fwoiax, IAX);
93 T1 (X (1),  fxiax,  IAX);
94 
95 
96 #define IAN  int n, int[n]
97 #define CIAN int n, const int[n]
98 
99 T2 (NONE,      fian,   IAN);
100 T2 (NONE,      fcian,  CIAN); // { dg-warning "\\\[-Wmaybe-uninitialized" "" { xfail *-*-* } }
101 T2 (RO (2, 1), froian, IAN);  // { dg-warning "\\\[-Wuninitialized" "" { xfail *-*-* } }
102 T2 (RW (2, 1), frwian, IAN);  // { dg-warning "\\\[-Wmaybe-uninitialized" "" { xfail *-*-* } }
103 T2 (WO (2, 1), fwoian, IAN);
104 T2 (X (2, 1),  fxian,  IAN);
105 
106 
107 typedef int* IP;
108 typedef const int* CIP;
109 
110 T1 (NONE,   fip,   IP);
111 T1 (NONE,   fcip,  CIP);     // { dg-warning "\\\[-Wmaybe-uninitialized" "" { xfail *-*-* } }
112 T1 (RO (1), froip, IP);      // { dg-warning "\\\[-Wuninitialized" "" { xfail *-*-* } }
113 T1 (RW (1), frwip, IP);      // { dg-warning "\\\[-Wmaybe-uninitialized" "" { xfail *-*-* } }
114 T1 (WO (1), fwoip, IP);
115 T1 (X (1),  fxip,  IP);
116 
117 
118 /* Verify that the notes printed after the warning mention attribute
119    access only when the attribute is explicitly used in the declaration
120    and not otherwise.  */
121 
test_note_cst_restrict(void)122 void test_note_cst_restrict (void)
123 {
124   extern void
125     fccar (const char[restrict]);   // { dg-message "by argument 1 of type 'const char\\\[restrict]' to 'fccar'" "note" }
126 
127   char a[1];                  // { dg-message "'a' declared here" "note" }
128   fccar (a);                  // { dg-warning "'a' may be used uninitialized" }
129 }
130 
test_note_vla(int n)131 void test_note_vla (int n)
132 {
133   extern void
134     fccvla (const char[n]);   // { dg-message "by argument 1 of type 'const char\\\[n]' to 'fccvla'" "note" }
135 
136   char a[2];                  // { dg-message "'a' declared here" "note" }
137   fccvla (a);                 // { dg-warning "'a' may be used uninitialized" }
138 }
139 
test_note_ro(void)140 void test_note_ro (void)
141 {
142   extern RO (1) void
143     frocar (char[restrict]);  // { dg-message "in a call to 'frocar' declared with attribute 'access \\\(read_only, 1\\\)'" "note" }
144 
145   char a[3];                  // { dg-message "'a' declared here" "note" }
146   frocar (a);                 // { dg-warning "'a' is used uninitialized" }
147 }
148 
test_note_rw(void)149 void test_note_rw (void)
150 {
151   extern RW (1) void
152     frwcar (char[restrict]);  // { dg-message "in a call to 'frwcar' declared with attribute 'access \\\(read_write, 1\\\)'" "note" }
153 
154   char a[4];                  // { dg-message "'a' declared here" "note" }
155   frwcar (a);                 // { dg-warning "'a' may be used uninitialized" }
156 }
157