2 mcs51 specific general functions.
4 Note that mlh prepended _mcs51_ on the static functions. Makes
5 it easier to set a breakpoint using the debugger.
11 #include "../SDCCutil.h"
12 extern const char *preArgv[128]; /* pre-processor arguments */
14 static char _defaultRules[] =
19 /* list of key words used by msc51 */
20 static char *_mcs51_keywords[] =
50 void mcs51_assignRegisters (eBBlock ** ebbs, int count);
52 static int regParmFlg = 0; /* determine if we can register a parameter */
57 asm_addTree (&asm_asxxxx_mapping);
61 _mcs51_reset_regparm ()
67 _mcs51_regparm (sym_link * l)
69 if (options.parms_in_bank1 == 0) {
70 /* simple can pass only the first parameter in a register */
77 int size = getSize(l);
80 /* first one goes the usual way to DPTR */
81 if (regParmFlg == 0) {
85 /* second one onwards goes to RB1_0 thru RB1_7 */
86 remain = regParmFlg - 4;
87 if (size > (8 - remain)) {
92 return regParmFlg - size + 1;
97 _mcs51_parseOptions (int *pargc, char **argv, int *i)
99 /* TODO: allow port-specific command line options to specify
100 * segment names here.
106 _mcs51_finaliseOptions (void)
108 if (options.model == MODEL_LARGE) {
109 port->mem.default_local_map = xdata;
110 port->mem.default_globl_map = xdata;
114 port->mem.default_local_map = data;
115 port->mem.default_globl_map = data;
118 if (options.parms_in_bank1) {
119 addToList (preArgv, "-DSDCC_PARMS_IN_BANK1");
124 _mcs51_setDefaultOptions (void)
129 _mcs51_getRegName (struct regs *reg)
137 _mcs51_genAssemblerPreamble (FILE * of)
139 if (options.parms_in_bank1) {
141 for (i=0; i < 8 ; i++ )
142 fprintf (of,"b1_%d = 0x%x \n",i,8+i);
146 /* Generate interrupt vector table. */
148 _mcs51_genIVT (FILE * of, symbol ** interrupts, int maxInterrupts)
153 /* Generate code to copy XINIT to XISEG */
154 static void _mcs51_genXINIT (FILE * of) {
155 fprintf (of, "; _mcs51_genXINIT() start\n");
156 fprintf (of, " mov a,#l_XINIT\n");
157 fprintf (of, " orl a,#l_XINIT>>8\n");
158 fprintf (of, " jz 00003$\n");
159 fprintf (of, " mov a,#s_XINIT\n");
160 fprintf (of, " add a,#l_XINIT\n");
161 fprintf (of, " mov r1,a\n");
162 fprintf (of, " mov a,#s_XINIT>>8\n");
163 fprintf (of, " addc a,#l_XINIT>>8\n");
164 fprintf (of, " mov r2,a\n");
165 fprintf (of, " mov dptr,#s_XINIT\n");
166 fprintf (of, " mov r0,#s_XISEG\n");
167 fprintf (of, " mov p2,#(s_XISEG >> 8)\n");
168 fprintf (of, "00001$: clr a\n");
169 fprintf (of, " movc a,@a+dptr\n");
170 fprintf (of, " movx @r0,a\n");
171 fprintf (of, " inc dptr\n");
172 fprintf (of, " inc r0\n");
173 fprintf (of, " cjne r0,#0,00002$\n");
174 fprintf (of, " inc p2\n");
175 fprintf (of, "00002$: mov a,dpl\n");
176 fprintf (of, " cjne a,ar1,00001$\n");
177 fprintf (of, " mov a,dph\n");
178 fprintf (of, " cjne a,ar2,00001$\n");
179 fprintf (of, " mov p2,#0xFF\n");
180 fprintf (of, "00003$:\n");
181 fprintf (of, "; _mcs51_genXINIT() end\n");
185 /* Do CSE estimation */
186 static bool cseCostEstimation (iCode *ic, iCode *pdic)
188 operand *result = IC_RESULT(ic);
189 sym_link *result_type = operandType(result);
191 /* if it is a pointer then return ok for now */
192 if (IC_RESULT(ic) && IS_PTR(result_type)) return 1;
194 /* if bitwise | add & subtract then no since mcs51 is pretty good at it
195 so we will cse only if they are local (i.e. both ic & pdic belong to
196 the same basic block */
197 if (IS_BITWISE_OP(ic) || ic->op == '+' || ic->op == '-') {
198 /* then if they are the same Basic block then ok */
199 if (ic->eBBlockNum == pdic->eBBlockNum) return 1;
203 /* for others it is cheaper to do the cse */
207 /** $1 is always the basename.
208 $2 is always the output file.
210 $l is the list of extra options that should be there somewhere...
211 MUST be terminated with a NULL.
213 static const char *_linkCmd[] =
215 "{bindir}{sep}aslink", "-nf", "$1", NULL
218 /* $3 is replaced by assembler.debug_opts resp. port->assembler.plain_opts */
219 static const char *_asmCmd[] =
221 "asx8051", "$l", "$3", "$1.asm", NULL
229 "MCU 8051", /* Target name */
231 TRUE, /* Emit glue around main */
232 MODEL_SMALL | MODEL_LARGE,
238 "-plosgffc", /* Options with debug */
239 "-plosgff", /* Options without debug */
242 NULL /* no do_assemble function */
254 /* Sizes: char, short, int, long, ptr, fptr, gptr, bit, float, max */
255 1, 2, 2, 4, 1, 2, 3, 1, 4, 4
270 "XISEG (XDATA)", // initialized xdata
271 "XINIT (CODE)", // a code copy of xiseg
279 /* mcs51 has an 8 bit mul */
286 _mcs51_finaliseOptions,
287 _mcs51_setDefaultOptions,
288 mcs51_assignRegisters,
291 _mcs51_genAssemblerPreamble,
292 NULL, /* no genAssemblerEnd */
295 _mcs51_reset_regparm,
303 1, /* transform <= to ! > */
304 1, /* transform >= to ! < */
305 1, /* transform != to !(a == b) */
307 FALSE, /* No array initializer support. */
309 NULL, /* no builtin functions */
310 GPOINTER, /* treat unqualified pointers as "generic" pointers */
311 1, /* reset labelKey to 1 */
312 1, /* globals & local static allowed */