1; RUN: llc -mtriple=i386-pc-linux-gnu < %s -o - | FileCheck --check-prefix=LINUX-I386 %s
2; RUN: llc -mtriple=x86_64-pc-linux-gnu < %s -o - | FileCheck --check-prefix=LINUX-X64 %s
3; RUN: llc -code-model=kernel -mtriple=x86_64-pc-linux-gnu < %s -o - | FileCheck --check-prefix=LINUX-KERNEL-X64 %s
4; RUN: llc -mtriple=x86_64-apple-darwin < %s -o - | FileCheck --check-prefix=DARWIN-X64 %s
5; RUN: llc -mtriple=amd64-pc-openbsd < %s -o - | FileCheck --check-prefix=OPENBSD-AMD64 %s
6; RUN: llc -mtriple=i386-pc-windows-msvc < %s -o - | FileCheck -check-prefix=MSVC-I386 %s
7; RUN: llc -mtriple=x86_64-w64-mingw32 < %s -o - | FileCheck --check-prefix=MINGW-X64 %s
8; RUN: llc -mtriple=x86_64-pc-linux-gnu < %s -o - | FileCheck --check-prefix=IGNORE_INTRIN %s
9
10%struct.foo = type { [16 x i8] }
11%struct.foo.0 = type { [4 x i8] }
12%struct.pair = type { i32, i32 }
13%struct.nest = type { %struct.pair, %struct.pair }
14%struct.vec = type { <4 x i32> }
15%class.A = type { [2 x i8] }
16%struct.deep = type { %union.anon }
17%union.anon = type { %struct.anon }
18%struct.anon = type { %struct.anon.0 }
19%struct.anon.0 = type { %union.anon.1 }
20%union.anon.1 = type { [2 x i8] }
21%struct.small = type { i8 }
22%struct.small_char = type { i32, [5 x i8] }
23
24@.str = private unnamed_addr constant [4 x i8] c"%s\0A\00", align 1
25
26; test1a: array of [16 x i8]
27;         no ssp attribute
28; Requires no protector.
29define void @test1a(ptr %a) {
30entry:
31; LINUX-I386-LABEL: test1a:
32; LINUX-I386-NOT: calll __stack_chk_fail
33; LINUX-I386: .cfi_endproc
34
35; LINUX-X64-LABEL: test1a:
36; LINUX-X64-NOT: callq __stack_chk_fail
37; LINUX-X64: .cfi_endproc
38
39; LINUX-KERNEL-X64-LABEL: test1a:
40; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
41; LINUX-KERNEL-X64: .cfi_endproc
42
43; DARWIN-X64-LABEL: test1a:
44; DARWIN-X64-NOT: callq ___stack_chk_fail
45; DARWIN-X64: .cfi_endproc
46
47; MSVC-I386-LABEL: test1a:
48; MSVC-I386-NOT: calll  @__security_check_cookie@4
49; MSVC-I386: retl
50
51; MINGW-X64-LABEL: test1a:
52; MINGW-X64-NOT: callq __stack_chk_fail
53; MINGW-X64: .seh_endproc
54
55  %a.addr = alloca ptr, align 8
56  %buf = alloca [16 x i8], align 16
57  store ptr %a, ptr %a.addr, align 8
58  %0 = load ptr, ptr %a.addr, align 8
59  %call = call ptr @strcpy(ptr %buf, ptr %0)
60  %call2 = call i32 (ptr, ...) @printf(ptr @.str, ptr %buf)
61  ret void
62}
63
64; test1b: array of [16 x i8]
65;         ssp attribute
66; Requires protector.
67; Function Attrs: ssp
68define void @test1b(ptr %a) #0 {
69entry:
70; LINUX-I386-LABEL: test1b:
71; LINUX-I386: mov{{l|q}} %gs:
72; LINUX-I386: calll __stack_chk_fail
73
74; LINUX-X64-LABEL: test1b:
75; LINUX-X64: mov{{l|q}} %fs:
76; LINUX-X64: callq __stack_chk_fail
77
78; LINUX-KERNEL-X64-LABEL: test1b:
79; LINUX-KERNEL-X64: mov{{l|q}} %gs:
80; LINUX-KERNEL-X64: callq __stack_chk_fail
81
82; DARWIN-X64-LABEL: test1b:
83; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
84; DARWIN-X64: callq ___stack_chk_fail
85
86; OPENBSD-AMD64-LABEL: test1b:
87; OPENBSD-AMD64: movq __guard_local(%rip)
88; OPENBSD-AMD64: callq __stack_smash_handler
89
90; MSVC-I386-LABEL: test1b:
91; MSVC-I386: movl ___security_cookie,
92; MSVC-I386: calll @__security_check_cookie@4
93
94; MINGW-X64-LABEL: test1b:
95; MINGW-X64: mov{{l|q}} .refptr.__stack_chk_guard
96; MINGW-X64: callq __stack_chk_fail
97
98  %a.addr = alloca ptr, align 8
99  %buf = alloca [16 x i8], align 16
100  store ptr %a, ptr %a.addr, align 8
101  %0 = load ptr, ptr %a.addr, align 8
102  %call = call ptr @strcpy(ptr %buf, ptr %0)
103  %call2 = call i32 (ptr, ...) @printf(ptr @.str, ptr %buf)
104  ret void
105}
106
107; test1c: array of [16 x i8]
108;         sspstrong attribute
109; Requires protector.
110; Function Attrs: sspstrong
111define void @test1c(ptr %a) #1 {
112entry:
113; LINUX-I386-LABEL: test1c:
114; LINUX-I386: mov{{l|q}} %gs:
115; LINUX-I386: calll __stack_chk_fail
116
117; LINUX-X64-LABEL: test1c:
118; LINUX-X64: mov{{l|q}} %fs:
119; LINUX-X64: callq __stack_chk_fail
120
121; LINUX-KERNEL-X64-LABEL: test1c:
122; LINUX-KERNEL-X64: mov{{l|q}} %gs:
123; LINUX-KERNEL-X64: callq __stack_chk_fail
124
125; DARWIN-X64-LABEL: test1c:
126; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
127; DARWIN-X64: callq ___stack_chk_fail
128
129; MSVC-I386-LABEL: test1c:
130; MSVC-I386: movl ___security_cookie,
131; MSVC-I386: calll @__security_check_cookie@4
132
133; MINGW-X64-LABEL: test1c:
134; MINGW-X64: mov{{l|q}} .refptr.__stack_chk_guard
135; MINGW-X64: callq __stack_chk_fail
136
137  %a.addr = alloca ptr, align 8
138  %buf = alloca [16 x i8], align 16
139  store ptr %a, ptr %a.addr, align 8
140  %0 = load ptr, ptr %a.addr, align 8
141  %call = call ptr @strcpy(ptr %buf, ptr %0)
142  %call2 = call i32 (ptr, ...) @printf(ptr @.str, ptr %buf)
143  ret void
144}
145
146; test1d: array of [16 x i8]
147;         sspreq attribute
148; Requires protector.
149; Function Attrs: sspreq
150define void @test1d(ptr %a) #2 {
151entry:
152; LINUX-I386-LABEL: test1d:
153; LINUX-I386: mov{{l|q}} %gs:
154; LINUX-I386: calll __stack_chk_fail
155
156; LINUX-X64-LABEL: test1d:
157; LINUX-X64: mov{{l|q}} %fs:
158; LINUX-X64: callq __stack_chk_fail
159
160; LINUX-KERNEL-X64-LABEL: test1d:
161; LINUX-KERNEL-X64: mov{{l|q}} %gs:
162; LINUX-KERNEL-X64: callq __stack_chk_fail
163
164; DARWIN-X64-LABEL: test1d:
165; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
166; DARWIN-X64: callq ___stack_chk_fail
167
168; MSVC-I386-LABEL: test1d:
169; MSVC-I386: movl ___security_cookie,
170; MSVC-I386: calll @__security_check_cookie@4
171
172; MINGW-X64-LABEL: test1d:
173; MINGW-X64: mov{{l|q}} .refptr.__stack_chk_guard
174; MINGW-X64: callq __stack_chk_fail
175
176  %a.addr = alloca ptr, align 8
177  %buf = alloca [16 x i8], align 16
178  store ptr %a, ptr %a.addr, align 8
179  %0 = load ptr, ptr %a.addr, align 8
180  %call = call ptr @strcpy(ptr %buf, ptr %0)
181  %call2 = call i32 (ptr, ...) @printf(ptr @.str, ptr %buf)
182  ret void
183}
184
185; test2a: struct { [16 x i8] }
186;         no ssp attribute
187; Requires no protector.
188define void @test2a(ptr %a) {
189entry:
190; LINUX-I386-LABEL: test2a:
191; LINUX-I386-NOT: calll __stack_chk_fail
192; LINUX-I386: .cfi_endproc
193
194; LINUX-X64-LABEL: test2a:
195; LINUX-X64-NOT: callq __stack_chk_fail
196; LINUX-X64: .cfi_endproc
197
198; LINUX-KERNEL-X64-LABEL: test2a:
199; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
200; LINUX-KERNEL-X64: .cfi_endproc
201
202; DARWIN-X64-LABEL: test2a:
203; DARWIN-X64-NOT: callq ___stack_chk_fail
204; DARWIN-X64: .cfi_endproc
205
206; MSVC-I386-LABEL: test2a:
207; MSVC-I386-NOT: calll @__security_check_cookie@4
208; MSVC-I386: retl
209
210; MINGW-X64-LABEL: test2a:
211; MINGW-X64-NOT: callq __stack_chk_fail
212; MINGW-X64: .seh_endproc
213
214  %a.addr = alloca ptr, align 8
215  %b = alloca %struct.foo, align 1
216  store ptr %a, ptr %a.addr, align 8
217  %0 = load ptr, ptr %a.addr, align 8
218  %call = call ptr @strcpy(ptr %b, ptr %0)
219  %call3 = call i32 (ptr, ...) @printf(ptr @.str, ptr %b)
220  ret void
221}
222
223; test2b: struct { [16 x i8] }
224;          ssp attribute
225; Requires protector.
226; Function Attrs: ssp
227define void @test2b(ptr %a) #0 {
228entry:
229; LINUX-I386-LABEL: test2b:
230; LINUX-I386: mov{{l|q}} %gs:
231; LINUX-I386: calll __stack_chk_fail
232
233; LINUX-X64-LABEL: test2b:
234; LINUX-X64: mov{{l|q}} %fs:
235; LINUX-X64: callq __stack_chk_fail
236
237; LINUX-KERNEL-X64-LABEL: test2b:
238; LINUX-KERNEL-X64: mov{{l|q}} %gs:
239; LINUX-KERNEL-X64: callq __stack_chk_fail
240
241; DARWIN-X64-LABEL: test2b:
242; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
243; DARWIN-X64: callq ___stack_chk_fail
244
245; MINGW-X64-LABEL: test2b:
246; MINGW-X64: mov{{l|q}} .refptr.__stack_chk_guard
247; MINGW-X64: callq __stack_chk_fail
248
249  %a.addr = alloca ptr, align 8
250  %b = alloca %struct.foo, align 1
251  store ptr %a, ptr %a.addr, align 8
252  %0 = load ptr, ptr %a.addr, align 8
253  %call = call ptr @strcpy(ptr %b, ptr %0)
254  %call3 = call i32 (ptr, ...) @printf(ptr @.str, ptr %b)
255  ret void
256}
257
258; test2c: struct { [16 x i8] }
259;          sspstrong attribute
260; Requires protector.
261; Function Attrs: sspstrong
262define void @test2c(ptr %a) #1 {
263entry:
264; LINUX-I386-LABEL: test2c:
265; LINUX-I386: mov{{l|q}} %gs:
266; LINUX-I386: calll __stack_chk_fail
267
268; LINUX-X64-LABEL: test2c:
269; LINUX-X64: mov{{l|q}} %fs:
270; LINUX-X64: callq __stack_chk_fail
271
272; LINUX-KERNEL-X64-LABEL: test2c:
273; LINUX-KERNEL-X64: mov{{l|q}} %gs:
274; LINUX-KERNEL-X64: callq __stack_chk_fail
275
276; DARWIN-X64-LABEL: test2c:
277; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
278; DARWIN-X64: callq ___stack_chk_fail
279
280; MSVC-I386-LABEL: test2c:
281; MSVC-I386: movl ___security_cookie,
282; MSVC-I386: calll @__security_check_cookie@4
283
284; MINGW-X64-LABEL: test2c:
285; MINGW-X64: mov{{l|q}} .refptr.__stack_chk_guard
286; MINGW-X64: callq __stack_chk_fail
287
288  %a.addr = alloca ptr, align 8
289  %b = alloca %struct.foo, align 1
290  store ptr %a, ptr %a.addr, align 8
291  %0 = load ptr, ptr %a.addr, align 8
292  %call = call ptr @strcpy(ptr %b, ptr %0)
293  %call3 = call i32 (ptr, ...) @printf(ptr @.str, ptr %b)
294  ret void
295}
296
297; test2d: struct { [16 x i8] }
298;          sspreq attribute
299; Requires protector.
300; Function Attrs: sspreq
301define void @test2d(ptr %a) #2 {
302entry:
303; LINUX-I386-LABEL: test2d:
304; LINUX-I386: mov{{l|q}} %gs:
305; LINUX-I386: calll __stack_chk_fail
306
307; LINUX-X64-LABEL: test2d:
308; LINUX-X64: mov{{l|q}} %fs:
309; LINUX-X64: callq __stack_chk_fail
310
311; LINUX-KERNEL-X64-LABEL: test2d:
312; LINUX-KERNEL-X64: mov{{l|q}} %gs:
313; LINUX-KERNEL-X64: callq __stack_chk_fail
314
315; DARWIN-X64-LABEL: test2d:
316; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
317; DARWIN-X64: callq ___stack_chk_fail
318
319; MSVC-I386-LABEL: test2d:
320; MSVC-I386: movl ___security_cookie,
321; MSVC-I386: calll @__security_check_cookie@4
322
323; MINGW-X64-LABEL: test2d:
324; MINGW-X64: mov{{l|q}} .refptr.__stack_chk_guard
325; MINGW-X64: callq __stack_chk_fail
326
327  %a.addr = alloca ptr, align 8
328  %b = alloca %struct.foo, align 1
329  store ptr %a, ptr %a.addr, align 8
330  %0 = load ptr, ptr %a.addr, align 8
331  %call = call ptr @strcpy(ptr %b, ptr %0)
332  %call3 = call i32 (ptr, ...) @printf(ptr @.str, ptr %b)
333  ret void
334}
335
336; test3a:  array of [4 x i8]
337;          no ssp attribute
338; Requires no protector.
339define void @test3a(ptr %a) {
340entry:
341; LINUX-I386-LABEL: test3a:
342; LINUX-I386-NOT: calll __stack_chk_fail
343; LINUX-I386: .cfi_endproc
344
345; LINUX-X64-LABEL: test3a:
346; LINUX-X64-NOT: callq __stack_chk_fail
347; LINUX-X64: .cfi_endproc
348
349; LINUX-KERNEL-X64-LABEL: test3a:
350; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
351; LINUX-KERNEL-X64: .cfi_endproc
352
353; DARWIN-X64-LABEL: test3a:
354; DARWIN-X64-NOT: callq ___stack_chk_fail
355; DARWIN-X64: .cfi_endproc
356
357; MSVC-I386-LABEL: test3a:
358; MSVC-I386-NOT: calll @__security_check_cookie@4
359; MSVC-I386: retl
360
361; MINGW-X64-LABEL: test3a:
362; MINGW-X64-NOT: callq __stack_chk_fail
363; MINGW-X64: .seh_endproc
364
365  %a.addr = alloca ptr, align 8
366  %buf = alloca [4 x i8], align 1
367  store ptr %a, ptr %a.addr, align 8
368  %0 = load ptr, ptr %a.addr, align 8
369  %call = call ptr @strcpy(ptr %buf, ptr %0)
370  %call2 = call i32 (ptr, ...) @printf(ptr @.str, ptr %buf)
371  ret void
372}
373
374; test3b:  array [4 x i8]
375;          ssp attribute
376; Requires no protector.
377; Function Attrs: ssp
378define void @test3b(ptr %a) #0 {
379entry:
380; LINUX-I386-LABEL: test3b:
381; LINUX-I386-NOT: calll __stack_chk_fail
382; LINUX-I386: .cfi_endproc
383
384; LINUX-X64-LABEL: test3b:
385; LINUX-X64-NOT: callq __stack_chk_fail
386; LINUX-X64: .cfi_endproc
387
388; LINUX-KERNEL-X64-LABEL: test3b:
389; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
390; LINUX-KERNEL-X64: .cfi_endproc
391
392; DARWIN-X64-LABEL: test3b:
393; DARWIN-X64-NOT: callq ___stack_chk_fail
394; DARWIN-X64: .cfi_endproc
395
396; MSVC-I386-LABEL: test3b:
397; MSVC-I386-NOT: calll @__security_check_cookie@4
398; MSVC-I386: retl
399
400; MINGW-X64-LABEL: test3b:
401; MINGW-X64-NOT: callq __stack_chk_fail
402; MINGW-X64: .seh_endproc
403
404  %a.addr = alloca ptr, align 8
405  %buf = alloca [4 x i8], align 1
406  store ptr %a, ptr %a.addr, align 8
407  %0 = load ptr, ptr %a.addr, align 8
408  %call = call ptr @strcpy(ptr %buf, ptr %0)
409  %call2 = call i32 (ptr, ...) @printf(ptr @.str, ptr %buf)
410  ret void
411}
412
413; test3c:  array of [4 x i8]
414;          sspstrong attribute
415; Requires protector.
416; Function Attrs: sspstrong
417define void @test3c(ptr %a) #1 {
418entry:
419; LINUX-I386-LABEL: test3c:
420; LINUX-I386: mov{{l|q}} %gs:
421; LINUX-I386: calll __stack_chk_fail
422
423; LINUX-X64-LABEL: test3c:
424; LINUX-X64: mov{{l|q}} %fs:
425; LINUX-X64: callq __stack_chk_fail
426
427; LINUX-KERNEL-X64-LABEL: test3c:
428; LINUX-KERNEL-X64: mov{{l|q}} %gs:
429; LINUX-KERNEL-X64: callq __stack_chk_fail
430
431; DARWIN-X64-LABEL: test3c:
432; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
433; DARWIN-X64: callq ___stack_chk_fail
434
435; MSVC-I386-LABEL: test3c:
436; MSVC-I386: movl ___security_cookie,
437; MSVC-I386: calll @__security_check_cookie@4
438
439; MINGW-X64-LABEL: test3c:
440; MINGW-X64: mov{{l|q}} .refptr.__stack_chk_guard
441; MINGW-X64: callq __stack_chk_fail
442
443  %a.addr = alloca ptr, align 8
444  %buf = alloca [4 x i8], align 1
445  store ptr %a, ptr %a.addr, align 8
446  %0 = load ptr, ptr %a.addr, align 8
447  %call = call ptr @strcpy(ptr %buf, ptr %0)
448  %call2 = call i32 (ptr, ...) @printf(ptr @.str, ptr %buf)
449  ret void
450}
451
452; test3d:  array of [4 x i8]
453;          sspreq attribute
454; Requires protector.
455; Function Attrs: sspreq
456define void @test3d(ptr %a) #2 {
457entry:
458; LINUX-I386-LABEL: test3d:
459; LINUX-I386: mov{{l|q}} %gs:
460; LINUX-I386: calll __stack_chk_fail
461
462; LINUX-X64-LABEL: test3d:
463; LINUX-X64: mov{{l|q}} %fs:
464; LINUX-X64: callq __stack_chk_fail
465
466; LINUX-KERNEL-X64-LABEL: test3d:
467; LINUX-KERNEL-X64: mov{{l|q}} %gs:
468; LINUX-KERNEL-X64: callq __stack_chk_fail
469
470; DARWIN-X64-LABEL: test3d:
471; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
472; DARWIN-X64: callq ___stack_chk_fail
473
474; MSVC-I386-LABEL: test3d:
475; MSVC-I386: movl ___security_cookie,
476; MSVC-I386: calll @__security_check_cookie@4
477
478; MINGW-X64-LABEL: test3d:
479; MINGW-X64: mov{{l|q}} .refptr.__stack_chk_guard
480; MINGW-X64: callq __stack_chk_fail
481
482  %a.addr = alloca ptr, align 8
483  %buf = alloca [4 x i8], align 1
484  store ptr %a, ptr %a.addr, align 8
485  %0 = load ptr, ptr %a.addr, align 8
486  %call = call ptr @strcpy(ptr %buf, ptr %0)
487  %call2 = call i32 (ptr, ...) @printf(ptr @.str, ptr %buf)
488  ret void
489}
490
491; test4a:  struct { [4 x i8] }
492;          no ssp attribute
493; Requires no protector.
494define void @test4a(ptr %a) {
495entry:
496; LINUX-I386-LABEL: test4a:
497; LINUX-I386-NOT: calll __stack_chk_fail
498; LINUX-I386: .cfi_endproc
499
500; LINUX-X64-LABEL: test4a:
501; LINUX-X64-NOT: callq __stack_chk_fail
502; LINUX-X64: .cfi_endproc
503
504; LINUX-KERNEL-X64-LABEL: test4a:
505; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
506; LINUX-KERNEL-X64: .cfi_endproc
507
508; DARWIN-X64-LABEL: test4a:
509; DARWIN-X64-NOT: callq ___stack_chk_fail
510; DARWIN-X64: .cfi_endproc
511
512; MSVC-I386-LABEL: test4a:
513; MSVC-I386-NOT: calll @__security_check_cookie@4
514; MSVC-I386: retl
515
516; MINGW-X64-LABEL: test4a:
517; MINGW-X64-NOT: callq __stack_chk_fail
518; MINGW-X64: .seh_endproc
519
520  %a.addr = alloca ptr, align 8
521  %b = alloca %struct.foo.0, align 1
522  store ptr %a, ptr %a.addr, align 8
523  %0 = load ptr, ptr %a.addr, align 8
524  %call = call ptr @strcpy(ptr %b, ptr %0)
525  %call3 = call i32 (ptr, ...) @printf(ptr @.str, ptr %b)
526  ret void
527}
528
529; test4b:  struct { [4 x i8] }
530;          ssp attribute
531; Requires no protector.
532; Function Attrs: ssp
533define void @test4b(ptr %a) #0 {
534entry:
535; LINUX-I386-LABEL: test4b:
536; LINUX-I386-NOT: calll __stack_chk_fail
537; LINUX-I386: .cfi_endproc
538
539; LINUX-X64-LABEL: test4b:
540; LINUX-X64-NOT: callq __stack_chk_fail
541; LINUX-X64: .cfi_endproc
542
543; LINUX-KERNEL-X64-LABEL: test4b:
544; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
545; LINUX-KERNEL-X64: .cfi_endproc
546
547; DARWIN-X64-LABEL: test4b:
548; DARWIN-X64-NOT: callq ___stack_chk_fail
549; DARWIN-X64: .cfi_endproc
550
551; MSVC-I386-LABEL: test4b:
552; MSVC-I386-NOT: calll @__security_check_cookie@4
553; MSVC-I386: retl
554
555; MINGW-X64-LABEL: test4b:
556; MINGW-X64-NOT: callq __stack_chk_fail
557; MINGW-X64: .seh_endproc
558
559  %a.addr = alloca ptr, align 8
560  %b = alloca %struct.foo.0, align 1
561  store ptr %a, ptr %a.addr, align 8
562  %0 = load ptr, ptr %a.addr, align 8
563  %call = call ptr @strcpy(ptr %b, ptr %0)
564  %call3 = call i32 (ptr, ...) @printf(ptr @.str, ptr %b)
565  ret void
566}
567
568; test4c:  struct { [4 x i8] }
569;          sspstrong attribute
570; Requires protector.
571; Function Attrs: sspstrong
572define void @test4c(ptr %a) #1 {
573entry:
574; LINUX-I386-LABEL: test4c:
575; LINUX-I386: mov{{l|q}} %gs:
576; LINUX-I386: calll __stack_chk_fail
577
578; LINUX-X64-LABEL: test4c:
579; LINUX-X64: mov{{l|q}} %fs:
580; LINUX-X64: callq __stack_chk_fail
581
582; LINUX-KERNEL-X64-LABEL: test4c:
583; LINUX-KERNEL-X64: mov{{l|q}} %gs:
584; LINUX-KERNEL-X64: callq __stack_chk_fail
585
586; DARWIN-X64-LABEL: test4c:
587; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
588; DARWIN-X64: callq ___stack_chk_fail
589
590; MSVC-I386-LABEL: test4c:
591; MSVC-I386: movl ___security_cookie,
592; MSVC-I386: calll @__security_check_cookie@4
593
594; MINGW-X64-LABEL: test4c:
595; MINGW-X64: mov{{l|q}} .refptr.__stack_chk_guard
596; MINGW-X64: callq __stack_chk_fail
597
598  %a.addr = alloca ptr, align 8
599  %b = alloca %struct.foo.0, align 1
600  store ptr %a, ptr %a.addr, align 8
601  %0 = load ptr, ptr %a.addr, align 8
602  %call = call ptr @strcpy(ptr %b, ptr %0)
603  %call3 = call i32 (ptr, ...) @printf(ptr @.str, ptr %b)
604  ret void
605}
606
607; test4d:  struct { [4 x i8] }
608;          sspreq attribute
609; Requires protector.
610; Function Attrs: sspreq
611define void @test4d(ptr %a) #2 {
612entry:
613; LINUX-I386-LABEL: test4d:
614; LINUX-I386: mov{{l|q}} %gs:
615; LINUX-I386: calll __stack_chk_fail
616
617; LINUX-X64-LABEL: test4d:
618; LINUX-X64: mov{{l|q}} %fs:
619; LINUX-X64: callq __stack_chk_fail
620
621; LINUX-KERNEL-X64-LABEL: test4d:
622; LINUX-KERNEL-X64: mov{{l|q}} %gs:
623; LINUX-KERNEL-X64: callq __stack_chk_fail
624
625; DARWIN-X64-LABEL: test4d:
626; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
627; DARWIN-X64: callq ___stack_chk_fail
628
629; MSVC-I386-LABEL: test4d:
630; MSVC-I386: movl ___security_cookie,
631; MSVC-I386: calll @__security_check_cookie@4
632
633; MINGW-X64-LABEL: test4d:
634; MINGW-X64: mov{{l|q}} .refptr.__stack_chk_guard
635; MINGW-X64: callq __stack_chk_fail
636
637  %a.addr = alloca ptr, align 8
638  %b = alloca %struct.foo.0, align 1
639  store ptr %a, ptr %a.addr, align 8
640  %0 = load ptr, ptr %a.addr, align 8
641  %call = call ptr @strcpy(ptr %b, ptr %0)
642  %call3 = call i32 (ptr, ...) @printf(ptr @.str, ptr %b)
643  ret void
644}
645
646; test5a:  no arrays / no nested arrays
647;          no ssp attribute
648; Requires no protector.
649define void @test5a(ptr %a) {
650entry:
651; LINUX-I386-LABEL: test5a:
652; LINUX-I386-NOT: calll __stack_chk_fail
653; LINUX-I386: .cfi_endproc
654
655; LINUX-X64-LABEL: test5a:
656; LINUX-X64-NOT: callq __stack_chk_fail
657; LINUX-X64: .cfi_endproc
658
659; LINUX-KERNEL-X64-LABEL: test5a:
660; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
661; LINUX-KERNEL-X64: .cfi_endproc
662
663; DARWIN-X64-LABEL: test5a:
664; DARWIN-X64-NOT: callq ___stack_chk_fail
665; DARWIN-X64: .cfi_endproc
666
667; MSVC-I386-LABEL: test5a:
668; MSVC-I386-NOT: calll @__security_check_cookie@4
669; MSVC-I386: retl
670
671; MINGW-X64-LABEL: test5a:
672; MINGW-X64-NOT: callq __stack_chk_fail
673; MINGW-X64: .seh_endproc
674
675  %a.addr = alloca ptr, align 8
676  store ptr %a, ptr %a.addr, align 8
677  %0 = load ptr, ptr %a.addr, align 8
678  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %0)
679  ret void
680}
681
682; test5b:  no arrays / no nested arrays
683;          ssp attribute
684; Requires no protector.
685; Function Attrs: ssp
686define void @test5b(ptr %a) #0 {
687entry:
688; LINUX-I386-LABEL: test5b:
689; LINUX-I386-NOT: calll __stack_chk_fail
690; LINUX-I386: .cfi_endproc
691
692; LINUX-X64-LABEL: test5b:
693; LINUX-X64-NOT: callq __stack_chk_fail
694; LINUX-X64: .cfi_endproc
695
696; LINUX-KERNEL-X64-LABEL: test5b:
697; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
698; LINUX-KERNEL-X64: .cfi_endproc
699
700; DARWIN-X64-LABEL: test5b:
701; DARWIN-X64-NOT: callq ___stack_chk_fail
702; DARWIN-X64: .cfi_endproc
703
704; MSVC-I386-LABEL: test5b:
705; MSVC-I386-NOT: calll @__security_check_cookie@4
706; MSVC-I386: retl
707
708; MINGW-X64-LABEL: test5b:
709; MINGW-X64-NOT: callq __stack_chk_fail
710; MINGW-X64: .seh_endproc
711
712  %a.addr = alloca ptr, align 8
713  store ptr %a, ptr %a.addr, align 8
714  %0 = load ptr, ptr %a.addr, align 8
715  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %0)
716  ret void
717}
718
719; test5c:  no arrays / no nested arrays
720;          sspstrong attribute
721; Requires no protector.
722; Function Attrs: sspstrong
723define void @test5c(ptr %a) #1 {
724entry:
725; LINUX-I386-LABEL: test5c:
726; LINUX-I386-NOT: calll __stack_chk_fail
727; LINUX-I386: .cfi_endproc
728
729; LINUX-X64-LABEL: test5c:
730; LINUX-X64-NOT: callq __stack_chk_fail
731; LINUX-X64: .cfi_endproc
732
733; LINUX-KERNEL-X64-LABEL: test5c:
734; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
735; LINUX-KERNEL-X64: .cfi_endproc
736
737; DARWIN-X64-LABEL: test5c:
738; DARWIN-X64-NOT: callq ___stack_chk_fail
739; DARWIN-X64: .cfi_endproc
740
741; MSVC-I386-LABEL: test5c:
742; MSVC-I386-NOT: calll @__security_check_cookie@4
743; MSVC-I386: retl
744
745; MINGW-X64-LABEL: test5c:
746; MINGW-X64-NOT: callq __stack_chk_fail
747; MINGW-X64: .seh_endproc
748
749  %a.addr = alloca ptr, align 8
750  store ptr %a, ptr %a.addr, align 8
751  %0 = load ptr, ptr %a.addr, align 8
752  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %0)
753  ret void
754}
755
756; test5d:  no arrays / no nested arrays
757;          sspreq attribute
758; Requires protector.
759; Function Attrs: sspreq
760define void @test5d(ptr %a) #2 {
761entry:
762; LINUX-I386-LABEL: test5d:
763; LINUX-I386: mov{{l|q}} %gs:
764; LINUX-I386: calll __stack_chk_fail
765
766; LINUX-X64-LABEL: test5d:
767; LINUX-X64: mov{{l|q}} %fs:
768; LINUX-X64: callq __stack_chk_fail
769
770; LINUX-KERNEL-X64-LABEL: test5d:
771; LINUX-KERNEL-X64: mov{{l|q}} %gs:
772; LINUX-KERNEL-X64: callq __stack_chk_fail
773
774; DARWIN-X64-LABEL: test5d:
775; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
776; DARWIN-X64: callq ___stack_chk_fail
777
778; MSVC-I386-LABEL: test5d:
779; MSVC-I386: movl ___security_cookie,
780; MSVC-I386: calll @__security_check_cookie@4
781
782; MINGW-X64-LABEL: test5d:
783; MINGW-X64: mov{{l|q}} .refptr.__stack_chk_guard
784; MINGW-X64: callq __stack_chk_fail
785
786  %a.addr = alloca ptr, align 8
787  store ptr %a, ptr %a.addr, align 8
788  %0 = load ptr, ptr %a.addr, align 8
789  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %0)
790  ret void
791}
792
793; test6a:  Address-of local taken (j = &a)
794;          no ssp attribute
795; Requires no protector.
796define void @test6a() {
797entry:
798; LINUX-I386-LABEL: test6a:
799; LINUX-I386-NOT: calll __stack_chk_fail
800; LINUX-I386: .cfi_endproc
801
802; LINUX-X64-LABEL: test6a:
803; LINUX-X64-NOT: callq __stack_chk_fail
804; LINUX-X64: .cfi_endproc
805
806; LINUX-KERNEL-X64-LABEL: test6a:
807; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
808; LINUX-KERNEL-X64: .cfi_endproc
809
810; DARWIN-X64-LABEL: test6a:
811; DARWIN-X64-NOT: callq ___stack_chk_fail
812; DARWIN-X64: .cfi_endproc
813
814; MSVC-I386-LABEL: test6a:
815; MSVC-I386-NOT: calll @__security_check_cookie@4
816; MSVC-I386: retl
817
818; MINGW-X64-LABEL: test6a:
819; MINGW-X64-NOT: callq __stack_chk_fail
820; MINGW-X64: .seh_endproc
821
822  %retval = alloca i32, align 4
823  %a = alloca i32, align 4
824  %j = alloca ptr, align 8
825  store i32 0, ptr %retval
826  %0 = load i32, ptr %a, align 4
827  %add = add nsw i32 %0, 1
828  store i32 %add, ptr %a, align 4
829  store ptr %a, ptr %j, align 8
830  ret void
831}
832
833; test6b:  Address-of local taken (j = &a)
834;          ssp attribute
835; Requires no protector.
836; Function Attrs: ssp
837define void @test6b() #0 {
838entry:
839; LINUX-I386-LABEL: test6b:
840; LINUX-I386-NOT: calll __stack_chk_fail
841; LINUX-I386: .cfi_endproc
842
843; LINUX-X64-LABEL: test6b:
844; LINUX-X64-NOT: callq __stack_chk_fail
845; LINUX-X64: .cfi_endproc
846
847; LINUX-KERNEL-X64-LABEL: test6b:
848; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
849; LINUX-KERNEL-X64: .cfi_endproc
850
851; DARWIN-X64-LABEL: test6b:
852; DARWIN-X64-NOT: callq ___stack_chk_fail
853; DARWIN-X64: .cfi_endproc
854
855; MSVC-I386-LABEL: test6b:
856; MSVC-I386-NOT: calll @__security_check_cookie@4
857; MSVC-I386: retl
858
859; MINGW-X64-LABEL: test6b:
860; MINGW-X64-NOT: callq __stack_chk_fail
861; MINGW-X64: .seh_endproc
862
863  %retval = alloca i32, align 4
864  %a = alloca i32, align 4
865  %j = alloca ptr, align 8
866  store i32 0, ptr %retval
867  %0 = load i32, ptr %a, align 4
868  %add = add nsw i32 %0, 1
869  store i32 %add, ptr %a, align 4
870  store ptr %a, ptr %j, align 8
871  ret void
872}
873
874; test6c:  Address-of local taken (j = &a)
875;          sspstrong attribute
876; Requires protector.
877; Function Attrs: sspstrong
878define void @test6c() #1 {
879entry:
880; LINUX-I386-LABEL: test6c:
881; LINUX-I386: mov{{l|q}} %gs:
882; LINUX-I386: calll __stack_chk_fail
883
884; LINUX-X64-LABEL: test6c:
885; LINUX-X64: mov{{l|q}} %fs:
886; LINUX-X64: callq __stack_chk_fail
887
888; LINUX-KERNEL-X64-LABEL: test6c:
889; LINUX-KERNEL-X64: mov{{l|q}} %gs:
890; LINUX-KERNEL-X64: callq __stack_chk_fail
891
892; DARWIN-X64-LABEL: test6c:
893; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
894; DARWIN-X64: callq ___stack_chk_fail
895
896; MSVC-I386-LABEL: test6c:
897; MSVC-I386: movl ___security_cookie,
898; MSVC-I386: calll @__security_check_cookie@4
899
900; MINGW-X64-LABEL: test6c:
901; MINGW-X64: mov{{l|q}} .refptr.__stack_chk_guard
902; MINGW-X64: callq __stack_chk_fail
903
904  %retval = alloca i32, align 4
905  %a = alloca i32, align 4
906  %j = alloca ptr, align 8
907  store i32 0, ptr %retval
908  %0 = load i32, ptr %a, align 4
909  %add = add nsw i32 %0, 1
910  store i32 %add, ptr %a, align 4
911  store ptr %a, ptr %j, align 8
912  ret void
913}
914
915; test6d:  Address-of local taken (j = &a)
916;          sspreq attribute
917; Requires protector.
918; Function Attrs: sspreq
919define void @test6d() #2 {
920entry:
921; LINUX-I386-LABEL: test6d:
922; LINUX-I386: mov{{l|q}} %gs:
923; LINUX-I386: calll __stack_chk_fail
924
925; LINUX-X64-LABEL: test6d:
926; LINUX-X64: mov{{l|q}} %fs:
927; LINUX-X64: callq __stack_chk_fail
928
929; LINUX-KERNEL-X64-LABEL: test6d:
930; LINUX-KERNEL-X64: mov{{l|q}} %gs:
931; LINUX-KERNEL-X64: callq __stack_chk_fail
932
933; DARWIN-X64-LABEL: test6d:
934; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
935; DARWIN-X64: callq ___stack_chk_fail
936
937; MSVC-I386-LABEL: test6d:
938; MSVC-I386: movl ___security_cookie,
939; MSVC-I386: calll @__security_check_cookie@4
940
941; MINGW-X64-LABEL: test6d:
942; MINGW-X64: mov{{l|q}} .refptr.__stack_chk_guard
943; MINGW-X64: callq __stack_chk_fail
944
945  %retval = alloca i32, align 4
946  %a = alloca i32, align 4
947  %j = alloca ptr, align 8
948  store i32 0, ptr %retval
949  %0 = load i32, ptr %a, align 4
950  %add = add nsw i32 %0, 1
951  store i32 %add, ptr %a, align 4
952  store ptr %a, ptr %j, align 8
953  ret void
954}
955
956; test7a:  PtrToInt Cast
957;          no ssp attribute
958; Requires no protector.
959define void @test7a()  {
960entry:
961; LINUX-I386-LABEL: test7a:
962; LINUX-I386-NOT: calll __stack_chk_fail
963; LINUX-I386: .cfi_endproc
964
965; LINUX-X64-LABEL: test7a:
966; LINUX-X64-NOT: callq __stack_chk_fail
967; LINUX-X64: .cfi_endproc
968
969; LINUX-KERNEL-X64-LABEL: test7a:
970; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
971; LINUX-KERNEL-X64: .cfi_endproc
972
973; DARWIN-X64-LABEL: test7a:
974; DARWIN-X64-NOT: callq ___stack_chk_fail
975; DARWIN-X64: .cfi_endproc
976
977; MSVC-I386-LABEL: test7a:
978; MSVC-I386-NOT: calll @__security_check_cookie@4
979; MSVC-I386: retl
980
981; MINGW-X64-LABEL: test7a:
982; MINGW-X64-NOT: callq __stack_chk_fail
983; MINGW-X64: .seh_endproc
984
985  %a = alloca i32, align 4
986  %0 = ptrtoint ptr %a to i64
987  %call = call i32 (ptr, ...) @printf(ptr @.str, i64 %0)
988  ret void
989}
990
991; test7b:  PtrToInt Cast
992;          ssp attribute
993; Requires no protector.
994; Function Attrs: ssp
995define void @test7b() #0 {
996entry:
997; LINUX-I386-LABEL: test7b:
998; LINUX-I386-NOT: calll __stack_chk_fail
999; LINUX-I386: .cfi_endproc
1000
1001; LINUX-X64-LABEL: test7b:
1002; LINUX-X64-NOT: callq __stack_chk_fail
1003; LINUX-X64: .cfi_endproc
1004
1005; LINUX-KERNEL-X64-LABEL: test7b:
1006; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
1007; LINUX-KERNEL-X64: .cfi_endproc
1008
1009; DARWIN-X64-LABEL: test7b:
1010; DARWIN-X64-NOT: callq ___stack_chk_fail
1011; DARWIN-X64: .cfi_endproc
1012
1013; MSVC-I386-LABEL: test7b:
1014; MSVC-I386-NOT: calll @__security_check_cookie@4
1015; MSVC-I386: retl
1016
1017; MINGW-X64-LABEL: test7b:
1018; MINGW-X64-NOT: callq __stack_chk_fail
1019; MINGW-X64: .seh_endproc
1020
1021  %a = alloca i32, align 4
1022  %0 = ptrtoint ptr %a to i64
1023  %call = call i32 (ptr, ...) @printf(ptr @.str, i64 %0)
1024  ret void
1025}
1026
1027; test7c:  PtrToInt Cast
1028;          sspstrong attribute
1029; Requires protector.
1030; Function Attrs: sspstrong
1031define void @test7c() #1 {
1032entry:
1033; LINUX-I386-LABEL: test7c:
1034; LINUX-I386: mov{{l|q}} %gs:
1035; LINUX-I386: calll __stack_chk_fail
1036
1037; LINUX-X64-LABEL: test7c:
1038; LINUX-X64: mov{{l|q}} %fs:
1039; LINUX-X64: callq __stack_chk_fail
1040
1041; LINUX-KERNEL-X64-LABEL: test7c:
1042; LINUX-KERNEL-X64: mov{{l|q}} %gs:
1043; LINUX-KERNEL-X64: callq __stack_chk_fail
1044
1045; DARWIN-X64-LABEL: test7c:
1046; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
1047; DARWIN-X64: callq ___stack_chk_fail
1048
1049; MSVC-I386-LABEL: test7c:
1050; MSVC-I386: movl ___security_cookie,
1051; MSVC-I386: calll @__security_check_cookie@4
1052
1053; MINGW-X64-LABEL: test7c:
1054; MINGW-X64: mov{{l|q}} .refptr.__stack_chk_guard
1055; MINGW-X64: .seh_endproc
1056
1057  %a = alloca i32, align 4
1058  %0 = ptrtoint ptr %a to i64
1059  %call = call i32 (ptr, ...) @printf(ptr @.str, i64 %0)
1060  ret void
1061}
1062
1063; test7d:  PtrToInt Cast
1064;          sspreq attribute
1065; Requires protector.
1066; Function Attrs: sspreq
1067define void @test7d() #2 {
1068entry:
1069; LINUX-I386-LABEL: test7d:
1070; LINUX-I386: mov{{l|q}} %gs:
1071; LINUX-I386: calll __stack_chk_fail
1072
1073; LINUX-X64-LABEL: test7d:
1074; LINUX-X64: mov{{l|q}} %fs:
1075; LINUX-X64: callq __stack_chk_fail
1076
1077; LINUX-KERNEL-X64-LABEL: test7d:
1078; LINUX-KERNEL-X64: mov{{l|q}} %gs:
1079; LINUX-KERNEL-X64: callq __stack_chk_fail
1080
1081; DARWIN-X64-LABEL: test7d:
1082; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
1083; DARWIN-X64: callq ___stack_chk_fail
1084
1085; MSVC-I386-LABEL: test7d:
1086; MSVC-I386: movl ___security_cookie,
1087; MSVC-I386: calll @__security_check_cookie@4
1088
1089; MINGW-X64-LABEL: test7d:
1090; MINGW-X64: mov{{l|q}} .refptr.__stack_chk_guard
1091; MINGW-X64: callq __stack_chk_fail
1092
1093  %a = alloca i32, align 4
1094  %0 = ptrtoint ptr %a to i64
1095  %call = call i32 (ptr, ...) @printf(ptr @.str, i64 %0)
1096  ret void
1097}
1098
1099; test8a:  Passing addr-of to function call
1100;          no ssp attribute
1101; Requires no protector.
1102define void @test8a() {
1103entry:
1104; LINUX-I386-LABEL: test8a:
1105; LINUX-I386-NOT: calll __stack_chk_fail
1106; LINUX-I386: .cfi_endproc
1107
1108; LINUX-X64-LABEL: test8a:
1109; LINUX-X64-NOT: callq __stack_chk_fail
1110; LINUX-X64: .cfi_endproc
1111
1112; LINUX-KERNEL-X64-LABEL: test8a:
1113; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
1114; LINUX-KERNEL-X64: .cfi_endproc
1115
1116; DARWIN-X64-LABEL: test8a:
1117; DARWIN-X64-NOT: callq ___stack_chk_fail
1118; DARWIN-X64: .cfi_endproc
1119
1120; MSVC-I386-LABEL: test8a:
1121; MSVC-I386-NOT: calll @__security_check_cookie@4
1122; MSVC-I386: retl
1123
1124; MINGW-X64-LABEL: test8a:
1125; MINGW-X64-NOT: callq __stack_chk_fail
1126; MINGW-X64: .seh_endproc
1127
1128  %b = alloca i32, align 4
1129  call void @funcall(ptr %b)
1130  ret void
1131}
1132
1133; test8b:  Passing addr-of to function call
1134;          ssp attribute
1135; Requires no protector.
1136; Function Attrs: ssp
1137define void @test8b() #0 {
1138entry:
1139; LINUX-I386-LABEL: test8b:
1140; LINUX-I386-NOT: calll __stack_chk_fail
1141; LINUX-I386: .cfi_endproc
1142
1143; LINUX-X64-LABEL: test8b:
1144; LINUX-X64-NOT: callq __stack_chk_fail
1145; LINUX-X64: .cfi_endproc
1146
1147; LINUX-KERNEL-X64-LABEL: test8b:
1148; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
1149; LINUX-KERNEL-X64: .cfi_endproc
1150
1151; DARWIN-X64-LABEL: test8b:
1152; DARWIN-X64-NOT: callq ___stack_chk_fail
1153; DARWIN-X64: .cfi_endproc
1154
1155; MSVC-I386-LABEL: test8b:
1156; MSVC-I386-NOT: calll @__security_check_cookie@4
1157; MSVC-I386: retl
1158
1159; MINGW-X64-LABEL: test8b:
1160; MINGW-X64-NOT: callq __stack_chk_fail
1161; MINGW-X64: .seh_endproc
1162
1163  %b = alloca i32, align 4
1164  call void @funcall(ptr %b)
1165  ret void
1166}
1167
1168; test8c:  Passing addr-of to function call
1169;          sspstrong attribute
1170; Requires protector.
1171; Function Attrs: sspstrong
1172define void @test8c() #1 {
1173entry:
1174; LINUX-I386-LABEL: test8c:
1175; LINUX-I386: mov{{l|q}} %gs:
1176; LINUX-I386: calll __stack_chk_fail
1177
1178; LINUX-X64-LABEL: test8c:
1179; LINUX-X64: mov{{l|q}} %fs:
1180; LINUX-X64: callq __stack_chk_fail
1181
1182; LINUX-KERNEL-X64-LABEL: test8c:
1183; LINUX-KERNEL-X64: mov{{l|q}} %gs:
1184; LINUX-KERNEL-X64: callq __stack_chk_fail
1185
1186; DARWIN-X64-LABEL: test8c:
1187; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
1188; DARWIN-X64: callq ___stack_chk_fail
1189
1190; MSVC-I386-LABEL: test8c:
1191; MSVC-I386: movl ___security_cookie,
1192; MSVC-I386: calll @__security_check_cookie@4
1193
1194; MINGW-X64-LABEL: test8c:
1195; MINGW-X64: mov{{l|q}} .refptr.__stack_chk_guard
1196; MINGW-X64: callq __stack_chk_fail
1197
1198  %b = alloca i32, align 4
1199  call void @funcall(ptr %b)
1200  ret void
1201}
1202
1203; test8d:  Passing addr-of to function call
1204;          sspreq attribute
1205; Requires protector.
1206; Function Attrs: sspreq
1207define void @test8d() #2 {
1208entry:
1209; LINUX-I386-LABEL: test8d:
1210; LINUX-I386: mov{{l|q}} %gs:
1211; LINUX-I386: calll __stack_chk_fail
1212
1213; LINUX-X64-LABEL: test8d:
1214; LINUX-X64: mov{{l|q}} %fs:
1215; LINUX-X64: callq __stack_chk_fail
1216
1217; LINUX-KERNEL-X64-LABEL: test8d:
1218; LINUX-KERNEL-X64: mov{{l|q}} %gs:
1219; LINUX-KERNEL-X64: callq __stack_chk_fail
1220
1221; DARWIN-X64-LABEL: test8d:
1222; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
1223; DARWIN-X64: callq ___stack_chk_fail
1224
1225; MSVC-I386-LABEL: test8d:
1226; MSVC-I386: movl ___security_cookie,
1227; MSVC-I386: calll @__security_check_cookie@4
1228
1229; MINGW-X64-LABEL: test8d:
1230; MINGW-X64: mov{{l|q}} .refptr.__stack_chk_guard
1231; MINGW-X64: callq __stack_chk_fail
1232
1233  %b = alloca i32, align 4
1234  call void @funcall(ptr %b)
1235  ret void
1236}
1237
1238; test9a:  Addr-of in select instruction
1239;          no ssp attribute
1240; Requires no protector.
1241define void @test9a() {
1242entry:
1243; LINUX-I386-LABEL: test9a:
1244; LINUX-I386-NOT: calll __stack_chk_fail
1245; LINUX-I386: .cfi_endproc
1246
1247; LINUX-X64-LABEL: test9a:
1248; LINUX-X64-NOT: callq __stack_chk_fail
1249; LINUX-X64: .cfi_endproc
1250
1251; LINUX-KERNEL-X64-LABEL: test9a:
1252; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
1253; LINUX-KERNEL-X64: .cfi_endproc
1254
1255; DARWIN-X64-LABEL: test9a:
1256; DARWIN-X64-NOT: callq ___stack_chk_fail
1257; DARWIN-X64: .cfi_endproc
1258
1259; MSVC-I386-LABEL: test9a:
1260; MSVC-I386-NOT: calll @__security_check_cookie@4
1261; MSVC-I386: retl
1262  %x = alloca double, align 8
1263  %call = call double @testi_aux()
1264  store double %call, ptr %x, align 8
1265  %cmp2 = fcmp ogt double %call, 0.000000e+00
1266  %y.1 = select i1 %cmp2, ptr %x, ptr null
1267  %call2 = call i32 (ptr, ...) @printf(ptr @.str, ptr %y.1)
1268  ret void
1269}
1270
1271; test9b:  Addr-of in select instruction
1272;          ssp attribute
1273; Requires no protector.
1274; Function Attrs: ssp
1275define void @test9b() #0 {
1276entry:
1277; LINUX-I386-LABEL: test9b:
1278; LINUX-I386-NOT: calll __stack_chk_fail
1279; LINUX-I386: .cfi_endproc
1280
1281; LINUX-X64-LABEL: test9b:
1282; LINUX-X64-NOT: callq __stack_chk_fail
1283; LINUX-X64: .cfi_endproc
1284
1285; LINUX-KERNEL-X64-LABEL: test9b:
1286; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
1287; LINUX-KERNEL-X64: .cfi_endproc
1288
1289; DARWIN-X64-LABEL: test9b:
1290; DARWIN-X64-NOT: callq ___stack_chk_fail
1291; DARWIN-X64: .cfi_endproc
1292
1293; MSVC-I386-LABEL: test9b:
1294; MSVC-I386-NOT: calll @__security_check_cookie@4
1295; MSVC-I386: retl
1296  %x = alloca double, align 8
1297  %call = call double @testi_aux()
1298  store double %call, ptr %x, align 8
1299  %cmp2 = fcmp ogt double %call, 0.000000e+00
1300  %y.1 = select i1 %cmp2, ptr %x, ptr null
1301  %call2 = call i32 (ptr, ...) @printf(ptr @.str, ptr %y.1)
1302  ret void
1303}
1304
1305; test9c:  Addr-of in select instruction
1306;          sspstrong attribute
1307; Requires protector.
1308; Function Attrs: sspstrong
1309define void @test9c() #1 {
1310entry:
1311; LINUX-I386-LABEL: test9c:
1312; LINUX-I386: mov{{l|q}} %gs:
1313; LINUX-I386: calll __stack_chk_fail
1314
1315; LINUX-X64-LABEL: test9c:
1316; LINUX-X64: mov{{l|q}} %fs:
1317; LINUX-X64: callq __stack_chk_fail
1318
1319; LINUX-KERNEL-X64-LABEL: test9c:
1320; LINUX-KERNEL-X64: mov{{l|q}} %gs:
1321; LINUX-KERNEL-X64: callq __stack_chk_fail
1322
1323; DARWIN-X64-LABEL: test9c:
1324; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
1325; DARWIN-X64: callq ___stack_chk_fail
1326
1327; MSVC-I386-LABEL: test9c:
1328; MSVC-I386: movl ___security_cookie,
1329; MSVC-I386: calll @__security_check_cookie@4
1330  %x = alloca double, align 8
1331  %call = call double @testi_aux()
1332  store double %call, ptr %x, align 8
1333  %cmp2 = fcmp ogt double %call, 0.000000e+00
1334  %y.1 = select i1 %cmp2, ptr %x, ptr null
1335  %call2 = call i32 (ptr, ...) @printf(ptr @.str, ptr %y.1)
1336  ret void
1337}
1338
1339; test9d:  Addr-of in select instruction
1340;          sspreq attribute
1341; Requires protector.
1342; Function Attrs: sspreq
1343define void @test9d() #2 {
1344entry:
1345; LINUX-I386-LABEL: test9d:
1346; LINUX-I386: mov{{l|q}} %gs:
1347; LINUX-I386: calll __stack_chk_fail
1348
1349; LINUX-X64-LABEL: test9d:
1350; LINUX-X64: mov{{l|q}} %fs:
1351; LINUX-X64: callq __stack_chk_fail
1352
1353; LINUX-KERNEL-X64-LABEL: test9d:
1354; LINUX-KERNEL-X64: mov{{l|q}} %gs:
1355; LINUX-KERNEL-X64: callq __stack_chk_fail
1356
1357; DARWIN-X64-LABEL: test9d:
1358; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
1359; DARWIN-X64: callq ___stack_chk_fail
1360
1361; MSVC-I386-LABEL: test9d:
1362; MSVC-I386: movl ___security_cookie,
1363; MSVC-I386: calll @__security_check_cookie@4
1364  %x = alloca double, align 8
1365  %call = call double @testi_aux()
1366  store double %call, ptr %x, align 8
1367  %cmp2 = fcmp ogt double %call, 0.000000e+00
1368  %y.1 = select i1 %cmp2, ptr %x, ptr null
1369  %call2 = call i32 (ptr, ...) @printf(ptr @.str, ptr %y.1)
1370  ret void
1371}
1372
1373; test10a: Addr-of in phi instruction
1374;          no ssp attribute
1375; Requires no protector.
1376define void @test10a() {
1377entry:
1378; LINUX-I386-LABEL: test10a:
1379; LINUX-I386-NOT: calll __stack_chk_fail
1380; LINUX-I386: .cfi_endproc
1381
1382; LINUX-X64-LABEL: test10a:
1383; LINUX-X64-NOT: callq __stack_chk_fail
1384; LINUX-X64: .cfi_endproc
1385
1386; LINUX-KERNEL-X64-LABEL: test10a:
1387; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
1388; LINUX-KERNEL-X64: .cfi_endproc
1389
1390; DARWIN-X64-LABEL: test10a:
1391; DARWIN-X64-NOT: callq ___stack_chk_fail
1392; DARWIN-X64: .cfi_endproc
1393
1394; MSVC-I386-LABEL: test10a:
1395; MSVC-I386-NOT: calll @__security_check_cookie@4
1396; MSVC-I386: retl
1397  %x = alloca double, align 8
1398  %call = call double @testi_aux()
1399  store double %call, ptr %x, align 8
1400  %cmp = fcmp ogt double %call, 3.140000e+00
1401  br i1 %cmp, label %if.then, label %if.else
1402
1403if.then:                                          ; preds = %entry
1404  %call1 = call double @testi_aux()
1405  store double %call1, ptr %x, align 8
1406  br label %if.end4
1407
1408if.else:                                          ; preds = %entry
1409  %cmp2 = fcmp ogt double %call, 1.000000e+00
1410  br i1 %cmp2, label %if.then3, label %if.end4
1411
1412if.then3:                                         ; preds = %if.else
1413  br label %if.end4
1414
1415if.end4:                                          ; preds = %if.else, %if.then3, %if.then
1416  %y.0 = phi ptr [ null, %if.then ], [ %x, %if.then3 ], [ null, %if.else ]
1417  %call5 = call i32 (ptr, ...) @printf(ptr @.str, ptr %y.0)
1418  ret void
1419}
1420
1421; test10b: Addr-of in phi instruction
1422;          ssp attribute
1423; Requires no protector.
1424; Function Attrs: ssp
1425define void @test10b() #0 {
1426entry:
1427; LINUX-I386-LABEL: test10b:
1428; LINUX-I386-NOT: calll __stack_chk_fail
1429; LINUX-I386: .cfi_endproc
1430
1431; LINUX-X64-LABEL: test10b:
1432; LINUX-X64-NOT: callq __stack_chk_fail
1433; LINUX-X64: .cfi_endproc
1434
1435; LINUX-KERNEL-X64-LABEL: test10b:
1436; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
1437; LINUX-KERNEL-X64: .cfi_endproc
1438
1439; DARWIN-X64-LABEL: test10b:
1440; DARWIN-X64-NOT: callq ___stack_chk_fail
1441; DARWIN-X64: .cfi_endproc
1442
1443; MSVC-I386-LABEL: test10b:
1444; MSVC-I386-NOT: calll @__security_check_cookie@4
1445; MSVC-I386: retl
1446  %x = alloca double, align 8
1447  %call = call double @testi_aux()
1448  store double %call, ptr %x, align 8
1449  %cmp = fcmp ogt double %call, 3.140000e+00
1450  br i1 %cmp, label %if.then, label %if.else
1451
1452if.then:                                          ; preds = %entry
1453  %call1 = call double @testi_aux()
1454  store double %call1, ptr %x, align 8
1455  br label %if.end4
1456
1457if.else:                                          ; preds = %entry
1458  %cmp2 = fcmp ogt double %call, 1.000000e+00
1459  br i1 %cmp2, label %if.then3, label %if.end4
1460
1461if.then3:                                         ; preds = %if.else
1462  br label %if.end4
1463
1464if.end4:                                          ; preds = %if.else, %if.then3, %if.then
1465  %y.0 = phi ptr [ null, %if.then ], [ %x, %if.then3 ], [ null, %if.else ]
1466  %call5 = call i32 (ptr, ...) @printf(ptr @.str, ptr %y.0)
1467  ret void
1468}
1469
1470; test10c: Addr-of in phi instruction
1471;          sspstrong attribute
1472; Requires protector.
1473; Function Attrs: sspstrong
1474define void @test10c() #1 {
1475entry:
1476; LINUX-I386-LABEL: test10c:
1477; LINUX-I386: mov{{l|q}} %gs:
1478; LINUX-I386: calll __stack_chk_fail
1479
1480; LINUX-X64-LABEL: test10c:
1481; LINUX-X64: mov{{l|q}} %fs:
1482; LINUX-X64: callq __stack_chk_fail
1483
1484; LINUX-KERNEL-X64-LABEL: test10c:
1485; LINUX-KERNEL-X64: mov{{l|q}} %gs:
1486; LINUX-KERNEL-X64: callq __stack_chk_fail
1487
1488; DARWIN-X64-LABEL: test10c:
1489; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
1490; DARWIN-X64: callq ___stack_chk_fail
1491
1492; MSVC-I386-LABEL: test10c:
1493; MSVC-I386: movl ___security_cookie,
1494; MSVC-I386: calll @__security_check_cookie@4
1495  %x = alloca double, align 8
1496  %call = call double @testi_aux()
1497  store double %call, ptr %x, align 8
1498  %cmp = fcmp ogt double %call, 3.140000e+00
1499  br i1 %cmp, label %if.then, label %if.else
1500
1501if.then:                                          ; preds = %entry
1502  %call1 = call double @testi_aux()
1503  store double %call1, ptr %x, align 8
1504  br label %if.end4
1505
1506if.else:                                          ; preds = %entry
1507  %cmp2 = fcmp ogt double %call, 1.000000e+00
1508  br i1 %cmp2, label %if.then3, label %if.end4
1509
1510if.then3:                                         ; preds = %if.else
1511  br label %if.end4
1512
1513if.end4:                                          ; preds = %if.else, %if.then3, %if.then
1514  %y.0 = phi ptr [ null, %if.then ], [ %x, %if.then3 ], [ null, %if.else ]
1515  %call5 = call i32 (ptr, ...) @printf(ptr @.str, ptr %y.0)
1516  ret void
1517}
1518
1519; test10d: Addr-of in phi instruction
1520;          sspreq attribute
1521; Requires protector.
1522; Function Attrs: sspreq
1523define void @test10d() #2 {
1524entry:
1525; LINUX-I386-LABEL: test10d:
1526; LINUX-I386: mov{{l|q}} %gs:
1527; LINUX-I386: calll __stack_chk_fail
1528
1529; LINUX-X64-LABEL: test10d:
1530; LINUX-X64: mov{{l|q}} %fs:
1531; LINUX-X64: callq __stack_chk_fail
1532
1533; LINUX-KERNEL-X64-LABEL: test10d:
1534; LINUX-KERNEL-X64: mov{{l|q}} %gs:
1535; LINUX-KERNEL-X64: callq __stack_chk_fail
1536
1537; DARWIN-X64-LABEL: test10d:
1538; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
1539; DARWIN-X64: callq ___stack_chk_fail
1540
1541; MSVC-I386-LABEL: test10d:
1542; MSVC-I386: movl ___security_cookie,
1543; MSVC-I386: calll @__security_check_cookie@4
1544  %x = alloca double, align 8
1545  %call = call double @testi_aux()
1546  store double %call, ptr %x, align 8
1547  %cmp = fcmp ogt double %call, 3.140000e+00
1548  br i1 %cmp, label %if.then, label %if.else
1549
1550if.then:                                          ; preds = %entry
1551  %call1 = call double @testi_aux()
1552  store double %call1, ptr %x, align 8
1553  br label %if.end4
1554
1555if.else:                                          ; preds = %entry
1556  %cmp2 = fcmp ogt double %call, 1.000000e+00
1557  br i1 %cmp2, label %if.then3, label %if.end4
1558
1559if.then3:                                         ; preds = %if.else
1560  br label %if.end4
1561
1562if.end4:                                          ; preds = %if.else, %if.then3, %if.then
1563  %y.0 = phi ptr [ null, %if.then ], [ %x, %if.then3 ], [ null, %if.else ]
1564  %call5 = call i32 (ptr, ...) @printf(ptr @.str, ptr %y.0)
1565  ret void
1566}
1567
1568; test11a: Addr-of struct element. (GEP followed by store).
1569;          no ssp attribute
1570; Requires no protector.
1571define void @test11a() {
1572entry:
1573; LINUX-I386-LABEL: test11a:
1574; LINUX-I386-NOT: calll __stack_chk_fail
1575; LINUX-I386: .cfi_endproc
1576
1577; LINUX-X64-LABEL: test11a:
1578; LINUX-X64-NOT: callq __stack_chk_fail
1579; LINUX-X64: .cfi_endproc
1580
1581; LINUX-KERNEL-X64-LABEL: test11a:
1582; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
1583; LINUX-KERNEL-X64: .cfi_endproc
1584
1585; DARWIN-X64-LABEL: test11a:
1586; DARWIN-X64-NOT: callq ___stack_chk_fail
1587; DARWIN-X64: .cfi_endproc
1588
1589; MSVC-I386-LABEL: test11a:
1590; MSVC-I386-NOT: calll @__security_check_cookie@4
1591; MSVC-I386: retl
1592  %c = alloca %struct.pair, align 4
1593  %b = alloca ptr, align 8
1594  %y = getelementptr inbounds %struct.pair, ptr %c, i32 0, i32 1
1595  store ptr %y, ptr %b, align 8
1596  %0 = load ptr, ptr %b, align 8
1597  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %0)
1598  ret void
1599}
1600
1601; test11b: Addr-of struct element. (GEP followed by store).
1602;          ssp attribute
1603; Requires no protector.
1604; Function Attrs: ssp
1605define void @test11b() #0 {
1606entry:
1607; LINUX-I386-LABEL: test11b:
1608; LINUX-I386-NOT: calll __stack_chk_fail
1609; LINUX-I386: .cfi_endproc
1610
1611; LINUX-X64-LABEL: test11b:
1612; LINUX-X64-NOT: callq __stack_chk_fail
1613; LINUX-X64: .cfi_endproc
1614
1615; LINUX-KERNEL-X64-LABEL: test11b:
1616; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
1617; LINUX-KERNEL-X64: .cfi_endproc
1618
1619; DARWIN-X64-LABEL: test11b:
1620; DARWIN-X64-NOT: callq ___stack_chk_fail
1621; DARWIN-X64: .cfi_endproc
1622
1623; MSVC-I386-LABEL: test11b:
1624; MSVC-I386-NOT: calll @__security_check_cookie@4
1625; MSVC-I386: retl
1626  %c = alloca %struct.pair, align 4
1627  %b = alloca ptr, align 8
1628  %y = getelementptr inbounds %struct.pair, ptr %c, i32 0, i32 1
1629  store ptr %y, ptr %b, align 8
1630  %0 = load ptr, ptr %b, align 8
1631  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %0)
1632  ret void
1633}
1634
1635; test11c: Addr-of struct element. (GEP followed by store).
1636;          sspstrong attribute
1637; Requires protector.
1638; Function Attrs: sspstrong
1639define void @test11c() #1 {
1640entry:
1641; LINUX-I386-LABEL: test11c:
1642; LINUX-I386: mov{{l|q}} %gs:
1643; LINUX-I386: calll __stack_chk_fail
1644
1645; LINUX-X64-LABEL: test11c:
1646; LINUX-X64: mov{{l|q}} %fs:
1647; LINUX-X64: callq __stack_chk_fail
1648
1649; LINUX-KERNEL-X64-LABEL: test11c:
1650; LINUX-KERNEL-X64: mov{{l|q}} %gs:
1651; LINUX-KERNEL-X64: callq __stack_chk_fail
1652
1653; DARWIN-X64-LABEL: test11c:
1654; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
1655; DARWIN-X64: callq ___stack_chk_fail
1656
1657; MSVC-I386-LABEL: test11c:
1658; MSVC-I386: movl ___security_cookie,
1659; MSVC-I386: calll @__security_check_cookie@4
1660  %c = alloca %struct.pair, align 4
1661  %b = alloca ptr, align 8
1662  %y = getelementptr inbounds %struct.pair, ptr %c, i32 0, i32 1
1663  store ptr %y, ptr %b, align 8
1664  %0 = load ptr, ptr %b, align 8
1665  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %0)
1666  ret void
1667}
1668
1669; test11d: Addr-of struct element. (GEP followed by store).
1670;          sspreq attribute
1671; Requires protector.
1672; Function Attrs: sspreq
1673define void @test11d() #2 {
1674entry:
1675; LINUX-I386-LABEL: test11d:
1676; LINUX-I386: mov{{l|q}} %gs:
1677; LINUX-I386: calll __stack_chk_fail
1678
1679; LINUX-X64-LABEL: test11d:
1680; LINUX-X64: mov{{l|q}} %fs:
1681; LINUX-X64: callq __stack_chk_fail
1682
1683; LINUX-KERNEL-X64-LABEL: test11d:
1684; LINUX-KERNEL-X64: mov{{l|q}} %gs:
1685; LINUX-KERNEL-X64: callq __stack_chk_fail
1686
1687; DARWIN-X64-LABEL: test11d:
1688; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
1689; DARWIN-X64: callq ___stack_chk_fail
1690
1691; MSVC-I386-LABEL: test11d:
1692; MSVC-I386: movl ___security_cookie,
1693; MSVC-I386: calll @__security_check_cookie@4
1694  %c = alloca %struct.pair, align 4
1695  %b = alloca ptr, align 8
1696  %y = getelementptr inbounds %struct.pair, ptr %c, i32 0, i32 1
1697  store ptr %y, ptr %b, align 8
1698  %0 = load ptr, ptr %b, align 8
1699  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %0)
1700  ret void
1701}
1702
1703; test12a: Addr-of struct element, GEP followed by ptrtoint.
1704;          no ssp attribute
1705; Requires no protector.
1706define void @test12a() {
1707entry:
1708; LINUX-I386-LABEL: test12a:
1709; LINUX-I386-NOT: calll __stack_chk_fail
1710; LINUX-I386: .cfi_endproc
1711
1712; LINUX-X64-LABEL: test12a:
1713; LINUX-X64-NOT: callq __stack_chk_fail
1714; LINUX-X64: .cfi_endproc
1715
1716; LINUX-KERNEL-X64-LABEL: test12a:
1717; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
1718; LINUX-KERNEL-X64: .cfi_endproc
1719
1720; DARWIN-X64-LABEL: test12a:
1721; DARWIN-X64-NOT: callq ___stack_chk_fail
1722; DARWIN-X64: .cfi_endproc
1723
1724; MSVC-I386-LABEL: test12a:
1725; MSVC-I386-NOT: calll @__security_check_cookie@4
1726; MSVC-I386: retl
1727  %c = alloca %struct.pair, align 4
1728  %b = alloca ptr, align 8
1729  %y = getelementptr inbounds %struct.pair, ptr %c, i32 0, i32 1
1730  %0 = ptrtoint ptr %y to i64
1731  %call = call i32 (ptr, ...) @printf(ptr @.str, i64 %0)
1732  ret void
1733}
1734
1735; test12b: Addr-of struct element, GEP followed by ptrtoint.
1736;          ssp attribute
1737; Requires no protector.
1738; Function Attrs: ssp
1739define void @test12b() #0 {
1740entry:
1741; LINUX-I386-LABEL: test12b:
1742; LINUX-I386-NOT: calll __stack_chk_fail
1743; LINUX-I386: .cfi_endproc
1744
1745; LINUX-X64-LABEL: test12b:
1746; LINUX-X64-NOT: callq __stack_chk_fail
1747; LINUX-X64: .cfi_endproc
1748
1749; LINUX-KERNEL-X64-LABEL: test12b:
1750; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
1751; LINUX-KERNEL-X64: .cfi_endproc
1752
1753; DARWIN-X64-LABEL: test12b:
1754; DARWIN-X64-NOT: callq ___stack_chk_fail
1755; DARWIN-X64: .cfi_endproc
1756
1757; MSVC-I386-LABEL: test12b:
1758; MSVC-I386-NOT: calll @__security_check_cookie@4
1759; MSVC-I386: retl
1760  %c = alloca %struct.pair, align 4
1761  %b = alloca ptr, align 8
1762  %y = getelementptr inbounds %struct.pair, ptr %c, i32 0, i32 1
1763  %0 = ptrtoint ptr %y to i64
1764  %call = call i32 (ptr, ...) @printf(ptr @.str, i64 %0)
1765  ret void
1766}
1767
1768; test12c: Addr-of struct element, GEP followed by ptrtoint.
1769;          sspstrong attribute
1770; Function Attrs: sspstrong
1771define void @test12c() #1 {
1772entry:
1773; LINUX-I386-LABEL: test12c:
1774; LINUX-I386: mov{{l|q}} %gs:
1775; LINUX-I386: calll __stack_chk_fail
1776
1777; LINUX-X64-LABEL: test12c:
1778; LINUX-X64: mov{{l|q}} %fs:
1779; LINUX-X64: callq __stack_chk_fail
1780
1781; LINUX-KERNEL-X64-LABEL: test12c:
1782; LINUX-KERNEL-X64: mov{{l|q}} %gs:
1783; LINUX-KERNEL-X64: callq __stack_chk_fail
1784
1785; DARWIN-X64-LABEL: test12c:
1786; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
1787; DARWIN-X64: callq ___stack_chk_fail
1788
1789; MSVC-I386-LABEL: test12c:
1790; MSVC-I386: movl ___security_cookie,
1791; MSVC-I386: calll @__security_check_cookie@4
1792  %c = alloca %struct.pair, align 4
1793  %b = alloca ptr, align 8
1794  %y = getelementptr inbounds %struct.pair, ptr %c, i32 0, i32 1
1795  %0 = ptrtoint ptr %y to i64
1796  %call = call i32 (ptr, ...) @printf(ptr @.str, i64 %0)
1797  ret void
1798}
1799
1800; test12d: Addr-of struct element, GEP followed by ptrtoint.
1801;          sspreq attribute
1802; Requires protector.
1803; Function Attrs: sspreq
1804define void @test12d() #2 {
1805entry:
1806; LINUX-I386-LABEL: test12d:
1807; LINUX-I386: mov{{l|q}} %gs:
1808; LINUX-I386: calll __stack_chk_fail
1809
1810; LINUX-X64-LABEL: test12d:
1811; LINUX-X64: mov{{l|q}} %fs:
1812; LINUX-X64: callq __stack_chk_fail
1813
1814; LINUX-KERNEL-X64-LABEL: test12d:
1815; LINUX-KERNEL-X64: mov{{l|q}} %gs:
1816; LINUX-KERNEL-X64: callq __stack_chk_fail
1817
1818; DARWIN-X64-LABEL: test12d:
1819; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
1820; DARWIN-X64: callq ___stack_chk_fail
1821
1822; MSVC-I386-LABEL: test12d:
1823; MSVC-I386: movl ___security_cookie,
1824; MSVC-I386: calll @__security_check_cookie@4
1825  %c = alloca %struct.pair, align 4
1826  %b = alloca ptr, align 8
1827  %y = getelementptr inbounds %struct.pair, ptr %c, i32 0, i32 1
1828  %0 = ptrtoint ptr %y to i64
1829  %call = call i32 (ptr, ...) @printf(ptr @.str, i64 %0)
1830  ret void
1831}
1832
1833; test13a: Addr-of struct element, GEP followed by callinst.
1834;          no ssp attribute
1835; Requires no protector.
1836define void @test13a() {
1837entry:
1838; LINUX-I386-LABEL: test13a:
1839; LINUX-I386-NOT: calll __stack_chk_fail
1840; LINUX-I386: .cfi_endproc
1841
1842; LINUX-X64-LABEL: test13a:
1843; LINUX-X64-NOT: callq __stack_chk_fail
1844; LINUX-X64: .cfi_endproc
1845
1846; LINUX-KERNEL-X64-LABEL: test13a:
1847; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
1848; LINUX-KERNEL-X64: .cfi_endproc
1849
1850; DARWIN-X64-LABEL: test13a:
1851; DARWIN-X64-NOT: callq ___stack_chk_fail
1852; DARWIN-X64: .cfi_endproc
1853
1854; MSVC-I386-LABEL: test13a:
1855; MSVC-I386-NOT: calll @__security_check_cookie@4
1856; MSVC-I386: retl
1857  %c = alloca %struct.pair, align 4
1858  %y = getelementptr inbounds %struct.pair, ptr %c, i64 0, i32 1
1859  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %y)
1860  ret void
1861}
1862
1863; test13b: Addr-of struct element, GEP followed by callinst.
1864;          ssp attribute
1865; Requires no protector.
1866; Function Attrs: ssp
1867define void @test13b() #0 {
1868entry:
1869; LINUX-I386-LABEL: test13b:
1870; LINUX-I386-NOT: calll __stack_chk_fail
1871; LINUX-I386: .cfi_endproc
1872
1873; LINUX-X64-LABEL: test13b:
1874; LINUX-X64-NOT: callq __stack_chk_fail
1875; LINUX-X64: .cfi_endproc
1876
1877; LINUX-KERNEL-X64-LABEL: test13b:
1878; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
1879; LINUX-KERNEL-X64: .cfi_endproc
1880
1881; DARWIN-X64-LABEL: test13b:
1882; DARWIN-X64-NOT: callq ___stack_chk_fail
1883; DARWIN-X64: .cfi_endproc
1884
1885; MSVC-I386-LABEL: test13b:
1886; MSVC-I386-NOT: calll @__security_check_cookie@4
1887; MSVC-I386: retl
1888  %c = alloca %struct.pair, align 4
1889  %y = getelementptr inbounds %struct.pair, ptr %c, i64 0, i32 1
1890  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %y)
1891  ret void
1892}
1893
1894; test13c: Addr-of struct element, GEP followed by callinst.
1895;          sspstrong attribute
1896; Requires protector.
1897; Function Attrs: sspstrong
1898define void @test13c() #1 {
1899entry:
1900; LINUX-I386-LABEL: test13c:
1901; LINUX-I386: mov{{l|q}} %gs:
1902; LINUX-I386: calll __stack_chk_fail
1903
1904; LINUX-X64-LABEL: test13c:
1905; LINUX-X64: mov{{l|q}} %fs:
1906; LINUX-X64: callq __stack_chk_fail
1907
1908; LINUX-KERNEL-X64-LABEL: test13c:
1909; LINUX-KERNEL-X64: mov{{l|q}} %gs:
1910; LINUX-KERNEL-X64: callq __stack_chk_fail
1911
1912; DARWIN-X64-LABEL: test13c:
1913; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
1914; DARWIN-X64: callq ___stack_chk_fail
1915
1916; MSVC-I386-LABEL: test13c:
1917; MSVC-I386: movl ___security_cookie,
1918; MSVC-I386: calll @__security_check_cookie@4
1919  %c = alloca %struct.pair, align 4
1920  %y = getelementptr inbounds %struct.pair, ptr %c, i64 0, i32 1
1921  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %y)
1922  ret void
1923}
1924
1925; test13d: Addr-of struct element, GEP followed by callinst.
1926;          sspreq attribute
1927; Requires protector.
1928; Function Attrs: sspreq
1929define void @test13d() #2 {
1930entry:
1931; LINUX-I386-LABEL: test13d:
1932; LINUX-I386: mov{{l|q}} %gs:
1933; LINUX-I386: calll __stack_chk_fail
1934
1935; LINUX-X64-LABEL: test13d:
1936; LINUX-X64: mov{{l|q}} %fs:
1937; LINUX-X64: callq __stack_chk_fail
1938
1939; LINUX-KERNEL-X64-LABEL: test13d:
1940; LINUX-KERNEL-X64: mov{{l|q}} %gs:
1941; LINUX-KERNEL-X64: callq __stack_chk_fail
1942
1943; DARWIN-X64-LABEL: test13d:
1944; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
1945; DARWIN-X64: callq ___stack_chk_fail
1946
1947; MSVC-I386-LABEL: test13d:
1948; MSVC-I386: movl ___security_cookie,
1949; MSVC-I386: calll @__security_check_cookie@4
1950  %c = alloca %struct.pair, align 4
1951  %y = getelementptr inbounds %struct.pair, ptr %c, i64 0, i32 1
1952  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %y)
1953  ret void
1954}
1955
1956; test14a: Addr-of a local, optimized into a GEP (e.g., &a - 12)
1957;          no ssp attribute
1958; Requires no protector.
1959define void @test14a() {
1960entry:
1961; LINUX-I386-LABEL: test14a:
1962; LINUX-I386-NOT: calll __stack_chk_fail
1963; LINUX-I386: .cfi_endproc
1964
1965; LINUX-X64-LABEL: test14a:
1966; LINUX-X64-NOT: callq __stack_chk_fail
1967; LINUX-X64: .cfi_endproc
1968
1969; LINUX-KERNEL-X64-LABEL: test14a:
1970; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
1971; LINUX-KERNEL-X64: .cfi_endproc
1972
1973; DARWIN-X64-LABEL: test14a:
1974; DARWIN-X64-NOT: callq ___stack_chk_fail
1975; DARWIN-X64: .cfi_endproc
1976
1977; MSVC-I386-LABEL: test14a:
1978; MSVC-I386-NOT: calll @__security_check_cookie@4
1979; MSVC-I386: retl
1980  %a = alloca i32, align 4
1981  %add.ptr5 = getelementptr inbounds i32, ptr %a, i64 -12
1982  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %add.ptr5)
1983  ret void
1984}
1985
1986; test14b: Addr-of a local, optimized into a GEP (e.g., &a - 12)
1987;          ssp attribute
1988; Requires no protector.
1989; Function Attrs: ssp
1990define void @test14b() #0 {
1991entry:
1992; LINUX-I386-LABEL: test14b:
1993; LINUX-I386-NOT: calll __stack_chk_fail
1994; LINUX-I386: .cfi_endproc
1995
1996; LINUX-X64-LABEL: test14b:
1997; LINUX-X64-NOT: callq __stack_chk_fail
1998; LINUX-X64: .cfi_endproc
1999
2000; LINUX-KERNEL-X64-LABEL: test14b:
2001; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
2002; LINUX-KERNEL-X64: .cfi_endproc
2003
2004; DARWIN-X64-LABEL: test14b:
2005; DARWIN-X64-NOT: callq ___stack_chk_fail
2006; DARWIN-X64: .cfi_endproc
2007
2008; MSVC-I386-LABEL: test14b:
2009; MSVC-I386-NOT: calll @__security_check_cookie@4
2010; MSVC-I386: retl
2011  %a = alloca i32, align 4
2012  %add.ptr5 = getelementptr inbounds i32, ptr %a, i64 -12
2013  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %add.ptr5)
2014  ret void
2015}
2016
2017; test14c: Addr-of a local, optimized into a GEP (e.g., &a - 12)
2018;          sspstrong attribute
2019; Requires protector.
2020; Function Attrs: sspstrong
2021define void @test14c() #1 {
2022entry:
2023; LINUX-I386-LABEL: test14c:
2024; LINUX-I386: mov{{l|q}} %gs:
2025; LINUX-I386: calll __stack_chk_fail
2026
2027; LINUX-X64-LABEL: test14c:
2028; LINUX-X64: mov{{l|q}} %fs:
2029; LINUX-X64: callq __stack_chk_fail
2030
2031; LINUX-KERNEL-X64-LABEL: test14c:
2032; LINUX-KERNEL-X64: mov{{l|q}} %gs:
2033; LINUX-KERNEL-X64: callq __stack_chk_fail
2034
2035; DARWIN-X64-LABEL: test14c:
2036; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
2037; DARWIN-X64: callq ___stack_chk_fail
2038
2039; MSVC-I386-LABEL: test14c:
2040; MSVC-I386: movl ___security_cookie,
2041; MSVC-I386: calll @__security_check_cookie@4
2042  %a = alloca i32, align 4
2043  %add.ptr5 = getelementptr inbounds i32, ptr %a, i64 -12
2044  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %add.ptr5)
2045  ret void
2046}
2047
2048; test14d: Addr-of a local, optimized into a GEP (e.g., &a - 12)
2049;          sspreq  attribute
2050; Requires protector.
2051; Function Attrs: sspreq
2052define void @test14d() #2 {
2053entry:
2054; LINUX-I386-LABEL: test14d:
2055; LINUX-I386: mov{{l|q}} %gs:
2056; LINUX-I386: calll __stack_chk_fail
2057
2058; LINUX-X64-LABEL: test14d:
2059; LINUX-X64: mov{{l|q}} %fs:
2060; LINUX-X64: callq __stack_chk_fail
2061
2062; LINUX-KERNEL-X64-LABEL: test14d:
2063; LINUX-KERNEL-X64: mov{{l|q}} %gs:
2064; LINUX-KERNEL-X64: callq __stack_chk_fail
2065
2066; DARWIN-X64-LABEL: test14d:
2067; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
2068; DARWIN-X64: callq ___stack_chk_fail
2069
2070; MSVC-I386-LABEL: test14d:
2071; MSVC-I386: movl ___security_cookie,
2072; MSVC-I386: calll @__security_check_cookie@4
2073  %a = alloca i32, align 4
2074  %add.ptr5 = getelementptr inbounds i32, ptr %a, i64 -12
2075  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %add.ptr5)
2076  ret void
2077}
2078
2079; test15a: Addr-of a local cast to a ptr of a different type
2080;           (e.g., int a; ... ; ptr b = &a;)
2081;          no ssp attribute
2082; Requires no protector.
2083define void @test15a() {
2084entry:
2085; LINUX-I386-LABEL: test15a:
2086; LINUX-I386-NOT: calll __stack_chk_fail
2087; LINUX-I386: .cfi_endproc
2088
2089; LINUX-X64-LABEL: test15a:
2090; LINUX-X64-NOT: callq __stack_chk_fail
2091; LINUX-X64: .cfi_endproc
2092
2093; LINUX-KERNEL-X64-LABEL: test15a:
2094; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
2095; LINUX-KERNEL-X64: .cfi_endproc
2096
2097; DARWIN-X64-LABEL: test15a:
2098; DARWIN-X64-NOT: callq ___stack_chk_fail
2099; DARWIN-X64: .cfi_endproc
2100
2101; MSVC-I386-LABEL: test15a:
2102; MSVC-I386-NOT: calll @__security_check_cookie@4
2103; MSVC-I386: retl
2104  %a = alloca i32, align 4
2105  %b = alloca ptr, align 8
2106  store i32 0, ptr %a, align 4
2107  store ptr %a, ptr %b, align 8
2108  %0 = load ptr, ptr %b, align 8
2109  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %0)
2110  ret void
2111}
2112
2113; test15b: Addr-of a local cast to a ptr of a different type
2114;           (e.g., int a; ... ; ptr b = &a;)
2115;          ssp attribute
2116; Requires no protector.
2117; Function Attrs: ssp
2118define void @test15b() #0 {
2119entry:
2120; LINUX-I386-LABEL: test15b:
2121; LINUX-I386-NOT: calll __stack_chk_fail
2122; LINUX-I386: .cfi_endproc
2123
2124; LINUX-X64-LABEL: test15b:
2125; LINUX-X64-NOT: callq __stack_chk_fail
2126; LINUX-X64: .cfi_endproc
2127
2128; LINUX-KERNEL-X64-LABEL: test15b:
2129; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
2130; LINUX-KERNEL-X64: .cfi_endproc
2131
2132; DARWIN-X64-LABEL: test15b:
2133; DARWIN-X64-NOT: callq ___stack_chk_fail
2134; DARWIN-X64: .cfi_endproc
2135
2136; MSVC-I386-LABEL: test15b:
2137; MSVC-I386-NOT: calll @__security_check_cookie@4
2138; MSVC-I386: retl
2139  %a = alloca i32, align 4
2140  %b = alloca ptr, align 8
2141  store i32 0, ptr %a, align 4
2142  store ptr %a, ptr %b, align 8
2143  %0 = load ptr, ptr %b, align 8
2144  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %0)
2145  ret void
2146}
2147
2148; test15c: Addr-of a local cast to a ptr of a different type
2149;           (e.g., int a; ... ; ptr b = &a;)
2150;          sspstrong attribute
2151; Requires protector.
2152; Function Attrs: sspstrong
2153define void @test15c() #1 {
2154entry:
2155; LINUX-I386-LABEL: test15c:
2156; LINUX-I386: mov{{l|q}} %gs:
2157; LINUX-I386: calll __stack_chk_fail
2158
2159; LINUX-X64-LABEL: test15c:
2160; LINUX-X64: mov{{l|q}} %fs:
2161; LINUX-X64: callq __stack_chk_fail
2162
2163; LINUX-KERNEL-X64-LABEL: test15c:
2164; LINUX-KERNEL-X64: mov{{l|q}} %gs:
2165; LINUX-KERNEL-X64: callq __stack_chk_fail
2166
2167; DARWIN-X64-LABEL: test15c:
2168; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
2169; DARWIN-X64: callq ___stack_chk_fail
2170
2171; MSVC-I386-LABEL: test15c:
2172; MSVC-I386: movl ___security_cookie,
2173; MSVC-I386: calll @__security_check_cookie@4
2174  %a = alloca i32, align 4
2175  %b = alloca ptr, align 8
2176  store i32 0, ptr %a, align 4
2177  store ptr %a, ptr %b, align 8
2178  %0 = load ptr, ptr %b, align 8
2179  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %0)
2180  ret void
2181}
2182
2183; test15d: Addr-of a local cast to a ptr of a different type
2184;           (e.g., int a; ... ; ptr b = &a;)
2185;          sspreq attribute
2186; Requires protector.
2187; Function Attrs: sspreq
2188define void @test15d() #2 {
2189entry:
2190; LINUX-I386-LABEL: test15d:
2191; LINUX-I386: mov{{l|q}} %gs:
2192; LINUX-I386: calll __stack_chk_fail
2193
2194; LINUX-X64-LABEL: test15d:
2195; LINUX-X64: mov{{l|q}} %fs:
2196; LINUX-X64: callq __stack_chk_fail
2197
2198; LINUX-KERNEL-X64-LABEL: test15d:
2199; LINUX-KERNEL-X64: mov{{l|q}} %gs:
2200; LINUX-KERNEL-X64: callq __stack_chk_fail
2201
2202; DARWIN-X64-LABEL: test15d:
2203; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
2204; DARWIN-X64: callq ___stack_chk_fail
2205
2206; MSVC-I386-LABEL: test15d:
2207; MSVC-I386: movl ___security_cookie,
2208; MSVC-I386: calll @__security_check_cookie@4
2209  %a = alloca i32, align 4
2210  %b = alloca ptr, align 8
2211  store i32 0, ptr %a, align 4
2212  store ptr %a, ptr %b, align 8
2213  %0 = load ptr, ptr %b, align 8
2214  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %0)
2215  ret void
2216}
2217
2218; test16a: Addr-of a local cast to a ptr of a different type (optimized)
2219;           (e.g., int a; ... ; ptr b = &a;)
2220;          no ssp attribute
2221; Requires no protector.
2222define void @test16a() {
2223entry:
2224; LINUX-I386-LABEL: test16a:
2225; LINUX-I386-NOT: calll __stack_chk_fail
2226; LINUX-I386: .cfi_endproc
2227
2228; LINUX-X64-LABEL: test16a:
2229; LINUX-X64-NOT: callq __stack_chk_fail
2230; LINUX-X64: .cfi_endproc
2231
2232; LINUX-KERNEL-X64-LABEL: test16a:
2233; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
2234; LINUX-KERNEL-X64: .cfi_endproc
2235
2236; DARWIN-X64-LABEL: test16a:
2237; DARWIN-X64-NOT: callq ___stack_chk_fail
2238; DARWIN-X64: .cfi_endproc
2239
2240; MSVC-I386-LABEL: test16a:
2241; MSVC-I386-NOT: calll @__security_check_cookie@4
2242; MSVC-I386: retl
2243  %a = alloca i32, align 4
2244  store i32 0, ptr %a, align 4
2245  call void @funfloat(ptr %a)
2246  ret void
2247}
2248
2249; test16b: Addr-of a local cast to a ptr of a different type (optimized)
2250;           (e.g., int a; ... ; ptr b = &a;)
2251;          ssp attribute
2252; Requires no protector.
2253; Function Attrs: ssp
2254define void @test16b() #0 {
2255entry:
2256; LINUX-I386-LABEL: test16b:
2257; LINUX-I386-NOT: calll __stack_chk_fail
2258; LINUX-I386: .cfi_endproc
2259
2260; LINUX-X64-LABEL: test16b:
2261; LINUX-X64-NOT: callq __stack_chk_fail
2262; LINUX-X64: .cfi_endproc
2263
2264; LINUX-KERNEL-X64-LABEL: test16b:
2265; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
2266; LINUX-KERNEL-X64: .cfi_endproc
2267
2268; DARWIN-X64-LABEL: test16b:
2269; DARWIN-X64-NOT: callq ___stack_chk_fail
2270; DARWIN-X64: .cfi_endproc
2271
2272; MSVC-I386-LABEL: test16b:
2273; MSVC-I386-NOT: calll @__security_check_cookie@4
2274; MSVC-I386: retl
2275  %a = alloca i32, align 4
2276  store i32 0, ptr %a, align 4
2277  call void @funfloat(ptr %a)
2278  ret void
2279}
2280
2281; test16c: Addr-of a local cast to a ptr of a different type (optimized)
2282;           (e.g., int a; ... ; ptr b = &a;)
2283;          sspstrong attribute
2284; Requires protector.
2285; Function Attrs: sspstrong
2286define void @test16c() #1 {
2287entry:
2288; LINUX-I386-LABEL: test16c:
2289; LINUX-I386: mov{{l|q}} %gs:
2290; LINUX-I386: calll __stack_chk_fail
2291
2292; LINUX-X64-LABEL: test16c:
2293; LINUX-X64: mov{{l|q}} %fs:
2294; LINUX-X64: callq __stack_chk_fail
2295
2296; LINUX-KERNEL-X64-LABEL: test16c:
2297; LINUX-KERNEL-X64: mov{{l|q}} %gs:
2298; LINUX-KERNEL-X64: callq __stack_chk_fail
2299
2300; DARWIN-X64-LABEL: test16c:
2301; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
2302; DARWIN-X64: callq ___stack_chk_fail
2303
2304; MSVC-I386-LABEL: test16c:
2305; MSVC-I386: movl ___security_cookie,
2306; MSVC-I386: calll @__security_check_cookie@4
2307  %a = alloca i32, align 4
2308  store i32 0, ptr %a, align 4
2309  call void @funfloat(ptr %a)
2310  ret void
2311}
2312
2313; test16d: Addr-of a local cast to a ptr of a different type (optimized)
2314;           (e.g., int a; ... ; ptr b = &a;)
2315;          sspreq attribute
2316; Requires protector.
2317; Function Attrs: sspreq
2318define void @test16d() #2 {
2319entry:
2320; LINUX-I386-LABEL: test16d:
2321; LINUX-I386: mov{{l|q}} %gs:
2322; LINUX-I386: calll __stack_chk_fail
2323
2324; LINUX-X64-LABEL: test16d:
2325; LINUX-X64: mov{{l|q}} %fs:
2326; LINUX-X64: callq __stack_chk_fail
2327
2328; LINUX-KERNEL-X64-LABEL: test16d:
2329; LINUX-KERNEL-X64: mov{{l|q}} %gs:
2330; LINUX-KERNEL-X64: callq __stack_chk_fail
2331
2332; DARWIN-X64-LABEL: test16d:
2333; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
2334; DARWIN-X64: callq ___stack_chk_fail
2335
2336; MSVC-I386-LABEL: test16d:
2337; MSVC-I386: movl ___security_cookie,
2338; MSVC-I386: calll @__security_check_cookie@4
2339  %a = alloca i32, align 4
2340  store i32 0, ptr %a, align 4
2341  call void @funfloat(ptr %a)
2342  ret void
2343}
2344
2345; test17a: Addr-of a vector nested in a struct
2346;          no ssp attribute
2347; Requires no protector.
2348define void @test17a() {
2349entry:
2350; LINUX-I386-LABEL: test17a:
2351; LINUX-I386-NOT: calll __stack_chk_fail
2352; LINUX-I386: .cfi_endproc
2353
2354; LINUX-X64-LABEL: test17a:
2355; LINUX-X64-NOT: callq __stack_chk_fail
2356; LINUX-X64: .cfi_endproc
2357
2358; LINUX-KERNEL-X64-LABEL: test17a:
2359; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
2360; LINUX-KERNEL-X64: .cfi_endproc
2361
2362; DARWIN-X64-LABEL: test17a:
2363; DARWIN-X64-NOT: callq ___stack_chk_fail
2364; DARWIN-X64: .cfi_endproc
2365
2366; MSVC-I386-LABEL: test17a:
2367; MSVC-I386-NOT: calll @__security_check_cookie@4
2368; MSVC-I386: retl
2369  %c = alloca %struct.vec, align 16
2370  %add.ptr = getelementptr inbounds <4 x i32>, ptr %c, i64 -12
2371  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %add.ptr)
2372  ret void
2373}
2374
2375; test17b: Addr-of a vector nested in a struct
2376;          ssp attribute
2377; Requires no protector.
2378; Function Attrs: ssp
2379define void @test17b() #0 {
2380entry:
2381; LINUX-I386-LABEL: test17b:
2382; LINUX-I386-NOT: calll __stack_chk_fail
2383; LINUX-I386: .cfi_endproc
2384
2385; LINUX-X64-LABEL: test17b:
2386; LINUX-X64-NOT: callq __stack_chk_fail
2387; LINUX-X64: .cfi_endproc
2388
2389; LINUX-KERNEL-X64-LABEL: test17b:
2390; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
2391; LINUX-KERNEL-X64: .cfi_endproc
2392
2393; DARWIN-X64-LABEL: test17b:
2394; DARWIN-X64-NOT: callq ___stack_chk_fail
2395; DARWIN-X64: .cfi_endproc
2396
2397; MSVC-I386-LABEL: test17b:
2398; MSVC-I386-NOT: calll @__security_check_cookie@4
2399; MSVC-I386: retl
2400  %c = alloca %struct.vec, align 16
2401  %add.ptr = getelementptr inbounds <4 x i32>, ptr %c, i64 -12
2402  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %add.ptr)
2403  ret void
2404}
2405
2406; test17c: Addr-of a vector nested in a struct
2407;          sspstrong attribute
2408; Requires protector.
2409; Function Attrs: sspstrong
2410define void @test17c() #1 {
2411entry:
2412; LINUX-I386-LABEL: test17c:
2413; LINUX-I386: mov{{l|q}} %gs:
2414; LINUX-I386: calll __stack_chk_fail
2415
2416; LINUX-X64-LABEL: test17c:
2417; LINUX-X64: mov{{l|q}} %fs:
2418; LINUX-X64: callq __stack_chk_fail
2419
2420; LINUX-KERNEL-X64-LABEL: test17c:
2421; LINUX-KERNEL-X64: mov{{l|q}} %gs:
2422; LINUX-KERNEL-X64: callq __stack_chk_fail
2423
2424; DARWIN-X64-LABEL: test17c:
2425; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
2426; DARWIN-X64: callq ___stack_chk_fail
2427
2428; MSVC-I386-LABEL: test17c:
2429; MSVC-I386: movl ___security_cookie,
2430; MSVC-I386: calll @__security_check_cookie@4
2431  %c = alloca %struct.vec, align 16
2432  %add.ptr = getelementptr inbounds <4 x i32>, ptr %c, i64 -12
2433  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %add.ptr)
2434  ret void
2435}
2436
2437; test17d: Addr-of a vector nested in a struct
2438;          sspreq attribute
2439; Requires protector.
2440; Function Attrs: sspreq
2441define void @test17d() #2 {
2442entry:
2443; LINUX-I386-LABEL: test17d:
2444; LINUX-I386: mov{{l|q}} %gs:
2445; LINUX-I386: calll __stack_chk_fail
2446
2447; LINUX-X64-LABEL: test17d:
2448; LINUX-X64: mov{{l|q}} %fs:
2449; LINUX-X64: callq __stack_chk_fail
2450
2451; LINUX-KERNEL-X64-LABEL: test17d:
2452; LINUX-KERNEL-X64: mov{{l|q}} %gs:
2453; LINUX-KERNEL-X64: callq __stack_chk_fail
2454
2455; DARWIN-X64-LABEL: test17d:
2456; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
2457; DARWIN-X64: callq ___stack_chk_fail
2458
2459; MSVC-I386-LABEL: test17d:
2460; MSVC-I386: movl ___security_cookie,
2461; MSVC-I386: calll @__security_check_cookie@4
2462  %c = alloca %struct.vec, align 16
2463  %add.ptr = getelementptr inbounds <4 x i32>, ptr %c, i64 -12
2464  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %add.ptr)
2465  ret void
2466}
2467
2468; test18a: Addr-of a variable passed into an invoke instruction.
2469;          no ssp attribute
2470; Requires no protector.
2471define i32 @test18a() personality ptr @__gxx_personality_v0 {
2472entry:
2473; LINUX-I386-LABEL: test18a:
2474; LINUX-I386-NOT: calll __stack_chk_fail
2475; LINUX-I386: .cfi_endproc
2476
2477; LINUX-X64-LABEL: test18a:
2478; LINUX-X64-NOT: callq __stack_chk_fail
2479; LINUX-X64: .cfi_endproc
2480
2481; LINUX-KERNEL-X64-LABEL: test18a:
2482; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
2483; LINUX-KERNEL-X64: .cfi_endproc
2484
2485; DARWIN-X64-LABEL: test18a:
2486; DARWIN-X64-NOT: callq ___stack_chk_fail
2487; DARWIN-X64: .cfi_endproc
2488
2489; MSVC-I386-LABEL: test18a:
2490; MSVC-I386-NOT: calll @__security_check_cookie@4
2491; MSVC-I386: retl
2492  %a = alloca i32, align 4
2493  %exn.slot = alloca ptr
2494  %ehselector.slot = alloca i32
2495  store i32 0, ptr %a, align 4
2496  invoke void @_Z3exceptPi(ptr %a)
2497          to label %invoke.cont unwind label %lpad
2498
2499invoke.cont:
2500  ret i32 0
2501
2502lpad:
2503  %0 = landingpad { ptr, i32 }
2504          catch ptr null
2505  ret i32 0
2506}
2507
2508; test18b: Addr-of a variable passed into an invoke instruction.
2509;          ssp attribute
2510; Requires no protector.
2511; Function Attrs: ssp
2512define i32 @test18b() #0 personality ptr @__gxx_personality_v0 {
2513entry:
2514; LINUX-I386-LABEL: test18b:
2515; LINUX-I386-NOT: calll __stack_chk_fail
2516; LINUX-I386: .cfi_endproc
2517
2518; LINUX-X64-LABEL: test18b:
2519; LINUX-X64-NOT: callq __stack_chk_fail
2520; LINUX-X64: .cfi_endproc
2521
2522; LINUX-KERNEL-X64-LABEL: test18b:
2523; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
2524; LINUX-KERNEL-X64: .cfi_endproc
2525
2526; DARWIN-X64-LABEL: test18b:
2527; DARWIN-X64-NOT: callq ___stack_chk_fail
2528; DARWIN-X64: .cfi_endproc
2529
2530; MSVC-I386-LABEL: test18b:
2531; MSVC-I386-NOT: calll @__security_check_cookie@4
2532; MSVC-I386: retl
2533  %a = alloca i32, align 4
2534  %exn.slot = alloca ptr
2535  %ehselector.slot = alloca i32
2536  store i32 0, ptr %a, align 4
2537  invoke void @_Z3exceptPi(ptr %a)
2538          to label %invoke.cont unwind label %lpad
2539
2540invoke.cont:
2541  ret i32 0
2542
2543lpad:
2544  %0 = landingpad { ptr, i32 }
2545          catch ptr null
2546  ret i32 0
2547}
2548
2549; test18c: Addr-of a variable passed into an invoke instruction.
2550;          sspstrong attribute
2551; Requires protector.
2552; Function Attrs: sspstrong
2553define i32 @test18c() #1 personality ptr @__gxx_personality_v0 {
2554entry:
2555; LINUX-I386-LABEL: test18c:
2556; LINUX-I386: mov{{l|q}} %gs:
2557; LINUX-I386: calll __stack_chk_fail
2558
2559; LINUX-X64-LABEL: test18c:
2560; LINUX-X64: mov{{l|q}} %fs:
2561; LINUX-X64: callq __stack_chk_fail
2562
2563; LINUX-KERNEL-X64-LABEL: test18c:
2564; LINUX-KERNEL-X64: mov{{l|q}} %gs:
2565; LINUX-KERNEL-X64: callq __stack_chk_fail
2566
2567; DARWIN-X64-LABEL: test18c:
2568; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
2569; DARWIN-X64: callq ___stack_chk_fail
2570
2571; MSVC-I386-LABEL: test18c:
2572; MSVC-I386: movl ___security_cookie,
2573; MSVC-I386: calll @__security_check_cookie@4
2574  %a = alloca i32, align 4
2575  %exn.slot = alloca ptr
2576  %ehselector.slot = alloca i32
2577  store i32 0, ptr %a, align 4
2578  invoke void @_Z3exceptPi(ptr %a)
2579          to label %invoke.cont unwind label %lpad
2580
2581invoke.cont:
2582  ret i32 0
2583
2584lpad:
2585  %0 = landingpad { ptr, i32 }
2586          catch ptr null
2587  ret i32 0
2588}
2589
2590; test18d: Addr-of a variable passed into an invoke instruction.
2591;          sspreq attribute
2592; Requires protector.
2593; Function Attrs: sspreq
2594define i32 @test18d() #2 personality ptr @__gxx_personality_v0 {
2595entry:
2596; LINUX-I386-LABEL: test18d:
2597; LINUX-I386: mov{{l|q}} %gs:
2598; LINUX-I386: calll __stack_chk_fail
2599
2600; LINUX-X64-LABEL: test18d:
2601; LINUX-X64: mov{{l|q}} %fs:
2602; LINUX-X64: callq __stack_chk_fail
2603
2604; LINUX-KERNEL-X64-LABEL: test18d:
2605; LINUX-KERNEL-X64: mov{{l|q}} %gs:
2606; LINUX-KERNEL-X64: callq __stack_chk_fail
2607
2608; DARWIN-X64-LABEL: test18d:
2609; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
2610; DARWIN-X64: callq ___stack_chk_fail
2611
2612; MSVC-I386-LABEL: test18d:
2613; MSVC-I386: movl ___security_cookie,
2614; MSVC-I386: calll @__security_check_cookie@4
2615  %a = alloca i32, align 4
2616  %exn.slot = alloca ptr
2617  %ehselector.slot = alloca i32
2618  store i32 0, ptr %a, align 4
2619  invoke void @_Z3exceptPi(ptr %a)
2620          to label %invoke.cont unwind label %lpad
2621
2622invoke.cont:
2623  ret i32 0
2624
2625lpad:
2626  %0 = landingpad { ptr, i32 }
2627          catch ptr null
2628  ret i32 0
2629}
2630; test19a: Addr-of a struct element passed into an invoke instruction.
2631;           (GEP followed by an invoke)
2632;          no ssp attribute
2633; Requires no protector.
2634define i32 @test19a() personality ptr @__gxx_personality_v0 {
2635entry:
2636; LINUX-I386-LABEL: test19a:
2637; LINUX-I386-NOT: calll __stack_chk_fail
2638; LINUX-I386: .cfi_endproc
2639
2640; LINUX-X64-LABEL: test19a:
2641; LINUX-X64-NOT: callq __stack_chk_fail
2642; LINUX-X64: .cfi_endproc
2643
2644; LINUX-KERNEL-X64-LABEL: test19a:
2645; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
2646; LINUX-KERNEL-X64: .cfi_endproc
2647
2648; DARWIN-X64-LABEL: test19a:
2649; DARWIN-X64-NOT: callq ___stack_chk_fail
2650; DARWIN-X64: .cfi_endproc
2651
2652; MSVC-I386-LABEL: test19a:
2653; MSVC-I386-NOT: calll @__security_check_cookie@4
2654; MSVC-I386: retl
2655  %c = alloca %struct.pair, align 4
2656  %exn.slot = alloca ptr
2657  %ehselector.slot = alloca i32
2658  store i32 0, ptr %c, align 4
2659  invoke void @_Z3exceptPi(ptr %c)
2660          to label %invoke.cont unwind label %lpad
2661
2662invoke.cont:
2663  ret i32 0
2664
2665lpad:
2666  %0 = landingpad { ptr, i32 }
2667          catch ptr null
2668  ret i32 0
2669}
2670
2671; test19b: Addr-of a struct element passed into an invoke instruction.
2672;           (GEP followed by an invoke)
2673;          ssp attribute
2674; Requires no protector.
2675; Function Attrs: ssp
2676define i32 @test19b() #0 personality ptr @__gxx_personality_v0 {
2677entry:
2678; LINUX-I386-LABEL: test19b:
2679; LINUX-I386-NOT: calll __stack_chk_fail
2680; LINUX-I386: .cfi_endproc
2681
2682; LINUX-X64-LABEL: test19b:
2683; LINUX-X64-NOT: callq __stack_chk_fail
2684; LINUX-X64: .cfi_endproc
2685
2686; LINUX-KERNEL-X64-LABEL: test19b:
2687; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
2688; LINUX-KERNEL-X64: .cfi_endproc
2689
2690; DARWIN-X64-LABEL: test19b:
2691; DARWIN-X64-NOT: callq ___stack_chk_fail
2692; DARWIN-X64: .cfi_endproc
2693
2694; MSVC-I386-LABEL: test19b:
2695; MSVC-I386-NOT: calll @__security_check_cookie@4
2696; MSVC-I386: retl
2697  %c = alloca %struct.pair, align 4
2698  %exn.slot = alloca ptr
2699  %ehselector.slot = alloca i32
2700  store i32 0, ptr %c, align 4
2701  invoke void @_Z3exceptPi(ptr %c)
2702          to label %invoke.cont unwind label %lpad
2703
2704invoke.cont:
2705  ret i32 0
2706
2707lpad:
2708  %0 = landingpad { ptr, i32 }
2709          catch ptr null
2710  ret i32 0
2711}
2712
2713; test19c: Addr-of a struct element passed into an invoke instruction.
2714;           (GEP followed by an invoke)
2715;          sspstrong attribute
2716; Requires protector.
2717; Function Attrs: sspstrong
2718define i32 @test19c() #1 personality ptr @__gxx_personality_v0 {
2719entry:
2720; LINUX-I386-LABEL: test19c:
2721; LINUX-I386: mov{{l|q}} %gs:
2722; LINUX-I386: calll __stack_chk_fail
2723
2724; LINUX-X64-LABEL: test19c:
2725; LINUX-X64: mov{{l|q}} %fs:
2726; LINUX-X64: callq __stack_chk_fail
2727
2728; LINUX-KERNEL-X64-LABEL: test19c:
2729; LINUX-KERNEL-X64: mov{{l|q}} %gs:
2730; LINUX-KERNEL-X64: callq __stack_chk_fail
2731
2732; DARWIN-X64-LABEL: test19c:
2733; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
2734; DARWIN-X64: callq ___stack_chk_fail
2735
2736; MSVC-I386-LABEL: test19c:
2737; MSVC-I386: movl ___security_cookie,
2738; MSVC-I386: calll @__security_check_cookie@4
2739  %c = alloca %struct.pair, align 4
2740  %exn.slot = alloca ptr
2741  %ehselector.slot = alloca i32
2742  store i32 0, ptr %c, align 4
2743  invoke void @_Z3exceptPi(ptr %c)
2744          to label %invoke.cont unwind label %lpad
2745
2746invoke.cont:
2747  ret i32 0
2748
2749lpad:
2750  %0 = landingpad { ptr, i32 }
2751          catch ptr null
2752  ret i32 0
2753}
2754
2755; test19d: Addr-of a struct element passed into an invoke instruction.
2756;           (GEP followed by an invoke)
2757;          sspreq attribute
2758; Requires protector.
2759; Function Attrs: sspreq
2760define i32 @test19d() #2 personality ptr @__gxx_personality_v0 {
2761entry:
2762; LINUX-I386-LABEL: test19d:
2763; LINUX-I386: mov{{l|q}} %gs:
2764; LINUX-I386: calll __stack_chk_fail
2765; LINUX-I386-NOT: calll __stack_chk_fail
2766
2767; LINUX-X64-LABEL: test19d:
2768; LINUX-X64: mov{{l|q}} %fs:
2769; LINUX-X64: callq __stack_chk_fail
2770; LINUX-X64-NOT: callq __stack_chk_fail
2771
2772; LINUX-KERNEL-X64-LABEL: test19d:
2773; LINUX-KERNEL-X64: mov{{l|q}} %gs:
2774; LINUX-KERNEL-X64: callq __stack_chk_fail
2775; LINUX-KERNEL-X64-NOT: callq ___stack_chk_fail
2776
2777; DARWIN-X64-LABEL: test19d:
2778; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
2779; DARWIN-X64: callq ___stack_chk_fail
2780; DARWIN-X64-NOT: callq ___stack_chk_fail
2781
2782; MSVC-I386-LABEL: test19d:
2783; MSVC-I386: movl ___security_cookie,
2784; MSVC-I386: calll @__security_check_cookie@4
2785
2786; MINGW-X64-LABEL: test19d:
2787; MINGW-X64: mov{{l|q}} .refptr.__stack_chk_guard
2788; MINGW-X64: callq __stack_chk_fail
2789
2790  %c = alloca %struct.pair, align 4
2791  %exn.slot = alloca ptr
2792  %ehselector.slot = alloca i32
2793  store i32 0, ptr %c, align 4
2794  invoke void @_Z3exceptPi(ptr %c)
2795          to label %invoke.cont unwind label %lpad
2796
2797invoke.cont:
2798  ret i32 0
2799
2800lpad:
2801  %0 = landingpad { ptr, i32 }
2802          catch ptr null
2803  ret i32 0
2804}
2805
2806; test20a: Addr-of a pointer
2807;          no ssp attribute
2808; Requires no protector.
2809define void @test20a() {
2810entry:
2811; LINUX-I386-LABEL: test20a:
2812; LINUX-I386-NOT: calll __stack_chk_fail
2813; LINUX-I386: .cfi_endproc
2814
2815; LINUX-X64-LABEL: test20a:
2816; LINUX-X64-NOT: callq __stack_chk_fail
2817; LINUX-X64: .cfi_endproc
2818
2819; LINUX-KERNEL-X64-LABEL: test20a:
2820; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
2821; LINUX-KERNEL-X64: .cfi_endproc
2822
2823; DARWIN-X64-LABEL: test20a:
2824; DARWIN-X64-NOT: callq ___stack_chk_fail
2825; DARWIN-X64: .cfi_endproc
2826
2827; MSVC-I386-LABEL: test20a:
2828; MSVC-I386-NOT: calll @__security_check_cookie@4
2829; MSVC-I386: retl
2830  %a = alloca ptr, align 8
2831  %b = alloca ptr, align 8
2832  %call = call ptr @getp()
2833  store ptr %call, ptr %a, align 8
2834  store ptr %a, ptr %b, align 8
2835  %0 = load ptr, ptr %b, align 8
2836  call void @funcall2(ptr %0)
2837  ret void
2838}
2839
2840; test20b: Addr-of a pointer
2841;          ssp attribute
2842; Requires no protector.
2843; Function Attrs: ssp
2844define void @test20b() #0 {
2845entry:
2846; LINUX-I386-LABEL: test20b:
2847; LINUX-I386-NOT: calll __stack_chk_fail
2848; LINUX-I386: .cfi_endproc
2849
2850; LINUX-X64-LABEL: test20b:
2851; LINUX-X64-NOT: callq __stack_chk_fail
2852; LINUX-X64: .cfi_endproc
2853
2854; LINUX-KERNEL-X64-LABEL: test20b:
2855; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
2856; LINUX-KERNEL-X64: .cfi_endproc
2857
2858; DARWIN-X64-LABEL: test20b:
2859; DARWIN-X64-NOT: callq ___stack_chk_fail
2860; DARWIN-X64: .cfi_endproc
2861
2862; MSVC-I386-LABEL: test20b:
2863; MSVC-I386-NOT: calll @__security_check_cookie@4
2864; MSVC-I386: retl
2865  %a = alloca ptr, align 8
2866  %b = alloca ptr, align 8
2867  %call = call ptr @getp()
2868  store ptr %call, ptr %a, align 8
2869  store ptr %a, ptr %b, align 8
2870  %0 = load ptr, ptr %b, align 8
2871  call void @funcall2(ptr %0)
2872  ret void
2873}
2874
2875; test20c: Addr-of a pointer
2876;          sspstrong attribute
2877; Requires protector.
2878; Function Attrs: sspstrong
2879define void @test20c() #1 {
2880entry:
2881; LINUX-I386-LABEL: test20c:
2882; LINUX-I386: mov{{l|q}} %gs:
2883; LINUX-I386: calll __stack_chk_fail
2884
2885; LINUX-X64-LABEL: test20c:
2886; LINUX-X64: mov{{l|q}} %fs:
2887; LINUX-X64: callq __stack_chk_fail
2888
2889; LINUX-KERNEL-X64-LABEL: test20c:
2890; LINUX-KERNEL-X64: mov{{l|q}} %gs:
2891; LINUX-KERNEL-X64: callq __stack_chk_fail
2892
2893; DARWIN-X64-LABEL: test20c:
2894; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
2895; DARWIN-X64: callq ___stack_chk_fail
2896
2897; MSVC-I386-LABEL: test20c:
2898; MSVC-I386: movl ___security_cookie,
2899; MSVC-I386: calll @__security_check_cookie@4
2900  %a = alloca ptr, align 8
2901  %b = alloca ptr, align 8
2902  %call = call ptr @getp()
2903  store ptr %call, ptr %a, align 8
2904  store ptr %a, ptr %b, align 8
2905  %0 = load ptr, ptr %b, align 8
2906  call void @funcall2(ptr %0)
2907  ret void
2908}
2909
2910; test20d: Addr-of a pointer
2911;          sspreq attribute
2912; Requires protector.
2913; Function Attrs: sspreq
2914define void @test20d() #2 {
2915entry:
2916; LINUX-I386-LABEL: test20d:
2917; LINUX-I386: mov{{l|q}} %gs:
2918; LINUX-I386: calll __stack_chk_fail
2919
2920; LINUX-X64-LABEL: test20d:
2921; LINUX-X64: mov{{l|q}} %fs:
2922; LINUX-X64: callq __stack_chk_fail
2923
2924; LINUX-KERNEL-X64-LABEL: test20d:
2925; LINUX-KERNEL-X64: mov{{l|q}} %gs:
2926; LINUX-KERNEL-X64: callq __stack_chk_fail
2927
2928; DARWIN-X64-LABEL: test20d:
2929; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
2930; DARWIN-X64: callq ___stack_chk_fail
2931
2932; MSVC-I386-LABEL: test20d:
2933; MSVC-I386: movl ___security_cookie,
2934; MSVC-I386: calll @__security_check_cookie@4
2935  %a = alloca ptr, align 8
2936  %b = alloca ptr, align 8
2937  %call = call ptr @getp()
2938  store ptr %call, ptr %a, align 8
2939  store ptr %a, ptr %b, align 8
2940  %0 = load ptr, ptr %b, align 8
2941  call void @funcall2(ptr %0)
2942  ret void
2943}
2944
2945; test21a: Addr-of a casted pointer
2946;          no ssp attribute
2947; Requires no protector.
2948define void @test21a() {
2949entry:
2950; LINUX-I386-LABEL: test21a:
2951; LINUX-I386-NOT: calll __stack_chk_fail
2952; LINUX-I386: .cfi_endproc
2953
2954; LINUX-X64-LABEL: test21a:
2955; LINUX-X64-NOT: callq __stack_chk_fail
2956; LINUX-X64: .cfi_endproc
2957
2958; LINUX-KERNEL-X64-LABEL: test21a:
2959; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
2960; LINUX-KERNEL-X64: .cfi_endproc
2961
2962; DARWIN-X64-LABEL: test21a:
2963; DARWIN-X64-NOT: callq ___stack_chk_fail
2964; DARWIN-X64: .cfi_endproc
2965
2966; MSVC-I386-LABEL: test21a:
2967; MSVC-I386-NOT: calll @__security_check_cookie@4
2968; MSVC-I386: retl
2969  %a = alloca ptr, align 8
2970  %b = alloca ptr, align 8
2971  %call = call ptr @getp()
2972  store ptr %call, ptr %a, align 8
2973  store ptr %a, ptr %b, align 8
2974  %0 = load ptr, ptr %b, align 8
2975  call void @funfloat2(ptr %0)
2976  ret void
2977}
2978
2979; test21b: Addr-of a casted pointer
2980;          ssp attribute
2981; Requires no protector.
2982; Function Attrs: ssp
2983define void @test21b() #0 {
2984entry:
2985; LINUX-I386-LABEL: test21b:
2986; LINUX-I386-NOT: calll __stack_chk_fail
2987; LINUX-I386: .cfi_endproc
2988
2989; LINUX-X64-LABEL: test21b:
2990; LINUX-X64-NOT: callq __stack_chk_fail
2991; LINUX-X64: .cfi_endproc
2992
2993; LINUX-KERNEL-X64-LABEL: test21b:
2994; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
2995; LINUX-KERNEL-X64: .cfi_endproc
2996
2997; DARWIN-X64-LABEL: test21b:
2998; DARWIN-X64-NOT: callq ___stack_chk_fail
2999; DARWIN-X64: .cfi_endproc
3000
3001; MSVC-I386-LABEL: test21b:
3002; MSVC-I386-NOT: calll @__security_check_cookie@4
3003; MSVC-I386: retl
3004  %a = alloca ptr, align 8
3005  %b = alloca ptr, align 8
3006  %call = call ptr @getp()
3007  store ptr %call, ptr %a, align 8
3008  store ptr %a, ptr %b, align 8
3009  %0 = load ptr, ptr %b, align 8
3010  call void @funfloat2(ptr %0)
3011  ret void
3012}
3013
3014; test21c: Addr-of a casted pointer
3015;          sspstrong attribute
3016; Requires protector.
3017; Function Attrs: sspstrong
3018define void @test21c() #1 {
3019entry:
3020; LINUX-I386-LABEL: test21c:
3021; LINUX-I386: mov{{l|q}} %gs:
3022; LINUX-I386: calll __stack_chk_fail
3023
3024; LINUX-X64-LABEL: test21c:
3025; LINUX-X64: mov{{l|q}} %fs:
3026; LINUX-X64: callq __stack_chk_fail
3027
3028; LINUX-KERNEL-X64-LABEL: test21c:
3029; LINUX-KERNEL-X64: mov{{l|q}} %gs:
3030; LINUX-KERNEL-X64: callq __stack_chk_fail
3031
3032; DARWIN-X64-LABEL: test21c:
3033; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
3034; DARWIN-X64: callq ___stack_chk_fail
3035
3036; MSVC-I386-LABEL: test21c:
3037; MSVC-I386: movl ___security_cookie,
3038; MSVC-I386: calll @__security_check_cookie@4
3039  %a = alloca ptr, align 8
3040  %b = alloca ptr, align 8
3041  %call = call ptr @getp()
3042  store ptr %call, ptr %a, align 8
3043  store ptr %a, ptr %b, align 8
3044  %0 = load ptr, ptr %b, align 8
3045  call void @funfloat2(ptr %0)
3046  ret void
3047}
3048
3049; test21d: Addr-of a casted pointer
3050;          sspreq attribute
3051; Requires protector.
3052; Function Attrs: sspreq
3053define void @test21d() #2 {
3054entry:
3055; LINUX-I386-LABEL: test21d:
3056; LINUX-I386: mov{{l|q}} %gs:
3057; LINUX-I386: calll __stack_chk_fail
3058
3059; LINUX-X64-LABEL: test21d:
3060; LINUX-X64: mov{{l|q}} %fs:
3061; LINUX-X64: callq __stack_chk_fail
3062
3063; LINUX-KERNEL-X64-LABEL: test21d:
3064; LINUX-KERNEL-X64: mov{{l|q}} %gs:
3065; LINUX-KERNEL-X64: callq __stack_chk_fail
3066
3067; DARWIN-X64-LABEL: test21d:
3068; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
3069; DARWIN-X64: callq ___stack_chk_fail
3070
3071; MSVC-I386-LABEL: test21d:
3072; MSVC-I386: movl ___security_cookie,
3073; MSVC-I386: calll @__security_check_cookie@4
3074  %a = alloca ptr, align 8
3075  %b = alloca ptr, align 8
3076  %call = call ptr @getp()
3077  store ptr %call, ptr %a, align 8
3078  store ptr %a, ptr %b, align 8
3079  %0 = load ptr, ptr %b, align 8
3080  call void @funfloat2(ptr %0)
3081  ret void
3082}
3083
3084; test22a: [2 x i8] in a class
3085;          no ssp attribute
3086; Requires no protector.
3087define signext i8 @test22a() {
3088entry:
3089; LINUX-I386-LABEL: test22a:
3090; LINUX-I386-NOT: calll __stack_chk_fail
3091; LINUX-I386: .cfi_endproc
3092
3093; LINUX-X64-LABEL: test22a:
3094; LINUX-X64-NOT: callq __stack_chk_fail
3095; LINUX-X64: .cfi_endproc
3096
3097; LINUX-KERNEL-X64-LABEL: test22a:
3098; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
3099; LINUX-KERNEL-X64: .cfi_endproc
3100
3101; DARWIN-X64-LABEL: test22a:
3102; DARWIN-X64-NOT: callq ___stack_chk_fail
3103; DARWIN-X64: .cfi_endproc
3104
3105; MSVC-I386-LABEL: test22a:
3106; MSVC-I386-NOT: calll @__security_check_cookie@4
3107; MSVC-I386: retl
3108  %a = alloca %class.A, align 1
3109  %0 = load i8, ptr %a, align 1
3110  ret i8 %0
3111}
3112
3113; test22b: [2 x i8] in a class
3114;          ssp attribute
3115; Requires no protector.
3116; Function Attrs: ssp
3117define signext i8 @test22b() #0 {
3118entry:
3119; LINUX-I386-LABEL: test22b:
3120; LINUX-I386-NOT: calll __stack_chk_fail
3121; LINUX-I386: .cfi_endproc
3122
3123; LINUX-X64-LABEL: test22b:
3124; LINUX-X64-NOT: callq __stack_chk_fail
3125; LINUX-X64: .cfi_endproc
3126
3127; LINUX-KERNEL-X64-LABEL: test22b:
3128; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
3129; LINUX-KERNEL-X64: .cfi_endproc
3130
3131; DARWIN-X64-LABEL: test22b:
3132; DARWIN-X64-NOT: callq ___stack_chk_fail
3133; DARWIN-X64: .cfi_endproc
3134
3135; MSVC-I386-LABEL: test22b:
3136; MSVC-I386-NOT: calll @__security_check_cookie@4
3137; MSVC-I386: retl
3138  %a = alloca %class.A, align 1
3139  %0 = load i8, ptr %a, align 1
3140  ret i8 %0
3141}
3142
3143; test22c: [2 x i8] in a class
3144;          sspstrong attribute
3145; Requires protector.
3146; Function Attrs: sspstrong
3147define signext i8 @test22c() #1 {
3148entry:
3149; LINUX-I386-LABEL: test22c:
3150; LINUX-I386: mov{{l|q}} %gs:
3151; LINUX-I386: calll __stack_chk_fail
3152
3153; LINUX-X64-LABEL: test22c:
3154; LINUX-X64: mov{{l|q}} %fs:
3155; LINUX-X64: callq __stack_chk_fail
3156
3157; LINUX-KERNEL-X64-LABEL: test22c:
3158; LINUX-KERNEL-X64: mov{{l|q}} %gs:
3159; LINUX-KERNEL-X64: callq __stack_chk_fail
3160
3161; DARWIN-X64-LABEL: test22c:
3162; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
3163; DARWIN-X64: callq ___stack_chk_fail
3164
3165; MSVC-I386-LABEL: test22c:
3166; MSVC-I386: movl ___security_cookie,
3167; MSVC-I386: calll @__security_check_cookie@4
3168  %a = alloca %class.A, align 1
3169  %0 = load i8, ptr %a, align 1
3170  ret i8 %0
3171}
3172
3173; test22d: [2 x i8] in a class
3174;          sspreq attribute
3175; Requires protector.
3176; Function Attrs: sspreq
3177define signext i8 @test22d() #2 {
3178entry:
3179; LINUX-I386-LABEL: test22d:
3180; LINUX-I386: mov{{l|q}} %gs:
3181; LINUX-I386: calll __stack_chk_fail
3182
3183; LINUX-X64-LABEL: test22d:
3184; LINUX-X64: mov{{l|q}} %fs:
3185; LINUX-X64: callq __stack_chk_fail
3186
3187; LINUX-KERNEL-X64-LABEL: test22d:
3188; LINUX-KERNEL-X64: mov{{l|q}} %gs:
3189; LINUX-KERNEL-X64: callq __stack_chk_fail
3190
3191; DARWIN-X64-LABEL: test22d:
3192; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
3193; DARWIN-X64: callq ___stack_chk_fail
3194
3195; MSVC-I386-LABEL: test22d:
3196; MSVC-I386: movl ___security_cookie,
3197; MSVC-I386: calll @__security_check_cookie@4
3198  %a = alloca %class.A, align 1
3199  %0 = load i8, ptr %a, align 1
3200  ret i8 %0
3201}
3202
3203; test23a: [2 x i8] nested in several layers of structs and unions
3204;          no ssp attribute
3205; Requires no protector.
3206define signext i8 @test23a() {
3207entry:
3208; LINUX-I386-LABEL: test23a:
3209; LINUX-I386-NOT: calll __stack_chk_fail
3210; LINUX-I386: .cfi_endproc
3211
3212; LINUX-X64-LABEL: test23a:
3213; LINUX-X64-NOT: callq __stack_chk_fail
3214; LINUX-X64: .cfi_endproc
3215
3216; LINUX-KERNEL-X64-LABEL: test23a:
3217; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
3218; LINUX-KERNEL-X64: .cfi_endproc
3219
3220; DARWIN-X64-LABEL: test23a:
3221; DARWIN-X64-NOT: callq ___stack_chk_fail
3222; DARWIN-X64: .cfi_endproc
3223
3224; MSVC-I386-LABEL: test23a:
3225; MSVC-I386-NOT: calll @__security_check_cookie@4
3226; MSVC-I386: retl
3227  %x = alloca %struct.deep, align 1
3228  %0 = load i8, ptr %x, align 1
3229  ret i8 %0
3230}
3231
3232; test23b: [2 x i8] nested in several layers of structs and unions
3233;          ssp attribute
3234; Requires no protector.
3235; Function Attrs: ssp
3236define signext i8 @test23b() #0 {
3237entry:
3238; LINUX-I386-LABEL: test23b:
3239; LINUX-I386-NOT: calll __stack_chk_fail
3240; LINUX-I386: .cfi_endproc
3241
3242; LINUX-X64-LABEL: test23b:
3243; LINUX-X64-NOT: callq __stack_chk_fail
3244; LINUX-X64: .cfi_endproc
3245
3246; LINUX-KERNEL-X64-LABEL: test23b:
3247; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
3248; LINUX-KERNEL-X64: .cfi_endproc
3249
3250; DARWIN-X64-LABEL: test23b:
3251; DARWIN-X64-NOT: callq ___stack_chk_fail
3252; DARWIN-X64: .cfi_endproc
3253
3254; MSVC-I386-LABEL: test23b:
3255; MSVC-I386-NOT: calll @__security_check_cookie@4
3256; MSVC-I386: retl
3257  %x = alloca %struct.deep, align 1
3258  %0 = load i8, ptr %x, align 1
3259  ret i8 %0
3260}
3261
3262; test23c: [2 x i8] nested in several layers of structs and unions
3263;          sspstrong attribute
3264; Requires protector.
3265; Function Attrs: sspstrong
3266define signext i8 @test23c() #1 {
3267entry:
3268; LINUX-I386-LABEL: test23c:
3269; LINUX-I386: mov{{l|q}} %gs:
3270; LINUX-I386: calll __stack_chk_fail
3271
3272; LINUX-X64-LABEL: test23c:
3273; LINUX-X64: mov{{l|q}} %fs:
3274; LINUX-X64: callq __stack_chk_fail
3275
3276; LINUX-KERNEL-X64-LABEL: test23c:
3277; LINUX-KERNEL-X64: mov{{l|q}} %gs:
3278; LINUX-KERNEL-X64: callq __stack_chk_fail
3279
3280; DARWIN-X64-LABEL: test23c:
3281; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
3282; DARWIN-X64: callq ___stack_chk_fail
3283
3284; MSVC-I386-LABEL: test23c:
3285; MSVC-I386: movl ___security_cookie,
3286; MSVC-I386: calll @__security_check_cookie@4
3287  %x = alloca %struct.deep, align 1
3288  %0 = load i8, ptr %x, align 1
3289  ret i8 %0
3290}
3291
3292; test23d: [2 x i8] nested in several layers of structs and unions
3293;          sspreq attribute
3294; Requires protector.
3295; Function Attrs: sspreq
3296define signext i8 @test23d() #2 {
3297entry:
3298; LINUX-I386-LABEL: test23d:
3299; LINUX-I386: mov{{l|q}} %gs:
3300; LINUX-I386: calll __stack_chk_fail
3301
3302; LINUX-X64-LABEL: test23d:
3303; LINUX-X64: mov{{l|q}} %fs:
3304; LINUX-X64: callq __stack_chk_fail
3305
3306; LINUX-KERNEL-X64-LABEL: test23d:
3307; LINUX-KERNEL-X64: mov{{l|q}} %gs:
3308; LINUX-KERNEL-X64: callq __stack_chk_fail
3309
3310; DARWIN-X64-LABEL: test23d:
3311; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
3312; DARWIN-X64: callq ___stack_chk_fail
3313
3314; MSVC-I386-LABEL: test23d:
3315; MSVC-I386: movl ___security_cookie,
3316; MSVC-I386: calll @__security_check_cookie@4
3317  %x = alloca %struct.deep, align 1
3318  %0 = load i8, ptr %x, align 1
3319  ret i8 %0
3320}
3321
3322; test24a: Variable sized alloca
3323;          no ssp attribute
3324; Requires no protector.
3325define void @test24a(i32 %n) {
3326entry:
3327; LINUX-I386-LABEL: test24a:
3328; LINUX-I386-NOT: calll __stack_chk_fail
3329; LINUX-I386: .cfi_endproc
3330
3331; LINUX-X64-LABEL: test24a:
3332; LINUX-X64-NOT: callq __stack_chk_fail
3333; LINUX-X64: .cfi_endproc
3334
3335; LINUX-KERNEL-X64-LABEL: test24a:
3336; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
3337; LINUX-KERNEL-X64: .cfi_endproc
3338
3339; DARWIN-X64-LABEL: test24a:
3340; DARWIN-X64-NOT: callq ___stack_chk_fail
3341; DARWIN-X64: .cfi_endproc
3342
3343; MSVC-I386-LABEL: test24a:
3344; MSVC-I386-NOT: calll @__security_check_cookie@4
3345; MSVC-I386: retl
3346  %n.addr = alloca i32, align 4
3347  %a = alloca ptr, align 8
3348  store i32 %n, ptr %n.addr, align 4
3349  %0 = load i32, ptr %n.addr, align 4
3350  %conv = sext i32 %0 to i64
3351  %1 = alloca i8, i64 %conv
3352  store ptr %1, ptr %a, align 8
3353  ret void
3354}
3355
3356; test24b: Variable sized alloca
3357;          ssp attribute
3358; Requires protector.
3359; Function Attrs: ssp
3360define void @test24b(i32 %n) #0 {
3361entry:
3362; LINUX-I386-LABEL: test24b:
3363; LINUX-I386: mov{{l|q}} %gs:
3364; LINUX-I386: calll __stack_chk_fail
3365
3366; LINUX-X64-LABEL: test24b:
3367; LINUX-X64: mov{{l|q}} %fs:
3368; LINUX-X64: callq __stack_chk_fail
3369
3370; LINUX-KERNEL-X64-LABEL: test24b:
3371; LINUX-KERNEL-X64: mov{{l|q}} %gs:
3372; LINUX-KERNEL-X64: callq __stack_chk_fail
3373
3374; DARWIN-X64-LABEL: test24b:
3375; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
3376; DARWIN-X64: callq ___stack_chk_fail
3377
3378; MSVC-I386-LABEL: test24b:
3379; MSVC-I386: movl ___security_cookie,
3380; MSVC-I386: calll @__security_check_cookie@4
3381  %n.addr = alloca i32, align 4
3382  %a = alloca ptr, align 8
3383  store i32 %n, ptr %n.addr, align 4
3384  %0 = load i32, ptr %n.addr, align 4
3385  %conv = sext i32 %0 to i64
3386  %1 = alloca i8, i64 %conv
3387  store ptr %1, ptr %a, align 8
3388  ret void
3389}
3390
3391; test24c: Variable sized alloca
3392;          sspstrong attribute
3393; Requires protector.
3394; Function Attrs: sspstrong
3395define void @test24c(i32 %n) #1 {
3396entry:
3397; LINUX-I386-LABEL: test24c:
3398; LINUX-I386: mov{{l|q}} %gs:
3399; LINUX-I386: calll __stack_chk_fail
3400
3401; LINUX-X64-LABEL: test24c:
3402; LINUX-X64: mov{{l|q}} %fs:
3403; LINUX-X64: callq __stack_chk_fail
3404
3405; LINUX-KERNEL-X64-LABEL: test24c:
3406; LINUX-KERNEL-X64: mov{{l|q}} %gs:
3407; LINUX-KERNEL-X64: callq __stack_chk_fail
3408
3409; DARWIN-X64-LABEL: test24c:
3410; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
3411; DARWIN-X64: callq ___stack_chk_fail
3412
3413; MSVC-I386-LABEL: test24c:
3414; MSVC-I386: movl ___security_cookie,
3415; MSVC-I386: calll @__security_check_cookie@4
3416  %n.addr = alloca i32, align 4
3417  %a = alloca ptr, align 8
3418  store i32 %n, ptr %n.addr, align 4
3419  %0 = load i32, ptr %n.addr, align 4
3420  %conv = sext i32 %0 to i64
3421  %1 = alloca i8, i64 %conv
3422  store ptr %1, ptr %a, align 8
3423  ret void
3424}
3425
3426; test24d: Variable sized alloca
3427;          sspreq attribute
3428; Requires protector.
3429; Function Attrs: sspreq
3430define void @test24d(i32 %n) #2 {
3431entry:
3432; LINUX-I386-LABEL: test24d:
3433; LINUX-I386: mov{{l|q}} %gs:
3434; LINUX-I386: calll __stack_chk_fail
3435
3436; LINUX-X64-LABEL: test24d:
3437; LINUX-X64: mov{{l|q}} %fs:
3438; LINUX-X64: callq __stack_chk_fail
3439
3440; LINUX-KERNEL-X64-LABEL: test24d:
3441; LINUX-KERNEL-X64: mov{{l|q}} %gs:
3442; LINUX-KERNEL-X64: callq __stack_chk_fail
3443
3444; DARWIN-X64-LABEL: test24d:
3445; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
3446; DARWIN-X64: callq ___stack_chk_fail
3447
3448; MSVC-I386-LABEL: test24d:
3449; MSVC-I386: movl ___security_cookie,
3450; MSVC-I386: calll @__security_check_cookie@4
3451  %n.addr = alloca i32, align 4
3452  %a = alloca ptr, align 8
3453  store i32 %n, ptr %n.addr, align 4
3454  %0 = load i32, ptr %n.addr, align 4
3455  %conv = sext i32 %0 to i64
3456  %1 = alloca i8, i64 %conv
3457  store ptr %1, ptr %a, align 8
3458  ret void
3459}
3460
3461; test25a: array of [4 x i32]
3462;          no ssp attribute
3463; Requires no protector.
3464define i32 @test25a() {
3465entry:
3466; LINUX-I386-LABEL: test25a:
3467; LINUX-I386-NOT: calll __stack_chk_fail
3468; LINUX-I386: .cfi_endproc
3469
3470; LINUX-X64-LABEL: test25a:
3471; LINUX-X64-NOT: callq __stack_chk_fail
3472; LINUX-X64: .cfi_endproc
3473
3474; LINUX-KERNEL-X64-LABEL: test25a:
3475; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
3476; LINUX-KERNEL-X64: .cfi_endproc
3477
3478; DARWIN-X64-LABEL: test25a:
3479; DARWIN-X64-NOT: callq ___stack_chk_fail
3480; DARWIN-X64: .cfi_endproc
3481
3482; MSVC-I386-LABEL: test25a:
3483; MSVC-I386-NOT: calll @__security_check_cookie@4
3484; MSVC-I386: retl
3485  %a = alloca [4 x i32], align 16
3486  %0 = load i32, ptr %a, align 4
3487  ret i32 %0
3488}
3489
3490; test25b: array of [4 x i32]
3491;          ssp attribute
3492; Requires no protector, except for Darwin which _does_ require a protector.
3493; Function Attrs: ssp
3494define i32 @test25b() #0 {
3495entry:
3496; LINUX-I386-LABEL: test25b:
3497; LINUX-I386-NOT: calll __stack_chk_fail
3498; LINUX-I386: .cfi_endproc
3499
3500; LINUX-X64-LABEL: test25b:
3501; LINUX-X64-NOT: callq __stack_chk_fail
3502; LINUX-X64: .cfi_endproc
3503
3504; LINUX-KERNEL-X64-LABEL: test25b:
3505; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
3506; LINUX-KERNEL-X64: .cfi_endproc
3507
3508; DARWIN-X64-LABEL: test25b:
3509; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
3510; DARWIN-X64: callq ___stack_chk_fail
3511
3512; MSVC-I386-LABEL: test25b:
3513; MSVC-I386-NOT: calll @__security_check_cookie@4
3514; MSVC-I386: retl
3515
3516; MINGW-X64-LABEL: test25b:
3517; MINGW-X64-NOT: callq __stack_chk_fail
3518; MINGW-X64: .seh_endproc
3519
3520  %a = alloca [4 x i32], align 16
3521  %0 = load i32, ptr %a, align 4
3522  ret i32 %0
3523}
3524
3525; test25c: array of [4 x i32]
3526;          sspstrong attribute
3527; Requires protector.
3528; Function Attrs: sspstrong
3529define i32 @test25c() #1 {
3530entry:
3531; LINUX-I386-LABEL: test25c:
3532; LINUX-I386: mov{{l|q}} %gs:
3533; LINUX-I386: calll __stack_chk_fail
3534
3535; LINUX-X64-LABEL: test25c:
3536; LINUX-X64: mov{{l|q}} %fs:
3537; LINUX-X64: callq __stack_chk_fail
3538
3539; LINUX-KERNEL-X64-LABEL: test25c:
3540; LINUX-KERNEL-X64: mov{{l|q}} %gs:
3541; LINUX-KERNEL-X64: callq __stack_chk_fail
3542
3543; DARWIN-X64-LABEL: test25c:
3544; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
3545; DARWIN-X64: callq ___stack_chk_fail
3546
3547; MSVC-I386-LABEL: test25c:
3548; MSVC-I386: movl ___security_cookie,
3549; MSVC-I386: calll @__security_check_cookie@4
3550  %a = alloca [4 x i32], align 16
3551  %0 = load i32, ptr %a, align 4
3552  ret i32 %0
3553}
3554
3555; test25d: array of [4 x i32]
3556;          sspreq attribute
3557; Requires protector.
3558; Function Attrs: sspreq
3559define i32 @test25d() #2 {
3560entry:
3561; LINUX-I386-LABEL: test25d:
3562; LINUX-I386: mov{{l|q}} %gs:
3563; LINUX-I386: calll __stack_chk_fail
3564
3565; LINUX-X64-LABEL: test25d:
3566; LINUX-X64: mov{{l|q}} %fs:
3567; LINUX-X64: callq __stack_chk_fail
3568
3569; LINUX-KERNEL-X64-LABEL: test25d:
3570; LINUX-KERNEL-X64: mov{{l|q}} %gs:
3571; LINUX-KERNEL-X64: callq __stack_chk_fail
3572
3573; DARWIN-X64-LABEL: test25d:
3574; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
3575; DARWIN-X64: callq ___stack_chk_fail
3576
3577; MSVC-I386-LABEL: test25d:
3578; MSVC-I386: movl ___security_cookie,
3579; MSVC-I386: calll @__security_check_cookie@4
3580  %a = alloca [4 x i32], align 16
3581  %0 = load i32, ptr %a, align 4
3582  ret i32 %0
3583}
3584
3585; test26: Nested structure, no arrays, no address-of expressions.
3586;         Verify that the resulting gep-of-gep does not incorrectly trigger
3587;         a stack protector.
3588;         ssptrong attribute
3589; Requires no protector.
3590; Function Attrs: sspstrong
3591define void @test26() #1 {
3592entry:
3593; LINUX-I386-LABEL: test26:
3594; LINUX-I386-NOT: calll __stack_chk_fail
3595; LINUX-I386: .cfi_endproc
3596
3597; LINUX-X64-LABEL: test26:
3598; LINUX-X64-NOT: callq __stack_chk_fail
3599; LINUX-X64: .cfi_endproc
3600
3601; LINUX-KERNEL-X64-LABEL: test26:
3602; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
3603; LINUX-KERNEL-X64: .cfi_endproc
3604
3605; DARWIN-X64-LABEL: test26:
3606; DARWIN-X64-NOT: callq ___stack_chk_fail
3607; DARWIN-X64: .cfi_endproc
3608
3609; MSVC-I386-LABEL: test26:
3610; MSVC-I386-NOT: calll @__security_check_cookie@4
3611; MSVC-I386: retl
3612  %c = alloca %struct.nest, align 4
3613  %b = getelementptr inbounds %struct.nest, ptr %c, i32 0, i32 1
3614  %0 = load i32, ptr %b, align 4
3615  %call = call i32 (ptr, ...) @printf(ptr @.str, i32 %0)
3616  ret void
3617}
3618
3619; test27: Address-of a structure taken in a function with a loop where
3620;         the alloca is an incoming value to a PHI node and a use of that PHI
3621;         node is also an incoming value.
3622;         Verify that the address-of analysis does not get stuck in infinite
3623;         recursion when chasing the alloca through the PHI nodes.
3624; Requires protector.
3625; Function Attrs: sspstrong
3626define i32 @test27(i32 %arg) #1 {
3627bb:
3628; LINUX-I386-LABEL: test27:
3629; LINUX-I386: mov{{l|q}} %gs:
3630; LINUX-I386: calll __stack_chk_fail
3631
3632; LINUX-X64-LABEL: test27:
3633; LINUX-X64: mov{{l|q}} %fs:
3634; LINUX-X64: callq __stack_chk_fail
3635
3636; LINUX-KERNEL-X64-LABEL: test27:
3637; LINUX-KERNEL-X64: mov{{l|q}} %gs:
3638; LINUX-KERNEL-X64: callq __stack_chk_fail
3639
3640; DARWIN-X64-LABEL: test27:
3641; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
3642; DARWIN-X64: callq ___stack_chk_fail
3643
3644; MSVC-I386-LABEL: test27:
3645; MSVC-I386: movl ___security_cookie,
3646; MSVC-I386: calll @__security_check_cookie@4
3647  %tmp = alloca ptr, align 8
3648  %tmp1 = call i32 (...) @dummy(ptr %tmp)
3649  %tmp2 = load ptr, ptr %tmp, align 8
3650  %tmp3 = ptrtoint ptr %tmp2 to i64
3651  %tmp4 = trunc i64 %tmp3 to i32
3652  %tmp5 = icmp sgt i32 %tmp4, 0
3653  br i1 %tmp5, label %bb6, label %bb21
3654
3655bb6:                                              ; preds = %bb17, %bb
3656  %tmp7 = phi ptr [ %tmp19, %bb17 ], [ %tmp2, %bb ]
3657  %tmp8 = phi i64 [ %tmp20, %bb17 ], [ 1, %bb ]
3658  %tmp9 = phi i32 [ %tmp14, %bb17 ], [ %tmp1, %bb ]
3659  %tmp11 = load i8, ptr %tmp7, align 1
3660  %tmp12 = icmp eq i8 %tmp11, 1
3661  %tmp13 = add nsw i32 %tmp9, 8
3662  %tmp14 = select i1 %tmp12, i32 %tmp13, i32 %tmp9
3663  %tmp15 = trunc i64 %tmp8 to i32
3664  %tmp16 = icmp eq i32 %tmp15, %tmp4
3665  br i1 %tmp16, label %bb21, label %bb17
3666
3667bb17:                                             ; preds = %bb6
3668  %tmp18 = getelementptr inbounds ptr, ptr %tmp, i64 %tmp8
3669  %tmp19 = load ptr, ptr %tmp18, align 8
3670  %tmp20 = add i64 %tmp8, 1
3671  br label %bb6
3672
3673bb21:                                             ; preds = %bb6, %bb
3674  %tmp22 = phi i32 [ %tmp1, %bb ], [ %tmp14, %bb6 ]
3675  %tmp23 = call i32 (...) @dummy(i32 %tmp22)
3676  ret i32 undef
3677}
3678
3679; test28a: An array of [32 x i8] and a requested ssp-buffer-size of 33.
3680; Requires no protector.
3681; Function Attrs: ssp stack-protector-buffer-size=33
3682define i32 @test28a() #3 {
3683entry:
3684; LINUX-I386-LABEL: test28a:
3685; LINUX-I386-NOT: calll __stack_chk_fail
3686; LINUX-I386: .cfi_endproc
3687
3688; LINUX-X64-LABEL: test28a:
3689; LINUX-X64-NOT: callq __stack_chk_fail
3690; LINUX-X64: .cfi_endproc
3691
3692; LINUX-KERNEL-X64-LABEL: test28a:
3693; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
3694; LINUX-KERNEL-X64: .cfi_endproc
3695
3696; DARWIN-X64-LABEL: test28a:
3697; DARWIN-X64-NOT: callq ___stack_chk_fail
3698; DARWIN-X64: .cfi_endproc
3699
3700; MSVC-I386-LABEL: test28a:
3701; MSVC-I386-NOT: calll @__security_check_cookie@4
3702; MSVC-I386: retl
3703  %test = alloca [32 x i8], align 16
3704  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %test)
3705  ret i32 %call
3706}
3707
3708; test28b: An array of [33 x i8] and a requested ssp-buffer-size of 33.
3709; Requires protector.
3710; Function Attrs: ssp stack-protector-buffer-size=33
3711define i32 @test28b() #3 {
3712entry:
3713; LINUX-I386-LABEL: test28b:
3714; LINUX-I386: mov{{l|q}} %gs:
3715; LINUX-I386: calll __stack_chk_fail
3716
3717; LINUX-X64-LABEL: test28b:
3718; LINUX-X64: mov{{l|q}} %fs:
3719; LINUX-X64: callq __stack_chk_fail
3720
3721; LINUX-KERNEL-X64-LABEL: test28b:
3722; LINUX-KERNEL-X64: mov{{l|q}} %gs:
3723; LINUX-KERNEL-X64: callq __stack_chk_fail
3724
3725; DARWIN-X64-LABEL: test28b:
3726; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
3727; DARWIN-X64: callq ___stack_chk_fail
3728
3729; MSVC-I386-LABEL: test28b:
3730; MSVC-I386: movl ___security_cookie,
3731; MSVC-I386: calll @__security_check_cookie@4
3732  %test = alloca [33 x i8], align 16
3733  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %test)
3734  ret i32 %call
3735}
3736
3737; test29a: An array of [4 x i8] and a requested ssp-buffer-size of 5.
3738; Requires no protector.
3739; Function Attrs: ssp stack-protector-buffer-size=5
3740define i32 @test29a() #4 {
3741entry:
3742; LINUX-I386-LABEL: test29a:
3743; LINUX-I386-NOT: calll __stack_chk_fail
3744; LINUX-I386: .cfi_endproc
3745
3746; LINUX-X64-LABEL: test29a:
3747; LINUX-X64-NOT: callq __stack_chk_fail
3748; LINUX-X64: .cfi_endproc
3749
3750; LINUX-KERNEL-X64-LABEL: test29a:
3751; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
3752; LINUX-KERNEL-X64: .cfi_endproc
3753
3754; DARWIN-X64-LABEL: test29a:
3755; DARWIN-X64-NOT: callq ___stack_chk_fail
3756; DARWIN-X64: .cfi_endproc
3757
3758; MSVC-I386-LABEL: test29a:
3759; MSVC-I386-NOT: calll @__security_check_cookie@4
3760; MSVC-I386: retl
3761  %test = alloca [4 x i8], align 1
3762  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %test)
3763  ret i32 %call
3764}
3765
3766; test29b: An array of [5 x i8] and a requested ssp-buffer-size of 5.
3767; Requires protector.
3768; Function Attrs: ssp stack-protector-buffer-size=5
3769define i32 @test29b() #4 {
3770entry:
3771; LINUX-I386-LABEL: test29b:
3772; LINUX-I386: mov{{l|q}} %gs:
3773; LINUX-I386: calll __stack_chk_fail
3774
3775; LINUX-X64-LABEL: test29b:
3776; LINUX-X64: mov{{l|q}} %fs:
3777; LINUX-X64: callq __stack_chk_fail
3778
3779; LINUX-KERNEL-X64-LABEL: test29b:
3780; LINUX-KERNEL-X64: mov{{l|q}} %gs:
3781; LINUX-KERNEL-X64: callq __stack_chk_fail
3782
3783; DARWIN-X64-LABEL: test29b:
3784; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
3785; DARWIN-X64: callq ___stack_chk_fail
3786
3787; MSVC-I386-LABEL: test29b:
3788; MSVC-I386: movl ___security_cookie,
3789; MSVC-I386: calll @__security_check_cookie@4
3790  %test = alloca [5 x i8], align 1
3791  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %test)
3792  ret i32 %call
3793}
3794
3795; test30a: An structure containing an i32 and an array of [5 x i8].
3796;          Requested ssp-buffer-size of 6.
3797; Requires no protector.
3798; Function Attrs: ssp stack-protector-buffer-size=6
3799define i32 @test30a() #5 {
3800entry:
3801; LINUX-I386-LABEL: test30a:
3802; LINUX-I386-NOT: calll __stack_chk_fail
3803; LINUX-I386: .cfi_endproc
3804
3805; LINUX-X64-LABEL: test30a:
3806; LINUX-X64-NOT: callq __stack_chk_fail
3807; LINUX-X64: .cfi_endproc
3808
3809; LINUX-KERNEL-X64-LABEL: test30a:
3810; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
3811; LINUX-KERNEL-X64: .cfi_endproc
3812
3813; DARWIN-X64-LABEL: test30a:
3814; DARWIN-X64-NOT: callq ___stack_chk_fail
3815; DARWIN-X64: .cfi_endproc
3816
3817; MSVC-I386-LABEL: test30a:
3818; MSVC-I386-NOT: calll @__security_check_cookie@4
3819; MSVC-I386: retl
3820  %test = alloca %struct.small_char, align 4
3821  %test.coerce = alloca { i64, i8 }
3822  call void @llvm.memcpy.p0.p0.i64(ptr %test.coerce, ptr %test, i64 12, i1 false)
3823  %0 = getelementptr { i64, i8 }, ptr %test.coerce, i32 0, i32 0
3824  %1 = load i64, ptr %0, align 1
3825  %2 = getelementptr { i64, i8 }, ptr %test.coerce, i32 0, i32 1
3826  %3 = load i8, ptr %2, align 1
3827  %call = call i32 (ptr, ...) @printf(ptr @.str, i64 %1, i8 %3)
3828  ret i32 %call
3829}
3830
3831; test30b: An structure containing an i32 and an array of [5 x i8].
3832;          Requested ssp-buffer-size of 5.
3833; Requires protector.
3834; Function Attrs: ssp stack-protector-buffer-size=5
3835define i32 @test30b() #4 {
3836entry:
3837; LINUX-I386-LABEL: test30b:
3838; LINUX-I386: mov{{l|q}} %gs:
3839; LINUX-I386: calll __stack_chk_fail
3840
3841; LINUX-X64-LABEL: test30b:
3842; LINUX-X64: mov{{l|q}} %fs:
3843; LINUX-X64: callq __stack_chk_fail
3844
3845; LINUX-KERNEL-X64-LABEL: test30b:
3846; LINUX-KERNEL-X64: mov{{l|q}} %gs:
3847; LINUX-KERNEL-X64: callq __stack_chk_fail
3848
3849; DARWIN-X64-LABEL: test30b:
3850; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
3851; DARWIN-X64: callq ___stack_chk_fail
3852
3853; MSVC-I386-LABEL: test30b:
3854; MSVC-I386: movl ___security_cookie,
3855; MSVC-I386: calll @__security_check_cookie@4
3856  %test = alloca %struct.small_char, align 4
3857  %test.coerce = alloca { i64, i8 }
3858  call void @llvm.memcpy.p0.p0.i64(ptr %test.coerce, ptr %test, i64 12, i1 false)
3859  %0 = getelementptr { i64, i8 }, ptr %test.coerce, i32 0, i32 0
3860  %1 = load i64, ptr %0, align 1
3861  %2 = getelementptr { i64, i8 }, ptr %test.coerce, i32 0, i32 1
3862  %3 = load i8, ptr %2, align 1
3863  %call = call i32 (ptr, ...) @printf(ptr @.str, i64 %1, i8 %3)
3864  ret i32 %call
3865}
3866
3867; test31a: An alloca of size 5.
3868;          Requested ssp-buffer-size of 6.
3869; Requires no protector.
3870; Function Attrs: ssp stack-protector-buffer-size=6
3871define i32 @test31a() #5 {
3872entry:
3873; LINUX-I386-LABEL: test31a:
3874; LINUX-I386-NOT: calll __stack_chk_fail
3875; LINUX-I386: .cfi_endproc
3876
3877; LINUX-X64-LABEL: test31a:
3878; LINUX-X64-NOT: callq __stack_chk_fail
3879; LINUX-X64: .cfi_endproc
3880
3881; LINUX-KERNEL-X64-LABEL: test31a:
3882; LINUX-KERNEL-X64-NOT: callq __stack_chk_fail
3883; LINUX-KERNEL-X64: .cfi_endproc
3884
3885; DARWIN-X64-LABEL: test31a:
3886; DARWIN-X64-NOT: callq ___stack_chk_fail
3887; DARWIN-X64: .cfi_endproc
3888
3889; MSVC-I386-LABEL: test31a:
3890; MSVC-I386-NOT: calll @__security_check_cookie@4
3891; MSVC-I386: retl
3892  %test = alloca ptr, align 8
3893  %0 = alloca i8, i64 4
3894  store ptr %0, ptr %test, align 8
3895  %1 = load ptr, ptr %test, align 8
3896  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %1)
3897  ret i32 %call
3898}
3899
3900; test31b: An alloca of size 5.
3901;          Requested ssp-buffer-size of 5.
3902; Requires protector.
3903define i32 @test31b() #4 {
3904entry:
3905; LINUX-I386-LABEL: test31b:
3906; LINUX-I386: mov{{l|q}} %gs:
3907; LINUX-I386: calll __stack_chk_fail
3908
3909; LINUX-X64-LABEL: test31b:
3910; LINUX-X64: mov{{l|q}} %fs:
3911; LINUX-X64: callq __stack_chk_fail
3912
3913; LINUX-KERNEL-X64-LABEL: test31b:
3914; LINUX-KERNEL-X64: mov{{l|q}} %gs:
3915; LINUX-KERNEL-X64: callq __stack_chk_fail
3916
3917; DARWIN-X64-LABEL: test31b:
3918; DARWIN-X64: mov{{l|q}} ___stack_chk_guard
3919; DARWIN-X64: callq ___stack_chk_fail
3920
3921; MSVC-I386-LABEL: test31b:
3922; MSVC-I386: movl ___security_cookie,
3923; MSVC-I386: calll @__security_check_cookie@4
3924  %test = alloca ptr, align 8
3925  %0 = alloca i8, i64 5
3926  store ptr %0, ptr %test, align 8
3927  %1 = load ptr, ptr %test, align 8
3928  %call = call i32 (ptr, ...) @printf(ptr @.str, ptr %1)
3929  ret i32 %call
3930}
3931
3932define void @__stack_chk_fail() #1 !dbg !6 {
3933entry:
3934  ret void
3935}
3936
3937define void @test32() #1 !dbg !7 {
3938entry:
3939; LINUX-I386-LABEL: test32:
3940; LINUX-I386:       .loc 1 4 2 prologue_end
3941; LINUX-I386:       .loc 1 0 0
3942; LINUX-I386-NEXT:  calll __stack_chk_fail
3943
3944; LINUX-X64-LABEL: test32:
3945; LINUX-X64:       .loc 1 4 2 prologue_end
3946; LINUX-X64:       .loc 1 0 0
3947; LINUX-X64-NEXT:  callq __stack_chk_fail
3948
3949; LINUX-KERNEL-X64-LABEL: test32:
3950; LINUX-KERNEL-X64:       .loc 1 4 2 prologue_end
3951; LINUX-KERNEL-X64:       .loc 1 0 0
3952; LINUX-KERNEL-X64-NEXT:  callq __stack_chk_fail
3953
3954; OPENBSD-AMD64-LABEL: test32:
3955; OPENBSD-AMD64:       .loc 1 4 2 prologue_end
3956; OPENBSD-AMD64:       .loc 1 0 0
3957; OPENBSD-AMD64-NEXT:  movl
3958; OPENBSD-AMD64-NEXT:  callq __stack_smash_handler
3959  %0 = alloca [5 x i8], align 1
3960  ret void, !dbg !9
3961}
3962
3963define i32 @IgnoreIntrinsicTest() #1 {
3964; IGNORE_INTRIN: IgnoreIntrinsicTest:
3965  %1 = alloca i32, align 4
3966  call void @llvm.lifetime.start.p0(i64 4, ptr nonnull %1)
3967  store volatile i32 1, ptr %1, align 4
3968  %2 = load volatile i32, ptr %1, align 4
3969  %3 = mul nsw i32 %2, 42
3970  call void @llvm.lifetime.end.p0(i64 4, ptr nonnull %1)
3971  ret i32 %3
3972; IGNORE_INTRIN-NOT: callq __stack_chk_fail
3973; IGNORE_INTRIN:     .cfi_endproc
3974}
3975
3976declare double @testi_aux()
3977declare ptr @strcpy(ptr, ptr)
3978declare i32 @printf(ptr, ...)
3979declare void @funcall(ptr)
3980declare void @funcall2(ptr)
3981declare void @funfloat(ptr)
3982declare void @funfloat2(ptr)
3983declare void @_Z3exceptPi(ptr)
3984declare i32 @__gxx_personality_v0(...)
3985declare ptr @getp()
3986declare i32 @dummy(...)
3987declare void @llvm.memcpy.p0.p0.i64(ptr nocapture, ptr nocapture readonly, i64, i1)
3988declare void @llvm.lifetime.start.p0(i64, ptr nocapture)
3989declare void @llvm.lifetime.end.p0(i64, ptr nocapture)
3990
3991attributes #0 = { ssp }
3992attributes #1 = { sspstrong }
3993attributes #2 = { sspreq }
3994attributes #3 = { ssp "stack-protector-buffer-size"="33" }
3995attributes #4 = { ssp "stack-protector-buffer-size"="5" }
3996attributes #5 = { ssp "stack-protector-buffer-size"="6" }
3997
3998!llvm.dbg.cu = !{!0}
3999!llvm.module.flags = !{!3, !4}
4000!llvm.ident = !{!5}
4001
4002!0 = distinct !DICompileUnit(language: DW_LANG_C99, file: !1, emissionKind: FullDebug)
4003!1 = !DIFile(filename: "test.c", directory: "/tmp")
4004!2 = !{}
4005!3 = !{i32 2, !"Dwarf Version", i32 4}
4006!4 = !{i32 2, !"Debug Info Version", i32 3}
4007!5 = !{!"clang version x.y.z"}
4008!6 = distinct !DISubprogram(name: "__stack_chk_fail", scope: !1, type: !8, unit: !0)
4009!7 = distinct !DISubprogram(name: "test32", scope: !1, type: !8, unit: !0)
4010!8 = !DISubroutineType(types: !2)
4011!9 = !DILocation(line: 4, column: 2, scope: !7)
4012