1 /*------------------------------------------------------------------------
3 SDCCralloc.c - source file for register allocation. (8051) specific
5 Written By - Sandeep Dutta . sandeep.dutta@usa.net (1998)
7 This program is free software; you can redistribute it and/or modify it
8 under the terms of the GNU General Public License as published by the
9 Free Software Foundation; either version 2, or (at your option) any
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
21 In other words, you are welcome to use, share and improve this program.
22 You are forbidden to forbid anyone else to use, share and improve
23 what you give them. Help stamp out software-hoarding!
24 -------------------------------------------------------------------------*/
30 /*-----------------------------------------------------------------*/
31 /* At this point we start getting processor specific although */
32 /* some routines are non-processor specific & can be reused when */
33 /* targetting other processors. The decision for this will have */
34 /* to be made on a routine by routine basis */
35 /* routines used to pack registers are most definitely not reusable */
36 /* since the pack the registers depending strictly on the MCU */
37 /*-----------------------------------------------------------------*/
39 extern void genhc08Code (iCode *);
48 bitVect *totRegAssigned; /* final set of LRs that got into registers */
51 bitVect *funcrUsed; /* registers used in a function */
57 /* Shared with gen.c */
58 int hc08_ptrRegReq; /* one byte pointer register required */
64 {REG_GPR, A_IDX, REG_GPR, "a", "a", "0", 1, NULL, 0, 1},
65 {REG_GPR, X_IDX, REG_GPR, "x", "x", "0", 2, NULL, 0, 1},
66 {REG_GPR, H_IDX, REG_GPR, "h", "h", "0", 4, NULL, 0, 1},
67 {REG_PTR, HX_IDX, REG_PTR, "hx", "hx", "0", 6, NULL, 0, 1},
68 {REG_GPR, XA_IDX, REG_GPR, "xa", "xa", "0", 3, NULL, 0, 1},
70 {REG_CND, CND_IDX, REG_CND, "C", "C", "xreg", 0, NULL, 0, 1},
80 static void spillThis (symbol *);
81 static void freeAllRegs ();
83 /*-----------------------------------------------------------------*/
84 /* allocReg - allocates register of given type */
85 /*-----------------------------------------------------------------*/
91 if ((type==REG_PTR) && (regshc08[HX_IDX].isFree))
93 regshc08[HX_IDX].isFree = 0;
96 bitVectSetBit (currFunc->regsUsed, HX_IDX);
97 return ®shc08[HX_IDX];
102 /*-----------------------------------------------------------------*/
103 /* hc08_regWithIdx - returns pointer to register wit index number */
104 /*-----------------------------------------------------------------*/
106 hc08_regWithIdx (int idx)
110 for (i = 0; i < hc08_nRegs; i++)
111 if (regshc08[i].rIdx == idx)
114 werror (E_INTERNAL_ERROR, __FILE__, __LINE__,
115 "regWithIdx not found");
119 /*-----------------------------------------------------------------*/
120 /* hc08_freeReg - frees a register */
121 /*-----------------------------------------------------------------*/
123 hc08_freeReg (regs * reg)
127 werror (E_INTERNAL_ERROR, __FILE__, __LINE__,
128 "hc08_freeReg - Freeing NULL register");
137 if (hc08_reg_x->isFree)
138 hc08_reg_xa->isFree = 1;
141 if (hc08_reg_a->isFree)
142 hc08_reg_xa->isFree = 1;
143 if (hc08_reg_h->isFree)
144 hc08_reg_hx->isFree = 1;
147 if (hc08_reg_x->isFree)
148 hc08_reg_hx->isFree = 1;
151 hc08_reg_h->isFree = 1;
152 hc08_reg_x->isFree = 1;
153 if (hc08_reg_a->isFree)
154 hc08_reg_xa->isFree = 1;
157 hc08_reg_x->isFree = 1;
158 hc08_reg_a->isFree = 1;
159 if (hc08_reg_h->isFree)
160 hc08_reg_hx->isFree = 1;
168 /*-----------------------------------------------------------------*/
169 /* nFreeRegs - returns number of free registers */
170 /*-----------------------------------------------------------------*/
179 for (i = 0; i < hc08_nRegs; i++)
180 if (regshc08[i].isFree && regshc08[i].type == type)
185 /*-----------------------------------------------------------------*/
186 /* nfreeRegsType - free registers with type */
187 /*-----------------------------------------------------------------*/
189 nfreeRegsType (int type)
194 if ((nfr = nFreeRegs (type)) == 0)
195 return nFreeRegs (REG_GPR);
198 return nFreeRegs (type);
201 /*-----------------------------------------------------------------*/
202 /* hc08_useReg - marks a register as used */
203 /*-----------------------------------------------------------------*/
205 hc08_useReg (regs * reg)
212 hc08_reg_xa->aop = NULL;
213 hc08_reg_xa->isFree = 0;
216 hc08_reg_xa->aop = NULL;
217 hc08_reg_xa->isFree = 0;
218 hc08_reg_hx->aop = NULL;
219 hc08_reg_hx->isFree = 0;
222 hc08_reg_hx->aop = NULL;
223 hc08_reg_hx->isFree = 0;
226 hc08_reg_h->aop = NULL;
227 hc08_reg_h->isFree = 0;
228 hc08_reg_x->aop = NULL;
229 hc08_reg_x->isFree = 0;
232 hc08_reg_x->aop = NULL;
233 hc08_reg_x->isFree = 0;
234 hc08_reg_a->aop = NULL;
235 hc08_reg_a->isFree = 0;
243 /*-----------------------------------------------------------------*/
244 /* hc08_dirtyReg - marks a register as dirty */
245 /*-----------------------------------------------------------------*/
247 hc08_dirtyReg (regs * reg, bool freereg)
254 hc08_reg_xa->aop = NULL;
257 hc08_reg_xa->aop = NULL;
258 hc08_reg_hx->aop = NULL;
261 hc08_reg_hx->aop = NULL;
264 hc08_reg_h->aop = NULL;
265 hc08_reg_x->aop = NULL;
268 hc08_reg_x->aop = NULL;
269 hc08_reg_a->aop = NULL;
278 /*-----------------------------------------------------------------*/
279 /* computeSpillable - given a point find the spillable live ranges */
280 /*-----------------------------------------------------------------*/
282 computeSpillable (iCode * ic)
286 /* spillable live ranges are those that are live at this
287 point . the following categories need to be subtracted
289 a) - those that are already spilt
290 b) - if being used by this one
291 c) - defined by this one */
293 spillable = bitVectCopy (ic->rlive);
295 bitVectCplAnd (spillable, _G.spiltSet); /* those already spilt */
297 bitVectCplAnd (spillable, ic->uses); /* used in this one */
298 bitVectUnSetBit (spillable, ic->defKey);
299 spillable = bitVectIntersect (spillable, _G.regAssigned);
304 /*-----------------------------------------------------------------*/
305 /* noSpilLoc - return true if a variable has no spil location */
306 /*-----------------------------------------------------------------*/
308 noSpilLoc (symbol * sym, eBBlock * ebp, iCode * ic)
310 return (sym->usl.spillLoc ? 0 : 1);
313 /*-----------------------------------------------------------------*/
314 /* hasSpilLoc - will return 1 if the symbol has spil location */
315 /*-----------------------------------------------------------------*/
317 hasSpilLoc (symbol * sym, eBBlock * ebp, iCode * ic)
319 return (sym->usl.spillLoc ? 1 : 0);
322 /*-----------------------------------------------------------------*/
323 /* directSpilLoc - will return 1 if the splilocation is in direct */
324 /*-----------------------------------------------------------------*/
326 directSpilLoc (symbol * sym, eBBlock * ebp, iCode * ic)
328 if (sym->usl.spillLoc &&
329 (IN_DIRSPACE (SPEC_OCLS (sym->usl.spillLoc->etype))))
335 /*-----------------------------------------------------------------*/
336 /* hasSpilLocnoUptr - will return 1 if the symbol has spil location */
337 /* but is not used as a pointer */
338 /*-----------------------------------------------------------------*/
340 hasSpilLocnoUptr (symbol * sym, eBBlock * ebp, iCode * ic)
342 return ((sym->usl.spillLoc && !sym->uptr) ? 1 : 0);
345 /*-----------------------------------------------------------------*/
346 /* rematable - will return 1 if the remat flag is set */
347 /*-----------------------------------------------------------------*/
349 rematable (symbol * sym, eBBlock * ebp, iCode * ic)
354 /*-----------------------------------------------------------------*/
355 /* notUsedInRemaining - not used or defined in remain of the block */
356 /*-----------------------------------------------------------------*/
358 notUsedInRemaining (symbol * sym, eBBlock * ebp, iCode * ic)
360 return ((usedInRemaining (operandFromSymbol (sym), ic) ? 0 : 1) &&
361 allDefsOutOfRange (sym->defs, ebp->fSeq, ebp->lSeq));
364 /*-----------------------------------------------------------------*/
365 /* allLRs - return true for all */
366 /*-----------------------------------------------------------------*/
368 allLRs (symbol * sym, eBBlock * ebp, iCode * ic)
373 /*-----------------------------------------------------------------*/
374 /* liveRangesWith - applies function to a given set of live range */
375 /*-----------------------------------------------------------------*/
377 liveRangesWith (bitVect * lrs, int (func) (symbol *, eBBlock *, iCode *),
378 eBBlock * ebp, iCode * ic)
383 if (!lrs || !lrs->size)
386 for (i = 1; i < lrs->size; i++)
389 if (!bitVectBitValue (lrs, i))
392 /* if we don't find it in the live range
393 hash table we are in serious trouble */
394 if (!(sym = hTabItemWithKey (liveRanges, i)))
396 werror (E_INTERNAL_ERROR, __FILE__, __LINE__,
397 "liveRangesWith could not find liveRange");
401 if (func (sym, ebp, ic) && bitVectBitValue (_G.regAssigned, sym->key))
402 addSetHead (&rset, sym);
409 /*-----------------------------------------------------------------*/
410 /* leastUsedLR - given a set determines which is the least used */
411 /*-----------------------------------------------------------------*/
413 leastUsedLR (set * sset)
415 symbol *sym = NULL, *lsym = NULL;
417 sym = lsym = setFirstItem (sset);
422 for (; lsym; lsym = setNextItem (sset))
425 /* if usage is the same then prefer
426 the spill the smaller of the two */
427 if (lsym->used == sym->used)
428 if (getSize (lsym->type) < getSize (sym->type))
432 if (lsym->used < sym->used)
437 setToNull ((void *) &sset);
442 /*-----------------------------------------------------------------*/
443 /* noOverLap - will iterate through the list looking for over lap */
444 /*-----------------------------------------------------------------*/
446 noOverLap (set * itmpStack, symbol * fsym)
451 for (sym = setFirstItem (itmpStack); sym;
452 sym = setNextItem (itmpStack))
454 if (bitVectBitValue(sym->clashes,fsym->key)) return 0;
460 /*-----------------------------------------------------------------*/
461 /* isFree - will return 1 if the a free spil location is found */
462 /*-----------------------------------------------------------------*/
467 V_ARG (symbol **, sloc);
468 V_ARG (symbol *, fsym);
470 /* if already found */
474 /* if it is free && and the itmp assigned to
475 this does not have any overlapping live ranges
476 with the one currently being assigned and
477 the size can be accomodated */
479 noOverLap (sym->usl.itmpStack, fsym) &&
480 getSize (sym->type) >= getSize (fsym->type))
489 /*-----------------------------------------------------------------*/
490 /* spillLRWithPtrReg :- will spil those live ranges which use PTR */
491 /*-----------------------------------------------------------------*/
493 spillLRWithPtrReg (symbol * forSym)
499 if (!_G.regAssigned ||
500 bitVectIsZero (_G.regAssigned))
503 hx = hc08_regWithIdx (HX_IDX);
505 /* for all live ranges */
506 for (lrsym = hTabFirstItem (liveRanges, &k); lrsym;
507 lrsym = hTabNextItem (liveRanges, &k))
511 /* if no registers assigned to it or spilt */
512 /* if it does not overlap with this then
513 not need to spill it */
515 if (lrsym->isspilt || !lrsym->nRegs ||
516 (lrsym->liveTo < forSym->liveFrom))
519 /* go thru the registers : if it is either
520 r0 or r1 then spil it */
521 for (j = 0; j < lrsym->nRegs; j++)
522 if (lrsym->regs[j] == hx)
531 /*-----------------------------------------------------------------*/
532 /* createStackSpil - create a location on the stack to spil */
533 /*-----------------------------------------------------------------*/
535 createStackSpil (symbol * sym)
538 int useXstack, model;
542 /* first go try and find a free one that is already
543 existing on the stack */
544 if (applyToSet (_G.stackSpil, isFree, &sloc, sym))
546 /* found a free one : just update & return */
547 sym->usl.spillLoc = sloc;
550 addSetHead (&sloc->usl.itmpStack, sym);
554 /* could not then have to create one , this is the hard part
555 we need to allocate this on the stack : this is really a
556 hack!! but cannot think of anything better at this time */
558 if (sprintf (slocBuffer, "sloc%d", _G.slocNum++) >= sizeof (slocBuffer))
560 fprintf (stderr, "***Internal error: slocBuffer overflowed: %s:%d\n",
565 sloc = newiTemp (slocBuffer);
567 /* set the type to the spilling symbol */
568 sloc->type = copyLinkChain (sym->type);
569 sloc->etype = getSpec (sloc->type);
570 SPEC_SCLS (sloc->etype) = S_DATA;
571 SPEC_EXTR (sloc->etype) = 0;
572 SPEC_STAT (sloc->etype) = 0;
573 SPEC_VOLATILE(sloc->etype) = 0;
574 SPEC_ABSA(sloc->etype) = 0;
576 /* we don't allow it to be allocated`
577 onto the external stack since : so we
578 temporarily turn it off ; we also
579 turn off memory model to prevent
580 the spil from going to the external storage
583 useXstack = options.useXstack;
584 model = options.model;
585 /* noOverlay = options.noOverlay; */
586 /* options.noOverlay = 1; */
587 options.model = options.useXstack = 0;
591 options.useXstack = useXstack;
592 options.model = model;
593 /* options.noOverlay = noOverlay; */
594 sloc->isref = 1; /* to prevent compiler warning */
596 /* if it is on the stack then update the stack */
597 if (IN_STACK (sloc->etype))
599 currFunc->stack += getSize (sloc->type);
600 _G.stackExtend += getSize (sloc->type);
603 _G.dataExtend += getSize (sloc->type);
605 /* add it to the _G.stackSpil set */
606 addSetHead (&_G.stackSpil, sloc);
607 sym->usl.spillLoc = sloc;
610 /* add it to the set of itempStack set
611 of the spill location */
612 addSetHead (&sloc->usl.itmpStack, sym);
616 /*-----------------------------------------------------------------*/
617 /* isSpiltOnStack - returns true if the spil location is on stack */
618 /*-----------------------------------------------------------------*/
620 isSpiltOnStack (symbol * sym)
630 /* if (sym->_G.stackSpil) */
633 if (!sym->usl.spillLoc)
636 etype = getSpec (sym->usl.spillLoc->type);
637 if (IN_STACK (etype))
643 /*-----------------------------------------------------------------*/
644 /* spillThis - spils a specific operand */
645 /*-----------------------------------------------------------------*/
647 spillThis (symbol * sym)
650 /* if this is rematerializable or has a spillLocation
651 we are okay, else we need to create a spillLocation
653 if (!(sym->remat || sym->usl.spillLoc))
654 createStackSpil (sym);
656 /* mark it has spilt & put it in the spilt set */
657 sym->isspilt = sym->spillA = 1;
658 _G.spiltSet = bitVectSetBit (_G.spiltSet, sym->key);
660 bitVectUnSetBit (_G.regAssigned, sym->key);
661 bitVectUnSetBit (_G.totRegAssigned, sym->key);
663 for (i = 0; i < sym->nRegs; i++)
667 hc08_freeReg (sym->regs[i]);
671 /* if spilt on stack then free up r0 & r1
672 if they could have been assigned to some
674 // if (!hc08_ptrRegReq && isSpiltOnStack (sym))
677 // spillLRWithPtrReg (sym);
680 if (sym->usl.spillLoc && !sym->remat)
681 sym->usl.spillLoc->allocreq++;
685 /*-----------------------------------------------------------------*/
686 /* selectSpil - select a iTemp to spil : rather a simple procedure */
687 /*-----------------------------------------------------------------*/
689 selectSpil (iCode * ic, eBBlock * ebp, symbol * forSym)
691 bitVect *lrcs = NULL;
695 /* get the spillable live ranges */
696 lrcs = computeSpillable (ic);
698 /* get all live ranges that are rematerizable */
699 if ((selectS = liveRangesWith (lrcs, rematable, ebp, ic)))
702 /* return the least used of these */
703 return leastUsedLR (selectS);
706 /* get live ranges with spillLocations in direct space */
707 if ((selectS = liveRangesWith (lrcs, directSpilLoc, ebp, ic)))
709 sym = leastUsedLR (selectS);
710 strcpy (sym->rname, (sym->usl.spillLoc->rname[0] ?
711 sym->usl.spillLoc->rname :
712 sym->usl.spillLoc->name));
714 /* mark it as allocation required */
715 sym->usl.spillLoc->allocreq++;
719 /* if the symbol is local to the block then */
720 if (forSym->liveTo < ebp->lSeq)
723 /* check if there are any live ranges allocated
724 to registers that are not used in this block */
725 if (!_G.blockSpil && (selectS = liveRangesWith (lrcs, notUsedInBlock, ebp, ic)))
727 sym = leastUsedLR (selectS);
728 /* if this is not rematerializable */
737 /* check if there are any live ranges that not
738 used in the remainder of the block */
739 if (!_G.blockSpil && (selectS = liveRangesWith (lrcs, notUsedInRemaining, ebp, ic)))
741 sym = leastUsedLR (selectS);
754 /* find live ranges with spillocation && not used as pointers */
755 if ((selectS = liveRangesWith (lrcs, hasSpilLocnoUptr, ebp, ic)))
758 sym = leastUsedLR (selectS);
759 /* mark this as allocation required */
760 sym->usl.spillLoc->allocreq++;
764 /* find live ranges with spillocation */
765 if ((selectS = liveRangesWith (lrcs, hasSpilLoc, ebp, ic)))
768 sym = leastUsedLR (selectS);
769 sym->usl.spillLoc->allocreq++;
773 /* couldn't find then we need to create a spil
774 location on the stack , for which one? the least
776 if ((selectS = liveRangesWith (lrcs, noSpilLoc, ebp, ic)))
779 /* return a created spil location */
780 sym = createStackSpil (leastUsedLR (selectS));
781 sym->usl.spillLoc->allocreq++;
785 /* this is an extreme situation we will spill
786 this one : happens very rarely but it does happen */
792 /*-----------------------------------------------------------------*/
793 /* spilSomething - spil some variable & mark registers as free */
794 /*-----------------------------------------------------------------*/
796 spilSomething (iCode * ic, eBBlock * ebp, symbol * forSym)
801 /* get something we can spil */
802 ssym = selectSpil (ic, ebp, forSym);
804 /* mark it as spilt */
805 ssym->isspilt = ssym->spillA = 1;
806 _G.spiltSet = bitVectSetBit (_G.spiltSet, ssym->key);
808 /* mark it as not register assigned &
809 take it away from the set */
810 bitVectUnSetBit (_G.regAssigned, ssym->key);
811 bitVectUnSetBit (_G.totRegAssigned, ssym->key);
813 /* mark the registers as free */
814 for (i = 0; i < ssym->nRegs; i++)
816 hc08_freeReg (ssym->regs[i]);
818 /* if spilt on stack then free up hx
819 if it could have been assigned to as gprs */
820 if (!hc08_ptrRegReq && isSpiltOnStack (ssym))
823 spillLRWithPtrReg (ssym);
826 /* if this was a block level spil then insert push & pop
827 at the start & end of block respectively */
830 iCode *nic = newiCode (IPUSH, operandFromSymbol (ssym), NULL);
831 /* add push to the start of the block */
832 addiCodeToeBBlock (ebp, nic, (ebp->sch->op == LABEL ?
833 ebp->sch->next : ebp->sch));
834 nic = newiCode (IPOP, operandFromSymbol (ssym), NULL);
835 /* add pop to the end of the block */
836 addiCodeToeBBlock (ebp, nic, NULL);
839 /* if spilt because not used in the remainder of the
840 block then add a push before this instruction and
841 a pop at the end of the block */
842 if (ssym->remainSpil)
845 iCode *nic = newiCode (IPUSH, operandFromSymbol (ssym), NULL);
846 /* add push just before this instruction */
847 addiCodeToeBBlock (ebp, nic, ic);
849 nic = newiCode (IPOP, operandFromSymbol (ssym), NULL);
850 /* add pop to the end of the block */
851 addiCodeToeBBlock (ebp, nic, NULL);
860 /*-----------------------------------------------------------------*/
861 /* getRegPtr - will try for PTR if not a GPR type if not spil */
862 /*-----------------------------------------------------------------*/
864 getRegPtr (iCode * ic, eBBlock * ebp, symbol * sym)
869 /* try for a ptr type */
870 if ((reg = allocReg (REG_PTR)))
873 /* try for gpr type */
874 if ((reg = allocReg (REG_GPR)))
877 /* we have to spil */
878 if (!spilSomething (ic, ebp, sym))
881 /* this looks like an infinite loop but
882 in really selectSpil will abort */
886 /*-----------------------------------------------------------------*/
887 /* getRegGpr - will try for GPR if not spil */
888 /*-----------------------------------------------------------------*/
890 getRegGpr (iCode * ic, eBBlock * ebp, symbol * sym)
895 /* try for gpr type */
896 if ((reg = allocReg (REG_GPR)))
900 if ((reg = allocReg (REG_PTR)))
903 /* we have to spil */
904 if (!spilSomething (ic, ebp, sym))
907 /* this looks like an infinite loop but
908 in really selectSpil will abort */
912 /*-----------------------------------------------------------------*/
913 /* getRegPtrNoSpil - get it cannot split */
914 /*-----------------------------------------------------------------*/
915 static regs *getRegPtrNoSpil()
919 /* try for a ptr type */
920 if ((reg = allocReg (REG_PTR)))
923 /* try for gpr type */
924 if ((reg = allocReg (REG_GPR)))
929 /* just to make the compiler happy */
933 /*-----------------------------------------------------------------*/
934 /* getRegGprNoSpil - get it cannot split */
935 /*-----------------------------------------------------------------*/
936 static regs *getRegGprNoSpil()
940 if ((reg = allocReg (REG_GPR)))
944 if ((reg = allocReg (REG_PTR)))
949 /* just to make the compiler happy */
953 /*-----------------------------------------------------------------*/
954 /* symHasReg - symbol has a given register */
955 /*-----------------------------------------------------------------*/
957 symHasReg (symbol * sym, regs * reg)
961 for (i = 0; i < sym->nRegs; i++)
962 if (sym->regs[i] == reg)
968 /*-----------------------------------------------------------------*/
969 /* deassignLRs - check the live to and if they have registers & are */
970 /* not spilt then free up the registers */
971 /*-----------------------------------------------------------------*/
973 deassignLRs (iCode * ic, eBBlock * ebp)
979 for (sym = hTabFirstItem (liveRanges, &k); sym;
980 sym = hTabNextItem (liveRanges, &k))
984 /* if it does not end here */
985 if (sym->liveTo > ic->seq)
988 /* if it was spilt on stack then we can
989 mark the stack spil location as free */
994 sym->usl.spillLoc->isFree = 1;
1000 if (!bitVectBitValue (_G.regAssigned, sym->key))
1003 /* special case check if this is an IFX &
1004 the privious one was a pop and the
1005 previous one was not spilt then keep track
1007 if (ic->op == IFX && ic->prev &&
1008 ic->prev->op == IPOP &&
1009 !ic->prev->parmPush &&
1010 !OP_SYMBOL (IC_LEFT (ic->prev))->isspilt)
1011 psym = OP_SYMBOL (IC_LEFT (ic->prev));
1017 bitVectUnSetBit (_G.regAssigned, sym->key);
1019 /* if the result of this one needs registers
1020 and does not have it then assign it right
1022 if (IC_RESULT (ic) &&
1023 !(SKIP_IC2 (ic) || /* not a special icode */
1024 ic->op == JUMPTABLE ||
1029 POINTER_SET (ic)) &&
1030 (result = OP_SYMBOL (IC_RESULT (ic))) && /* has a result */
1031 result->liveTo > ic->seq && /* and will live beyond this */
1032 result->liveTo <= ebp->lSeq && /* does not go beyond this block */
1033 result->regType == sym->regType && /* same register types */
1034 result->nRegs && /* which needs registers */
1035 !result->isspilt && /* and does not already have them */
1037 !bitVectBitValue (_G.regAssigned, result->key) &&
1038 /* the number of free regs + number of regs in this LR
1039 can accomodate the what result Needs */
1040 ((nfreeRegsType (result->regType) +
1041 sym->nRegs) >= result->nRegs)
1045 for (i = 0; i < result->nRegs; i++)
1047 result->regs[i] = sym->regs[i];
1049 result->regs[i] = getRegGpr (ic, ebp, result);
1051 _G.regAssigned = bitVectSetBit (_G.regAssigned, result->key);
1052 _G.totRegAssigned = bitVectSetBit (_G.totRegAssigned, result->key);
1056 /* free the remaining */
1057 for (; i < sym->nRegs; i++)
1061 if (!symHasReg (psym, sym->regs[i]))
1062 hc08_freeReg (sym->regs[i]);
1065 hc08_freeReg (sym->regs[i]);
1072 /*-----------------------------------------------------------------*/
1073 /* reassignLR - reassign this to registers */
1074 /*-----------------------------------------------------------------*/
1076 reassignLR (operand * op)
1078 symbol *sym = OP_SYMBOL (op);
1081 /* not spilt any more */
1082 sym->isspilt = sym->spillA = sym->blockSpil = sym->remainSpil = 0;
1083 bitVectUnSetBit (_G.spiltSet, sym->key);
1085 _G.regAssigned = bitVectSetBit (_G.regAssigned, sym->key);
1086 _G.totRegAssigned = bitVectSetBit (_G.totRegAssigned, sym->key);
1090 for (i = 0; i < sym->nRegs; i++)
1091 sym->regs[i]->isFree = 0;
1094 /*-----------------------------------------------------------------*/
1095 /* willCauseSpill - determines if allocating will cause a spill */
1096 /*-----------------------------------------------------------------*/
1098 willCauseSpill (int nr, int rt)
1100 /* first check if there are any avlb registers
1101 of te type required */
1104 /* special case for pointer type
1105 if pointer type not avlb then
1106 check for type gpr */
1107 if (nFreeRegs (rt) >= nr)
1109 if (nFreeRegs (REG_GPR) >= nr)
1116 if (nFreeRegs (rt) >= nr)
1121 if (nFreeRegs (REG_PTR) +
1122 nFreeRegs (REG_GPR) >= nr)
1127 /* it will cause a spil */
1131 /*-----------------------------------------------------------------*/
1132 /* positionRegs - the allocator can allocate same registers to res- */
1133 /* ult and operand, if this happens make sure they are in the same */
1134 /* position as the operand otherwise chaos results */
1135 /*-----------------------------------------------------------------*/
1137 positionRegs (symbol * result, symbol * opsym)
1139 int count = min (result->nRegs, opsym->nRegs);
1140 int i, j = 0, shared = 0;
1143 /* if the result has been spilt then cannot share */
1148 /* first make sure that they actually share */
1149 for (i = 0; i < count; i++)
1151 for (j = 0; j < count; j++)
1153 if (result->regs[i] == opsym->regs[j] && i != j)
1163 regs *tmp = result->regs[i];
1164 result->regs[i] = result->regs[j];
1165 result->regs[j] = tmp;
1172 /*-----------------------------------------------------------------*/
1173 /* serialRegAssign - serially allocate registers to the variables */
1174 /*-----------------------------------------------------------------*/
1176 serialRegAssign (eBBlock ** ebbs, int count)
1180 /* for all blocks */
1181 for (i = 0; i < count; i++) {
1185 if (ebbs[i]->noPath &&
1186 (ebbs[i]->entryLabel != entryLabel &&
1187 ebbs[i]->entryLabel != returnLabel))
1190 /* of all instructions do */
1191 for (ic = ebbs[i]->sch; ic; ic = ic->next) {
1195 // update the registers in use at the start of this icode
1196 for (reg=0; reg<hc08_nRegs; reg++) {
1197 if (regshc08[reg].isFree) {
1198 ic->riu &= ~(regshc08[reg].mask);
1200 ic->riu |= (regshc08[reg].mask);
1205 /* if this is an ipop that means some live
1206 range will have to be assigned again */
1208 reassignLR (IC_LEFT (ic));
1210 /* if result is present && is a true symbol */
1211 if (IC_RESULT (ic) && ic->op != IFX &&
1212 IS_TRUE_SYMOP (IC_RESULT (ic)))
1213 OP_SYMBOL (IC_RESULT (ic))->allocreq++;
1215 /* take away registers from live
1216 ranges that end at this instruction */
1217 deassignLRs (ic, ebbs[i]);
1219 /* some don't need registers */
1220 if (SKIP_IC2 (ic) ||
1221 ic->op == JUMPTABLE ||
1225 (IC_RESULT (ic) && POINTER_SET (ic)))
1228 /* now we need to allocate registers
1229 only for the result */
1230 if (IC_RESULT (ic)) {
1231 symbol *sym = OP_SYMBOL (IC_RESULT (ic));
1237 /* if it does not need or is spilt
1238 or is already assigned to registers
1239 or will not live beyond this instructions */
1242 bitVectBitValue (_G.regAssigned, sym->key) ||
1243 sym->liveTo <= ic->seq)
1246 /* if some liverange has been spilt at the block level
1247 and this one live beyond this block then spil this
1249 if (_G.blockSpil && sym->liveTo > ebbs[i]->lSeq) {
1253 /* if trying to allocate this will cause
1254 a spill and there is nothing to spill
1255 or this one is rematerializable then
1257 willCS = willCauseSpill (sym->nRegs, sym->regType);
1258 spillable = computeSpillable (ic);
1259 if (sym->remat || (willCS && bitVectIsZero (spillable))) {
1264 /* if it has a spillocation & is used less than
1265 all other live ranges then spill this */
1267 if (sym->usl.spillLoc) {
1268 symbol *leastUsed = leastUsedLR (liveRangesWith (spillable,
1269 allLRs, ebbs[i], ic));
1270 if (leastUsed && leastUsed->used > sym->used) {
1275 /* if none of the liveRanges have a spillLocation then better
1276 to spill this one than anything else already assigned to registers */
1277 if (liveRangesWith(spillable,noSpilLoc,ebbs[i],ic)) {
1278 /* if this is local to this block then we might find a block spil */
1279 if (!(sym->liveFrom >= ebbs[i]->fSeq && sym->liveTo <= ebbs[i]->lSeq)) {
1286 /* if we need ptr regs for the right side
1288 if (POINTER_GET (ic) && IS_SYMOP (IC_LEFT (ic))
1289 && getSize (OP_SYMBOL (IC_LEFT (ic))->type) <= (unsigned int) PTRSIZE) {
1293 /* else we assign registers to it */
1294 _G.regAssigned = bitVectSetBit (_G.regAssigned, sym->key);
1295 _G.totRegAssigned = bitVectSetBit (_G.totRegAssigned, sym->key);
1297 for (j = 0; j < sym->nRegs; j++) {
1298 if (sym->regType == REG_PTR)
1299 sym->regs[j] = getRegPtr (ic, ebbs[i], sym);
1301 sym->regs[j] = getRegGpr (ic, ebbs[i], sym);
1303 /* if the allocation failed which means
1304 this was spilt then break */
1305 if (!sym->regs[j]) {
1310 /* if it shares registers with operands make sure
1311 that they are in the same position */
1312 if (IC_LEFT (ic) && IS_SYMOP (IC_LEFT (ic)) &&
1313 OP_SYMBOL (IC_LEFT (ic))->nRegs && ic->op != '=') {
1314 positionRegs (OP_SYMBOL (IC_RESULT (ic)),
1315 OP_SYMBOL (IC_LEFT (ic)));
1317 /* do the same for the right operand */
1318 if (IC_RIGHT (ic) && IS_SYMOP (IC_RIGHT (ic)) &&
1319 OP_SYMBOL (IC_RIGHT (ic))->nRegs) {
1320 positionRegs (OP_SYMBOL (IC_RESULT (ic)),
1321 OP_SYMBOL (IC_RIGHT (ic)));
1334 /*-----------------------------------------------------------------*/
1335 /* fillGaps - Try to fill in the Gaps left by Pass1 */
1336 /*-----------------------------------------------------------------*/
1337 static void fillGaps()
1342 if (getenv("DISABLE_FILL_GAPS")) return;
1344 /* look for livernages that was spilt by the allocator */
1345 for (sym = hTabFirstItem(liveRanges,&key) ; sym ;
1346 sym = hTabNextItem(liveRanges,&key)) {
1351 if (!sym->spillA || !sym->clashes || sym->remat) continue ;
1353 /* find the liveRanges this one clashes with, that are
1354 still assigned to registers & mark the registers as used*/
1355 for ( i = 0 ; i < sym->clashes->size ; i ++) {
1359 if (bitVectBitValue(sym->clashes,i) == 0 || /* those that clash with this */
1360 bitVectBitValue(_G.totRegAssigned,i) == 0) /* and are still assigned to registers */
1363 clr = hTabItemWithKey(liveRanges,i);
1366 /* mark these registers as used */
1367 for (k = 0 ; k < clr->nRegs ; k++ )
1368 hc08_useReg(clr->regs[k]);
1371 if (willCauseSpill(sym->nRegs,sym->regType)) {
1372 /* NOPE :( clear all registers & and continue */
1377 /* THERE IS HOPE !!!! */
1378 for (i=0; i < sym->nRegs ; i++ ) {
1379 if (sym->regType == REG_PTR)
1380 sym->regs[i] = getRegPtrNoSpil ();
1382 sym->regs[i] = getRegGprNoSpil ();
1385 /* for all its definitions check if the registers
1386 allocated needs positioning NOTE: we can position
1387 only ONCE if more than One positioning required
1390 for (i = 0 ; i < sym->defs->size ; i++ ) {
1391 if (bitVectBitValue(sym->defs,i)) {
1393 if (!(ic = hTabItemWithKey(iCodehTab,i))) continue ;
1394 if (SKIP_IC(ic)) continue;
1395 assert(isSymbolEqual(sym,OP_SYMBOL(IC_RESULT(ic)))); /* just making sure */
1396 /* if left is assigned to registers */
1397 if (IS_SYMOP(IC_LEFT(ic)) &&
1398 bitVectBitValue(_G.totRegAssigned,OP_SYMBOL(IC_LEFT(ic))->key)) {
1399 pdone += positionRegs(sym,OP_SYMBOL(IC_LEFT(ic)));
1401 if (IS_SYMOP(IC_RIGHT(ic)) &&
1402 bitVectBitValue(_G.totRegAssigned,OP_SYMBOL(IC_RIGHT(ic))->key)) {
1403 pdone += positionRegs(sym,OP_SYMBOL(IC_RIGHT(ic)));
1405 if (pdone > 1) break;
1408 for (i = 0 ; i < sym->uses->size ; i++ ) {
1409 if (bitVectBitValue(sym->uses,i)) {
1411 if (!(ic = hTabItemWithKey(iCodehTab,i))) continue ;
1412 if (SKIP_IC(ic)) continue;
1413 if (!IS_ASSIGN_ICODE(ic)) continue ;
1415 /* if result is assigned to registers */
1416 if (IS_SYMOP(IC_RESULT(ic)) &&
1417 bitVectBitValue(_G.totRegAssigned,OP_SYMBOL(IC_RESULT(ic))->key)) {
1418 pdone += positionRegs(sym,OP_SYMBOL(IC_RESULT(ic)));
1420 if (pdone > 1) break;
1423 /* had to position more than once GIVE UP */
1425 /* UNDO all the changes we made to try this */
1427 for (i=0; i < sym->nRegs ; i++ ) {
1428 sym->regs[i] = NULL;
1431 D(printf ("Fill Gap gave up due to positioning for %s in function %s\n",sym->name, currFunc ? currFunc->name : "UNKNOWN"));
1434 D(printf ("FILLED GAP for %s in function %s\n",sym->name, currFunc ? currFunc->name : "UNKNOWN"));
1435 _G.totRegAssigned = bitVectSetBit(_G.totRegAssigned,sym->key);
1436 sym->isspilt = sym->spillA = 0 ;
1437 sym->usl.spillLoc->allocreq--;
1442 /*-----------------------------------------------------------------*/
1443 /* rUmaskForOp :- returns register mask for an operand */
1444 /*-----------------------------------------------------------------*/
1446 hc08_rUmaskForOp (operand * op)
1452 /* only temporaries are assigned registers */
1456 sym = OP_SYMBOL (op);
1458 /* if spilt or no registers assigned to it
1460 if (sym->isspilt || !sym->nRegs)
1463 rumask = newBitVect (hc08_nRegs);
1465 for (j = 0; j < sym->nRegs; j++)
1467 rumask = bitVectSetBit (rumask,
1468 sym->regs[j]->rIdx);
1474 /*-----------------------------------------------------------------*/
1475 /* regsUsedIniCode :- returns bit vector of registers used in iCode */
1476 /*-----------------------------------------------------------------*/
1478 regsUsedIniCode (iCode * ic)
1480 bitVect *rmask = newBitVect (hc08_nRegs);
1482 /* do the special cases first */
1485 rmask = bitVectUnion (rmask,
1486 hc08_rUmaskForOp (IC_COND (ic)));
1490 /* for the jumptable */
1491 if (ic->op == JUMPTABLE)
1493 rmask = bitVectUnion (rmask,
1494 hc08_rUmaskForOp (IC_JTCOND (ic)));
1499 /* of all other cases */
1501 rmask = bitVectUnion (rmask,
1502 hc08_rUmaskForOp (IC_LEFT (ic)));
1506 rmask = bitVectUnion (rmask,
1507 hc08_rUmaskForOp (IC_RIGHT (ic)));
1510 rmask = bitVectUnion (rmask,
1511 hc08_rUmaskForOp (IC_RESULT (ic)));
1517 /*-----------------------------------------------------------------*/
1518 /* createRegMask - for each instruction will determine the regsUsed */
1519 /*-----------------------------------------------------------------*/
1521 createRegMask (eBBlock ** ebbs, int count)
1525 /* for all blocks */
1526 for (i = 0; i < count; i++)
1530 if (ebbs[i]->noPath &&
1531 (ebbs[i]->entryLabel != entryLabel &&
1532 ebbs[i]->entryLabel != returnLabel))
1535 /* for all instructions */
1536 for (ic = ebbs[i]->sch; ic; ic = ic->next)
1541 if (SKIP_IC2 (ic) || !ic->rlive)
1544 /* first mark the registers used in this
1546 ic->rUsed = regsUsedIniCode (ic);
1547 _G.funcrUsed = bitVectUnion (_G.funcrUsed, ic->rUsed);
1549 /* now create the register mask for those
1550 registers that are in use : this is a
1551 super set of ic->rUsed */
1552 ic->rMask = newBitVect (hc08_nRegs + 1);
1554 /* for all live Ranges alive at this point */
1555 for (j = 1; j < ic->rlive->size; j++)
1560 /* if not alive then continue */
1561 if (!bitVectBitValue (ic->rlive, j))
1564 /* find the live range we are interested in */
1565 if (!(sym = hTabItemWithKey (liveRanges, j)))
1567 werror (E_INTERNAL_ERROR, __FILE__, __LINE__,
1568 "createRegMask cannot find live range");
1569 fprintf(stderr, "\tmissing live range: key=%d\n", j);
1573 /* if no register assigned to it */
1574 if (!sym->nRegs || sym->isspilt)
1577 /* for all the registers allocated to it */
1578 for (k = 0; k < sym->nRegs; k++)
1581 bitVectSetBit (ic->rMask, sym->regs[k]->rIdx);
1587 /*-----------------------------------------------------------------*/
1588 /* rematStr - returns the rematerialized string for a remat var */
1589 /*-----------------------------------------------------------------*/
1591 rematStr (symbol * sym)
1594 iCode *ic = sym->rematiCode;
1599 /* if plus or minus print the right hand side */
1600 if (ic->op == '+' || ic->op == '-')
1602 sprintf (s, "0x%04x %c ", (int) operandLitValue (IC_RIGHT (ic)),
1605 ic = OP_SYMBOL (IC_LEFT (ic))->rematiCode;
1612 offset += operandLitValue (IC_RIGHT (ic));
1613 ic = OP_SYMBOL (IC_LEFT (ic))->rematiCode;
1618 offset -= operandLitValue (IC_RIGHT (ic));
1619 ic = OP_SYMBOL (IC_LEFT (ic))->rematiCode;
1623 /* cast then continue */
1624 if (IS_CAST_ICODE(ic)) {
1625 ic = OP_SYMBOL (IC_RIGHT (ic))->rematiCode;
1628 /* we reached the end */
1629 if (ic->op == ADDRESS_OF)
1630 sprintf (s, "%s", OP_SYMBOL (IC_LEFT (ic))->rname);
1631 else if (ic->op == '=')
1632 sprintf (s, "0x%04x", (int) operandLitValue (IC_RIGHT (ic)) );
1639 /*-----------------------------------------------------------------*/
1640 /* regTypeNum - computes the type & number of registers required */
1641 /*-----------------------------------------------------------------*/
1643 regTypeNum (eBBlock *ebbs)
1649 /* for each live range do */
1650 for (sym = hTabFirstItem (liveRanges, &k); sym;
1651 sym = hTabNextItem (liveRanges, &k))
1654 /* if used zero times then no registers needed */
1655 if ((sym->liveTo - sym->liveFrom) == 0)
1659 /* if the live range is a temporary */
1663 /* if the type is marked as a conditional */
1664 if (sym->regType == REG_CND)
1667 /* if used in return only then we don't
1669 if (sym->ruonly || sym->accuse)
1671 if (IS_AGGREGATE (sym->type) || sym->isptr)
1672 sym->type = aggrToPtr (sym->type, FALSE);
1676 /* if the symbol has only one definition &
1677 that definition is a get_pointer */
1678 if (bitVectnBitsOn (sym->defs) == 1 &&
1679 (ic = hTabItemWithKey (iCodehTab,
1680 bitVectFirstBit (sym->defs))) &&
1683 !IS_BITVAR (sym->etype))
1687 /* and that pointer is remat in data space */
1688 if (IS_SYMOP (IC_LEFT (ic)) &&
1689 OP_SYMBOL (IC_LEFT (ic))->remat &&
1690 !IS_CAST_ICODE(OP_SYMBOL (IC_LEFT (ic))->rematiCode) &&
1691 DCL_TYPE (aggrToPtr (operandType(IC_LEFT(ic)), FALSE)) == POINTER)
1693 /* create a psuedo symbol & force a spil */
1694 symbol *psym = newSymbol (rematStr (OP_SYMBOL (IC_LEFT (ic))), 1);
1695 psym->type = sym->type;
1696 psym->etype = sym->etype;
1697 strcpy (psym->rname, psym->name);
1699 sym->usl.spillLoc = psym;
1700 #if 0 // an alternative fix for bug #480076
1701 /* now this is a useless assignment to itself */
1702 remiCodeFromeBBlock (ebbs, ic);
1704 /* now this really is an assignment to itself, make it so;
1705 it will be optimized out later */
1707 ReplaceOpWithCheaperOp(&IC_RIGHT(ic), IC_RESULT(ic));
1713 /* if in data space or idata space then try to
1714 allocate pointer register */
1718 /* if not then we require registers */
1719 sym->nRegs = ((IS_AGGREGATE (sym->type) || sym->isptr) ?
1720 getSize (sym->type = aggrToPtr (sym->type, FALSE)) :
1721 getSize (sym->type));
1725 fprintf (stderr, "allocated more than 4 or 0 registers for type ");
1726 printTypeChain (sym->type, stderr);
1727 fprintf (stderr, "\n");
1730 /* determine the type of register required */
1731 if (sym->nRegs == 1 &&
1732 IS_PTR (sym->type) &&
1734 sym->regType = REG_PTR;
1736 sym->regType = REG_GPR;
1740 /* for the first run we don't provide */
1741 /* registers for true symbols we will */
1742 /* see how things go */
1748 /*-----------------------------------------------------------------*/
1749 /* freeAllRegs - mark all registers as free */
1750 /*-----------------------------------------------------------------*/
1756 for (i = 0; i < hc08_nRegs; i++) {
1757 regshc08[i].isFree = 1;
1758 regshc08[i].aop = NULL;
1762 /*-----------------------------------------------------------------*/
1763 /* deallocStackSpil - this will set the stack pointer back */
1764 /*-----------------------------------------------------------------*/
1766 DEFSETFUNC (deallocStackSpil)
1775 /*-----------------------------------------------------------------*/
1776 /* farSpacePackable - returns the packable icode for far variables */
1777 /*-----------------------------------------------------------------*/
1779 farSpacePackable (iCode * ic)
1783 /* go thru till we find a definition for the
1784 symbol on the right */
1785 for (dic = ic->prev; dic; dic = dic->prev)
1787 /* if the definition is a call then no */
1788 if ((dic->op == CALL || dic->op == PCALL) &&
1789 IC_RESULT (dic)->key == IC_RIGHT (ic)->key)
1794 /* if shift by unknown amount then not */
1795 if ((dic->op == LEFT_OP || dic->op == RIGHT_OP) &&
1796 IC_RESULT (dic)->key == IC_RIGHT (ic)->key)
1800 /* if pointer get and size > 1 */
1801 if (POINTER_GET (dic) &&
1802 getSize (aggrToPtr (operandType (IC_LEFT (dic)), FALSE)) > 1)
1805 if (POINTER_SET (dic) &&
1806 getSize (aggrToPtr (operandType (IC_RESULT (dic)), FALSE)) > 1)
1810 /* if any three is a true symbol in far space */
1811 if (IC_RESULT (dic) &&
1812 IS_TRUE_SYMOP (IC_RESULT (dic)) /* &&
1813 isOperandInFarSpace (IC_RESULT (dic)) */)
1816 if (IC_RIGHT (dic) &&
1817 IS_TRUE_SYMOP (IC_RIGHT (dic)) /* &&
1818 isOperandInFarSpace (IC_RIGHT (dic)) */ &&
1819 !isOperandEqual (IC_RIGHT (dic), IC_RESULT (ic)))
1822 if (IC_LEFT (dic) &&
1823 IS_TRUE_SYMOP (IC_LEFT (dic)) /* &&
1824 isOperandInFarSpace (IC_LEFT (dic)) */ &&
1825 !isOperandEqual (IC_LEFT (dic), IC_RESULT (ic)))
1828 if (isOperandEqual (IC_RIGHT (ic), IC_RESULT (dic)))
1830 if ((dic->op == LEFT_OP ||
1831 dic->op == RIGHT_OP ||
1833 IS_OP_LITERAL (IC_RIGHT (dic)))
1846 packRegsForLiteral (iCode * ic)
1853 if (POINTER_SET (ic))
1855 if (!IS_LITERAL (getSpec (operandType (IC_RIGHT (ic)))))
1857 if (bitVectnBitsOn (OP_DEFS (IC_RESULT (ic))) > 1)
1860 for (k=0; k< OP_USES (IC_RESULT (ic))->size; k++)
1861 if (bitVectBitValue (OP_USES (IC_RESULT (ic)), k))
1863 uic = hTabItemWithKey (iCodehTab, k);
1866 if (uic->op != IFX && uic->op != JUMPTABLE)
1868 if (IC_LEFT (uic) && IC_LEFT (uic)->key == IC_RESULT (ic)->key)
1869 ReplaceOpWithCheaperOp(&IC_LEFT(uic), IC_RIGHT(ic));
1870 if (IC_RIGHT (uic) && IC_RIGHT (uic)->key == IC_RESULT (ic)->key)
1871 ReplaceOpWithCheaperOp(&IC_RIGHT(uic), IC_RIGHT(ic));
1872 if (IC_RESULT (uic) && IC_RESULT (uic)->key == IC_RESULT (ic)->key)
1873 ReplaceOpWithCheaperOp(&IC_RESULT(uic), IC_RIGHT(ic));
1881 /*-----------------------------------------------------------------*/
1882 /* packRegsForAssign - register reduction for assignment */
1883 /*-----------------------------------------------------------------*/
1885 packRegsForAssign (iCode * ic, eBBlock * ebp)
1889 if (!IS_ITEMP (IC_RIGHT (ic)) ||
1890 OP_SYMBOL (IC_RIGHT (ic))->isind ||
1891 OP_LIVETO (IC_RIGHT (ic)) > ic->seq)
1897 /* if the true symbol is defined in far space or on stack
1898 then we should not since this will increase register pressure */
1900 if (isOperandInFarSpace(IC_RESULT(ic)) && !farSpacePackable(ic)) {
1905 /* find the definition of iTempNN scanning backwards if we find a
1906 a use of the true symbol in before we find the definition then
1908 for (dic = ic->prev; dic; dic = dic->prev)
1911 #if 0 /* jwk: This collides with 1.43 but I really see no need for
1912 this anymore. It fixes bug #716790 and substantially improves
1913 redundant register usage around function calls.
1916 /* if there is a function call then don't pack it */
1917 if ((dic->op == CALL || dic->op == PCALL))
1927 if (IS_TRUE_SYMOP (IC_RESULT (dic)) &&
1928 IS_OP_VOLATILE (IC_RESULT (dic)))
1934 if (IS_SYMOP (IC_RESULT (dic)) &&
1935 IC_RESULT (dic)->key == IC_RIGHT (ic)->key)
1937 if (POINTER_SET (dic))
1943 if (IS_SYMOP (IC_RIGHT (dic)) &&
1944 (IC_RIGHT (dic)->key == IC_RESULT (ic)->key ||
1945 IC_RIGHT (dic)->key == IC_RIGHT (ic)->key))
1951 if (IS_SYMOP (IC_LEFT (dic)) &&
1952 (IC_LEFT (dic)->key == IC_RESULT (ic)->key ||
1953 IC_LEFT (dic)->key == IC_RIGHT (ic)->key))
1959 if (POINTER_SET (dic) &&
1960 IC_RESULT (dic)->key == IC_RESULT (ic)->key)
1968 return 0; /* did not find */
1970 /* if assignment then check that right is not a bit */
1971 if (ASSIGNMENT (dic) && !POINTER_SET (dic))
1973 sym_link *etype = operandType (IC_RIGHT (dic));
1974 if (IS_BITFIELD (etype))
1976 /* if result is a bit too then it's ok */
1977 etype = operandType (IC_RESULT (dic));
1978 if (!IS_BITFIELD (etype))
1982 /* if the result is on stack or iaccess then it must be
1983 the same atleast one of the operands */
1984 if (OP_SYMBOL (IC_RESULT (ic))->onStack ||
1985 OP_SYMBOL (IC_RESULT (ic))->iaccess)
1988 /* the operation has only one symbol
1989 operator then we can pack */
1990 if ((IC_LEFT (dic) && !IS_SYMOP (IC_LEFT (dic))) ||
1991 (IC_RIGHT (dic) && !IS_SYMOP (IC_RIGHT (dic))))
1994 if (!((IC_LEFT (dic) &&
1995 IC_RESULT (ic)->key == IC_LEFT (dic)->key) ||
1997 IC_RESULT (ic)->key == IC_RIGHT (dic)->key)))
2001 /* found the definition */
2002 /* replace the result with the result of */
2003 /* this assignment and remove this assignment */
2004 bitVectUnSetBit(OP_SYMBOL(IC_RESULT(dic))->defs,dic->key);
2005 ReplaceOpWithCheaperOp(&IC_RESULT (dic), IC_RESULT (ic));
2007 if (IS_ITEMP (IC_RESULT (dic)) && OP_SYMBOL (IC_RESULT (dic))->liveFrom > dic->seq)
2009 OP_SYMBOL (IC_RESULT (dic))->liveFrom = dic->seq;
2011 // TODO: and the otherway around?
2013 /* delete from liverange table also
2014 delete from all the points inbetween and the new
2016 for (sic = dic; sic != ic; sic = sic->next)
2018 bitVectUnSetBit (sic->rlive, IC_RESULT (ic)->key);
2019 if (IS_ITEMP (IC_RESULT (dic)))
2020 bitVectSetBit (sic->rlive, IC_RESULT (dic)->key);
2023 remiCodeFromeBBlock (ebp, ic);
2024 bitVectUnSetBit(OP_SYMBOL(IC_RESULT(ic))->defs,ic->key);
2025 hTabDeleteItem (&iCodehTab, ic->key, ic, DELETE_ITEM, NULL);
2026 OP_DEFS(IC_RESULT (dic))=bitVectSetBit (OP_DEFS (IC_RESULT (dic)), dic->key);
2031 /*------------------------------------------------------------------*/
2032 /* findAssignToSym : scanning backwards looks for first assig found */
2033 /*------------------------------------------------------------------*/
2035 findAssignToSym (operand * op, iCode * ic)
2039 /* This routine is used to find sequences like
2041 ...; (intervening ops don't use iTempAA or modify FOO)
2042 blah = blah + iTempAA;
2044 and eliminate the use of iTempAA, freeing up its register for
2049 for (dic = ic->prev; dic; dic = dic->prev)
2052 /* if definition by assignment */
2053 if (dic->op == '=' &&
2054 !POINTER_SET (dic) &&
2055 IC_RESULT (dic)->key == op->key
2056 && IS_TRUE_SYMOP(IC_RIGHT(dic))
2058 break; /* found where this temp was defined */
2060 /* if we find an usage then we cannot delete it */
2061 if (IC_LEFT (dic) && IC_LEFT (dic)->key == op->key)
2064 if (IC_RIGHT (dic) && IC_RIGHT (dic)->key == op->key)
2067 if (POINTER_SET (dic) && IC_RESULT (dic)->key == op->key)
2072 return NULL; /* didn't find any assignment to op */
2074 /* we are interested only if defined in far space */
2075 /* or in stack space in case of + & - */
2077 /* if assigned to a non-symbol then don't repack regs */
2078 if (!IS_SYMOP (IC_RIGHT (dic)))
2081 /* if the symbol is volatile then we should not */
2082 if (isOperandVolatile (IC_RIGHT (dic), TRUE))
2084 /* XXX TODO --- should we be passing FALSE to isOperandVolatile()?
2085 What does it mean for an iTemp to be volatile, anyway? Passing
2086 TRUE is more cautious but may prevent possible optimizations */
2088 /* if the symbol is in far space then we should not */
2089 /* if (isOperandInFarSpace (IC_RIGHT (dic)))
2092 /* for + & - operations make sure that
2093 if it is on the stack it is the same
2094 as one of the three operands */
2096 if ((ic->op == '+' || ic->op == '-') &&
2097 OP_SYMBOL (IC_RIGHT (dic))->onStack)
2100 if (IC_RESULT (ic)->key != IC_RIGHT (dic)->key &&
2101 IC_LEFT (ic)->key != IC_RIGHT (dic)->key &&
2102 IC_RIGHT (ic)->key != IC_RIGHT (dic)->key)
2107 /* now make sure that the right side of dic
2108 is not defined between ic & dic */
2111 iCode *sic = dic->next;
2113 for (; sic != ic; sic = sic->next)
2114 if (IC_RESULT (sic) &&
2115 IC_RESULT (sic)->key == IC_RIGHT (dic)->key)
2122 /*-----------------------------------------------------------------*/
2123 /* reassignAliasedSym - used by packRegsForSupport to replace */
2124 /* redundant iTemp with equivalent symbol */
2125 /*-----------------------------------------------------------------*/
2127 reassignAliasedSym (eBBlock *ebp, iCode *assignment, iCode *use, operand *op)
2130 unsigned oldSymKey, newSymKey;
2132 oldSymKey = op->key;
2133 newSymKey = IC_RIGHT(assignment)->key;
2135 /* only track live ranges of compiler-generated temporaries */
2136 if (!IS_ITEMP(IC_RIGHT(assignment)))
2139 /* update the live-value bitmaps */
2140 for (ic = assignment; ic != use; ic = ic->next) {
2141 bitVectUnSetBit (ic->rlive, oldSymKey);
2143 ic->rlive = bitVectSetBit (ic->rlive, newSymKey);
2146 /* update the sym of the used operand */
2147 OP_SYMBOL(op) = OP_SYMBOL(IC_RIGHT(assignment));
2148 op->key = OP_SYMBOL(op)->key;
2150 /* update the sym's liverange */
2151 if ( OP_LIVETO(op) < ic->seq )
2152 setToRange(op, ic->seq, FALSE);
2154 /* remove the assignment iCode now that its result is unused */
2155 remiCodeFromeBBlock (ebp, assignment);
2156 bitVectUnSetBit(OP_SYMBOL(IC_RESULT(assignment))->defs, assignment->key);
2157 hTabDeleteItem (&iCodehTab, assignment->key, assignment, DELETE_ITEM, NULL);
2161 /*-----------------------------------------------------------------*/
2162 /* packRegsForSupport :- reduce some registers for support calls */
2163 /*-----------------------------------------------------------------*/
2165 packRegsForSupport (iCode * ic, eBBlock * ebp)
2170 /* for the left & right operand :- look to see if the
2171 left was assigned a true symbol in far space in that
2172 case replace them */
2174 if (IS_ITEMP (IC_LEFT (ic)) &&
2175 OP_SYMBOL (IC_LEFT (ic))->liveTo <= ic->seq)
2177 dic = findAssignToSym (IC_LEFT (ic), ic);
2181 /* found it we need to remove it from the block */
2182 reassignAliasedSym (ebp, dic, ic, IC_LEFT(ic));
2187 /* do the same for the right operand */
2188 if (IS_ITEMP (IC_RIGHT (ic)) &&
2189 OP_SYMBOL (IC_RIGHT (ic))->liveTo <= ic->seq)
2191 iCode *dic = findAssignToSym (IC_RIGHT (ic), ic);
2195 /* found it we need to remove it from the block */
2196 reassignAliasedSym (ebp, dic, ic, IC_RIGHT(ic));
2204 #define IS_OP_RUONLY(x) (x && IS_SYMOP(x) && OP_SYMBOL(x)->ruonly)
2208 /*-----------------------------------------------------------------*/
2209 /* packRegsForOneuse : - will reduce some registers for single Use */
2210 /*-----------------------------------------------------------------*/
2212 packRegsForOneuse (iCode * ic, operand * op, eBBlock * ebp)
2217 /* if returning a literal then do nothing */
2221 /* only up to 2 bytes */
2222 if (getSize (operandType (op)) > (fReturnSizeHC08 - 2))
2227 if (ic->op != SEND //RETURN
2229 && !POINTER_SET (ic)
2230 && !POINTER_GET (ic) )
2233 if (ic->op == SEND && ic->argreg != 1) return NULL;
2235 /* this routine will mark the a symbol as used in one
2236 instruction use only && if the defintion is local
2237 (ie. within the basic block) && has only one definition &&
2238 that definiion is either a return value from a
2239 function or does not contain any variables in
2241 uses = bitVectCopy (OP_USES (op));
2242 bitVectUnSetBit (uses, ic->key); /* take away this iCode */
2243 if (!bitVectIsZero (uses)) /* has other uses */
2246 /* if it has only one defintion */
2247 if (bitVectnBitsOn (OP_DEFS (op)) > 1)
2248 return NULL; /* has more than one definition */
2250 /* get that definition */
2252 hTabItemWithKey (iCodehTab,
2253 bitVectFirstBit (OP_DEFS (op)))))
2256 /* if that only usage is a cast */
2257 if (dic->op == CAST) {
2258 /* to a bigger type */
2259 if (getSize(OP_SYM_TYPE(IC_RESULT(dic))) >
2260 getSize(OP_SYM_TYPE(IC_RIGHT(dic)))) {
2261 /* than we can not, since we cannot predict the usage of b & acc */
2266 /* found the definition now check if it is local */
2267 if (dic->seq < ebp->fSeq ||
2268 dic->seq > ebp->lSeq)
2269 return NULL; /* non-local */
2271 /* now check if it is the return from
2273 if (dic->op == CALL || dic->op == PCALL)
2275 if (ic->op != SEND && ic->op != RETURN &&
2276 !POINTER_SET(ic) && !POINTER_GET(ic))
2278 OP_SYMBOL (op)->ruonly = 1;
2285 /* otherwise check that the definition does
2286 not contain any symbols in far space */
2287 // if (isOperandInFarSpace (IC_LEFT (dic)) ||
2288 // isOperandInFarSpace (IC_RIGHT (dic)) ||
2289 // IS_OP_RUONLY (IC_LEFT (ic)) ||
2290 // IS_OP_RUONLY (IC_RIGHT (ic)))
2295 /* if pointer set then make sure the pointer
2298 if (POINTER_SET (dic) &&
2299 !IS_DATA_PTR (aggrToPtr (operandType (IC_RESULT (dic)), FALSE)))
2302 if (POINTER_GET (dic) &&
2303 !IS_DATA_PTR (aggrToPtr (operandType (IC_LEFT (dic)), FALSE)))
2309 /* also make sure the intervenening instructions
2310 don't have any thing in far space */
2311 for (dic = dic->next; dic && dic != ic && sic != ic; dic = dic->next)
2314 /* if there is an intervening function call then no */
2315 if (dic->op == CALL || dic->op == PCALL)
2317 /* if pointer set then make sure the pointer
2320 if (POINTER_SET (dic) &&
2321 !IS_DATA_PTR (aggrToPtr (operandType (IC_RESULT (dic)), FALSE)))
2324 if (POINTER_GET (dic) &&
2325 !IS_DATA_PTR (aggrToPtr (operandType (IC_LEFT (dic)), FALSE)))
2328 /* if address of & the result is remat the okay */
2329 if (dic->op == ADDRESS_OF &&
2330 OP_SYMBOL (IC_RESULT (dic))->remat)
2333 /* if operand has size of three or more & this
2334 operation is a '*','/' or '%' then 'b' may
2337 if ((dic->op == '%' || dic->op == '/' || dic->op == '*') &&
2338 getSize (operandType (op)) >= 3)
2342 /* if left or right or result is in far space */
2343 // if (isOperandInFarSpace (IC_LEFT (dic)) ||
2344 // isOperandInFarSpace (IC_RIGHT (dic)) ||
2345 // isOperandInFarSpace (IC_RESULT (dic)) ||
2346 // IS_OP_RUONLY (IC_LEFT (dic)) ||
2347 // IS_OP_RUONLY (IC_RIGHT (dic)) ||
2348 // IS_OP_RUONLY (IC_RESULT (dic)))
2352 // /* if left or right or result is on stack */
2353 // if (isOperandOnStack(IC_LEFT(dic)) ||
2354 // isOperandOnStack(IC_RIGHT(dic)) ||
2355 // isOperandOnStack(IC_RESULT(dic))) {
2360 OP_SYMBOL (op)->ruonly = 1;
2365 /*-----------------------------------------------------------------*/
2366 /* isBitwiseOptimizable - requirements of JEAN LOUIS VERN */
2367 /*-----------------------------------------------------------------*/
2369 isBitwiseOptimizable (iCode * ic)
2371 sym_link *ltype = getSpec (operandType (IC_LEFT (ic)));
2372 sym_link *rtype = getSpec (operandType (IC_RIGHT (ic)));
2374 /* bitwise operations are considered optimizable
2375 under the following conditions (Jean-Louis VERN)
2387 if (IS_LITERAL(rtype) ||
2388 (IS_BITVAR (ltype) && IN_BITSPACE (SPEC_OCLS (ltype))))
2394 /*-----------------------------------------------------------------*/
2395 /* isCommutativeOp - tests whether this op cares what order its */
2396 /* operands are in */
2397 /*-----------------------------------------------------------------*/
2398 bool isCommutativeOp2(unsigned int op)
2400 if (op == '+' || op == '*' || op == EQ_OP ||
2401 op == '^' || op == '|' || op == BITWISEAND)
2407 /*-----------------------------------------------------------------*/
2408 /* operandUsesAcc2 - determines whether the code generated for this */
2409 /* operand will have to use the accumulator */
2410 /*-----------------------------------------------------------------*/
2411 bool operandUsesAcc2(operand *op)
2417 symbol *sym = OP_SYMBOL(op);
2421 return TRUE; /* duh! */
2423 // if (IN_STACK(sym->etype) || sym->onStack ||
2424 // (SPIL_LOC(op) && SPIL_LOC(op)->onStack))
2425 // return TRUE; /* acc is used to calc stack offset */
2430 sym = SPIL_LOC(op); /* if spilled, look at spill location */
2432 return FALSE; /* more checks? */
2436 symspace = SPEC_OCLS(sym->etype);
2438 // if (sym->iaccess && symspace->paged)
2439 // return TRUE; /* must fetch paged indirect sym via accumulator */
2441 if (IN_BITSPACE(symspace))
2442 return TRUE; /* fetching bit vars uses the accumulator */
2444 if (IN_FARSPACE(symspace) || IN_CODESPACE(symspace))
2445 return TRUE; /* fetched via accumulator and dptr */
2451 /*-----------------------------------------------------------------*/
2452 /* packRegsForAccUse - pack registers for acc use */
2453 /*-----------------------------------------------------------------*/
2455 packRegsForAccUse (iCode * ic)
2459 /* if this is an aggregate, e.g. a one byte char array */
2460 if (IS_AGGREGATE(operandType(IC_RESULT(ic)))) {
2464 /* if we are calling a reentrant function that has stack parameters */
2466 if (ic->op == CALL &&
2467 IFFUNC_ISREENT(operandType(IC_LEFT(ic))) &&
2468 FUNC_HASSTACKPARM(operandType(IC_LEFT(ic))))
2471 if (ic->op == PCALL &&
2472 IFFUNC_ISREENT(operandType(IC_LEFT(ic))->next) &&
2473 FUNC_HASSTACKPARM(operandType(IC_LEFT(ic))->next))
2477 /* if + or - then it has to be one byte result */
2478 if ((ic->op == '+' || ic->op == '-')
2479 && getSize (operandType (IC_RESULT (ic))) > 1)
2483 /* if shift operation make sure right side is a literal */
2484 if (ic->op == RIGHT_OP &&
2485 (!isOperandLiteral (IC_RIGHT (ic)) ||
2486 (getSize (operandType (IC_RESULT (ic) )) > 1)))
2489 if (ic->op == LEFT_OP &&
2490 (!isOperandLiteral (IC_RIGHT (ic)) ||
2491 (getSize (operandType (IC_RESULT (ic) )) > 1)))
2494 if (IS_BITWISE_OP (ic) &&
2495 getSize (operandType (IC_RESULT (ic))) > 1)
2499 /* has only one definition */
2500 if (bitVectnBitsOn (OP_DEFS (IC_RESULT (ic))) > 1)
2503 /* has only one use */
2504 if (bitVectnBitsOn (OP_USES (IC_RESULT (ic))) > 1)
2507 /* and the usage immediately follows this iCode */
2508 if (!(uic = hTabItemWithKey (iCodehTab,
2509 bitVectFirstBit (OP_USES (IC_RESULT (ic))))))
2512 if (ic->next != uic)
2515 /* if it is a conditional branch then we definitely can */
2519 if (uic->op == JUMPTABLE)
2523 if (POINTER_SET (uic) &&
2524 getSize (aggrToPtr (operandType (IC_RESULT (uic)), FALSE)) > 1)
2528 /* if the usage is not is an assignment
2529 or an arithmetic / bitwise / shift operation then not */
2530 if (uic->op != '=' &&
2531 !IS_ARITHMETIC_OP (uic) &&
2532 !IS_BITWISE_OP (uic) &&
2533 (uic->op != LEFT_OP) &&
2534 (uic->op != RIGHT_OP) &&
2535 (uic->op != GETHBIT) &&
2536 (uic->op != RETURN) &&
2542 /* if used in ^ operation then make sure right is not a
2543 literal (WIML: Why is this?) */
2544 if (uic->op == '^' && isOperandLiteral (IC_RIGHT (uic)))
2547 /* if shift operation make sure right side is not a literal */
2548 /* WIML: Why is this? */
2549 if (uic->op == RIGHT_OP &&
2550 (isOperandLiteral (IC_RIGHT (uic)) ||
2551 getSize (operandType (IC_RESULT (uic))) > 1))
2553 if (uic->op == LEFT_OP &&
2554 (isOperandLiteral (IC_RIGHT (uic)) ||
2555 getSize (operandType (IC_RESULT (uic))) > 1))
2559 /* make sure that the result of this icode is not on the
2560 stack, since acc is used to compute stack offset */
2562 if (IS_TRUE_SYMOP (IC_RESULT (uic)) &&
2563 OP_SYMBOL (IC_RESULT (uic))->onStack)
2566 // if (isOperandOnStack(IC_RESULT(uic)))
2570 /* if the usage has only one operand then we can */
2571 if (IC_LEFT (uic) == NULL ||
2572 IC_RIGHT (uic) == NULL)
2576 /* if the other operand uses the accumulator then we cannot */
2577 if ( (IC_LEFT(uic)->key == IC_RESULT(ic)->key &&
2578 operandUsesAcc2(IC_RIGHT(uic))) ||
2579 (IC_RIGHT(uic)->key == IC_RESULT(ic)->key &&
2580 operandUsesAcc2(IC_LEFT(uic))) )
2583 /* make sure this is on the left side if not commutative */
2584 /* except for '-', which has been written to be able to
2585 handle reversed operands */
2586 if (!(isCommutativeOp2(ic->op) || ic->op == '-') &&
2587 IC_LEFT (uic)->key != IC_RESULT (ic)->key)
2592 // this is too dangerous and need further restrictions
2595 /* if one of them is a literal then we can */
2596 if ((IC_LEFT (uic) && IS_OP_LITERAL (IC_LEFT (uic))) ||
2597 (IC_RIGHT (uic) && IS_OP_LITERAL (IC_RIGHT (uic))))
2599 OP_SYMBOL (IC_RESULT (ic))->accuse = 1;
2606 if ((POINTER_GET(uic))
2607 || (ic->op == ADDRESS_OF && uic->op == '+' && IS_OP_LITERAL (IC_RIGHT (uic))))
2609 OP_SYMBOL (IC_RESULT (ic))->accuse = ACCUSE_HX;
2613 OP_SYMBOL (IC_RESULT (ic))->accuse = ACCUSE_XA;
2616 /*-----------------------------------------------------------------*/
2617 /* packForPush - hueristics to reduce iCode for pushing */
2618 /*-----------------------------------------------------------------*/
2620 packForPush (iCode * ic, eBBlock ** ebpp, int blockno)
2624 struct eBBlock * ebp=ebpp[blockno];
2626 if (ic->op != IPUSH || !IS_ITEMP (IC_LEFT (ic)))
2629 /* must have only definition & one usage */
2630 if (bitVectnBitsOn (OP_DEFS (IC_LEFT (ic))) != 1 ||
2631 bitVectnBitsOn (OP_USES (IC_LEFT (ic))) != 1)
2634 /* find the definition */
2635 if (!(dic = hTabItemWithKey (iCodehTab,
2636 bitVectFirstBit (OP_DEFS (IC_LEFT (ic))))))
2639 if (dic->op != '=' || POINTER_SET (dic))
2642 if (dic->seq < ebp->fSeq) { // Evelyn did this
2644 for (i=0; i<blockno; i++) {
2645 if (dic->seq >= ebpp[i]->fSeq && dic->seq <= ebpp[i]->lSeq) {
2650 wassert (i!=blockno); // no way to recover from here
2653 if (IS_SYMOP(IC_RIGHT(dic))) {
2654 /* make sure the right side does not have any definitions
2656 dbv = OP_DEFS(IC_RIGHT(dic));
2657 for (lic = ic; lic && lic != dic ; lic = lic->prev) {
2658 if (bitVectBitValue(dbv,lic->key))
2661 /* make sure they have the same type */
2662 if (IS_SPEC(operandType(IC_LEFT(ic))))
2664 sym_link *itype=operandType(IC_LEFT(ic));
2665 sym_link *ditype=operandType(IC_RIGHT(dic));
2667 if (SPEC_USIGN(itype)!=SPEC_USIGN(ditype) ||
2668 SPEC_LONG(itype)!=SPEC_LONG(ditype))
2671 /* extend the live range of replaced operand if needed */
2672 if (OP_SYMBOL(IC_RIGHT(dic))->liveTo < ic->seq) {
2673 OP_SYMBOL(IC_RIGHT(dic))->liveTo = ic->seq;
2675 bitVectUnSetBit(OP_SYMBOL(IC_RESULT(dic))->defs,dic->key);
2678 /* we now we know that it has one & only one def & use
2679 and the that the definition is an assignment */
2680 ReplaceOpWithCheaperOp(&IC_LEFT (ic), IC_RIGHT (dic));
2681 remiCodeFromeBBlock (ebp, dic);
2682 hTabDeleteItem (&iCodehTab, dic->key, dic, DELETE_ITEM, NULL);
2685 /*-----------------------------------------------------------------*/
2686 /* packRegisters - does some transformations to reduce register */
2688 /*-----------------------------------------------------------------*/
2690 packRegisters (eBBlock ** ebpp, int blockno)
2694 eBBlock *ebp=ebpp[blockno];
2701 /* look for assignments of the form */
2702 /* iTempNN = TRueSym (someoperation) SomeOperand */
2704 /* TrueSym := iTempNN:1 */
2705 for (ic = ebp->sch; ic; ic = ic->next)
2707 /* find assignment of the form TrueSym := iTempNN:1 */
2708 if (ic->op == '=' && !POINTER_SET (ic) )
2709 change += packRegsForAssign (ic, ebp);
2716 for (ic = ebp->sch; ic; ic = ic->next)
2718 //packRegsForLiteral (ic);
2720 /* if this is an itemp & result of an address of a true sym
2721 then mark this as rematerialisable */
2722 if (ic->op == ADDRESS_OF &&
2723 IS_ITEMP (IC_RESULT (ic)) &&
2724 IS_TRUE_SYMOP (IC_LEFT (ic)) &&
2725 bitVectnBitsOn (OP_DEFS (IC_RESULT (ic))) == 1 &&
2726 !OP_SYMBOL (IC_LEFT (ic))->onStack )
2729 OP_SYMBOL (IC_RESULT (ic))->remat = 1;
2730 OP_SYMBOL (IC_RESULT (ic))->rematiCode = ic;
2731 OP_SYMBOL (IC_RESULT (ic))->usl.spillLoc = NULL;
2735 if (ic->op == '=' &&
2736 !POINTER_SET (ic) &&
2737 IS_ITEMP (IC_RESULT (ic)) &&
2738 IS_VALOP (IC_RIGHT (ic)) &&
2739 bitVectnBitsOn (OP_DEFS (IC_RESULT (ic))) == 1)
2742 OP_SYMBOL (IC_RESULT (ic))->remat = 1;
2743 OP_SYMBOL (IC_RESULT (ic))->rematiCode = ic;
2744 OP_SYMBOL (IC_RESULT (ic))->usl.spillLoc = NULL;
2748 /* if straight assignment then carry remat flag if
2749 this is the only definition */
2750 if (ic->op == '=' &&
2751 !POINTER_SET (ic) &&
2752 IS_SYMOP (IC_RIGHT (ic)) &&
2753 OP_SYMBOL (IC_RIGHT (ic))->remat &&
2754 !IS_CAST_ICODE(OP_SYMBOL (IC_RIGHT (ic))->rematiCode) &&
2755 bitVectnBitsOn (OP_SYMBOL (IC_RESULT (ic))->defs) <= 1)
2758 OP_SYMBOL (IC_RESULT (ic))->remat =
2759 OP_SYMBOL (IC_RIGHT (ic))->remat;
2760 OP_SYMBOL (IC_RESULT (ic))->rematiCode =
2761 OP_SYMBOL (IC_RIGHT (ic))->rematiCode;
2764 /* if cast to a generic pointer & the pointer being
2765 cast is remat, then we can remat this cast as well */
2766 if (ic->op == CAST &&
2767 IS_SYMOP(IC_RIGHT(ic)) &&
2768 OP_SYMBOL(IC_RIGHT(ic))->remat &&
2769 bitVectnBitsOn (OP_DEFS (IC_RESULT (ic))) == 1) {
2770 sym_link *to_type = operandType(IC_LEFT(ic));
2771 sym_link *from_type = operandType(IC_RIGHT(ic));
2772 if (IS_GENPTR(to_type) && IS_PTR(from_type)) {
2773 OP_SYMBOL (IC_RESULT (ic))->remat = 1;
2774 OP_SYMBOL (IC_RESULT (ic))->rematiCode = ic;
2775 OP_SYMBOL (IC_RESULT (ic))->usl.spillLoc = NULL;
2779 /* if this is a +/- operation with a rematerizable
2780 then mark this as rematerializable as well */
2781 if ((ic->op == '+' || ic->op == '-') &&
2782 (IS_SYMOP (IC_LEFT (ic)) &&
2783 IS_ITEMP (IC_RESULT (ic)) &&
2784 IS_OP_LITERAL (IC_RIGHT (ic))) &&
2785 OP_SYMBOL (IC_LEFT (ic))->remat &&
2786 (!IS_SYMOP (IC_RIGHT (ic)) || !IS_CAST_ICODE(OP_SYMBOL (IC_RIGHT (ic))->rematiCode)) &&
2787 bitVectnBitsOn (OP_DEFS (IC_RESULT (ic))) == 1)
2789 OP_SYMBOL (IC_RESULT (ic))->remat = 1;
2790 OP_SYMBOL (IC_RESULT (ic))->rematiCode = ic;
2791 OP_SYMBOL (IC_RESULT (ic))->usl.spillLoc = NULL;
2794 /* mark the pointer usages */
2795 if (POINTER_SET (ic))
2796 OP_SYMBOL (IC_RESULT (ic))->uptr = 1;
2798 if (POINTER_GET (ic) &&
2799 IS_SYMOP(IC_LEFT (ic)))
2800 OP_SYMBOL (IC_LEFT (ic))->uptr = 1;
2805 /* if we are using a symbol on the stack
2806 then we should say hc08_ptrRegReq */
2807 if (ic->op == IFX && IS_SYMOP (IC_COND (ic)))
2808 hc08_ptrRegReq += ((OP_SYMBOL (IC_COND (ic))->onStack ||
2809 OP_SYMBOL (IC_COND (ic))->iaccess) ? 1 : 0);
2810 else if (ic->op == JUMPTABLE && IS_SYMOP (IC_JTCOND (ic)))
2811 hc08_ptrRegReq += ((OP_SYMBOL (IC_JTCOND (ic))->onStack ||
2812 OP_SYMBOL (IC_JTCOND (ic))->iaccess) ? 1 : 0);
2815 if (IS_SYMOP (IC_LEFT (ic)))
2816 hc08_ptrRegReq += ((OP_SYMBOL (IC_LEFT (ic))->onStack ||
2817 OP_SYMBOL (IC_LEFT (ic))->iaccess) ? 1 : 0);
2818 if (IS_SYMOP (IC_RIGHT (ic)))
2819 hc08_ptrRegReq += ((OP_SYMBOL (IC_RIGHT (ic))->onStack ||
2820 OP_SYMBOL (IC_RIGHT (ic))->iaccess) ? 1 : 0);
2821 if (IS_SYMOP (IC_RESULT (ic)))
2822 hc08_ptrRegReq += ((OP_SYMBOL (IC_RESULT (ic))->onStack ||
2823 OP_SYMBOL (IC_RESULT (ic))->iaccess) ? 1 : 0);
2828 /* if the condition of an if instruction
2829 is defined in the previous instruction and
2830 this is the only usage then
2831 mark the itemp as a conditional */
2832 if ((IS_CONDITIONAL (ic) ||
2833 (IS_BITWISE_OP(ic) && isBitwiseOptimizable (ic))) &&
2834 ic->next && ic->next->op == IFX &&
2835 bitVectnBitsOn (OP_USES(IC_RESULT(ic)))==1 &&
2836 isOperandEqual (IC_RESULT (ic), IC_COND (ic->next)) &&
2837 OP_SYMBOL (IC_RESULT (ic))->liveTo <= ic->next->seq)
2839 OP_SYMBOL (IC_RESULT (ic))->regType = REG_CND;
2843 /* reduce for support function calls */
2844 if (ic->supportRtn || (ic->op != IFX && ic->op != JUMPTABLE))
2845 packRegsForSupport (ic, ebp);
2848 /* some cases the redundant moves can
2849 can be eliminated for return statements */
2850 if ((ic->op == RETURN || (ic->op == SEND && ic->argreg == 1)) &&
2851 /* !isOperandInFarSpace (IC_LEFT (ic)) && */
2852 options.model == MODEL_SMALL) {
2853 packRegsForOneuse (ic, IC_LEFT (ic), ebp);
2856 /* if pointer set & left has a size more than
2857 one and right is not in far space */
2858 if (POINTER_SET (ic) &&
2859 /* !isOperandInFarSpace (IC_RIGHT (ic)) && */
2860 !OP_SYMBOL (IC_RESULT (ic))->remat &&
2861 !IS_OP_RUONLY (IC_RIGHT (ic))
2862 /* && getSize (aggrToPtr (operandType (IC_RESULT (ic)), FALSE)) > 1 */ )
2863 packRegsForOneuse (ic, IC_RESULT (ic), ebp);
2865 /* if pointer get */
2866 if (POINTER_GET (ic) &&
2867 IS_SYMOP (IC_LEFT (ic)) &&
2868 /* !isOperandInFarSpace (IC_RESULT (ic)) && */
2869 !OP_SYMBOL (IC_LEFT (ic))->remat &&
2870 !IS_OP_RUONLY (IC_RESULT (ic))
2871 /* && getSize (aggrToPtr (operandType (IC_LEFT (ic)), FALSE)) > 1 */)
2872 packRegsForOneuse (ic, IC_LEFT (ic), ebp);
2875 /* if this is cast for intergral promotion then
2876 check if only use of the definition of the
2877 operand being casted/ if yes then replace
2878 the result of that arithmetic operation with
2879 this result and get rid of the cast */
2882 sym_link *fromType = operandType (IC_RIGHT (ic));
2883 sym_link *toType = operandType (IC_LEFT (ic));
2885 if (IS_INTEGRAL (fromType) && IS_INTEGRAL (toType) &&
2886 getSize (fromType) != getSize (toType) &&
2887 SPEC_USIGN (fromType) == SPEC_USIGN (toType))
2890 iCode *dic = packRegsForOneuse (ic, IC_RIGHT (ic), ebp);
2893 if (IS_ARITHMETIC_OP (dic))
2895 bitVectUnSetBit(OP_SYMBOL(IC_RESULT(dic))->defs,dic->key);
2896 ReplaceOpWithCheaperOp(&IC_RESULT (dic), IC_RESULT (ic));
2897 remiCodeFromeBBlock (ebp, ic);
2898 bitVectUnSetBit(OP_SYMBOL(IC_RESULT(ic))->defs,ic->key);
2899 hTabDeleteItem (&iCodehTab, ic->key, ic, DELETE_ITEM, NULL);
2900 OP_DEFS(IC_RESULT (dic))=bitVectSetBit (OP_DEFS (IC_RESULT (dic)), dic->key);
2904 OP_SYMBOL (IC_RIGHT (ic))->ruonly = 0;
2910 /* if the type from and type to are the same
2911 then if this is the only use then packit */
2912 if (compareType (operandType (IC_RIGHT (ic)),
2913 operandType (IC_LEFT (ic))) == 1)
2915 iCode *dic = packRegsForOneuse (ic, IC_RIGHT (ic), ebp);
2918 bitVectUnSetBit(OP_SYMBOL(IC_RESULT(dic))->defs,dic->key);
2919 ReplaceOpWithCheaperOp(&IC_RESULT (dic), IC_RESULT (ic));
2920 remiCodeFromeBBlock (ebp, ic);
2921 bitVectUnSetBit(OP_SYMBOL(IC_RESULT(ic))->defs,ic->key);
2922 hTabDeleteItem (&iCodehTab, ic->key, ic, DELETE_ITEM, NULL);
2923 OP_DEFS(IC_RESULT (dic))=bitVectSetBit (OP_DEFS (IC_RESULT (dic)), dic->key);
2932 iTempNN := (some variable in farspace) V1
2937 if (ic->op == IPUSH)
2939 packForPush (ic, ebpp, blockno);
2944 /* pack registers for accumulator use, when the
2945 result of an arithmetic or bit wise operation
2946 has only one use, that use is immediately following
2947 the defintion and the using iCode has only one
2948 operand or has two operands but one is literal &
2949 the result of that operation is not on stack then
2950 we can leave the result of this operation in x:a
2952 if ((IS_ARITHMETIC_OP (ic)
2953 || IS_CONDITIONAL(ic)
2954 || IS_BITWISE_OP (ic)
2958 || ic->op == GETHBIT
2959 || ic->op == LEFT_OP || ic->op == RIGHT_OP || ic->op == CALL
2960 || (ic->op == ADDRESS_OF && isOperandOnStack (IC_LEFT (ic)))
2961 || ic->op == RECEIVE
2963 IS_ITEMP (IC_RESULT (ic)) &&
2964 getSize (operandType (IC_RESULT (ic))) <= 1)
2966 packRegsForAccUse (ic);
2971 /*-----------------------------------------------------------------*/
2972 /* assignRegisters - assigns registers to each live range as need */
2973 /*-----------------------------------------------------------------*/
2975 hc08_assignRegisters (eBBlock ** ebbs, int count)
2980 setToNull ((void *) &_G.funcrUsed);
2981 setToNull ((void *) &_G.regAssigned);
2982 setToNull ((void *) &_G.totRegAssigned);
2983 hc08_ptrRegReq = _G.stackExtend = _G.dataExtend = 0;
2985 hc08_reg_a = hc08_regWithIdx(A_IDX);
2986 hc08_reg_x = hc08_regWithIdx(X_IDX);
2987 hc08_reg_h = hc08_regWithIdx(H_IDX);
2988 hc08_reg_hx = hc08_regWithIdx(HX_IDX);
2989 hc08_reg_xa = hc08_regWithIdx(XA_IDX);
2991 /* change assignments this will remove some
2992 live ranges reducing some register pressure */
2993 for (i = 0; i < count; i++)
2994 packRegisters (ebbs, i);
2996 /* liveranges probably changed by register packing
2997 so we compute them again */
2998 recomputeLiveRanges (ebbs, count);
3000 if (options.dump_pack)
3001 dumpEbbsToFileExt (DUMP_PACK, ebbs, count);
3003 /* first determine for each live range the number of
3004 registers & the type of registers required for each */
3007 /* and serially allocate registers */
3008 serialRegAssign (ebbs, count);
3011 //setToNull ((void *) &_G.regAssigned);
3012 //setToNull ((void *) &_G.totRegAssigned);
3015 /* if stack was extended then tell the user */
3018 /* werror(W_TOOMANY_SPILS,"stack", */
3019 /* _G.stackExtend,currFunc->name,""); */
3025 /* werror(W_TOOMANY_SPILS,"data space", */
3026 /* _G.dataExtend,currFunc->name,""); */
3030 /* after that create the register mask
3031 for each of the instruction */
3032 createRegMask (ebbs, count);
3034 /* redo that offsets for stacked automatic variables */
3036 redoStackOffsets ();
3039 if (options.dump_rassgn)
3041 dumpEbbsToFileExt (DUMP_RASSGN, ebbs, count);
3042 dumpLiveRanges (DUMP_LRANGE, liveRanges);
3045 /* do the overlaysegment stuff SDCCmem.c */
3046 doOverlays (ebbs, count);
3048 /* now get back the chain */
3049 ic = iCodeLabelOptimize (iCodeFromeBBlock (ebbs, count));
3053 /* free up any _G.stackSpil locations allocated */
3054 applyToSet (_G.stackSpil, deallocStackSpil);
3056 setToNull ((void **) &_G.stackSpil);
3057 setToNull ((void **) &_G.spiltSet);
3058 /* mark all registers as free */