1 /*        Id: macdefs.h,v 1.93 2015/11/24 17:35:11 ragge Exp          */
2 /*        $NetBSD: macdefs.h,v 1.1.1.6 2016/02/09 20:28:16 plunky Exp $         */
3 /*
4  * Copyright (c) 2003 Anders Magnusson (ragge@ludd.luth.se).
5  * All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  * 1. Redistributions of source code must retain the above copyright
11  *    notice, this list of conditions and the following disclaimer.
12  * 2. Redistributions in binary form must reproduce the above copyright
13  *    notice, this list of conditions and the following disclaimer in the
14  *    documentation and/or other materials provided with the distribution.
15  * 3. The name of the author may not be used to endorse or promote products
16  *    derived from this software without specific prior written permission
17  *
18  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
19  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
20  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
21  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
22  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
23  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
24  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
25  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
26  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
27  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28  */
29 
30 /*
31  * Machine-dependent defines for both passes.
32  */
33 
34 /*
35  * Convert (multi-)character constant to integer.
36  */
37 #define makecc(val,i)         lastcon = (lastcon<<8)|((val<<24)>>24);
38 
39 #define ARGINIT               64        /* # bits above fp where arguments start */
40 #define AUTOINIT    0         /* # bits below fp where automatics start */
41 
42 /*
43  * Storage space requirements
44  */
45 #define SZCHAR                8
46 #define SZBOOL                8
47 #define SZINT                 32
48 #define SZFLOAT               32
49 #define SZDOUBLE    64
50 #ifdef MACHOABI
51 #define SZLDOUBLE   128
52 #else
53 #define SZLDOUBLE   96
54 #endif
55 #define SZLONG                32
56 #define SZSHORT               16
57 #define SZLONGLONG  64
58 #define SZPOINT(t)  32
59 
60 /*
61  * Alignment constraints
62  */
63 #define ALCHAR                8
64 #define ALBOOL                8
65 #define ALINT                 32
66 #define ALFLOAT               32
67 #define ALDOUBLE    32
68 #ifdef MACHOABI
69 #define ALLDOUBLE   128
70 #else
71 #define ALLDOUBLE   32
72 #endif
73 #define ALLONG                32
74 #define ALLONGLONG  32
75 #define ALSHORT               16
76 #define ALPOINT               32
77 #undef ALSTRUCT               /* Not defined if ELF ABI */
78 #define ALSTACK               32
79 #define   ALMAX               128       /* not yet supported type */
80 
81 /*
82  * Min/max values.
83  */
84 #define   MIN_CHAR  -128
85 #define   MAX_CHAR  127
86 #define   MAX_UCHAR 255
87 #define   MIN_SHORT -32768
88 #define   MAX_SHORT 32767
89 #define   MAX_USHORT          65535
90 #define   MIN_INT             (-0x7fffffff-1)
91 #define   MAX_INT             0x7fffffff
92 #define   MAX_UNSIGNED        0xffffffff
93 #define   MIN_LONG  MIN_INT
94 #define   MAX_LONG  MAX_INT
95 #define   MAX_ULONG MAX_UNSIGNED
96 #define   MIN_LONGLONG        0x8000000000000000LL
97 #define   MAX_LONGLONG        0x7fffffffffffffffLL
98 #define   MAX_ULONGLONG       0xffffffffffffffffULL
99 
100 /* Default char is signed */
101 #undef    CHAR_UNSIGNED
102 #define   BOOL_TYPE UCHAR     /* what used to store _Bool */
103 #undef UNALIGNED_ACCESS
104 /*
105  * Use large-enough types.
106  */
107 typedef   long long CONSZ;
108 typedef   unsigned long long U_CONSZ;
109 typedef long long OFFSZ;
110 
111 #define CONFMT      "%lld"              /* format for printing constants */
112 #if defined(ELFABI)
113 #define LABFMT      ".L%d"              /* format for printing labels */
114 #define   STABLBL   ".LL%d"             /* format for stab (debugging) labels */
115 #else
116 #define LABFMT      "L%d"               /* format for printing labels */
117 #define   STABLBL   "LL%d"              /* format for stab (debugging) labels */
118 #endif
119 #ifdef LANG_F77
120 #define BLANKCOMMON "_BLNK_"
121 #define MSKIREG  (M(TYSHORT)|M(TYLONG))
122 #define TYIREG TYLONG
123 #define FSZLENG  FSZLONG
124 #define   AUTOREG   EBP
125 #define   ARGREG    EBP
126 #define ARGOFFSET 8
127 #endif
128 
129 #ifdef MACHOABI
130 #define STAB_LINE_ABSOLUTE    /* S_LINE fields use absolute addresses */
131 #define   MYALIGN                       /* user power-of-2 alignment */
132 #endif
133 
134 #define BACKAUTO              /* stack grows negatively for automatics */
135 #define BACKTEMP              /* stack grows negatively for temporaries */
136 
137 #undef    FIELDOPS            /* no bit-field instructions */
138 #define TARGET_ENDIAN TARGET_LE
139 
140 #define FINDMOPS    /* i386 has instructions that modifies memory */
141 #define   CC_DIV_0  /* division by zero is safe in the compiler */
142 
143 /* Definitions mostly used in pass2 */
144 
145 #define BYTEOFF(x)  ((x)&03)
146 #define wdal(k)               (BYTEOFF(k)==0)
147 
148 #define STOARG(p)
149 #define STOFARG(p)
150 #define STOSTARG(p)
151 #define genfcall(a,b)         gencall(a,b)
152 
153 #define   szty(t)   (((t) == DOUBLE || (t) == FLOAT || \
154           (t) == LONGLONG || (t) == ULONGLONG) ? 2 : (t) == LDOUBLE ? 3 : 1)
155 
156 /*
157  * The x86 has a bunch of register classes, most of them interfering
158  * with each other.  All registers are given a sequential number to
159  * identify it which must match rnames[] in local2.c.
160  * Class membership and overlaps are defined in the macros RSTATUS
161  * and ROVERLAP below.
162  *
163  * The classes used on x86 are:
164  *        A - short and int regs
165  *        B - char regs
166  *        C - long long regs
167  *        D - floating point
168  */
169 #define   EAX       000       /* Scratch and return register */
170 #define   EDX       001       /* Scratch and secondary return register */
171 #define   ECX       002       /* Scratch (and shift count) register */
172 #define   EBX       003       /* GDT pointer or callee-saved temporary register */
173 #define   ESI       004       /* Callee-saved temporary register */
174 #define   EDI       005       /* Callee-saved temporary register */
175 #define   EBP       006       /* Frame pointer */
176 #define   ESP       007       /* Stack pointer */
177 
178 #define   AL        010
179 #define   AH        011
180 #define   DL        012
181 #define   DH        013
182 #define   CL        014
183 #define   CH        015
184 #define   BL        016
185 #define   BH        017
186 
187 #define   EAXEDX    020
188 #define   EAXECX    021
189 #define   EAXEBX    022
190 #define   EAXESI    023
191 #define   EAXEDI    024
192 #define   EDXECX    025
193 #define   EDXEBX    026
194 #define   EDXESI    027
195 #define   EDXEDI    030
196 #define   ECXEBX    031
197 #define   ECXESI    032
198 #define   ECXEDI    033
199 #define   EBXESI    034
200 #define   EBXEDI    035
201 #define   ESIEDI    036
202 
203 /* The 8 math registers in class D lacks names */
204 
205 #define   MAXREGS   047       /* 39 registers */
206 
207 #define   RSTATUS   \
208           SAREG|TEMPREG, SAREG|TEMPREG, SAREG|TEMPREG, SAREG|PERMREG, \
209           SAREG|PERMREG, SAREG|PERMREG, 0, 0,                                   \
210           SBREG, SBREG, SBREG, SBREG, SBREG, SBREG, SBREG, SBREG,               \
211           SCREG, SCREG, SCREG, SCREG, SCREG, SCREG, SCREG, SCREG,     \
212           SCREG, SCREG, SCREG, SCREG, SCREG, SCREG, SCREG,            \
213           SDREG, SDREG, SDREG, SDREG,  SDREG, SDREG, SDREG, SDREG,
214 
215 #define   ROVERLAP \
216           /* 8 basic registers */\
217           { AL, AH, EAXEDX, EAXECX, EAXEBX, EAXESI, EAXEDI, -1 },\
218           { DL, DH, EAXEDX, EDXECX, EDXEBX, EDXESI, EDXEDI, -1 },\
219           { CL, CH, EAXECX, EDXECX, ECXEBX, ECXESI, ECXEDI, -1 },\
220           { BL, BH, EAXEBX, EDXEBX, ECXEBX, EBXESI, EBXEDI, -1 },\
221           { EAXESI, EDXESI, ECXESI, EBXESI, ESIEDI, -1 },\
222           { EAXEDI, EDXEDI, ECXEDI, EBXEDI, ESIEDI, -1 },\
223           { -1 },\
224           { -1 },\
225 \
226           /* 8 char registers */\
227           { EAX, EAXEDX, EAXECX, EAXEBX, EAXESI, EAXEDI, -1 },\
228           { EAX, EAXEDX, EAXECX, EAXEBX, EAXESI, EAXEDI, -1 },\
229           { EDX, EAXEDX, EDXECX, EDXEBX, EDXESI, EDXEDI, -1 },\
230           { EDX, EAXEDX, EDXECX, EDXEBX, EDXESI, EDXEDI, -1 },\
231           { ECX, EAXECX, EDXECX, ECXEBX, ECXESI, ECXEDI, -1 },\
232           { ECX, EAXECX, EDXECX, ECXEBX, ECXESI, ECXEDI, -1 },\
233           { EBX, EAXEBX, EDXEBX, ECXEBX, EBXESI, EBXEDI, -1 },\
234           { EBX, EAXEBX, EDXEBX, ECXEBX, EBXESI, EBXEDI, -1 },\
235 \
236           /* 15 long-long-emulating registers */\
237           { EAX, AL, AH, EDX, DL, DH, EAXECX, EAXEBX, EAXESI,         /* eaxedx */\
238             EAXEDI, EDXECX, EDXEBX, EDXESI, EDXEDI, -1, },\
239           { EAX, AL, AH, ECX, CL, CH, EAXEDX, EAXEBX, EAXESI,         /* eaxecx */\
240             EAXEDI, EDXECX, ECXEBX, ECXESI, ECXEDI, -1 },\
241           { EAX, AL, AH, EBX, BL, BH, EAXEDX, EAXECX, EAXESI,         /* eaxebx */\
242             EAXEDI, EDXEBX, ECXEBX, EBXESI, EBXEDI, -1 },\
243           { EAX, AL, AH, ESI, EAXEDX, EAXECX, EAXEBX, EAXEDI,         /* eaxesi */\
244             EDXESI, ECXESI, EBXESI, ESIEDI, -1 },\
245           { EAX, AL, AH, EDI, EAXEDX, EAXECX, EAXEBX, EAXESI,         /* eaxedi */\
246             EDXEDI, ECXEDI, EBXEDI, ESIEDI, -1 },\
247           { EDX, DL, DH, ECX, CL, CH, EAXEDX, EAXECX, EDXEBX,         /* edxecx */\
248             EDXESI, EDXEDI, ECXEBX, ECXESI, ECXEDI, -1 },\
249           { EDX, DL, DH, EBX, BL, BH, EAXEDX, EDXECX, EDXESI,         /* edxebx */\
250             EDXEDI, EAXEBX, ECXEBX, EBXESI, EBXEDI, -1 },\
251           { EDX, DL, DH, ESI, EAXEDX, EDXECX, EDXEBX, EDXEDI,         /* edxesi */\
252             EAXESI, ECXESI, EBXESI, ESIEDI, -1 },\
253           { EDX, DL, DH, EDI, EAXEDX, EDXECX, EDXEBX, EDXESI,         /* edxedi */\
254             EAXEDI, ECXEDI, EBXEDI, ESIEDI, -1 },\
255           { ECX, CL, CH, EBX, BL, BH, EAXECX, EDXECX, ECXESI,         /* ecxebx */\
256             ECXEDI, EAXEBX, EDXEBX, EBXESI, EBXEDI, -1 },\
257           { ECX, CL, CH, ESI, EAXECX, EDXECX, ECXEBX, ECXEDI,         /* ecxesi */\
258             EAXESI, EDXESI, EBXESI, ESIEDI, -1 },\
259           { ECX, CL, CH, EDI, EAXECX, EDXECX, ECXEBX, ECXESI,         /* ecxedi */\
260             EAXEDI, EDXEDI, EBXEDI, ESIEDI, -1 },\
261           { EBX, BL, BH, ESI, EAXEBX, EDXEBX, ECXEBX, EBXEDI,         /* ebxesi */\
262             EAXESI, EDXESI, ECXESI, ESIEDI, -1 },\
263           { EBX, BL, BH, EDI, EAXEBX, EDXEBX, ECXEBX, EBXESI,         /* ebxedi */\
264             EAXEDI, EDXEDI, ECXEDI, ESIEDI, -1 },\
265           { ESI, EDI, EAXESI, EDXESI, ECXESI, EBXESI,                 /* esiedi */\
266             EAXEDI, EDXEDI, ECXEDI, EBXEDI, -1 },\
267 \
268           /* The fp registers do not overlap with anything */\
269           { -1 },\
270           { -1 },\
271           { -1 },\
272           { -1 },\
273           { -1 },\
274           { -1 },\
275           { -1 },\
276           { -1 },
277 
278 
279 /* Return a register class based on the type of the node */
280 #define PCLASS(p) (p->n_type <= UCHAR ? SBREG : \
281                       (p->n_type == LONGLONG || p->n_type == ULONGLONG ? SCREG : \
282                       (p->n_type >= FLOAT && p->n_type <= LDOUBLE ? SDREG : SAREG)))
283 
284 #define   NUMCLASS  4         /* highest number of reg classes used */
285 
286 int COLORMAP(int c, int *r);
287 #define   GCLASS(x) (x < 8 ? CLASSA : x < 16 ? CLASSB : x < 31 ? CLASSC : CLASSD)
288 #define DECRA(x,y)  (((x) >> (y*6)) & 63)         /* decode encoded regs */
289 #define   ENCRD(x)  (x)                 /* Encode dest reg in n_reg */
290 #define ENCRA1(x)   ((x) << 6)          /* A1 */
291 #define ENCRA2(x)   ((x) << 12)         /* A2 */
292 #define ENCRA(x,y)  ((x) << (6+y*6))    /* encode regs in int */
293 /* XXX - return char in al? */
294 #define   RETREG(x) (x == CHAR || x == UCHAR ? AL : \
295                                x == LONGLONG || x == ULONGLONG ? EAXEDX : \
296                                x == FLOAT || x == DOUBLE || x == LDOUBLE ? 31 : EAX)
297 
298 #if 0
299 #define R2REGS      1         /* permit double indexing */
300 #endif
301 
302 /* XXX - to die */
303 #define FPREG       EBP       /* frame pointer */
304 #define STKREG      ESP       /* stack pointer */
305 
306 #define   SHSTR               (MAXSPECIAL+1)      /* short struct */
307 #define   SFUNCALL  (MAXSPECIAL+2)      /* struct assign after function call */
308 #define   SPCON               (MAXSPECIAL+3)      /* positive nonnamed constant */
309 
310 /*
311  * Specials that indicate the applicability of machine idioms.
312  */
313 #define SMIXOR                (MAXSPECIAL+4)
314 #define SMILWXOR    (MAXSPECIAL+5)
315 #define SMIHWXOR    (MAXSPECIAL+6)
316 
317 /*
318  * i386-specific symbol table flags.
319  */
320 #define   SSECTION  SLOCAL1
321 #define SSTDCALL    SLOCAL2
322 #define SDLLINDIRECT          SLOCAL3
323 
324 /*
325  * i386-specific interpass stuff.
326  */
327 
328 #define TARGET_IPP_MEMBERS                        \
329           int ipp_argstacksize;
330 
331 #define   target_members_print_prolog(ipp) printf("%d", ipp->ipp_argstacksize)
332 #define   target_members_print_epilog(ipp) printf("%d", ipp->ipp_argstacksize)
333 #define target_members_read_prolog(ipp) ipp->ipp_argstacksize = rdint(&p)
334 #define target_members_read_epilog(ipp) ipp->ipp_argstacksize = rdint(&p)
335 
336 #define   HAVE_WEAKREF
337 #define   TARGET_FLT_EVAL_METHOD        2         /* all as long double */
338 
339 /*
340  * Extended assembler macros.
341  */
342 void targarg(char *w, void *arg);
343 #define   XASM_TARGARG(w, ary)          \
344           (w[1] == 'b' || w[1] == 'h' || w[1] == 'w' || w[1] == 'k' ? \
345           w++, targarg(w, ary), 1 : 0)
346 int numconv(void *ip, void *p, void *q);
347 #define   XASM_NUMCONV(ip, p, q)        numconv(ip, p, q)
348 int xasmconstregs(char *);
349 #define   XASMCONSTREGS(x) xasmconstregs(x)
350 #define   MYSETXARG if (XASMVAL(cw) == 'q') {     \
351           c = 'r'; addalledges(&ablock[ESI]); addalledges(&ablock[EDI]); }
352 
353 #if defined(MACHOABI)
354 struct stub {
355           struct { struct stub *q_forw, *q_back; } link;
356           char *name;
357 };
358 extern struct stub stublist;
359 extern struct stub nlplist;
360 void addstub(struct stub *list, char *name);
361 #endif
362 
363 /* -m flags */
364 extern int msettings;
365 #define   MI386     0x001
366 #define   MI486     0x002
367 #define   MI586     0x004
368 #define   MI686     0x008
369 #define   MCPUMSK   0x00f
370 
371 /* target specific attributes */
372 #define   ATTR_MI_TARGET      ATTR_I386_FCMPLRET, ATTR_I386_FPPOP
373 #define NATIVE_FLOATING_POINT
374