1 // RUN: %clang_cc1 -triple thumbv8m.base-none-eabi -mcmse -verify %s
2 
3 typedef void (*callback_ns_1t)() __attribute__((cmse_nonsecure_call));
4 typedef void (*callback_1t)();
5 typedef void (*callback_ns_2t)() __attribute__((cmse_nonsecure_call));
6 typedef void (*callback_2t)();
7 
foo(callback_ns_1t nsfptr,callback_1t fptr)8 void foo(callback_ns_1t nsfptr, // expected-error{{functions may not be declared with 'cmse_nonsecure_call' attribute}}
9          callback_1t fptr) __attribute__((cmse_nonsecure_call))
10 {
11   callback_1t fp1 = nsfptr; // expected-warning{{incompatible function pointer types initializing 'callback_1t'}}
12   callback_ns_1t fp2 = fptr; // expected-warning{{incompatible function pointer types initializing 'callback_ns_1t'}}
13   callback_2t fp3 = fptr;
14   callback_ns_2t fp4 = nsfptr;
15 }
16 
bar()17 static void bar() __attribute__((cmse_nonsecure_entry)) // expected-warning{{'cmse_nonsecure_entry' cannot be applied to functions with internal linkage}}
18 {
19 }
20 
21 typedef void nonsecure_fn_t(int) __attribute__((cmse_nonsecure_call));
22 extern nonsecure_fn_t baz; // expected-error{{functions may not be declared with 'cmse_nonsecure_call' attribute}}
23 
24 int v0 __attribute__((cmse_nonsecure_call)); // expected-warning {{'cmse_nonsecure_call' only applies to function types; type here is 'int'}}
25 int v1 __attribute__((cmse_nonsecure_entry)); // expected-warning {{'cmse_nonsecure_entry' attribute only applies to functions}}
26 
27 void fn0() __attribute__((cmse_nonsecure_entry));
28 void fn1() __attribute__((cmse_nonsecure_entry(1)));  // expected-error {{'cmse_nonsecure_entry' attribute takes no arguments}}
29 
30 typedef void (*fn2_t)() __attribute__((cmse_nonsecure_call("abc"))); // expected-error {{'cmse_nonsecure_call' attribute takes no argument}}
31 
32 union U { unsigned n; char b[4]; } u;
33 
xyzzy()34 union U xyzzy() __attribute__((cmse_nonsecure_entry)) {
35   return u; // expected-warning {{passing union across security boundary via return value may leak information}}
36 }
37 
38 void (*fn2)(int, union U) __attribute__((cmse_nonsecure_call));
39 void (*fn3)() __attribute__ ((cmse_nonsecure_call));
40 
41 struct S {
42   int t;
43   union {
44     char b[4];
45     unsigned w;
46   };
47 } s;
48 
qux()49 void qux() {
50   fn2(1,
51       u); // expected-warning {{passing union across security boundary via parameter 1 may leak information}}
52 
53   fn3(
54        u, // expected-warning {{passing union across security boundary via parameter 0 may leak information}}
55        1,
56        s); // expected-warning {{passing union across security boundary via parameter 2 may leak information}}
57 }
58