History

mutiples fix for _Generic

* check that _Generic don't match unsigned char * with char * this case is usefull as with -funsigned-char, 'char *' are unsigned * change VT_LONG so it's now a qualifier VT_LONG are never use for code generation, but only durring parsing state, in _Generic we need to be able to make diference between 'long' and 'long long' So VT_LONG is now use as a type qualifier, it's old behaviour is still here, but we can keep trace of what was a long and what wasn't * add TOK_CLONG and TOK_CULONG tcc was directly converting value like '7171L' into TOK_CLLONG or TOK_CINT depending of the machine architecture. because of that, we was unable to make diference between a long and a long long, which doesn't work with _Generic. So now 7171L is a TOK_CLONG, and we can handle _Generic properly * check that _Generic can make diference between long and long long * uncomment "type match twice" as it should now pass tests on any platforms * add inside_generic global the point of this variable is to use VT_LONG in comparaison only when we are evaluating a _Generic. problem is with my lastest patchs tcc can now make the diference between a 'long long' and a 'long', but in 64 bit stddef.h typedef uint64_t as typedef signed long long int int64_t and stdint.h as unsigned long int, so tcc break when stdint.h and stddef.h are include together. Another solution woud be to modifie include/stddef.h so it define uint64_t as unsigned long int when processor is 64 bit, but this could break some legacy code, so for now, VT_LONG are use only inside generc. * check that _Generic parse first argument correctly * check that _Generic evaluate correctly exresion like "f() / 2"

matthias committed 9 years ago

Commit fdc18d31 parent 0cc24d05 files · +106 −23Browse files

Unified · Split

5 files
  1. tcc.h +11 −2
  2. tccgen.c +42 −14
  3. tccpp.c +36 −3
  4. tests/tests2/94_generic.c +13 −3
  5. tests/tests2/94_generic.expect +4 −1
