arm: fixed minor typo
[neatcc.git] / ncc.c
blob8057066dbfc7b912e2e21a94d118b56a9dd3c166
1 /*
2 * THE NEATCC C COMPILER
4 * Copyright (C) 2010-2016 Ali Gholami Rudi
6 * Permission to use, copy, modify, and/or distribute this software for any
7 * purpose with or without fee is hereby granted, provided that the above
8 * copyright notice and this permission notice appear in all copies.
10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
11 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
12 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
13 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
14 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
15 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
16 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
19 * neatcc parser
21 * The parser reads tokens from the tokenizer (tok_*) and calls the
22 * appropriate code generation functions (o_*). The generator
23 * maintains a stack of values pushed via, for instance, o_num()
24 * and generates the necessary code for the accesses to the items
25 * in this stack, like o_bop() for performing a binary operations
26 * on the top two items of the stack. The parser maintains the
27 * types of values pushed to the generator stack in its type stack
28 * (ts_*). For instance, for binary operations two types are
29 * popped first and the resulting type is pushed to the type stack
30 * (ts_binop()).
33 #include <ctype.h>
34 #include <fcntl.h>
35 #include <unistd.h>
36 #include <stdarg.h>
37 #include <stdlib.h>
38 #include <string.h>
39 #include <stdio.h>
40 #include <sys/stat.h>
41 #include <sys/types.h>
42 #include "ncc.h"
44 #define ALIGN(x, a) (((x) + (a) - 1) & ~((a) - 1))
45 #define MIN(a, b) ((a) < (b) ? (a) : (b))
46 #define MAX(a, b) ((a) < (b) ? (b) : (a))
48 #define TYPE_BT(t) ((t)->ptr ? ULNG : (t)->bt)
49 #define TYPE_SZ(t) ((t)->ptr ? ULNG : (t)->bt & T_MSIZE)
50 #define TYPE_VOID(t) (!(t)->bt && !(t)->flags && !(t)->ptr)
52 /* type->flag values */
53 #define T_ARRAY 0x01
54 #define T_STRUCT 0x02
55 #define T_FUNC 0x04
57 /* variable definition flags */
58 #define F_STATIC 0x01
59 #define F_EXTERN 0x02
61 struct type {
62 unsigned bt;
63 unsigned flags;
64 int ptr;
65 int id; /* for structs, functions and arrays */
66 int addr; /* the address is passed to gen.c; deref for value */
69 /* type stack */
70 static struct type ts[NTMPS];
71 static int nts;
73 static void ts_push_bt(unsigned bt)
75 ts[nts].ptr = 0;
76 ts[nts].flags = 0;
77 ts[nts].addr = 0;
78 ts[nts++].bt = bt;
79 #ifdef NCCWORDCAST
80 o_cast(bt); /* casting to architecture word */
81 #endif
84 static void ts_push(struct type *t)
86 struct type *d = &ts[nts++];
87 memcpy(d, t, sizeof(*t));
90 static void ts_push_addr(struct type *t)
92 ts_push(t);
93 ts[nts - 1].addr = 1;
96 static void ts_pop(struct type *type)
98 nts--;
99 if (type)
100 *type = ts[nts];
103 void err(char *fmt, ...)
105 va_list ap;
106 char msg[512];
107 va_start(ap, fmt);
108 vsprintf(msg, fmt, ap);
109 va_end(ap);
110 die("%s: %s", cpp_loc(tok_addr()), msg);
113 void *mextend(void *old, long oldsz, long newsz, long memsz)
115 void *new = malloc(newsz * memsz);
116 memcpy(new, old, oldsz * memsz);
117 memset(new + oldsz * memsz, 0, (newsz - oldsz) * memsz);
118 free(old);
119 return new;
122 struct name {
123 char name[NAMELEN];
124 char elfname[NAMELEN]; /* local elf name for function static variables */
125 struct type type;
126 long addr; /* local stack offset, global data addr, struct offset */
129 static struct name *locals;
130 static int locals_n, locals_sz;
131 static struct name *globals;
132 static int globals_n, globals_sz;
134 static void local_add(struct name *name)
136 if (locals_n >= locals_sz) {
137 locals_sz = MAX(128, locals_sz * 2);
138 locals = mextend(locals, locals_n, locals_sz, sizeof(locals[0]));
140 memcpy(&locals[locals_n++], name, sizeof(*name));
143 static int local_find(char *name)
145 int i;
146 for (i = locals_n - 1; i >= 0; --i)
147 if (!strcmp(locals[i].name, name))
148 return i;
149 return -1;
152 static int global_find(char *name)
154 int i;
155 for (i = globals_n - 1; i >= 0; i--)
156 if (!strcmp(name, globals[i].name))
157 return i;
158 return -1;
161 static void global_add(struct name *name)
163 if (globals_n >= globals_sz) {
164 globals_sz = MAX(128, globals_sz * 2);
165 globals = mextend(globals, globals_n, globals_sz, sizeof(globals[0]));
167 memcpy(&globals[globals_n++], name, sizeof(*name));
170 #define LABEL() (++label)
172 static int label; /* last used label id */
173 static int l_break; /* current break label */
174 static int l_cont; /* current continue label */
176 static struct enumval {
177 char name[NAMELEN];
178 int n;
179 } *enums;
180 static int enums_n, enums_sz;
182 static void enum_add(char *name, int val)
184 struct enumval *ev;
185 if (enums_n >= enums_sz) {
186 enums_sz = MAX(128, enums_sz * 2);
187 enums = mextend(enums, enums_n, enums_sz, sizeof(enums[0]));
189 ev = &enums[enums_n++];
190 strcpy(ev->name, name);
191 ev->n = val;
194 static int enum_find(int *val, char *name)
196 int i;
197 for (i = enums_n - 1; i >= 0; --i)
198 if (!strcmp(name, enums[i].name)) {
199 *val = enums[i].n;
200 return 0;
202 return 1;
205 static struct typdefinfo {
206 char name[NAMELEN];
207 struct type type;
208 } *typedefs;
209 static int typedefs_n, typedefs_sz;
211 static void typedef_add(char *name, struct type *type)
213 struct typdefinfo *ti;
214 if (typedefs_n >= typedefs_sz) {
215 typedefs_sz = MAX(128, typedefs_sz * 2);
216 typedefs = mextend(typedefs, typedefs_n, typedefs_sz,
217 sizeof(typedefs[0]));
219 ti = &typedefs[typedefs_n++];
220 strcpy(ti->name, name);
221 memcpy(&ti->type, type, sizeof(*type));
224 static int typedef_find(char *name)
226 int i;
227 for (i = typedefs_n - 1; i >= 0; --i)
228 if (!strcmp(name, typedefs[i].name))
229 return i;
230 return -1;
233 static struct array {
234 struct type type;
235 int n;
236 } *arrays;
237 static int arrays_n, arrays_sz;
239 static int array_add(struct type *type, int n)
241 struct array *a;
242 if (arrays_n >= arrays_sz) {
243 arrays_sz = MAX(128, arrays_sz * 2);
244 arrays = mextend(arrays, arrays_n, arrays_sz, sizeof(arrays[0]));
246 a = &arrays[arrays_n++];
247 memcpy(&a->type, type, sizeof(*type));
248 a->n = n;
249 return a - arrays;
252 static void array2ptr(struct type *t)
254 if (t->flags & T_ARRAY && !t->ptr) {
255 memcpy(t, &arrays[t->id].type, sizeof(*t));
256 t->ptr++;
260 static struct structinfo {
261 char name[NAMELEN];
262 struct name fields[NFIELDS];
263 int nfields;
264 int isunion;
265 int size;
266 } *structs;
267 static int structs_n, structs_sz;
269 static int struct_find(char *name, int isunion)
271 int i;
272 for (i = structs_n - 1; i >= 0; --i)
273 if (*structs[i].name && !strcmp(name, structs[i].name) &&
274 structs[i].isunion == isunion)
275 return i;
276 if (structs_n >= structs_sz) {
277 structs_sz = MAX(128, structs_sz * 2);
278 structs = mextend(structs, structs_n, structs_sz, sizeof(structs[0]));
280 i = structs_n++;
281 memset(&structs[i], 0, sizeof(structs[i]));
282 strcpy(structs[i].name, name);
283 structs[i].isunion = isunion;
284 return i;
287 static struct name *struct_field(int id, char *name)
289 struct structinfo *si = &structs[id];
290 int i;
291 for (i = 0; i < si->nfields; i++)
292 if (!strcmp(name, si->fields[i].name))
293 return &si->fields[i];
294 err("unknown field <%s>\n", name);
295 return NULL;
298 /* return t's size */
299 static int type_totsz(struct type *t)
301 if (t->ptr)
302 return ULNG;
303 if (t->flags & T_ARRAY)
304 return arrays[t->id].n * type_totsz(&arrays[t->id].type);
305 return t->flags & T_STRUCT ? structs[t->id].size : T_SZ(t->bt);
308 /* return t's dereferenced size */
309 static unsigned type_szde(struct type *t)
311 struct type de = *t;
312 array2ptr(&de);
313 de.ptr--;
314 return type_totsz(&de);
317 /* dereference stack top if t->addr (ie. address is pushed to gen.c) */
318 static void ts_de(int deref)
320 struct type *t = &ts[nts - 1];
321 array2ptr(t);
322 if (deref && t->addr && (t->ptr || !(t->flags & T_FUNC)))
323 o_deref(TYPE_BT(t));
324 t->addr = 0;
327 /* pop stack pop to *t and dereference if t->addr */
328 static void ts_pop_de(struct type *t)
330 ts_de(1);
331 ts_pop(t);
334 /* pop the top 2 stack values and dereference them if t->addr */
335 static void ts_pop_de2(struct type *t1, struct type *t2)
337 ts_pop_de(t1);
338 o_tmpswap();
339 ts_pop_de(t2);
340 o_tmpswap();
343 /* the previous identifier; to handle labels */
344 static char tok_previden[NAMELEN];
346 static char *tok_iden(void)
348 snprintf(tok_previden, sizeof(tok_previden), "%s", tok_get());
349 return tok_previden;
352 static int tok_jmp(char *tok)
354 if (strcmp(tok, tok_see()))
355 return 1;
356 tok_get();
357 return 0;
360 static int tok_comes(char *tok)
362 return !strcmp(tok, tok_see());
365 static void tok_req(char *tok)
367 char *got = tok_get();
368 if (strcmp(tok, got))
369 err("syntax error (expected <%s> but got <%s>)\n", tok, got);
372 static int tok_grp(void)
374 int c = (unsigned char) tok_see()[0];
375 if (c == '"')
376 return '"';
377 if (c == '\'' || isdigit(c))
378 return '0';
379 if (c == '_' || isalpha(c))
380 return 'a';
381 return 0;
384 /* the result of a binary operation on variables of type bt1 and bt2 */
385 static unsigned bt_op(unsigned bt1, unsigned bt2)
387 /* Type conversion according to ISO9899, sec. 6.3.1.8.
388 * http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1256.pdf
390 * Summary:
391 * Size: Always convert to largest size.
392 * Sign:
393 * - Same sign: Keep sign.
394 * - Same size or unsigned larger: Convert to unsigned.
395 * - Signed larger: Convert to signed.
397 int sz = MAX(T_SZ(bt1), T_SZ(bt2));
398 /* the unsigned operand is at least as large as the signed one */
399 if ((!T_SG(bt1) && T_SG(bt2) && T_SZ(bt1) >= T_SZ(bt2)) ||
400 (T_SG(bt1) && !T_SG(bt2) && T_SZ(bt1) <= T_SZ(bt2)))
401 return MAX(sz, UINT);
402 return T_SG(bt1) | T_SG(bt2) | MAX(sz, UINT);
405 /* the result of a unary operation on variables of bt */
406 static unsigned bt_uop(unsigned bt)
408 return bt_op(bt, SINT);
411 /* push the result of a binary operation on the type stack */
412 static void ts_binop(int op)
414 struct type t1, t2;
415 unsigned bt1, bt2, bt;
416 ts_pop_de2(&t1, &t2);
417 bt1 = TYPE_BT(&t1);
418 bt2 = TYPE_BT(&t2);
419 bt = bt_op(bt1, bt2);
420 if (op == O_DIV || op == O_MOD)
421 bt = T_MK(bt2 & T_MSIGN, bt);
422 o_bop(O_MK(op, bt));
423 ts_push_bt(bt);
426 /* push the result of an additive binary operation on the type stack */
427 static void ts_addop(int op)
429 struct type t1, t2;
430 ts_pop_de2(&t1, &t2);
431 if (!t1.ptr && !t2.ptr) {
432 o_bop(op);
433 ts_push_bt(bt_op(TYPE_BT(&t1), TYPE_BT(&t2)));
434 return;
436 if (t1.ptr && !t2.ptr)
437 o_tmpswap();
438 if (!t1.ptr && t2.ptr)
439 if (type_szde(&t2) > 1) {
440 o_num(type_szde(&t2));
441 o_bop(O_MUL);
443 if (t1.ptr && !t2.ptr)
444 o_tmpswap();
445 o_bop(op);
446 if (t1.ptr && t2.ptr) {
447 int sz = type_szde(&t1);
448 if (sz > 1) {
449 o_num(sz);
450 o_bop(O_DIV);
452 ts_push_bt(SLNG);
453 } else {
454 ts_push(t1.ptr ? &t1 : &t2);
458 /* function prototypes for parsing function and variable declarations */
459 static int readname(struct type *main, char *name, struct type *base);
460 static int readtype(struct type *type);
461 static int readdefs(void (*def)(long data, struct name *name, unsigned flags),
462 long data);
463 static int readdefs_int(void (*def)(long data, struct name *name, unsigned flags),
464 long data);
466 /* function prototypes for parsing initializer expressions */
467 static int initsize(void);
468 static void initexpr(struct type *t, int off, void *obj,
469 void (*set)(void *obj, int off, struct type *t));
471 static int type_alignment(struct type *t)
473 if (t->flags & T_ARRAY && !t->ptr)
474 return type_alignment(&arrays[t->id].type);
475 if (t->flags & T_STRUCT && !t->ptr)
476 return type_alignment(&structs[t->id].fields[0].type);
477 return MIN(ULNG, type_totsz(t));
480 static void structdef(long data, struct name *name, unsigned flags)
482 struct structinfo *si = &structs[data];
483 if (si->isunion) {
484 name->addr = 0;
485 if (si->size < type_totsz(&name->type))
486 si->size = type_totsz(&name->type);
487 } else {
488 struct type *t = &name->type;
489 int alignment = type_alignment(t);
490 if (t->flags & T_ARRAY && !t->ptr)
491 alignment = MIN(ULNG, type_totsz(&arrays[t->id].type));
492 si->size = ALIGN(si->size, alignment);
493 name->addr = si->size;
494 si->size += type_totsz(&name->type);
496 memcpy(&si->fields[si->nfields++], name, sizeof(*name));
499 static int struct_create(char *name, int isunion)
501 int id = struct_find(name, isunion);
502 tok_req("{");
503 while (tok_jmp("}")) {
504 readdefs(structdef, id);
505 tok_req(";");
507 return id;
510 static void readexpr(void);
512 static void enum_create(void)
514 long n = 0;
515 tok_req("{");
516 while (tok_jmp("}")) {
517 char name[NAMELEN];
518 strcpy(name, tok_get());
519 if (!tok_jmp("=")) {
520 readexpr();
521 ts_pop_de(NULL);
522 if (o_popnum(&n))
523 err("const expr expected!\n");
525 enum_add(name, n++);
526 tok_jmp(",");
530 /* used to differentiate labels from case and cond exprs */
531 static int ncexpr;
532 static int caseexpr;
534 static void readpre(void);
536 static char *tmp_str(char *buf, int len)
538 static char name[NAMELEN];
539 static int id;
540 sprintf(name, "__neatcc.s%d", id++);
541 buf[len] = '\0';
542 o_dscpy(o_dsnew(name, len + 1, 0), buf, len + 1);
543 return name;
546 static void readprimary(void)
548 if (tok_grp() == '0') {
549 long n;
550 int bt = tok_num(tok_get(), &n);
551 o_num(n);
552 ts_push_bt(bt);
553 return;
555 if (tok_grp() == '"') {
556 struct type t = {}; /* char type inside the arrays */
557 struct type a = {}; /* the char array type */
558 char *buf = tok_get() + 1;
559 int len = tok_len() - 2;
560 t.bt = 1 | T_MSIGN;
561 a.id = array_add(&t, len + 1);
562 a.flags = T_ARRAY;
563 o_sym(tmp_str(buf, len));
564 ts_push(&a);
565 return;
567 if (tok_grp() == 'a') {
568 struct name unkn = {""};
569 char *name = unkn.name;
570 int n;
571 strcpy(name, tok_iden());
572 /* don't search for labels here */
573 if (!ncexpr && !caseexpr && tok_comes(":"))
574 return;
575 if ((n = local_find(name)) != -1) {
576 struct name *l = &locals[n];
577 o_local(l->addr);
578 ts_push_addr(&l->type);
579 return;
581 if ((n = global_find(name)) != -1) {
582 struct name *g = &globals[n];
583 o_sym(*g->elfname ? g->elfname : g->name);
584 ts_push_addr(&g->type);
585 return;
587 if (!enum_find(&n, name)) {
588 o_num(n);
589 ts_push_bt(SINT);
590 return;
592 if (!tok_comes("("))
593 err("unknown symbol <%s>\n", name);
594 global_add(&unkn);
595 o_sym(unkn.name);
596 ts_push_bt(ULNG);
597 return;
599 if (!tok_jmp("(")) {
600 struct type t;
601 if (!readtype(&t)) {
602 struct type o;
603 tok_req(")");
604 readpre();
605 ts_pop_de(&o);
606 ts_push(&t);
607 if (!t.ptr || !o.ptr)
608 o_cast(TYPE_BT(&t));
609 } else {
610 readexpr();
611 while (tok_jmp(")")) {
612 tok_req(",");
613 ts_pop(NULL);
614 o_tmpdrop(1);
615 readexpr();
618 return;
622 static void arrayderef(void)
624 struct type t;
625 int sz;
626 ts_pop_de(NULL);
627 ts_pop(&t);
628 if (!(t.flags & T_ARRAY && !t.ptr) && t.addr) {
629 o_tmpswap();
630 o_deref(TYPE_BT(&t));
631 o_tmpswap();
633 array2ptr(&t);
634 t.ptr--;
635 sz = type_totsz(&t);
636 t.addr = 1;
637 if (sz > 1) {
638 o_num(sz);
639 o_bop(O_MUL);
641 o_bop(O_ADD);
642 ts_push(&t);
645 static void inc_post(int op)
647 struct type t = ts[nts - 1];
648 /* pushing the value before inc */
649 o_tmpcopy();
650 ts_de(1);
651 o_tmpswap();
653 /* increment by 1 or pointer size */
654 o_tmpcopy();
655 ts_push(&t);
656 ts_pop_de(&t);
657 o_num(t.ptr > 0 ? type_szde(&t) : 1);
658 o_bop(op);
660 /* assign back */
661 o_assign(TYPE_BT(&t));
662 o_tmpdrop(1);
665 static void readfield(void)
667 struct name *field;
668 struct type t;
669 ts_pop(&t);
670 array2ptr(&t);
671 field = struct_field(t.id, tok_get());
672 if (field->addr) {
673 o_num(field->addr);
674 o_bop(O_ADD);
676 ts_push_addr(&field->type);
679 static struct funcinfo {
680 struct type args[NARGS];
681 struct type ret;
682 int nargs;
683 int varg;
684 /* function and argument names; useful only when defining */
685 char argnames[NARGS][NAMELEN];
686 char name[NAMELEN];
687 } *funcs;
688 static int funcs_n, funcs_sz;
690 static int func_create(struct type *ret, char *name, char argnames[][NAMELEN],
691 struct type *args, int nargs, int varg)
693 struct funcinfo *fi;
694 int i;
695 if (funcs_n >= funcs_sz) {
696 funcs_sz = MAX(128, funcs_sz * 2);
697 funcs = mextend(funcs, funcs_n, funcs_sz, sizeof(funcs[0]));
699 fi = &funcs[funcs_n++];
700 memcpy(&fi->ret, ret, sizeof(*ret));
701 for (i = 0; i < nargs; i++)
702 memcpy(&fi->args[i], &args[i], sizeof(*ret));
703 fi->nargs = nargs;
704 fi->varg = varg;
705 strcpy(fi->name, name ? name : "");
706 for (i = 0; i < nargs; i++)
707 strcpy(fi->argnames[i], argnames[i]);
708 return fi - funcs;
711 static void readcall(void)
713 struct type t;
714 struct funcinfo *fi;
715 int argc = 0;
716 ts_pop(&t);
717 if (t.flags & T_FUNC && t.ptr > 0)
718 o_deref(ULNG);
719 if (!tok_comes(")")) {
720 do {
721 readexpr();
722 ts_pop_de(NULL);
723 argc++;
724 } while (!tok_jmp(","));
726 tok_req(")");
727 fi = t.flags & T_FUNC ? &funcs[t.id] : NULL;
728 o_call(argc, fi ? TYPE_BT(&fi->ret) : SINT);
729 if (fi) {
730 if (TYPE_BT(&fi->ret))
731 o_cast(TYPE_BT(&fi->ret));
732 ts_push(&fi->ret);
733 } else {
734 ts_push_bt(SINT);
738 static void readpost(void)
740 readprimary();
741 while (1) {
742 if (!tok_jmp("[")) {
743 readexpr();
744 tok_req("]");
745 arrayderef();
746 continue;
748 if (!tok_jmp("(")) {
749 readcall();
750 continue;
752 if (!tok_jmp("++")) {
753 inc_post(O_ADD);
754 continue;
756 if (!tok_jmp("--")) {
757 inc_post(O_SUB);
758 continue;
760 if (!tok_jmp(".")) {
761 readfield();
762 continue;
764 if (!tok_jmp("->")) {
765 ts_de(1);
766 readfield();
767 continue;
769 break;
773 static void inc_pre(int op)
775 struct type t;
776 readpre();
777 /* copy the destination */
778 o_tmpcopy();
779 ts_push(&ts[nts - 1]);
780 /* increment by 1 or pointer size */
781 ts_pop_de(&t);
782 o_num(t.ptr > 0 ? type_szde(&t) : 1);
783 o_bop(op);
784 /* assign the result */
785 o_assign(TYPE_BT(&t));
786 ts_de(0);
789 static void readpre(void)
791 struct type t;
792 if (!tok_jmp("&")) {
793 readpre();
794 ts_pop(&t);
795 if (!t.addr)
796 err("cannot use the address\n");
797 t.ptr++;
798 t.addr = 0;
799 ts_push(&t);
800 return;
802 if (!tok_jmp("*")) {
803 readpre();
804 ts_pop(&t);
805 array2ptr(&t);
806 if (!t.ptr)
807 err("dereferencing non-pointer\n");
808 if (t.addr)
809 o_deref(TYPE_BT(&t));
810 t.ptr--;
811 t.addr = 1;
812 ts_push(&t);
813 return;
815 if (!tok_jmp("!")) {
816 readpre();
817 ts_pop_de(NULL);
818 o_uop(O_LNOT);
819 ts_push_bt(SINT);
820 return;
822 if (!tok_jmp("+")) {
823 readpre();
824 ts_de(1);
825 ts_pop(&t);
826 ts_push_bt(bt_uop(TYPE_BT(&t)));
827 return;
829 if (!tok_jmp("-")) {
830 readpre();
831 ts_de(1);
832 ts_pop(&t);
833 o_uop(O_NEG);
834 ts_push_bt(bt_uop(TYPE_BT(&t)));
835 return;
837 if (!tok_jmp("~")) {
838 readpre();
839 ts_de(1);
840 ts_pop(&t);
841 o_uop(O_NOT);
842 ts_push_bt(bt_uop(TYPE_BT(&t)));
843 return;
845 if (!tok_jmp("++")) {
846 inc_pre(O_ADD);
847 return;
849 if (!tok_jmp("--")) {
850 inc_pre(O_SUB);
851 return;
853 if (!tok_jmp("sizeof")) {
854 struct type t;
855 int op = !tok_jmp("(");
856 if (readtype(&t)) {
857 long m = o_mark();
858 if (op)
859 readexpr();
860 else
861 readpre();
862 o_back(m);
863 ts_pop(&t);
864 o_tmpdrop(1);
866 o_num(type_totsz(&t));
867 ts_push_bt(ULNG);
868 if (op)
869 tok_req(")");
870 return;
872 readpost();
875 static void readmul(void)
877 readpre();
878 while (1) {
879 if (!tok_jmp("*")) {
880 readpre();
881 ts_binop(O_MUL);
882 continue;
884 if (!tok_jmp("/")) {
885 readpre();
886 ts_binop(O_DIV);
887 continue;
889 if (!tok_jmp("%")) {
890 readpre();
891 ts_binop(O_MOD);
892 continue;
894 break;
898 static void readadd(void)
900 readmul();
901 while (1) {
902 if (!tok_jmp("+")) {
903 readmul();
904 ts_addop(O_ADD);
905 continue;
907 if (!tok_jmp("-")) {
908 readmul();
909 ts_addop(O_SUB);
910 continue;
912 break;
916 static void shift(int op)
918 struct type t;
919 readadd();
920 ts_pop_de2(NULL, &t);
921 o_bop(O_MK(op, TYPE_BT(&t)));
922 ts_push_bt(bt_uop(TYPE_BT(&t)));
925 static void readshift(void)
927 readadd();
928 while (1) {
929 if (!tok_jmp("<<")) {
930 shift(O_SHL);
931 continue;
933 if (!tok_jmp(">>")) {
934 shift(O_SHR);
935 continue;
937 break;
941 static void cmp(int op)
943 struct type t1, t2;
944 int bt;
945 readshift();
946 ts_pop_de2(&t1, &t2);
947 bt = bt_op(TYPE_BT(&t1), TYPE_BT(&t2));
948 o_bop(O_MK(op, bt));
949 ts_push_bt(SINT);
952 static void readcmp(void)
954 readshift();
955 while (1) {
956 if (!tok_jmp("<")) {
957 cmp(O_LT);
958 continue;
960 if (!tok_jmp(">")) {
961 cmp(O_GT);
962 continue;
964 if (!tok_jmp("<=")) {
965 cmp(O_LE);
966 continue;
968 if (!tok_jmp(">=")) {
969 cmp(O_GE);
970 continue;
972 break;
976 static void eq(int op)
978 readcmp();
979 ts_pop_de2(NULL, NULL);
980 o_bop(op);
981 ts_push_bt(SINT);
984 static void readeq(void)
986 readcmp();
987 while (1) {
988 if (!tok_jmp("==")) {
989 eq(O_EQ);
990 continue;
992 if (!tok_jmp("!=")) {
993 eq(O_NE);
994 continue;
996 break;
1000 static void readbitand(void)
1002 readeq();
1003 while (!tok_jmp("&")) {
1004 readeq();
1005 ts_binop(O_AND);
1009 static void readxor(void)
1011 readbitand();
1012 while (!tok_jmp("^")) {
1013 readbitand();
1014 ts_binop(O_XOR);
1018 static void readbitor(void)
1020 readxor();
1021 while (!tok_jmp("|")) {
1022 readxor();
1023 ts_binop(O_OR);
1027 static void savelocal(long val, int bt)
1029 o_local(val);
1030 o_tmpswap();
1031 o_assign(bt);
1032 o_tmpdrop(1);
1035 static void loadlocal(long val, int bt)
1037 o_local(val);
1038 o_deref(bt);
1039 o_rmlocal(val, bt);
1042 static void readand(void)
1044 int l_out, l_fail;
1045 long val;
1046 readbitor();
1047 if (!tok_comes("&&"))
1048 return;
1049 val = o_mklocal(UINT);
1050 l_out = LABEL();
1051 l_fail = LABEL();
1052 ts_pop_de(NULL);
1053 o_jz(l_fail);
1054 while (!tok_jmp("&&")) {
1055 readbitor();
1056 ts_pop_de(NULL);
1057 o_jz(l_fail);
1059 o_num(1);
1060 savelocal(val, UINT);
1061 o_jmp(l_out);
1062 o_label(l_fail);
1063 o_num(0);
1064 savelocal(val, UINT);
1065 o_label(l_out);
1066 loadlocal(val, SINT);
1067 ts_push_bt(SINT);
1070 static void reador(void)
1072 int l_pass, l_end;
1073 long val;
1074 readand();
1075 if (!tok_comes("||"))
1076 return;
1077 val = o_mklocal(UINT);
1078 l_pass = LABEL();
1079 l_end = LABEL();
1080 ts_pop_de(NULL);
1081 o_uop(O_LNOT);
1082 o_jz(l_pass);
1083 while (!tok_jmp("||")) {
1084 readand();
1085 ts_pop_de(NULL);
1086 o_uop(O_LNOT);
1087 o_jz(l_pass);
1089 o_num(0);
1090 savelocal(val, SINT);
1091 o_jmp(l_end);
1092 o_label(l_pass);
1093 o_num(1);
1094 savelocal(val, SINT);
1095 o_label(l_end);
1096 loadlocal(val, SINT);
1097 ts_push_bt(SINT);
1100 static void readcexpr(void);
1102 static int readcexpr_const(void)
1104 long c, m = 0;
1105 if (o_popnum(&c))
1106 return -1;
1107 if (!c)
1108 m = o_mark();
1109 readcexpr();
1110 /* both branches yield the same type; so ignore the first */
1111 ts_pop_de(NULL);
1112 tok_req(":");
1113 if (!c) {
1114 o_back(m);
1115 o_tmpdrop(1);
1117 if (c)
1118 m = o_mark();
1119 readcexpr();
1120 /* making sure t->addr == 0 on both branches */
1121 ts_de(1);
1122 if (c) {
1123 o_back(m);
1124 o_tmpdrop(1);
1126 return 0;
1129 static void readcexpr(void)
1131 reador();
1132 if (tok_jmp("?"))
1133 return;
1134 ncexpr++;
1135 ts_pop_de(NULL);
1136 if (readcexpr_const()) {
1137 long val = 0;
1138 int l_fail = LABEL();
1139 int l_end = LABEL();
1140 struct type ret;
1141 o_jz(l_fail);
1142 readcexpr();
1143 /* both branches yield the same type; so ignore the first */
1144 ts_pop_de(&ret);
1145 if (!TYPE_VOID(&ret)) {
1146 val = o_mklocal(ULNG);
1147 savelocal(val, ULNG);
1149 o_jmp(l_end);
1151 tok_req(":");
1152 o_label(l_fail);
1153 readcexpr();
1154 /* making sure t->addr == 0 on both branches */
1155 ts_de(1);
1156 if (!TYPE_VOID(&ret)) {
1157 savelocal(val, ULNG);
1159 o_label(l_end);
1160 if (!TYPE_VOID(&ret)) {
1161 loadlocal(val, ULNG);
1164 ncexpr--;
1167 static void opassign(int op, int ptrop)
1169 struct type t = ts[nts - 1];
1170 o_tmpcopy();
1171 ts_push(&t);
1172 readexpr();
1173 if (op == O_ADD || op == O_SUB)
1174 ts_addop(op);
1175 else
1176 ts_binop(op);
1177 o_assign(TYPE_BT(&ts[nts - 2]));
1178 ts_pop(NULL);
1179 ts_de(0);
1182 static void doassign(void)
1184 struct type t = ts[nts - 1];
1185 if (!t.ptr && t.flags & T_STRUCT) {
1186 ts_pop(NULL);
1187 o_num(type_totsz(&t));
1188 o_memcpy();
1189 } else {
1190 ts_pop_de(NULL);
1191 o_assign(TYPE_BT(&ts[nts - 1]));
1192 ts_de(0);
1196 static void readexpr(void)
1198 readcexpr();
1199 if (!tok_jmp("=")) {
1200 readexpr();
1201 doassign();
1202 return;
1204 if (!tok_jmp("+=")) {
1205 opassign(O_ADD, 1);
1206 return;
1208 if (!tok_jmp("-=")) {
1209 opassign(O_SUB, 1);
1210 return;
1212 if (!tok_jmp("*=")) {
1213 opassign(O_MUL, 0);
1214 return;
1216 if (!tok_jmp("/=")) {
1217 opassign(O_DIV, 0);
1218 return;
1220 if (!tok_jmp("%=")) {
1221 opassign(O_MOD, 0);
1222 return;
1224 if (!tok_jmp("<<=")) {
1225 opassign(O_SHL, 0);
1226 return;
1228 if (!tok_jmp(">>=")) {
1229 opassign(O_SHR, 0);
1230 return;
1232 if (!tok_jmp("&=")) {
1233 opassign(O_AND, 0);
1234 return;
1236 if (!tok_jmp("|=")) {
1237 opassign(O_OR, 0);
1238 return;
1240 if (!tok_jmp("^=")) {
1241 opassign(O_XOR, 0);
1242 return;
1246 static void readestmt(void)
1248 do {
1249 o_tmpdrop(-1);
1250 nts = 0;
1251 readexpr();
1252 } while (!tok_jmp(","));
1255 #define F_GLOBAL(flags) (!((flags) & F_STATIC))
1257 static void globalinit(void *obj, int off, struct type *t)
1259 struct name *name = obj;
1260 char *elfname = *name->elfname ? name->elfname : name->name;
1261 if (t->flags & T_ARRAY && tok_grp() == '"') {
1262 struct type *t_de = &arrays[t->id].type;
1263 if (!t_de->ptr && !t_de->flags && TYPE_SZ(t_de) == 1) {
1264 char *buf = tok_get() + 1;
1265 int len = tok_len() - 2;
1266 buf[len] = '\0';
1267 o_dscpy(name->addr + off, buf, len + 1);
1268 return;
1271 readexpr();
1272 ts_de(1);
1273 o_dsset(elfname, off, TYPE_BT(t));
1274 ts_pop(NULL);
1277 static void readfunc(struct name *name, int flags);
1279 static void globaldef(long data, struct name *name, unsigned flags)
1281 struct type *t = &name->type;
1282 char *elfname = *name->elfname ? name->elfname : name->name;
1283 int sz;
1284 if (t->flags & T_ARRAY && !t->ptr && !arrays[t->id].n)
1285 if (~flags & F_EXTERN)
1286 arrays[t->id].n = initsize();
1287 sz = type_totsz(t);
1288 if (!(flags & F_EXTERN) && (!(t->flags & T_FUNC) || t->ptr)) {
1289 if (tok_comes("="))
1290 name->addr = o_dsnew(elfname, sz, F_GLOBAL(flags));
1291 else
1292 o_bsnew(elfname, sz, F_GLOBAL(flags));
1294 global_add(name);
1295 if (!tok_jmp("="))
1296 initexpr(t, 0, name, globalinit);
1297 if (tok_comes("{") && name->type.flags & T_FUNC)
1298 readfunc(name, flags);
1301 /* generate the address of local + off */
1302 static void o_localoff(long addr, int off)
1304 o_local(addr);
1305 if (off) {
1306 o_num(off);
1307 o_bop(O_ADD);
1311 static void localinit(void *obj, int off, struct type *t)
1313 long addr = *(long *) obj;
1314 if (t->flags & T_ARRAY && tok_grp() == '"') {
1315 struct type *t_de = &arrays[t->id].type;
1316 if (!t_de->ptr && !t_de->flags && TYPE_SZ(t_de) == 1) {
1317 char *buf = tok_get() + 1;
1318 int len = tok_len() - 2;
1319 o_localoff(addr, off);
1320 o_sym(tmp_str(buf, len));
1321 o_num(len + 1);
1322 o_memcpy();
1323 o_tmpdrop(1);
1324 return;
1327 o_localoff(addr, off);
1328 ts_push(t);
1329 readexpr();
1330 doassign();
1331 ts_pop(NULL);
1332 o_tmpdrop(1);
1335 /* current function name */
1336 static char func_name[NAMELEN];
1338 static void localdef(long data, struct name *name, unsigned flags)
1340 struct type *t = &name->type;
1341 if ((flags & F_EXTERN) || ((t->flags & T_FUNC) && !t->ptr)) {
1342 global_add(name);
1343 return;
1345 if (flags & F_STATIC) {
1346 sprintf(name->elfname, "__neatcc.%s.%s", func_name, name->name);
1347 globaldef(data, name, flags);
1348 return;
1350 if (t->flags & T_ARRAY && !t->ptr && !arrays[t->id].n)
1351 arrays[t->id].n = initsize();
1352 name->addr = o_mklocal(type_totsz(&name->type));
1353 local_add(name);
1354 if (!tok_jmp("=")) {
1355 /* this is not necessary for "struct x = y" */
1356 if (t->flags & (T_ARRAY | T_STRUCT) && !t->ptr) {
1357 o_local(name->addr);
1358 o_num(0);
1359 o_num(type_totsz(t));
1360 o_memset();
1361 o_tmpdrop(1);
1363 initexpr(t, 0, &name->addr, localinit);
1367 static void typedefdef(long data, struct name *name, unsigned flags)
1369 typedef_add(name->name, &name->type);
1372 static void readstmt(void);
1374 static void readswitch(void)
1376 int o_break = l_break;
1377 long val_addr = o_mklocal(ULNG);
1378 struct type t;
1379 int ncases = 0; /* number of case labels */
1380 int l_failed = LABEL(); /* address of last failed jmp */
1381 int l_matched = LABEL(); /* address of last walk through jmp */
1382 int l_default = 0; /* default case label */
1383 l_break = LABEL();
1384 tok_req("(");
1385 readexpr();
1386 ts_pop_de(&t);
1387 o_local(val_addr);
1388 o_tmpswap();
1389 o_assign(TYPE_BT(&t));
1390 o_tmpdrop(1);
1391 tok_req(")");
1392 tok_req("{");
1393 while (tok_jmp("}")) {
1394 if (!tok_comes("case") && !tok_comes("default")) {
1395 readstmt();
1396 continue;
1398 if (ncases)
1399 o_jmp(l_matched);
1400 if (!strcmp("case", tok_get())) {
1401 o_label(l_failed);
1402 l_failed = LABEL();
1403 caseexpr = 1;
1404 readexpr();
1405 ts_pop_de(NULL);
1406 caseexpr = 0;
1407 o_local(val_addr);
1408 o_deref(TYPE_BT(&t));
1409 o_bop(O_EQ);
1410 o_jz(l_failed);
1411 o_tmpdrop(1);
1412 } else {
1413 if (!ncases)
1414 o_jmp(l_failed);
1415 l_default = LABEL();
1416 o_label(l_default);
1418 tok_req(":");
1419 o_label(l_matched);
1420 l_matched = LABEL();
1421 ncases++;
1423 o_rmlocal(val_addr, ULNG);
1424 o_jmp(l_break);
1425 o_label(l_failed);
1426 if (l_default)
1427 o_jmp(l_default);
1428 o_label(l_break);
1429 l_break = o_break;
1432 static char (*label_name)[NAMELEN];
1433 static int *label_ids;
1434 static int label_n, label_sz;
1436 static int label_id(char *name)
1438 int i;
1439 if (label_n >= label_sz) {
1440 label_sz = MAX(128, label_sz * 2);
1441 label_name = mextend(label_name, label_n, label_sz,
1442 sizeof(label_name[0]));
1443 label_ids = mextend(label_ids, label_n, label_sz,
1444 sizeof(label_ids[0]));
1446 for (i = label_n - 1; i >= 0; --i)
1447 if (!strcmp(label_name[i], name))
1448 return label_ids[i];
1449 strcpy(label_name[label_n], name);
1450 label_ids[label_n] = LABEL();
1451 return label_ids[label_n++];
1454 static void readstmt(void)
1456 o_tmpdrop(-1);
1457 nts = 0;
1458 if (!tok_jmp("{")) {
1459 int _nlocals = locals_n;
1460 int _nglobals = globals_n;
1461 int _nenums = enums_n;
1462 int _ntypedefs = typedefs_n;
1463 int _nstructs = structs_n;
1464 int _nfuncs = funcs_n;
1465 int _narrays = arrays_n;
1466 while (tok_jmp("}"))
1467 readstmt();
1468 locals_n = _nlocals;
1469 enums_n = _nenums;
1470 typedefs_n = _ntypedefs;
1471 structs_n = _nstructs;
1472 funcs_n = _nfuncs;
1473 arrays_n = _narrays;
1474 globals_n = _nglobals;
1475 return;
1477 if (!readdefs(localdef, 0)) {
1478 tok_req(";");
1479 return;
1481 if (!tok_jmp("typedef")) {
1482 readdefs(typedefdef, 0);
1483 tok_req(";");
1484 return;
1486 if (!tok_jmp("if")) {
1487 int l_fail = LABEL();
1488 int l_end = LABEL();
1489 tok_req("(");
1490 readestmt();
1491 tok_req(")");
1492 ts_pop_de(NULL);
1493 o_jz(l_fail);
1494 readstmt();
1495 if (!tok_jmp("else")) {
1496 o_jmp(l_end);
1497 o_label(l_fail);
1498 readstmt();
1499 o_label(l_end);
1500 } else {
1501 o_label(l_fail);
1503 return;
1505 if (!tok_jmp("while")) {
1506 int o_break = l_break;
1507 int o_cont = l_cont;
1508 l_break = LABEL();
1509 l_cont = LABEL();
1510 o_label(l_cont);
1511 tok_req("(");
1512 readestmt();
1513 tok_req(")");
1514 ts_pop_de(NULL);
1515 o_jz(l_break);
1516 readstmt();
1517 o_jmp(l_cont);
1518 o_label(l_break);
1519 l_break = o_break;
1520 l_cont = o_cont;
1521 return;
1523 if (!tok_jmp("do")) {
1524 int o_break = l_break;
1525 int o_cont = l_cont;
1526 int l_beg = LABEL();
1527 l_break = LABEL();
1528 l_cont = LABEL();
1529 o_label(l_beg);
1530 readstmt();
1531 tok_req("while");
1532 tok_req("(");
1533 o_label(l_cont);
1534 readexpr();
1535 ts_pop_de(NULL);
1536 o_uop(O_LNOT);
1537 o_jz(l_beg);
1538 tok_req(")");
1539 o_label(l_break);
1540 tok_req(";");
1541 l_break = o_break;
1542 l_cont = o_cont;
1543 return;
1545 if (!tok_jmp("for")) {
1546 int o_break = l_break;
1547 int o_cont = l_cont;
1548 int l_check = LABEL(); /* for condition label */
1549 int l_body = LABEL(); /* for block label */
1550 l_cont = LABEL();
1551 l_break = LABEL();
1552 tok_req("(");
1553 if (!tok_comes(";"))
1554 readestmt();
1555 tok_req(";");
1556 o_label(l_check);
1557 if (!tok_comes(";")) {
1558 readestmt();
1559 ts_pop_de(NULL);
1560 o_jz(l_break);
1562 tok_req(";");
1563 o_jmp(l_body);
1564 o_label(l_cont);
1565 if (!tok_comes(")"))
1566 readestmt();
1567 tok_req(")");
1568 o_jmp(l_check);
1569 o_label(l_body);
1570 readstmt();
1571 o_jmp(l_cont);
1572 o_label(l_break);
1573 l_break = o_break;
1574 l_cont = o_cont;
1575 return;
1577 if (!tok_jmp("switch")) {
1578 readswitch();
1579 return;
1581 if (!tok_jmp("return")) {
1582 int ret = !tok_comes(";");
1583 if (ret) {
1584 readexpr();
1585 ts_pop_de(NULL);
1587 tok_req(";");
1588 o_ret(ret);
1589 return;
1591 if (!tok_jmp("break")) {
1592 tok_req(";");
1593 o_jmp(l_break);
1594 return;
1596 if (!tok_jmp("continue")) {
1597 tok_req(";");
1598 o_jmp(l_cont);
1599 return;
1601 if (!tok_jmp("goto")) {
1602 o_jmp(label_id(tok_get()));
1603 tok_req(";");
1604 return;
1606 readestmt();
1607 /* labels */
1608 if (!tok_jmp(":")) {
1609 o_label(label_id(tok_previden));
1610 return;
1612 tok_req(";");
1615 static void readfunc(struct name *name, int flags)
1617 struct funcinfo *fi = &funcs[name->type.id];
1618 int i;
1619 strcpy(func_name, fi->name);
1620 o_func_beg(func_name, fi->nargs, F_GLOBAL(flags), fi->varg);
1621 for (i = 0; i < fi->nargs; i++) {
1622 struct name arg = {"", "", fi->args[i], o_arg2loc(i)};
1623 strcpy(arg.name, fi->argnames[i]);
1624 local_add(&arg);
1626 label = 0;
1627 label_n = 0;
1628 readstmt();
1629 o_func_end();
1630 func_name[0] = '\0';
1631 locals_n = 0;
1634 static void readdecl(void)
1636 if (!tok_jmp("typedef")) {
1637 readdefs(typedefdef, 0);
1638 tok_req(";");
1639 return;
1641 readdefs_int(globaldef, 0);
1642 tok_jmp(";");
1645 static void parse(void)
1647 while (tok_jmp(""))
1648 readdecl();
1651 static void compat_macros(void)
1653 cpp_define("__STDC__", "");
1654 cpp_define("__linux__", "");
1655 cpp_define(I_ARCH, "");
1656 cpp_define("__neatcc__", "");
1658 /* ignored keywords */
1659 cpp_define("const", "");
1660 cpp_define("register", "");
1661 cpp_define("volatile", "");
1662 cpp_define("inline", "");
1663 cpp_define("restrict", "");
1664 cpp_define("__inline__", "");
1665 cpp_define("__restrict__", "");
1666 cpp_define("__attribute__(x)", "");
1667 cpp_define("__builtin_va_list__", "long");
1670 static int ncc_opt = 2;
1672 /* return one if the given optimization level is enabled */
1673 int opt(int level)
1675 return level <= ncc_opt;
1678 int main(int argc, char *argv[])
1680 char obj[128] = "";
1681 int ofd = 1;
1682 int cpp = 0;
1683 int i;
1684 compat_macros();
1685 for (i = 1; i < argc && argv[i][0] == '-'; i++) {
1686 if (argv[i][1] == 'I')
1687 cpp_path(argv[i][2] ? argv[i] + 2 : argv[++i]);
1688 if (argv[i][1] == 'O')
1689 ncc_opt = argv[i][2] ? atoi(argv[i] + 2) : 2;
1690 if (argv[i][1] == 'E')
1691 cpp = 1;
1692 if (argv[i][1] == 'D') {
1693 char *name = argv[i] + 2;
1694 char *def = "";
1695 char *eq = strchr(name, '=');
1696 if (eq) {
1697 *eq = '\0';
1698 def = eq + 1;
1700 cpp_define(name, def);
1702 if (argv[i][1] == 'o')
1703 strcpy(obj, argv[i][2] ? argv[i] + 2 : argv[++i]);
1704 if (argv[i][1] == 'h') {
1705 printf("Usage: %s [options] source\n", argv[0]);
1706 printf("\n");
1707 printf("Options:\n");
1708 printf(" -I dir \tspecify a header directory\n");
1709 printf(" -o out \tspecify output file name\n");
1710 printf(" -E \tpreprocess only\n");
1711 printf(" -Dname=val \tdefine a macro\n");
1712 printf(" -On \toptimize (-O0 to disable)\n");
1713 return 0;
1716 if (i == argc)
1717 die("neatcc: no file given\n");
1718 if (cpp_init(argv[i]))
1719 die("neatcc: cannot open <%s>\n", argv[i]);
1720 if (cpp) {
1721 long clen;
1722 char *cbuf;
1723 if (*obj)
1724 ofd = open(obj, O_WRONLY | O_TRUNC | O_CREAT, 0600);
1725 while (!cpp_read(&cbuf, &clen))
1726 write(ofd, cbuf, clen);
1727 if (*obj)
1728 close(ofd);
1729 return 0;
1731 out_init(0);
1732 parse();
1733 if (!*obj) {
1734 char *cp = strrchr(argv[i], '/');
1735 strcpy(obj, cp ? cp + 1 : argv[i]);
1736 obj[strlen(obj) - 1] = 'o';
1738 free(locals);
1739 free(globals);
1740 free(label_name);
1741 free(label_ids);
1742 free(funcs);
1743 free(typedefs);
1744 free(structs);
1745 free(arrays);
1746 tok_done();
1747 ofd = open(obj, O_WRONLY | O_TRUNC | O_CREAT, 0600);
1748 o_write(ofd);
1749 close(ofd);
1750 return 0;
1754 /* parsing function and variable declarations */
1756 /* read the base type of a variable */
1757 static int basetype(struct type *type, unsigned *flags)
1759 int sign = 1;
1760 int size = UINT;
1761 int done = 0;
1762 int i = 0;
1763 int isunion;
1764 char name[NAMELEN] = "";
1765 *flags = 0;
1766 type->flags = 0;
1767 type->ptr = 0;
1768 type->addr = 0;
1769 while (!done) {
1770 if (!tok_jmp("static")) {
1771 *flags |= F_STATIC;
1772 } else if (!tok_jmp("extern")) {
1773 *flags |= F_EXTERN;
1774 } else if (!tok_jmp("void")) {
1775 sign = 0;
1776 size = 0;
1777 done = 1;
1778 } else if (!tok_jmp("int")) {
1779 done = 1;
1780 } else if (!tok_jmp("char")) {
1781 size = UCHR;
1782 done = 1;
1783 } else if (!tok_jmp("short")) {
1784 size = USHT;
1785 } else if (!tok_jmp("long")) {
1786 size = ULNG;
1787 } else if (!tok_jmp("signed")) {
1788 sign = 1;
1789 } else if (!tok_jmp("unsigned")) {
1790 sign = 0;
1791 } else if (tok_comes("union") || tok_comes("struct")) {
1792 isunion = !strcmp("union", tok_get());
1793 if (tok_grp() == 'a')
1794 strcpy(name, tok_get());
1795 if (tok_comes("{"))
1796 type->id = struct_create(name, isunion);
1797 else
1798 type->id = struct_find(name, isunion);
1799 type->flags |= T_STRUCT;
1800 type->bt = ULNG;
1801 return 0;
1802 } else if (!tok_jmp("enum")) {
1803 if (tok_grp() == 'a')
1804 tok_get();
1805 if (tok_comes("{"))
1806 enum_create();
1807 type->bt = SINT;
1808 return 0;
1809 } else {
1810 if (tok_grp() == 'a') {
1811 int id = typedef_find(tok_see());
1812 if (id != -1) {
1813 tok_get();
1814 memcpy(type, &typedefs[id].type,
1815 sizeof(*type));
1816 return 0;
1819 if (!i)
1820 return 1;
1821 done = 1;
1822 continue;
1824 i++;
1826 type->bt = size | (sign ? T_MSIGN : 0);
1827 return 0;
1830 static void readptrs(struct type *type)
1832 while (!tok_jmp("*")) {
1833 type->ptr++;
1834 if (!type->bt)
1835 type->bt = 1;
1839 /* read function arguments */
1840 static int readargs(struct type *args, char argnames[][NAMELEN], int *varg)
1842 int nargs = 0;
1843 tok_req("(");
1844 *varg = 0;
1845 while (!tok_comes(")")) {
1846 if (!tok_jmp("...")) {
1847 *varg = 1;
1848 break;
1850 if (readname(&args[nargs], argnames[nargs], NULL)) {
1851 /* argument has no type, assume int */
1852 memset(&args[nargs], 0, sizeof(struct type));
1853 args[nargs].bt = SINT;
1854 strcpy(argnames[nargs], tok_get());
1856 /* argument arrays are pointers */
1857 array2ptr(&args[nargs]);
1858 nargs++;
1859 if (tok_jmp(","))
1860 break;
1862 tok_req(")");
1863 /* void argument */
1864 if (nargs == 1 && !TYPE_BT(&args[0]))
1865 return 0;
1866 return nargs;
1869 /* read K&R function arguments */
1870 static void krdef(long data, struct name *name, unsigned flags)
1872 struct funcinfo *fi = &funcs[data];
1873 int i;
1874 for (i = 0; i < fi->nargs; i++)
1875 if (!strcmp(fi->argnames[i], name->name))
1876 memcpy(&fi->args[i], &name->type, sizeof(name->type));
1880 * readarrays() parses array specifiers when reading a definition in
1881 * readname(). The "type" parameter contains the type contained in the
1882 * inner array; for instance, type in "int *a[10][20]" would be an int
1883 * pointer. When returning, the "type" parameter is changed to point
1884 * to the final array. The function returns a pointer to the type in
1885 * the inner array; this is useful when the type is not complete yet,
1886 * like when creating an array of function pointers as in
1887 * "int (*f[10])(int)". If there is no array brackets, NULL is returned.
1889 static struct type *readarrays(struct type *type)
1891 long arsz[16];
1892 struct type *inner = NULL;
1893 int nar = 0;
1894 int i;
1895 while (!tok_jmp("[")) {
1896 long n = 0;
1897 if (tok_jmp("]")) {
1898 readexpr();
1899 ts_pop_de(NULL);
1900 if (o_popnum(&n))
1901 err("const expr expected\n");
1902 tok_req("]");
1904 arsz[nar++] = n;
1906 for (i = nar - 1; i >= 0; i--) {
1907 type->id = array_add(type, arsz[i]);
1908 if (!inner)
1909 inner = &arrays[type->id].type;
1910 type->flags = T_ARRAY;
1911 type->bt = ULNG;
1912 type->ptr = 0;
1914 return inner;
1917 static struct type *innertype(struct type *t)
1919 while (t->flags & T_ARRAY && !t->ptr)
1920 t = &arrays[t->id].type;
1921 return t;
1924 static void innertype_modify(struct type *t, struct type *s)
1926 struct type *inner = innertype(t);
1927 int ptr = inner->ptr;
1928 memcpy(inner, s, sizeof(*inner));
1929 inner->ptr = ptr;
1933 * readname() reads a variable definition; the name is copied into
1934 * "name" and the type is copied into "main" argument. The "base"
1935 * argument, if not NULL, indicates the base type of the variable.
1936 * For instance, the base type of "a" and "b" in "int *a, b[10]" is
1937 * "int". If NULL, basetype() is called directly to read the base
1938 * type of the variable. readname() returns zero, only if the
1939 * variable can be read.
1941 static int readname(struct type *main, char *name, struct type *base)
1943 struct type type; /* the main type */
1944 struct type btype; /* type before parenthesis; e.g. "int *" in "int *(*p)[10] */
1945 int paren;
1946 unsigned flags;
1947 if (name)
1948 *name = '\0';
1949 if (!base) {
1950 if (basetype(&type, &flags))
1951 return 1;
1952 } else {
1953 type = *base;
1955 readptrs(&type);
1956 paren = !tok_jmp("(");
1957 if (paren) {
1958 btype = type;
1959 readptrs(&type);
1961 if (tok_grp() == 'a' && name)
1962 strcpy(name, tok_get());
1963 readarrays(&type);
1964 if (paren)
1965 tok_req(")");
1966 if (tok_comes("(")) {
1967 struct type args[NARGS];
1968 char argnames[NARGS][NAMELEN];
1969 int varg = 0;
1970 int nargs = readargs(args, argnames, &varg);
1971 struct type rtype = type; /* return type */
1972 struct type ftype = {0}; /* function type */
1973 if (paren)
1974 rtype = btype;
1975 ftype.flags = T_FUNC;
1976 ftype.bt = ULNG;
1977 ftype.id = func_create(&rtype, name, argnames, args, nargs, varg);
1978 if (paren)
1979 innertype_modify(&type, &ftype);
1980 else
1981 type = ftype;
1982 if (!tok_comes(";"))
1983 while (!tok_comes("{") && !readdefs(krdef, type.id))
1984 tok_req(";");
1985 } else {
1986 if (paren && readarrays(&btype))
1987 innertype_modify(&type, &btype);
1989 *main = type;
1990 return 0;
1993 static int readtype(struct type *type)
1995 return readname(type, NULL, NULL);
1999 * readdefs() reads a variable definition statement. The definition
2000 * can appear in different contexts: global variables, function
2001 * local variables, struct fields, and typedefs. For each defined
2002 * variable, def() callback is called with the appropriate name
2003 * struct and flags; the callback should finish parsing the definition
2004 * by possibly reading the initializer expression and saving the name
2005 * struct.
2007 static int readdefs(void (*def)(long data, struct name *name, unsigned flags),
2008 long data)
2010 struct type base;
2011 unsigned base_flags;
2012 if (basetype(&base, &base_flags))
2013 return 1;
2014 if (tok_comes(";") || tok_comes("{"))
2015 return 0;
2016 do {
2017 struct name name = {{""}};
2018 if (readname(&name.type, name.name, &base))
2019 break;
2020 def(data, &name, base_flags);
2021 } while (!tok_jmp(","));
2022 return 0;
2025 /* just like readdefs, but default to int type; for handling K&R functions */
2026 static int readdefs_int(void (*def)(long data, struct name *name, unsigned flags),
2027 long data)
2029 struct type base;
2030 unsigned flags = 0;
2031 int nobase = 0;
2032 if (basetype(&base, &flags)) {
2033 nobase = 1;
2034 if (tok_grp() != 'a')
2035 return 1;
2036 memset(&base, 0, sizeof(base));
2037 base.bt = SINT;
2039 if (!tok_comes(";")) {
2040 do {
2041 struct name name = {{""}};
2042 if (readname(&name.type, name.name, &base))
2043 break;
2044 if (nobase && tok_grp() == 'a')
2045 err("type missing!\n");
2046 def(data, &name, flags);
2047 } while (!tok_jmp(","));
2049 return 0;
2053 /* parsing initializer expressions */
2055 static void jumpbrace(void)
2057 int depth = 0;
2058 while (!tok_comes("}") || depth--)
2059 if (!strcmp("{", tok_get()))
2060 depth++;
2061 tok_req("}");
2064 /* compute the size of the initializer expression */
2065 static int initsize(void)
2067 long addr = tok_addr();
2068 int n = 0;
2069 if (tok_jmp("="))
2070 return 0;
2071 if (tok_grp() == '"') {
2072 tok_get();
2073 n = tok_len() - 2 + 1;
2074 tok_jump(addr);
2075 return n;
2077 tok_req("{");
2078 while (tok_jmp("}")) {
2079 long idx = n;
2080 if (!tok_jmp("[")) {
2081 readexpr();
2082 ts_pop_de(NULL);
2083 o_popnum(&idx);
2084 tok_req("]");
2085 tok_req("=");
2087 if (n < idx + 1)
2088 n = idx + 1;
2089 while (!tok_comes("}") && !tok_comes(","))
2090 if (!strcmp("{", tok_get()))
2091 jumpbrace();
2092 tok_jmp(",");
2094 tok_jump(addr);
2095 return n;
2098 /* read the initializer expression and initialize basic types using set() cb */
2099 static void initexpr(struct type *t, int off, void *obj,
2100 void (*set)(void *obj, int off, struct type *t))
2102 if (tok_jmp("{")) {
2103 set(obj, off, t);
2104 return;
2106 if (!t->ptr && t->flags & T_STRUCT) {
2107 struct structinfo *si = &structs[t->id];
2108 int i;
2109 for (i = 0; i < si->nfields && !tok_comes("}"); i++) {
2110 struct name *field = &si->fields[i];
2111 if (!tok_jmp(".")) {
2112 field = struct_field(t->id, tok_get());
2113 tok_req("=");
2115 initexpr(&field->type, off + field->addr, obj, set);
2116 if (tok_jmp(","))
2117 break;
2119 } else if (t->flags & T_ARRAY) {
2120 struct type t_de = arrays[t->id].type;
2121 int i;
2122 /* handling extra braces as in: char s[] = {"sth"} */
2123 if (TYPE_SZ(&t_de) == 1 && tok_grp() == '"') {
2124 set(obj, off, t);
2125 tok_req("}");
2126 return;
2128 for (i = 0; !tok_comes("}"); i++) {
2129 long idx = i;
2130 struct type it = t_de;
2131 if (!tok_jmp("[")) {
2132 readexpr();
2133 ts_pop_de(NULL);
2134 o_popnum(&idx);
2135 tok_req("]");
2136 tok_req("=");
2138 if (!tok_comes("{") && (tok_grp() != '"' ||
2139 !(it.flags & T_ARRAY)))
2140 it = *innertype(&t_de);
2141 initexpr(&it, off + type_totsz(&it) * idx, obj, set);
2142 if (tok_jmp(","))
2143 break;
2146 tok_req("}");