scc

A fork of https://git.simple-cc.org/scc/ for Qute

git clone https://git.8pit.net/scc.git

  1#define ASLABEL 0
  2
  3#ifdef NDEBUG
  4#define PRCFG(msg)
  5#define PRTREE(msg)
  6#else
  7#define PRCFG(msg) (enadebug ? prcfg(msg) : (void)0)
  8#define PRTREE(msg) (enadebug ? prforest(msg) : (void)0)
  9#endif
 10
 11enum iflags {
 12	BBENTRY =    1,        /* basic block entry */
 13	BBEXIT  =    2,        /* basic block exit */
 14};
 15
 16enum tflags {
 17	SIGNF   =     1 << 0,  /* Signed type */
 18	INTF    =     1 << 1,  /* integer type */
 19	FLOATF  =     1 << 2,  /* float type */
 20	STRF    =     1 << 3,  /* string */
 21	AGGRF   =     1 << 4,  /* aggregate */
 22	FUNF    =     1 << 5,  /* function */
 23	PARF    =     1 << 6,  /* parameter */
 24	INITF   =     1 << 7,  /* initializer flag */
 25	ELLIPS  =     1 << 8,  /* vararg function */
 26	ARRF    =     1 << 9,  /* array flag */
 27	PTRF    =     1 << 10, /* pointer flag */
 28};
 29
 30enum sclass {
 31	SAUTO     = 'A',
 32	SREG      = 'R',
 33	SLABEL    = 'L',
 34	SINDEX    = 'I',
 35	STMP      = 'N',
 36	SGLOB     = 'G',
 37	SEXTRN    = 'X',
 38	SPRIV     = 'Y',
 39	SLOCAL    = 'T',
 40	SMEMB     = 'M',
 41	SCONST    = '#',
 42	STRING    = '"',
 43	SNONE     = 0 /* cc2 relies on SNONE being 0 in nextpc() */
 44};
 45
 46enum types {
 47	ELLIPSIS = 'E',
 48	INT8     = 'C',
 49	INT16    = 'I',
 50	INT32    = 'W',
 51	INT64    = 'Q',
 52	UINT8    = 'K',
 53	UINT16   = 'N',
 54	UINT32   = 'Z',
 55	UINT64   = 'O',
 56	POINTER  = 'P',
 57	FUNCTION = 'F',
 58	VECTOR   = 'V',
 59	UNION    = 'U',
 60	STRUCT   = 'S',
 61	BOOL     = 'B',
 62	FLOAT    = 'J',
 63	DOUBLE   = 'D',
 64	LDOUBLE  = 'H',
 65	VOID     = '0'
 66};
 67
 68enum op {
 69	/* kind of operand */
 70	/* operands */
 71	OMEM     = 'M',
 72	OINDEX   = 'I',
 73	OTMP     = 'N',
 74	OAUTO    = 'A',
 75	OREG     = 'R',
 76	OMREG    = 'G',
 77	OCONST   = '#',
 78	OSTRING  = '"',
 79	OLOAD    = 'D',
 80	OLABEL   = 'L',
 81	OADD     = '+',
 82	OSUB     = '-',
 83	OMUL     = '*',
 84	OMOD     = '%',
 85	ODIV     = '/',
 86	OSHL     = 'l',
 87	OSHR     = 'r',
 88	OLT      = '<',
 89	OGT      = '>',
 90	OLE      = '[',
 91	OGE      = ']',
 92	OEQ      = '=',
 93	ONE      = '!',
 94	OBAND    = '&',
 95	OBOR     = '|',
 96	OBXOR    = '^',
 97	OCPL     = '~',
 98	OASSIG   = ':',
 99	OSNEG    = '_',
100	OCALL    = 'c',
101	OCALLE   = 'z',
102	OPAR     = 'p',
103	OFIELD   = '.',
104	OCOMMA   = ',',
105	OASK     = '?',
106	OCOLON   = ' ',
107	OADDR    = '\'',
108	OAND     = 'a',
109	OOR      = 'o',
110	ONEG     = 'n',
111	OPTR     = '@',
112	OCAST    = 'g',
113	OINC     = 'i',
114	ODEC     = 'd',
115	OBUILTIN = 'm',
116	/*statements */
117	ONOP     = 'q',
118	OJMP     = 'j',
119	OBRANCH  = 'y',
120	ORET     = 'h',
121	OBLOOP   = 'b',
122	OELOOP   = 'e',
123	OCASE    = 'v',
124	ODEFAULT = 'f',
125	OBSWITCH = 's',
126	OESWITCH = 't',
127	OBFUN    = 'x',
128	OEFUN    = 'k',
129};
130
131enum builtins {
132	BVA_START = 's',
133	BVA_END   = 'e',
134	BVA_ARG   = 'a',
135	BVA_COPY  = 'c',
136};
137
138enum nerrors {
139	EEOFFUN,       /* EOF while parsing function */
140	ENLABEL,       /* label without statement */
141	EIDOVER,       /* identifier overflow */
142	EOUTPAR,       /* out pf params */
143	ESYNTAX,       /* syntax error */
144	ESTACKA,       /* stack unaligned */
145	ESTACKO,       /* stack overflow */
146	ESTACKU,       /* stack underflow */
147	ELNLINE,       /* line too long */
148	ELNBLNE,       /* line without new line */
149	EFERROR,       /* error reading from file:%s */
150	EBADID,        /* incorrect symbol id */
151	EWTACKO,       /* switch stack overflow */
152	EWTACKU,       /* switch stack underflow */
153	ENOSWTC,       /* Out of switch statement */
154	EBBUILT,       /* Unknown builtin */
155	EOVERFL,       /* Numerical overflow */
156	EBAFFUN,       /* Function body not finished */
157	ENUMERR
158};
159
160typedef struct node Node;
161typedef struct type Type;
162typedef struct symbol Symbol;
163typedef struct addr Addr;
164typedef struct inst Inst;
165typedef struct block Block;
166typedef struct swtch Swtch;
167typedef struct mach Mach;
168
169struct mach {
170	int swtchif;
171};
172
173struct swtch {
174	int nr;
175	long long min, max;
176	Node *bswtch;
177	Node *eswtch;
178	Node **cases;
179	Node *defnode;
180
181	Swtch *next;
182};
183
184struct type {
185	unsigned long size;
186	unsigned align;
187	unsigned short id;
188	unsigned short flags;
189};
190
191struct symbol {
192	Type type;
193	Type rtype;
194	unsigned short id;
195	unsigned short numid;
196	int refcnt;
197	char *name;
198	char kind;
199	union {
200		long off;
201		Node *stmt;
202		Inst *inst;
203	} u;
204	Symbol *next, *prev;
205	Symbol *h_next;
206};
207
208struct node {
209	char op;
210	Type type;
211	int complex;
212	int address;
213	unsigned flags;
214	union {
215		unsigned long long i;
216		char *s;
217		Symbol *sym;
218		Swtch *swtch;
219		int reg;
220		int subop;
221		long off;
222	} u;
223	Symbol *label;
224	Block *bb;
225	Node *left, *right;
226	Node *next, *prev;
227};
228
229struct block {
230	int id;
231	int printed, visited;
232	Node *entryp, *exitp;
233	Block *btrue, *bfalse;
234	Swtch *swtch;
235	Block *next;
236};
237
238struct addr {
239	char kind;
240	union {
241		int reg;
242		unsigned long long i;
243		Symbol *sym;
244		long off;
245	} u;
246};
247
248struct inst {
249	unsigned char op;
250	unsigned char flags;
251	Symbol *label;
252	Inst *next, *prev;
253	Addr from1, from2, to;
254};
255
256/* main.c */
257void error(unsigned nerror, ...);
258
259/* parse.c */
260void parse(void);
261
262/* cgen.c */
263void genaddr(void);
264void genasm(void);
265Node *tsethi(Node *);
266
267/* peep.c */
268void peephole(void);
269
270/* code.c */
271void data(Node *np);
272void writeout(void), endinit(void);
273void code(int op, Node *to, Node *from1, Node *from2);
274void defvar(Symbol *), defpar(Symbol *), defglobal(Symbol *);
275void setlabel(Symbol *);
276Node *label2node(Node *np, Symbol *sym);
277Node *constnode(Node *np, unsigned long long n, Type *tp);
278Node *tmpnode(Type *, Symbol *);
279Node *idxnode(Node *, long);
280void delcode(void);
281Symbol *newlabel(void);
282void pprint(char *s);
283void deftype(Type *);
284Node *labelstmt(Node *, Symbol *);
285Node *savelabel(void);
286
287/* node.c */
288void newfun(Symbol *, Node *);
289void apply(Node *(*fun)(Node *));
290void cleannodes(void);
291void delnode(Node *np);
292void deltree(Node *np);
293void prtree(Node *np), prforest(char *msg);
294Node *node(int op);
295Node *addstmt(Node *);
296Node *delstmt(Node *);
297Node *insstmt(Node *, Node *);
298Node *prestmt(Node *);
299void delrange(Node *, Node *);
300Node *unlinkstmt(Node *);
301
302/* symbol.c */
303#define TMPSYM  0
304Symbol *getsym(unsigned id);
305void popctx(void);
306void pushctx(void);
307void freesym(Symbol *sym);
308
309/* cfg.c */
310void gencfg(void);
311void cleancfg(void);
312Node *sethi(Node *);
313
314/* swtch.c */
315void cleanswtch(void);
316Swtch *newswtch(Swtch *);
317Node *swtch(Node *);
318Node *swtchdefault(Swtch *);
319
320/* globals */
321extern Symbol *curfun;
322extern Symbol *locals;
323extern Inst *pc, *prog;
324extern Node *laststmt;
325extern Mach mach;
326
327/* target */
328extern Type int8type, int16type, int32type, int64type,
329            uint8type, uint16type, uint32type, uint64type,
330            float32type, float64type, float80type,
331            booltype,
332            ptrtype,
333            voidtype,
334            arg_type;