tcc.h+11−2
@@ -849,7 +849,6 @@ struct filespec { · 848 unmodified lines
849#define VT_DOUBLE 9 /* IEEE double */849#define VT_DOUBLE 9 /* IEEE double */
850#define VT_LDOUBLE 10 /* IEEE long double */850#define VT_LDOUBLE 10 /* IEEE long double */
851#define VT_BOOL 11 /* ISOC99 boolean type */851#define VT_BOOL 11 /* ISOC99 boolean type */
852#define VT_LONG 12 /* long integer (NEVER USED as type, only during parsing) */
853#define VT_QLONG 13 /* 128-bit integer. Only used for x86-64 ABI */852#define VT_QLONG 13 /* 128-bit integer. Only used for x86-64 ABI */
854#define VT_QFLOAT 14 /* 128-bit float. Only used for x86-64 ABI */853#define VT_QFLOAT 14 /* 128-bit float. Only used for x86-64 ABI */
855 854
@@ -860,6 +859,7 @@ struct filespec { · 4 unmodified lines
860#define VT_CONSTANT 0x0100 /* const modifier */859#define VT_CONSTANT 0x0100 /* const modifier */
861#define VT_VOLATILE 0x0200 /* volatile modifier */860#define VT_VOLATILE 0x0200 /* volatile modifier */
862#define VT_VLA 0x0400 /* VLA type (also has VT_PTR and VT_ARRAY) */861#define VT_VLA 0x0400 /* VLA type (also has VT_PTR and VT_ARRAY) */
862#define VT_LONG 0x0800
863 863
864/* storage */864/* storage */
865#define VT_EXTERN 0x00001000 /* extern definition */865#define VT_EXTERN 0x00001000 /* extern definition */
@@ -939,7 +939,16 @@ struct filespec { · 73 unmodified lines
939#define TOK_TWOSHARPS 0xca /* ## preprocessing token */939#define TOK_TWOSHARPS 0xca /* ## preprocessing token */
940#define TOK_PLCHLDR 0xcb /* placeholder token as defined in C99 */940#define TOK_PLCHLDR 0xcb /* placeholder token as defined in C99 */
941#define TOK_NOSUBST 0xcc /* means following token has already been pp'd */941#define TOK_NOSUBST 0xcc /* means following token has already been pp'd */
942#define TOK_PPJOIN 0xce /* A '##' in the right position to mean pasting */942#define TOK_PPJOIN 0xcd /* A '##' in the right position to mean pasting */
943
944#define TOK_CLONG 0xce /* long constant */
945#define TOK_CULONG 0xcf /* unsigned long constant */
946
947
948#if defined TCC_TARGET_X86_64 && !defined TCC_TARGET_PE
949 #define TCC_LONG_ARE_64_BIT
950#endif
951
943 952
944#define TOK_SHL 0x01 /* shift left */953#define TOK_SHL 0x01 /* shift left */
945#define TOK_SAR 0x02 /* signed shift right */954#define TOK_SAR 0x02 /* signed shift right */
tccgen.c+42−14
@@ -42,6 +42,7 @@ ST_DATA Sym *local_label_stack; · 41 unmodified lines
42static int local_scope;42static int local_scope;
43static int in_sizeof;43static int in_sizeof;
44static int section_sym;44static int section_sym;
45static int inside_generic;
45 46
46ST_DATA int vlas_in_scope; /* number of VLAs that are currently in scope */47ST_DATA int vlas_in_scope; /* number of VLAs that are currently in scope */
47ST_DATA int vla_sp_root_loc; /* vla_sp_loc for SP before any VLAs were pushed */48ST_DATA int vla_sp_root_loc; /* vla_sp_loc for SP before any VLAs were pushed */
@@ -2218,6 +2219,10 @@ redo: · 2170 unmodified lines
2218 } else if (bt1 == VT_LLONG || bt2 == VT_LLONG) {2219 } else if (bt1 == VT_LLONG || bt2 == VT_LLONG) {
2219 /* cast to biggest op */2220 /* cast to biggest op */
2220 t = VT_LLONG;2221 t = VT_LLONG;
2222 /* check if we need to keep type as long or as long long */
2223 if ((t1 & VT_LONG && (t2 & (VT_BTYPE | VT_LONG)) != VT_LLONG) ||
2224 (t2 & VT_LONG && (t1 & (VT_BTYPE | VT_LONG)) != VT_LLONG))
2225 t |= VT_LONG;
2221 /* convert to unsigned if it does not fit in a long long */2226 /* convert to unsigned if it does not fit in a long long */
2222 if ((t1 & (VT_BTYPE | VT_UNSIGNED | VT_BITFIELD)) == (VT_LLONG | VT_UNSIGNED) ||2227 if ((t1 & (VT_BTYPE | VT_UNSIGNED | VT_BITFIELD)) == (VT_LLONG | VT_UNSIGNED) ||
2223 (t2 & (VT_BTYPE | VT_UNSIGNED | VT_BITFIELD)) == (VT_LLONG | VT_UNSIGNED))2228 (t2 & (VT_BTYPE | VT_UNSIGNED | VT_BITFIELD)) == (VT_LLONG | VT_UNSIGNED))
@@ -2226,7 +2231,11 @@ redo: · 2 unmodified lines
2226 } else {2231 } else {
2227 /* integer operations */2232 /* integer operations */
2228 t = VT_INT;2233 t = VT_INT;
2229 /* convert to unsigned if it does not fit in an integer */2234
2235 if ((t1 & VT_LONG) || (t2 & VT_LONG))
2236 t |= VT_LONG;
2237
2238 /* convert to unsigned if it does not fit in an integer */
2230 if ((t1 & (VT_BTYPE | VT_UNSIGNED | VT_BITFIELD)) == (VT_INT | VT_UNSIGNED) ||2239 if ((t1 & (VT_BTYPE | VT_UNSIGNED | VT_BITFIELD)) == (VT_INT | VT_UNSIGNED) ||
2231 (t2 & (VT_BTYPE | VT_UNSIGNED | VT_BITFIELD)) == (VT_INT | VT_UNSIGNED))2240 (t2 & (VT_BTYPE | VT_UNSIGNED | VT_BITFIELD)) == (VT_INT | VT_UNSIGNED))
2232 t |= VT_UNSIGNED;2241 t |= VT_UNSIGNED;
@@ -2723,6 +2732,11 @@ static int compare_types(CType *type1, CType *type2, int unqualified) · 490 unmodified lines
2723 t1 &= ~(VT_CONSTANT | VT_VOLATILE);2732 t1 &= ~(VT_CONSTANT | VT_VOLATILE);
2724 t2 &= ~(VT_CONSTANT | VT_VOLATILE);2733 t2 &= ~(VT_CONSTANT | VT_VOLATILE);
2725 }2734 }
2735
2736 if (!inside_generic) {
2737 t1 &= ~VT_LONG;
2738 t2 &= ~VT_LONG;
2739 }
2726 /* Default Vs explicit signedness only matters for char */2740 /* Default Vs explicit signedness only matters for char */
2727 if ((t1 & VT_BTYPE) != VT_BYTE) {2741 if ((t1 & VT_BTYPE) != VT_BYTE) {
2728 t1 &= ~VT_DEFSIGN;2742 t1 &= ~VT_DEFSIGN;
@@ -2799,6 +2813,12 @@ static void type_to_str(char *buf, int buf_size, · 70 unmodified lines
2799 tstr = "enum ";2813 tstr = "enum ";
2800 goto tstruct;2814 goto tstruct;
2801 }2815 }
2816
2817 if (!bt && VT_LONG & t) {
2818 tstr = "long";
2819 goto add_tstr;
2820 }
2821
2802 switch(bt) {2822 switch(bt) {
2803 case VT_VOID:2823 case VT_VOID:
2804 tstr = "void";2824 tstr = "void";
@@ -2815,9 +2835,6 @@ static void type_to_str(char *buf, int buf_size, · 10 unmodified lines
2815 case VT_INT:2835 case VT_INT:
2816 tstr = "int";2836 tstr = "int";
2817 goto add_tstr;2837 goto add_tstr;
2818 case VT_LONG:
2819 tstr = "long";
2820 goto add_tstr;
2821 case VT_LLONG:2838 case VT_LLONG:
2822 tstr = "long long";2839 tstr = "long long";
2823 goto add_tstr;2840 goto add_tstr;
@@ -3960,10 +3977,10 @@ static int parse_btype(CType *type, AttributeDef *ad) · 1136 unmodified lines
3960 case TOK_LONG:3977 case TOK_LONG:
3961 if ((t & VT_BTYPE) == VT_DOUBLE) {3978 if ((t & VT_BTYPE) == VT_DOUBLE) {
3962#ifndef TCC_TARGET_PE3979#ifndef TCC_TARGET_PE
3963 t = (t & ~VT_BTYPE) | VT_LDOUBLE;3980 t = (t & ~(VT_LONG | VT_BTYPE)) | VT_LDOUBLE;
3964#endif3981#endif
3965 } else if ((t & VT_BTYPE) == VT_LONG) {3982 } else if (t & VT_LONG) {
3966 t = (t & ~VT_BTYPE) | VT_LLONG;3983 t = (t & ~(VT_LONG | VT_BTYPE)) | VT_LLONG;
3967 } else {3984 } else {
3968 u = VT_LONG;3985 u = VT_LONG;
3969 goto basic_type;3986 goto basic_type;
@@ -3984,11 +4001,11 @@ static int parse_btype(CType *type, AttributeDef *ad) · 14 unmodified lines
3984 u = VT_FLOAT;4001 u = VT_FLOAT;
3985 goto basic_type;4002 goto basic_type;
3986 case TOK_DOUBLE:4003 case TOK_DOUBLE:
3987 if ((t & VT_BTYPE) == VT_LONG) {4004 if (t & VT_LONG) {
3988#ifdef TCC_TARGET_PE4005#ifdef TCC_TARGET_PE
3989 t = (t & ~VT_BTYPE) | VT_DOUBLE;4006 t = (t & ~(VT_LONG | VT_BTYPE)) | VT_DOUBLE;
3990#else4007#else
3991 t = (t & ~VT_BTYPE) | VT_LDOUBLE;4008 t = (t & ~(VT_LONG | VT_BTYPE)) | VT_LDOUBLE;
3992#endif4009#endif
3993 } else {4010 } else {
3994 u = VT_DOUBLE;4011 u = VT_DOUBLE;
@@ -4122,7 +4139,7 @@ the_end: · 127 unmodified lines
4122 }4139 }
4123 4140
4124 /* long is never used as type */4141 /* long is never used as type */
4125 if ((t & VT_BTYPE) == VT_LONG)4142 if (t & VT_LONG)
4126#if PTR_SIZE == 8 && !defined TCC_TARGET_PE4143#if PTR_SIZE == 8 && !defined TCC_TARGET_PE
4127 t = (t & ~VT_BTYPE) | VT_LLONG;4144 t = (t & ~VT_BTYPE) | VT_LLONG;
4128#else4145#else
@@ -4552,7 +4569,16 @@ ST_FUNC void unary(void) · 423 unmodified lines
4552 case TOK_CLDOUBLE:4569 case TOK_CLDOUBLE:
4553 t = VT_LDOUBLE;4570 t = VT_LDOUBLE;
4554 goto push_tokc;4571 goto push_tokc;
4555 4572 case TOK_CLONG:
4573 case TOK_CULONG:
4574 #ifdef TCC_LONG_ARE_64_BIT
4575 t = VT_LLONG | VT_LONG;
4576 #else
4577 t = VT_INT | VT_LONG;
4578 #endif
4579 if (tok == TOK_CULONG)
4580 t |= VT_UNSIGNED;
4581 goto push_tokc;
4556 case TOK___FUNCTION__:4582 case TOK___FUNCTION__:
4557 if (!gnu_ext)4583 if (!gnu_ext)
4558 goto tok_identifier;4584 goto tok_identifier;
@@ -4906,8 +4932,9 @@ ST_FUNC void unary(void) · 347 unmodified lines
4906 4932
4907 next();4933 next();
4908 skip('(');4934 skip('(');
4935 inside_generic = 1;
4909 expr_type(&controlling_type, expr_eq);4936 expr_type(&controlling_type, expr_eq);
4910 controlling_type.t &= ~(VT_CONSTANT|VT_VOLATILE|VT_ARRAY);4937 controlling_type.t &= ~(VT_CONSTANT | VT_VOLATILE | VT_ARRAY);
4911 for (;;) {4938 for (;;) {
4912 learn = 0;4939 learn = 0;
4913 skip(',');4940 skip(',');
@@ -4926,7 +4953,7 @@ ST_FUNC void unary(void) · 12 unmodified lines
4926 type_decl(&cur_type, &ad_tmp, &itmp, TYPE_ABSTRACT);4953 type_decl(&cur_type, &ad_tmp, &itmp, TYPE_ABSTRACT);
4927 if (compare_types(&controlling_type, &cur_type, 0)) {4954 if (compare_types(&controlling_type, &cur_type, 0)) {
4928 if (has_match) {4955 if (has_match) {
4929 // tcc_error("type match twice");4956 tcc_error("type match twice");
4930 }4957 }
4931 has_match = 1;4958 has_match = 1;
4932 learn = 1;4959 learn = 1;
@@ -4950,6 +4977,7 @@ ST_FUNC void unary(void) · 17 unmodified lines
4950 }4977 }
4951 begin_macro(str, 1);4978 begin_macro(str, 1);
4952 next();4979 next();
4980 inside_generic = 0;
4953 expr_eq();4981 expr_eq();
4954 if (tok != TOK_EOF)4982 if (tok != TOK_EOF)
4955 expect(",");4983 expect(",");
tccpp.c+36−3
@@ -480,6 +480,8 @@ ST_FUNC const char *get_tok_str(int v, CValue *cv) · 479 unmodified lines
480 switch(v) {480 switch(v) {
481 case TOK_CINT:481 case TOK_CINT:
482 case TOK_CUINT:482 case TOK_CUINT:
483 case TOK_CLONG:
484 case TOK_CULONG:
483 case TOK_CLLONG:485 case TOK_CLLONG:
484 case TOK_CULLONG:486 case TOK_CULLONG:
485 /* XXX: not quite exact, but only useful for testing */487 /* XXX: not quite exact, but only useful for testing */
@@ -1014,6 +1016,10 @@ static inline int tok_size(const int *p) · 528 unmodified lines
1014 case TOK_LCHAR:1016 case TOK_LCHAR:
1015 case TOK_CFLOAT:1017 case TOK_CFLOAT:
1016 case TOK_LINENUM:1018 case TOK_LINENUM:
1019#ifndef TCC_LONG_ARE_64_BIT
1020 case TOK_CLONG;
1021 case TOK_CULONG;
1022#endif
1017 return 1 + 1;1023 return 1 + 1;
1018 case TOK_STR:1024 case TOK_STR:
1019 case TOK_LSTR:1025 case TOK_LSTR:
@@ -1023,6 +1029,10 @@ static inline int tok_size(const int *p) · 3 unmodified lines
1023 case TOK_CDOUBLE:1029 case TOK_CDOUBLE:
1024 case TOK_CLLONG:1030 case TOK_CLLONG:
1025 case TOK_CULLONG:1031 case TOK_CULLONG:
1032#ifdef TCC_LONG_ARE_64_BIT
1033 case TOK_CLONG;
1034 case TOK_CULONG;
1035#endif
1026 return 1 + 2;1036 return 1 + 2;
1027 case TOK_CLDOUBLE:1037 case TOK_CLDOUBLE:
1028 return 1 + LDOUBLE_SIZE / 4;1038 return 1 + LDOUBLE_SIZE / 4;
@@ -1138,6 +1148,10 @@ static void tok_str_add2(TokenString *s, int t, CValue *cv) · 109 unmodified lines
1138 case TOK_LCHAR:1148 case TOK_LCHAR:
1139 case TOK_CFLOAT:1149 case TOK_CFLOAT:
1140 case TOK_LINENUM:1150 case TOK_LINENUM:
1151#ifndef TCC_LONG_ARE_64_BIT
1152 case TOK_CLONG:
1153 case TOK_CULONG:
1154#endif
1141 str[len++] = cv->tab[0];1155 str[len++] = cv->tab[0];
1142 break;1156 break;
1143 case TOK_PPNUM:1157 case TOK_PPNUM:
@@ -1158,6 +1172,10 @@ static void tok_str_add2(TokenString *s, int t, CValue *cv) · 14 unmodified lines
1158 case TOK_CDOUBLE:1172 case TOK_CDOUBLE:
1159 case TOK_CLLONG:1173 case TOK_CLLONG:
1160 case TOK_CULLONG:1174 case TOK_CULLONG:
1175#ifdef TCC_LONG_ARE_64_BIT
1176 case TOK_CLONG:
1177 case TOK_CULONG:
1178#endif
1161#if LDOUBLE_SIZE == 81179#if LDOUBLE_SIZE == 8
1162 case TOK_CLDOUBLE:1180 case TOK_CLDOUBLE:
1163#endif1181#endif
@@ -1213,6 +1231,10 @@ static inline void TOK_GET(int *t, const int **pp, CValue *cv) · 49 unmodified lines
1213 case TOK_CCHAR:1231 case TOK_CCHAR:
1214 case TOK_LCHAR:1232 case TOK_LCHAR:
1215 case TOK_LINENUM:1233 case TOK_LINENUM:
1234#ifndef TCC_LONG_ARE_64_BIT
1235 case TOK_CLONG:
1236 case TOK_CULONG:
1237#endif
1216 tab[0] = *p++;1238 tab[0] = *p++;
1217 cv->i = (*t == TOK_CUINT) ? (unsigned)cv->i : (int)cv->i;1239 cv->i = (*t == TOK_CUINT) ? (unsigned)cv->i : (int)cv->i;
1218 break;1240 break;
@@ -1230,6 +1252,10 @@ static inline void TOK_GET(int *t, const int **pp, CValue *cv) · 11 unmodified lines
1230 case TOK_CDOUBLE:1252 case TOK_CDOUBLE:
1231 case TOK_CLLONG:1253 case TOK_CLLONG:
1232 case TOK_CULLONG:1254 case TOK_CULLONG:
1255#ifdef TCC_LONG_ARE_64_BIT
1256 case TOK_CLONG:
1257 case TOK_CULONG:
1258#endif
1233 n = 2;1259 n = 2;
1234 goto copy;1260 goto copy;
1235 case TOK_CLDOUBLE:1261 case TOK_CLDOUBLE:
@@ -2407,9 +2433,7 @@ static void parse_number(const char *p) · 1171 unmodified lines
2407 if (lcount && *(p - 1) != ch)2433 if (lcount && *(p - 1) != ch)
2408 tcc_error("incorrect integer suffix: %s", p1);2434 tcc_error("incorrect integer suffix: %s", p1);
2409 lcount++;2435 lcount++;
2410#if !defined TCC_TARGET_X86_64 || defined TCC_TARGET_PE
2411 if (lcount == 2)2436 if (lcount == 2)
2412#endif
2413 must_64bit = 1;2437 must_64bit = 1;
2414 ch = *p++;2438 ch = *p++;
2415 } else if (t == 'U') {2439 } else if (t == 'U') {
@@ -2426,6 +2450,13 @@ static void parse_number(const char *p) · 10 unmodified lines
2426 if (n & 0xffffffff00000000LL || must_64bit) {2450 if (n & 0xffffffff00000000LL || must_64bit) {
2427 tok = TOK_CLLONG;2451 tok = TOK_CLLONG;
2428 n1 = n >> 32;2452 n1 = n >> 32;
2453 } else if (lcount) {
2454#ifdef TCC_LONG_ARE_64_BIT
2455 n1 = n >> 32;
2456#else
2457 n1 = n;
2458#endif
2459 tok = TOK_CLONG;
2429 } else {2460 } else {
2430 tok = TOK_CINT;2461 tok = TOK_CINT;
2431 n1 = n;2462 n1 = n;
@@ -2435,7 +2466,9 @@ static void parse_number(const char *p) · 3 unmodified lines
2435 if (ucount || ((n1 >> 31) && (b != 10))) {2466 if (ucount || ((n1 >> 31) && (b != 10))) {
2436 if (tok == TOK_CLLONG)2467 if (tok == TOK_CLLONG)
2437 tok = TOK_CULLONG;2468 tok = TOK_CULLONG;
2438 else2469 else if (tok == TOK_CLONG)
2470 tok = TOK_CULONG;
2471 else
2439 tok = TOK_CUINT;2472 tok = TOK_CUINT;
2440 /* If decimal and no unsigned suffix, bump to 64 bits or throw error */2473 /* If decimal and no unsigned suffix, bump to 64 bits or throw error */
2441 } else if (n1 >> 31) {2474 } else if (n1 >> 31) {
tests/tests2/94_generic.c+13−3
@@ -20,6 +20,8 @@ int b_f() · 19 unmodified lines
20 return 10;20 return 10;
21}21}
22 22
23typedef int int_type1;
24
23#define gen_sw(a) _Generic(a, const char *: 1, default: 8, int: 123);25#define gen_sw(a) _Generic(a, const char *: 1, default: 8, int: 123);
24 26
25int main()27int main()
@@ -28,24 +30,32 @@ int main() · 2 unmodified lines
28 struct b titi;30 struct b titi;
29 const int * const ptr;31 const int * const ptr;
30 const char *ti;32 const char *ti;
33 int_type1 i2;
31 34
32 i = _Generic(a, int: a_f, const int: b_f)();35 i = _Generic(a, int: a_f, const int: b_f)();
33 printf("%d\n", i);36 printf("%d\n", i);
37 i = _Generic(a, int: a_f() / 2, const int: b_f() / 2);
38 printf("%d\n", i);
34 i = _Generic(ptr, int *:1, int * const:2, default:20);39 i = _Generic(ptr, int *:1, int * const:2, default:20);
35 printf("%d\n", i);40 printf("%d\n", i);
36 i = gen_sw(a);41 i = gen_sw(a);
37 printf("%d\n", i);42 printf("%d\n", i);
38 i = _Generic(titi, struct a:1, struct b:2, default:20);43 i = _Generic(titi, struct a:1, struct b:2, default:20);
39 printf("%d\n", i);44 printf("%d\n", i);
45 i = _Generic(i2, char: 1, int : 0);
46 printf("%d\n", i);
40 i = _Generic(a, char:1, int[4]:2, default:5);47 i = _Generic(a, char:1, int[4]:2, default:5);
41 printf("%d\n", i);48 printf("%d\n", i);
42 i = _Generic(17, int :1, int **:2);49 i = _Generic(17, int :1, int **:2);
43 printf("%d\n", i);50 printf("%d\n", i);
44 i = _Generic(17L, int :1, long :2);51 i = _Generic(17L, int :1, long :2, long long : 3);
45 printf("%d\n", i);52 printf("%d\n", i);
46 i = _Generic("17, io", const char *:1, char *:3, const int :2);53 i = _Generic("17, io", char *: 3, const char *: 1);
47 printf("%d\n", i);54 printf("%d\n", i);
48 i = _Generic(ti, const char *:1, char *:3, const int :2);55 i = _Generic(ti, const unsigned char *:1, const char *:4, char *:3,
56 const signed char *:2);
49 printf("%d\n", i);57 printf("%d\n", i);
58 printf("%s\n", _Generic(i + 2L, long: "long", int: "int",
59 long long: "long long"));
50 return 0;60 return 0;
51}61}
tests/tests2/94_generic.expect+4−1
@@ -1,9 +1,12 @@
120120
210
220320
31234123
4252
60
5575
6181
7292
83103
91114
12long

Keyboard shortcuts

General

Show keyboard shortcuts
?
Focus the current search
/

Issues and pull requests

Open filters
f

Issues, pull requests and Inbox

Select next item
j↓
Select previous item
k↑
Open selected item
Enter
Dismiss filters or clear selection
Esc

Repository code

Go to file
t