tccgen: Allow struct init from struct
[tinycc.git] / tests / tcctest.c
blob7425311f058869763808d4e5198809a9ebb94a1c
1 /*
2 * TCC auto test program
3 */
4 #include "config.h"
6 /* identify the configured reference compiler in use */
7 #define CC_gcc 1
8 #define CC_clang 2
9 #define CC_tcc 3
11 /* Unfortunately, gcc version < 3 does not handle that! */
12 #define ALL_ISOC99
14 /* only gcc 3 handles _Bool correctly */
15 #define BOOL_ISOC99
17 /* __VA_ARGS__ and __func__ support */
18 #define C99_MACROS
20 #ifndef __TINYC__
21 typedef __SIZE_TYPE__ uintptr_t;
22 #endif
24 #if defined(_WIN32) || \
25 (defined(__arm__) && \
26 (defined(__FreeBSD__) || defined(__OpenBSD__) || defined(__NetBSD__)))
27 #define LONG_LONG_FORMAT "%lld"
28 #define ULONG_LONG_FORMAT "%llu"
29 #else
30 #define LONG_LONG_FORMAT "%Ld"
31 #define ULONG_LONG_FORMAT "%Lu"
32 #endif
34 // MinGW has 80-bit rather than 64-bit long double which isn't compatible with TCC or MSVC
35 #if defined(_WIN32) && defined(__GNUC__)
36 #define LONG_DOUBLE double
37 #define LONG_DOUBLE_LITERAL(x) x
38 #else
39 #define LONG_DOUBLE long double
40 #define LONG_DOUBLE_LITERAL(x) x ## L
41 #endif
43 /* test various include syntaxes */
45 #define TCCLIB_INC <tcclib.h>
46 #define TCCLIB_INC1 <tcclib
47 #define TCCLIB_INC2 h>
48 #define TCCLIB_INC3 "tcclib.h"
50 #include TCCLIB_INC
52 #include TCCLIB_INC1.TCCLIB_INC2
54 #include TCCLIB_INC1.h>
56 #include TCCLIB_INC3
58 #include <tcclib.h>
60 #include "tcclib.h"
62 #include "tcctest.h"
64 /* Test two more ways to include a file named like a pp-number */
65 #define INC(name) <tests/name.h>
66 #define funnyname 42test.h
67 #define incdir tests/
68 #ifdef __clang__
69 /* clang's preprocessor is broken in this regard and adds spaces
70 to the tokens 'incdir' and 'funnyname' when expanding */
71 #define incname <tests/42test.h>
72 #else
73 #define incname < incdir funnyname >
74 #endif
75 #define __stringify(x) #x
76 #define stringify(x) __stringify(x)
77 #include INC(42test)
78 #include incname
79 #include stringify(funnyname)
81 int fib(int n);
82 void num(int n);
83 void forward_ref(void);
84 int isid(int c);
86 /* Line joining happens before tokenization, so the following
87 must be parsed as ellipsis. */
88 void funny_line_continuation (int, ..\
89 . );
91 #define A 2
92 #define N 1234 + A
93 #define pf printf
94 #define M1(a, b) (a) + (b)
96 #define str\
97 (s) # s
98 #define glue(a, b) a ## b
99 #define xglue(a, b) glue(a, b)
100 #define HIGHLOW "hello"
101 #define LOW LOW ", world"
103 static int onetwothree = 123;
104 #define onetwothree4 onetwothree
105 #define onetwothree xglue(onetwothree,4)
107 #define min(a, b) ((a) < (b) ? (a) : (b))
109 #ifdef C99_MACROS
110 #define dprintf(level,...) printf(__VA_ARGS__)
111 #endif
113 /* gcc vararg macros */
114 #define dprintf1(level, fmt, args...) printf(fmt, ## args)
116 #define MACRO_NOARGS()
118 #define TEST_CALL(f, ...) f(__VA_ARGS__)
119 #define TEST_CONST() 123
121 #define AAA 3
122 #undef AAA
123 #define AAA 4
125 #if 1
126 #define B3 1
127 #elif 1
128 #define B3 2
129 #elif 0
130 #define B3 3
131 #else
132 #define B3 4
133 #endif
135 #ifdef __TINYC__
136 /* We try to handle this syntax. Make at least sure it doesn't segfault. */
137 char invalid_function_def()[] {return 0;}
138 #endif
140 #define __INT64_C(c) c ## LL
141 #define INT64_MIN (-__INT64_C(9223372036854775807)-1)
143 int qq(int x)
145 return x + 40;
147 #define qq(x) x
149 #define spin_lock(lock) do { } while (0)
150 #define wq_spin_lock spin_lock
151 #define TEST2() wq_spin_lock(a)
153 void macro_test(void)
155 pf("N=%d\n", N);
156 printf("aaa=%d\n", AAA);
158 printf("min=%d\n", min(1, min(2, -1)));
160 printf("s1=%s\n", glue(HIGH, LOW));
161 printf("s2=%s\n", xglue(HIGH, LOW));
162 printf("s3=%s\n", str("c"));
163 printf("s4=%s\n", str(a1));
164 printf("B3=%d\n", B3);
166 printf("onetwothree=%d\n", onetwothree);
168 #ifdef A
169 printf("A defined\n");
170 #endif
171 #ifdef B
172 printf("B defined\n");
173 #endif
174 #ifdef A
175 printf("A defined\n");
176 #else
177 printf("A not defined\n");
178 #endif
179 #ifdef B
180 printf("B defined\n");
181 #else
182 printf("B not defined\n");
183 #endif
185 #ifdef A
186 printf("A defined\n");
187 #ifdef B
188 printf("B1 defined\n");
189 #else
190 printf("B1 not defined\n");
191 #endif
192 #else
193 printf("A not defined\n");
194 #ifdef B
195 printf("B2 defined\n");
196 #else
197 printf("B2 not defined\n");
198 #endif
199 #endif
201 #if 1+1
202 printf("test true1\n");
203 #endif
204 #if 0
205 printf("test true2\n");
206 #endif
207 #if 1-1
208 printf("test true3\n");
209 #endif
210 #if defined(A)
211 printf("test trueA\n");
212 #endif
213 #if defined(B)
214 printf("test trueB\n");
215 #endif
217 #if 0
218 printf("test 0\n");
219 #elif 0
220 printf("test 1\n");
221 #elif 2
222 printf("test 2\n");
223 #else
224 printf("test 3\n");
225 #endif
227 MACRO_NOARGS();
229 printf("%d\n", TEST_CALL(TEST_CONST));
231 /* not strictly preprocessor, but we test it there */
232 #ifdef C99_MACROS
233 printf("__func__ = %s\n", __func__);
234 dprintf(1, "vaarg=%d\n", 1);
235 #endif
236 dprintf1(1, "vaarg1\n");
237 dprintf1(1, "vaarg1=%d\n", 2);
238 dprintf1(1, "vaarg1=%d %d\n", 1, 2);
240 /* gcc extension */
241 printf("func='%s'\n", __FUNCTION__);
243 /* complicated macros in glibc */
244 printf("INT64_MIN=" LONG_LONG_FORMAT "\n", INT64_MIN);
246 int a;
247 a = 1;
248 glue(a+, +);
249 printf("a=%d\n", a);
250 glue(a <, <= 2);
251 printf("a=%d\n", a);
254 /* macro function with argument outside the macro string */
255 #define MF_s MF_hello
256 #define MF_hello(msg) printf("%s\n",msg)
258 #define MF_t printf("tralala\n"); MF_hello
260 MF_s("hi");
261 MF_t("hi");
263 /* test macro substitution inside args (should not eat stream) */
264 printf("qq=%d\n", qq(qq)(2));
266 /* test zero argument case. NOTE: gcc 2.95.x does not accept a
267 null argument without a space. gcc 3.2 fixes that. */
269 #define qq1(x) 1
270 printf("qq1=%d\n", qq1( ));
272 /* comment with stray handling *\
274 /* this is a valid *\/ comment */
275 /* this is a valid comment *\*/
276 // this is a valid\
277 comment
279 /* test function macro substitution when the function name is
280 substituted */
281 TEST2();
283 /* And again when the name and parentheses are separated by a
284 comment. */
285 TEST2 /* the comment */ ();
287 printf("basefromheader %s\n", get_basefile_from_header());
288 printf("base %s\n", __BASE_FILE__);
290 /* Some compilers (clang) prepend './' to __FILE__ from included
291 files. */
292 const char *fn = get_file_from_header();
293 if (fn[0] == '.' && fn[1] == '/')
294 fn += 2;
295 printf("filefromheader %s\n", fn);
297 printf("file %s\n", __FILE__);
299 /* Check that funnily named include was in fact included */
300 have_included_42test_h = 1;
301 have_included_42test_h_second = 1;
302 have_included_42test_h_third = 1;
304 /* Check that we don't complain about stray \ here */
305 printf("print a backslash: %s\n", stringify(\\));
309 static void print_num(char *fn, int line, int num) {
310 printf("fn %s, line %d, num %d\n", fn, line, num);
313 void recursive_macro_test(void)
316 #define ELF32_ST_TYPE(val) ((val) & 0xf)
317 #define ELF32_ST_INFO(bind, type) (((bind) << 4) + ((type) & 0xf))
318 #define STB_WEAK 2 /* Weak symbol */
319 #define ELFW(type) ELF##32##_##type
320 printf("%d\n", ELFW(ST_INFO)(STB_WEAK, ELFW(ST_TYPE)(123)));
322 #define WRAP(x) x
324 #define print_num(x) print_num(__FILE__,__LINE__,x)
325 print_num(123);
326 WRAP(print_num(123));
327 WRAP(WRAP(print_num(123)));
329 static struct recursive_macro { int rm_field; } G;
330 #define rm_field (G.rm_field)
331 printf("rm_field = %d\n", rm_field);
332 printf("rm_field = %d\n", WRAP(rm_field));
333 WRAP((printf("rm_field = %d %d\n", rm_field, WRAP(rm_field))));
336 int op(a,b)
338 return a / b;
341 int ret(a)
343 if (a == 2)
344 return 1;
345 if (a == 3)
346 return 2;
347 return 0;
350 #if !defined(__TINYC__) && (__GNUC__ >= 8)
351 /* Old GCCs don't regard "foo"[1] as constant, even in GNU dialect. */
352 #define CONSTANTINDEXEDSTRLIT
353 #endif
354 char str_ag1[] = "b";
355 char str_ag2[] = { "b" };
356 /*char str_bg1[] = ("cccc"); GCC accepts this with pedantic warning, TCC not */
357 #ifdef CONSTANTINDEXEDSTRLIT
358 char str_ag3[] = { "ab"[1], 0 };
359 char str_x[2] = { "xy" "z"[2], 0 };
360 #endif
361 char *str_ar[] = { "one", "two" };
362 struct str_SS {unsigned char a[3], b; };
363 struct str_SS str_sinit15 = { "r" };
364 struct str_SS str_sinit16[] = { { "q" }, 2 };
366 static void string_test2()
368 char *p = "hello";
369 char a3[2] = { "p" };
370 char a4[2] = { "ab" "c"[2], 0 };
371 char *pa1 = "def" + 1;
372 char *pa2 = { "xyz" + 1 };
373 int i = 0;
374 struct str_SS ss = { { [0 ... 1] = 'a' }, 0 };
375 #ifndef CONSTANTINDEXEDSTRLIT
376 char str_ag3[] = { "ab"[1], 0 };
377 char str_x[2] = { "xy" "z"[2], 0 };
378 #endif
379 puts("string_test2");
380 puts(str_ag1);
381 puts(str_ag2);
382 /*puts(str_bg1);*/
383 puts(str_ag3);
384 puts(str_x);
385 puts(str_sinit15.a);
386 puts(str_sinit16[0].a);
387 puts(a3);
388 puts(a4);
389 puts(p);
390 puts("world");
391 printf("%s\n", "bla");
392 puts(str_ar[0]);
393 puts(str_ar[1]);
394 puts(ss.a);
395 puts(i >= 0 ? "one" : "two");
396 puts(pa1);
397 puts(pa2);
400 void ps(const char *s)
402 int c;
403 while (1) {
404 c = *s;
405 if (c == 0)
406 break;
407 printf("%c", c);
408 s++;
412 const char foo1_string[] = "\
413 bar\n\
414 test\14\
417 void string_test()
419 unsigned int b;
420 printf("string:\n");
421 printf("\141\1423\143\n");/* dezdez test */
422 printf("\x41\x42\x43\x3a\n");
423 printf("c=%c\n", 'r');
424 printf("wc=%C 0x%lx %C\n", L'a', L'\x1234', L'c');
425 printf("foo1_string='%s'\n", foo1_string);
426 #if 0
427 printf("wstring=%S\n", L"abc");
428 printf("wstring=%S\n", L"abc" L"def" "ghi");
429 printf("'\\377'=%d '\\xff'=%d\n", '\377', '\xff');
430 printf("L'\\377'=%d L'\\xff'=%d\n", L'\377', L'\xff');
431 #endif
432 ps("test\n");
433 b = 32;
434 while ((b = b + 1) < 96) {
435 printf("%c", b);
437 printf("\n");
438 printf("fib=%d\n", fib(33));
439 b = 262144;
440 while (b != 0x80000000) {
441 num(b);
442 b = b * 2;
444 string_test2();
448 void if1t(int n, int a, int b, int c)
450 if (a && b) printf("if1t: %d 1 %d %d\n", n, a, b);
451 if (a && !b) printf("if1t: %d 2 %d %d\n", n, a, b);
452 if (!a && b) printf("if1t: %d 3 %d %d\n", n, a, b);
453 if (!a && !b) printf("if1t: %d 4 %d %d\n", n, a, b);
454 if (a || b) printf("if1t: %d 5 %d %d\n", n, a, b);
455 if (a || !b) printf("if1t: %d 6 %d %d\n", n, a, b);
456 if (!a || b) printf("if1t: %d 7 %d %d\n", n, a, b);
457 if (!a || !b) printf("if1t: %d 8 %d %d\n", n, a, b);
458 if (a && b || c) printf("if1t: %d 9 %d %d %d\n", n, a, b, c);
459 if (a || b && c) printf("if1t: %d 10 %d %d %d\n", n, a, b, c);
460 if (a > b - 1 && c) printf("if1t: %d 11 %d %d %d\n", n, a, b, c);
461 if (a > b - 1 || c) printf("if1t: %d 12 %d %d %d\n", n, a, b, c);
462 if (a > 0 && 1) printf("if1t: %d 13 %d %d %d\n", n, a, b, c);
463 if (a > 0 || 0) printf("if1t: %d 14 %d %d %d\n", n, a, b, c);
466 void if2t(void)
468 if (0 && 1 || printf("if2t:ok\n") || 1)
469 printf("if2t:ok2\n");
470 printf("if2t:ok3\n");
473 void if3t(void)
475 volatile long long i = 1;
476 if (i <= 18446744073709551615ULL)
478 else
479 printf ("if3t:wrong 1\n");
482 void if_test(void)
484 if1t(1, 0, 0, 0);
485 if1t(2, 0, 3, 0);
486 if1t(3, 2, 0, 0);
487 if1t(4, 2, 3, 0);
488 if2t();
489 if3t();
492 void loop_test()
494 int i;
495 i = 0;
496 while (i < 10)
497 printf("%d", i++);
498 printf("\n");
499 for(i = 0; i < 10;i++)
500 printf("%d", i);
501 printf("\n");
502 i = 0;
503 do {
504 printf("%d", i++);
505 } while (i < 10);
506 printf("\n");
508 char count = 123;
509 /* c99 for loop init test */
510 for (size_t count = 1; count < 3; count++)
511 printf("count=%d\n", count);
512 printf("count = %d\n", count);
514 /* break/continue tests */
515 i = 0;
516 while (1) {
517 if (i == 6)
518 break;
519 i++;
520 if (i == 3)
521 continue;
522 printf("%d", i);
524 printf("\n");
526 /* break/continue tests */
527 i = 0;
528 do {
529 if (i == 6)
530 break;
531 i++;
532 if (i == 3)
533 continue;
534 printf("%d", i);
535 } while(1);
536 printf("\n");
538 for(i = 0;i < 10;i++) {
539 if (i == 3)
540 continue;
541 printf("%d", i);
543 printf("\n");
546 typedef int typedef_and_label;
548 void goto_test()
550 int i;
551 static void *label_table[3] = { &&label1, &&label2, &&label3 };
553 printf("\ngoto:\n");
554 i = 0;
555 /* This needs to parse as label, not as start of decl. */
556 typedef_and_label x;
557 typedef_and_label:
558 s_loop:
559 if (i >= 10)
560 goto s_end;
561 printf("%d", i);
562 i++;
563 goto s_loop;
564 s_end:
565 printf("\n");
567 /* we also test computed gotos (GCC extension) */
568 for(i=0;i<3;i++) {
569 goto *label_table[i];
570 label1:
571 printf("label1\n");
572 goto next;
573 label2:
574 printf("label2\n");
575 goto next;
576 label3:
577 printf("label3\n");
578 next: ;
582 enum {
584 E1 = 2,
585 E2 = 4,
590 enum test {
591 E5 = 1000,
594 struct S_enum {
595 enum {E6 = 42, E7, E8} e:8;
598 enum ELong {
599 /* This is either 0 on L32 machines, or a large number
600 on L64 machines. We should be able to store this. */
601 EL_large = ((unsigned long)0xf000 << 31) << 1,
604 enum { BIASU = -1U<<31 };
605 enum { BIASS = -1 << 31 };
607 static int getint(int i)
609 if (i)
610 return 0;
611 else
612 return (int)(-1U << 31);
615 void enum_test()
617 enum test b1;
618 /* The following should give no warning */
619 unsigned *p = &b1;
620 struct S_enum s = {E7};
621 printf("%d %d %d %d %d %d %d\n", s.e,
622 E0, E1, E2, E3, E4, E5);
623 b1 = 1;
624 printf("b1=%d\n", b1);
625 printf("enum large: %ld\n", EL_large);
627 if (getint(0) == BIASU)
628 printf("enum unsigned: ok\n");
629 else
630 printf("enum unsigned: wrong\n");
631 if (getint(0) == BIASS)
632 printf("enum unsigned: ok\n");
633 else
634 printf("enum unsigned: wrong\n");
637 typedef int *my_ptr;
639 typedef int mytype1;
640 typedef int mytype2;
642 void typedef_test()
644 my_ptr a;
645 mytype1 mytype2;
646 int b;
648 a = &b;
649 *a = 1234;
650 printf("a=%d\n", *a);
651 mytype2 = 2;
652 printf("mytype2=%d\n", mytype2);
655 void forward_test()
657 forward_ref();
658 forward_ref();
662 void forward_ref(void)
664 printf("forward ok\n");
667 typedef struct struct1 {
668 int f1;
669 int f2, f3;
670 union union1 {
671 int v1;
672 int v2;
673 } u;
674 char str[3];
675 } struct1;
677 struct struct2 {
678 int a;
679 char b;
682 union union2 {
683 int w1;
684 int w2;
687 struct struct1 st1, st2;
689 struct empty_mem {
690 /* nothing */ ;
691 int x;
694 int tab[3];
695 int tab2[3][2];
697 int g;
699 void f1(g)
701 printf("g1=%d\n", g);
704 void scope_test()
706 g = 2;
707 f1(1);
708 printf("g2=%d\n", g);
710 int g;
711 g = 3;
712 printf("g3=%d\n", g);
714 int g;
715 g = 4;
716 printf("g4=%d\n", g);
719 printf("g5=%d\n", g);
722 int st2_i;
723 int *st2_p = &st2_i;
724 void scope2_test()
726 char a[50];
727 st2_i = 42;
728 for (int st2_i = 1; st2_i < 10; st2_i++) {
729 extern int st2_i;
730 st2_i++;
731 printf("exloc: %d\n", st2_i);
733 printf("exloc: %d\n", *st2_p);
736 /* C has tentative definition, and they may be repeated. */
737 extern int st_global1;
738 int st_global1=42;
739 extern int st_global1;
740 int st_global1;
741 extern int st_global2;
742 int st_global2;
743 extern int st_global2;
744 int st_global2;
746 void array_test()
748 int i, j, a[4];
750 printf("sizeof(a) = %d\n", sizeof(a));
751 printf("sizeof(\"a\") = %d\n", sizeof("a"));
752 #ifdef C99_MACROS
753 printf("sizeof(__func__) = %d\n", sizeof(__func__));
754 #endif
755 printf("sizeof tab %d\n", sizeof(tab));
756 printf("sizeof tab2 %d\n", sizeof tab2);
757 tab[0] = 1;
758 tab[1] = 2;
759 tab[2] = 3;
760 printf("%d %d %d\n", tab[0], tab[1], tab[2]);
761 for(i=0;i<3;i++)
762 for(j=0;j<2;j++)
763 tab2[i][j] = 10 * i + j;
764 for(i=0;i<3*2;i++) {
765 printf(" %3d", ((int *)tab2)[i]);
767 printf("\n");
768 printf("sizeof(size_t)=%d\n", sizeof(size_t));
769 printf("sizeof(ptrdiff_t)=%d\n", sizeof(ptrdiff_t));
772 void expr_test()
774 int a, b;
775 a = 0;
776 printf("%d\n", a += 1);
777 printf("%d\n", a -= 2);
778 printf("%d\n", a *= 31232132);
779 printf("%d\n", a /= 4);
780 printf("%d\n", a %= 20);
781 printf("%d\n", a &= 6);
782 printf("%d\n", a ^= 7);
783 printf("%d\n", a |= 8);
784 printf("%d\n", a >>= 3);
785 printf("%d\n", a <<= 4);
787 a = 22321;
788 b = -22321;
789 printf("%d\n", a + 1);
790 printf("%d\n", a - 2);
791 printf("%d\n", a * 312);
792 printf("%d\n", a / 4);
793 printf("%d\n", b / 4);
794 printf("%d\n", (unsigned)b / 4);
795 printf("%d\n", a % 20);
796 printf("%d\n", b % 20);
797 printf("%d\n", (unsigned)b % 20);
798 printf("%d\n", a & 6);
799 printf("%d\n", a ^ 7);
800 printf("%d\n", a | 8);
801 printf("%d\n", a >> 3);
802 printf("%d\n", b >> 3);
803 printf("%d\n", (unsigned)b >> 3);
804 printf("%d\n", a << 4);
805 printf("%d\n", ~a);
806 printf("%d\n", -a);
807 printf("%d\n", +a);
809 printf("%d\n", 12 + 1);
810 printf("%d\n", 12 - 2);
811 printf("%d\n", 12 * 312);
812 printf("%d\n", 12 / 4);
813 printf("%d\n", 12 % 20);
814 printf("%d\n", 12 & 6);
815 printf("%d\n", 12 ^ 7);
816 printf("%d\n", 12 | 8);
817 printf("%d\n", 12 >> 2);
818 printf("%d\n", 12 << 4);
819 printf("%d\n", ~12);
820 printf("%d\n", -12);
821 printf("%d\n", +12);
822 printf("%d %d %d %d\n",
823 isid('a'),
824 isid('g'),
825 isid('T'),
826 isid('('));
829 int isid(int c)
831 return (c >= 'a' & c <= 'z') | (c >= 'A' & c <= 'Z') | c == '_';
834 /**********************/
836 int vstack[10], *vstack_ptr;
838 void vpush(int vt, int vc)
840 *vstack_ptr++ = vt;
841 *vstack_ptr++ = vc;
844 void vpop(int *ft, int *fc)
846 *fc = *--vstack_ptr;
847 *ft = *--vstack_ptr;
850 void expr2_test()
852 int a, b;
854 vstack_ptr = vstack;
855 vpush(1432432, 2);
856 vstack_ptr[-2] &= ~0xffffff80;
857 vpop(&a, &b);
858 printf("res= %d %d\n", a, b);
861 int const_len_ar[sizeof(1/0)]; /* div-by-zero, but in unevaluated context */
863 void constant_expr_test()
865 int a;
866 a = 3;
867 printf("%d\n", a * 16);
868 printf("%d\n", a * 1);
869 printf("%d\n", a + 0);
870 printf("%d\n", sizeof(const_len_ar));
873 int tab4[10];
875 void expr_ptr_test()
877 int *p, *q;
878 int i = -1;
880 p = tab4;
881 q = tab4 + 10;
882 printf("diff=%d\n", q - p);
883 p++;
884 printf("inc=%d\n", p - tab4);
885 p--;
886 printf("dec=%d\n", p - tab4);
887 ++p;
888 printf("inc=%d\n", p - tab4);
889 --p;
890 printf("dec=%d\n", p - tab4);
891 printf("add=%d\n", p + 3 - tab4);
892 printf("add=%d\n", 3 + p - tab4);
894 /* check if 64bit support is ok */
895 q = p = 0;
896 q += i;
897 printf("%p %p %ld\n", q, p, p-q);
898 printf("%d %d %d %d %d %d\n",
899 p == q, p != q, p < q, p <= q, p >= q, p > q);
900 i = 0xf0000000;
901 p += i;
902 printf("%p %p %ld\n", q, p, p-q);
903 printf("%d %d %d %d %d %d\n",
904 p == q, p != q, p < q, p <= q, p >= q, p > q);
905 p = (int *)((char *)p + 0xf0000000);
906 printf("%p %p %ld\n", q, p, p-q);
907 printf("%d %d %d %d %d %d\n",
908 p == q, p != q, p < q, p <= q, p >= q, p > q);
909 p += 0xf0000000;
910 printf("%p %p %ld\n", q, p, p-q);
911 printf("%d %d %d %d %d %d\n",
912 p == q, p != q, p < q, p <= q, p >= q, p > q);
914 struct size12 {
915 int i, j, k;
917 struct size12 s[2], *sp = s;
918 int i, j;
919 sp->i = 42;
920 sp++;
921 j = -1;
922 printf("%d\n", sp[j].i);
924 #ifdef __LP64__
925 i = 1;
926 p = (int*)0x100000000UL + i;
927 i = ((long)p) >> 32;
928 printf("largeptr: %p %d\n", p, i);
929 #endif
932 void expr_cmp_test()
934 int a, b;
935 a = -1;
936 b = 1;
937 printf("%d\n", a == a);
938 printf("%d\n", a != a);
940 printf("%d\n", a < b);
941 printf("%d\n", a <= b);
942 printf("%d\n", a <= a);
943 printf("%d\n", b >= a);
944 printf("%d\n", a >= a);
945 printf("%d\n", b > a);
947 printf("%d\n", (unsigned)a < b);
948 printf("%d\n", (unsigned)a <= b);
949 printf("%d\n", (unsigned)a <= a);
950 printf("%d\n", (unsigned)b >= a);
951 printf("%d\n", (unsigned)a >= a);
952 printf("%d\n", (unsigned)b > a);
955 struct empty {
958 struct aligntest1 {
959 char a[10];
962 struct aligntest2 {
963 int a;
964 char b[10];
967 struct aligntest3 {
968 double a, b;
971 struct aligntest4 {
972 double a[0];
975 struct __attribute__((aligned(16))) aligntest5
977 int i;
979 struct aligntest6
981 int i;
982 } __attribute__((aligned(16)));
983 struct aligntest7
985 int i;
987 struct aligntest5 altest5[2];
988 struct aligntest6 altest6[2];
989 int pad1;
990 /* altest7 is correctly aligned to 16 bytes also with TCC,
991 but __alignof__ returns the wrong result (4) because we
992 can't store the alignment yet when specified on symbols
993 directly (it's stored in the type so we'd need to make
994 a copy of it). -- FIXED */
995 struct aligntest7 altest7[2] __attribute__((aligned(16)));
997 struct aligntest8
999 int i;
1000 } __attribute__((aligned(4096)));
1002 struct Large {
1003 unsigned long flags;
1004 union {
1005 void *u1;
1006 int *u2;
1009 struct {
1010 union {
1011 unsigned long index;
1012 void *freelist;
1014 union {
1015 unsigned long counters;
1016 struct {
1017 int bla;
1022 union {
1023 struct {
1024 long u3;
1025 long u4;
1027 void *u5;
1028 struct {
1029 unsigned long compound_head;
1030 unsigned int compound_dtor;
1031 unsigned int compound_order;
1034 } __attribute__((aligned(2 * sizeof(long))));
1036 typedef unsigned long long __attribute__((aligned(4))) unaligned_u64;
1038 struct aligntest9 {
1039 unsigned int buf_nr;
1040 unaligned_u64 start_lba;
1043 struct aligntest10 {
1044 unsigned int buf_nr;
1045 unsigned long long start_lba;
1048 void struct_test()
1050 struct1 *s;
1051 union union2 u;
1052 struct Large ls;
1054 printf("sizes: %d %d %d %d\n",
1055 sizeof(struct struct1),
1056 sizeof(struct struct2),
1057 sizeof(union union1),
1058 sizeof(union union2));
1059 printf("offsets: %d\n", (int)((char*)&st1.u.v1 - (char*)&st1));
1060 st1.f1 = 1;
1061 st1.f2 = 2;
1062 st1.f3 = 3;
1063 printf("st1: %d %d %d\n",
1064 st1.f1, st1.f2, st1.f3);
1065 st1.u.v1 = 1;
1066 st1.u.v2 = 2;
1067 printf("union1: %d\n", st1.u.v1);
1068 u.w1 = 1;
1069 u.w2 = 2;
1070 printf("union2: %d\n", u.w1);
1071 s = &st2;
1072 s->f1 = 3;
1073 s->f2 = 2;
1074 s->f3 = 1;
1075 printf("st2: %d %d %d\n",
1076 s->f1, s->f2, s->f3);
1077 printf("str_addr=%x\n", (int)(uintptr_t)st1.str - (int)(uintptr_t)&st1.f1);
1079 /* align / size tests */
1080 printf("aligntest1 sizeof=%d alignof=%d\n",
1081 sizeof(struct aligntest1), __alignof__(struct aligntest1));
1082 printf("aligntest2 sizeof=%d alignof=%d\n",
1083 sizeof(struct aligntest2), __alignof__(struct aligntest2));
1084 printf("aligntest3 sizeof=%d alignof=%d\n",
1085 sizeof(struct aligntest3), __alignof__(struct aligntest3));
1086 printf("aligntest4 sizeof=%d alignof=%d\n",
1087 sizeof(struct aligntest4), __alignof__(struct aligntest4));
1088 printf("aligntest5 sizeof=%d alignof=%d\n",
1089 sizeof(struct aligntest5), __alignof__(struct aligntest5));
1090 printf("aligntest6 sizeof=%d alignof=%d\n",
1091 sizeof(struct aligntest6), __alignof__(struct aligntest6));
1092 printf("aligntest7 sizeof=%d alignof=%d\n",
1093 sizeof(struct aligntest7), __alignof__(struct aligntest7));
1094 printf("aligntest8 sizeof=%d alignof=%d\n",
1095 sizeof(struct aligntest8), __alignof__(struct aligntest8));
1096 printf("aligntest9 sizeof=%d alignof=%d\n",
1097 sizeof(struct aligntest9), __alignof__(struct aligntest9));
1098 printf("aligntest10 sizeof=%d alignof=%d\n",
1099 sizeof(struct aligntest10), __alignof__(struct aligntest10));
1100 printf("altest5 sizeof=%d alignof=%d\n",
1101 sizeof(altest5), __alignof__(altest5));
1102 printf("altest6 sizeof=%d alignof=%d\n",
1103 sizeof(altest6), __alignof__(altest6));
1104 printf("altest7 sizeof=%d alignof=%d\n",
1105 sizeof(altest7), __alignof__(altest7));
1107 /* empty structures (GCC extension) */
1108 printf("sizeof(struct empty) = %d\n", sizeof(struct empty));
1109 printf("alignof(struct empty) = %d\n", __alignof__(struct empty));
1111 printf("Large: sizeof=%d\n", sizeof(ls));
1112 memset(&ls, 0, sizeof(ls));
1113 ls.compound_head = 42;
1114 printf("Large: offsetof(compound_head)=%d\n", (int)((char*)&ls.compound_head - (char*)&ls));
1117 /* simulate char/short return value with undefined upper bits */
1118 static int __csf(int x) { return x; }
1119 static void *_csf = __csf;
1120 #define csf(t,n) ((t(*)(int))_csf)(n)
1122 /* XXX: depend on endianness */
1123 void char_short_test()
1125 int var1, var2;
1126 signed char var3;
1127 long long var4;
1129 var1 = 0x01020304;
1130 var2 = 0xfffefdfc;
1131 printf("s8=%d %d\n",
1132 *(signed char *)&var1, *(signed char *)&var2);
1133 printf("u8=%d %d\n",
1134 *(unsigned char *)&var1, *(unsigned char *)&var2);
1135 printf("s16=%d %d\n",
1136 *(short *)&var1, *(short *)&var2);
1137 printf("u16=%d %d\n",
1138 *(unsigned short *)&var1, *(unsigned short *)&var2);
1139 printf("s32=%d %d\n",
1140 *(int *)&var1, *(int *)&var2);
1141 printf("u32=%d %d\n",
1142 *(unsigned int *)&var1, *(unsigned int *)&var2);
1143 *(signed char *)&var1 = 0x08;
1144 printf("var1=%x\n", var1);
1145 *(short *)&var1 = 0x0809;
1146 printf("var1=%x\n", var1);
1147 *(int *)&var1 = 0x08090a0b;
1148 printf("var1=%x\n", var1);
1150 var1 = 0x778899aa;
1151 var4 = 0x11223344aa998877ULL;
1152 var1 = var3 = var1 + 1;
1153 var4 = var3 = var4 + 1;
1154 printf("promote char/short assign %d "LONG_LONG_FORMAT"\n", var1, var4);
1155 var1 = 0x778899aa;
1156 var4 = 0x11223344aa998877ULL;
1157 printf("promote char/short assign VA %d %d\n", var3 = var1 + 1, var3 = var4 + 1);
1158 printf("promote char/short cast VA %d %d\n", (signed char)(var1 + 1), (signed char)(var4 + 1));
1159 #if !defined(__arm__)
1160 /* We can't really express GCC behaviour of return type promotion in
1161 the presence of undefined behaviour (like __csf is). */
1162 var1 = csf(unsigned char,0x89898989);
1163 var4 = csf(signed char,0xabababab);
1164 printf("promote char/short funcret %d "LONG_LONG_FORMAT"\n", var1, var4);
1165 printf("promote char/short fumcret VA %d %d %d %d\n",
1166 csf(unsigned short,0xcdcdcdcd),
1167 csf(short,0xefefefef),
1168 csf(_Bool,0x33221100),
1169 csf(_Bool,0x33221101));
1170 #endif
1171 var3 = -10;
1172 var1 = (signed char)(unsigned char)(var3 + 1);
1173 var4 = (signed char)(unsigned char)(var3 + 1);
1174 printf("promote multicast (char)(unsigned char) %d "LONG_LONG_FORMAT"\n", var1, var4);
1175 var4 = 0x11223344aa998877ULL;
1176 var4 = (unsigned)(int)(var4 + 1);
1177 printf("promote multicast (unsigned)(int) "LONG_LONG_FORMAT"\n", var4);
1178 var4 = 0x11223344bbaa9988ULL;
1179 var4 = (unsigned)(signed char)(var4 + 1);
1180 printf("promote multicast (unsigned)(char) "LONG_LONG_FORMAT"\n", var4);
1183 /******************/
1185 typedef struct Sym {
1186 int v;
1187 int t;
1188 int c;
1189 struct Sym *next;
1190 struct Sym *prev;
1191 } Sym;
1193 #define ISLOWER(c) ('a' <= (c) && (c) <= 'z')
1194 #define TOUPPER(c) (ISLOWER(c) ? 'A' + ((c) - 'a') : (c))
1196 static int toupper1(int a)
1198 return TOUPPER(a);
1201 static unsigned int calc_vm_flags(unsigned int prot)
1203 unsigned int prot_bits;
1204 /* This used to segfault in some revisions: */
1205 prot_bits = ((0x1==0x00000001)?(prot&0x1):(prot&0x1)?0x00000001:0);
1206 return prot_bits;
1209 void bool_test()
1211 int *s, a, b, t, f, i;
1213 a = 0;
1214 s = (void*)0;
1215 printf("!s=%d\n", !s);
1217 if (!s || !s[0])
1218 a = 1;
1219 printf("a=%d\n", a);
1221 printf("a=%d %d %d\n", 0 || 0, 0 || 1, 1 || 1);
1222 printf("a=%d %d %d\n", 0 && 0, 0 && 1, 1 && 1);
1223 printf("a=%d %d\n", 1 ? 1 : 0, 0 ? 1 : 0);
1224 #if 1 && 1
1225 printf("a1\n");
1226 #endif
1227 #if 1 || 0
1228 printf("a2\n");
1229 #endif
1230 #if 1 ? 0 : 1
1231 printf("a3\n");
1232 #endif
1233 #if 0 ? 0 : 1
1234 printf("a4\n");
1235 #endif
1237 a = 4;
1238 printf("b=%d\n", a + (0 ? 1 : a / 2));
1240 /* test register spilling */
1241 a = 10;
1242 b = 10;
1243 a = (a + b) * ((a < b) ?
1244 ((b - a) * (a - b)): a + b);
1245 printf("a=%d\n", a);
1247 /* test complex || or && expressions */
1248 t = 1;
1249 f = 0;
1250 a = 32;
1251 printf("exp=%d\n", f == (32 <= a && a <= 3));
1252 printf("r=%d\n", (t || f) + (t && f));
1254 /* test ? : cast */
1256 int aspect_on;
1257 int aspect_native = 65536;
1258 double bfu_aspect = 1.0;
1259 int aspect;
1260 for(aspect_on = 0; aspect_on < 2; aspect_on++) {
1261 aspect=aspect_on?(aspect_native*bfu_aspect+0.5):65535UL;
1262 printf("aspect=%d\n", aspect);
1266 /* test ? : GCC extension */
1268 static int v1 = 34 ? : -1; /* constant case */
1269 static int v2 = 0 ? : -1; /* constant case */
1270 int a = 30;
1272 printf("%d %d\n", v1, v2);
1273 printf("%d %d\n", a - 30 ? : a * 2, a + 1 ? : a * 2);
1276 /* again complex expression */
1277 for(i=0;i<256;i++) {
1278 if (toupper1 (i) != TOUPPER (i))
1279 printf("error %d\n", i);
1281 printf ("bits = 0x%x\n", calc_vm_flags (0x1));
1284 extern int undefined_function(void);
1285 extern int defined_function(void);
1287 #ifdef __clang__
1288 int undefined_function(void) {}
1289 #endif
1291 static inline void refer_to_undefined(void)
1293 undefined_function();
1296 void optimize_out_test(void)
1298 int i = 0 ? undefined_function() : defined_function();
1299 printf ("oo:%d\n", i);
1300 int j = 1 ? defined_function() : undefined_function();
1301 printf ("oo:%d\n", j);
1302 if (0)
1303 printf("oo:%d\n", undefined_function());
1304 else
1305 printf("oo:%d\n", defined_function());
1306 if (1)
1307 printf("oo:%d\n", defined_function());
1308 else
1309 printf("oo:%d\n", undefined_function());
1310 while (1) {
1311 printf("oow:%d\n", defined_function());
1312 break;
1313 printf("oow:%d\n", undefined_function());
1315 j = 1;
1316 /* Following is a switch without {} block intentionally. */
1317 switch (j)
1318 case 1: break;
1319 printf ("oos:%d\n", defined_function());
1320 /* The following break shouldn't lead to disabled code after
1321 the while. */
1322 while (1)
1323 break;
1324 printf ("ool1:%d\n", defined_function());
1325 /* Same for the other types of loops. */
1327 break;
1328 while (1);
1329 printf ("ool2:%d\n", defined_function());
1330 for (;;)
1331 break;
1332 printf ("ool3:%d\n", defined_function());
1333 /* Normal {} blocks without controlling statements
1334 shouldn't reactivate code emission */
1335 while (1) {
1337 break;
1339 printf ("ool4:%d\n", undefined_function());
1341 j = 1;
1342 while (j) {
1343 if (j == 0)
1344 break; /* this break shouldn't disable code outside the if. */
1345 printf("ool5:%d\n", defined_function());
1346 j--;
1349 j = 1;
1350 while (j) {
1351 if (1)
1352 j--;
1353 else
1354 breakhere: break;
1355 printf("ool6:%d\n", defined_function());
1356 goto breakhere;
1358 j = 1;
1359 while (j) {
1360 j--;
1361 continue;
1362 printf("ool7:%d\n", undefined_function());
1365 /* Test that constants in logical && are optimized: */
1366 i = 0 && undefined_function();
1367 i = defined_function() && 0 && undefined_function();
1368 if (0 && undefined_function())
1369 undefined_function();
1370 if (defined_function() && 0)
1371 undefined_function();
1372 if (0 && 0)
1373 undefined_function();
1374 if (defined_function() && 0 && undefined_function())
1375 undefined_function();
1376 /* The same for || : */
1377 i = 1 || undefined_function();
1378 i = defined_function() || 1 || undefined_function();
1379 if (1 || undefined_function())
1381 else
1382 undefined_function();
1383 if (defined_function() || 1)
1385 else
1386 undefined_function();
1387 if (1 || 1)
1389 else
1390 undefined_function();
1391 if (defined_function() || 1 || undefined_function())
1393 else
1394 undefined_function();
1396 if (defined_function() && 0)
1397 refer_to_undefined();
1399 if (0) {
1400 (void)sizeof( ({
1401 do { } while (0);
1403 }) );
1404 undefined_function();
1407 /* Leave the "if(1)return; printf()" in this order and last in the function */
1408 if (1)
1409 return;
1410 printf ("oor:%d\n", undefined_function());
1413 int defined_function(void)
1415 static int i = 40;
1416 return i++;
1419 /* GCC accepts that */
1420 static int tab_reinit[];
1421 static int tab_reinit[10];
1423 static int tentative_ar[];
1424 static int tentative_ar[] = {1,2,3};
1426 //int cinit1; /* a global variable can be defined several times without error ! */
1427 int cinit1;
1428 int cinit1;
1429 int cinit1 = 0;
1430 int *cinit2 = (int []){3, 2, 1};
1432 void compound_literal_test(void)
1434 int *p, i;
1435 char *q, *q3;
1437 p = (int []){1, 2, 3};
1438 for(i=0;i<3;i++)
1439 printf(" %d", p[i]);
1440 printf("\n");
1442 for(i=0;i<3;i++)
1443 printf("%d", cinit2[i]);
1444 printf("\n");
1446 q = "tralala1";
1447 printf("q1=%s\n", q);
1449 q = (char *){ "tralala2" };
1450 printf("q2=%s\n", q);
1452 q3 = (char *){ q };
1453 printf("q3=%s\n", q3);
1455 q = (char []){ "tralala3" };
1456 printf("q4=%s\n", q);
1458 #ifdef ALL_ISOC99
1459 p = (int []){1, 2, cinit1 + 3};
1460 for(i=0;i<3;i++)
1461 printf(" %d", p[i]);
1462 printf("\n");
1464 for(i=0;i<3;i++) {
1465 p = (int []){1, 2, 4 + i};
1466 printf("%d %d %d\n",
1467 p[0],
1468 p[1],
1469 p[2]);
1471 #endif
1474 /* K & R protos */
1476 kr_func1(a, b)
1478 return a + b;
1481 int kr_func2(a, b)
1483 return a + b;
1486 kr_test()
1488 printf("func1=%d\n", kr_func1(3, 4));
1489 printf("func2=%d\n", kr_func2(3, 4));
1490 return 0;
1493 void num(int n)
1495 char *tab, *p;
1496 tab = (char*)malloc(20);
1497 p = tab;
1498 while (1) {
1499 *p = 48 + (n % 10);
1500 p++;
1501 n = n / 10;
1502 if (n == 0)
1503 break;
1505 while (p != tab) {
1506 p--;
1507 printf("%c", *p);
1509 printf("\n");
1510 free(tab);
1513 /* structure assignment tests */
1514 struct structa1 {
1515 int f1;
1516 char f2;
1519 struct structa1 ssta1;
1521 void struct_assign_test1(struct structa1 s1, int t, float f)
1523 printf("%d %d %d %f\n", s1.f1, s1.f2, t, f);
1526 struct structa1 struct_assign_test2(struct structa1 s1, int t)
1528 s1.f1 += t;
1529 s1.f2 -= t;
1530 return s1;
1533 void struct_assign_test(void)
1535 struct S {
1536 struct structa1 lsta1, lsta2;
1537 int i;
1538 } s, *ps;
1540 ps = &s;
1541 ps->i = 4;
1542 #if 0
1543 s.lsta1.f1 = 1;
1544 s.lsta1.f2 = 2;
1545 printf("%d %d\n", s.lsta1.f1, s.lsta1.f2);
1546 s.lsta2 = s.lsta1;
1547 printf("%d %d\n", s.lsta2.f1, s.lsta2.f2);
1548 #else
1549 s.lsta2.f1 = 1;
1550 s.lsta2.f2 = 2;
1551 #endif
1552 struct_assign_test1(ps->lsta2, 3, 4.5);
1554 printf("before call: %d %d\n", s.lsta2.f1, s.lsta2.f2);
1555 ps->lsta2 = struct_assign_test2(ps->lsta2, ps->i);
1556 printf("after call: %d %d\n", ps->lsta2.f1, ps->lsta2.f2);
1558 static struct {
1559 void (*elem)();
1560 } t[] = {
1561 /* XXX: we should allow this even without braces */
1562 { struct_assign_test }
1564 printf("%d\n", struct_assign_test == t[0].elem);
1567 /* casts to short/char */
1569 void cast1(char a, short b, unsigned char c, unsigned short d)
1571 printf("%d %d %d %d\n", a, b, c, d);
1574 char bcast;
1575 short scast;
1577 void cast_test()
1579 int a;
1580 char c;
1581 char tab[10];
1582 unsigned b,d;
1583 short s;
1584 char *p = NULL;
1585 unsigned long ul = 0x80000000UL;
1586 p -= 0x700000000042;
1588 a = 0xfffff;
1589 cast1(a, a, a, a);
1590 a = 0xffffe;
1591 printf("%d %d %d %d\n",
1592 (char)(a + 1),
1593 (short)(a + 1),
1594 (unsigned char)(a + 1),
1595 (unsigned short)(a + 1));
1596 printf("%d %d %d %d\n",
1597 (char)0xfffff,
1598 (short)0xfffff,
1599 (unsigned char)0xfffff,
1600 (unsigned short)0xfffff);
1602 a = (bcast = 128) + 1;
1603 printf("%d\n", a);
1604 a = (scast = 65536) + 1;
1605 printf("%d\n", a);
1607 printf("sizeof(c) = %d, sizeof((int)c) = %d\n", sizeof(c), sizeof((int)c));
1609 /* test cast from unsigned to signed short to int */
1610 b = 0xf000;
1611 d = (short)b;
1612 printf("((unsigned)(short)0x%08x) = 0x%08x\n", b, d);
1613 b = 0xf0f0;
1614 d = (char)b;
1615 printf("((unsigned)(char)0x%08x) = 0x%08x\n", b, d);
1617 /* test implicit int casting for array accesses */
1618 c = 0;
1619 tab[1] = 2;
1620 tab[c] = 1;
1621 printf("%d %d\n", tab[0], tab[1]);
1623 /* test implicit casting on some operators */
1624 printf("sizeof(+(char)'a') = %d\n", sizeof(+(char)'a'));
1625 printf("sizeof(-(char)'a') = %d\n", sizeof(-(char)'a'));
1626 printf("sizeof(~(char)'a') = %d\n", sizeof(-(char)'a'));
1628 #if CC_NAME != CC_clang /* clang doesn't support non-portable conversions */
1629 /* from pointer to integer types */
1630 printf("%d %d %ld %ld %lld %lld\n",
1631 (int)p, (unsigned int)p,
1632 (long)p, (unsigned long)p,
1633 (long long)p, (unsigned long long)p);
1634 #endif
1636 /* from integers to pointers */
1637 printf("%p %p %p %p\n",
1638 (void *)a, (void *)b, (void *)c, (void *)d);
1640 /* int to int with sign set */
1641 printf("0x%lx\n", (unsigned long)(int)ul);
1644 /* initializers tests */
1645 struct structinit1 {
1646 int f1;
1647 char f2;
1648 short f3;
1649 int farray[3];
1652 int sinit1 = 2;
1653 int sinit2 = { 3 };
1654 int sinit3[3] = { 1, 2, {{3}}, };
1655 int sinit4[3][2] = { {1, 2}, {3, 4}, {5, 6} };
1656 int sinit5[3][2] = { 1, 2, 3, 4, 5, 6 };
1657 int sinit6[] = { 1, 2, 3 };
1658 int sinit7[] = { [2] = 3, [0] = 1, 2 };
1659 char sinit8[] = "hello" "trala";
1661 struct structinit1 sinit9 = { 1, 2, 3 };
1662 struct structinit1 sinit10 = { .f2 = 2, 3, .f1 = 1 };
1663 struct structinit1 sinit11 = { .f2 = 2, 3, .f1 = 1,
1664 #ifdef ALL_ISOC99
1665 .farray[0] = 10,
1666 .farray[1] = 11,
1667 .farray[2] = 12,
1668 #endif
1671 char *sinit12 = "hello world";
1672 char *sinit13[] = {
1673 "test1",
1674 "test2",
1675 "test3",
1677 char sinit14[10] = { "abc" };
1678 int sinit15[3] = { sizeof(sinit15), 1, 2 };
1680 struct { int a[3], b; } sinit16[] = { { 1 }, 2 };
1682 struct bar {
1683 char *s;
1684 int len;
1685 } sinit17[] = {
1686 "a1", 4,
1687 "a2", 1
1690 int sinit18[10] = {
1691 [2 ... 5] = 20,
1693 [8] = 10,
1696 struct complexinit0 {
1697 int a;
1698 int b;
1701 struct complexinit {
1702 int a;
1703 const struct complexinit0 *b;
1706 const static struct complexinit cix[] = {
1707 [0] = {
1708 .a = 2000,
1709 .b = (const struct complexinit0[]) {
1710 { 2001, 2002 },
1711 { 2003, 2003 },
1717 struct complexinit2 {
1718 int a;
1719 int b[];
1722 struct complexinit2 cix20;
1724 struct complexinit2 cix21 = {
1725 .a = 3000,
1726 .b = { 3001, 3002, 3003 }
1729 struct complexinit2 cix22 = {
1730 .a = 4000,
1731 .b = { 4001, 4002, 4003, 4004, 4005, 4006 }
1734 typedef int arrtype1[];
1735 arrtype1 sinit19 = {1};
1736 arrtype1 sinit20 = {2,3};
1737 typedef int arrtype2[3];
1738 arrtype2 sinit21 = {4};
1739 arrtype2 sinit22 = {5,6,7};
1741 /* Address comparisons of non-weak symbols with zero can be const-folded */
1742 int sinit23[2] = { "astring" ? sizeof("astring") : -1,
1743 &sinit23 ? 42 : -1 };
1745 int sinit24 = 2 || 1 / 0; /* exception in constant but unevaluated context */
1747 /* bitfield init */
1748 struct bf_SS {unsigned int bit:1,bits31:31; };
1749 struct bf_SS bf_init = { .bit = 1 };
1750 struct bfn_SS {int a,b; struct bf_SS c; int d,e; };
1751 struct bfn_SS bfn_init = { .c.bit = 1 };
1752 struct bfa_SS {int a,b; struct bf_SS c[3]; int d,e; };
1753 struct bfa_SS bfa_init = { .c[1].bit = 1 };
1754 struct bf_SS bfaa_init[3] = { [1].bit = 1 };
1755 struct bf_SS bfaa_vinit[] = { [2].bit = 1 };
1756 struct b2_SS {long long int field : 52; long long int pad : 12; };
1757 struct b2_SS bf_init2 = {0xFFF000FFF000FLL, 0x123};
1759 extern int external_inited = 42;
1761 void init_test(void)
1763 int linit1 = 2;
1764 int linit2 = { 3 };
1765 int linit4[3][2] = { {1, 2}, {3, 4}, {5, 6} };
1766 int linit6[] = { 1, 2, 3 };
1767 int i, j;
1768 char linit8[] = "hello" "trala";
1769 int linit12[10] = { 1, 2 };
1770 int linit13[10] = { 1, 2, [7] = 3, [3] = 4, };
1771 char linit14[10] = "abc";
1772 int linit15[10] = { linit1, linit1 + 1, [6] = linit1 + 2, };
1773 struct linit16 { int a1, a2, a3, a4; } linit16 = { 1, .a3 = 2 };
1774 int linit17 = sizeof(linit17);
1775 int zero = 0;
1776 /* Addresses on non-weak symbols are non-zero, but not the access itself */
1777 int linit18[2] = {&zero ? 1 : -1, zero ? -1 : 1 };
1778 struct bf_SS bf_finit = { .bit = 1 };
1779 struct bfn_SS bfn_finit = { .c.bit = 1 };
1780 struct bfa_SS bfa_finit = { .c[1].bit = 1 };
1781 struct bf_SS bfaa_finit[3] = { [1].bit = 1 };
1782 struct bf_SS bfaa_fvinit[] = { [2].bit = 1 };
1783 struct b2_SS bf_finit2 = {0xFFF000FFF000FLL, 0x123};
1785 printf("sinit1=%d\n", sinit1);
1786 printf("sinit2=%d\n", sinit2);
1787 printf("sinit3=%d %d %d %d\n",
1788 sizeof(sinit3),
1789 sinit3[0],
1790 sinit3[1],
1791 sinit3[2]
1793 printf("sinit6=%d\n", sizeof(sinit6));
1794 printf("sinit7=%d %d %d %d\n",
1795 sizeof(sinit7),
1796 sinit7[0],
1797 sinit7[1],
1798 sinit7[2]
1800 printf("sinit8=%s\n", sinit8);
1801 printf("sinit9=%d %d %d\n",
1802 sinit9.f1,
1803 sinit9.f2,
1804 sinit9.f3
1806 printf("sinit10=%d %d %d\n",
1807 sinit10.f1,
1808 sinit10.f2,
1809 sinit10.f3
1811 printf("sinit11=%d %d %d %d %d %d\n",
1812 sinit11.f1,
1813 sinit11.f2,
1814 sinit11.f3,
1815 sinit11.farray[0],
1816 sinit11.farray[1],
1817 sinit11.farray[2]
1820 for(i=0;i<3;i++)
1821 for(j=0;j<2;j++)
1822 printf("[%d][%d] = %d %d %d\n",
1823 i, j, sinit4[i][j], sinit5[i][j], linit4[i][j]);
1824 printf("linit1=%d\n", linit1);
1825 printf("linit2=%d\n", linit2);
1826 printf("linit6=%d\n", sizeof(linit6));
1827 printf("linit8=%d %s\n", sizeof(linit8), linit8);
1829 printf("sinit12=%s\n", sinit12);
1830 printf("sinit13=%d %s %s %s\n",
1831 sizeof(sinit13),
1832 sinit13[0],
1833 sinit13[1],
1834 sinit13[2]);
1835 printf("sinit14=%s\n", sinit14);
1837 for(i=0;i<10;i++) printf(" %d", linit12[i]);
1838 printf("\n");
1839 for(i=0;i<10;i++) printf(" %d", linit13[i]);
1840 printf("\n");
1841 for(i=0;i<10;i++) printf(" %d", linit14[i]);
1842 printf("\n");
1843 for(i=0;i<10;i++) printf(" %d", linit15[i]);
1844 printf("\n");
1845 printf("%d %d %d %d\n",
1846 linit16.a1,
1847 linit16.a2,
1848 linit16.a3,
1849 linit16.a4);
1850 /* test that initialisation is done after variable declare */
1851 printf("linit17=%d\n", linit17);
1852 printf("sinit15=%d\n", sinit15[0]);
1853 printf("sinit16=%d %d\n", sinit16[0].a[0], sinit16[1].a[0]);
1854 printf("sinit17=%s %d %s %d\n",
1855 sinit17[0].s, sinit17[0].len,
1856 sinit17[1].s, sinit17[1].len);
1857 for(i=0;i<10;i++)
1858 printf("%x ", sinit18[i]);
1859 printf("\n");
1860 /* complex init check */
1861 printf("cix: %d %d %d %d %d %d %d\n",
1862 cix[0].a,
1863 cix[0].b[0].a, cix[0].b[0].b,
1864 cix[0].b[1].a, cix[0].b[1].b,
1865 cix[0].b[2].a, cix[0].b[2].b);
1866 printf("cix2: %d %d\n", cix21.b[2], cix22.b[5]);
1867 printf("sizeof cix20 %d, cix21 %d, sizeof cix22 %d\n", sizeof cix20, sizeof cix21, sizeof cix22);
1869 printf("arrtype1: %d %d %d\n", sinit19[0], sinit20[0], sinit20[1]);
1870 printf("arrtype2: %d %d\n", sizeof(sinit19), sizeof(sinit20));
1871 printf("arrtype3: %d %d %d\n", sinit21[0], sinit21[1], sinit21[2]);
1872 printf("arrtype4: %d %d %d\n", sinit22[0], sinit22[1], sinit22[2]);
1873 printf("arrtype5: %d %d\n", sizeof(sinit21), sizeof(sinit22));
1874 printf("arrtype6: %d\n", sizeof(arrtype2));
1876 printf("sinit23= %d %d\n", sinit23[0], sinit23[1]);
1877 printf("sinit24=%d\n", sinit24);
1878 printf("linit18= %d %d\n", linit18[0], linit18[1]);
1879 printf ("bf1: %u %u\n", bf_init.bit, bf_init.bits31);
1880 printf ("bf2: %u %u\n", bf_finit.bit, bf_finit.bits31);
1881 printf ("bf3: %u %u\n", bfn_init.c.bit, bfn_init.c.bits31);
1882 printf ("bf4: %u %u\n", bfn_finit.c.bit, bfn_finit.c.bits31);
1883 for (i = 0; i < 3; i++)
1884 printf ("bf5[%d]: %u %u\n", i, bfa_init.c[i].bit, bfa_init.c[i].bits31);
1885 for (i = 0; i < 3; i++)
1886 printf ("bf6[%d]: %u %u\n", i, bfa_finit.c[i].bit, bfa_finit.c[i].bits31);
1887 for (i = 0; i < 3; i++)
1888 printf ("bf7[%d]: %u %u\n", i, bfaa_init[i].bit, bfaa_init[i].bits31);
1889 for (i = 0; i < 3; i++)
1890 printf ("bf8[%d]: %u %u\n", i, bfaa_finit[i].bit, bfaa_finit[i].bits31);
1891 for (i = 0; i < 3; i++)
1892 printf ("bf9[%d]: %u %u\n", i, bfaa_vinit[i].bit, bfaa_vinit[i].bits31);
1893 for (i = 0; i < 3; i++)
1894 printf ("bf10[%d]: %u %u\n", i, bfaa_fvinit[i].bit, bfaa_fvinit[i].bits31);
1897 void switch_uc(unsigned char uc)
1899 switch (uc) {
1900 case 0xfb ... 0xfe:
1901 printf("ucsw:1\n");
1902 break;
1903 case 0xff:
1904 printf("ucsw:2\n");
1905 break;
1906 case 0 ... 5:
1907 printf("ucsw:3\n");
1908 break;
1909 default:
1910 printf("ucsw: broken!\n");
1914 void switch_sc(signed char sc)
1916 switch (sc) {
1917 case -5 ... -2:
1918 printf("scsw:1\n");
1919 break;
1920 case -1:
1921 printf("scsw:2\n");
1922 break;
1923 case 0 ... 5:
1924 printf("scsw:3\n");
1925 break;
1926 default:
1927 printf("scsw: broken!\n");
1931 void switch_test()
1933 int i;
1934 unsigned long long ull;
1935 long long ll;
1937 for(i=0;i<15;i++) {
1938 switch(i) {
1939 case 0:
1940 case 1:
1941 printf("a");
1942 break;
1943 default:
1944 printf("%d", i);
1945 break;
1946 case 8 ... 12:
1947 printf("c");
1948 break;
1949 case 3:
1950 printf("b");
1951 break;
1952 case 0xc33c6b9fU:
1953 case 0x7c9eeeb9U:
1954 break;
1957 printf("\n");
1959 for (i = 1; i <= 5; i++) {
1960 ull = (unsigned long long)i << 61;
1961 switch (ull) {
1962 case 1ULL << 61:
1963 printf("ullsw:1\n");
1964 break;
1965 case 2ULL << 61:
1966 printf("ullsw:2\n");
1967 break;
1968 case 3ULL << 61:
1969 printf("ullsw:3\n");
1970 break;
1971 case 4ULL << 61:
1972 printf("ullsw:4\n");
1973 break;
1974 case 5ULL << 61:
1975 printf("ullsw:5\n");
1976 break;
1977 default:
1978 printf("ullsw: broken!\n");
1982 for (i = 1; i <= 5; i++) {
1983 ll = (long long)i << 61;
1984 switch (ll) {
1985 case 1LL << 61:
1986 printf("llsw:1\n");
1987 break;
1988 case 2LL << 61:
1989 printf("llsw:2\n");
1990 break;
1991 case 3LL << 61:
1992 printf("llsw:3\n");
1993 break;
1994 case 4LL << 61:
1995 printf("llsw:4\n");
1996 break;
1997 case 5LL << 61:
1998 printf("llsw:5\n");
1999 break;
2000 default:
2001 printf("llsw: broken!\n");
2005 for (i = -5; i <= 5; i++) {
2006 switch_uc((unsigned char)i);
2009 for (i = -5; i <= 5; i++) {
2010 switch_sc ((signed char)i);
2014 /* ISOC99 _Bool type */
2015 void c99_bool_test(void)
2017 #ifdef BOOL_ISOC99
2018 int a;
2019 _Bool b, b2;
2021 printf("sizeof(_Bool) = %d\n", sizeof(_Bool));
2022 a = 3;
2023 printf("cast: %d %d %d\n", (_Bool)10, (_Bool)0, (_Bool)a);
2024 b = 3;
2025 printf("b = %d\n", b);
2026 b++;
2027 printf("b = %d\n", b);
2028 b2 = 0;
2029 printf("sizeof(x ? _Bool : _Bool) = %d (should be sizeof int)\n",
2030 sizeof((volatile)a ? b : b2));
2031 #endif
2034 void bitfield_test(void)
2036 int a;
2037 short sa;
2038 unsigned char ca;
2039 struct sbf1 {
2040 int f1 : 3;
2041 int : 2;
2042 int f2 : 1;
2043 int : 0;
2044 int f3 : 5;
2045 int f4 : 7;
2046 unsigned int f5 : 7;
2047 } st1;
2048 printf("sizeof(st1) = %d\n", sizeof(st1));
2050 st1.f1 = 3;
2051 st1.f2 = 1;
2052 st1.f3 = 15;
2053 a = 120;
2054 st1.f4 = a;
2055 st1.f5 = a;
2056 st1.f5++;
2057 printf("%d %d %d %d %d\n",
2058 st1.f1, st1.f2, st1.f3, st1.f4, st1.f5);
2059 sa = st1.f5;
2060 ca = st1.f5;
2061 printf("%d %d\n", sa, ca);
2063 st1.f1 = 7;
2064 if (st1.f1 == -1)
2065 printf("st1.f1 == -1\n");
2066 else
2067 printf("st1.f1 != -1\n");
2068 if (st1.f2 == -1)
2069 printf("st1.f2 == -1\n");
2070 else
2071 printf("st1.f2 != -1\n");
2073 struct sbf2 {
2074 long long f1 : 45;
2075 long long : 2;
2076 long long f2 : 35;
2077 unsigned long long f3 : 38;
2078 } st2;
2079 st2.f1 = 0x123456789ULL;
2080 a = 120;
2081 st2.f2 = (long long)a << 25;
2082 st2.f3 = a;
2083 st2.f2++;
2084 printf("%lld %lld %lld\n", st2.f1, st2.f2, st2.f3);
2086 #if 0
2087 Disabled for now until further clarification re GCC compatibility
2088 struct sbf3 {
2089 int f1 : 7;
2090 int f2 : 1;
2091 char f3;
2092 int f4 : 8;
2093 int f5 : 1;
2094 int f6 : 16;
2095 } st3;
2096 printf("sizeof(st3) = %d\n", sizeof(st3));
2097 #endif
2099 struct sbf4 {
2100 int x : 31;
2101 char y : 2;
2102 } st4;
2103 st4.y = 1;
2104 printf("st4.y == %d\n", st4.y);
2105 struct sbf5 {
2106 int a;
2107 char b;
2108 int x : 12, y : 4, : 0, : 4, z : 3;
2109 char c;
2110 } st5 = { 1, 2, 3, 4, -3, 6 };
2111 printf("st5 = %d %d %d %d %d %d\n", st5.a, st5.b, st5.x, st5.y, st5.z, st5.c);
2112 struct sbf6 {
2113 short x : 12;
2114 unsigned char y : 2;
2115 } st6;
2116 st6.y = 1;
2117 printf("st6.y == %d\n", st6.y);
2120 #ifdef __x86_64__
2121 #define FLOAT_FMT "%f\n"
2122 #else
2123 /* x86's float isn't compatible with GCC */
2124 #define FLOAT_FMT "%.5f\n"
2125 #endif
2127 /* declare strto* functions as they are C99 */
2128 double strtod(const char *nptr, char **endptr);
2130 #if defined(_WIN32)
2131 float strtof(const char *nptr, char **endptr) {return (float)strtod(nptr, endptr);}
2132 LONG_DOUBLE strtold(const char *nptr, char **endptr) {return (LONG_DOUBLE)strtod(nptr, endptr);}
2133 #else
2134 float strtof(const char *nptr, char **endptr);
2135 LONG_DOUBLE strtold(const char *nptr, char **endptr);
2136 #endif
2138 #if CC_NAME == CC_clang
2139 /* In clang 0.0/0.0 is nan and not -nan.
2140 Also some older clang version do v=-v
2141 as v = -0 - v */
2142 static char enable_nan_test = 0;
2143 #else
2144 static char enable_nan_test = 1;
2145 #endif
2147 #define FTEST(prefix, typename, type, fmt)\
2148 void prefix ## cmp(type a, type b)\
2150 printf("%d %d %d %d %d %d\n",\
2151 a == b,\
2152 a != b,\
2153 a < b,\
2154 a > b,\
2155 a >= b,\
2156 a <= b);\
2157 printf(fmt " " fmt " " fmt " " fmt " " fmt " " fmt " " fmt "\n",\
2160 a + b,\
2161 a - b,\
2162 a * b,\
2163 a / b,\
2164 -a);\
2165 printf(fmt "\n", ++a);\
2166 printf(fmt "\n", a++);\
2167 printf(fmt "\n", a);\
2168 b = 0;\
2169 printf("%d %d\n", !a, !b);\
2171 void prefix ## fcast(type a)\
2173 float fa;\
2174 double da;\
2175 LONG_DOUBLE la;\
2176 int ia;\
2177 long long llia;\
2178 unsigned int ua;\
2179 unsigned long long llua;\
2180 type b;\
2181 fa = a;\
2182 da = a;\
2183 la = a;\
2184 printf("ftof: %f %f %Lf\n", fa, da, la);\
2185 ia = (int)a;\
2186 llia = (long long)a;\
2187 a = (a >= 0) ? a : -a;\
2188 ua = (unsigned int)a;\
2189 llua = (unsigned long long)a;\
2190 printf("ftoi: %d %u %lld %llu\n", ia, ua, llia, llua);\
2191 ia = -1234;\
2192 ua = 0x81234500;\
2193 llia = -0x123456789012345LL;\
2194 llua = 0xf123456789012345LLU;\
2195 b = ia;\
2196 printf("itof: " fmt "\n", b);\
2197 b = ua;\
2198 printf("utof: " fmt "\n", b);\
2199 b = llia;\
2200 printf("lltof: " fmt "\n", b);\
2201 b = llua;\
2202 printf("ulltof: " fmt "\n", b);\
2205 float prefix ## retf(type a) { return a; }\
2206 double prefix ## retd(type a) { return a; }\
2207 LONG_DOUBLE prefix ## retld(type a) { return a; }\
2209 void prefix ## call(void)\
2211 printf("float: " FLOAT_FMT, prefix ## retf(42.123456789));\
2212 printf("double: %f\n", prefix ## retd(42.123456789));\
2213 printf("long double: %Lf\n", prefix ## retld(42.123456789));\
2214 printf("strto%s: %f\n", #prefix, (double)strto ## prefix("1.2", NULL));\
2217 void prefix ## signed_zeros(void) \
2219 type x = 0.0, y = -0.0, n, p;\
2220 if (x == y)\
2221 printf ("Test 1.0 / x != 1.0 / y returns %d (should be 1).\n",\
2222 1.0 / x != 1.0 / y);\
2223 else\
2224 printf ("x != y; this is wrong!\n");\
2226 n = -x;\
2227 if (x == n)\
2228 printf ("Test 1.0 / x != 1.0 / -x returns %d (should be 1).\n",\
2229 1.0 / x != 1.0 / n);\
2230 else\
2231 printf ("x != -x; this is wrong!\n");\
2233 p = +y;\
2234 if (x == p)\
2235 printf ("Test 1.0 / x != 1.0 / +y returns %d (should be 1).\n",\
2236 1.0 / x != 1.0 / p);\
2237 else\
2238 printf ("x != +y; this is wrong!\n");\
2239 p = -y;\
2240 if (x == p)\
2241 printf ("Test 1.0 / x != 1.0 / -y returns %d (should be 0).\n",\
2242 1.0 / x != 1.0 / p);\
2243 else\
2244 printf ("x != -y; this is wrong!\n");\
2246 void prefix ## nan(void)\
2248 type nan = 0.0/0.0;\
2249 type nnan = -nan; \
2250 printf("nantest: " fmt " " fmt "\n", nan, nnan);\
2252 void prefix ## test(void)\
2254 printf("testing '%s'\n", #typename);\
2255 prefix ## cmp(1, 2.5);\
2256 prefix ## cmp(2, 1.5);\
2257 prefix ## cmp(1, 1);\
2258 prefix ## fcast(234.6);\
2259 prefix ## fcast(-2334.6);\
2260 prefix ## call();\
2261 prefix ## signed_zeros();\
2262 if (enable_nan_test) prefix ## nan();\
2265 FTEST(f, float, float, "%f")
2266 FTEST(d, double, double, "%f")
2267 FTEST(ld, long double, LONG_DOUBLE, "%Lf")
2269 double ftab1[3] = { 1.2, 3.4, -5.6 };
2272 void float_test(void)
2274 #if !defined(__arm__) || defined(__ARM_PCS_VFP)
2275 volatile float fa, fb;
2276 volatile double da, db;
2277 int a;
2278 unsigned int b;
2279 static double nan2 = 0.0/0.0;
2280 static double inf1 = 1.0/0.0;
2281 static double inf2 = 1e5000;
2282 volatile LONG_DOUBLE la;
2284 printf("sizeof(float) = %d\n", sizeof(float));
2285 printf("sizeof(double) = %d\n", sizeof(double));
2286 printf("sizeof(long double) = %d\n", sizeof(LONG_DOUBLE));
2287 ftest();
2288 dtest();
2289 ldtest();
2290 printf("%f %f %f\n", ftab1[0], ftab1[1], ftab1[2]);
2291 printf("%f %f %f\n", 2.12, .5, 2.3e10);
2292 // printf("%f %f %f\n", 0x1234p12, 0x1e23.23p10, 0x12dp-10);
2293 da = 123;
2294 printf("da=%f\n", da);
2295 fa = 123;
2296 printf("fa=%f\n", fa);
2297 a = 4000000000;
2298 da = a;
2299 printf("da = %f\n", da);
2300 b = 4000000000;
2301 db = b;
2302 printf("db = %f\n", db);
2303 printf("nan != nan = %d, inf1 = %f, inf2 = %f\n", nan2 != nan2, inf1, inf2);
2304 da = 0x0.88p-1022; /* a subnormal */
2305 la = da;
2306 printf ("da subnormal = %a\n", da);
2307 printf ("da subnormal = %.40g\n", da);
2308 printf ("la subnormal = %La\n", la);
2309 printf ("la subnormal = %.40Lg\n", la);
2310 da /= 2;
2311 la = da;
2312 printf ("da/2 subnormal = %a\n", da);
2313 printf ("da/2 subnormal = %.40g\n", da);
2314 printf ("la/2 subnormal = %La\n", la);
2315 printf ("la/2 subnormal = %.40Lg\n", la);
2316 fa = 0x0.88p-126f; /* a subnormal */
2317 la = fa;
2318 printf ("fa subnormal = %a\n", fa);
2319 printf ("fa subnormal = %.40g\n", fa);
2320 printf ("la subnormal = %La\n", la);
2321 printf ("la subnormal = %.40Lg\n", la);
2322 fa /= 2;
2323 la = fa;
2324 printf ("fa/2 subnormal = %a\n", fa);
2325 printf ("fa/2 subnormal = %.40g\n", fa);
2326 printf ("la/2 subnormal = %La\n", la);
2327 printf ("la/2 subnormal = %.40Lg\n", la);
2328 #endif
2331 int fib(int n)
2333 if (n <= 2)
2334 return 1;
2335 else
2336 return fib(n-1) + fib(n-2);
2339 #if __GNUC__ == 3 || __GNUC__ == 4
2340 # define aligned_function 0
2341 #else
2342 void __attribute__((aligned(16))) aligned_function(int i) {}
2343 #endif
2345 void funcptr_test()
2347 void (*func)(int);
2348 int a;
2349 struct {
2350 int dummy;
2351 void (*func)(int);
2352 } st1;
2353 long diff;
2355 func = &num;
2356 (*func)(12345);
2357 func = num;
2358 a = 1;
2359 a = 1;
2360 func(12345);
2361 /* more complicated pointer computation */
2362 st1.func = num;
2363 st1.func(12346);
2364 printf("sizeof1 = %d\n", sizeof(funcptr_test));
2365 printf("sizeof2 = %d\n", sizeof funcptr_test);
2366 printf("sizeof3 = %d\n", sizeof(&funcptr_test));
2367 printf("sizeof4 = %d\n", sizeof &funcptr_test);
2368 a = 0;
2369 func = num + a;
2370 diff = func - num;
2371 func(42);
2372 (func + diff)(42);
2373 (num + a)(43);
2375 /* Check that we can align functions */
2376 func = aligned_function;
2377 printf("aligned_function (should be zero): %d\n", ((int)(uintptr_t)func) & 15);
2380 void lloptest(long long a, long long b)
2382 unsigned long long ua, ub;
2384 ua = a;
2385 ub = b;
2386 /* arith */
2387 printf("arith: " LONG_LONG_FORMAT " " LONG_LONG_FORMAT " " LONG_LONG_FORMAT "\n",
2388 a + b,
2389 a - b,
2390 a * b);
2392 if (b != 0) {
2393 printf("arith1: " LONG_LONG_FORMAT " " LONG_LONG_FORMAT "\n",
2394 a / b,
2395 a % b);
2398 /* binary */
2399 printf("bin: " LONG_LONG_FORMAT " " LONG_LONG_FORMAT " " LONG_LONG_FORMAT "\n",
2400 a & b,
2401 a | b,
2402 a ^ b);
2404 /* tests */
2405 printf("test: %d %d %d %d %d %d\n",
2406 a == b,
2407 a != b,
2408 a < b,
2409 a > b,
2410 a >= b,
2411 a <= b);
2413 printf("utest: %d %d %d %d %d %d\n",
2414 ua == ub,
2415 ua != ub,
2416 ua < ub,
2417 ua > ub,
2418 ua >= ub,
2419 ua <= ub);
2421 /* arith2 */
2422 a++;
2423 b++;
2424 printf("arith2: " LONG_LONG_FORMAT " " LONG_LONG_FORMAT "\n", a, b);
2425 printf("arith2: " LONG_LONG_FORMAT " " LONG_LONG_FORMAT "\n", a++, b++);
2426 printf("arith2: " LONG_LONG_FORMAT " " LONG_LONG_FORMAT "\n", --a, --b);
2427 printf("arith2: " LONG_LONG_FORMAT " " LONG_LONG_FORMAT "\n", a, b);
2428 b = ub = 0;
2429 printf("not: %d %d %d %d\n", !a, !ua, !b, !ub);
2432 void llshift(long long a, int b)
2434 printf("shift: " LONG_LONG_FORMAT " " LONG_LONG_FORMAT " " LONG_LONG_FORMAT "\n",
2435 (unsigned long long)a >> b,
2436 a >> b,
2437 a << b);
2438 printf("shiftc: " LONG_LONG_FORMAT " " LONG_LONG_FORMAT " " LONG_LONG_FORMAT "\n",
2439 (unsigned long long)a >> 3,
2440 a >> 3,
2441 a << 3);
2442 printf("shiftc: " LONG_LONG_FORMAT " " LONG_LONG_FORMAT " " LONG_LONG_FORMAT "\n",
2443 (unsigned long long)a >> 35,
2444 a >> 35,
2445 a << 35);
2448 void llfloat(void)
2450 float fa;
2451 double da;
2452 LONG_DOUBLE lda;
2453 long long la, lb, lc;
2454 unsigned long long ula, ulb, ulc;
2455 la = 0x12345678;
2456 ula = 0x72345678;
2457 la = (la << 20) | 0x12345;
2458 ula = ula << 33;
2459 printf("la=" LONG_LONG_FORMAT " ula=" ULONG_LONG_FORMAT "\n", la, ula);
2461 fa = la;
2462 da = la;
2463 lda = la;
2464 printf("lltof: %f %f %Lf\n", fa, da, lda);
2466 la = fa;
2467 lb = da;
2468 lc = lda;
2469 printf("ftoll: " LONG_LONG_FORMAT " " LONG_LONG_FORMAT " " LONG_LONG_FORMAT "\n", la, lb, lc);
2471 fa = ula;
2472 da = ula;
2473 lda = ula;
2474 printf("ulltof: %f %f %Lf\n", fa, da, lda);
2476 ula = fa;
2477 ulb = da;
2478 ulc = lda;
2479 printf("ftoull: " ULONG_LONG_FORMAT " " ULONG_LONG_FORMAT " " ULONG_LONG_FORMAT "\n", ula, ulb, ulc);
2482 long long llfunc1(int a)
2484 return a * 2;
2487 struct S {
2488 int id;
2489 char item;
2492 long long int value(struct S *v)
2494 return ((long long int)v->item);
2497 long long llfunc2(long long x, long long y, int z)
2499 return x * y * z;
2502 void check_opl_save_regs(char *a, long long b, int c)
2504 *a = b < 0 && !c;
2507 void longlong_test(void)
2509 long long a, b, c;
2510 int ia;
2511 unsigned int ua;
2512 printf("sizeof(long long) = %d\n", sizeof(long long));
2513 ia = -1;
2514 ua = -2;
2515 a = ia;
2516 b = ua;
2517 printf(LONG_LONG_FORMAT " " LONG_LONG_FORMAT "\n", a, b);
2518 printf(LONG_LONG_FORMAT " " LONG_LONG_FORMAT " " LONG_LONG_FORMAT " %Lx\n",
2519 (long long)1,
2520 (long long)-2,
2521 1LL,
2522 0x1234567812345679);
2523 a = llfunc1(-3);
2524 printf(LONG_LONG_FORMAT "\n", a);
2526 lloptest(1000, 23);
2527 lloptest(0xff, 0x1234);
2528 b = 0x72345678 << 10;
2529 lloptest(-3, b);
2530 llshift(0x123, 5);
2531 llshift(-23, 5);
2532 b = 0x72345678LL << 10;
2533 llshift(b, 47);
2535 llfloat();
2536 #if 1
2537 b = 0x12345678;
2538 a = -1;
2539 c = a + b;
2540 printf("%Lx\n", c);
2541 #endif
2543 /* long long reg spill test */
2545 struct S a;
2547 a.item = 3;
2548 printf("%lld\n", value(&a));
2550 lloptest(0x80000000, 0);
2553 long long *p, v, **pp;
2554 v = 1;
2555 p = &v;
2556 p[0]++;
2557 printf("another long long spill test : %lld\n", *p);
2558 pp = &p;
2560 v = llfunc2(**pp, **pp, ia);
2561 printf("a long long function (arm-)reg-args test : %lld\n", v);
2563 a = 68719476720LL;
2564 b = 4294967295LL;
2565 printf("%d %d %d %d\n", a > b, a < b, a >= b, a <= b);
2567 printf(LONG_LONG_FORMAT "\n", 0x123456789LLU);
2569 /* long long pointer deref in argument passing test */
2570 a = 0x123;
2571 long long *p = &a;
2572 llshift(*p, 5);
2574 /* shortening followed by widening */
2575 unsigned long long u = 0x8000000000000001ULL;
2576 u = (unsigned)(u + 1);
2577 printf("long long u=" ULONG_LONG_FORMAT "\n", u);
2578 u = 0x11223344aa998877ULL;
2579 u = (unsigned)(int)(u + 1);
2580 printf("long long u=" ULONG_LONG_FORMAT "\n", u);
2582 /* was a problem with missing save_regs in gen_opl on 32-bit platforms */
2583 char cc = 78;
2584 check_opl_save_regs(&cc, -1, 0);
2585 printf("check_opl_save_regs: %d\n", cc);
2588 void manyarg_test(void)
2590 LONG_DOUBLE ld = 1234567891234LL;
2591 printf("%d %d %d %d %d %d %d %d %f %f %f %f %f %f %f %f %f %f\n",
2592 1, 2, 3, 4, 5, 6, 7, 8,
2593 0.1, 1.2, 2.3, 3.4, 4.5, 5.6, 6.7, 7.8, 8.9, 9.0);
2594 printf("%d %d %d %d %d %d %d %d %f %f %f %f %f %f %f %f %f %f "
2595 LONG_LONG_FORMAT " " LONG_LONG_FORMAT " %f %f\n",
2596 1, 2, 3, 4, 5, 6, 7, 8,
2597 0.1, 1.2, 2.3, 3.4, 4.5, 5.6, 6.7, 7.8, 8.9, 9.0,
2598 1234567891234LL, 987654321986LL,
2599 42.0, 43.0);
2600 printf("%Lf %d %d %d %d %d %d %d %d %f %f %f %f %f %f %f %f %f %f "
2601 LONG_LONG_FORMAT " " LONG_LONG_FORMAT " %f %f\n",
2602 ld, 1, 2, 3, 4, 5, 6, 7, 8,
2603 0.1, 1.2, 2.3, 3.4, 4.5, 5.6, 6.7, 7.8, 8.9, 9.0,
2604 1234567891234LL, 987654321986LL,
2605 42.0, 43.0);
2606 printf("%d %d %d %d %d %d %d %d %Lf\n",
2607 1, 2, 3, 4, 5, 6, 7, 8, ld);
2608 printf("%d %d %d %d %d %d %d %d %f %f %f %f %f %f %f %f %f %f "
2609 LONG_LONG_FORMAT " " LONG_LONG_FORMAT "%f %f %Lf\n",
2610 1, 2, 3, 4, 5, 6, 7, 8,
2611 0.1, 1.2, 2.3, 3.4, 4.5, 5.6, 6.7, 7.8, 8.9, 9.0,
2612 1234567891234LL, 987654321986LL,
2613 42.0, 43.0, ld);
2614 printf("%d %d %d %d %d %d %d %d %f %f %f %f %f %f %f %f %f %f "
2615 "%Lf " LONG_LONG_FORMAT " " LONG_LONG_FORMAT " %f %f %Lf\n",
2616 1, 2, 3, 4, 5, 6, 7, 8,
2617 0.1, 1.2, 2.3, 3.4, 4.5, 5.6, 6.7, 7.8, 8.9, 9.0,
2618 ld, 1234567891234LL, 987654321986LL,
2619 42.0, 43.0, ld);
2622 void*
2623 va_arg_with_struct_ptr(va_list ap) {
2625 * This was a BUG identified with FFTW-3.3.8 on arm64.
2626 * The test case only checks it compiles on all supported
2627 * architectures. This function is not currently called.
2629 struct X { int _x; };
2630 struct X *x = va_arg(ap, struct X *);
2631 return x;
2634 void vprintf1(const char *fmt, ...)
2636 va_list ap, aq;
2637 const char *p;
2638 int c, i;
2639 double d;
2640 long long ll;
2641 LONG_DOUBLE ld;
2643 va_start(aq, fmt);
2644 va_copy(ap, aq);
2646 p = fmt;
2647 for(;;) {
2648 c = *p;
2649 if (c == '\0')
2650 break;
2651 p++;
2652 if (c == '%') {
2653 c = *p;
2654 switch(c) {
2655 case '\0':
2656 goto the_end;
2657 case 'd':
2658 i = va_arg(ap, int);
2659 printf("%d", i);
2660 break;
2661 case 'f':
2662 d = va_arg(ap, double);
2663 printf("%f", d);
2664 break;
2665 case 'l':
2666 ll = va_arg(ap, long long);
2667 printf(LONG_LONG_FORMAT, ll);
2668 break;
2669 case 'F':
2670 ld = va_arg(ap, LONG_DOUBLE);
2671 printf("%Lf", ld);
2672 break;
2674 p++;
2675 } else {
2676 putchar(c);
2679 the_end:
2680 va_end(aq);
2681 va_end(ap);
2684 struct myspace {
2685 short int profile;
2687 struct myspace2 {
2688 #if CC_NAME == CC_clang /* clang7 doesn't support zero sized structs */
2689 char a[1];
2690 #else
2691 char a[0];
2692 #endif
2694 struct myspace3 {
2695 char a[1];
2697 struct myspace4 {
2698 char a[2];
2700 struct mytest {
2701 void *foo, *bar, *baz;
2704 struct mytest stdarg_for_struct(struct myspace bob, ...)
2706 struct myspace george, bill;
2707 struct myspace2 alex1;
2708 struct myspace3 alex2;
2709 struct myspace4 alex3;
2710 va_list ap;
2711 short int validate;
2713 va_start(ap, bob);
2714 alex1 = va_arg(ap, struct myspace2);
2715 alex2 = va_arg(ap, struct myspace3);
2716 alex3 = va_arg(ap, struct myspace4);
2717 bill = va_arg(ap, struct myspace);
2718 george = va_arg(ap, struct myspace);
2719 validate = va_arg(ap, int);
2720 printf("stdarg_for_struct: %d %d %d %d %d %d %d\n",
2721 alex2.a[0], alex3.a[0], alex3.a[1],
2722 bob.profile, bill.profile, george.profile, validate);
2723 va_end(ap);
2724 return (struct mytest) {};
2727 void stdarg_for_libc(const char *fmt, ...)
2729 va_list args;
2730 va_start(args, fmt);
2731 vprintf(fmt, args);
2732 va_end(args);
2735 void stdarg_syntax(int n, ...)
2737 int i;
2738 va_list ap;
2739 if (1)
2740 va_start(ap, n);
2741 else
2743 i = va_arg(ap, int);
2744 printf("stdarg_void_expr: %d\n", i);
2745 (va_end(ap));
2748 typedef struct{
2749 double x,y;
2750 } point;
2751 point pts[]={{1.0,2.0},{3.0,4.0},{5.0,6.0},{7.0,8.0},{9.0,10.0},{11.0,12.0}};
2753 static void stdarg_double_struct(int nargs, int posd,...)
2755 int i;
2756 double d;
2757 point pi;
2758 va_list args;
2760 printf ("stdarg_double_struct: %d\n", posd);
2761 va_start(args,posd);
2762 for(i = 0; i < nargs; i++) {
2763 if (i == posd) {
2764 d = va_arg (args, double);
2765 printf ("d %d = %g\n", i, d);
2767 else {
2768 pi = va_arg (args, point);
2769 printf ("pts[%d] = %g %g\n", i, pi.x, pi.y);
2772 va_end(args);
2775 void stdarg_test(void)
2777 LONG_DOUBLE ld = 1234567891234LL;
2778 struct myspace bob;
2779 struct myspace2 bob2;
2780 struct myspace3 bob3;
2781 struct myspace4 bob4;
2783 vprintf1("%d %d %d\n", 1, 2, 3);
2784 vprintf1("%f %d %f\n", 1.0, 2, 3.0);
2785 vprintf1("%l %l %d %f\n", 1234567891234LL, 987654321986LL, 3, 1234.0);
2786 vprintf1("%F %F %F\n", LONG_DOUBLE_LITERAL(1.2), LONG_DOUBLE_LITERAL(2.3), LONG_DOUBLE_LITERAL(3.4));
2787 vprintf1("%d %f %l %F %d %f %l %F\n",
2788 1, 1.2, 3LL, LONG_DOUBLE_LITERAL(4.5), 6, 7.8, 9LL, LONG_DOUBLE_LITERAL(0.1));
2789 vprintf1("%d %d %d %d %d %d %d %d %f %f %f %f %f %f %f %f\n",
2790 1, 2, 3, 4, 5, 6, 7, 8,
2791 0.1, 1.2, 2.3, 3.4, 4.5, 5.6, 6.7, 7.8);
2792 vprintf1("%d %d %d %d %d %d %d %d %f %f %f %f %f %f %f %f %f %f\n",
2793 1, 2, 3, 4, 5, 6, 7, 8,
2794 0.1, 1.2, 2.3, 3.4, 4.5, 5.6, 6.7, 7.8, 8.9, 9.0);
2795 vprintf1("%d %d %d %d %d %d %d %d %f %f %f %f %f %f %f %f %f %f "
2796 "%l %l %f %f\n",
2797 1, 2, 3, 4, 5, 6, 7, 8,
2798 0.1, 1.2, 2.3, 3.4, 4.5, 5.6, 6.7, 7.8, 8.9, 9.0,
2799 1234567891234LL, 987654321986LL,
2800 42.0, 43.0);
2801 vprintf1("%F %d %d %d %d %d %d %d %d %f %f %f %f %f %f %f %f %f %f "
2802 "%l %l %f %f\n",
2803 ld, 1, 2, 3, 4, 5, 6, 7, 8,
2804 0.1, 1.2, 2.3, 3.4, 4.5, 5.6, 6.7, 7.8, 8.9, 9.0,
2805 1234567891234LL, 987654321986LL,
2806 42.0, 43.0);
2807 vprintf1("%d %d %d %d %d %d %d %d %F\n",
2808 1, 2, 3, 4, 5, 6, 7, 8, ld);
2809 vprintf1("%d %d %d %d %d %d %d %d %f %f %f %f %f %f %f %f %f %f "
2810 "%l %l %f %f %F\n",
2811 1, 2, 3, 4, 5, 6, 7, 8,
2812 0.1, 1.2, 2.3, 3.4, 4.5, 5.6, 6.7, 7.8, 8.9, 9.0,
2813 1234567891234LL, 987654321986LL,
2814 42.0, 43.0, ld);
2815 vprintf1("%d %d %d %d %d %d %d %d %f %f %f %f %f %f %f %f %f %f "
2816 "%F %l %l %f %f %F\n",
2817 1, 2, 3, 4, 5, 6, 7, 8,
2818 0.1, 1.2, 2.3, 3.4, 4.5, 5.6, 6.7, 7.8, 8.9, 9.0,
2819 ld, 1234567891234LL, 987654321986LL,
2820 42.0, 43.0, ld);
2822 bob.profile = 42;
2823 bob3.a[0] = 1;
2824 bob4.a[0] = 2;
2825 bob4.a[1] = 3;
2826 stdarg_for_struct(bob, bob2, bob3, bob4, bob, bob, bob.profile);
2827 stdarg_for_libc("stdarg_for_libc: %s %.2f %d\n", "string", 1.23, 456);
2828 stdarg_syntax(1, 17);
2829 stdarg_double_struct(6,-1,pts[0],pts[1],pts[2],pts[3],pts[4],pts[5]);
2830 stdarg_double_struct(7,1,pts[0],-1.0,pts[1],pts[2],pts[3],pts[4],pts[5]);
2831 stdarg_double_struct(7,2,pts[0],pts[1],-1.0,pts[2],pts[3],pts[4],pts[5]);
2832 stdarg_double_struct(7,3,pts[0],pts[1],pts[2],-1.0,pts[3],pts[4],pts[5]);
2833 stdarg_double_struct(7,4,pts[0],pts[1],pts[2],pts[3],-1.0,pts[4],pts[5]);
2834 stdarg_double_struct(7,5,pts[0],pts[1],pts[2],pts[3],pts[4],-1.0,pts[5]);
2837 int reltab[3] = { 1, 2, 3 };
2839 int *rel1 = &reltab[1];
2840 int *rel2 = &reltab[2];
2842 void getmyaddress(void)
2844 printf("in getmyaddress\n");
2847 #ifdef __LP64__
2848 long __pa_symbol(void)
2850 /* This 64bit constant was handled incorrectly, it was used as addend
2851 (which can hold 64bit just fine) in connection with a symbol,
2852 and TCC generates wrong code for that (displacements are 32bit only).
2853 This effectively is "+ 0x80000000", and if addresses of globals
2854 are below 2GB the result should be a number without high 32 bits set. */
2855 return ((long)(((unsigned long)(&rel1))) - (0xffffffff80000000UL));
2857 #endif
2859 uintptr_t theaddress = (uintptr_t)getmyaddress;
2860 void relocation_test(void)
2862 void (*fptr)(void) = (void (*)(void))theaddress;
2863 printf("*rel1=%d\n", *rel1);
2864 printf("*rel2=%d\n", *rel2);
2865 fptr();
2866 #ifdef __LP64__
2867 printf("pa_symbol=0x%lx\n", __pa_symbol() >> 63);
2868 #endif
2871 void old_style_f(a,b,c)
2872 int a, b;
2873 double c;
2875 printf("a=%d b=%d b=%f\n", a, b, c);
2878 void decl_func1(int cmpfn())
2880 printf("cmpfn=%lx\n", (long)cmpfn);
2883 void decl_func2(cmpfn)
2884 int cmpfn();
2886 printf("cmpfn=%lx\n", (long)cmpfn);
2889 void old_style_function_test(void)
2891 old_style_f((void *)1, 2, 3.0);
2892 decl_func1(NULL);
2893 decl_func2(NULL);
2896 void alloca_test()
2898 #if defined __i386__ || defined __x86_64__ || defined __arm__
2899 char *p = alloca(16);
2900 strcpy(p,"123456789012345");
2901 printf("alloca: p is %s\n", p);
2902 char *demo = "This is only a test.\n";
2903 /* Test alloca embedded in a larger expression */
2904 printf("alloca: %s\n", strcpy(alloca(strlen(demo)+1),demo) );
2905 #endif
2908 void *bounds_checking_is_enabled()
2910 char ca[10], *cp = ca-1;
2911 return (ca != cp + 1) ? cp : NULL;
2914 typedef int constant_negative_array_size_as_compile_time_assertion_idiom[(1 ? 2 : 0) - 1];
2916 void c99_vla_test_1(int size1, int size2)
2918 int size = size1 * size2;
2919 int tab1[size][2], tab2[10][2];
2920 void *tab1_ptr, *tab2_ptr, *bad_ptr;
2922 /* "size" should have been 'captured' at tab1 declaration,
2923 so modifying it should have no effect on VLA behaviour. */
2924 size = size-1;
2926 printf("Test C99 VLA 1 (sizeof): ");
2927 printf("%s\n", (sizeof tab1 == size1 * size2 * 2 * sizeof(int)) ? "PASSED" : "FAILED");
2928 tab1_ptr = tab1;
2929 tab2_ptr = tab2;
2930 printf("Test C99 VLA 2 (ptrs subtract): ");
2931 printf("%s\n", (tab2 - tab1 == (tab2_ptr - tab1_ptr) / (sizeof(int) * 2)) ? "PASSED" : "FAILED");
2932 printf("Test C99 VLA 3 (ptr add): ");
2933 printf("%s\n", &tab1[5][1] == (tab1_ptr + (5 * 2 + 1) * sizeof(int)) ? "PASSED" : "FAILED");
2934 printf("Test C99 VLA 4 (ptr access): ");
2935 tab1[size1][1] = 42;
2936 printf("%s\n", (*((int *) (tab1_ptr + (size1 * 2 + 1) * sizeof(int))) == 42) ? "PASSED" : "FAILED");
2938 printf("Test C99 VLA 5 (bounds checking (might be disabled)): ");
2939 if (bad_ptr = bounds_checking_is_enabled()) {
2940 int *t1 = &tab1[size1 * size2 - 1][3];
2941 int *t2 = &tab2[9][3];
2942 printf("%s ", bad_ptr == t1 ? "PASSED" : "FAILED");
2943 printf("%s ", bad_ptr == t2 ? "PASSED" : "FAILED");
2945 char*c1 = 1 + sizeof(tab1) + (char*)tab1;
2946 char*c2 = 1 + sizeof(tab2) + (char*)tab2;
2947 printf("%s ", bad_ptr == c1 ? "PASSED" : "FAILED");
2948 printf("%s ", bad_ptr == c2 ? "PASSED" : "FAILED");
2950 int *i1 = tab1[-1];
2951 int *i2 = tab2[-1];
2952 printf("%s ", bad_ptr == i1 ? "PASSED" : "FAILED");
2953 printf("%s ", bad_ptr == i2 ? "PASSED" : "FAILED");
2955 int *x1 = tab1[size1 * size2 + 1];
2956 int *x2 = tab2[10 + 1];
2957 printf("%s ", bad_ptr == x1 ? "PASSED" : "FAILED");
2958 printf("%s ", bad_ptr == x2 ? "PASSED" : "FAILED");
2959 } else {
2960 printf("PASSED PASSED PASSED PASSED PASSED PASSED PASSED PASSED ");
2962 printf("\n");
2965 void c99_vla_test_2(int d, int h, int w)
2967 int x, y, z;
2968 int (*arr)[h][w] = malloc(sizeof(int) * d*h*w);
2969 int c = 1;
2971 printf("Test C99 VLA 6 (pointer)\n");
2973 for (z=0; z<d; z++) {
2974 for (y=0; y<h; y++) {
2975 for (x=0; x<w; x++) {
2976 arr[z][y][x] = c++;
2980 for (z=0; z<d; z++) {
2981 for (y=0; y<h; y++) {
2982 for (x=0; x<w; x++) {
2983 printf(" %2d", arr[z][y][x]);
2985 puts("");
2987 puts("");
2989 printf(" sizes : %d %d %d\n"
2990 " pdiff : %d %d\n"
2991 " tests : %d %d\n",
2992 sizeof (*arr), sizeof (*arr)[0], sizeof (*arr)[0][0],
2993 arr + 2 - arr, *arr + 3 - *arr,
2994 0 == sizeof (*arr + 1) - sizeof arr,
2995 0 == sizeof sizeof *arr - sizeof arr
2997 free (arr);
3000 void c99_vla_test(void)
3002 c99_vla_test_1(5, 2);
3003 c99_vla_test_2(3, 4, 5);
3007 void sizeof_test(void)
3009 int a;
3010 int **ptr;
3012 printf("sizeof(int) = %d\n", sizeof(int));
3013 printf("sizeof(unsigned int) = %d\n", sizeof(unsigned int));
3014 printf("sizeof(long) = %d\n", sizeof(long));
3015 printf("sizeof(unsigned long) = %d\n", sizeof(unsigned long));
3016 printf("sizeof(short) = %d\n", sizeof(short));
3017 printf("sizeof(unsigned short) = %d\n", sizeof(unsigned short));
3018 printf("sizeof(char) = %d\n", sizeof(char));
3019 printf("sizeof(unsigned char) = %d\n", sizeof(unsigned char));
3020 printf("sizeof(func) = %d\n", sizeof sizeof_test());
3021 a = 1;
3022 printf("sizeof(a++) = %d\n", sizeof a++);
3023 printf("a=%d\n", a);
3024 ptr = NULL;
3025 printf("sizeof(**ptr) = %d\n", sizeof (**ptr));
3027 /* The type of sizeof should be as large as a pointer, actually
3028 it should be size_t. */
3029 printf("sizeof(sizeof(int) = %d\n", sizeof(sizeof(int)));
3030 uintptr_t t = 1;
3031 uintptr_t t2;
3032 /* Effectively <<32, but defined also on 32bit machines. */
3033 t <<= 16;
3034 t <<= 16;
3035 t++;
3036 /* This checks that sizeof really can be used to manipulate
3037 uintptr_t objects, without truncation. */
3038 t2 = t & -sizeof(uintptr_t);
3039 printf ("%lu %lu\n", t, t2);
3041 /* some alignof tests */
3042 printf("__alignof__(int) = %d\n", __alignof__(int));
3043 printf("__alignof__(unsigned int) = %d\n", __alignof__(unsigned int));
3044 printf("__alignof__(short) = %d\n", __alignof__(short));
3045 printf("__alignof__(unsigned short) = %d\n", __alignof__(unsigned short));
3046 printf("__alignof__(char) = %d\n", __alignof__(char));
3047 printf("__alignof__(unsigned char) = %d\n", __alignof__(unsigned char));
3048 printf("__alignof__(func) = %d\n", __alignof__ sizeof_test());
3050 /* sizes of VLAs need to be evaluated even inside sizeof: */
3051 a = 2;
3052 printf("sizeof(char[1+2*a]) = %d\n", sizeof(char[1+2*a]));
3053 /* And checking if sizeof compound literal works. Parenthesized: */
3054 printf("sizeof( (struct {int i; int j;}){4,5} ) = %d\n",
3055 sizeof( (struct {int i; int j;}){4,5} ));
3056 /* And as direct sizeof argument (as unary expression): */
3057 printf("sizeof (struct {short i; short j;}){4,5} = %d\n",
3058 sizeof (struct {short i; short j;}){4,5} );
3060 /* sizeof(x && y) should be sizeof(int), even if constant
3061 evaluating is possible. */
3062 printf("sizeof(t && 0) = %d\n", sizeof(t && 0));
3063 printf("sizeof(1 && 1) = %d\n", sizeof(1 && 1));
3064 printf("sizeof(t || 1) = %d\n", sizeof(t || 1));
3065 printf("sizeof(0 || 0) = %d\n", sizeof(0 || 0));
3068 void typeof_test(void)
3070 double a;
3071 typeof(a) b;
3072 typeof(float) c;
3074 a = 1.5;
3075 b = 2.5;
3076 c = 3.5;
3077 printf("a=%f b=%f c=%f\n", a, b, c);
3081 struct hlist_node;
3082 struct hlist_head {
3083 struct hlist_node *first, *last;
3086 void consume_ulong (unsigned long i)
3088 i = 0;
3091 void statement_expr_test(void)
3093 int a, i;
3095 /* Basic stmt expr test */
3096 a = 0;
3097 for(i=0;i<10;i++) {
3098 a += 1 +
3099 ( { int b, j;
3100 b = 0;
3101 for(j=0;j<5;j++)
3102 b += j; b;
3103 } );
3105 printf("a=%d\n", a);
3107 /* Test that symbols aren't freed prematurely.
3108 With SYM_DEBUG valgrind will show a read from a freed
3109 symbol, and tcc will show an (invalid) warning on the initialization
3110 of 'ptr' below, if symbols are popped after the stmt expr. */
3111 void *v = (void*)39;
3112 typeof(({
3113 (struct hlist_node *)v;
3114 })) x;
3115 typeof (x)
3116 ptr = (struct hlist_node *)v;
3118 /* This part used to segfault when symbols were popped prematurely.
3119 The symbols for the static local would be overwritten with
3120 helper symbols from the pre-processor expansions in between. */
3121 #define some_attr __attribute__((aligned(1)))
3122 #define tps(str) ({ \
3123 static const char *t some_attr = str; \
3124 t; \
3126 printf ("stmtexpr: %s %s\n",
3127 tps("somerandomlongstring"),
3128 tps("anotherlongstring"));
3130 /* Test that the three decls of 't' don't interact. */
3131 int t = 40;
3132 int b = ({ int t = 41; t; });
3133 int c = ({ int t = 42; t; });
3135 /* Test that aggregate return values work. */
3136 struct hlist_head h
3137 = ({
3138 typedef struct hlist_head T;
3139 long pre = 48;
3140 T t = { (void*)43, (void*)44 };
3141 long post = 49;
3144 printf ("stmtexpr: %d %d %d\n", t, b, c);
3145 printf ("stmtexpr: %ld %ld\n", (long)h.first, (long)h.last);
3147 /* Test that we can give out addresses of local labels. */
3148 consume_ulong(({ __label__ __here; __here: (unsigned long)&&__here; }));
3150 /* Test interaction between local and global label stacks and the
3151 need to defer popping symbol from them when within statement
3152 expressions. Note how the labels are both named LBL. */
3153 i = 0;
3156 __label__ LBL;
3157 LBL: if (i++ == 0) goto LBL;
3159 /* jump to a classical label out of an expr-stmt that had previously
3160 overshadowed that classical label */
3161 goto LBL;
3163 LBL:
3164 printf("stmtexpr: %d should be 2\n", i);
3167 void local_label_test(void)
3169 int a;
3170 goto l1;
3172 a = 1 + ({
3173 __label__ l1, l2, l3, l4;
3174 goto l1;
3176 printf("aa1\n");
3177 goto l3;
3179 printf("aa3\n");
3180 goto l4;
3182 printf("aa2\n");
3183 goto l2;
3184 l3:;
3187 printf("a=%d\n", a);
3188 return;
3190 printf("bb1\n");
3191 goto l2;
3193 printf("bb2\n");
3194 goto l4;
3197 /* inline assembler test */
3198 #if defined(__i386__) || defined(__x86_64__)
3200 /* from linux kernel */
3201 static char * strncat1(char * dest,const char * src,size_t count)
3203 long d0, d1, d2, d3;
3204 __asm__ __volatile__(
3205 "repne\n\t"
3206 "scasb\n\t"
3207 "dec %1\n\t"
3208 "mov %8,%3\n"
3209 "1:\tdec %3\n\t"
3210 "js 2f\n\t"
3211 "lodsb\n\t"
3212 "stosb\n\t"
3213 "testb %%al,%%al\n\t"
3214 "jne 1b\n"
3215 "2:\txor %2,%2\n\t"
3216 "stosb"
3217 : "=&S" (d0), "=&D" (d1), "=&a" (d2), "=&c" (d3)
3218 : "0" (src),"1" (dest),"2" (0),"3" (0xffffffff), "g" (count)
3219 : "memory");
3220 return dest;
3223 static char * strncat2(char * dest,const char * src,size_t count)
3225 long d0, d1, d2, d3;
3226 __asm__ __volatile__(
3227 "repne scasb\n\t" /* one-line repne prefix + string op */
3228 "dec %1\n\t"
3229 "mov %8,%3\n"
3230 "1:\tdec %3\n\t"
3231 "js 2f\n\t"
3232 "lodsb\n\t"
3233 "stosb\n\t"
3234 "testb %%al,%%al\n\t"
3235 "jne 1b\n"
3236 "2:\txor %2,%2\n\t"
3237 "stosb"
3238 : "=&S" (d0), "=&D" (d1), "=&a" (d2), "=&c" (d3)
3239 : "0" (src),"1" (dest),"2" (0),"3" (0xffffffff), "g" (count)
3240 : "memory");
3241 return dest;
3244 static inline void * memcpy1(void * to, const void * from, size_t n)
3246 size_t d0, d1, d2;
3247 __asm__ __volatile__(
3248 "rep ; movsl\n\t"
3249 "testb $2,%b4\n\t"
3250 "je 1f\n\t"
3251 "movsw\n"
3252 "1:\ttestb $1,%b4\n\t"
3253 "je 2f\n\t"
3254 "movsb\n"
3255 "2:"
3256 : "=&c" (d0), "=&D" (d1), "=&S" (d2)
3257 :"0" (n/4), "q" (n),"1" ((size_t) to),"2" ((size_t) from)
3258 : "memory");
3259 return (to);
3262 static inline void * memcpy2(void * to, const void * from, size_t n)
3264 size_t d0, d1, d2;
3265 __asm__ __volatile__(
3266 "rep movsl\n\t" /* one-line rep prefix + string op */
3267 "testb $2,%b4\n\t"
3268 "je 1f\n\t"
3269 "movsw\n"
3270 "1:\ttestb $1,%b4\n\t"
3271 "je 2f\n\t"
3272 "movsb\n"
3273 "2:"
3274 : "=&c" (d0), "=&D" (d1), "=&S" (d2)
3275 :"0" (n/4), "q" (n),"1" ((size_t) to),"2" ((size_t) from)
3276 : "memory");
3277 return (to);
3280 static __inline__ void sigaddset1(unsigned int *set, int _sig)
3282 __asm__("btsl %1,%0" : "=m"(*set) : "Ir"(_sig - 1) : "cc");
3285 static __inline__ void sigdelset1(unsigned int *set, int _sig)
3287 asm("btrl %1,%0" : "=m"(*set) : "Ir"(_sig - 1) : "cc", "flags");
3290 #ifdef __clang__
3291 /* clang's inline asm is uncapable of 'xchgb %b0,%h0' */
3292 static __inline__ __const__ unsigned int swab32(unsigned int x)
3294 return ((x >> 24) & 0xff) |
3295 ((x >> 8) & 0xff00) |
3296 ((x << 8) & 0xff0000) |
3297 ((x << 24) & 0xff000000);
3299 #else
3300 static __inline__ __const__ unsigned int swab32(unsigned int x)
3302 __asm__("xchgb %b0,%h0\n\t" /* swap lower bytes */
3303 "rorl $16,%0\n\t" /* swap words */
3304 "xchgb %b0,%h0" /* swap higher bytes */
3305 :"=" "q" (x)
3306 : "0" (x));
3307 return x;
3309 #endif
3311 static __inline__ unsigned long long mul64(unsigned int a, unsigned int b)
3313 unsigned long long res;
3314 #ifdef __x86_64__
3315 /* Using the A constraint is wrong (it means rdx:rax, which is too large)
3316 but still test the 32bit->64bit mull. */
3317 unsigned int resh, resl;
3318 __asm__("mull %2" : "=a" (resl), "=d" (resh) : "a" (a), "r" (b));
3319 res = ((unsigned long long)resh << 32) | resl;
3320 #else
3321 __asm__("mull %2" : "=A" (res) : "a" (a), "r" (b));
3322 #endif
3323 return res;
3326 static __inline__ unsigned long long inc64(unsigned long long a)
3328 unsigned long long res;
3329 #ifdef __x86_64__
3330 /* Using the A constraint is wrong, and increments are tested
3331 elsewhere. */
3332 res = a + 1;
3333 #else
3334 __asm__("addl $1, %%eax ; adcl $0, %%edx" : "=A" (res) : "A" (a));
3335 #endif
3336 return res;
3339 struct struct123 {
3340 int a;
3341 int b;
3343 struct struct1231 {
3344 unsigned long addr;
3347 unsigned long mconstraint_test(struct struct1231 *r)
3349 unsigned long ret;
3350 unsigned int a[2];
3351 a[0] = 0;
3352 __asm__ volatile ("lea %2,%0; movl 4(%0),%k0; addl %2,%k0; movl $51,%2; movl $52,4%2; movl $63,%1"
3353 : "=&r" (ret), "=m" (a)
3354 : "m" (*(struct struct123 *)r->addr));
3355 return ret + a[0];
3358 #ifdef __x86_64__
3359 int fls64(unsigned long long x)
3361 int bitpos = -1;
3362 asm("bsrq %1,%q0"
3363 : "+r" (bitpos)
3364 : "rm" (x));
3365 return bitpos + 1;
3367 #endif
3369 void other_constraints_test(void)
3371 unsigned long ret;
3372 int var;
3373 #ifndef _WIN64
3374 __asm__ volatile ("mov %P1,%0" : "=r" (ret) : "p" (&var));
3375 printf ("oc1: %d\n", ret == (unsigned long)&var);
3376 #endif
3379 #ifndef _WIN32
3380 /* Test global asm blocks playing with aliases. */
3381 void base_func(void)
3383 printf ("asmc: base\n");
3386 #ifndef __APPLE__
3387 extern void override_func1 (void);
3388 extern void override_func2 (void);
3390 asm(".weak override_func1\n.set override_func1, base_func");
3391 asm(".set override_func1, base_func");
3392 asm(".set override_func2, base_func");
3394 void override_func2 (void)
3396 printf ("asmc: override2\n");
3399 /* This checks a construct used by the linux kernel to encode
3400 references to strings by PC relative references. */
3401 extern int bug_table[] __attribute__((section("__bug_table")));
3402 char * get_asm_string (void)
3404 /* On i386 when -fPIC is enabled this would cause a compile error with GCC,
3405 the problem being the "i" constraint used with a symbolic operand
3406 resolving to a local label. That check is overly zealous as the code
3407 within the asm makes sure to use it only in PIC-possible contexts,
3408 but all GCC versions behave like so. We arrange for PIC to be disabled
3409 for compiling tcctest.c in the Makefile.
3411 Additionally the usage of 'c' in "%c0" in the template is actually wrong,
3412 as that would expect an operand that is a condition code. The operand
3413 as is (a local label) is accepted by GCC in non-PIC mode, and on x86-64.
3414 What the linux kernel really wanted is 'p' to disable the addition of '$'
3415 to the printed operand (as in "$.LC0" where the template only wants the
3416 bare operand ".LC0"). But the code below is what the linux kernel
3417 happens to use and as such is the one we want to test. */
3418 #ifndef __clang__
3419 extern int some_symbol;
3420 asm volatile (".globl some_symbol\n"
3421 "jmp .+6\n"
3422 "1:\n"
3423 "some_symbol: .long 0\n"
3424 ".pushsection __bug_table, \"a\"\n"
3425 ".globl bug_table\n"
3426 "bug_table:\n"
3427 /* The first entry (1b-2b) is unused in this test,
3428 but we include it to check if cross-section
3429 PC-relative references work. */
3430 "2:\t.long 1b - 2b, %c0 - 2b\n"
3431 ".popsection\n" : : "i" ("A string"));
3432 char * str = ((char*)bug_table) + bug_table[1];
3433 return str;
3434 #else
3435 return (char *) "A string";
3436 #endif
3439 /* This checks another constructs with local labels. */
3440 extern unsigned char alld_stuff[];
3441 asm(".data\n"
3442 ".byte 41\n"
3443 "alld_stuff:\n"
3444 "661:\n"
3445 ".byte 42\n"
3446 "662:\n"
3447 ".pushsection .data.ignore\n"
3448 ".long 661b - .\n" /* This reference to 661 generates an external sym
3449 which shouldn't somehow overwrite the offset that's
3450 already determined for it. */
3451 ".popsection\n"
3452 ".byte 662b - 661b\n" /* So that this value is undeniably 1. */);
3454 void asm_local_label_diff (void)
3456 printf ("asm_local_label_diff: %d %d\n", alld_stuff[0], alld_stuff[1]);
3458 #endif
3460 /* This checks that static local variables are available from assembler. */
3461 void asm_local_statics (void)
3463 static int localint = 41;
3464 asm("incl %0" : "+m" (localint));
3465 printf ("asm_local_statics: %d\n", localint);
3467 #endif
3469 static
3470 unsigned int set;
3472 void fancy_copy (unsigned *in, unsigned *out)
3474 asm volatile ("" : "=r" (*out) : "0" (*in));
3477 void fancy_copy2 (unsigned *in, unsigned *out)
3479 asm volatile ("mov %0,(%1)" : : "r" (*in), "r" (out) : "memory");
3482 #if defined __x86_64__ && !defined _WIN64
3483 void clobber_r12(void)
3485 asm volatile("mov $1, %%r12" ::: "r12");
3487 #endif
3489 void test_high_clobbers_really(void)
3491 #if defined __x86_64__ && !defined _WIN64
3492 register long val asm("r12");
3493 long val2;
3494 /* This tests if asm clobbers correctly save/restore callee saved
3495 registers if they are clobbered and if it's the high 8 x86-64
3496 registers. This is fragile for GCC as the constraints do not
3497 correctly capture the data flow, but good enough for us. */
3498 asm volatile("mov $0x4542, %%r12" : "=r" (val):: "memory");
3499 clobber_r12();
3500 asm volatile("mov %%r12, %0" : "=r" (val2) : "r" (val): "memory");
3501 printf("asmhc: 0x%x\n", val2);
3502 #endif
3505 void test_high_clobbers(void)
3507 #if defined __x86_64__ && !defined _WIN64
3508 long x1, x2;
3509 asm volatile("mov %%r12,%0" :: "m" (x1)); /* save r12 */
3510 test_high_clobbers_really();
3511 asm volatile("mov %%r12,%0" :: "m" (x2)); /* new r12 */
3512 asm volatile("mov %0,%%r12" :: "m" (x1)); /* restore r12 */
3513 /* should be 0 but tcc doesn't save r12 automatically, which has
3514 bad effects when gcc helds TCCState *s in r12 in tcc.c:main */
3515 //printf("r12-clobber-diff: %lx\n", x2 - x1);
3516 #endif
3519 static long cpu_number;
3520 void trace_console(long len, long len2)
3522 #ifdef __x86_64__
3523 /* This generated invalid code when the emission of the switch
3524 table isn't disabled. The asms are necessary to show the bug,
3525 normal statements don't work (they need to generate some code
3526 even under nocode_wanted, which normal statements don't do,
3527 but asms do). Also at least these number of cases is necessary
3528 to generate enough "random" bytes. They ultimately are enough
3529 to create invalid instruction patterns to which the first
3530 skip-to-decision-table jump jumps. If decision table emission
3531 is disabled all of this is no problem.
3533 It also is necessary that the switches are in a statement expression
3534 (which has the property of not being enterable from outside. no
3535 matter what). */
3536 if (0
3539 long pscr_ret__;
3540 switch(len) {
3541 case 4:
3543 long pfo_ret__;
3544 switch (len2) {
3545 case 8: printf("bla"); pfo_ret__ = 42; break;
3547 pscr_ret__ = pfo_ret__;
3549 break;
3550 case 8:
3552 long pfo_ret__;
3553 switch (len2) {
3554 case 1:asm("movq %1,%0": "=r" (pfo_ret__) : "m" (cpu_number)); break;
3555 case 2:asm("movq %1,%0": "=r" (pfo_ret__) : "m" (cpu_number)); break;
3556 case 4:asm("movq %1,%0": "=r" (pfo_ret__) : "m" (cpu_number)); break;
3557 case 8:asm("movq %1,%0": "=r" (pfo_ret__) : "m" (cpu_number)); break;
3558 default: printf("impossible\n");
3560 pscr_ret__ = pfo_ret__;
3562 break;
3564 pscr_ret__;
3567 printf("huh?\n");
3569 #endif
3572 void test_asm_dead_code(void)
3574 long rdi;
3575 /* Try to make sure that xdi contains a zero, and hence will
3576 lead to a segfault if the next asm is evaluated without
3577 arguments being set up. */
3578 asm volatile ("" : "=D" (rdi) : "0" (0));
3579 (void)sizeof (({
3580 int var;
3581 /* This shouldn't trigger a segfault, either the argument
3582 registers need to be set up and the asm emitted despite
3583 this being in an unevaluated context, or both the argument
3584 setup _and_ the asm emission need to be suppressed. The latter
3585 is better. Disabling asm code gen when suppression is on
3586 also fixes the above trace_console bug, but that came earlier
3587 than asm suppression. */
3588 asm volatile ("movl $0,(%0)" : : "D" (&var) : "memory");
3589 var;
3590 }));
3593 void test_asm_call(void)
3595 #if defined __x86_64__ && !defined _WIN64
3596 static char str[] = "PATH";
3597 char *s;
3598 /* This tests if a reference to an undefined symbol from an asm
3599 block, which isn't otherwise referenced in this file, is correctly
3600 regarded as global symbol, so that it's resolved by other object files
3601 or libraries. We chose getenv here, which isn't used anywhere else
3602 in this file. (If we used e.g. printf, which is used we already
3603 would have a global symbol entry, not triggering the bug which is
3604 tested here). */
3605 /* two pushes so stack remains aligned */
3606 asm volatile ("push %%rdi; push %%rdi; mov %0, %%rdi;"
3607 #if 1 && !defined(__TINYC__) && (defined(__PIC__) || defined(__PIE__)) && !defined(__APPLE__)
3608 "call getenv@plt;"
3609 #elif defined(__APPLE__)
3610 "call _getenv;"
3611 #else
3612 "call getenv;"
3613 #endif
3614 "pop %%rdi; pop %%rdi"
3615 : "=a" (s) : "r" (str));
3616 printf("asmd: %s\n", s);
3617 #endif
3620 #if defined __x86_64__
3621 # define RX "(%rip)"
3622 #else
3623 # define RX
3624 #endif
3626 void asm_dot_test(void)
3628 #ifndef __APPLE__
3629 int x;
3630 for (x = 1;; ++x) {
3631 int r = x;
3632 switch (x) {
3633 case 1:
3634 asm(".text; lea S"RX",%eax; lea ."RX",%ecx; sub %ecx,%eax; S=.; jmp p0");
3635 case 2:
3636 #ifndef __clang__
3637 /* clangs internal assembler is broken */
3638 asm(".text; jmp .+6; .int 123; mov .-4"RX",%eax; jmp p0");
3639 #else
3640 asm(".text; mov $123, %eax; jmp p0");
3641 #endif
3642 case 3:
3643 #if !defined(_WIN32) && !defined(__clang__)
3644 asm(".pushsection \".data\"; Y=.; .int 999; X=Y; .int 456; X=.-4; .popsection");
3645 #else
3646 asm(".data; Y=.; .int 999; X=Y; .int 456; X=.-4; .text");
3647 #endif
3648 asm(".text; mov X"RX",%eax; jmp p0");
3649 case 4:
3650 #ifdef __clang__
3651 /* Bah! Clang! Doesn't want to redefine 'X' */
3652 asm(".text; mov $789,%eax; jmp p0");
3653 #else
3654 #ifndef _WIN32
3655 asm(".data; X=.; .int 789; Y=.; .int 999; .previous");
3656 #else
3657 asm(".data; X=.; .int 789; Y=.; .int 999; .text");
3658 #endif
3659 asm(".text; mov X"RX",%eax; X=Y; jmp p0");
3660 #endif
3661 case 0:
3662 asm(".text; p0=.; mov %%eax,%0;" : "=m"(r)); break;
3664 if (r == x)
3665 break;
3666 printf("asm_dot_test %d: %d\n", x, r);
3668 #endif
3671 void asm_test(void)
3673 char buf[128];
3674 unsigned int val, val2;
3675 struct struct123 s1;
3676 struct struct1231 s2 = { (unsigned long)&s1 };
3677 /* Hide the outer base_func, but check later that the inline
3678 asm block gets the outer one. */
3679 int base_func = 42;
3680 void override_func3 (void);
3681 unsigned long asmret;
3682 #ifdef BOOL_ISOC99
3683 _Bool somebool;
3684 #endif
3685 register int regvar asm("%esi");
3687 // parse 0x1E-1 as 3 tokens in asm mode
3688 asm volatile ("mov $0x1E-1,%eax");
3690 /* test the no operand case */
3691 asm volatile ("xorl %eax, %eax");
3693 memcpy1(buf, "hello", 6);
3694 strncat1(buf, " worldXXXXX", 3);
3695 printf("%s\n", buf);
3697 memcpy2(buf, "hello", 6);
3698 strncat2(buf, " worldXXXXX", 3);
3699 printf("%s\n", buf);
3701 /* 'A' constraint test */
3702 printf("mul64=0x%Lx\n", mul64(0x12345678, 0xabcd1234));
3703 printf("inc64=0x%Lx\n", inc64(0x12345678ffffffff));
3705 s1.a = 42;
3706 s1.b = 43;
3707 printf("mconstraint: %d", mconstraint_test(&s2));
3708 printf(" %d %d\n", s1.a, s1.b);
3709 other_constraints_test();
3710 set = 0xff;
3711 sigdelset1(&set, 2);
3712 sigaddset1(&set, 16);
3713 /* NOTE: we test here if C labels are correctly restored after the
3714 asm statement */
3715 goto label1;
3716 label2:
3717 __asm__("btsl %1,%0" : "=m"(set) : "Ir"(20) : "cc");
3718 printf("set=0x%x\n", set);
3719 val = 0x01020304;
3720 printf("swab32(0x%08x) = 0x%0x\n", val, swab32(val));
3721 #ifndef _WIN32
3722 #ifndef __APPLE__
3723 override_func1();
3724 override_func2();
3725 /* The base_func ref from the following inline asm should find
3726 the global one, not the local decl from this function. */
3727 asm volatile(".weak override_func3\n.set override_func3, base_func");
3728 override_func3();
3729 printf("asmstr: %s\n", get_asm_string());
3730 asm_local_label_diff();
3731 #endif
3732 asm_local_statics();
3733 #endif
3734 #ifndef __clang__
3735 /* clang can't deal with the type change */
3736 /* Check that we can also load structs of appropriate layout
3737 into registers. */
3738 asm volatile("" : "=r" (asmret) : "0"(s2));
3739 if (asmret != s2.addr)
3740 printf("asmstr: failed\n");
3741 #endif
3742 #ifdef BOOL_ISOC99
3743 /* Check that the typesize correctly sets the register size to
3744 8 bit. */
3745 asm volatile("cmp %1,%2; sete %0" : "=a"(somebool) : "r"(1), "r"(2));
3746 if (!somebool)
3747 printf("asmbool: failed\n");
3748 #endif
3749 val = 43;
3750 fancy_copy (&val, &val2);
3751 printf ("fancycpy(%d)=%d\n", val, val2);
3752 val = 44;
3753 fancy_copy2 (&val, &val2);
3754 printf ("fancycpy2(%d)=%d\n", val, val2);
3755 asm volatile ("mov $0x4243, %%esi" : "=r" (regvar));
3756 printf ("regvar=%x\n", regvar);
3757 test_high_clobbers();
3758 trace_console(8, 8);
3759 test_asm_dead_code();
3760 test_asm_call();
3761 asm_dot_test();
3762 return;
3763 label1:
3764 goto label2;
3767 #else
3769 void asm_test(void)
3773 #endif
3775 #define COMPAT_TYPE(type1, type2) \
3777 printf("__builtin_types_compatible_p(%s, %s) = %d\n", #type1, #type2, \
3778 __builtin_types_compatible_p (type1, type2));\
3781 int constant_p_var;
3783 int func(void);
3785 void builtin_test(void)
3787 short s;
3788 int i;
3789 long long ll;
3790 #if GCC_MAJOR >= 3
3791 COMPAT_TYPE(int, int);
3792 COMPAT_TYPE(int, unsigned int);
3793 COMPAT_TYPE(int, char);
3794 COMPAT_TYPE(int, const int);
3795 COMPAT_TYPE(int, volatile int);
3796 COMPAT_TYPE(int *, int *);
3797 COMPAT_TYPE(int *, void *);
3798 COMPAT_TYPE(int *, const int *);
3799 COMPAT_TYPE(char *, unsigned char *);
3800 COMPAT_TYPE(char *, signed char *);
3801 COMPAT_TYPE(char *, char *);
3802 /* space is needed because tcc preprocessor introduces a space between each token */
3803 COMPAT_TYPE(char * *, void *);
3804 #endif
3805 printf("res1 = %d\n", __builtin_constant_p(1));
3806 printf("res2 = %d\n", __builtin_constant_p(1 + 2));
3807 printf("res3 = %d\n", __builtin_constant_p(&constant_p_var));
3808 printf("res4 = %d\n", __builtin_constant_p(constant_p_var));
3809 printf("res5 = %d\n", __builtin_constant_p(100000 / constant_p_var));
3810 #ifdef __clang__
3811 /* clang doesn't regard this as constant expression */
3812 printf("res6 = 1\n");
3813 #else
3814 printf("res6 = %d\n", __builtin_constant_p(i && 0));
3815 #endif
3816 printf("res7 = %d\n", __builtin_constant_p(i && 1));
3817 #ifdef __clang__
3818 /* clang doesn't regard this as constant expression */
3819 printf("res8 = 1\n");
3820 #else
3821 printf("res8 = %d\n", __builtin_constant_p(i && 0 ? i : 34));
3822 #endif
3823 printf("res9 = %d\n", __builtin_constant_p("hi"));
3824 printf("res10 = %d\n", __builtin_constant_p(func()));
3825 s = 1;
3826 ll = 2;
3827 i = __builtin_choose_expr (1 != 0, ll, s);
3828 printf("bce: %d\n", i);
3829 i = __builtin_choose_expr (1 != 1, ll, s);
3830 printf("bce: %d\n", i);
3831 i = sizeof (__builtin_choose_expr (1, ll, s));
3832 printf("bce: %d\n", i);
3833 i = sizeof (__builtin_choose_expr (0, ll, s));
3834 printf("bce: %d\n", i);
3836 //printf("bera: %p\n", __builtin_extract_return_addr((void*)43));
3839 #ifdef _WIN32
3840 void weak_test(void) {}
3841 #else
3842 extern int __attribute__((weak)) weak_f1(void);
3843 extern int __attribute__((weak)) weak_f2(void);
3844 extern int weak_f3(void);
3845 extern int __attribute__((weak)) weak_v1;
3846 extern int __attribute__((weak)) weak_v2;
3847 extern int weak_v3;
3849 extern int (*weak_fpa)() __attribute__((weak));
3850 extern int __attribute__((weak)) (*weak_fpb)();
3851 extern __attribute__((weak)) int (*weak_fpc)();
3853 extern int weak_asm_f1(void) asm("weak_asm_f1x") __attribute((weak));
3854 extern int __attribute((weak)) weak_asm_f2(void) asm("weak_asm_f2x") ;
3855 extern int __attribute((weak)) weak_asm_f3(void) asm("weak_asm_f3x") __attribute((weak));
3856 extern int weak_asm_v1 asm("weak_asm_v1x") __attribute((weak));
3857 extern int __attribute((weak)) weak_asm_v2 asm("weak_asm_v2x") ;
3858 extern int __attribute((weak)) weak_asm_v3(void) asm("weak_asm_v3x") __attribute((weak));
3860 #ifndef __clang__
3861 static const size_t dummy = 0;
3862 extern __typeof(dummy) weak_dummy1 __attribute__((weak, alias("dummy")));
3863 extern __typeof(dummy) __attribute__((weak, alias("dummy"))) weak_dummy2;
3864 extern __attribute__((weak, alias("dummy"))) __typeof(dummy) weak_dummy3;
3865 #endif
3867 int some_lib_func(void);
3868 int dummy_impl_of_slf(void) { return 444; }
3869 #ifndef __clang__
3870 int some_lib_func(void) __attribute__((weak, alias("dummy_impl_of_slf")));
3871 #endif
3873 int weak_toolate() __attribute__((weak));
3874 int weak_toolate() { return 0; }
3876 void __attribute__((weak)) weak_test(void)
3878 printf("weak_f1=%d\n", weak_f1 ? weak_f1() : 123);
3879 printf("weak_f2=%d\n", weak_f2 ? weak_f2() : 123);
3880 printf("weak_f3=%d\n", weak_f3 ? weak_f3() : 123);
3881 printf("weak_v1=%d\n",&weak_v1 ? weak_v1 : 123);
3882 printf("weak_v2=%d\n",&weak_v2 ? weak_v2 : 123);
3883 printf("weak_v3=%d\n",&weak_v3 ? weak_v3 : 123);
3885 printf("weak_fpa=%d\n",&weak_fpa ? weak_fpa() : 123);
3886 printf("weak_fpb=%d\n",&weak_fpb ? weak_fpb() : 123);
3887 printf("weak_fpc=%d\n",&weak_fpc ? weak_fpc() : 123);
3889 printf("weak_asm_f1=%d\n", weak_asm_f1 != NULL);
3890 printf("weak_asm_f2=%d\n", weak_asm_f2 != NULL);
3891 printf("weak_asm_f3=%d\n", weak_asm_f3 != NULL);
3892 printf("weak_asm_v1=%d\n",&weak_asm_v1 != NULL);
3893 printf("weak_asm_v2=%d\n",&weak_asm_v2 != NULL);
3894 printf("weak_asm_v3=%d\n",&weak_asm_v3 != NULL);
3895 #ifdef __clang__
3896 printf("some_lib_func=444\n");
3897 #else
3898 printf("some_lib_func=%d\n", &some_lib_func ? some_lib_func() : 0);
3899 #endif
3902 int __attribute__((weak)) weak_f2() { return 222; }
3903 int __attribute__((weak)) weak_f3() { return 333; }
3904 int __attribute__((weak)) weak_v2 = 222;
3905 int __attribute__((weak)) weak_v3 = 333;
3906 #endif
3908 void const_func(const int a)
3912 void const_warn_test(void)
3914 const_func(1);
3917 struct condstruct {
3918 int i;
3921 int getme (struct condstruct *s, int i)
3923 int i1 = (i == 0 ? 0 : s)->i;
3924 int i2 = (i == 0 ? s : 0)->i;
3925 int i3 = (i == 0 ? (void*)0 : s)->i;
3926 int i4 = (i == 0 ? s : (void*)0)->i;
3927 return i1 + i2 + i3 + i4;
3930 struct global_data
3932 int a[40];
3933 int *b[40];
3936 struct global_data global_data;
3938 int global_data_getstuff (int *, int);
3940 void global_data_callit (int i)
3942 *global_data.b[i] = global_data_getstuff (global_data.b[i], 1);
3945 int global_data_getstuff (int *p, int i)
3947 return *p + i;
3950 void global_data_test (void)
3952 global_data.a[0] = 42;
3953 global_data.b[0] = &global_data.a[0];
3954 global_data_callit (0);
3955 printf ("%d\n", global_data.a[0]);
3958 struct cmpcmpS
3960 unsigned char fill : 3;
3961 unsigned char b1 : 1;
3962 unsigned char b2 : 1;
3963 unsigned char fill2 : 3;
3966 int glob1, glob2, glob3;
3968 void compare_comparisons (struct cmpcmpS *s)
3970 if (s->b1 != (glob1 == glob2)
3971 || (s->b2 != (glob1 == glob3)))
3972 printf ("comparing comparisons broken\n");
3975 void cmp_comparison_test(void)
3977 struct cmpcmpS s;
3978 s.b1 = 1;
3979 glob1 = 42; glob2 = 42;
3980 s.b2 = 0;
3981 glob3 = 43;
3982 compare_comparisons (&s);
3985 int fcompare (double a, double b, int code)
3987 switch (code) {
3988 case 0: return a == b;
3989 case 1: return a != b;
3990 case 2: return a < b;
3991 case 3: return a >= b;
3992 case 4: return a > b;
3993 case 5: return a <= b;
3995 return 0;
3998 void math_cmp_test(void)
4000 double nan = 0.0/0.0;
4001 double one = 1.0;
4002 double two = 2.0;
4003 int comp = 0;
4004 int v;
4005 #define bug(a,b,op,iop,part) printf("Test broken: %s %s %s %s %d\n", #a, #b, #op, #iop, part)
4007 /* This asserts that "a op b" is _not_ true, but "a iop b" is true.
4008 And it does this in various ways so that all code generation paths
4009 are checked (generating inverted tests, or non-inverted tests, or
4010 producing a 0/1 value without jumps (that's done in the fcompare
4011 function). */
4012 #define FCMP(a,b,op,iop,code) \
4013 if (fcompare (a,b,code)) \
4014 bug (a,b,op,iop,1); \
4015 if (a op b) \
4016 bug (a,b,op,iop,2); \
4017 if (a iop b) \
4019 else \
4020 bug (a,b,op,iop,3); \
4021 if ((a op b) || comp) \
4022 bug (a,b,op,iop,4); \
4023 if ((a iop b) || comp) \
4025 else \
4026 bug (a,b,op,iop,5); \
4027 if (v = !(a op b), !v) bug(a,b,op,iop,7);
4029 /* Equality tests. */
4030 FCMP(nan, nan, ==, !=, 0);
4031 FCMP(one, two, ==, !=, 0);
4032 FCMP(one, one, !=, ==, 1);
4033 /* Non-equality is a bit special. */
4034 if (!fcompare (nan, nan, 1))
4035 bug (nan, nan, !=, ==, 6);
4037 /* Relational tests on numbers. */
4038 FCMP(two, one, <, >=, 2);
4039 FCMP(one, two, >=, <, 3);
4040 FCMP(one, two, >, <=, 4);
4041 FCMP(two, one, <=, >, 5);
4043 /* Relational tests on NaNs. Note that the inverse op here is
4044 always !=, there's no operator in C that is equivalent to !(a < b),
4045 when NaNs are involved, same for the other relational ops. */
4046 FCMP(nan, nan, <, !=, 2);
4047 FCMP(nan, nan, >=, !=, 3);
4048 FCMP(nan, nan, >, !=, 4);
4049 FCMP(nan, nan, <=, !=, 5);
4052 double get100 () { return 100.0; }
4054 void callsave_test(void)
4056 #if defined __i386__ || defined __x86_64__ || defined __arm__
4057 int i, s; double *d; double t;
4058 s = sizeof (double);
4059 printf ("callsavetest: %d\n", s);
4060 d = alloca (sizeof(double));
4061 d[0] = 10.0;
4062 /* x86-64 had a bug were the next call to get100 would evict
4063 the lvalue &d[0] as VT_LLOCAL, and the reload would be done
4064 in int type, not pointer type. When alloca returns a pointer
4065 with the high 32 bit set (which is likely on x86-64) the access
4066 generates a segfault. */
4067 i = d[0] > get100 ();
4068 printf ("%d\n", i);
4069 #endif
4073 void bfa3(ptrdiff_t str_offset)
4075 printf("bfa3: %s\n", (char *)__builtin_frame_address(3) + str_offset);
4077 void bfa2(ptrdiff_t str_offset)
4079 printf("bfa2: %s\n", (char *)__builtin_frame_address(2) + str_offset);
4080 bfa3(str_offset);
4082 void bfa1(ptrdiff_t str_offset)
4084 printf("bfa1: %s\n", (char *)__builtin_frame_address(1) + str_offset);
4085 bfa2(str_offset);
4088 void builtin_frame_address_test(void)
4090 /* builtin_frame_address fails on ARM with gcc which make test3 fail */
4091 #ifndef __arm__
4092 char str[] = "__builtin_frame_address";
4093 char *fp0 = __builtin_frame_address(0);
4095 printf("str: %s\n", str);
4096 #ifndef __riscv // gcc dumps core. tcc, clang work
4097 bfa1(str-fp0);
4098 #endif
4099 #endif
4102 char via_volatile (char i)
4104 char volatile vi;
4105 vi = i;
4106 return vi;
4109 void volatile_test(void)
4111 if (via_volatile (42) != 42)
4112 printf (" broken\n");
4113 else
4114 printf (" ok\n");
4117 struct __attribute__((__packed__)) Spacked {
4118 char a;
4119 short b;
4120 int c;
4122 struct Spacked spacked;
4123 typedef struct __attribute__((__packed__)) {
4124 char a;
4125 short b;
4126 int c;
4127 } Spacked2;
4128 Spacked2 spacked2;
4129 typedef struct Spacked3_s {
4130 char a;
4131 short b;
4132 int c;
4133 } __attribute__((__packed__)) Spacked3;
4134 Spacked3 spacked3;
4135 struct gate_struct64 {
4136 unsigned short offset_low;
4137 unsigned short segment;
4138 unsigned ist : 3, zero0 : 5, type : 5, dpl : 2, p : 1;
4139 unsigned short offset_middle;
4140 unsigned offset_high;
4141 unsigned zero1;
4142 } __attribute__((packed));
4143 typedef struct gate_struct64 gate_desc;
4144 gate_desc a_gate_desc;
4145 void attrib_test(void)
4147 #ifndef _WIN32
4148 printf("attr: %d %d %d %d\n", sizeof(struct Spacked),
4149 sizeof(spacked), sizeof(Spacked2), sizeof(spacked2));
4150 printf("attr: %d %d\n", sizeof(Spacked3), sizeof(spacked3));
4151 printf("attr: %d %d\n", sizeof(gate_desc), sizeof(a_gate_desc));
4152 #endif
4154 extern __attribute__((__unused__)) char * __attribute__((__unused__)) *
4155 strange_attrib_placement (void);
4157 void * __attribute__((__unused__)) get_void_ptr (void *a)
4159 return a;
4162 /* This part checks for a bug in TOK_GET (used for inline expansion),
4163 where the large long long constant left the the high bits set for
4164 the integer constant token. */
4165 static inline
4166 int __get_order(unsigned long long size)
4168 int order;
4169 size -= 0xffff880000000000ULL; // this const left high bits set in the token
4171 struct S { int i : 1; } s; // constructed for this '1'
4173 order = size;
4174 return order;
4177 /* This just forces the above inline function to be actually emitted. */
4178 int force_get_order(unsigned long s)
4180 return __get_order(s);
4183 #define pv(m) printf(sizeof (s->m + 0) == 8 ? "%016llx\n" : "%02x\n", s->m)
4185 /* Test failed when using bounds checking */
4186 void bounds_check1_test (void)
4188 struct s {
4189 int x;
4190 long long y;
4191 } _s, *s = &_s;
4192 s->x = 10;
4193 s->y = 20;
4194 pv(x);
4195 pv(y);
4198 /* This failed on arm64/riscv64 */
4199 void map_add(int a, int b, int c, int d, int e, int f, int g, int h, int i)
4201 printf ("%d %d %d %d %d %d %d %d %d\n", a, b, c, d, e, f, g, h, i);
4204 void func_arg_test(void)
4206 int a = 0;
4207 int b = 1;
4208 map_add(0, 1, 2, 3, 4, 5, 6, 7, a && b);
4211 /* gcc 2.95.3 does not handle correctly CR in strings or after strays */
4212 #define CORRECT_CR_HANDLING
4214 /* deprecated and no longer supported in gcc 3.3 */
4215 #ifdef __TINYC__
4216 # define ACCEPT_CR_IN_STRINGS
4217 #endif
4219 /* keep this as the last test because GCC messes up line-numbers
4220 with the ^L^K^M characters below */
4221 void whitespace_test(void)
4223 char *str;
4225 \f\v #if 1
4226 pri\
4227 ntf("whitspace:\n");\f\v
4228 #endif
4229 pf("N=%d\n", 2);
4231 #ifdef CORRECT_CR_HANDLING
4232 pri\
4233 ntf("aaa=%d\n", 3);
4234 #endif
4236 pri\
4238 ntf("min=%d\n", 4);
4240 #ifdef ACCEPT_CR_IN_STRINGS
4241 printf("len1=%d\n", strlen("
4242 "));
4243 #ifdef CORRECT_CR_HANDLING
4244 str = "
4246 printf("len1=%d str[0]=%d\n", strlen(str), str[0]);
4247 #endif
4248 printf("len1=%d\n", strlen(" a
4249 "));
4250 #else
4251 printf("len1=1\nlen1=1 str[0]=10\nlen1=3\n");
4252 #endif /* ACCEPT_CR_IN_STRINGS */
4254 #ifdef __LINE__
4255 printf("__LINE__ defined\n");
4256 #endif
4258 #if 0
4259 /* wrong with GCC */
4260 printf("__LINE__=%d __FILE__=%s\n", __LINE__, __FILE__);
4261 #line 1111
4262 printf("__LINE__=%d __FILE__=%s\n", __LINE__, __FILE__);
4263 #line 2222 "test"
4264 printf("__LINE__=%d __FILE__=%s\n", __LINE__, __FILE__);
4265 #endif
4268 #define RUN(test) puts("---- " #test " ----"), test(), puts("")
4270 int main(int argc, char **argv)
4272 RUN(whitespace_test);
4273 RUN(macro_test);
4274 RUN(recursive_macro_test);
4275 RUN(string_test);
4276 RUN(expr_test);
4277 RUN(scope_test);
4278 RUN(scope2_test);
4279 RUN(forward_test);
4280 RUN(funcptr_test);
4281 RUN(if_test);
4282 RUN(loop_test);
4283 RUN(switch_test);
4284 RUN(goto_test);
4285 RUN(enum_test);
4286 RUN(typedef_test);
4287 RUN(struct_test);
4288 RUN(array_test);
4289 RUN(expr_ptr_test);
4290 RUN(bool_test);
4291 RUN(optimize_out_test);
4292 RUN(expr2_test);
4293 RUN(constant_expr_test);
4294 RUN(expr_cmp_test);
4295 RUN(char_short_test);
4296 RUN(init_test);
4297 RUN(compound_literal_test);
4298 RUN(kr_test);
4299 RUN(struct_assign_test);
4300 RUN(cast_test);
4301 RUN(bitfield_test);
4302 RUN(c99_bool_test);
4303 RUN(float_test);
4304 RUN(longlong_test);
4305 RUN(manyarg_test);
4306 RUN(stdarg_test);
4307 RUN(relocation_test);
4308 RUN(old_style_function_test);
4309 RUN(alloca_test);
4310 RUN(c99_vla_test);
4311 RUN(sizeof_test);
4312 RUN(typeof_test);
4313 RUN(statement_expr_test);
4314 RUN(local_label_test);
4315 RUN(asm_test);
4316 RUN(builtin_test);
4317 RUN(weak_test);
4318 RUN(global_data_test);
4319 RUN(cmp_comparison_test);
4320 RUN(math_cmp_test);
4321 RUN(callsave_test);
4322 RUN(builtin_frame_address_test);
4323 RUN(volatile_test);
4324 RUN(attrib_test);
4325 RUN(bounds_check1_test);
4326 RUN(func_arg_test);
4328 return 0;