2 * TCC - Tiny C Compiler
4 * Copyright (c) 2001-2004 Fabrice Bellard
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
24 /********************************************************/
25 /* global variables */
27 /* loc : local variable index
28 ind : output code index
30 anon_sym: anonymous symbol index
32 ST_DATA
int rsym
, anon_sym
, ind
, loc
;
34 ST_DATA Sym
*global_stack
;
35 ST_DATA Sym
*local_stack
;
36 ST_DATA Sym
*define_stack
;
37 ST_DATA Sym
*global_label_stack
;
38 ST_DATA Sym
*local_label_stack
;
40 static Sym
*sym_free_first
;
41 static void **sym_pools
;
42 static int nb_sym_pools
;
44 static Sym
*all_cleanups
, *pending_gotos
;
45 static int local_scope
;
47 static int in_generic
;
48 static int section_sym
;
51 static SValue _vstack
[1 + VSTACK_SIZE
];
52 #define vstack (_vstack + 1)
54 ST_DATA
int const_wanted
; /* true if constant wanted */
55 ST_DATA
int nocode_wanted
; /* no code generation wanted */
56 #define unevalmask 0xffff /* unevaluated subexpression */
57 #define NODATA_WANTED (nocode_wanted > 0) /* no static data output wanted either */
58 #define STATIC_DATA_WANTED (nocode_wanted & 0xC0000000) /* only static data output */
60 /* Automagical code suppression ----> */
61 #define CODE_OFF() (nocode_wanted |= 0x20000000)
62 #define CODE_ON() (nocode_wanted &= ~0x20000000)
64 /* Clear 'nocode_wanted' at label if it was used */
65 ST_FUNC
void gsym(int t
) { if (t
) { gsym_addr(t
, ind
); CODE_ON(); }}
66 static int gind(void) { CODE_ON(); return ind
; }
68 /* Set 'nocode_wanted' after unconditional jumps */
69 static void gjmp_addr_acs(int t
) { gjmp_addr(t
); CODE_OFF(); }
70 static int gjmp_acs(int t
) { t
= gjmp(t
); CODE_OFF(); return t
; }
72 /* These are #undef'd at the end of this file */
73 #define gjmp_addr gjmp_addr_acs
77 ST_DATA
int global_expr
; /* true if compound literals must be allocated globally (used during initializers parsing */
78 ST_DATA CType func_vt
; /* current function return type (used by return instruction) */
79 ST_DATA
int func_var
; /* true if current function is variadic (used by return instruction) */
81 static int last_line_num
, new_file
, func_ind
; /* debug info control */
82 ST_DATA
const char *funcname
;
83 ST_DATA CType int_type
, func_old_type
, char_pointer_type
;
86 #define VT_SIZE_T (VT_INT | VT_UNSIGNED)
87 #define VT_PTRDIFF_T VT_INT
89 #define VT_SIZE_T (VT_LLONG | VT_UNSIGNED)
90 #define VT_PTRDIFF_T VT_LLONG
92 #define VT_SIZE_T (VT_LONG | VT_LLONG | VT_UNSIGNED)
93 #define VT_PTRDIFF_T (VT_LONG | VT_LLONG)
96 ST_DATA
struct switch_t
{
100 } **p
; int n
; /* list of case ranges */
101 int def_sym
; /* default symbol */
104 struct switch_t
*prev
;
106 } *cur_switch
; /* current switch */
108 #define MAX_TEMP_LOCAL_VARIABLE_NUMBER 8
109 /*list of temporary local variables on the stack in current function. */
110 ST_DATA
struct temp_local_variable
{
111 int location
; //offset on stack. Svalue.c.i
114 } arr_temp_local_vars
[MAX_TEMP_LOCAL_VARIABLE_NUMBER
];
115 short nb_temp_local_vars
;
117 static struct scope
{
119 struct { int loc
, num
; } vla
;
120 struct { Sym
*s
; int n
; } cl
;
123 } *cur_scope
, *loop_scope
, *root_scope
;
125 /********************************************************/
126 #ifndef CONFIG_TCC_ASM
127 ST_FUNC
void asm_instr(void)
129 tcc_error("inline asm() not supported");
131 ST_FUNC
void asm_global_instr(void)
133 tcc_error("inline asm() not supported");
137 /* ------------------------------------------------------------------------- */
139 static void gen_cast(CType
*type
);
140 static void gen_cast_s(int t
);
141 static inline CType
*pointed_type(CType
*type
);
142 static int is_compatible_types(CType
*type1
, CType
*type2
);
143 static int parse_btype(CType
*type
, AttributeDef
*ad
);
144 static CType
*type_decl(CType
*type
, AttributeDef
*ad
, int *v
, int td
);
145 static void parse_expr_type(CType
*type
);
146 static void init_putv(CType
*type
, Section
*sec
, unsigned long c
);
147 static void decl_initializer(CType
*type
, Section
*sec
, unsigned long c
, int flags
);
148 static void block(int is_expr
);
149 static void decl_initializer_alloc(CType
*type
, AttributeDef
*ad
, int r
, int has_init
, int v
, int scope
);
150 static void decl(int l
);
151 static int decl0(int l
, int is_for_loop_init
, Sym
*);
152 static void expr_eq(void);
153 static void vla_runtime_type_size(CType
*type
, int *a
);
154 static int is_compatible_unqualified_types(CType
*type1
, CType
*type2
);
155 static inline int64_t expr_const64(void);
156 static void vpush64(int ty
, unsigned long long v
);
157 static void vpush(CType
*type
);
158 static int gvtst(int inv
, int t
);
159 static void gen_inline_functions(TCCState
*s
);
160 static void free_inline_functions(TCCState
*s
);
161 static void skip_or_save_block(TokenString
**str
);
162 static void gv_dup(void);
163 static int get_temp_local_var(int size
,int align
);
164 static void clear_temp_local_var_list();
165 static void cast_error(CType
*st
, CType
*dt
);
167 ST_INLN
int is_float(int t
)
169 int bt
= t
& VT_BTYPE
;
170 return bt
== VT_LDOUBLE
176 static inline int is_integer_btype(int bt
)
185 static int btype_size(int bt
)
187 return bt
== VT_BYTE
|| bt
== VT_BOOL
? 1 :
191 bt
== VT_PTR
? PTR_SIZE
: 0;
194 /* returns function return register from type */
195 static int R_RET(int t
)
199 #ifdef TCC_TARGET_X86_64
200 if ((t
& VT_BTYPE
) == VT_LDOUBLE
)
202 #elif defined TCC_TARGET_RISCV64
203 if ((t
& VT_BTYPE
) == VT_LDOUBLE
)
209 /* returns 2nd function return register, if any */
210 static int R2_RET(int t
)
216 #elif defined TCC_TARGET_X86_64
221 #elif defined TCC_TARGET_RISCV64
228 /* returns true for two-word types */
229 #define USING_TWO_WORDS(t) (R2_RET(t) != VT_CONST)
231 /* put function return registers to stack value */
232 static void PUT_R_RET(SValue
*sv
, int t
)
234 sv
->r
= R_RET(t
), sv
->r2
= R2_RET(t
);
237 /* returns function return register class for type t */
238 static int RC_RET(int t
)
240 return reg_classes
[R_RET(t
)] & ~(RC_FLOAT
| RC_INT
);
243 /* returns generic register class for type t */
244 static int RC_TYPE(int t
)
248 #ifdef TCC_TARGET_X86_64
249 if ((t
& VT_BTYPE
) == VT_LDOUBLE
)
251 if ((t
& VT_BTYPE
) == VT_QFLOAT
)
253 #elif defined TCC_TARGET_RISCV64
254 if ((t
& VT_BTYPE
) == VT_LDOUBLE
)
260 /* returns 2nd register class corresponding to t and rc */
261 static int RC2_TYPE(int t
, int rc
)
263 if (!USING_TWO_WORDS(t
))
278 /* we use our own 'finite' function to avoid potential problems with
279 non standard math libs */
280 /* XXX: endianness dependent */
281 ST_FUNC
int ieee_finite(double d
)
284 memcpy(p
, &d
, sizeof(double));
285 return ((unsigned)((p
[1] | 0x800fffff) + 1)) >> 31;
288 /* compiling intel long double natively */
289 #if (defined __i386__ || defined __x86_64__) \
290 && (defined TCC_TARGET_I386 || defined TCC_TARGET_X86_64)
291 # define TCC_IS_NATIVE_387
294 ST_FUNC
void test_lvalue(void)
296 if (!(vtop
->r
& VT_LVAL
))
300 ST_FUNC
void check_vstack(void)
302 if (vtop
!= vstack
- 1)
303 tcc_error("internal compiler error: vstack leak (%d)", vtop
- vstack
+ 1);
306 /* ------------------------------------------------------------------------- */
307 /* vstack debugging aid */
310 void pv (const char *lbl
, int a
, int b
)
313 for (i
= a
; i
< a
+ b
; ++i
) {
314 SValue
*p
= &vtop
[-i
];
315 printf("%s vtop[-%d] : type.t:%04x r:%04x r2:%04x c.i:%d\n",
316 lbl
, i
, p
->type
.t
, p
->r
, p
->r2
, (int)p
->c
.i
);
321 /* ------------------------------------------------------------------------- */
322 /* start of translation unit info */
323 ST_FUNC
void tcc_debug_start(TCCState
*s1
)
328 /* file info: full path + filename */
329 section_sym
= put_elf_sym(symtab_section
, 0, 0,
330 ELFW(ST_INFO
)(STB_LOCAL
, STT_SECTION
), 0,
331 text_section
->sh_num
, NULL
);
332 getcwd(buf
, sizeof(buf
));
334 normalize_slashes(buf
);
336 pstrcat(buf
, sizeof(buf
), "/");
337 put_stabs_r(s1
, buf
, N_SO
, 0, 0,
338 text_section
->data_offset
, text_section
, section_sym
);
339 put_stabs_r(s1
, file
->prev
->filename
, N_SO
, 0, 0,
340 text_section
->data_offset
, text_section
, section_sym
);
341 new_file
= last_line_num
= 0;
343 /* we're currently 'including' the <command line> */
347 /* an elf symbol of type STT_FILE must be put so that STB_LOCAL
348 symbols can be safely used */
349 put_elf_sym(symtab_section
, 0, 0,
350 ELFW(ST_INFO
)(STB_LOCAL
, STT_FILE
), 0,
351 SHN_ABS
, file
->filename
);
354 /* put end of translation unit info */
355 ST_FUNC
void tcc_debug_end(TCCState
*s1
)
359 put_stabs_r(s1
, NULL
, N_SO
, 0, 0,
360 text_section
->data_offset
, text_section
, section_sym
);
363 static BufferedFile
* put_new_file(TCCState
*s1
)
365 BufferedFile
*f
= file
;
366 /* use upper file if from inline ":asm:" */
367 if (f
->filename
[0] == ':')
370 put_stabs_r(s1
, f
->filename
, N_SOL
, 0, 0, ind
, text_section
, section_sym
);
371 new_file
= last_line_num
= 0;
376 /* generate line number info */
377 ST_FUNC
void tcc_debug_line(TCCState
*s1
)
381 || cur_text_section
!= text_section
382 || !(f
= put_new_file(s1
))
383 || last_line_num
== f
->line_num
)
385 if (func_ind
!= -1) {
386 put_stabn(s1
, N_SLINE
, 0, f
->line_num
, ind
- func_ind
);
388 /* from tcc_assemble */
389 put_stabs_r(s1
, NULL
, N_SLINE
, 0, f
->line_num
, ind
, text_section
, section_sym
);
391 last_line_num
= f
->line_num
;
394 /* put function symbol */
395 ST_FUNC
void tcc_debug_funcstart(TCCState
*s1
, Sym
*sym
)
399 if (!s1
->do_debug
|| !(f
= put_new_file(s1
)))
401 /* XXX: we put here a dummy type */
402 snprintf(buf
, sizeof(buf
), "%s:%c1",
403 funcname
, sym
->type
.t
& VT_STATIC
? 'f' : 'F');
404 put_stabs_r(s1
, buf
, N_FUN
, 0, f
->line_num
, 0, cur_text_section
, sym
->c
);
408 /* put function size */
409 ST_FUNC
void tcc_debug_funcend(TCCState
*s1
, int size
)
413 put_stabn(s1
, N_FUN
, 0, 0, size
);
416 /* put alternative filename */
417 ST_FUNC
void tcc_debug_putfile(TCCState
*s1
, const char *filename
)
419 if (0 == strcmp(file
->filename
, filename
))
421 pstrcpy(file
->filename
, sizeof(file
->filename
), filename
);
425 /* begin of #include */
426 ST_FUNC
void tcc_debug_bincl(TCCState
*s1
)
430 put_stabs(s1
, file
->filename
, N_BINCL
, 0, 0, 0);
434 /* end of #include */
435 ST_FUNC
void tcc_debug_eincl(TCCState
*s1
)
439 put_stabn(s1
, N_EINCL
, 0, 0, 0);
443 /* ------------------------------------------------------------------------- */
444 /* initialize vstack and types. This must be done also for tcc -E */
445 ST_FUNC
void tccgen_init(TCCState
*s1
)
448 memset(vtop
, 0, sizeof *vtop
);
450 /* define some often used types */
452 char_pointer_type
.t
= VT_BYTE
;
453 mk_pointer(&char_pointer_type
);
454 func_old_type
.t
= VT_FUNC
;
455 func_old_type
.ref
= sym_push(SYM_FIELD
, &int_type
, 0, 0);
456 func_old_type
.ref
->f
.func_call
= FUNC_CDECL
;
457 func_old_type
.ref
->f
.func_type
= FUNC_OLD
;
460 ST_FUNC
int tccgen_compile(TCCState
*s1
)
462 cur_text_section
= NULL
;
464 anon_sym
= SYM_FIRST_ANOM
;
467 nocode_wanted
= 0x80000000;
471 #ifdef TCC_TARGET_ARM
475 printf("%s: **** new file\n", file
->filename
);
477 parse_flags
= PARSE_FLAG_PREPROCESS
| PARSE_FLAG_TOK_NUM
| PARSE_FLAG_TOK_STR
;
480 gen_inline_functions(s1
);
482 /* end of translation unit info */
487 ST_FUNC
void tccgen_finish(TCCState
*s1
)
489 free_inline_functions(s1
);
490 sym_pop(&global_stack
, NULL
, 0);
491 sym_pop(&local_stack
, NULL
, 0);
492 /* free preprocessor macros */
495 dynarray_reset(&sym_pools
, &nb_sym_pools
);
496 sym_free_first
= NULL
;
499 /* ------------------------------------------------------------------------- */
500 ST_FUNC ElfSym
*elfsym(Sym
*s
)
504 return &((ElfSym
*)symtab_section
->data
)[s
->c
];
507 /* apply storage attributes to Elf symbol */
508 ST_FUNC
void update_storage(Sym
*sym
)
511 int sym_bind
, old_sym_bind
;
517 if (sym
->a
.visibility
)
518 esym
->st_other
= (esym
->st_other
& ~ELFW(ST_VISIBILITY
)(-1))
521 if (sym
->type
.t
& (VT_STATIC
| VT_INLINE
))
522 sym_bind
= STB_LOCAL
;
523 else if (sym
->a
.weak
)
526 sym_bind
= STB_GLOBAL
;
527 old_sym_bind
= ELFW(ST_BIND
)(esym
->st_info
);
528 if (sym_bind
!= old_sym_bind
) {
529 esym
->st_info
= ELFW(ST_INFO
)(sym_bind
, ELFW(ST_TYPE
)(esym
->st_info
));
533 if (sym
->a
.dllimport
)
534 esym
->st_other
|= ST_PE_IMPORT
;
535 if (sym
->a
.dllexport
)
536 esym
->st_other
|= ST_PE_EXPORT
;
540 printf("storage %s: bind=%c vis=%d exp=%d imp=%d\n",
541 get_tok_str(sym
->v
, NULL
),
542 sym_bind
== STB_WEAK
? 'w' : sym_bind
== STB_LOCAL
? 'l' : 'g',
550 /* ------------------------------------------------------------------------- */
551 /* update sym->c so that it points to an external symbol in section
552 'section' with value 'value' */
554 ST_FUNC
void put_extern_sym2(Sym
*sym
, int sh_num
,
555 addr_t value
, unsigned long size
,
556 int can_add_underscore
)
558 int sym_type
, sym_bind
, info
, other
, t
;
562 #ifdef CONFIG_TCC_BCHECK
567 name
= get_tok_str(sym
->v
, NULL
);
568 #ifdef CONFIG_TCC_BCHECK
569 if (tcc_state
->do_bounds_check
) {
570 /* XXX: avoid doing that for statics ? */
571 /* if bound checking is activated, we change some function
572 names by adding the "__bound" prefix */
575 /* XXX: we rely only on malloc hooks */
597 strcpy(buf
, "__bound_");
605 if ((t
& VT_BTYPE
) == VT_FUNC
) {
607 } else if ((t
& VT_BTYPE
) == VT_VOID
) {
608 sym_type
= STT_NOTYPE
;
610 sym_type
= STT_OBJECT
;
612 if (t
& (VT_STATIC
| VT_INLINE
))
613 sym_bind
= STB_LOCAL
;
615 sym_bind
= STB_GLOBAL
;
618 if (sym_type
== STT_FUNC
&& sym
->type
.ref
) {
619 Sym
*ref
= sym
->type
.ref
;
620 if (ref
->a
.nodecorate
) {
621 can_add_underscore
= 0;
623 if (ref
->f
.func_call
== FUNC_STDCALL
&& can_add_underscore
) {
624 sprintf(buf1
, "_%s@%d", name
, ref
->f
.func_args
* PTR_SIZE
);
626 other
|= ST_PE_STDCALL
;
627 can_add_underscore
= 0;
631 if (tcc_state
->leading_underscore
&& can_add_underscore
) {
633 pstrcpy(buf1
+ 1, sizeof(buf1
) - 1, name
);
637 name
= get_tok_str(sym
->asm_label
, NULL
);
638 info
= ELFW(ST_INFO
)(sym_bind
, sym_type
);
639 sym
->c
= put_elf_sym(symtab_section
, value
, size
, info
, other
, sh_num
, name
);
642 esym
->st_value
= value
;
643 esym
->st_size
= size
;
644 esym
->st_shndx
= sh_num
;
649 ST_FUNC
void put_extern_sym(Sym
*sym
, Section
*section
,
650 addr_t value
, unsigned long size
)
652 int sh_num
= section
? section
->sh_num
: SHN_UNDEF
;
653 put_extern_sym2(sym
, sh_num
, value
, size
, 1);
656 /* add a new relocation entry to symbol 'sym' in section 's' */
657 ST_FUNC
void greloca(Section
*s
, Sym
*sym
, unsigned long offset
, int type
,
662 if (nocode_wanted
&& s
== cur_text_section
)
667 put_extern_sym(sym
, NULL
, 0, 0);
671 /* now we can add ELF relocation info */
672 put_elf_reloca(symtab_section
, s
, offset
, type
, c
, addend
);
676 ST_FUNC
void greloc(Section
*s
, Sym
*sym
, unsigned long offset
, int type
)
678 greloca(s
, sym
, offset
, type
, 0);
682 /* ------------------------------------------------------------------------- */
683 /* symbol allocator */
684 static Sym
*__sym_malloc(void)
686 Sym
*sym_pool
, *sym
, *last_sym
;
689 sym_pool
= tcc_malloc(SYM_POOL_NB
* sizeof(Sym
));
690 dynarray_add(&sym_pools
, &nb_sym_pools
, sym_pool
);
692 last_sym
= sym_free_first
;
694 for(i
= 0; i
< SYM_POOL_NB
; i
++) {
695 sym
->next
= last_sym
;
699 sym_free_first
= last_sym
;
703 static inline Sym
*sym_malloc(void)
707 sym
= sym_free_first
;
709 sym
= __sym_malloc();
710 sym_free_first
= sym
->next
;
713 sym
= tcc_malloc(sizeof(Sym
));
718 ST_INLN
void sym_free(Sym
*sym
)
721 sym
->next
= sym_free_first
;
722 sym_free_first
= sym
;
728 /* push, without hashing */
729 ST_FUNC Sym
*sym_push2(Sym
**ps
, int v
, int t
, int c
)
734 memset(s
, 0, sizeof *s
);
744 /* find a symbol and return its associated structure. 's' is the top
745 of the symbol stack */
746 ST_FUNC Sym
*sym_find2(Sym
*s
, int v
)
758 /* structure lookup */
759 ST_INLN Sym
*struct_find(int v
)
762 if ((unsigned)v
>= (unsigned)(tok_ident
- TOK_IDENT
))
764 return table_ident
[v
]->sym_struct
;
767 /* find an identifier */
768 ST_INLN Sym
*sym_find(int v
)
771 if ((unsigned)v
>= (unsigned)(tok_ident
- TOK_IDENT
))
773 return table_ident
[v
]->sym_identifier
;
776 static int sym_scope(Sym
*s
)
778 if (IS_ENUM_VAL (s
->type
.t
))
779 return s
->type
.ref
->sym_scope
;
784 /* push a given symbol on the symbol stack */
785 ST_FUNC Sym
*sym_push(int v
, CType
*type
, int r
, int c
)
794 s
= sym_push2(ps
, v
, type
->t
, c
);
795 s
->type
.ref
= type
->ref
;
797 /* don't record fields or anonymous symbols */
799 if (!(v
& SYM_FIELD
) && (v
& ~SYM_STRUCT
) < SYM_FIRST_ANOM
) {
800 /* record symbol in token array */
801 ts
= table_ident
[(v
& ~SYM_STRUCT
) - TOK_IDENT
];
803 ps
= &ts
->sym_struct
;
805 ps
= &ts
->sym_identifier
;
808 s
->sym_scope
= local_scope
;
809 if (s
->prev_tok
&& sym_scope(s
->prev_tok
) == s
->sym_scope
)
810 tcc_error("redeclaration of '%s'",
811 get_tok_str(v
& ~SYM_STRUCT
, NULL
));
816 /* push a global identifier */
817 ST_FUNC Sym
*global_identifier_push(int v
, int t
, int c
)
820 s
= sym_push2(&global_stack
, v
, t
, c
);
821 s
->r
= VT_CONST
| VT_SYM
;
822 /* don't record anonymous symbol */
823 if (v
< SYM_FIRST_ANOM
) {
824 ps
= &table_ident
[v
- TOK_IDENT
]->sym_identifier
;
825 /* modify the top most local identifier, so that sym_identifier will
826 point to 's' when popped; happens when called from inline asm */
827 while (*ps
!= NULL
&& (*ps
)->sym_scope
)
828 ps
= &(*ps
)->prev_tok
;
835 /* pop symbols until top reaches 'b'. If KEEP is non-zero don't really
836 pop them yet from the list, but do remove them from the token array. */
837 ST_FUNC
void sym_pop(Sym
**ptop
, Sym
*b
, int keep
)
847 /* remove symbol in token array */
849 if (!(v
& SYM_FIELD
) && (v
& ~SYM_STRUCT
) < SYM_FIRST_ANOM
) {
850 ts
= table_ident
[(v
& ~SYM_STRUCT
) - TOK_IDENT
];
852 ps
= &ts
->sym_struct
;
854 ps
= &ts
->sym_identifier
;
865 /* ------------------------------------------------------------------------- */
866 static void vcheck_cmp(void)
868 /* cannot let cpu flags if other instruction are generated. Also
869 avoid leaving VT_JMP anywhere except on the top of the stack
870 because it would complicate the code generator.
872 Don't do this when nocode_wanted. vtop might come from
873 !nocode_wanted regions (see 88_codeopt.c) and transforming
874 it to a register without actually generating code is wrong
875 as their value might still be used for real. All values
876 we push under nocode_wanted will eventually be popped
877 again, so that the VT_CMP/VT_JMP value will be in vtop
878 when code is unsuppressed again. */
880 if (vtop
->r
== VT_CMP
&& !nocode_wanted
)
884 static void vsetc(CType
*type
, int r
, CValue
*vc
)
886 if (vtop
>= vstack
+ (VSTACK_SIZE
- 1))
887 tcc_error("memory full (vstack)");
897 ST_FUNC
void vswap(void)
907 /* pop stack value */
908 ST_FUNC
void vpop(void)
911 v
= vtop
->r
& VT_VALMASK
;
912 #if defined(TCC_TARGET_I386) || defined(TCC_TARGET_X86_64)
913 /* for x86, we need to pop the FP stack */
915 o(0xd8dd); /* fstp %st(0) */
919 /* need to put correct jump if && or || without test */
926 /* push constant of type "type" with useless value */
927 static void vpush(CType
*type
)
929 vset(type
, VT_CONST
, 0);
932 /* push arbitrary 64bit constant */
933 static void vpush64(int ty
, unsigned long long v
)
940 vsetc(&ctype
, VT_CONST
, &cval
);
943 /* push integer constant */
944 ST_FUNC
void vpushi(int v
)
949 /* push a pointer sized constant */
950 static void vpushs(addr_t v
)
952 vpush64(VT_SIZE_T
, v
);
955 /* push long long constant */
956 static inline void vpushll(long long v
)
958 vpush64(VT_LLONG
, v
);
961 ST_FUNC
void vset(CType
*type
, int r
, int v
)
965 vsetc(type
, r
, &cval
);
968 static void vseti(int r
, int v
)
976 ST_FUNC
void vpushv(SValue
*v
)
978 if (vtop
>= vstack
+ (VSTACK_SIZE
- 1))
979 tcc_error("memory full (vstack)");
984 static void vdup(void)
989 /* rotate n first stack elements to the bottom
990 I1 ... In -> I2 ... In I1 [top is right]
992 ST_FUNC
void vrotb(int n
)
1000 vtop
[i
] = vtop
[i
+1];
1004 /* rotate the n elements before entry e towards the top
1005 I1 ... In ... -> In I1 ... I(n-1) ... [top is right]
1007 ST_FUNC
void vrote(SValue
*e
, int n
)
1014 for(i
= 0;i
< n
- 1; i
++)
1019 /* rotate n first stack elements to the top
1020 I1 ... In -> In I1 ... I(n-1) [top is right]
1022 ST_FUNC
void vrott(int n
)
1027 /* ------------------------------------------------------------------------- */
1028 /* vtop->r = VT_CMP means CPU-flags have been set from comparison or test. */
1030 /* called from generators to set the result from relational ops */
1031 ST_FUNC
void vset_VT_CMP(int op
)
1039 /* called once before asking generators to load VT_CMP to a register */
1040 static void vset_VT_JMP(void)
1042 int op
= vtop
->cmp_op
;
1043 if (vtop
->jtrue
|| vtop
->jfalse
) {
1044 /* we need to jump to 'mov $0,%R' or 'mov $1,%R' */
1045 int inv
= op
& (op
< 2); /* small optimization */
1046 vseti(VT_JMP
+inv
, gvtst(inv
, 0));
1048 /* otherwise convert flags (rsp. 0/1) to register */
1050 if (op
< 2) /* doesn't seem to happen */
1055 /* Set CPU Flags, doesn't yet jump */
1056 static void gvtst_set(int inv
, int t
)
1059 if (vtop
->r
!= VT_CMP
) {
1062 if (vtop
->r
== VT_CMP
) /* must be VT_CONST otherwise */
1064 else if (vtop
->r
== VT_CONST
)
1065 vset_VT_CMP(vtop
->c
.i
!= 0);
1069 p
= inv
? &vtop
->jfalse
: &vtop
->jtrue
;
1070 *p
= gjmp_append(*p
, t
);
1073 /* Generate value test
1075 * Generate a test for any value (jump, comparison and integers) */
1076 static int gvtst(int inv
, int t
)
1082 t
= vtop
->jtrue
, u
= vtop
->jfalse
;
1084 x
= u
, u
= t
, t
= x
;
1087 /* jump to the wanted target */
1089 t
= gjmp_cond(op
^ inv
, t
);
1092 /* resolve complementary jumps to here */
1099 /* generate a zero or nozero test */
1100 static void gen_test_zero(int op
)
1102 if (vtop
->r
== VT_CMP
) {
1106 vtop
->jfalse
= vtop
->jtrue
;
1116 /* ------------------------------------------------------------------------- */
1117 /* push a symbol value of TYPE */
1118 static inline void vpushsym(CType
*type
, Sym
*sym
)
1122 vsetc(type
, VT_CONST
| VT_SYM
, &cval
);
1126 /* Return a static symbol pointing to a section */
1127 ST_FUNC Sym
*get_sym_ref(CType
*type
, Section
*sec
, unsigned long offset
, unsigned long size
)
1133 sym
= sym_push(v
, type
, VT_CONST
| VT_SYM
, 0);
1134 sym
->type
.t
|= VT_STATIC
;
1135 put_extern_sym(sym
, sec
, offset
, size
);
1139 /* push a reference to a section offset by adding a dummy symbol */
1140 static void vpush_ref(CType
*type
, Section
*sec
, unsigned long offset
, unsigned long size
)
1142 vpushsym(type
, get_sym_ref(type
, sec
, offset
, size
));
1145 /* define a new external reference to a symbol 'v' of type 'u' */
1146 ST_FUNC Sym
*external_global_sym(int v
, CType
*type
)
1152 /* push forward reference */
1153 s
= global_identifier_push(v
, type
->t
| VT_EXTERN
, 0);
1154 s
->type
.ref
= type
->ref
;
1155 } else if (IS_ASM_SYM(s
)) {
1156 s
->type
.t
= type
->t
| (s
->type
.t
& VT_EXTERN
);
1157 s
->type
.ref
= type
->ref
;
1163 /* Merge symbol attributes. */
1164 static void merge_symattr(struct SymAttr
*sa
, struct SymAttr
*sa1
)
1166 if (sa1
->aligned
&& !sa
->aligned
)
1167 sa
->aligned
= sa1
->aligned
;
1168 sa
->packed
|= sa1
->packed
;
1169 sa
->weak
|= sa1
->weak
;
1170 if (sa1
->visibility
!= STV_DEFAULT
) {
1171 int vis
= sa
->visibility
;
1172 if (vis
== STV_DEFAULT
1173 || vis
> sa1
->visibility
)
1174 vis
= sa1
->visibility
;
1175 sa
->visibility
= vis
;
1177 sa
->dllexport
|= sa1
->dllexport
;
1178 sa
->nodecorate
|= sa1
->nodecorate
;
1179 sa
->dllimport
|= sa1
->dllimport
;
1182 /* Merge function attributes. */
1183 static void merge_funcattr(struct FuncAttr
*fa
, struct FuncAttr
*fa1
)
1185 if (fa1
->func_call
&& !fa
->func_call
)
1186 fa
->func_call
= fa1
->func_call
;
1187 if (fa1
->func_type
&& !fa
->func_type
)
1188 fa
->func_type
= fa1
->func_type
;
1189 if (fa1
->func_args
&& !fa
->func_args
)
1190 fa
->func_args
= fa1
->func_args
;
1193 /* Merge attributes. */
1194 static void merge_attr(AttributeDef
*ad
, AttributeDef
*ad1
)
1196 merge_symattr(&ad
->a
, &ad1
->a
);
1197 merge_funcattr(&ad
->f
, &ad1
->f
);
1200 ad
->section
= ad1
->section
;
1201 if (ad1
->alias_target
)
1202 ad
->alias_target
= ad1
->alias_target
;
1204 ad
->asm_label
= ad1
->asm_label
;
1206 ad
->attr_mode
= ad1
->attr_mode
;
1209 /* Merge some type attributes. */
1210 static void patch_type(Sym
*sym
, CType
*type
)
1212 if (!(type
->t
& VT_EXTERN
) || IS_ENUM_VAL(sym
->type
.t
)) {
1213 if (!(sym
->type
.t
& VT_EXTERN
))
1214 tcc_error("redefinition of '%s'", get_tok_str(sym
->v
, NULL
));
1215 sym
->type
.t
&= ~VT_EXTERN
;
1218 if (IS_ASM_SYM(sym
)) {
1219 /* stay static if both are static */
1220 sym
->type
.t
= type
->t
& (sym
->type
.t
| ~VT_STATIC
);
1221 sym
->type
.ref
= type
->ref
;
1224 if (!is_compatible_types(&sym
->type
, type
)) {
1225 tcc_error("incompatible types for redefinition of '%s'",
1226 get_tok_str(sym
->v
, NULL
));
1228 } else if ((sym
->type
.t
& VT_BTYPE
) == VT_FUNC
) {
1229 int static_proto
= sym
->type
.t
& VT_STATIC
;
1230 /* warn if static follows non-static function declaration */
1231 if ((type
->t
& VT_STATIC
) && !static_proto
1232 /* XXX this test for inline shouldn't be here. Until we
1233 implement gnu-inline mode again it silences a warning for
1234 mingw caused by our workarounds. */
1235 && !((type
->t
| sym
->type
.t
) & VT_INLINE
))
1236 tcc_warning("static storage ignored for redefinition of '%s'",
1237 get_tok_str(sym
->v
, NULL
));
1239 /* set 'inline' if both agree or if one has static */
1240 if ((type
->t
| sym
->type
.t
) & VT_INLINE
) {
1241 if (!((type
->t
^ sym
->type
.t
) & VT_INLINE
)
1242 || ((type
->t
| sym
->type
.t
) & VT_STATIC
))
1243 static_proto
|= VT_INLINE
;
1246 if (0 == (type
->t
& VT_EXTERN
)) {
1247 /* put complete type, use static from prototype */
1248 sym
->type
.t
= (type
->t
& ~(VT_STATIC
|VT_INLINE
)) | static_proto
;
1249 sym
->type
.ref
= type
->ref
;
1251 sym
->type
.t
&= ~VT_INLINE
| static_proto
;
1254 if (sym
->type
.ref
->f
.func_type
== FUNC_OLD
1255 && type
->ref
->f
.func_type
!= FUNC_OLD
) {
1256 sym
->type
.ref
= type
->ref
;
1260 if ((sym
->type
.t
& VT_ARRAY
) && type
->ref
->c
>= 0) {
1261 /* set array size if it was omitted in extern declaration */
1262 sym
->type
.ref
->c
= type
->ref
->c
;
1264 if ((type
->t
^ sym
->type
.t
) & VT_STATIC
)
1265 tcc_warning("storage mismatch for redefinition of '%s'",
1266 get_tok_str(sym
->v
, NULL
));
1270 /* Merge some storage attributes. */
1271 static void patch_storage(Sym
*sym
, AttributeDef
*ad
, CType
*type
)
1274 patch_type(sym
, type
);
1276 #ifdef TCC_TARGET_PE
1277 if (sym
->a
.dllimport
!= ad
->a
.dllimport
)
1278 tcc_error("incompatible dll linkage for redefinition of '%s'",
1279 get_tok_str(sym
->v
, NULL
));
1281 merge_symattr(&sym
->a
, &ad
->a
);
1283 sym
->asm_label
= ad
->asm_label
;
1284 update_storage(sym
);
1287 /* copy sym to other stack */
1288 static Sym
*sym_copy(Sym
*s0
, Sym
**ps
)
1291 s
= sym_malloc(), *s
= *s0
;
1292 s
->prev
= *ps
, *ps
= s
;
1293 if (s
->v
< SYM_FIRST_ANOM
) {
1294 ps
= &table_ident
[s
->v
- TOK_IDENT
]->sym_identifier
;
1295 s
->prev_tok
= *ps
, *ps
= s
;
1300 /* copy s->type.ref to stack 'ps' for VT_FUNC and VT_PTR */
1301 static void sym_copy_ref(Sym
*s
, Sym
**ps
)
1303 int bt
= s
->type
.t
& VT_BTYPE
;
1304 if (bt
== VT_FUNC
|| bt
== VT_PTR
) {
1305 Sym
**sp
= &s
->type
.ref
;
1306 for (s
= *sp
, *sp
= NULL
; s
; s
= s
->next
) {
1307 Sym
*s2
= sym_copy(s
, ps
);
1308 sp
= &(*sp
= s2
)->next
;
1309 sym_copy_ref(s2
, ps
);
1314 /* define a new external reference to a symbol 'v' */
1315 static Sym
*external_sym(int v
, CType
*type
, int r
, AttributeDef
*ad
)
1319 /* look for global symbol */
1321 while (s
&& s
->sym_scope
)
1325 /* push forward reference */
1326 s
= global_identifier_push(v
, type
->t
, 0);
1329 s
->asm_label
= ad
->asm_label
;
1330 s
->type
.ref
= type
->ref
;
1331 /* copy type to the global stack */
1333 sym_copy_ref(s
, &global_stack
);
1335 patch_storage(s
, ad
, type
);
1337 /* push variables on local_stack if any */
1338 if (local_stack
&& (s
->type
.t
& VT_BTYPE
) != VT_FUNC
)
1339 s
= sym_copy(s
, &local_stack
);
1343 /* push a reference to global symbol v */
1344 ST_FUNC
void vpush_global_sym(CType
*type
, int v
)
1346 vpushsym(type
, external_global_sym(v
, type
));
1349 /* save registers up to (vtop - n) stack entry */
1350 ST_FUNC
void save_regs(int n
)
1353 for(p
= vstack
, p1
= vtop
- n
; p
<= p1
; p
++)
1357 /* save r to the memory stack, and mark it as being free */
1358 ST_FUNC
void save_reg(int r
)
1360 save_reg_upstack(r
, 0);
1363 /* save r to the memory stack, and mark it as being free,
1364 if seen up to (vtop - n) stack entry */
1365 ST_FUNC
void save_reg_upstack(int r
, int n
)
1367 int l
, size
, align
, bt
;
1370 if ((r
&= VT_VALMASK
) >= VT_CONST
)
1375 for(p
= vstack
, p1
= vtop
- n
; p
<= p1
; p
++) {
1376 if ((p
->r
& VT_VALMASK
) == r
|| p
->r2
== r
) {
1377 /* must save value on stack if not already done */
1379 bt
= p
->type
.t
& VT_BTYPE
;
1382 if ((p
->r
& VT_LVAL
) || bt
== VT_FUNC
)
1385 size
= type_size(&sv
.type
, &align
);
1386 l
= get_temp_local_var(size
,align
);
1387 sv
.r
= VT_LOCAL
| VT_LVAL
;
1389 store(p
->r
& VT_VALMASK
, &sv
);
1390 #if defined(TCC_TARGET_I386) || defined(TCC_TARGET_X86_64)
1391 /* x86 specific: need to pop fp register ST0 if saved */
1392 if (r
== TREG_ST0
) {
1393 o(0xd8dd); /* fstp %st(0) */
1396 /* special long long case */
1397 if (p
->r2
< VT_CONST
&& USING_TWO_WORDS(bt
)) {
1402 /* mark that stack entry as being saved on the stack */
1403 if (p
->r
& VT_LVAL
) {
1404 /* also clear the bounded flag because the
1405 relocation address of the function was stored in
1407 p
->r
= (p
->r
& ~(VT_VALMASK
| VT_BOUNDED
)) | VT_LLOCAL
;
1409 p
->r
= VT_LVAL
| VT_LOCAL
;
1417 #ifdef TCC_TARGET_ARM
1418 /* find a register of class 'rc2' with at most one reference on stack.
1419 * If none, call get_reg(rc) */
1420 ST_FUNC
int get_reg_ex(int rc
, int rc2
)
1425 for(r
=0;r
<NB_REGS
;r
++) {
1426 if (reg_classes
[r
] & rc2
) {
1429 for(p
= vstack
; p
<= vtop
; p
++) {
1430 if ((p
->r
& VT_VALMASK
) == r
||
1442 /* find a free register of class 'rc'. If none, save one register */
1443 ST_FUNC
int get_reg(int rc
)
1448 /* find a free register */
1449 for(r
=0;r
<NB_REGS
;r
++) {
1450 if (reg_classes
[r
] & rc
) {
1453 for(p
=vstack
;p
<=vtop
;p
++) {
1454 if ((p
->r
& VT_VALMASK
) == r
||
1463 /* no register left : free the first one on the stack (VERY
1464 IMPORTANT to start from the bottom to ensure that we don't
1465 spill registers used in gen_opi()) */
1466 for(p
=vstack
;p
<=vtop
;p
++) {
1467 /* look at second register (if long long) */
1469 if (r
< VT_CONST
&& (reg_classes
[r
] & rc
))
1471 r
= p
->r
& VT_VALMASK
;
1472 if (r
< VT_CONST
&& (reg_classes
[r
] & rc
)) {
1478 /* Should never comes here */
1482 /* find a free temporary local variable (return the offset on stack) match the size and align. If none, add new temporary stack variable*/
1483 static int get_temp_local_var(int size
,int align
){
1485 struct temp_local_variable
*temp_var
;
1492 for(i
=0;i
<nb_temp_local_vars
;i
++){
1493 temp_var
=&arr_temp_local_vars
[i
];
1494 if(temp_var
->size
<size
||align
!=temp_var
->align
){
1497 /*check if temp_var is free*/
1499 for(p
=vstack
;p
<=vtop
;p
++) {
1501 if(r
==VT_LOCAL
||r
==VT_LLOCAL
){
1502 if(p
->c
.i
==temp_var
->location
){
1509 found_var
=temp_var
->location
;
1515 loc
= (loc
- size
) & -align
;
1516 if(nb_temp_local_vars
<MAX_TEMP_LOCAL_VARIABLE_NUMBER
){
1517 temp_var
=&arr_temp_local_vars
[i
];
1518 temp_var
->location
=loc
;
1519 temp_var
->size
=size
;
1520 temp_var
->align
=align
;
1521 nb_temp_local_vars
++;
1528 static void clear_temp_local_var_list(){
1529 nb_temp_local_vars
=0;
1532 /* move register 's' (of type 't') to 'r', and flush previous value of r to memory
1534 static void move_reg(int r
, int s
, int t
)
1548 /* get address of vtop (vtop MUST BE an lvalue) */
1549 ST_FUNC
void gaddrof(void)
1551 vtop
->r
&= ~VT_LVAL
;
1552 /* tricky: if saved lvalue, then we can go back to lvalue */
1553 if ((vtop
->r
& VT_VALMASK
) == VT_LLOCAL
)
1554 vtop
->r
= (vtop
->r
& ~VT_VALMASK
) | VT_LOCAL
| VT_LVAL
;
1557 #ifdef CONFIG_TCC_BCHECK
1558 /* generate lvalue bound code */
1559 static void gbound(void)
1563 vtop
->r
&= ~VT_MUSTBOUND
;
1564 /* if lvalue, then use checking code before dereferencing */
1565 if (vtop
->r
& VT_LVAL
) {
1566 /* if not VT_BOUNDED value, then make one */
1567 if (!(vtop
->r
& VT_BOUNDED
)) {
1568 /* must save type because we must set it to int to get pointer */
1570 vtop
->type
.t
= VT_PTR
;
1573 gen_bounded_ptr_add();
1577 /* then check for dereferencing */
1578 gen_bounded_ptr_deref();
1582 /* we need to call __bound_ptr_add before we start to load function
1583 args into registers */
1584 ST_FUNC
void gbound_args(int nb_args
)
1587 for (i
= 1; i
<= nb_args
; ++i
)
1588 if (vtop
[1 - i
].r
& VT_MUSTBOUND
) {
1595 /* Add bounds for local symbols from S to E (via ->prev) */
1596 static void add_local_bounds(Sym
*s
, Sym
*e
)
1598 for (; s
!= e
; s
= s
->prev
) {
1599 if (!s
->v
|| (s
->r
& VT_VALMASK
) != VT_LOCAL
)
1601 /* Add arrays/structs/unions because we always take address */
1602 if ((s
->type
.t
& VT_ARRAY
)
1603 || (s
->type
.t
& VT_BTYPE
) == VT_STRUCT
1604 || s
->a
.addrtaken
) {
1605 /* add local bound info */
1606 int align
, size
= type_size(&s
->type
, &align
);
1607 addr_t
*bounds_ptr
= section_ptr_add(lbounds_section
,
1608 2 * sizeof(addr_t
));
1609 bounds_ptr
[0] = s
->c
;
1610 bounds_ptr
[1] = size
;
1616 /* Wrapper around sym_pop, that potentially also registers local bounds. */
1617 static void pop_local_syms(Sym
**ptop
, Sym
*b
, int keep
, int ellipsis
)
1619 #ifdef CONFIG_TCC_BCHECK
1620 if (!ellipsis
&& !keep
&& tcc_state
->do_bounds_check
)
1621 add_local_bounds(*ptop
, b
);
1623 sym_pop(ptop
, b
, keep
);
1626 static void incr_bf_adr(int o
)
1628 vtop
->type
= char_pointer_type
;
1632 vtop
->type
.t
= VT_BYTE
| VT_UNSIGNED
;
1636 /* single-byte load mode for packed or otherwise unaligned bitfields */
1637 static void load_packed_bf(CType
*type
, int bit_pos
, int bit_size
)
1640 save_reg_upstack(vtop
->r
, 1);
1641 vpush64(type
->t
& VT_BTYPE
, 0); // B X
1642 bits
= 0, o
= bit_pos
>> 3, bit_pos
&= 7;
1651 vpushi(bit_pos
), gen_op(TOK_SHR
), bit_pos
= 0; // X B Y
1653 vpushi((1 << n
) - 1), gen_op('&');
1656 vpushi(bits
), gen_op(TOK_SHL
);
1659 bits
+= n
, bit_size
-= n
, o
= 1;
1662 if (!(type
->t
& VT_UNSIGNED
)) {
1663 n
= ((type
->t
& VT_BTYPE
) == VT_LLONG
? 64 : 32) - bits
;
1664 vpushi(n
), gen_op(TOK_SHL
);
1665 vpushi(n
), gen_op(TOK_SAR
);
1669 /* single-byte store mode for packed or otherwise unaligned bitfields */
1670 static void store_packed_bf(int bit_pos
, int bit_size
)
1672 int bits
, n
, o
, m
, c
;
1674 c
= (vtop
->r
& (VT_VALMASK
| VT_LVAL
| VT_SYM
)) == VT_CONST
;
1676 save_reg_upstack(vtop
->r
, 1);
1677 bits
= 0, o
= bit_pos
>> 3, bit_pos
&= 7;
1679 incr_bf_adr(o
); // X B
1681 c
? vdup() : gv_dup(); // B V X
1684 vpushi(bits
), gen_op(TOK_SHR
);
1686 vpushi(bit_pos
), gen_op(TOK_SHL
);
1691 m
= ((1 << n
) - 1) << bit_pos
;
1692 vpushi(m
), gen_op('&'); // X B V1
1693 vpushv(vtop
-1); // X B V1 B
1694 vpushi(m
& 0x80 ? ~m
& 0x7f : ~m
);
1695 gen_op('&'); // X B V1 B1
1696 gen_op('|'); // X B V2
1698 vdup(), vtop
[-1] = vtop
[-2]; // X B B V2
1699 vstore(), vpop(); // X B
1700 bits
+= n
, bit_size
-= n
, bit_pos
= 0, o
= 1;
1705 static int adjust_bf(SValue
*sv
, int bit_pos
, int bit_size
)
1708 if (0 == sv
->type
.ref
)
1710 t
= sv
->type
.ref
->auxtype
;
1711 if (t
!= -1 && t
!= VT_STRUCT
) {
1712 sv
->type
.t
= (sv
->type
.t
& ~VT_BTYPE
) | t
;
1718 /* store vtop a register belonging to class 'rc'. lvalues are
1719 converted to values. Cannot be used if cannot be converted to
1720 register value (such as structures). */
1721 ST_FUNC
int gv(int rc
)
1723 int r
, r2
, r_ok
, r2_ok
, rc2
, bt
;
1724 int bit_pos
, bit_size
, size
, align
;
1726 /* NOTE: get_reg can modify vstack[] */
1727 if (vtop
->type
.t
& VT_BITFIELD
) {
1730 bit_pos
= BIT_POS(vtop
->type
.t
);
1731 bit_size
= BIT_SIZE(vtop
->type
.t
);
1732 /* remove bit field info to avoid loops */
1733 vtop
->type
.t
&= ~VT_STRUCT_MASK
;
1736 type
.t
= vtop
->type
.t
& VT_UNSIGNED
;
1737 if ((vtop
->type
.t
& VT_BTYPE
) == VT_BOOL
)
1738 type
.t
|= VT_UNSIGNED
;
1740 r
= adjust_bf(vtop
, bit_pos
, bit_size
);
1742 if ((vtop
->type
.t
& VT_BTYPE
) == VT_LLONG
)
1747 if (r
== VT_STRUCT
) {
1748 load_packed_bf(&type
, bit_pos
, bit_size
);
1750 int bits
= (type
.t
& VT_BTYPE
) == VT_LLONG
? 64 : 32;
1751 /* cast to int to propagate signedness in following ops */
1753 /* generate shifts */
1754 vpushi(bits
- (bit_pos
+ bit_size
));
1756 vpushi(bits
- bit_size
);
1757 /* NOTE: transformed to SHR if unsigned */
1762 if (is_float(vtop
->type
.t
) &&
1763 (vtop
->r
& (VT_VALMASK
| VT_LVAL
)) == VT_CONST
) {
1764 unsigned long offset
;
1765 /* CPUs usually cannot use float constants, so we store them
1766 generically in data segment */
1767 size
= type_size(&vtop
->type
, &align
);
1769 size
= 0, align
= 1;
1770 offset
= section_add(data_section
, size
, align
);
1771 vpush_ref(&vtop
->type
, data_section
, offset
, size
);
1773 init_putv(&vtop
->type
, data_section
, offset
);
1776 #ifdef CONFIG_TCC_BCHECK
1777 if (vtop
->r
& VT_MUSTBOUND
)
1781 bt
= vtop
->type
.t
& VT_BTYPE
;
1783 #ifdef TCC_TARGET_RISCV64
1785 if (bt
== VT_LDOUBLE
&& rc
== RC_FLOAT
)
1788 rc2
= RC2_TYPE(bt
, rc
);
1790 /* need to reload if:
1792 - lvalue (need to dereference pointer)
1793 - already a register, but not in the right class */
1794 r
= vtop
->r
& VT_VALMASK
;
1795 r_ok
= !(vtop
->r
& VT_LVAL
) && (r
< VT_CONST
) && (reg_classes
[r
] & rc
);
1796 r2_ok
= !rc2
|| ((vtop
->r2
< VT_CONST
) && (reg_classes
[vtop
->r2
] & rc2
));
1798 if (!r_ok
|| !r2_ok
) {
1802 int load_type
= (bt
== VT_QFLOAT
) ? VT_DOUBLE
: VT_PTRDIFF_T
;
1803 int original_type
= vtop
->type
.t
;
1805 /* two register type load :
1806 expand to two words temporarily */
1807 if ((vtop
->r
& (VT_VALMASK
| VT_LVAL
)) == VT_CONST
) {
1809 unsigned long long ll
= vtop
->c
.i
;
1810 vtop
->c
.i
= ll
; /* first word */
1812 vtop
->r
= r
; /* save register value */
1813 vpushi(ll
>> 32); /* second word */
1814 } else if (vtop
->r
& VT_LVAL
) {
1815 /* We do not want to modifier the long long pointer here.
1816 So we save any other instances down the stack */
1817 save_reg_upstack(vtop
->r
, 1);
1818 /* load from memory */
1819 vtop
->type
.t
= load_type
;
1822 vtop
[-1].r
= r
; /* save register value */
1823 /* increment pointer to get second word */
1824 vtop
->type
.t
= VT_PTRDIFF_T
;
1829 vtop
->type
.t
= load_type
;
1831 /* move registers */
1834 if (r2_ok
&& vtop
->r2
< VT_CONST
)
1837 vtop
[-1].r
= r
; /* save register value */
1838 vtop
->r
= vtop
[-1].r2
;
1840 /* Allocate second register. Here we rely on the fact that
1841 get_reg() tries first to free r2 of an SValue. */
1845 /* write second register */
1848 vtop
->type
.t
= original_type
;
1850 if (vtop
->r
== VT_CMP
)
1852 /* one register type load */
1857 #ifdef TCC_TARGET_C67
1858 /* uses register pairs for doubles */
1859 if (bt
== VT_DOUBLE
)
1866 /* generate vtop[-1] and vtop[0] in resp. classes rc1 and rc2 */
1867 ST_FUNC
void gv2(int rc1
, int rc2
)
1869 /* generate more generic register first. But VT_JMP or VT_CMP
1870 values must be generated first in all cases to avoid possible
1872 if (vtop
->r
!= VT_CMP
&& rc1
<= rc2
) {
1877 /* test if reload is needed for first register */
1878 if ((vtop
[-1].r
& VT_VALMASK
) >= VT_CONST
) {
1888 /* test if reload is needed for first register */
1889 if ((vtop
[0].r
& VT_VALMASK
) >= VT_CONST
) {
1896 /* expand 64bit on stack in two ints */
1897 ST_FUNC
void lexpand(void)
1900 u
= vtop
->type
.t
& (VT_DEFSIGN
| VT_UNSIGNED
);
1901 v
= vtop
->r
& (VT_VALMASK
| VT_LVAL
);
1902 if (v
== VT_CONST
) {
1905 } else if (v
== (VT_LVAL
|VT_CONST
) || v
== (VT_LVAL
|VT_LOCAL
)) {
1911 vtop
[0].r
= vtop
[-1].r2
;
1912 vtop
[0].r2
= vtop
[-1].r2
= VT_CONST
;
1914 vtop
[0].type
.t
= vtop
[-1].type
.t
= VT_INT
| u
;
1919 /* build a long long from two ints */
1920 static void lbuild(int t
)
1922 gv2(RC_INT
, RC_INT
);
1923 vtop
[-1].r2
= vtop
[0].r
;
1924 vtop
[-1].type
.t
= t
;
1929 /* convert stack entry to register and duplicate its value in another
1931 static void gv_dup(void)
1937 if ((t
& VT_BTYPE
) == VT_LLONG
) {
1938 if (t
& VT_BITFIELD
) {
1948 /* stack: H L L1 H1 */
1958 /* duplicate value */
1968 /* generate CPU independent (unsigned) long long operations */
1969 static void gen_opl(int op
)
1971 int t
, a
, b
, op1
, c
, i
;
1973 unsigned short reg_iret
= REG_IRET
;
1974 unsigned short reg_lret
= REG_IRE2
;
1980 func
= TOK___divdi3
;
1983 func
= TOK___udivdi3
;
1986 func
= TOK___moddi3
;
1989 func
= TOK___umoddi3
;
1996 /* call generic long long function */
1997 vpush_global_sym(&func_old_type
, func
);
2002 vtop
->r2
= reg_lret
;
2010 //pv("gen_opl A",0,2);
2016 /* stack: L1 H1 L2 H2 */
2021 vtop
[-2] = vtop
[-3];
2024 /* stack: H1 H2 L1 L2 */
2025 //pv("gen_opl B",0,4);
2031 /* stack: H1 H2 L1 L2 ML MH */
2034 /* stack: ML MH H1 H2 L1 L2 */
2038 /* stack: ML MH H1 L2 H2 L1 */
2043 /* stack: ML MH M1 M2 */
2046 } else if (op
== '+' || op
== '-') {
2047 /* XXX: add non carry method too (for MIPS or alpha) */
2053 /* stack: H1 H2 (L1 op L2) */
2056 gen_op(op1
+ 1); /* TOK_xxxC2 */
2059 /* stack: H1 H2 (L1 op L2) */
2062 /* stack: (L1 op L2) H1 H2 */
2064 /* stack: (L1 op L2) (H1 op H2) */
2072 if ((vtop
->r
& (VT_VALMASK
| VT_LVAL
| VT_SYM
)) == VT_CONST
) {
2073 t
= vtop
[-1].type
.t
;
2077 /* stack: L H shift */
2079 /* constant: simpler */
2080 /* NOTE: all comments are for SHL. the other cases are
2081 done by swapping words */
2092 if (op
!= TOK_SAR
) {
2125 /* XXX: should provide a faster fallback on x86 ? */
2128 func
= TOK___ashrdi3
;
2131 func
= TOK___lshrdi3
;
2134 func
= TOK___ashldi3
;
2140 /* compare operations */
2146 /* stack: L1 H1 L2 H2 */
2148 vtop
[-1] = vtop
[-2];
2150 /* stack: L1 L2 H1 H2 */
2154 /* when values are equal, we need to compare low words. since
2155 the jump is inverted, we invert the test too. */
2158 else if (op1
== TOK_GT
)
2160 else if (op1
== TOK_ULT
)
2162 else if (op1
== TOK_UGT
)
2172 /* generate non equal test */
2174 vset_VT_CMP(TOK_NE
);
2178 /* compare low. Always unsigned */
2182 else if (op1
== TOK_LE
)
2184 else if (op1
== TOK_GT
)
2186 else if (op1
== TOK_GE
)
2189 #if 0//def TCC_TARGET_I386
2190 if (op
== TOK_NE
) { gsym(b
); break; }
2191 if (op
== TOK_EQ
) { gsym(a
); break; }
2200 static uint64_t gen_opic_sdiv(uint64_t a
, uint64_t b
)
2202 uint64_t x
= (a
>> 63 ? -a
: a
) / (b
>> 63 ? -b
: b
);
2203 return (a
^ b
) >> 63 ? -x
: x
;
2206 static int gen_opic_lt(uint64_t a
, uint64_t b
)
2208 return (a
^ (uint64_t)1 << 63) < (b
^ (uint64_t)1 << 63);
2211 /* handle integer constant optimizations and various machine
2213 static void gen_opic(int op
)
2215 SValue
*v1
= vtop
- 1;
2217 int t1
= v1
->type
.t
& VT_BTYPE
;
2218 int t2
= v2
->type
.t
& VT_BTYPE
;
2219 int c1
= (v1
->r
& (VT_VALMASK
| VT_LVAL
| VT_SYM
)) == VT_CONST
;
2220 int c2
= (v2
->r
& (VT_VALMASK
| VT_LVAL
| VT_SYM
)) == VT_CONST
;
2221 uint64_t l1
= c1
? v1
->c
.i
: 0;
2222 uint64_t l2
= c2
? v2
->c
.i
: 0;
2223 int shm
= (t1
== VT_LLONG
) ? 63 : 31;
2225 if (t1
!= VT_LLONG
&& (PTR_SIZE
!= 8 || t1
!= VT_PTR
))
2226 l1
= ((uint32_t)l1
|
2227 (v1
->type
.t
& VT_UNSIGNED
? 0 : -(l1
& 0x80000000)));
2228 if (t2
!= VT_LLONG
&& (PTR_SIZE
!= 8 || t2
!= VT_PTR
))
2229 l2
= ((uint32_t)l2
|
2230 (v2
->type
.t
& VT_UNSIGNED
? 0 : -(l2
& 0x80000000)));
2234 case '+': l1
+= l2
; break;
2235 case '-': l1
-= l2
; break;
2236 case '&': l1
&= l2
; break;
2237 case '^': l1
^= l2
; break;
2238 case '|': l1
|= l2
; break;
2239 case '*': l1
*= l2
; break;
2246 /* if division by zero, generate explicit division */
2248 if (const_wanted
&& !(nocode_wanted
& unevalmask
))
2249 tcc_error("division by zero in constant");
2253 default: l1
= gen_opic_sdiv(l1
, l2
); break;
2254 case '%': l1
= l1
- l2
* gen_opic_sdiv(l1
, l2
); break;
2255 case TOK_UDIV
: l1
= l1
/ l2
; break;
2256 case TOK_UMOD
: l1
= l1
% l2
; break;
2259 case TOK_SHL
: l1
<<= (l2
& shm
); break;
2260 case TOK_SHR
: l1
>>= (l2
& shm
); break;
2262 l1
= (l1
>> 63) ? ~(~l1
>> (l2
& shm
)) : l1
>> (l2
& shm
);
2265 case TOK_ULT
: l1
= l1
< l2
; break;
2266 case TOK_UGE
: l1
= l1
>= l2
; break;
2267 case TOK_EQ
: l1
= l1
== l2
; break;
2268 case TOK_NE
: l1
= l1
!= l2
; break;
2269 case TOK_ULE
: l1
= l1
<= l2
; break;
2270 case TOK_UGT
: l1
= l1
> l2
; break;
2271 case TOK_LT
: l1
= gen_opic_lt(l1
, l2
); break;
2272 case TOK_GE
: l1
= !gen_opic_lt(l1
, l2
); break;
2273 case TOK_LE
: l1
= !gen_opic_lt(l2
, l1
); break;
2274 case TOK_GT
: l1
= gen_opic_lt(l2
, l1
); break;
2276 case TOK_LAND
: l1
= l1
&& l2
; break;
2277 case TOK_LOR
: l1
= l1
|| l2
; break;
2281 if (t1
!= VT_LLONG
&& (PTR_SIZE
!= 8 || t1
!= VT_PTR
))
2282 l1
= ((uint32_t)l1
|
2283 (v1
->type
.t
& VT_UNSIGNED
? 0 : -(l1
& 0x80000000)));
2287 /* if commutative ops, put c2 as constant */
2288 if (c1
&& (op
== '+' || op
== '&' || op
== '^' ||
2289 op
== '|' || op
== '*' || op
== TOK_EQ
|| op
== TOK_NE
)) {
2291 c2
= c1
; //c = c1, c1 = c2, c2 = c;
2292 l2
= l1
; //l = l1, l1 = l2, l2 = l;
2294 if (!const_wanted
&&
2296 (op
== TOK_SHL
|| op
== TOK_SHR
|| op
== TOK_SAR
)) ||
2297 (l1
== -1 && op
== TOK_SAR
))) {
2298 /* treat (0 << x), (0 >> x) and (-1 >> x) as constant */
2300 } else if (!const_wanted
&&
2301 c2
&& ((l2
== 0 && (op
== '&' || op
== '*')) ||
2303 (l2
== -1 || (l2
== 0xFFFFFFFF && t2
!= VT_LLONG
))) ||
2304 (l2
== 1 && (op
== '%' || op
== TOK_UMOD
)))) {
2305 /* treat (x & 0), (x * 0), (x | -1) and (x % 1) as constant */
2310 } else if (c2
&& (((op
== '*' || op
== '/' || op
== TOK_UDIV
||
2313 ((op
== '+' || op
== '-' || op
== '|' || op
== '^' ||
2314 op
== TOK_SHL
|| op
== TOK_SHR
|| op
== TOK_SAR
) &&
2317 (l2
== -1 || (l2
== 0xFFFFFFFF && t2
!= VT_LLONG
))))) {
2318 /* filter out NOP operations like x*1, x-0, x&-1... */
2320 } else if (c2
&& (op
== '*' || op
== TOK_PDIV
|| op
== TOK_UDIV
)) {
2321 /* try to use shifts instead of muls or divs */
2322 if (l2
> 0 && (l2
& (l2
- 1)) == 0) {
2331 else if (op
== TOK_PDIV
)
2337 } else if (c2
&& (op
== '+' || op
== '-') &&
2338 (((vtop
[-1].r
& (VT_VALMASK
| VT_LVAL
| VT_SYM
)) == (VT_CONST
| VT_SYM
))
2339 || (vtop
[-1].r
& (VT_VALMASK
| VT_LVAL
)) == VT_LOCAL
)) {
2340 /* symbol + constant case */
2344 /* The backends can't always deal with addends to symbols
2345 larger than +-1<<31. Don't construct such. */
2352 /* call low level op generator */
2353 if (t1
== VT_LLONG
|| t2
== VT_LLONG
||
2354 (PTR_SIZE
== 8 && (t1
== VT_PTR
|| t2
== VT_PTR
)))
2362 /* generate a floating point operation with constant propagation */
2363 static void gen_opif(int op
)
2367 #if defined _MSC_VER && defined __x86_64__
2368 /* avoid bad optimization with f1 -= f2 for f1:-0.0, f2:0.0 */
2375 /* currently, we cannot do computations with forward symbols */
2376 c1
= (v1
->r
& (VT_VALMASK
| VT_LVAL
| VT_SYM
)) == VT_CONST
;
2377 c2
= (v2
->r
& (VT_VALMASK
| VT_LVAL
| VT_SYM
)) == VT_CONST
;
2379 if (v1
->type
.t
== VT_FLOAT
) {
2382 } else if (v1
->type
.t
== VT_DOUBLE
) {
2390 /* NOTE: we only do constant propagation if finite number (not
2391 NaN or infinity) (ANSI spec) */
2392 if (!ieee_finite(f1
) || !ieee_finite(f2
))
2396 case '+': f1
+= f2
; break;
2397 case '-': f1
-= f2
; break;
2398 case '*': f1
*= f2
; break;
2401 /* If not in initializer we need to potentially generate
2402 FP exceptions at runtime, otherwise we want to fold. */
2408 /* XXX: also handles tests ? */
2412 /* XXX: overflow test ? */
2413 if (v1
->type
.t
== VT_FLOAT
) {
2415 } else if (v1
->type
.t
== VT_DOUBLE
) {
2427 static int pointed_size(CType
*type
)
2430 return type_size(pointed_type(type
), &align
);
2433 static void vla_runtime_pointed_size(CType
*type
)
2436 vla_runtime_type_size(pointed_type(type
), &align
);
2439 static inline int is_null_pointer(SValue
*p
)
2441 if ((p
->r
& (VT_VALMASK
| VT_LVAL
| VT_SYM
)) != VT_CONST
)
2443 return ((p
->type
.t
& VT_BTYPE
) == VT_INT
&& (uint32_t)p
->c
.i
== 0) ||
2444 ((p
->type
.t
& VT_BTYPE
) == VT_LLONG
&& p
->c
.i
== 0) ||
2445 ((p
->type
.t
& VT_BTYPE
) == VT_PTR
&&
2446 (PTR_SIZE
== 4 ? (uint32_t)p
->c
.i
== 0 : p
->c
.i
== 0) &&
2447 ((pointed_type(&p
->type
)->t
& VT_BTYPE
) == VT_VOID
) &&
2448 0 == (pointed_type(&p
->type
)->t
& (VT_CONSTANT
| VT_VOLATILE
))
2452 /* check types for comparison or subtraction of pointers */
2453 static void check_comparison_pointer_types(SValue
*p1
, SValue
*p2
, int op
)
2455 CType
*type1
, *type2
, tmp_type1
, tmp_type2
;
2458 /* null pointers are accepted for all comparisons as gcc */
2459 if (is_null_pointer(p1
) || is_null_pointer(p2
))
2463 bt1
= type1
->t
& VT_BTYPE
;
2464 bt2
= type2
->t
& VT_BTYPE
;
2465 /* accept comparison between pointer and integer with a warning */
2466 if ((is_integer_btype(bt1
) || is_integer_btype(bt2
)) && op
!= '-') {
2467 if (op
!= TOK_LOR
&& op
!= TOK_LAND
)
2468 tcc_warning("comparison between pointer and integer");
2472 /* both must be pointers or implicit function pointers */
2473 if (bt1
== VT_PTR
) {
2474 type1
= pointed_type(type1
);
2475 } else if (bt1
!= VT_FUNC
)
2476 goto invalid_operands
;
2478 if (bt2
== VT_PTR
) {
2479 type2
= pointed_type(type2
);
2480 } else if (bt2
!= VT_FUNC
) {
2482 tcc_error("invalid operands to binary %s", get_tok_str(op
, NULL
));
2484 if ((type1
->t
& VT_BTYPE
) == VT_VOID
||
2485 (type2
->t
& VT_BTYPE
) == VT_VOID
)
2489 tmp_type1
.t
&= ~(VT_DEFSIGN
| VT_UNSIGNED
| VT_CONSTANT
| VT_VOLATILE
);
2490 tmp_type2
.t
&= ~(VT_DEFSIGN
| VT_UNSIGNED
| VT_CONSTANT
| VT_VOLATILE
);
2491 if (!is_compatible_types(&tmp_type1
, &tmp_type2
)) {
2492 /* gcc-like error if '-' is used */
2494 goto invalid_operands
;
2496 tcc_warning("comparison of distinct pointer types lacks a cast");
2500 /* generic gen_op: handles types problems */
2501 ST_FUNC
void gen_op(int op
)
2503 int u
, t1
, t2
, bt1
, bt2
, t
;
2507 t1
= vtop
[-1].type
.t
;
2508 t2
= vtop
[0].type
.t
;
2509 bt1
= t1
& VT_BTYPE
;
2510 bt2
= t2
& VT_BTYPE
;
2512 if (bt1
== VT_STRUCT
|| bt2
== VT_STRUCT
) {
2513 tcc_error("operation on a struct");
2514 } else if (bt1
== VT_FUNC
|| bt2
== VT_FUNC
) {
2515 if (bt2
== VT_FUNC
) {
2516 mk_pointer(&vtop
->type
);
2519 if (bt1
== VT_FUNC
) {
2521 mk_pointer(&vtop
->type
);
2526 } else if (bt1
== VT_PTR
|| bt2
== VT_PTR
) {
2527 /* at least one operand is a pointer */
2528 /* relational op: must be both pointers */
2529 if (op
>= TOK_ULT
&& op
<= TOK_LOR
) {
2530 check_comparison_pointer_types(vtop
- 1, vtop
, op
);
2531 /* pointers are handled are unsigned */
2533 t
= VT_LLONG
| VT_UNSIGNED
;
2535 t
= VT_INT
| VT_UNSIGNED
;
2539 /* if both pointers, then it must be the '-' op */
2540 if (bt1
== VT_PTR
&& bt2
== VT_PTR
) {
2542 tcc_error("cannot use pointers here");
2543 check_comparison_pointer_types(vtop
- 1, vtop
, op
);
2544 /* XXX: check that types are compatible */
2545 if (vtop
[-1].type
.t
& VT_VLA
) {
2546 vla_runtime_pointed_size(&vtop
[-1].type
);
2548 vpushi(pointed_size(&vtop
[-1].type
));
2552 vtop
->type
.t
= VT_PTRDIFF_T
;
2556 /* exactly one pointer : must be '+' or '-'. */
2557 if (op
!= '-' && op
!= '+')
2558 tcc_error("cannot use pointers here");
2559 /* Put pointer as first operand */
2560 if (bt2
== VT_PTR
) {
2562 t
= t1
, t1
= t2
, t2
= t
;
2565 if ((vtop
[0].type
.t
& VT_BTYPE
) == VT_LLONG
)
2566 /* XXX: truncate here because gen_opl can't handle ptr + long long */
2569 type1
= vtop
[-1].type
;
2570 type1
.t
&= ~VT_ARRAY
;
2571 if (vtop
[-1].type
.t
& VT_VLA
)
2572 vla_runtime_pointed_size(&vtop
[-1].type
);
2574 u
= pointed_size(&vtop
[-1].type
);
2576 tcc_error("unknown array element size");
2580 /* XXX: cast to int ? (long long case) */
2585 #ifdef CONFIG_TCC_BCHECK
2586 if (tcc_state
->do_bounds_check
&& !const_wanted
) {
2587 /* if bounded pointers, we generate a special code to
2594 gen_bounded_ptr_add();
2600 /* put again type if gen_opic() swaped operands */
2603 } else if (is_float(bt1
) || is_float(bt2
)) {
2604 /* compute bigger type and do implicit casts */
2605 if (bt1
== VT_LDOUBLE
|| bt2
== VT_LDOUBLE
) {
2607 } else if (bt1
== VT_DOUBLE
|| bt2
== VT_DOUBLE
) {
2612 /* floats can only be used for a few operations */
2613 if (op
!= '+' && op
!= '-' && op
!= '*' && op
!= '/' &&
2614 (op
< TOK_ULT
|| op
> TOK_GT
))
2615 tcc_error("invalid operands for binary operation");
2617 } else if (op
== TOK_SHR
|| op
== TOK_SAR
|| op
== TOK_SHL
) {
2618 t
= bt1
== VT_LLONG
? VT_LLONG
: VT_INT
;
2619 if ((t1
& (VT_BTYPE
| VT_UNSIGNED
| VT_BITFIELD
)) == (t
| VT_UNSIGNED
))
2621 t
|= (VT_LONG
& t1
);
2623 } else if (bt1
== VT_LLONG
|| bt2
== VT_LLONG
) {
2624 /* cast to biggest op */
2625 t
= VT_LLONG
| VT_LONG
;
2626 if (bt1
== VT_LLONG
)
2628 if (bt2
== VT_LLONG
)
2630 /* convert to unsigned if it does not fit in a long long */
2631 if ((t1
& (VT_BTYPE
| VT_UNSIGNED
| VT_BITFIELD
)) == (VT_LLONG
| VT_UNSIGNED
) ||
2632 (t2
& (VT_BTYPE
| VT_UNSIGNED
| VT_BITFIELD
)) == (VT_LLONG
| VT_UNSIGNED
))
2636 /* integer operations */
2637 t
= VT_INT
| (VT_LONG
& (t1
| t2
));
2638 /* convert to unsigned if it does not fit in an integer */
2639 if ((t1
& (VT_BTYPE
| VT_UNSIGNED
| VT_BITFIELD
)) == (VT_INT
| VT_UNSIGNED
) ||
2640 (t2
& (VT_BTYPE
| VT_UNSIGNED
| VT_BITFIELD
)) == (VT_INT
| VT_UNSIGNED
))
2643 /* XXX: currently, some unsigned operations are explicit, so
2644 we modify them here */
2645 if (t
& VT_UNSIGNED
) {
2652 else if (op
== TOK_LT
)
2654 else if (op
== TOK_GT
)
2656 else if (op
== TOK_LE
)
2658 else if (op
== TOK_GE
)
2666 /* special case for shifts and long long: we keep the shift as
2668 if (op
== TOK_SHR
|| op
== TOK_SAR
|| op
== TOK_SHL
)
2675 if (op
>= TOK_ULT
&& op
<= TOK_GT
) {
2676 /* relational op: the result is an int */
2677 vtop
->type
.t
= VT_INT
;
2682 // Make sure that we have converted to an rvalue:
2683 if (vtop
->r
& VT_LVAL
)
2684 gv(is_float(vtop
->type
.t
& VT_BTYPE
) ? RC_FLOAT
: RC_INT
);
2687 #if defined TCC_TARGET_ARM64 || defined TCC_TARGET_RISCV64 || defined TCC_TARGET_ARM
2688 #define gen_cvt_itof1 gen_cvt_itof
2690 /* generic itof for unsigned long long case */
2691 static void gen_cvt_itof1(int t
)
2693 if ((vtop
->type
.t
& (VT_BTYPE
| VT_UNSIGNED
)) ==
2694 (VT_LLONG
| VT_UNSIGNED
)) {
2697 vpush_global_sym(&func_old_type
, TOK___floatundisf
);
2698 #if LDOUBLE_SIZE != 8
2699 else if (t
== VT_LDOUBLE
)
2700 vpush_global_sym(&func_old_type
, TOK___floatundixf
);
2703 vpush_global_sym(&func_old_type
, TOK___floatundidf
);
2714 #if defined TCC_TARGET_ARM64 || defined TCC_TARGET_RISCV64
2715 #define gen_cvt_ftoi1 gen_cvt_ftoi
2717 /* generic ftoi for unsigned long long case */
2718 static void gen_cvt_ftoi1(int t
)
2721 if (t
== (VT_LLONG
| VT_UNSIGNED
)) {
2722 /* not handled natively */
2723 st
= vtop
->type
.t
& VT_BTYPE
;
2725 vpush_global_sym(&func_old_type
, TOK___fixunssfdi
);
2726 #if LDOUBLE_SIZE != 8
2727 else if (st
== VT_LDOUBLE
)
2728 vpush_global_sym(&func_old_type
, TOK___fixunsxfdi
);
2731 vpush_global_sym(&func_old_type
, TOK___fixunsdfdi
);
2742 /* special delayed cast for char/short */
2743 static void force_charshort_cast(void)
2745 int sbt
= BFGET(vtop
->r
, VT_MUSTCAST
) == 2 ? VT_LLONG
: VT_INT
;
2746 int dbt
= vtop
->type
.t
;
2747 vtop
->r
&= ~VT_MUSTCAST
;
2749 gen_cast_s(dbt
== VT_BOOL
? VT_BYTE
|VT_UNSIGNED
: dbt
);
2753 static void gen_cast_s(int t
)
2761 /* cast 'vtop' to 'type'. Casting to bitfields is forbidden. */
2762 static void gen_cast(CType
*type
)
2764 int sbt
, dbt
, sf
, df
, c
;
2765 int dbt_bt
, sbt_bt
, ds
, ss
, bits
, trunc
;
2767 /* special delayed cast for char/short */
2768 if (vtop
->r
& VT_MUSTCAST
)
2769 force_charshort_cast();
2771 /* bitfields first get cast to ints */
2772 if (vtop
->type
.t
& VT_BITFIELD
)
2775 dbt
= type
->t
& (VT_BTYPE
| VT_UNSIGNED
);
2776 sbt
= vtop
->type
.t
& (VT_BTYPE
| VT_UNSIGNED
);
2784 dbt_bt
= dbt
& VT_BTYPE
;
2785 sbt_bt
= sbt
& VT_BTYPE
;
2787 c
= (vtop
->r
& (VT_VALMASK
| VT_LVAL
| VT_SYM
)) == VT_CONST
;
2788 #if !defined TCC_IS_NATIVE && !defined TCC_IS_NATIVE_387
2789 c
&= (dbt
!= VT_LDOUBLE
) | !!nocode_wanted
;
2792 /* constant case: we can do it now */
2793 /* XXX: in ISOC, cannot do it if error in convert */
2794 if (sbt
== VT_FLOAT
)
2795 vtop
->c
.ld
= vtop
->c
.f
;
2796 else if (sbt
== VT_DOUBLE
)
2797 vtop
->c
.ld
= vtop
->c
.d
;
2800 if (sbt_bt
== VT_LLONG
) {
2801 if ((sbt
& VT_UNSIGNED
) || !(vtop
->c
.i
>> 63))
2802 vtop
->c
.ld
= vtop
->c
.i
;
2804 vtop
->c
.ld
= -(long double)-vtop
->c
.i
;
2806 if ((sbt
& VT_UNSIGNED
) || !(vtop
->c
.i
>> 31))
2807 vtop
->c
.ld
= (uint32_t)vtop
->c
.i
;
2809 vtop
->c
.ld
= -(long double)-(uint32_t)vtop
->c
.i
;
2812 if (dbt
== VT_FLOAT
)
2813 vtop
->c
.f
= (float)vtop
->c
.ld
;
2814 else if (dbt
== VT_DOUBLE
)
2815 vtop
->c
.d
= (double)vtop
->c
.ld
;
2816 } else if (sf
&& dbt
== VT_BOOL
) {
2817 vtop
->c
.i
= (vtop
->c
.ld
!= 0);
2820 vtop
->c
.i
= vtop
->c
.ld
;
2821 else if (sbt_bt
== VT_LLONG
|| (PTR_SIZE
== 8 && sbt
== VT_PTR
))
2823 else if (sbt
& VT_UNSIGNED
)
2824 vtop
->c
.i
= (uint32_t)vtop
->c
.i
;
2826 vtop
->c
.i
= ((uint32_t)vtop
->c
.i
| -(vtop
->c
.i
& 0x80000000));
2828 if (dbt_bt
== VT_LLONG
|| (PTR_SIZE
== 8 && dbt
== VT_PTR
))
2830 else if (dbt
== VT_BOOL
)
2831 vtop
->c
.i
= (vtop
->c
.i
!= 0);
2833 uint32_t m
= dbt_bt
== VT_BYTE
? 0xff :
2834 dbt_bt
== VT_SHORT
? 0xffff :
2837 if (!(dbt
& VT_UNSIGNED
))
2838 vtop
->c
.i
|= -(vtop
->c
.i
& ((m
>> 1) + 1));
2843 } else if (dbt
== VT_BOOL
2844 && (vtop
->r
& (VT_VALMASK
| VT_LVAL
| VT_SYM
))
2845 == (VT_CONST
| VT_SYM
)) {
2846 /* addresses are considered non-zero (see tcctest.c:sinit23) */
2852 /* cannot generate code for global or static initializers */
2853 if (STATIC_DATA_WANTED
)
2856 /* non constant case: generate code */
2857 if (dbt
== VT_BOOL
) {
2858 gen_test_zero(TOK_NE
);
2864 /* convert from fp to fp */
2867 /* convert int to fp */
2870 /* convert fp to int */
2872 if (dbt_bt
!= VT_LLONG
&& dbt_bt
!= VT_INT
)
2875 goto again
; /* may need char/short cast */
2880 ds
= btype_size(dbt_bt
);
2881 ss
= btype_size(sbt_bt
);
2882 if (ds
== 0 || ss
== 0) {
2883 if (dbt_bt
== VT_VOID
)
2885 cast_error(&vtop
->type
, type
);
2887 if (IS_ENUM(type
->t
) && type
->ref
->c
< 0)
2888 tcc_error("cast to incomplete type");
2890 /* same size and no sign conversion needed */
2891 if (ds
== ss
&& ds
>= 4)
2893 if (dbt_bt
== VT_PTR
|| sbt_bt
== VT_PTR
) {
2894 tcc_warning("cast between pointer and integer of different size");
2895 if (sbt_bt
== VT_PTR
) {
2896 /* put integer type to allow logical operations below */
2897 vtop
->type
.t
= (PTR_SIZE
== 8 ? VT_LLONG
: VT_INT
);
2901 /* processor allows { int a = 0, b = *(char*)&a; }
2902 That means that if we cast to less width, we can just
2903 change the type and read it still later. */
2904 #define ALLOW_SUBTYPE_ACCESS 1
2906 if (ALLOW_SUBTYPE_ACCESS
&& (vtop
->r
& VT_LVAL
)) {
2907 /* value still in memory */
2913 goto done
; /* no 64bit envolved */
2921 /* generate high word */
2922 if (sbt
& VT_UNSIGNED
) {
2931 } else if (ss
== 8) {
2932 /* from long long: just take low order word */
2940 /* need to convert from 32bit to 64bit */
2941 if (sbt
& VT_UNSIGNED
) {
2942 #if defined(TCC_TARGET_RISCV64)
2943 /* RISC-V keeps 32bit vals in registers sign-extended.
2944 So here we need a zero-extension. */
2953 ss
= ds
, ds
= 4, dbt
= sbt
;
2954 } else if (ss
== 8) {
2955 /* XXX some architectures (e.g. risc-v) would like it
2956 better for this merely being a 32-to-64 sign or zero-
2958 trunc
= 32; /* zero upper 32 bits */
2966 #if defined TCC_TARGET_I386 || defined TCC_TARGET_X86_64 || defined TCC_TARGET_ARM64
2972 bits
= (ss
- ds
) * 8;
2973 /* for unsigned, gen_op will convert SAR to SHR */
2974 vtop
->type
.t
= (ss
== 8 ? VT_LLONG
: VT_INT
) | (dbt
& VT_UNSIGNED
);
2977 vpushi(bits
- trunc
);
2984 vtop
->type
.t
&= ~ ( VT_CONSTANT
| VT_VOLATILE
| VT_ARRAY
);
2987 /* return type size as known at compile time. Put alignment at 'a' */
2988 ST_FUNC
int type_size(CType
*type
, int *a
)
2993 bt
= type
->t
& VT_BTYPE
;
2994 if (bt
== VT_STRUCT
) {
2999 } else if (bt
== VT_PTR
) {
3000 if (type
->t
& VT_ARRAY
) {
3004 ts
= type_size(&s
->type
, a
);
3006 if (ts
< 0 && s
->c
< 0)
3014 } else if (IS_ENUM(type
->t
) && type
->ref
->c
< 0) {
3015 return -1; /* incomplete enum */
3016 } else if (bt
== VT_LDOUBLE
) {
3018 return LDOUBLE_SIZE
;
3019 } else if (bt
== VT_DOUBLE
|| bt
== VT_LLONG
) {
3020 #ifdef TCC_TARGET_I386
3021 #ifdef TCC_TARGET_PE
3026 #elif defined(TCC_TARGET_ARM)
3036 } else if (bt
== VT_INT
|| bt
== VT_FLOAT
) {
3039 } else if (bt
== VT_SHORT
) {
3042 } else if (bt
== VT_QLONG
|| bt
== VT_QFLOAT
) {
3046 /* char, void, function, _Bool */
3052 /* push type size as known at runtime time on top of value stack. Put
3054 ST_FUNC
void vla_runtime_type_size(CType
*type
, int *a
)
3056 if (type
->t
& VT_VLA
) {
3057 type_size(&type
->ref
->type
, a
);
3058 vset(&int_type
, VT_LOCAL
|VT_LVAL
, type
->ref
->c
);
3060 vpushi(type_size(type
, a
));
3064 /* return the pointed type of t */
3065 static inline CType
*pointed_type(CType
*type
)
3067 return &type
->ref
->type
;
3070 /* modify type so that its it is a pointer to type. */
3071 ST_FUNC
void mk_pointer(CType
*type
)
3074 s
= sym_push(SYM_FIELD
, type
, 0, -1);
3075 type
->t
= VT_PTR
| (type
->t
& VT_STORAGE
);
3079 /* compare function types. OLD functions match any new functions */
3080 static int is_compatible_func(CType
*type1
, CType
*type2
)
3086 if (s1
->f
.func_call
!= s2
->f
.func_call
)
3088 if (s1
->f
.func_type
!= s2
->f
.func_type
3089 && s1
->f
.func_type
!= FUNC_OLD
3090 && s2
->f
.func_type
!= FUNC_OLD
)
3092 /* we should check the function return type for FUNC_OLD too
3093 but that causes problems with the internally used support
3094 functions such as TOK_memmove */
3095 if (s1
->f
.func_type
== FUNC_OLD
&& !s1
->next
)
3097 if (s2
->f
.func_type
== FUNC_OLD
&& !s2
->next
)
3100 if (!is_compatible_unqualified_types(&s1
->type
, &s2
->type
))
3111 /* return true if type1 and type2 are the same. If unqualified is
3112 true, qualifiers on the types are ignored.
3114 static int compare_types(CType
*type1
, CType
*type2
, int unqualified
)
3118 t1
= type1
->t
& VT_TYPE
;
3119 t2
= type2
->t
& VT_TYPE
;
3121 /* strip qualifiers before comparing */
3122 t1
&= ~(VT_CONSTANT
| VT_VOLATILE
);
3123 t2
&= ~(VT_CONSTANT
| VT_VOLATILE
);
3126 /* Default Vs explicit signedness only matters for char */
3127 if ((t1
& VT_BTYPE
) != VT_BYTE
) {
3131 /* XXX: bitfields ? */
3136 && !(type1
->ref
->c
< 0
3137 || type2
->ref
->c
< 0
3138 || type1
->ref
->c
== type2
->ref
->c
))
3141 /* test more complicated cases */
3142 bt1
= t1
& VT_BTYPE
;
3143 if (bt1
== VT_PTR
) {
3144 type1
= pointed_type(type1
);
3145 type2
= pointed_type(type2
);
3146 return is_compatible_types(type1
, type2
);
3147 } else if (bt1
== VT_STRUCT
) {
3148 return (type1
->ref
== type2
->ref
);
3149 } else if (bt1
== VT_FUNC
) {
3150 return is_compatible_func(type1
, type2
);
3151 } else if (IS_ENUM(type1
->t
) || IS_ENUM(type2
->t
)) {
3152 return type1
->ref
== type2
->ref
;
3158 /* return true if type1 and type2 are exactly the same (including
3161 static int is_compatible_types(CType
*type1
, CType
*type2
)
3163 return compare_types(type1
,type2
,0);
3166 /* return true if type1 and type2 are the same (ignoring qualifiers).
3168 static int is_compatible_unqualified_types(CType
*type1
, CType
*type2
)
3170 return compare_types(type1
,type2
,1);
3173 /* print a type. If 'varstr' is not NULL, then the variable is also
3174 printed in the type */
3176 /* XXX: add array and function pointers */
3177 static void type_to_str(char *buf
, int buf_size
,
3178 CType
*type
, const char *varstr
)
3190 pstrcat(buf
, buf_size
, "extern ");
3192 pstrcat(buf
, buf_size
, "static ");
3194 pstrcat(buf
, buf_size
, "typedef ");
3196 pstrcat(buf
, buf_size
, "inline ");
3197 if (t
& VT_VOLATILE
)
3198 pstrcat(buf
, buf_size
, "volatile ");
3199 if (t
& VT_CONSTANT
)
3200 pstrcat(buf
, buf_size
, "const ");
3202 if (((t
& VT_DEFSIGN
) && bt
== VT_BYTE
)
3203 || ((t
& VT_UNSIGNED
)
3204 && (bt
== VT_SHORT
|| bt
== VT_INT
|| bt
== VT_LLONG
)
3207 pstrcat(buf
, buf_size
, (t
& VT_UNSIGNED
) ? "unsigned " : "signed ");
3209 buf_size
-= strlen(buf
);
3244 tstr
= "long double";
3246 pstrcat(buf
, buf_size
, tstr
);
3253 pstrcat(buf
, buf_size
, tstr
);
3254 v
= type
->ref
->v
& ~SYM_STRUCT
;
3255 if (v
>= SYM_FIRST_ANOM
)
3256 pstrcat(buf
, buf_size
, "<anonymous>");
3258 pstrcat(buf
, buf_size
, get_tok_str(v
, NULL
));
3263 if (varstr
&& '*' == *varstr
) {
3264 pstrcat(buf1
, sizeof(buf1
), "(");
3265 pstrcat(buf1
, sizeof(buf1
), varstr
);
3266 pstrcat(buf1
, sizeof(buf1
), ")");
3268 pstrcat(buf1
, buf_size
, "(");
3270 while (sa
!= NULL
) {
3272 type_to_str(buf2
, sizeof(buf2
), &sa
->type
, NULL
);
3273 pstrcat(buf1
, sizeof(buf1
), buf2
);
3276 pstrcat(buf1
, sizeof(buf1
), ", ");
3278 if (s
->f
.func_type
== FUNC_ELLIPSIS
)
3279 pstrcat(buf1
, sizeof(buf1
), ", ...");
3280 pstrcat(buf1
, sizeof(buf1
), ")");
3281 type_to_str(buf
, buf_size
, &s
->type
, buf1
);
3286 if (varstr
&& '*' == *varstr
)
3287 snprintf(buf1
, sizeof(buf1
), "(%s)[%d]", varstr
, s
->c
);
3289 snprintf(buf1
, sizeof(buf1
), "%s[%d]", varstr
? varstr
: "", s
->c
);
3290 type_to_str(buf
, buf_size
, &s
->type
, buf1
);
3293 pstrcpy(buf1
, sizeof(buf1
), "*");
3294 if (t
& VT_CONSTANT
)
3295 pstrcat(buf1
, buf_size
, "const ");
3296 if (t
& VT_VOLATILE
)
3297 pstrcat(buf1
, buf_size
, "volatile ");
3299 pstrcat(buf1
, sizeof(buf1
), varstr
);
3300 type_to_str(buf
, buf_size
, &s
->type
, buf1
);
3304 pstrcat(buf
, buf_size
, " ");
3305 pstrcat(buf
, buf_size
, varstr
);
3310 static void cast_error(CType
*st
, CType
*dt
)
3312 char buf1
[256], buf2
[256];
3313 type_to_str(buf1
, sizeof(buf1
), st
, NULL
);
3314 type_to_str(buf2
, sizeof(buf2
), dt
, NULL
);
3315 tcc_error("cannot convert '%s' to '%s'", buf1
, buf2
);
3318 /* verify type compatibility to store vtop in 'dt' type */
3319 static void verify_assign_cast(CType
*dt
)
3321 CType
*st
, *type1
, *type2
;
3322 int dbt
, sbt
, qualwarn
, lvl
;
3324 st
= &vtop
->type
; /* source type */
3325 dbt
= dt
->t
& VT_BTYPE
;
3326 sbt
= st
->t
& VT_BTYPE
;
3327 if (dt
->t
& VT_CONSTANT
)
3328 tcc_warning("assignment of read-only location");
3332 tcc_error("assignment to void expression");
3335 /* special cases for pointers */
3336 /* '0' can also be a pointer */
3337 if (is_null_pointer(vtop
))
3339 /* accept implicit pointer to integer cast with warning */
3340 if (is_integer_btype(sbt
)) {
3341 tcc_warning("assignment makes pointer from integer without a cast");
3344 type1
= pointed_type(dt
);
3346 type2
= pointed_type(st
);
3347 else if (sbt
== VT_FUNC
)
3348 type2
= st
; /* a function is implicitly a function pointer */
3351 if (is_compatible_types(type1
, type2
))
3353 for (qualwarn
= lvl
= 0;; ++lvl
) {
3354 if (((type2
->t
& VT_CONSTANT
) && !(type1
->t
& VT_CONSTANT
)) ||
3355 ((type2
->t
& VT_VOLATILE
) && !(type1
->t
& VT_VOLATILE
)))
3357 dbt
= type1
->t
& (VT_BTYPE
|VT_LONG
);
3358 sbt
= type2
->t
& (VT_BTYPE
|VT_LONG
);
3359 if (dbt
!= VT_PTR
|| sbt
!= VT_PTR
)
3361 type1
= pointed_type(type1
);
3362 type2
= pointed_type(type2
);
3364 if (!is_compatible_unqualified_types(type1
, type2
)) {
3365 if ((dbt
== VT_VOID
|| sbt
== VT_VOID
) && lvl
== 0) {
3366 /* void * can match anything */
3367 } else if (dbt
== sbt
3368 && is_integer_btype(sbt
& VT_BTYPE
)
3369 && IS_ENUM(type1
->t
) + IS_ENUM(type2
->t
)
3370 + !!((type1
->t
^ type2
->t
) & VT_UNSIGNED
) < 2) {
3371 /* Like GCC don't warn by default for merely changes
3372 in pointer target signedness. Do warn for different
3373 base types, though, in particular for unsigned enums
3374 and signed int targets. */
3376 tcc_warning("assignment from incompatible pointer type");
3381 tcc_warning("assignment discards qualifiers from pointer target type");
3387 if (sbt
== VT_PTR
|| sbt
== VT_FUNC
) {
3388 tcc_warning("assignment makes integer from pointer without a cast");
3389 } else if (sbt
== VT_STRUCT
) {
3390 goto case_VT_STRUCT
;
3392 /* XXX: more tests */
3396 if (!is_compatible_unqualified_types(dt
, st
)) {
3404 static void gen_assign_cast(CType
*dt
)
3406 verify_assign_cast(dt
);
3410 /* store vtop in lvalue pushed on stack */
3411 ST_FUNC
void vstore(void)
3413 int sbt
, dbt
, ft
, r
, size
, align
, bit_size
, bit_pos
, delayed_cast
;
3415 ft
= vtop
[-1].type
.t
;
3416 sbt
= vtop
->type
.t
& VT_BTYPE
;
3417 dbt
= ft
& VT_BTYPE
;
3419 verify_assign_cast(&vtop
[-1].type
);
3421 if (sbt
== VT_STRUCT
) {
3422 /* if structure, only generate pointer */
3423 /* structure assignment : generate memcpy */
3424 /* XXX: optimize if small size */
3425 size
= type_size(&vtop
->type
, &align
);
3429 #ifdef CONFIG_TCC_BCHECK
3430 if (vtop
->r
& VT_MUSTBOUND
)
3431 gbound(); /* check would be wrong after gaddrof() */
3433 vtop
->type
.t
= VT_PTR
;
3436 /* address of memcpy() */
3439 vpush_global_sym(&func_old_type
, TOK_memcpy8
);
3440 else if(!(align
& 3))
3441 vpush_global_sym(&func_old_type
, TOK_memcpy4
);
3444 /* Use memmove, rather than memcpy, as dest and src may be same: */
3445 vpush_global_sym(&func_old_type
, TOK_memmove
);
3450 #ifdef CONFIG_TCC_BCHECK
3451 if (vtop
->r
& VT_MUSTBOUND
)
3454 vtop
->type
.t
= VT_PTR
;
3459 /* leave source on stack */
3461 } else if (ft
& VT_BITFIELD
) {
3462 /* bitfield store handling */
3464 /* save lvalue as expression result (example: s.b = s.a = n;) */
3465 vdup(), vtop
[-1] = vtop
[-2];
3467 bit_pos
= BIT_POS(ft
);
3468 bit_size
= BIT_SIZE(ft
);
3469 /* remove bit field info to avoid loops */
3470 vtop
[-1].type
.t
= ft
& ~VT_STRUCT_MASK
;
3472 if (dbt
== VT_BOOL
) {
3473 gen_cast(&vtop
[-1].type
);
3474 vtop
[-1].type
.t
= (vtop
[-1].type
.t
& ~VT_BTYPE
) | (VT_BYTE
| VT_UNSIGNED
);
3476 r
= adjust_bf(vtop
- 1, bit_pos
, bit_size
);
3477 if (dbt
!= VT_BOOL
) {
3478 gen_cast(&vtop
[-1].type
);
3479 dbt
= vtop
[-1].type
.t
& VT_BTYPE
;
3481 if (r
== VT_STRUCT
) {
3482 store_packed_bf(bit_pos
, bit_size
);
3484 unsigned long long mask
= (1ULL << bit_size
) - 1;
3485 if (dbt
!= VT_BOOL
) {
3487 if (dbt
== VT_LLONG
)
3490 vpushi((unsigned)mask
);
3497 /* duplicate destination */
3500 /* load destination, mask and or with source */
3501 if (dbt
== VT_LLONG
)
3502 vpushll(~(mask
<< bit_pos
));
3504 vpushi(~((unsigned)mask
<< bit_pos
));
3509 /* ... and discard */
3512 } else if (dbt
== VT_VOID
) {
3515 /* optimize char/short casts */
3517 if ((dbt
== VT_BYTE
|| dbt
== VT_SHORT
)
3518 && is_integer_btype(sbt
)
3520 if ((vtop
->r
& VT_MUSTCAST
)
3521 && btype_size(dbt
) > btype_size(sbt
)
3523 force_charshort_cast();
3526 gen_cast(&vtop
[-1].type
);
3529 #ifdef CONFIG_TCC_BCHECK
3530 /* bound check case */
3531 if (vtop
[-1].r
& VT_MUSTBOUND
) {
3537 gv(RC_TYPE(dbt
)); /* generate value */
3540 vtop
->r
|= BFVAL(VT_MUSTCAST
, (sbt
== VT_LLONG
) + 1);
3541 //tcc_warning("deley cast %x -> %x", sbt, dbt);
3542 vtop
->type
.t
= ft
& VT_TYPE
;
3545 /* if lvalue was saved on stack, must read it */
3546 if ((vtop
[-1].r
& VT_VALMASK
) == VT_LLOCAL
) {
3548 r
= get_reg(RC_INT
);
3549 sv
.type
.t
= VT_PTRDIFF_T
;
3550 sv
.r
= VT_LOCAL
| VT_LVAL
;
3551 sv
.c
.i
= vtop
[-1].c
.i
;
3553 vtop
[-1].r
= r
| VT_LVAL
;
3556 r
= vtop
->r
& VT_VALMASK
;
3557 /* two word case handling :
3558 store second register at word + 4 (or +8 for x86-64) */
3559 if (USING_TWO_WORDS(dbt
)) {
3560 int load_type
= (dbt
== VT_QFLOAT
) ? VT_DOUBLE
: VT_PTRDIFF_T
;
3561 vtop
[-1].type
.t
= load_type
;
3564 /* convert to int to increment easily */
3565 vtop
->type
.t
= VT_PTRDIFF_T
;
3571 vtop
[-1].type
.t
= load_type
;
3572 /* XXX: it works because r2 is spilled last ! */
3573 store(vtop
->r2
, vtop
- 1);
3579 vtop
--; /* NOT vpop() because on x86 it would flush the fp stack */
3583 /* post defines POST/PRE add. c is the token ++ or -- */
3584 ST_FUNC
void inc(int post
, int c
)
3587 vdup(); /* save lvalue */
3589 gv_dup(); /* duplicate value */
3594 vpushi(c
- TOK_MID
);
3596 vstore(); /* store value */
3598 vpop(); /* if post op, return saved value */
3601 ST_FUNC
void parse_mult_str (CString
*astr
, const char *msg
)
3603 /* read the string */
3607 while (tok
== TOK_STR
) {
3608 /* XXX: add \0 handling too ? */
3609 cstr_cat(astr
, tokc
.str
.data
, -1);
3612 cstr_ccat(astr
, '\0');
3615 /* If I is >= 1 and a power of two, returns log2(i)+1.
3616 If I is 0 returns 0. */
3617 static int exact_log2p1(int i
)
3622 for (ret
= 1; i
>= 1 << 8; ret
+= 8)
3633 /* Parse __attribute__((...)) GNUC extension. */
3634 static void parse_attribute(AttributeDef
*ad
)
3640 if (tok
!= TOK_ATTRIBUTE1
&& tok
!= TOK_ATTRIBUTE2
)
3645 while (tok
!= ')') {
3646 if (tok
< TOK_IDENT
)
3647 expect("attribute name");
3659 tcc_warning("implicit declaration of function '%s'",
3660 get_tok_str(tok
, &tokc
));
3661 s
= external_global_sym(tok
, &func_old_type
);
3663 ad
->cleanup_func
= s
;
3668 case TOK_CONSTRUCTOR1
:
3669 case TOK_CONSTRUCTOR2
:
3670 ad
->f
.func_ctor
= 1;
3672 case TOK_DESTRUCTOR1
:
3673 case TOK_DESTRUCTOR2
:
3674 ad
->f
.func_dtor
= 1;
3679 parse_mult_str(&astr
, "section name");
3680 ad
->section
= find_section(tcc_state
, (char *)astr
.data
);
3687 parse_mult_str(&astr
, "alias(\"target\")");
3688 ad
->alias_target
= /* save string as token, for later */
3689 tok_alloc((char*)astr
.data
, astr
.size
-1)->tok
;
3693 case TOK_VISIBILITY1
:
3694 case TOK_VISIBILITY2
:
3696 parse_mult_str(&astr
,
3697 "visibility(\"default|hidden|internal|protected\")");
3698 if (!strcmp (astr
.data
, "default"))
3699 ad
->a
.visibility
= STV_DEFAULT
;
3700 else if (!strcmp (astr
.data
, "hidden"))
3701 ad
->a
.visibility
= STV_HIDDEN
;
3702 else if (!strcmp (astr
.data
, "internal"))
3703 ad
->a
.visibility
= STV_INTERNAL
;
3704 else if (!strcmp (astr
.data
, "protected"))
3705 ad
->a
.visibility
= STV_PROTECTED
;
3707 expect("visibility(\"default|hidden|internal|protected\")");
3716 if (n
<= 0 || (n
& (n
- 1)) != 0)
3717 tcc_error("alignment must be a positive power of two");
3722 ad
->a
.aligned
= exact_log2p1(n
);
3723 if (n
!= 1 << (ad
->a
.aligned
- 1))
3724 tcc_error("alignment of %d is larger than implemented", n
);
3736 /* currently, no need to handle it because tcc does not
3737 track unused objects */
3741 ad
->f
.func_noreturn
= 1;
3746 ad
->f
.func_call
= FUNC_CDECL
;
3751 ad
->f
.func_call
= FUNC_STDCALL
;
3753 #ifdef TCC_TARGET_I386
3763 ad
->f
.func_call
= FUNC_FASTCALL1
+ n
- 1;
3769 ad
->f
.func_call
= FUNC_FASTCALLW
;
3776 ad
->attr_mode
= VT_LLONG
+ 1;
3779 ad
->attr_mode
= VT_BYTE
+ 1;
3782 ad
->attr_mode
= VT_SHORT
+ 1;
3786 ad
->attr_mode
= VT_INT
+ 1;
3789 tcc_warning("__mode__(%s) not supported\n", get_tok_str(tok
, NULL
));
3796 ad
->a
.dllexport
= 1;
3798 case TOK_NODECORATE
:
3799 ad
->a
.nodecorate
= 1;
3802 ad
->a
.dllimport
= 1;
3805 if (tcc_state
->warn_unsupported
)
3806 tcc_warning("'%s' attribute ignored", get_tok_str(t
, NULL
));
3807 /* skip parameters */
3809 int parenthesis
= 0;
3813 else if (tok
== ')')
3816 } while (parenthesis
&& tok
!= -1);
3829 static Sym
* find_field (CType
*type
, int v
, int *cumofs
)
3833 while ((s
= s
->next
) != NULL
) {
3834 if ((s
->v
& SYM_FIELD
) &&
3835 (s
->type
.t
& VT_BTYPE
) == VT_STRUCT
&&
3836 (s
->v
& ~SYM_FIELD
) >= SYM_FIRST_ANOM
) {
3837 Sym
*ret
= find_field (&s
->type
, v
, cumofs
);
3849 static void struct_layout(CType
*type
, AttributeDef
*ad
)
3851 int size
, align
, maxalign
, offset
, c
, bit_pos
, bit_size
;
3852 int packed
, a
, bt
, prevbt
, prev_bit_size
;
3853 int pcc
= !tcc_state
->ms_bitfields
;
3854 int pragma_pack
= *tcc_state
->pack_stack_ptr
;
3861 prevbt
= VT_STRUCT
; /* make it never match */
3866 for (f
= type
->ref
->next
; f
; f
= f
->next
) {
3867 if (f
->type
.t
& VT_BITFIELD
)
3868 bit_size
= BIT_SIZE(f
->type
.t
);
3871 size
= type_size(&f
->type
, &align
);
3872 a
= f
->a
.aligned
? 1 << (f
->a
.aligned
- 1) : 0;
3875 if (pcc
&& bit_size
== 0) {
3876 /* in pcc mode, packing does not affect zero-width bitfields */
3879 /* in pcc mode, attribute packed overrides if set. */
3880 if (pcc
&& (f
->a
.packed
|| ad
->a
.packed
))
3883 /* pragma pack overrides align if lesser and packs bitfields always */
3886 if (pragma_pack
< align
)
3887 align
= pragma_pack
;
3888 /* in pcc mode pragma pack also overrides individual align */
3889 if (pcc
&& pragma_pack
< a
)
3893 /* some individual align was specified */
3897 if (type
->ref
->type
.t
== VT_UNION
) {
3898 if (pcc
&& bit_size
>= 0)
3899 size
= (bit_size
+ 7) >> 3;
3904 } else if (bit_size
< 0) {
3906 c
+= (bit_pos
+ 7) >> 3;
3907 c
= (c
+ align
- 1) & -align
;
3916 /* A bit-field. Layout is more complicated. There are two
3917 options: PCC (GCC) compatible and MS compatible */
3919 /* In PCC layout a bit-field is placed adjacent to the
3920 preceding bit-fields, except if:
3922 - an individual alignment was given
3923 - it would overflow its base type container and
3924 there is no packing */
3925 if (bit_size
== 0) {
3927 c
= (c
+ ((bit_pos
+ 7) >> 3) + align
- 1) & -align
;
3929 } else if (f
->a
.aligned
) {
3931 } else if (!packed
) {
3933 int ofs
= ((c
* 8 + bit_pos
) % a8
+ bit_size
+ a8
- 1) / a8
;
3934 if (ofs
> size
/ align
)
3938 /* in pcc mode, long long bitfields have type int if they fit */
3939 if (size
== 8 && bit_size
<= 32)
3940 f
->type
.t
= (f
->type
.t
& ~VT_BTYPE
) | VT_INT
, size
= 4;
3942 while (bit_pos
>= align
* 8)
3943 c
+= align
, bit_pos
-= align
* 8;
3946 /* In PCC layout named bit-fields influence the alignment
3947 of the containing struct using the base types alignment,
3948 except for packed fields (which here have correct align). */
3949 if (f
->v
& SYM_FIRST_ANOM
3950 // && bit_size // ??? gcc on ARM/rpi does that
3955 bt
= f
->type
.t
& VT_BTYPE
;
3956 if ((bit_pos
+ bit_size
> size
* 8)
3957 || (bit_size
> 0) == (bt
!= prevbt
)
3959 c
= (c
+ align
- 1) & -align
;
3962 /* In MS bitfield mode a bit-field run always uses
3963 at least as many bits as the underlying type.
3964 To start a new run it's also required that this
3965 or the last bit-field had non-zero width. */
3966 if (bit_size
|| prev_bit_size
)
3969 /* In MS layout the records alignment is normally
3970 influenced by the field, except for a zero-width
3971 field at the start of a run (but by further zero-width
3972 fields it is again). */
3973 if (bit_size
== 0 && prevbt
!= bt
)
3976 prev_bit_size
= bit_size
;
3979 f
->type
.t
= (f
->type
.t
& ~(0x3f << VT_STRUCT_SHIFT
))
3980 | (bit_pos
<< VT_STRUCT_SHIFT
);
3981 bit_pos
+= bit_size
;
3983 if (align
> maxalign
)
3987 printf("set field %s offset %-2d size %-2d align %-2d",
3988 get_tok_str(f
->v
& ~SYM_FIELD
, NULL
), offset
, size
, align
);
3989 if (f
->type
.t
& VT_BITFIELD
) {
3990 printf(" pos %-2d bits %-2d",
4003 c
+= (bit_pos
+ 7) >> 3;
4005 /* store size and alignment */
4006 a
= bt
= ad
->a
.aligned
? 1 << (ad
->a
.aligned
- 1) : 1;
4010 if (pragma_pack
&& pragma_pack
< maxalign
&& 0 == pcc
) {
4011 /* can happen if individual align for some member was given. In
4012 this case MSVC ignores maxalign when aligning the size */
4017 c
= (c
+ a
- 1) & -a
;
4021 printf("struct size %-2d align %-2d\n\n", c
, a
), fflush(stdout
);
4024 /* check whether we can access bitfields by their type */
4025 for (f
= type
->ref
->next
; f
; f
= f
->next
) {
4029 if (0 == (f
->type
.t
& VT_BITFIELD
))
4033 bit_size
= BIT_SIZE(f
->type
.t
);
4036 bit_pos
= BIT_POS(f
->type
.t
);
4037 size
= type_size(&f
->type
, &align
);
4038 if (bit_pos
+ bit_size
<= size
* 8 && f
->c
+ size
<= c
)
4041 /* try to access the field using a different type */
4042 c0
= -1, s
= align
= 1;
4044 px
= f
->c
* 8 + bit_pos
;
4045 cx
= (px
>> 3) & -align
;
4046 px
= px
- (cx
<< 3);
4049 s
= (px
+ bit_size
+ 7) >> 3;
4059 s
= type_size(&t
, &align
);
4063 if (px
+ bit_size
<= s
* 8 && cx
+ s
<= c
) {
4064 /* update offset and bit position */
4067 f
->type
.t
= (f
->type
.t
& ~(0x3f << VT_STRUCT_SHIFT
))
4068 | (bit_pos
<< VT_STRUCT_SHIFT
);
4072 printf("FIX field %s offset %-2d size %-2d align %-2d "
4073 "pos %-2d bits %-2d\n",
4074 get_tok_str(f
->v
& ~SYM_FIELD
, NULL
),
4075 cx
, s
, align
, px
, bit_size
);
4078 /* fall back to load/store single-byte wise */
4079 f
->auxtype
= VT_STRUCT
;
4081 printf("FIX field %s : load byte-wise\n",
4082 get_tok_str(f
->v
& ~SYM_FIELD
, NULL
));
4088 /* enum/struct/union declaration. u is VT_ENUM/VT_STRUCT/VT_UNION */
4089 static void struct_decl(CType
*type
, int u
)
4091 int v
, c
, size
, align
, flexible
;
4092 int bit_size
, bsize
, bt
;
4094 AttributeDef ad
, ad1
;
4097 memset(&ad
, 0, sizeof ad
);
4099 parse_attribute(&ad
);
4103 /* struct already defined ? return it */
4105 expect("struct/union/enum name");
4107 if (s
&& (s
->sym_scope
== local_scope
|| tok
!= '{')) {
4110 if (u
== VT_ENUM
&& IS_ENUM(s
->type
.t
))
4112 tcc_error("redefinition of '%s'", get_tok_str(v
, NULL
));
4117 /* Record the original enum/struct/union token. */
4118 type1
.t
= u
== VT_ENUM
? u
| VT_INT
| VT_UNSIGNED
: u
;
4120 /* we put an undefined size for struct/union */
4121 s
= sym_push(v
| SYM_STRUCT
, &type1
, 0, -1);
4122 s
->r
= 0; /* default alignment is zero as gcc */
4124 type
->t
= s
->type
.t
;
4130 tcc_error("struct/union/enum already defined");
4132 /* cannot be empty */
4133 /* non empty enums are not allowed */
4136 long long ll
= 0, pl
= 0, nl
= 0;
4139 /* enum symbols have static storage */
4140 t
.t
= VT_INT
|VT_STATIC
|VT_ENUM_VAL
;
4144 expect("identifier");
4146 if (ss
&& !local_stack
)
4147 tcc_error("redefinition of enumerator '%s'",
4148 get_tok_str(v
, NULL
));
4152 ll
= expr_const64();
4154 ss
= sym_push(v
, &t
, VT_CONST
, 0);
4156 *ps
= ss
, ps
= &ss
->next
;
4165 /* NOTE: we accept a trailing comma */
4170 /* set integral type of the enum */
4173 if (pl
!= (unsigned)pl
)
4174 t
.t
= (LONG_SIZE
==8 ? VT_LLONG
|VT_LONG
: VT_LLONG
);
4176 } else if (pl
!= (int)pl
|| nl
!= (int)nl
)
4177 t
.t
= (LONG_SIZE
==8 ? VT_LLONG
|VT_LONG
: VT_LLONG
);
4178 s
->type
.t
= type
->t
= t
.t
| VT_ENUM
;
4180 /* set type for enum members */
4181 for (ss
= s
->next
; ss
; ss
= ss
->next
) {
4183 if (ll
== (int)ll
) /* default is int if it fits */
4185 if (t
.t
& VT_UNSIGNED
) {
4186 ss
->type
.t
|= VT_UNSIGNED
;
4187 if (ll
== (unsigned)ll
)
4190 ss
->type
.t
= (ss
->type
.t
& ~VT_BTYPE
)
4191 | (LONG_SIZE
==8 ? VT_LLONG
|VT_LONG
: VT_LLONG
);
4196 while (tok
!= '}') {
4197 if (!parse_btype(&btype
, &ad1
)) {
4203 tcc_error("flexible array member '%s' not at the end of struct",
4204 get_tok_str(v
, NULL
));
4210 type_decl(&type1
, &ad1
, &v
, TYPE_DIRECT
);
4212 if ((type1
.t
& VT_BTYPE
) != VT_STRUCT
)
4213 expect("identifier");
4215 int v
= btype
.ref
->v
;
4216 if (!(v
& SYM_FIELD
) && (v
& ~SYM_STRUCT
) < SYM_FIRST_ANOM
) {
4217 if (tcc_state
->ms_extensions
== 0)
4218 expect("identifier");
4222 if (type_size(&type1
, &align
) < 0) {
4223 if ((u
== VT_STRUCT
) && (type1
.t
& VT_ARRAY
) && c
)
4226 tcc_error("field '%s' has incomplete type",
4227 get_tok_str(v
, NULL
));
4229 if ((type1
.t
& VT_BTYPE
) == VT_FUNC
||
4230 (type1
.t
& VT_BTYPE
) == VT_VOID
||
4231 (type1
.t
& VT_STORAGE
))
4232 tcc_error("invalid type for '%s'",
4233 get_tok_str(v
, NULL
));
4237 bit_size
= expr_const();
4238 /* XXX: handle v = 0 case for messages */
4240 tcc_error("negative width in bit-field '%s'",
4241 get_tok_str(v
, NULL
));
4242 if (v
&& bit_size
== 0)
4243 tcc_error("zero width for bit-field '%s'",
4244 get_tok_str(v
, NULL
));
4245 parse_attribute(&ad1
);
4247 size
= type_size(&type1
, &align
);
4248 if (bit_size
>= 0) {
4249 bt
= type1
.t
& VT_BTYPE
;
4255 tcc_error("bitfields must have scalar type");
4257 if (bit_size
> bsize
) {
4258 tcc_error("width of '%s' exceeds its type",
4259 get_tok_str(v
, NULL
));
4260 } else if (bit_size
== bsize
4261 && !ad
.a
.packed
&& !ad1
.a
.packed
) {
4262 /* no need for bit fields */
4264 } else if (bit_size
== 64) {
4265 tcc_error("field width 64 not implemented");
4267 type1
.t
= (type1
.t
& ~VT_STRUCT_MASK
)
4269 | (bit_size
<< (VT_STRUCT_SHIFT
+ 6));
4272 if (v
!= 0 || (type1
.t
& VT_BTYPE
) == VT_STRUCT
) {
4273 /* Remember we've seen a real field to check
4274 for placement of flexible array member. */
4277 /* If member is a struct or bit-field, enforce
4278 placing into the struct (as anonymous). */
4280 ((type1
.t
& VT_BTYPE
) == VT_STRUCT
||
4285 ss
= sym_push(v
| SYM_FIELD
, &type1
, 0, 0);
4290 if (tok
== ';' || tok
== TOK_EOF
)
4297 parse_attribute(&ad
);
4298 struct_layout(type
, &ad
);
4303 static void sym_to_attr(AttributeDef
*ad
, Sym
*s
)
4305 merge_symattr(&ad
->a
, &s
->a
);
4306 merge_funcattr(&ad
->f
, &s
->f
);
4309 /* Add type qualifiers to a type. If the type is an array then the qualifiers
4310 are added to the element type, copied because it could be a typedef. */
4311 static void parse_btype_qualify(CType
*type
, int qualifiers
)
4313 while (type
->t
& VT_ARRAY
) {
4314 type
->ref
= sym_push(SYM_FIELD
, &type
->ref
->type
, 0, type
->ref
->c
);
4315 type
= &type
->ref
->type
;
4317 type
->t
|= qualifiers
;
4320 /* return 0 if no type declaration. otherwise, return the basic type
4323 static int parse_btype(CType
*type
, AttributeDef
*ad
)
4325 int t
, u
, bt
, st
, type_found
, typespec_found
, g
, n
;
4329 memset(ad
, 0, sizeof(AttributeDef
));
4339 /* currently, we really ignore extension */
4349 if (u
== VT_SHORT
|| u
== VT_LONG
) {
4350 if (st
!= -1 || (bt
!= -1 && bt
!= VT_INT
))
4351 tmbt
: tcc_error("too many basic types");
4354 if (bt
!= -1 || (st
!= -1 && u
!= VT_INT
))
4359 t
= (t
& ~(VT_BTYPE
|VT_LONG
)) | u
;
4376 memset(&ad1
, 0, sizeof(AttributeDef
));
4377 if (parse_btype(&type1
, &ad1
)) {
4378 type_decl(&type1
, &ad1
, &n
, TYPE_ABSTRACT
);
4380 n
= 1 << (ad1
.a
.aligned
- 1);
4382 type_size(&type1
, &n
);
4385 if (n
<= 0 || (n
& (n
- 1)) != 0)
4386 tcc_error("alignment must be a positive power of two");
4389 ad
->a
.aligned
= exact_log2p1(n
);
4393 if ((t
& VT_BTYPE
) == VT_DOUBLE
) {
4394 t
= (t
& ~(VT_BTYPE
|VT_LONG
)) | VT_LDOUBLE
;
4395 } else if ((t
& (VT_BTYPE
|VT_LONG
)) == VT_LONG
) {
4396 t
= (t
& ~(VT_BTYPE
|VT_LONG
)) | VT_LLONG
;
4403 #ifdef TCC_TARGET_ARM64
4405 /* GCC's __uint128_t appears in some Linux header files. Make it a
4406 synonym for long double to get the size and alignment right. */
4417 if ((t
& (VT_BTYPE
|VT_LONG
)) == VT_LONG
) {
4418 t
= (t
& ~(VT_BTYPE
|VT_LONG
)) | VT_LDOUBLE
;
4426 struct_decl(&type1
, VT_ENUM
);
4429 type
->ref
= type1
.ref
;
4432 struct_decl(&type1
, VT_STRUCT
);
4435 struct_decl(&type1
, VT_UNION
);
4438 /* type modifiers */
4443 parse_btype_qualify(type
, VT_CONSTANT
);
4451 parse_btype_qualify(type
, VT_VOLATILE
);
4458 if ((t
& (VT_DEFSIGN
|VT_UNSIGNED
)) == (VT_DEFSIGN
|VT_UNSIGNED
))
4459 tcc_error("signed and unsigned modifier");
4472 if ((t
& (VT_DEFSIGN
|VT_UNSIGNED
)) == VT_DEFSIGN
)
4473 tcc_error("signed and unsigned modifier");
4474 t
|= VT_DEFSIGN
| VT_UNSIGNED
;
4490 if (t
& (VT_EXTERN
|VT_STATIC
|VT_TYPEDEF
) & ~g
)
4491 tcc_error("multiple storage classes");
4503 ad
->f
.func_noreturn
= 1;
4505 /* GNUC attribute */
4506 case TOK_ATTRIBUTE1
:
4507 case TOK_ATTRIBUTE2
:
4508 parse_attribute(ad
);
4509 if (ad
->attr_mode
) {
4510 u
= ad
->attr_mode
-1;
4511 t
= (t
& ~(VT_BTYPE
|VT_LONG
)) | u
;
4519 parse_expr_type(&type1
);
4520 /* remove all storage modifiers except typedef */
4521 type1
.t
&= ~(VT_STORAGE
&~VT_TYPEDEF
);
4523 sym_to_attr(ad
, type1
.ref
);
4529 if (!s
|| !(s
->type
.t
& VT_TYPEDEF
))
4533 if (tok
== ':' && !in_generic
) {
4534 /* ignore if it's a label */
4539 t
&= ~(VT_BTYPE
|VT_LONG
);
4540 u
= t
& ~(VT_CONSTANT
| VT_VOLATILE
), t
^= u
;
4541 type
->t
= (s
->type
.t
& ~VT_TYPEDEF
) | u
;
4542 type
->ref
= s
->type
.ref
;
4544 parse_btype_qualify(type
, t
);
4546 /* get attributes from typedef */
4555 if (tcc_state
->char_is_unsigned
) {
4556 if ((t
& (VT_DEFSIGN
|VT_BTYPE
)) == VT_BYTE
)
4559 /* VT_LONG is used just as a modifier for VT_INT / VT_LLONG */
4560 bt
= t
& (VT_BTYPE
|VT_LONG
);
4562 t
|= LONG_SIZE
== 8 ? VT_LLONG
: VT_INT
;
4563 #ifdef TCC_TARGET_PE
4564 if (bt
== VT_LDOUBLE
)
4565 t
= (t
& ~(VT_BTYPE
|VT_LONG
)) | VT_DOUBLE
;
4571 /* convert a function parameter type (array to pointer and function to
4572 function pointer) */
4573 static inline void convert_parameter_type(CType
*pt
)
4575 /* remove const and volatile qualifiers (XXX: const could be used
4576 to indicate a const function parameter */
4577 pt
->t
&= ~(VT_CONSTANT
| VT_VOLATILE
);
4578 /* array must be transformed to pointer according to ANSI C */
4580 if ((pt
->t
& VT_BTYPE
) == VT_FUNC
) {
4585 ST_FUNC
void parse_asm_str(CString
*astr
)
4588 parse_mult_str(astr
, "string constant");
4591 /* Parse an asm label and return the token */
4592 static int asm_label_instr(void)
4598 parse_asm_str(&astr
);
4601 printf("asm_alias: \"%s\"\n", (char *)astr
.data
);
4603 v
= tok_alloc(astr
.data
, astr
.size
- 1)->tok
;
4608 static int post_type(CType
*type
, AttributeDef
*ad
, int storage
, int td
)
4610 int n
, l
, t1
, arg_size
, align
, unused_align
;
4611 Sym
**plast
, *s
, *first
;
4616 /* function type, or recursive declarator (return if so) */
4618 if (td
&& !(td
& TYPE_ABSTRACT
))
4622 else if (parse_btype(&pt
, &ad1
))
4625 merge_attr (ad
, &ad1
);
4634 /* read param name and compute offset */
4635 if (l
!= FUNC_OLD
) {
4636 if ((pt
.t
& VT_BTYPE
) == VT_VOID
&& tok
== ')')
4638 type_decl(&pt
, &ad1
, &n
, TYPE_DIRECT
| TYPE_ABSTRACT
);
4639 if ((pt
.t
& VT_BTYPE
) == VT_VOID
)
4640 tcc_error("parameter declared as void");
4644 expect("identifier");
4645 pt
.t
= VT_VOID
; /* invalid type */
4649 convert_parameter_type(&pt
);
4650 arg_size
+= (type_size(&pt
, &align
) + PTR_SIZE
- 1) / PTR_SIZE
;
4651 s
= sym_push(n
| SYM_FIELD
, &pt
, 0, 0);
4657 if (l
== FUNC_NEW
&& tok
== TOK_DOTS
) {
4662 if (l
== FUNC_NEW
&& !parse_btype(&pt
, &ad1
))
4663 tcc_error("invalid type");
4666 /* if no parameters, then old type prototype */
4669 /* NOTE: const is ignored in returned type as it has a special
4670 meaning in gcc / C++ */
4671 type
->t
&= ~VT_CONSTANT
;
4672 /* some ancient pre-K&R C allows a function to return an array
4673 and the array brackets to be put after the arguments, such
4674 that "int c()[]" means something like "int[] c()" */
4677 skip(']'); /* only handle simple "[]" */
4680 /* we push a anonymous symbol which will contain the function prototype */
4681 ad
->f
.func_args
= arg_size
;
4682 ad
->f
.func_type
= l
;
4683 s
= sym_push(SYM_FIELD
, type
, 0, 0);
4689 } else if (tok
== '[') {
4690 int saved_nocode_wanted
= nocode_wanted
;
4691 /* array definition */
4694 /* XXX The optional type-quals and static should only be accepted
4695 in parameter decls. The '*' as well, and then even only
4696 in prototypes (not function defs). */
4698 case TOK_RESTRICT1
: case TOK_RESTRICT2
: case TOK_RESTRICT3
:
4713 if (!local_stack
|| (storage
& VT_STATIC
))
4714 vpushi(expr_const());
4716 /* VLAs (which can only happen with local_stack && !VT_STATIC)
4717 length must always be evaluated, even under nocode_wanted,
4718 so that its size slot is initialized (e.g. under sizeof
4723 if ((vtop
->r
& (VT_VALMASK
| VT_LVAL
| VT_SYM
)) == VT_CONST
) {
4726 tcc_error("invalid array size");
4728 if (!is_integer_btype(vtop
->type
.t
& VT_BTYPE
))
4729 tcc_error("size of variable length array should be an integer");
4735 /* parse next post type */
4736 post_type(type
, ad
, storage
, 0);
4738 if ((type
->t
& VT_BTYPE
) == VT_FUNC
)
4739 tcc_error("declaration of an array of functions");
4740 if ((type
->t
& VT_BTYPE
) == VT_VOID
4741 || type_size(type
, &unused_align
) < 0)
4742 tcc_error("declaration of an array of incomplete type elements");
4744 t1
|= type
->t
& VT_VLA
;
4748 tcc_error("need explicit inner array size in VLAs");
4749 loc
-= type_size(&int_type
, &align
);
4753 vla_runtime_type_size(type
, &align
);
4755 vset(&int_type
, VT_LOCAL
|VT_LVAL
, n
);
4761 nocode_wanted
= saved_nocode_wanted
;
4763 /* we push an anonymous symbol which will contain the array
4765 s
= sym_push(SYM_FIELD
, type
, 0, n
);
4766 type
->t
= (t1
? VT_VLA
: VT_ARRAY
) | VT_PTR
;
4772 /* Parse a type declarator (except basic type), and return the type
4773 in 'type'. 'td' is a bitmask indicating which kind of type decl is
4774 expected. 'type' should contain the basic type. 'ad' is the
4775 attribute definition of the basic type. It can be modified by
4776 type_decl(). If this (possibly abstract) declarator is a pointer chain
4777 it returns the innermost pointed to type (equals *type, but is a different
4778 pointer), otherwise returns type itself, that's used for recursive calls. */
4779 static CType
*type_decl(CType
*type
, AttributeDef
*ad
, int *v
, int td
)
4782 int qualifiers
, storage
;
4784 /* recursive type, remove storage bits first, apply them later again */
4785 storage
= type
->t
& VT_STORAGE
;
4786 type
->t
&= ~VT_STORAGE
;
4789 while (tok
== '*') {
4797 qualifiers
|= VT_CONSTANT
;
4802 qualifiers
|= VT_VOLATILE
;
4808 /* XXX: clarify attribute handling */
4809 case TOK_ATTRIBUTE1
:
4810 case TOK_ATTRIBUTE2
:
4811 parse_attribute(ad
);
4815 type
->t
|= qualifiers
;
4817 /* innermost pointed to type is the one for the first derivation */
4818 ret
= pointed_type(type
);
4822 /* This is possibly a parameter type list for abstract declarators
4823 ('int ()'), use post_type for testing this. */
4824 if (!post_type(type
, ad
, 0, td
)) {
4825 /* It's not, so it's a nested declarator, and the post operations
4826 apply to the innermost pointed to type (if any). */
4827 /* XXX: this is not correct to modify 'ad' at this point, but
4828 the syntax is not clear */
4829 parse_attribute(ad
);
4830 post
= type_decl(type
, ad
, v
, td
);
4834 } else if (tok
>= TOK_IDENT
&& (td
& TYPE_DIRECT
)) {
4835 /* type identifier */
4840 if (!(td
& TYPE_ABSTRACT
))
4841 expect("identifier");
4844 post_type(post
, ad
, storage
, 0);
4845 parse_attribute(ad
);
4850 /* indirection with full error checking and bound check */
4851 ST_FUNC
void indir(void)
4853 if ((vtop
->type
.t
& VT_BTYPE
) != VT_PTR
) {
4854 if ((vtop
->type
.t
& VT_BTYPE
) == VT_FUNC
)
4858 if (vtop
->r
& VT_LVAL
)
4860 vtop
->type
= *pointed_type(&vtop
->type
);
4861 /* Arrays and functions are never lvalues */
4862 if (!(vtop
->type
.t
& (VT_ARRAY
| VT_VLA
))
4863 && (vtop
->type
.t
& VT_BTYPE
) != VT_FUNC
) {
4865 /* if bound checking, the referenced pointer must be checked */
4866 #ifdef CONFIG_TCC_BCHECK
4867 if (tcc_state
->do_bounds_check
)
4868 vtop
->r
|= VT_MUSTBOUND
;
4873 /* pass a parameter to a function and do type checking and casting */
4874 static void gfunc_param_typed(Sym
*func
, Sym
*arg
)
4879 func_type
= func
->f
.func_type
;
4880 if (func_type
== FUNC_OLD
||
4881 (func_type
== FUNC_ELLIPSIS
&& arg
== NULL
)) {
4882 /* default casting : only need to convert float to double */
4883 if ((vtop
->type
.t
& VT_BTYPE
) == VT_FLOAT
) {
4884 gen_cast_s(VT_DOUBLE
);
4885 } else if (vtop
->type
.t
& VT_BITFIELD
) {
4886 type
.t
= vtop
->type
.t
& (VT_BTYPE
| VT_UNSIGNED
);
4887 type
.ref
= vtop
->type
.ref
;
4889 } else if (vtop
->r
& VT_MUSTCAST
) {
4890 force_charshort_cast();
4892 } else if (arg
== NULL
) {
4893 tcc_error("too many arguments to function");
4896 type
.t
&= ~VT_CONSTANT
; /* need to do that to avoid false warning */
4897 gen_assign_cast(&type
);
4901 /* parse an expression and return its type without any side effect. */
4902 static void expr_type(CType
*type
, void (*expr_fn
)(void))
4911 /* parse an expression of the form '(type)' or '(expr)' and return its
4913 static void parse_expr_type(CType
*type
)
4919 if (parse_btype(type
, &ad
)) {
4920 type_decl(type
, &ad
, &n
, TYPE_ABSTRACT
);
4922 expr_type(type
, gexpr
);
4927 static void parse_type(CType
*type
)
4932 if (!parse_btype(type
, &ad
)) {
4935 type_decl(type
, &ad
, &n
, TYPE_ABSTRACT
);
4938 static void parse_builtin_params(int nc
, const char *args
)
4945 while ((c
= *args
++)) {
4949 case 'e': expr_eq(); continue;
4950 case 't': parse_type(&t
); vpush(&t
); continue;
4951 default: tcc_error("internal error"); break;
4959 ST_FUNC
void unary(void)
4961 int n
, t
, align
, size
, r
, sizeof_caller
;
4966 /* generate line number info */
4967 if (tcc_state
->do_debug
)
4968 tcc_debug_line(tcc_state
);
4970 sizeof_caller
= in_sizeof
;
4973 /* XXX: GCC 2.95.3 does not generate a table although it should be
4981 #ifdef TCC_TARGET_PE
4982 t
= VT_SHORT
|VT_UNSIGNED
;
4990 vsetc(&type
, VT_CONST
, &tokc
);
4994 t
= VT_INT
| VT_UNSIGNED
;
5000 t
= VT_LLONG
| VT_UNSIGNED
;
5012 t
= (LONG_SIZE
== 8 ? VT_LLONG
: VT_INT
) | VT_LONG
;
5015 t
= (LONG_SIZE
== 8 ? VT_LLONG
: VT_INT
) | VT_LONG
| VT_UNSIGNED
;
5017 case TOK___FUNCTION__
:
5019 goto tok_identifier
;
5025 /* special function name identifier */
5026 len
= strlen(funcname
) + 1;
5027 /* generate char[len] type */
5032 vpush_ref(&type
, data_section
, data_section
->data_offset
, len
);
5033 if (!NODATA_WANTED
) {
5034 ptr
= section_ptr_add(data_section
, len
);
5035 memcpy(ptr
, funcname
, len
);
5041 #ifdef TCC_TARGET_PE
5042 t
= VT_SHORT
| VT_UNSIGNED
;
5048 /* string parsing */
5050 if (tcc_state
->char_is_unsigned
)
5051 t
= VT_BYTE
| VT_UNSIGNED
;
5053 if (tcc_state
->warn_write_strings
)
5058 memset(&ad
, 0, sizeof(AttributeDef
));
5059 decl_initializer_alloc(&type
, &ad
, VT_CONST
, 2, 0, 0);
5064 if (parse_btype(&type
, &ad
)) {
5065 type_decl(&type
, &ad
, &n
, TYPE_ABSTRACT
);
5067 /* check ISOC99 compound literal */
5069 /* data is allocated locally by default */
5074 /* all except arrays are lvalues */
5075 if (!(type
.t
& VT_ARRAY
))
5077 memset(&ad
, 0, sizeof(AttributeDef
));
5078 decl_initializer_alloc(&type
, &ad
, r
, 1, 0, 0);
5080 if (sizeof_caller
) {
5087 } else if (tok
== '{') {
5088 int saved_nocode_wanted
= nocode_wanted
;
5089 if (const_wanted
&& !(nocode_wanted
& unevalmask
))
5090 tcc_error("expected constant");
5091 /* save all registers */
5093 /* statement expression : we do not accept break/continue
5094 inside as GCC does. We do retain the nocode_wanted state,
5095 as statement expressions can't ever be entered from the
5096 outside, so any reactivation of code emission (from labels
5097 or loop heads) can be disabled again after the end of it. */
5099 nocode_wanted
= saved_nocode_wanted
;
5114 /* functions names must be treated as function pointers,
5115 except for unary '&' and sizeof. Since we consider that
5116 functions are not lvalues, we only have to handle it
5117 there and in function calls. */
5118 /* arrays can also be used although they are not lvalues */
5119 if ((vtop
->type
.t
& VT_BTYPE
) != VT_FUNC
&&
5120 !(vtop
->type
.t
& VT_ARRAY
))
5123 vtop
->sym
->a
.addrtaken
= 1;
5124 mk_pointer(&vtop
->type
);
5130 gen_test_zero(TOK_EQ
);
5141 if ((vtop
->type
.t
& VT_BTYPE
) == VT_PTR
)
5142 tcc_error("pointer not accepted for unary plus");
5143 /* In order to force cast, we add zero, except for floating point
5144 where we really need an noop (otherwise -0.0 will be transformed
5146 if (!is_float(vtop
->type
.t
)) {
5158 expr_type(&type
, unary
); /* Perform a in_sizeof = 0; */
5160 if (vtop
[1].r
& VT_SYM
)
5161 s
= vtop
[1].sym
; /* hack: accessing previous vtop */
5162 size
= type_size(&type
, &align
);
5163 if (s
&& s
->a
.aligned
)
5164 align
= 1 << (s
->a
.aligned
- 1);
5165 if (t
== TOK_SIZEOF
) {
5166 if (!(type
.t
& VT_VLA
)) {
5168 tcc_error("sizeof applied to an incomplete type");
5171 vla_runtime_type_size(&type
, &align
);
5176 vtop
->type
.t
|= VT_UNSIGNED
;
5179 case TOK_builtin_expect
:
5180 /* __builtin_expect is a no-op for now */
5181 parse_builtin_params(0, "ee");
5184 case TOK_builtin_types_compatible_p
:
5185 parse_builtin_params(0, "tt");
5186 vtop
[-1].type
.t
&= ~(VT_CONSTANT
| VT_VOLATILE
);
5187 vtop
[0].type
.t
&= ~(VT_CONSTANT
| VT_VOLATILE
);
5188 n
= is_compatible_types(&vtop
[-1].type
, &vtop
[0].type
);
5192 case TOK_builtin_choose_expr
:
5219 case TOK_builtin_constant_p
:
5220 parse_builtin_params(1, "e");
5221 n
= (vtop
->r
& (VT_VALMASK
| VT_LVAL
| VT_SYM
)) == VT_CONST
;
5225 case TOK_builtin_frame_address
:
5226 case TOK_builtin_return_address
:
5232 if (tok
!= TOK_CINT
) {
5233 tcc_error("%s only takes positive integers",
5234 tok1
== TOK_builtin_return_address
?
5235 "__builtin_return_address" :
5236 "__builtin_frame_address");
5238 level
= (uint32_t)tokc
.i
;
5243 vset(&type
, VT_LOCAL
, 0); /* local frame */
5245 mk_pointer(&vtop
->type
);
5246 indir(); /* -> parent frame */
5248 if (tok1
== TOK_builtin_return_address
) {
5249 // assume return address is just above frame pointer on stack
5252 mk_pointer(&vtop
->type
);
5257 #ifdef TCC_TARGET_RISCV64
5258 case TOK_builtin_va_start
:
5259 parse_builtin_params(0, "ee");
5260 r
= vtop
->r
& VT_VALMASK
;
5264 tcc_error("__builtin_va_start expects a local variable");
5269 #ifdef TCC_TARGET_X86_64
5270 #ifdef TCC_TARGET_PE
5271 case TOK_builtin_va_start
:
5272 parse_builtin_params(0, "ee");
5273 r
= vtop
->r
& VT_VALMASK
;
5277 tcc_error("__builtin_va_start expects a local variable");
5279 vtop
->type
= char_pointer_type
;
5284 case TOK_builtin_va_arg_types
:
5285 parse_builtin_params(0, "t");
5286 vpushi(classify_x86_64_va_arg(&vtop
->type
));
5293 #ifdef TCC_TARGET_ARM64
5294 case TOK___va_start
: {
5295 parse_builtin_params(0, "ee");
5299 vtop
->type
.t
= VT_VOID
;
5302 case TOK___va_arg
: {
5303 parse_builtin_params(0, "et");
5311 case TOK___arm64_clear_cache
: {
5312 parse_builtin_params(0, "ee");
5315 vtop
->type
.t
= VT_VOID
;
5319 /* pre operations */
5330 t
= vtop
->type
.t
& VT_BTYPE
;
5332 /* In IEEE negate(x) isn't subtract(0,x), but rather
5336 vtop
->c
.f
= -1.0 * 0.0;
5337 else if (t
== VT_DOUBLE
)
5338 vtop
->c
.d
= -1.0 * 0.0;
5340 vtop
->c
.ld
= -1.0 * 0.0;
5348 goto tok_identifier
;
5350 /* allow to take the address of a label */
5351 if (tok
< TOK_UIDENT
)
5352 expect("label identifier");
5353 s
= label_find(tok
);
5355 s
= label_push(&global_label_stack
, tok
, LABEL_FORWARD
);
5357 if (s
->r
== LABEL_DECLARED
)
5358 s
->r
= LABEL_FORWARD
;
5361 s
->type
.t
= VT_VOID
;
5362 mk_pointer(&s
->type
);
5363 s
->type
.t
|= VT_STATIC
;
5365 vpushsym(&s
->type
, s
);
5371 CType controlling_type
;
5372 int has_default
= 0;
5375 TokenString
*str
= NULL
;
5376 int saved_const_wanted
= const_wanted
;
5381 expr_type(&controlling_type
, expr_eq
);
5382 controlling_type
.t
&= ~(VT_CONSTANT
| VT_VOLATILE
| VT_ARRAY
);
5383 if ((controlling_type
.t
& VT_BTYPE
) == VT_FUNC
)
5384 mk_pointer(&controlling_type
);
5385 const_wanted
= saved_const_wanted
;
5389 if (tok
== TOK_DEFAULT
) {
5391 tcc_error("too many 'default'");
5397 AttributeDef ad_tmp
;
5402 parse_btype(&cur_type
, &ad_tmp
);
5405 type_decl(&cur_type
, &ad_tmp
, &itmp
, TYPE_ABSTRACT
);
5406 if (compare_types(&controlling_type
, &cur_type
, 0)) {
5408 tcc_error("type match twice");
5418 skip_or_save_block(&str
);
5420 skip_or_save_block(NULL
);
5427 type_to_str(buf
, sizeof buf
, &controlling_type
, NULL
);
5428 tcc_error("type '%s' does not match any association", buf
);
5430 begin_macro(str
, 1);
5439 // special qnan , snan and infinity values
5444 vtop
->type
.t
= VT_FLOAT
;
5449 goto special_math_val
;
5452 goto special_math_val
;
5459 expect("identifier");
5461 if (!s
|| IS_ASM_SYM(s
)) {
5462 const char *name
= get_tok_str(t
, NULL
);
5464 tcc_error("'%s' undeclared", name
);
5465 /* for simple function calls, we tolerate undeclared
5466 external reference to int() function */
5467 if (tcc_state
->warn_implicit_function_declaration
5468 #ifdef TCC_TARGET_PE
5469 /* people must be warned about using undeclared WINAPI functions
5470 (which usually start with uppercase letter) */
5471 || (name
[0] >= 'A' && name
[0] <= 'Z')
5474 tcc_warning("implicit declaration of function '%s'", name
);
5475 s
= external_global_sym(t
, &func_old_type
);
5479 /* A symbol that has a register is a local register variable,
5480 which starts out as VT_LOCAL value. */
5481 if ((r
& VT_VALMASK
) < VT_CONST
)
5482 r
= (r
& ~VT_VALMASK
) | VT_LOCAL
;
5484 vset(&s
->type
, r
, s
->c
);
5485 /* Point to s as backpointer (even without r&VT_SYM).
5486 Will be used by at least the x86 inline asm parser for
5492 } else if (r
== VT_CONST
&& IS_ENUM_VAL(s
->type
.t
)) {
5493 vtop
->c
.i
= s
->enum_val
;
5498 /* post operations */
5500 if (tok
== TOK_INC
|| tok
== TOK_DEC
) {
5503 } else if (tok
== '.' || tok
== TOK_ARROW
|| tok
== TOK_CDOUBLE
) {
5504 int qualifiers
, cumofs
= 0;
5506 if (tok
== TOK_ARROW
)
5508 qualifiers
= vtop
->type
.t
& (VT_CONSTANT
| VT_VOLATILE
);
5511 /* expect pointer on structure */
5512 if ((vtop
->type
.t
& VT_BTYPE
) != VT_STRUCT
)
5513 expect("struct or union");
5514 if (tok
== TOK_CDOUBLE
)
5515 expect("field name");
5517 if (tok
== TOK_CINT
|| tok
== TOK_CUINT
)
5518 expect("field name");
5519 s
= find_field(&vtop
->type
, tok
, &cumofs
);
5521 tcc_error("field not found: %s", get_tok_str(tok
& ~SYM_FIELD
, &tokc
));
5522 /* add field offset to pointer */
5523 vtop
->type
= char_pointer_type
; /* change type to 'char *' */
5524 vpushi(cumofs
+ s
->c
);
5526 /* change type to field type, and set to lvalue */
5527 vtop
->type
= s
->type
;
5528 vtop
->type
.t
|= qualifiers
;
5529 /* an array is never an lvalue */
5530 if (!(vtop
->type
.t
& VT_ARRAY
)) {
5532 #ifdef CONFIG_TCC_BCHECK
5533 /* if bound checking, the referenced pointer must be checked */
5534 if (tcc_state
->do_bounds_check
)
5535 vtop
->r
|= VT_MUSTBOUND
;
5539 } else if (tok
== '[') {
5545 } else if (tok
== '(') {
5548 int nb_args
, ret_nregs
, ret_align
, regsize
, variadic
;
5551 if ((vtop
->type
.t
& VT_BTYPE
) != VT_FUNC
) {
5552 /* pointer test (no array accepted) */
5553 if ((vtop
->type
.t
& (VT_BTYPE
| VT_ARRAY
)) == VT_PTR
) {
5554 vtop
->type
= *pointed_type(&vtop
->type
);
5555 if ((vtop
->type
.t
& VT_BTYPE
) != VT_FUNC
)
5559 expect("function pointer");
5562 vtop
->r
&= ~VT_LVAL
; /* no lvalue */
5564 /* get return type */
5567 sa
= s
->next
; /* first parameter */
5568 nb_args
= regsize
= 0;
5570 /* compute first implicit argument if a structure is returned */
5571 if ((s
->type
.t
& VT_BTYPE
) == VT_STRUCT
) {
5572 variadic
= (s
->f
.func_type
== FUNC_ELLIPSIS
);
5573 ret_nregs
= gfunc_sret(&s
->type
, variadic
, &ret
.type
,
5574 &ret_align
, ®size
);
5575 if (ret_nregs
<= 0) {
5576 /* get some space for the returned structure */
5577 size
= type_size(&s
->type
, &align
);
5578 #ifdef TCC_TARGET_ARM64
5579 /* On arm64, a small struct is return in registers.
5580 It is much easier to write it to memory if we know
5581 that we are allowed to write some extra bytes, so
5582 round the allocated space up to a power of 2: */
5584 while (size
& (size
- 1))
5585 size
= (size
| (size
- 1)) + 1;
5587 loc
= (loc
- size
) & -align
;
5589 ret
.r
= VT_LOCAL
| VT_LVAL
;
5590 /* pass it as 'int' to avoid structure arg passing
5592 vseti(VT_LOCAL
, loc
);
5604 if (ret_nregs
> 0) {
5605 /* return in register */
5607 PUT_R_RET(&ret
, ret
.type
.t
);
5612 gfunc_param_typed(s
, sa
);
5622 tcc_error("too few arguments to function");
5624 gfunc_call(nb_args
);
5626 if (ret_nregs
< 0) {
5627 vsetc(&ret
.type
, ret
.r
, &ret
.c
);
5628 #ifdef TCC_TARGET_RISCV64
5629 arch_transfer_ret_regs(1);
5633 for (r
= ret
.r
+ ret_nregs
+ !ret_nregs
; r
-- > ret
.r
;) {
5634 vsetc(&ret
.type
, r
, &ret
.c
);
5635 vtop
->r2
= ret
.r2
; /* Loop only happens when r2 is VT_CONST */
5638 /* handle packed struct return */
5639 if (((s
->type
.t
& VT_BTYPE
) == VT_STRUCT
) && ret_nregs
) {
5642 size
= type_size(&s
->type
, &align
);
5643 /* We're writing whole regs often, make sure there's enough
5644 space. Assume register size is power of 2. */
5645 if (regsize
> align
)
5647 loc
= (loc
- size
) & -align
;
5651 vset(&ret
.type
, VT_LOCAL
| VT_LVAL
, addr
+ offset
);
5655 if (--ret_nregs
== 0)
5659 vset(&s
->type
, VT_LOCAL
| VT_LVAL
, addr
);
5662 /* Promote char/short return values. This is matters only
5663 for calling function that were not compiled by TCC and
5664 only on some architectures. For those where it doesn't
5665 matter we expect things to be already promoted to int,
5667 t
= s
->type
.t
& VT_BTYPE
;
5668 if (t
== VT_BYTE
|| t
== VT_SHORT
|| t
== VT_BOOL
) {
5670 vtop
->r
|= BFVAL(VT_MUSTCAST
, 1);
5672 vtop
->type
.t
= VT_INT
;
5676 if (s
->f
.func_noreturn
)
5684 ST_FUNC
void expr_prod(void)
5689 while (tok
== '*' || tok
== '/' || tok
== '%') {
5697 ST_FUNC
void expr_sum(void)
5702 while (tok
== '+' || tok
== '-') {
5710 static void expr_shift(void)
5715 while (tok
== TOK_SHL
|| tok
== TOK_SAR
) {
5723 static void expr_cmp(void)
5728 while ((tok
>= TOK_ULE
&& tok
<= TOK_GT
) ||
5729 tok
== TOK_ULT
|| tok
== TOK_UGE
) {
5737 static void expr_cmpeq(void)
5742 while (tok
== TOK_EQ
|| tok
== TOK_NE
) {
5750 static void expr_and(void)
5753 while (tok
== '&') {
5760 static void expr_xor(void)
5763 while (tok
== '^') {
5770 static void expr_or(void)
5773 while (tok
== '|') {
5780 static int condition_3way(void);
5782 static void expr_landor(void(*e_fn
)(void), int e_op
, int i
)
5784 int t
= 0, cc
= 1, f
= 0, c
;
5786 c
= f
? i
: condition_3way();
5788 save_regs(1), cc
= 0;
5789 } else if (c
!= i
) {
5790 nocode_wanted
++, f
= 1;
5812 static void expr_land(void)
5815 if (tok
== TOK_LAND
)
5816 expr_landor(expr_or
, TOK_LAND
, 1);
5819 static void expr_lor(void)
5823 expr_landor(expr_land
, TOK_LOR
, 0);
5826 /* Assuming vtop is a value used in a conditional context
5827 (i.e. compared with zero) return 0 if it's false, 1 if
5828 true and -1 if it can't be statically determined. */
5829 static int condition_3way(void)
5832 if ((vtop
->r
& (VT_VALMASK
| VT_LVAL
)) == VT_CONST
&&
5833 (!(vtop
->r
& VT_SYM
) || !vtop
->sym
->a
.weak
)) {
5835 gen_cast_s(VT_BOOL
);
5842 static int is_cond_bool(SValue
*sv
)
5844 if ((sv
->r
& (VT_VALMASK
| VT_LVAL
| VT_SYM
)) == VT_CONST
5845 && (sv
->type
.t
& VT_BTYPE
) == VT_INT
)
5846 return (unsigned)sv
->c
.i
< 2;
5847 if (sv
->r
== VT_CMP
)
5852 static void expr_cond(void)
5854 int tt
, u
, r1
, r2
, rc
, t1
, t2
, bt1
, bt2
, islv
, c
, g
;
5856 CType type
, type1
, type2
;
5862 c
= condition_3way();
5863 g
= (tok
== ':' && gnu_ext
);
5873 /* needed to avoid having different registers saved in
5880 ncw_prev
= nocode_wanted
;
5887 if (c
< 0 && vtop
->r
== VT_CMP
) {
5893 if ((vtop
->type
.t
& VT_BTYPE
) == VT_FUNC
)
5894 mk_pointer(&vtop
->type
);
5896 sv
= *vtop
; /* save value to handle it later */
5897 vtop
--; /* no vpop so that FP stack is not flushed */
5907 nocode_wanted
= ncw_prev
;
5913 if (c
< 0 && is_cond_bool(vtop
) && is_cond_bool(&sv
)) {
5914 if (sv
.r
== VT_CMP
) {
5925 nocode_wanted
= ncw_prev
;
5926 // tcc_warning("two conditions expr_cond");
5930 if ((vtop
->type
.t
& VT_BTYPE
) == VT_FUNC
)
5931 mk_pointer(&vtop
->type
);
5934 bt1
= t1
& VT_BTYPE
;
5936 bt2
= t2
& VT_BTYPE
;
5939 /* cast operands to correct type according to ISOC rules */
5940 if (bt1
== VT_VOID
|| bt2
== VT_VOID
) {
5941 type
.t
= VT_VOID
; /* NOTE: as an extension, we accept void on only one side */
5942 } else if (is_float(bt1
) || is_float(bt2
)) {
5943 if (bt1
== VT_LDOUBLE
|| bt2
== VT_LDOUBLE
) {
5944 type
.t
= VT_LDOUBLE
;
5946 } else if (bt1
== VT_DOUBLE
|| bt2
== VT_DOUBLE
) {
5951 } else if (bt1
== VT_LLONG
|| bt2
== VT_LLONG
) {
5952 /* cast to biggest op */
5953 type
.t
= VT_LLONG
| VT_LONG
;
5954 if (bt1
== VT_LLONG
)
5956 if (bt2
== VT_LLONG
)
5958 /* convert to unsigned if it does not fit in a long long */
5959 if ((t1
& (VT_BTYPE
| VT_UNSIGNED
| VT_BITFIELD
)) == (VT_LLONG
| VT_UNSIGNED
) ||
5960 (t2
& (VT_BTYPE
| VT_UNSIGNED
| VT_BITFIELD
)) == (VT_LLONG
| VT_UNSIGNED
))
5961 type
.t
|= VT_UNSIGNED
;
5962 } else if (bt1
== VT_PTR
|| bt2
== VT_PTR
) {
5963 /* http://port70.net/~nsz/c/c99/n1256.html#6.5.15p6 */
5964 /* If one is a null ptr constant the result type
5966 if (is_null_pointer (vtop
)) type
= type1
;
5967 else if (is_null_pointer (&sv
)) type
= type2
;
5968 else if (bt1
!= bt2
)
5969 tcc_error("incompatible types in conditional expressions");
5971 CType
*pt1
= pointed_type(&type1
);
5972 CType
*pt2
= pointed_type(&type2
);
5973 int pbt1
= pt1
->t
& VT_BTYPE
;
5974 int pbt2
= pt2
->t
& VT_BTYPE
;
5975 int newquals
, copied
= 0;
5976 /* pointers to void get preferred, otherwise the
5977 pointed to types minus qualifs should be compatible */
5978 type
= (pbt1
== VT_VOID
) ? type1
: type2
;
5979 if (pbt1
!= VT_VOID
&& pbt2
!= VT_VOID
) {
5980 if(!compare_types(pt1
, pt2
, 1/*unqualif*/))
5981 tcc_warning("pointer type mismatch in conditional expression\n");
5983 /* combine qualifs */
5984 newquals
= ((pt1
->t
| pt2
->t
) & (VT_CONSTANT
| VT_VOLATILE
));
5985 if ((~pointed_type(&type
)->t
& (VT_CONSTANT
| VT_VOLATILE
))
5988 /* copy the pointer target symbol */
5989 type
.ref
= sym_push(SYM_FIELD
, &type
.ref
->type
,
5992 pointed_type(&type
)->t
|= newquals
;
5994 /* pointers to incomplete arrays get converted to
5995 pointers to completed ones if possible */
5996 if (pt1
->t
& VT_ARRAY
5997 && pt2
->t
& VT_ARRAY
5998 && pointed_type(&type
)->ref
->c
< 0
5999 && (pt1
->ref
->c
> 0 || pt2
->ref
->c
> 0))
6002 type
.ref
= sym_push(SYM_FIELD
, &type
.ref
->type
,
6004 pointed_type(&type
)->ref
=
6005 sym_push(SYM_FIELD
, &pointed_type(&type
)->ref
->type
,
6006 0, pointed_type(&type
)->ref
->c
);
6007 pointed_type(&type
)->ref
->c
=
6008 0 < pt1
->ref
->c
? pt1
->ref
->c
: pt2
->ref
->c
;
6011 } else if (bt1
== VT_STRUCT
|| bt2
== VT_STRUCT
) {
6012 /* XXX: test structure compatibility */
6013 type
= bt1
== VT_STRUCT
? type1
: type2
;
6015 /* integer operations */
6016 type
.t
= VT_INT
| (VT_LONG
& (t1
| t2
));
6017 /* convert to unsigned if it does not fit in an integer */
6018 if ((t1
& (VT_BTYPE
| VT_UNSIGNED
| VT_BITFIELD
)) == (VT_INT
| VT_UNSIGNED
) ||
6019 (t2
& (VT_BTYPE
| VT_UNSIGNED
| VT_BITFIELD
)) == (VT_INT
| VT_UNSIGNED
))
6020 type
.t
|= VT_UNSIGNED
;
6022 /* keep structs lvalue by transforming `(expr ? a : b)` to `*(expr ? &a : &b)` so
6023 that `(expr ? a : b).mem` does not error with "lvalue expected" */
6024 islv
= (vtop
->r
& VT_LVAL
) && (sv
.r
& VT_LVAL
) && VT_STRUCT
== (type
.t
& VT_BTYPE
);
6026 /* now we convert second operand */
6030 mk_pointer(&vtop
->type
);
6032 } else if (VT_STRUCT
== (vtop
->type
.t
& VT_BTYPE
))
6036 rc
= RC_TYPE(type
.t
);
6037 /* for long longs, we use fixed registers to avoid having
6038 to handle a complicated move */
6039 if (USING_TWO_WORDS(type
.t
))
6040 rc
= RC_RET(type
.t
);
6048 nocode_wanted
= ncw_prev
;
6050 /* this is horrible, but we must also convert first
6056 mk_pointer(&vtop
->type
);
6058 } else if (VT_STRUCT
== (vtop
->type
.t
& VT_BTYPE
))
6064 move_reg(r2
, r1
, islv
? VT_PTR
: type
.t
);
6075 static void expr_eq(void)
6081 (tok
>= TOK_A_MOD
&& tok
<= TOK_A_DIV
) ||
6082 tok
== TOK_A_XOR
|| tok
== TOK_A_OR
||
6083 tok
== TOK_A_SHL
|| tok
== TOK_A_SAR
) {
6098 ST_FUNC
void gexpr(void)
6109 /* parse a constant expression and return value in vtop. */
6110 static void expr_const1(void)
6113 nocode_wanted
+= unevalmask
+ 1;
6115 nocode_wanted
-= unevalmask
+ 1;
6119 /* parse an integer constant and return its value. */
6120 static inline int64_t expr_const64(void)
6124 if ((vtop
->r
& (VT_VALMASK
| VT_LVAL
| VT_SYM
)) != VT_CONST
)
6125 expect("constant expression");
6131 /* parse an integer constant and return its value.
6132 Complain if it doesn't fit 32bit (signed or unsigned). */
6133 ST_FUNC
int expr_const(void)
6136 int64_t wc
= expr_const64();
6138 if (c
!= wc
&& (unsigned)c
!= wc
)
6139 tcc_error("constant exceeds 32 bit");
6143 /* ------------------------------------------------------------------------- */
6144 /* return from function */
6146 #ifndef TCC_TARGET_ARM64
6147 static void gfunc_return(CType
*func_type
)
6149 if ((func_type
->t
& VT_BTYPE
) == VT_STRUCT
) {
6150 CType type
, ret_type
;
6151 int ret_align
, ret_nregs
, regsize
;
6152 ret_nregs
= gfunc_sret(func_type
, func_var
, &ret_type
,
6153 &ret_align
, ®size
);
6154 if (ret_nregs
< 0) {
6155 #ifdef TCC_TARGET_RISCV64
6156 arch_transfer_ret_regs(0);
6158 } else if (0 == ret_nregs
) {
6159 /* if returning structure, must copy it to implicit
6160 first pointer arg location */
6163 vset(&type
, VT_LOCAL
| VT_LVAL
, func_vc
);
6166 /* copy structure value to pointer */
6169 /* returning structure packed into registers */
6170 int size
, addr
, align
, rc
;
6171 size
= type_size(func_type
,&align
);
6172 if ((vtop
->r
!= (VT_LOCAL
| VT_LVAL
) ||
6173 (vtop
->c
.i
& (ret_align
-1)))
6174 && (align
& (ret_align
-1))) {
6175 loc
= (loc
- size
) & -ret_align
;
6178 vset(&type
, VT_LOCAL
| VT_LVAL
, addr
);
6182 vset(&ret_type
, VT_LOCAL
| VT_LVAL
, addr
);
6184 vtop
->type
= ret_type
;
6185 rc
= RC_RET(ret_type
.t
);
6193 if (--ret_nregs
== 0)
6195 /* We assume that when a structure is returned in multiple
6196 registers, their classes are consecutive values of the
6199 vtop
->c
.i
+= regsize
;
6204 gv(RC_RET(func_type
->t
));
6206 vtop
--; /* NOT vpop() because on x86 it would flush the fp stack */
6210 static void check_func_return(void)
6212 if ((func_vt
.t
& VT_BTYPE
) == VT_VOID
)
6214 if (!strcmp (funcname
, "main")
6215 && (func_vt
.t
& VT_BTYPE
) == VT_INT
) {
6216 /* main returns 0 by default */
6218 gen_assign_cast(&func_vt
);
6219 gfunc_return(&func_vt
);
6221 tcc_warning("function might return no value: '%s'", funcname
);
6225 /* ------------------------------------------------------------------------- */
6228 static int case_cmp(const void *pa
, const void *pb
)
6230 int64_t a
= (*(struct case_t
**) pa
)->v1
;
6231 int64_t b
= (*(struct case_t
**) pb
)->v1
;
6232 return a
< b
? -1 : a
> b
;
6235 static void gtst_addr(int t
, int a
)
6237 gsym_addr(gvtst(0, t
), a
);
6240 static void gcase(struct case_t
**base
, int len
, int *bsym
)
6244 int ll
= (vtop
->type
.t
& VT_BTYPE
) == VT_LLONG
;
6261 gtst_addr(0, p
->sym
); /* v1 <= x <= v2 */
6263 gcase(base
, len
/2, bsym
);
6267 base
+= e
; len
-= e
;
6277 if (p
->v1
== p
->v2
) {
6279 gtst_addr(0, p
->sym
);
6289 gtst_addr(0, p
->sym
);
6293 *bsym
= gjmp(*bsym
);
6296 /* ------------------------------------------------------------------------- */
6297 /* __attribute__((cleanup(fn))) */
6299 static void try_call_scope_cleanup(Sym
*stop
)
6301 Sym
*cls
= cur_scope
->cl
.s
;
6303 for (; cls
!= stop
; cls
= cls
->ncl
) {
6304 Sym
*fs
= cls
->next
;
6305 Sym
*vs
= cls
->prev_tok
;
6307 vpushsym(&fs
->type
, fs
);
6308 vset(&vs
->type
, vs
->r
, vs
->c
);
6310 mk_pointer(&vtop
->type
);
6316 static void try_call_cleanup_goto(Sym
*cleanupstate
)
6321 if (!cur_scope
->cl
.s
)
6324 /* search NCA of both cleanup chains given parents and initial depth */
6325 ocd
= cleanupstate
? cleanupstate
->v
& ~SYM_FIELD
: 0;
6326 for (ccd
= cur_scope
->cl
.n
, oc
= cleanupstate
; ocd
> ccd
; --ocd
, oc
= oc
->ncl
)
6328 for (cc
= cur_scope
->cl
.s
; ccd
> ocd
; --ccd
, cc
= cc
->ncl
)
6330 for (; cc
!= oc
; cc
= cc
->ncl
, oc
= oc
->ncl
, --ccd
)
6333 try_call_scope_cleanup(cc
);
6336 /* call 'func' for each __attribute__((cleanup(func))) */
6337 static void block_cleanup(struct scope
*o
)
6341 for (pg
= &pending_gotos
; (g
= *pg
) && g
->c
> o
->cl
.n
;) {
6342 if (g
->prev_tok
->r
& LABEL_FORWARD
) {
6347 try_call_scope_cleanup(o
->cl
.s
);
6348 pcl
->jnext
= gjmp(0);
6350 goto remove_pending
;
6360 try_call_scope_cleanup(o
->cl
.s
);
6363 /* ------------------------------------------------------------------------- */
6366 static void vla_restore(int loc
)
6369 gen_vla_sp_restore(loc
);
6372 static void vla_leave(struct scope
*o
)
6374 if (o
->vla
.num
< cur_scope
->vla
.num
)
6375 vla_restore(o
->vla
.loc
);
6378 /* ------------------------------------------------------------------------- */
6381 void new_scope(struct scope
*o
)
6383 /* copy and link previous scope */
6385 o
->prev
= cur_scope
;
6388 /* record local declaration stack position */
6389 o
->lstk
= local_stack
;
6390 o
->llstk
= local_label_stack
;
6395 void prev_scope(struct scope
*o
, int is_expr
)
6399 if (o
->cl
.s
!= o
->prev
->cl
.s
)
6400 block_cleanup(o
->prev
);
6402 /* pop locally defined labels */
6403 label_pop(&local_label_stack
, o
->llstk
, is_expr
);
6405 /* In the is_expr case (a statement expression is finished here),
6406 vtop might refer to symbols on the local_stack. Either via the
6407 type or via vtop->sym. We can't pop those nor any that in turn
6408 might be referred to. To make it easier we don't roll back
6409 any symbols in that case; some upper level call to block() will
6410 do that. We do have to remove such symbols from the lookup
6411 tables, though. sym_pop will do that. */
6413 /* pop locally defined symbols */
6414 pop_local_syms(&local_stack
, o
->lstk
, is_expr
, 0);
6416 cur_scope
= o
->prev
;
6420 /* leave a scope via break/continue(/goto) */
6421 void leave_scope(struct scope
*o
)
6425 try_call_scope_cleanup(o
->cl
.s
);
6429 /* ------------------------------------------------------------------------- */
6430 /* call block from 'for do while' loops */
6432 static void lblock(int *bsym
, int *csym
)
6434 struct scope
*lo
= loop_scope
, *co
= cur_scope
;
6435 int *b
= co
->bsym
, *c
= co
->csym
;
6449 static void block(int is_expr
)
6451 int a
, b
, c
, d
, e
, t
;
6456 /* default return value is (void) */
6458 vtop
->type
.t
= VT_VOID
;
6470 if (tok
== TOK_ELSE
) {
6475 gsym(d
); /* patch else jmp */
6480 } else if (t
== TOK_WHILE
) {
6492 } else if (t
== '{') {
6495 /* handle local labels declarations */
6496 while (tok
== TOK_LABEL
) {
6499 if (tok
< TOK_UIDENT
)
6500 expect("label identifier");
6501 label_push(&local_label_stack
, tok
, LABEL_DECLARED
);
6503 } while (tok
== ',');
6507 while (tok
!= '}') {
6516 prev_scope(&o
, is_expr
);
6519 else if (!nocode_wanted
)
6520 check_func_return();
6522 } else if (t
== TOK_RETURN
) {
6523 b
= (func_vt
.t
& VT_BTYPE
) != VT_VOID
;
6527 gen_assign_cast(&func_vt
);
6529 if (vtop
->type
.t
!= VT_VOID
)
6530 tcc_warning("void function returns a value");
6534 tcc_warning("'return' with no value");
6537 leave_scope(root_scope
);
6539 gfunc_return(&func_vt
);
6541 /* jump unless last stmt in top-level block */
6542 if (tok
!= '}' || local_scope
!= 1)
6546 } else if (t
== TOK_BREAK
) {
6548 if (!cur_scope
->bsym
)
6549 tcc_error("cannot break");
6550 if (cur_switch
&& cur_scope
->bsym
== cur_switch
->bsym
)
6551 leave_scope(cur_switch
->scope
);
6553 leave_scope(loop_scope
);
6554 *cur_scope
->bsym
= gjmp(*cur_scope
->bsym
);
6557 } else if (t
== TOK_CONTINUE
) {
6559 if (!cur_scope
->csym
)
6560 tcc_error("cannot continue");
6561 leave_scope(loop_scope
);
6562 *cur_scope
->csym
= gjmp(*cur_scope
->csym
);
6565 } else if (t
== TOK_FOR
) {
6570 /* c99 for-loop init decl? */
6571 if (!decl0(VT_LOCAL
, 1, NULL
)) {
6572 /* no, regular for-loop init expr */
6600 } else if (t
== TOK_DO
) {
6614 } else if (t
== TOK_SWITCH
) {
6615 struct switch_t
*sw
;
6617 sw
= tcc_mallocz(sizeof *sw
);
6619 sw
->scope
= cur_scope
;
6620 sw
->prev
= cur_switch
;
6626 sw
->sv
= *vtop
--; /* save switch value */
6629 b
= gjmp(0); /* jump to first case */
6631 a
= gjmp(a
); /* add implicit break */
6635 qsort(sw
->p
, sw
->n
, sizeof(void*), case_cmp
);
6636 for (b
= 1; b
< sw
->n
; b
++)
6637 if (sw
->p
[b
- 1]->v2
>= sw
->p
[b
]->v1
)
6638 tcc_error("duplicate case value");
6640 /* Our switch table sorting is signed, so the compared
6641 value needs to be as well when it's 64bit. */
6643 if ((vtop
->type
.t
& VT_BTYPE
) == VT_LLONG
)
6644 vtop
->type
.t
&= ~VT_UNSIGNED
;
6646 d
= 0, gcase(sw
->p
, sw
->n
, &d
);
6649 gsym_addr(d
, sw
->def_sym
);
6655 dynarray_reset(&sw
->p
, &sw
->n
);
6656 cur_switch
= sw
->prev
;
6659 } else if (t
== TOK_CASE
) {
6660 struct case_t
*cr
= tcc_malloc(sizeof(struct case_t
));
6663 cr
->v1
= cr
->v2
= expr_const64();
6664 if (gnu_ext
&& tok
== TOK_DOTS
) {
6666 cr
->v2
= expr_const64();
6667 if (cr
->v2
< cr
->v1
)
6668 tcc_warning("empty case range");
6671 dynarray_add(&cur_switch
->p
, &cur_switch
->n
, cr
);
6674 goto block_after_label
;
6676 } else if (t
== TOK_DEFAULT
) {
6679 if (cur_switch
->def_sym
)
6680 tcc_error("too many 'default'");
6681 cur_switch
->def_sym
= gind();
6684 goto block_after_label
;
6686 } else if (t
== TOK_GOTO
) {
6687 vla_restore(root_scope
->vla
.loc
);
6688 if (tok
== '*' && gnu_ext
) {
6692 if ((vtop
->type
.t
& VT_BTYPE
) != VT_PTR
)
6696 } else if (tok
>= TOK_UIDENT
) {
6697 s
= label_find(tok
);
6698 /* put forward definition if needed */
6700 s
= label_push(&global_label_stack
, tok
, LABEL_FORWARD
);
6701 else if (s
->r
== LABEL_DECLARED
)
6702 s
->r
= LABEL_FORWARD
;
6704 if (s
->r
& LABEL_FORWARD
) {
6705 /* start new goto chain for cleanups, linked via label->next */
6706 if (cur_scope
->cl
.s
&& !nocode_wanted
) {
6707 sym_push2(&pending_gotos
, SYM_FIELD
, 0, cur_scope
->cl
.n
);
6708 pending_gotos
->prev_tok
= s
;
6709 s
= sym_push2(&s
->next
, SYM_FIELD
, 0, 0);
6710 pending_gotos
->next
= s
;
6712 s
->jnext
= gjmp(s
->jnext
);
6714 try_call_cleanup_goto(s
->cleanupstate
);
6715 gjmp_addr(s
->jnext
);
6720 expect("label identifier");
6724 } else if (t
== TOK_ASM1
|| t
== TOK_ASM2
|| t
== TOK_ASM3
) {
6728 if (tok
== ':' && t
>= TOK_UIDENT
) {
6733 if (s
->r
== LABEL_DEFINED
)
6734 tcc_error("duplicate label '%s'", get_tok_str(s
->v
, NULL
));
6735 s
->r
= LABEL_DEFINED
;
6737 Sym
*pcl
; /* pending cleanup goto */
6738 for (pcl
= s
->next
; pcl
; pcl
= pcl
->prev
)
6740 sym_pop(&s
->next
, NULL
, 0);
6744 s
= label_push(&global_label_stack
, t
, LABEL_DEFINED
);
6747 s
->cleanupstate
= cur_scope
->cl
.s
;
6750 vla_restore(cur_scope
->vla
.loc
);
6751 /* we accept this, but it is a mistake */
6753 tcc_warning("deprecated use of label at end of compound statement");
6759 /* expression case */
6775 /* This skips over a stream of tokens containing balanced {} and ()
6776 pairs, stopping at outer ',' ';' and '}' (or matching '}' if we started
6777 with a '{'). If STR then allocates and stores the skipped tokens
6778 in *STR. This doesn't check if () and {} are nested correctly,
6779 i.e. "({)}" is accepted. */
6780 static void skip_or_save_block(TokenString
**str
)
6782 int braces
= tok
== '{';
6785 *str
= tok_str_alloc();
6787 while ((level
> 0 || (tok
!= '}' && tok
!= ',' && tok
!= ';' && tok
!= ')'))) {
6789 if (tok
== TOK_EOF
) {
6790 if (str
|| level
> 0)
6791 tcc_error("unexpected end of file");
6796 tok_str_add_tok(*str
);
6799 if (t
== '{' || t
== '(') {
6801 } else if (t
== '}' || t
== ')') {
6803 if (level
== 0 && braces
&& t
== '}')
6808 tok_str_add(*str
, -1);
6809 tok_str_add(*str
, 0);
6813 #define EXPR_CONST 1
6816 static void parse_init_elem(int expr_type
)
6818 int saved_global_expr
;
6821 /* compound literals must be allocated globally in this case */
6822 saved_global_expr
= global_expr
;
6825 global_expr
= saved_global_expr
;
6826 /* NOTE: symbols are accepted, as well as lvalue for anon symbols
6827 (compound literals). */
6828 if (((vtop
->r
& (VT_VALMASK
| VT_LVAL
)) != VT_CONST
6829 && ((vtop
->r
& (VT_SYM
|VT_LVAL
)) != (VT_SYM
|VT_LVAL
)
6830 || vtop
->sym
->v
< SYM_FIRST_ANOM
))
6831 #ifdef TCC_TARGET_PE
6832 || ((vtop
->r
& VT_SYM
) && vtop
->sym
->a
.dllimport
)
6835 tcc_error("initializer element is not constant");
6843 /* put zeros for variable based init */
6844 static void init_putz(Section
*sec
, unsigned long c
, int size
)
6847 /* nothing to do because globals are already set to zero */
6849 vpush_global_sym(&func_old_type
, TOK_memset
);
6851 #ifdef TCC_TARGET_ARM
6863 #define DIF_SIZE_ONLY 2
6864 #define DIF_HAVE_ELEM 4
6866 /* t is the array or struct type. c is the array or struct
6867 address. cur_field is the pointer to the current
6868 field, for arrays the 'c' member contains the current start
6869 index. 'flags' is as in decl_initializer.
6870 'al' contains the already initialized length of the
6871 current container (starting at c). This returns the new length of that. */
6872 static int decl_designator(CType
*type
, Section
*sec
, unsigned long c
,
6873 Sym
**cur_field
, int flags
, int al
)
6876 int index
, index_last
, align
, l
, nb_elems
, elem_size
;
6877 unsigned long corig
= c
;
6882 if (flags
& DIF_HAVE_ELEM
)
6885 if (gnu_ext
&& tok
>= TOK_UIDENT
) {
6892 /* NOTE: we only support ranges for last designator */
6893 while (nb_elems
== 1 && (tok
== '[' || tok
== '.')) {
6895 if (!(type
->t
& VT_ARRAY
))
6896 expect("array type");
6898 index
= index_last
= expr_const();
6899 if (tok
== TOK_DOTS
&& gnu_ext
) {
6901 index_last
= expr_const();
6905 if (index
< 0 || (s
->c
>= 0 && index_last
>= s
->c
) ||
6907 tcc_error("invalid index");
6909 (*cur_field
)->c
= index_last
;
6910 type
= pointed_type(type
);
6911 elem_size
= type_size(type
, &align
);
6912 c
+= index
* elem_size
;
6913 nb_elems
= index_last
- index
+ 1;
6920 if ((type
->t
& VT_BTYPE
) != VT_STRUCT
)
6921 expect("struct/union type");
6923 f
= find_field(type
, l
, &cumofs
);
6936 } else if (!gnu_ext
) {
6941 if (type
->t
& VT_ARRAY
) {
6942 index
= (*cur_field
)->c
;
6943 if (type
->ref
->c
>= 0 && index
>= type
->ref
->c
)
6944 tcc_error("index too large");
6945 type
= pointed_type(type
);
6946 c
+= index
* type_size(type
, &align
);
6949 while (f
&& (f
->v
& SYM_FIRST_ANOM
) && (f
->type
.t
& VT_BITFIELD
))
6950 *cur_field
= f
= f
->next
;
6952 tcc_error("too many field init");
6957 /* must put zero in holes (note that doing it that way
6958 ensures that it even works with designators) */
6959 if (!(flags
& DIF_SIZE_ONLY
) && c
- corig
> al
)
6960 init_putz(sec
, corig
+ al
, c
- corig
- al
);
6961 decl_initializer(type
, sec
, c
, flags
& ~DIF_FIRST
);
6963 /* XXX: make it more general */
6964 if (!(flags
& DIF_SIZE_ONLY
) && nb_elems
> 1) {
6965 unsigned long c_end
;
6970 vset(type
, VT_LOCAL
|VT_LVAL
, c
);
6971 for (i
= 1; i
< nb_elems
; i
++) {
6972 vset(type
, VT_LOCAL
|VT_LVAL
, c
+ elem_size
* i
);
6977 } else if (!NODATA_WANTED
) {
6978 c_end
= c
+ nb_elems
* elem_size
;
6979 if (c_end
> sec
->data_allocated
)
6980 section_realloc(sec
, c_end
);
6981 src
= sec
->data
+ c
;
6983 for(i
= 1; i
< nb_elems
; i
++) {
6985 memcpy(dst
, src
, elem_size
);
6989 c
+= nb_elems
* type_size(type
, &align
);
6995 /* store a value or an expression directly in global data or in local array */
6996 static void init_putv(CType
*type
, Section
*sec
, unsigned long c
)
7003 dtype
.t
&= ~VT_CONSTANT
; /* need to do that to avoid false warning */
7007 /* XXX: not portable */
7008 /* XXX: generate error if incorrect relocation */
7009 gen_assign_cast(&dtype
);
7010 bt
= type
->t
& VT_BTYPE
;
7012 if ((vtop
->r
& VT_SYM
)
7015 && (bt
!= (PTR_SIZE
== 8 ? VT_LLONG
: VT_INT
)
7016 || (type
->t
& VT_BITFIELD
))
7017 && !((vtop
->r
& VT_CONST
) && vtop
->sym
->v
>= SYM_FIRST_ANOM
)
7019 tcc_error("initializer element is not computable at load time");
7021 if (NODATA_WANTED
) {
7026 size
= type_size(type
, &align
);
7027 section_reserve(sec
, c
+ size
);
7028 ptr
= sec
->data
+ c
;
7030 /* XXX: make code faster ? */
7031 if ((vtop
->r
& (VT_SYM
|VT_CONST
)) == (VT_SYM
|VT_CONST
) &&
7032 vtop
->sym
->v
>= SYM_FIRST_ANOM
&&
7033 /* XXX This rejects compound literals like
7034 '(void *){ptr}'. The problem is that '&sym' is
7035 represented the same way, which would be ruled out
7036 by the SYM_FIRST_ANOM check above, but also '"string"'
7037 in 'char *p = "string"' is represented the same
7038 with the type being VT_PTR and the symbol being an
7039 anonymous one. That is, there's no difference in vtop
7040 between '(void *){x}' and '&(void *){x}'. Ignore
7041 pointer typed entities here. Hopefully no real code
7042 will every use compound literals with scalar type. */
7043 (vtop
->type
.t
& VT_BTYPE
) != VT_PTR
) {
7044 /* These come from compound literals, memcpy stuff over. */
7048 esym
= elfsym(vtop
->sym
);
7049 ssec
= tcc_state
->sections
[esym
->st_shndx
];
7050 memmove (ptr
, ssec
->data
+ esym
->st_value
, size
);
7052 /* We need to copy over all memory contents, and that
7053 includes relocations. Use the fact that relocs are
7054 created it order, so look from the end of relocs
7055 until we hit one before the copied region. */
7056 int num_relocs
= ssec
->reloc
->data_offset
/ sizeof(*rel
);
7057 rel
= (ElfW_Rel
*)(ssec
->reloc
->data
+ ssec
->reloc
->data_offset
);
7058 while (num_relocs
--) {
7060 if (rel
->r_offset
>= esym
->st_value
+ size
)
7062 if (rel
->r_offset
< esym
->st_value
)
7064 /* Note: if the same fields are initialized multiple
7065 times (possible with designators) then we possibly
7066 add multiple relocations for the same offset here.
7067 That would lead to wrong code, the last reloc needs
7068 to win. We clean this up later after the whole
7069 initializer is parsed. */
7070 put_elf_reloca(symtab_section
, sec
,
7071 c
+ rel
->r_offset
- esym
->st_value
,
7072 ELFW(R_TYPE
)(rel
->r_info
),
7073 ELFW(R_SYM
)(rel
->r_info
),
7083 if (type
->t
& VT_BITFIELD
) {
7084 int bit_pos
, bit_size
, bits
, n
;
7085 unsigned char *p
, v
, m
;
7086 bit_pos
= BIT_POS(vtop
->type
.t
);
7087 bit_size
= BIT_SIZE(vtop
->type
.t
);
7088 p
= (unsigned char*)ptr
+ (bit_pos
>> 3);
7089 bit_pos
&= 7, bits
= 0;
7094 v
= vtop
->c
.i
>> bits
<< bit_pos
;
7095 m
= ((1 << n
) - 1) << bit_pos
;
7096 *p
= (*p
& ~m
) | (v
& m
);
7097 bits
+= n
, bit_size
-= n
, bit_pos
= 0, ++p
;
7101 /* XXX: when cross-compiling we assume that each type has the
7102 same representation on host and target, which is likely to
7103 be wrong in the case of long double */
7105 vtop
->c
.i
= vtop
->c
.i
!= 0;
7107 *(char *)ptr
|= vtop
->c
.i
;
7110 *(short *)ptr
|= vtop
->c
.i
;
7113 *(float*)ptr
= vtop
->c
.f
;
7116 *(double *)ptr
= vtop
->c
.d
;
7119 #if defined TCC_IS_NATIVE_387
7120 if (sizeof (long double) >= 10) /* zero pad ten-byte LD */
7121 memcpy(ptr
, &vtop
->c
.ld
, 10);
7123 else if (sizeof (long double) == sizeof (double))
7124 __asm__("fldl %1\nfstpt %0\n" : "=m" (*ptr
) : "m" (vtop
->c
.ld
));
7126 else if (vtop
->c
.ld
== 0.0)
7130 if (sizeof(long double) == LDOUBLE_SIZE
)
7131 *(long double*)ptr
= vtop
->c
.ld
;
7132 else if (sizeof(double) == LDOUBLE_SIZE
)
7133 *(double *)ptr
= (double)vtop
->c
.ld
;
7135 tcc_error("can't cross compile long double constants");
7139 *(long long *)ptr
|= vtop
->c
.i
;
7146 addr_t val
= vtop
->c
.i
;
7148 if (vtop
->r
& VT_SYM
)
7149 greloca(sec
, vtop
->sym
, c
, R_DATA_PTR
, val
);
7151 *(addr_t
*)ptr
|= val
;
7153 if (vtop
->r
& VT_SYM
)
7154 greloc(sec
, vtop
->sym
, c
, R_DATA_PTR
);
7155 *(addr_t
*)ptr
|= val
;
7161 int val
= vtop
->c
.i
;
7163 if (vtop
->r
& VT_SYM
)
7164 greloca(sec
, vtop
->sym
, c
, R_DATA_PTR
, val
);
7168 if (vtop
->r
& VT_SYM
)
7169 greloc(sec
, vtop
->sym
, c
, R_DATA_PTR
);
7178 vset(&dtype
, VT_LOCAL
|VT_LVAL
, c
);
7185 /* 't' contains the type and storage info. 'c' is the offset of the
7186 object in section 'sec'. If 'sec' is NULL, it means stack based
7187 allocation. 'flags & DIF_FIRST' is true if array '{' must be read (multi
7188 dimension implicit array init handling). 'flags & DIF_SIZE_ONLY' is true if
7189 size only evaluation is wanted (only for arrays). */
7190 static void decl_initializer(CType
*type
, Section
*sec
, unsigned long c
,
7193 int len
, n
, no_oblock
, nb
, i
;
7199 if (!(flags
& DIF_HAVE_ELEM
) && tok
!= '{' &&
7200 /* In case of strings we have special handling for arrays, so
7201 don't consume them as initializer value (which would commit them
7202 to some anonymous symbol). */
7203 tok
!= TOK_LSTR
&& tok
!= TOK_STR
&&
7204 !(flags
& DIF_SIZE_ONLY
)) {
7205 parse_init_elem(!sec
? EXPR_ANY
: EXPR_CONST
);
7206 flags
|= DIF_HAVE_ELEM
;
7209 if ((flags
& DIF_HAVE_ELEM
) &&
7210 !(type
->t
& VT_ARRAY
) &&
7211 /* Use i_c_parameter_t, to strip toplevel qualifiers.
7212 The source type might have VT_CONSTANT set, which is
7213 of course assignable to non-const elements. */
7214 is_compatible_unqualified_types(type
, &vtop
->type
)) {
7215 init_putv(type
, sec
, c
);
7216 } else if (type
->t
& VT_ARRAY
) {
7219 t1
= pointed_type(type
);
7220 size1
= type_size(t1
, &align1
);
7223 if (((flags
& DIF_FIRST
) && tok
!= TOK_LSTR
&& tok
!= TOK_STR
) ||
7226 tcc_error("character array initializer must be a literal,"
7227 " optionally enclosed in braces");
7232 /* only parse strings here if correct type (otherwise: handle
7233 them as ((w)char *) expressions */
7234 if ((tok
== TOK_LSTR
&&
7235 #ifdef TCC_TARGET_PE
7236 (t1
->t
& VT_BTYPE
) == VT_SHORT
&& (t1
->t
& VT_UNSIGNED
)
7238 (t1
->t
& VT_BTYPE
) == VT_INT
7240 ) || (tok
== TOK_STR
&& (t1
->t
& VT_BTYPE
) == VT_BYTE
)) {
7242 while (tok
== TOK_STR
|| tok
== TOK_LSTR
) {
7245 /* compute maximum number of chars wanted */
7247 cstr_len
= tokc
.str
.size
;
7249 cstr_len
= tokc
.str
.size
/ sizeof(nwchar_t
);
7252 if (n
>= 0 && nb
> (n
- len
))
7254 if (!(flags
& DIF_SIZE_ONLY
)) {
7256 tcc_warning("initializer-string for array is too long");
7257 /* in order to go faster for common case (char
7258 string in global variable, we handle it
7260 if (sec
&& tok
== TOK_STR
&& size1
== 1) {
7262 memcpy(sec
->data
+ c
+ len
, tokc
.str
.data
, nb
);
7266 ch
= ((unsigned char *)tokc
.str
.data
)[i
];
7268 ch
= ((nwchar_t
*)tokc
.str
.data
)[i
];
7270 init_putv(t1
, sec
, c
+ (len
+ i
) * size1
);
7277 /* only add trailing zero if enough storage (no
7278 warning in this case since it is standard) */
7279 if (n
< 0 || len
< n
) {
7280 if (!(flags
& DIF_SIZE_ONLY
)) {
7282 init_putv(t1
, sec
, c
+ (len
* size1
));
7293 while (tok
!= '}' || (flags
& DIF_HAVE_ELEM
)) {
7294 len
= decl_designator(type
, sec
, c
, &f
, flags
, len
);
7295 flags
&= ~DIF_HAVE_ELEM
;
7296 if (type
->t
& VT_ARRAY
) {
7298 /* special test for multi dimensional arrays (may not
7299 be strictly correct if designators are used at the
7301 if (no_oblock
&& len
>= n
*size1
)
7304 if (s
->type
.t
== VT_UNION
)
7308 if (no_oblock
&& f
== NULL
)
7317 /* put zeros at the end */
7318 if (!(flags
& DIF_SIZE_ONLY
) && len
< n
*size1
)
7319 init_putz(sec
, c
+ len
, n
*size1
- len
);
7322 /* patch type size if needed, which happens only for array types */
7324 s
->c
= size1
== 1 ? len
: ((len
+ size1
- 1)/size1
);
7325 } else if ((type
->t
& VT_BTYPE
) == VT_STRUCT
) {
7328 if ((flags
& DIF_FIRST
) || tok
== '{') {
7336 } else if (tok
== '{') {
7337 if (flags
& DIF_HAVE_ELEM
)
7340 decl_initializer(type
, sec
, c
, flags
& ~DIF_HAVE_ELEM
);
7342 } else if ((flags
& DIF_SIZE_ONLY
)) {
7343 /* If we supported only ISO C we wouldn't have to accept calling
7344 this on anything than an array if DIF_SIZE_ONLY (and even then
7345 only on the outermost level, so no recursion would be needed),
7346 because initializing a flex array member isn't supported.
7347 But GNU C supports it, so we need to recurse even into
7348 subfields of structs and arrays when DIF_SIZE_ONLY is set. */
7349 /* just skip expression */
7350 skip_or_save_block(NULL
);
7352 if (!(flags
& DIF_HAVE_ELEM
)) {
7353 /* This should happen only when we haven't parsed
7354 the init element above for fear of committing a
7355 string constant to memory too early. */
7356 if (tok
!= TOK_STR
&& tok
!= TOK_LSTR
)
7357 expect("string constant");
7358 parse_init_elem(!sec
? EXPR_ANY
: EXPR_CONST
);
7360 init_putv(type
, sec
, c
);
7364 /* parse an initializer for type 't' if 'has_init' is non zero, and
7365 allocate space in local or global data space ('r' is either
7366 VT_LOCAL or VT_CONST). If 'v' is non zero, then an associated
7367 variable 'v' of scope 'scope' is declared before initializers
7368 are parsed. If 'v' is zero, then a reference to the new object
7369 is put in the value stack. If 'has_init' is 2, a special parsing
7370 is done to handle string constants. */
7371 static void decl_initializer_alloc(CType
*type
, AttributeDef
*ad
, int r
,
7372 int has_init
, int v
, int scope
)
7374 int size
, align
, addr
;
7375 TokenString
*init_str
= NULL
;
7378 Sym
*flexible_array
;
7380 int saved_nocode_wanted
= nocode_wanted
;
7381 #ifdef CONFIG_TCC_BCHECK
7382 int bcheck
= tcc_state
->do_bounds_check
&& !NODATA_WANTED
;
7385 /* Always allocate static or global variables */
7386 if (v
&& (r
& VT_VALMASK
) == VT_CONST
)
7387 nocode_wanted
|= 0x80000000;
7389 flexible_array
= NULL
;
7390 if ((type
->t
& VT_BTYPE
) == VT_STRUCT
) {
7391 Sym
*field
= type
->ref
->next
;
7394 field
= field
->next
;
7395 if (field
->type
.t
& VT_ARRAY
&& field
->type
.ref
->c
< 0)
7396 flexible_array
= field
;
7400 size
= type_size(type
, &align
);
7401 /* If unknown size, we must evaluate it before
7402 evaluating initializers because
7403 initializers can generate global data too
7404 (e.g. string pointers or ISOC99 compound
7405 literals). It also simplifies local
7406 initializers handling */
7407 if (size
< 0 || (flexible_array
&& has_init
)) {
7409 tcc_error("unknown type size");
7410 /* get all init string */
7411 if (has_init
== 2) {
7412 init_str
= tok_str_alloc();
7413 /* only get strings */
7414 while (tok
== TOK_STR
|| tok
== TOK_LSTR
) {
7415 tok_str_add_tok(init_str
);
7418 tok_str_add(init_str
, -1);
7419 tok_str_add(init_str
, 0);
7421 skip_or_save_block(&init_str
);
7426 begin_macro(init_str
, 1);
7428 decl_initializer(type
, NULL
, 0, DIF_FIRST
| DIF_SIZE_ONLY
);
7429 /* prepare second initializer parsing */
7430 macro_ptr
= init_str
->str
;
7433 /* if still unknown size, error */
7434 size
= type_size(type
, &align
);
7436 tcc_error("unknown type size");
7438 /* If there's a flex member and it was used in the initializer
7440 if (flexible_array
&&
7441 flexible_array
->type
.ref
->c
> 0)
7442 size
+= flexible_array
->type
.ref
->c
7443 * pointed_size(&flexible_array
->type
);
7444 /* take into account specified alignment if bigger */
7445 if (ad
->a
.aligned
) {
7446 int speca
= 1 << (ad
->a
.aligned
- 1);
7449 } else if (ad
->a
.packed
) {
7453 if (!v
&& NODATA_WANTED
)
7454 size
= 0, align
= 1;
7456 if ((r
& VT_VALMASK
) == VT_LOCAL
) {
7458 #ifdef CONFIG_TCC_BCHECK
7460 /* add padding between stack variables for bound checking */
7464 loc
= (loc
- size
) & -align
;
7466 #ifdef CONFIG_TCC_BCHECK
7468 /* add padding between stack variables for bound checking */
7473 /* local variable */
7474 #ifdef CONFIG_TCC_ASM
7475 if (ad
->asm_label
) {
7476 int reg
= asm_parse_regvar(ad
->asm_label
);
7478 r
= (r
& ~VT_VALMASK
) | reg
;
7481 sym
= sym_push(v
, type
, r
, addr
);
7482 if (ad
->cleanup_func
) {
7483 Sym
*cls
= sym_push2(&all_cleanups
,
7484 SYM_FIELD
| ++cur_scope
->cl
.n
, 0, 0);
7485 cls
->prev_tok
= sym
;
7486 cls
->next
= ad
->cleanup_func
;
7487 cls
->ncl
= cur_scope
->cl
.s
;
7488 cur_scope
->cl
.s
= cls
;
7493 /* push local reference */
7494 vset(type
, r
, addr
);
7497 if (v
&& scope
== VT_CONST
) {
7498 /* see if the symbol was already defined */
7501 patch_storage(sym
, ad
, type
);
7502 /* we accept several definitions of the same global variable. */
7503 if (!has_init
&& sym
->c
&& elfsym(sym
)->st_shndx
!= SHN_UNDEF
)
7508 /* allocate symbol in corresponding section */
7513 else if (tcc_state
->nocommon
)
7518 addr
= section_add(sec
, size
, align
);
7519 #ifdef CONFIG_TCC_BCHECK
7520 /* add padding if bound check */
7522 section_add(sec
, 1, 1);
7525 addr
= align
; /* SHN_COMMON is special, symbol value is align */
7526 sec
= common_section
;
7531 sym
= sym_push(v
, type
, r
| VT_SYM
, 0);
7532 patch_storage(sym
, ad
, NULL
);
7534 /* update symbol definition */
7535 put_extern_sym(sym
, sec
, addr
, size
);
7537 /* push global reference */
7538 vpush_ref(type
, sec
, addr
, size
);
7543 #ifdef CONFIG_TCC_BCHECK
7544 /* handles bounds now because the symbol must be defined
7545 before for the relocation */
7549 greloca(bounds_section
, sym
, bounds_section
->data_offset
, R_DATA_PTR
, 0);
7550 /* then add global bound info */
7551 bounds_ptr
= section_ptr_add(bounds_section
, 2 * sizeof(addr_t
));
7552 bounds_ptr
[0] = 0; /* relocated */
7553 bounds_ptr
[1] = size
;
7558 if (type
->t
& VT_VLA
) {
7564 /* save current stack pointer */
7565 if (root_scope
->vla
.loc
== 0) {
7566 struct scope
*v
= cur_scope
;
7567 gen_vla_sp_save(loc
-= PTR_SIZE
);
7568 do v
->vla
.loc
= loc
; while ((v
= v
->prev
));
7571 vla_runtime_type_size(type
, &a
);
7572 gen_vla_alloc(type
, a
);
7573 #if defined TCC_TARGET_PE && defined TCC_TARGET_X86_64
7574 /* on _WIN64, because of the function args scratch area, the
7575 result of alloca differs from RSP and is returned in RAX. */
7576 gen_vla_result(addr
), addr
= (loc
-= PTR_SIZE
);
7578 gen_vla_sp_save(addr
);
7579 cur_scope
->vla
.loc
= addr
;
7580 cur_scope
->vla
.num
++;
7581 } else if (has_init
) {
7582 size_t oldreloc_offset
= 0;
7583 if (sec
&& sec
->reloc
)
7584 oldreloc_offset
= sec
->reloc
->data_offset
;
7585 decl_initializer(type
, sec
, addr
, DIF_FIRST
);
7586 if (sec
&& sec
->reloc
)
7587 squeeze_multi_relocs(sec
, oldreloc_offset
);
7588 /* patch flexible array member size back to -1, */
7589 /* for possible subsequent similar declarations */
7591 flexible_array
->type
.ref
->c
= -1;
7595 /* restore parse state if needed */
7601 nocode_wanted
= saved_nocode_wanted
;
7604 /* parse a function defined by symbol 'sym' and generate its code in
7605 'cur_text_section' */
7606 static void gen_function(Sym
*sym
)
7608 /* Initialize VLA state */
7609 struct scope f
= { 0 };
7610 cur_scope
= root_scope
= &f
;
7613 ind
= cur_text_section
->data_offset
;
7614 if (sym
->a
.aligned
) {
7615 size_t newoff
= section_add(cur_text_section
, 0,
7616 1 << (sym
->a
.aligned
- 1));
7617 gen_fill_nops(newoff
- ind
);
7619 /* NOTE: we patch the symbol size later */
7620 put_extern_sym(sym
, cur_text_section
, ind
, 0);
7621 if (sym
->type
.ref
->f
.func_ctor
)
7622 add_array (tcc_state
, ".init_array", sym
->c
);
7623 if (sym
->type
.ref
->f
.func_dtor
)
7624 add_array (tcc_state
, ".fini_array", sym
->c
);
7625 funcname
= get_tok_str(sym
->v
, NULL
);
7627 /* put debug symbol */
7628 tcc_debug_funcstart(tcc_state
, sym
);
7629 /* push a dummy symbol to enable local sym storage */
7630 sym_push2(&local_stack
, SYM_FIELD
, 0, 0);
7631 local_scope
= 1; /* for function parameters */
7635 clear_temp_local_var_list();
7639 /* reset local stack */
7640 pop_local_syms(&local_stack
, NULL
, 0,
7641 sym
->type
.ref
->f
.func_type
== FUNC_ELLIPSIS
);
7643 cur_text_section
->data_offset
= ind
;
7645 label_pop(&global_label_stack
, NULL
, 0);
7646 sym_pop(&all_cleanups
, NULL
, 0);
7647 /* patch symbol size */
7648 elfsym(sym
)->st_size
= ind
- func_ind
;
7649 /* end of function */
7650 tcc_debug_funcend(tcc_state
, ind
- func_ind
);
7651 /* It's better to crash than to generate wrong code */
7652 cur_text_section
= NULL
;
7653 funcname
= ""; /* for safety */
7654 func_vt
.t
= VT_VOID
; /* for safety */
7655 func_var
= 0; /* for safety */
7656 ind
= 0; /* for safety */
7657 nocode_wanted
= 0x80000000;
7659 /* do this after funcend debug info */
7663 static void gen_inline_functions(TCCState
*s
)
7666 int inline_generated
, i
;
7667 struct InlineFunc
*fn
;
7669 tcc_open_bf(s
, ":inline:", 0);
7670 /* iterate while inline function are referenced */
7672 inline_generated
= 0;
7673 for (i
= 0; i
< s
->nb_inline_fns
; ++i
) {
7674 fn
= s
->inline_fns
[i
];
7676 if (sym
&& (sym
->c
|| !(sym
->type
.t
& VT_INLINE
))) {
7677 /* the function was used or forced (and then not internal):
7678 generate its code and convert it to a normal function */
7680 tcc_debug_putfile(s
, fn
->filename
);
7681 begin_macro(fn
->func_str
, 1);
7683 cur_text_section
= text_section
;
7687 inline_generated
= 1;
7690 } while (inline_generated
);
7694 static void free_inline_functions(TCCState
*s
)
7697 /* free tokens of unused inline functions */
7698 for (i
= 0; i
< s
->nb_inline_fns
; ++i
) {
7699 struct InlineFunc
*fn
= s
->inline_fns
[i
];
7701 tok_str_free(fn
->func_str
);
7703 dynarray_reset(&s
->inline_fns
, &s
->nb_inline_fns
);
7706 /* 'l' is VT_LOCAL or VT_CONST to define default storage type, or VT_CMP
7707 if parsing old style parameter decl list (and FUNC_SYM is set then) */
7708 static int decl0(int l
, int is_for_loop_init
, Sym
*func_sym
)
7713 AttributeDef ad
, adbase
;
7716 if (tok
== TOK_STATIC_ASSERT
) {
7724 tcc_error("%s", get_tok_str(tok
, &tokc
));
7730 if (!parse_btype(&btype
, &adbase
)) {
7731 if (is_for_loop_init
)
7733 /* skip redundant ';' if not in old parameter decl scope */
7734 if (tok
== ';' && l
!= VT_CMP
) {
7740 if (tok
== TOK_ASM1
|| tok
== TOK_ASM2
|| tok
== TOK_ASM3
) {
7741 /* global asm block */
7745 if (tok
>= TOK_UIDENT
) {
7746 /* special test for old K&R protos without explicit int
7747 type. Only accepted when defining global data */
7751 expect("declaration");
7756 if ((btype
.t
& VT_BTYPE
) == VT_STRUCT
) {
7757 int v
= btype
.ref
->v
;
7758 if (!(v
& SYM_FIELD
) && (v
& ~SYM_STRUCT
) >= SYM_FIRST_ANOM
)
7759 tcc_warning("unnamed struct/union that defines no instances");
7763 if (IS_ENUM(btype
.t
)) {
7768 while (1) { /* iterate thru each declaration */
7770 /* If the base type itself was an array type of unspecified
7771 size (like in 'typedef int arr[]; arr x = {1};') then
7772 we will overwrite the unknown size by the real one for
7773 this decl. We need to unshare the ref symbol holding
7775 if ((type
.t
& VT_ARRAY
) && type
.ref
->c
< 0) {
7776 type
.ref
= sym_push(SYM_FIELD
, &type
.ref
->type
, 0, type
.ref
->c
);
7779 type_decl(&type
, &ad
, &v
, TYPE_DIRECT
);
7783 type_to_str(buf
, sizeof(buf
), &type
, get_tok_str(v
, NULL
));
7784 printf("type = '%s'\n", buf
);
7787 if ((type
.t
& VT_BTYPE
) == VT_FUNC
) {
7788 if ((type
.t
& VT_STATIC
) && (l
== VT_LOCAL
))
7789 tcc_error("function without file scope cannot be static");
7790 /* if old style function prototype, we accept a
7793 if (sym
->f
.func_type
== FUNC_OLD
&& l
== VT_CONST
)
7794 decl0(VT_CMP
, 0, sym
);
7795 /* always compile 'extern inline' */
7796 if (type
.t
& VT_EXTERN
)
7797 type
.t
&= ~VT_INLINE
;
7800 if (gnu_ext
&& (tok
== TOK_ASM1
|| tok
== TOK_ASM2
|| tok
== TOK_ASM3
)) {
7801 ad
.asm_label
= asm_label_instr();
7802 /* parse one last attribute list, after asm label */
7803 parse_attribute(&ad
);
7805 /* gcc does not allow __asm__("label") with function definition,
7812 #ifdef TCC_TARGET_PE
7813 if (ad
.a
.dllimport
|| ad
.a
.dllexport
) {
7814 if (type
.t
& VT_STATIC
)
7815 tcc_error("cannot have dll linkage with static");
7816 if (type
.t
& VT_TYPEDEF
) {
7817 tcc_warning("'%s' attribute ignored for typedef",
7818 ad
.a
.dllimport
? (ad
.a
.dllimport
= 0, "dllimport") :
7819 (ad
.a
.dllexport
= 0, "dllexport"));
7820 } else if (ad
.a
.dllimport
) {
7821 if ((type
.t
& VT_BTYPE
) == VT_FUNC
)
7824 type
.t
|= VT_EXTERN
;
7830 tcc_error("cannot use local functions");
7831 if ((type
.t
& VT_BTYPE
) != VT_FUNC
)
7832 expect("function definition");
7834 /* reject abstract declarators in function definition
7835 make old style params without decl have int type */
7837 while ((sym
= sym
->next
) != NULL
) {
7838 if (!(sym
->v
& ~SYM_FIELD
))
7839 expect("identifier");
7840 if (sym
->type
.t
== VT_VOID
)
7841 sym
->type
= int_type
;
7844 /* put function symbol */
7845 type
.t
&= ~VT_EXTERN
;
7846 sym
= external_sym(v
, &type
, 0, &ad
);
7847 /* static inline functions are just recorded as a kind
7848 of macro. Their code will be emitted at the end of
7849 the compilation unit only if they are used */
7850 if (sym
->type
.t
& VT_INLINE
) {
7851 struct InlineFunc
*fn
;
7852 fn
= tcc_malloc(sizeof *fn
+ strlen(file
->filename
));
7853 strcpy(fn
->filename
, file
->filename
);
7855 skip_or_save_block(&fn
->func_str
);
7856 dynarray_add(&tcc_state
->inline_fns
,
7857 &tcc_state
->nb_inline_fns
, fn
);
7859 /* compute text section */
7860 cur_text_section
= ad
.section
;
7861 if (!cur_text_section
)
7862 cur_text_section
= text_section
;
7868 /* find parameter in function parameter list */
7869 for (sym
= func_sym
->next
; sym
; sym
= sym
->next
)
7870 if ((sym
->v
& ~SYM_FIELD
) == v
)
7872 tcc_error("declaration for parameter '%s' but no such parameter",
7873 get_tok_str(v
, NULL
));
7875 if (type
.t
& VT_STORAGE
) /* 'register' is okay */
7876 tcc_error("storage class specified for '%s'",
7877 get_tok_str(v
, NULL
));
7878 if (sym
->type
.t
!= VT_VOID
)
7879 tcc_error("redefinition of parameter '%s'",
7880 get_tok_str(v
, NULL
));
7881 convert_parameter_type(&type
);
7883 } else if (type
.t
& VT_TYPEDEF
) {
7884 /* save typedefed type */
7885 /* XXX: test storage specifiers ? */
7887 if (sym
&& sym
->sym_scope
== local_scope
) {
7888 if (!is_compatible_types(&sym
->type
, &type
)
7889 || !(sym
->type
.t
& VT_TYPEDEF
))
7890 tcc_error("incompatible redefinition of '%s'",
7891 get_tok_str(v
, NULL
));
7894 sym
= sym_push(v
, &type
, 0, 0);
7898 } else if ((type
.t
& VT_BTYPE
) == VT_VOID
7899 && !(type
.t
& VT_EXTERN
)) {
7900 tcc_error("declaration of void object");
7903 if ((type
.t
& VT_BTYPE
) == VT_FUNC
) {
7904 /* external function definition */
7905 /* specific case for func_call attribute */
7907 } else if (!(type
.t
& VT_ARRAY
)) {
7908 /* not lvalue if array */
7911 has_init
= (tok
== '=');
7912 if (has_init
&& (type
.t
& VT_VLA
))
7913 tcc_error("variable length array cannot be initialized");
7914 if (((type
.t
& VT_EXTERN
) && (!has_init
|| l
!= VT_CONST
))
7915 || (type
.t
& VT_BTYPE
) == VT_FUNC
7916 /* as with GCC, uninitialized global arrays with no size
7917 are considered extern: */
7918 || ((type
.t
& VT_ARRAY
) && !has_init
7919 && l
== VT_CONST
&& type
.ref
->c
< 0)
7921 /* external variable or function */
7922 type
.t
|= VT_EXTERN
;
7923 sym
= external_sym(v
, &type
, r
, &ad
);
7924 if (ad
.alias_target
) {
7927 alias_target
= sym_find(ad
.alias_target
);
7928 esym
= elfsym(alias_target
);
7930 tcc_error("unsupported forward __alias__ attribute");
7931 put_extern_sym2(sym
, esym
->st_shndx
, esym
->st_value
, esym
->st_size
, 0);
7934 if (type
.t
& VT_STATIC
)
7940 else if (l
== VT_CONST
)
7941 /* uninitialized global variables may be overridden */
7942 type
.t
|= VT_EXTERN
;
7943 decl_initializer_alloc(&type
, &ad
, r
, has_init
, v
, l
);
7947 if (is_for_loop_init
)
7959 static void decl(int l
)
7964 /* ------------------------------------------------------------------------- */
7967 /* ------------------------------------------------------------------------- */