ed6868c8d7326ca591ba8ba61b9eb571a75875c4
[fw/sdcc] / src / z80 / ralloc.c
1 /** @name Z80 Register allocation functions.
2     @author Michael Hope
3
4     Note: much of this is ripped straight from Sandeep's mcs51 code.
5
6     This code maps the virtual symbols and code onto the real
7     hardware.  It allocates based on usage and how long the varible
8     lives into registers or temporary memory on the stack.
9
10     On the Z80 hl and ix and a are reserved for the code generator,
11     leaving bc and de for allocation.  iy is unusable due to currently
12     as it's only adressable as a pair.  The extra register pressure
13     from reserving hl is made up for by how much easier the sub
14     operations become.  You could swap hl for iy if the undocumented
15     iyl/iyh instructions are available.
16
17     The stack frame is the common ix-bp style.  Basically:
18
19     ix+4+n:     param 1 
20     ix+4:       param 0 
21     ix+2:       return address 
22     ix+0:       calling functions ix 
23     ix-n:       local varibles 
24     ...  
25     sp:         end of local varibles
26
27     There is currently no support for bit spaces or banked functions.
28     
29     This program is free software; you can redistribute it and/or
30     modify it under the terms of the GNU General Public License as
31     published by the Free Software Foundation; either version 2, or (at
32     your option) any later version.  This program is distributed in the
33     hope that it will be useful, but WITHOUT ANY WARRANTY; without even
34     the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
35     PURPOSE.  See the GNU General Public License for more details.
36     
37     You should have received a copy of the GNU General Public License
38     along with this program; if not, write to the Free Software
39     Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307,
40     USA.  In other words, you are welcome to use, share and improve
41     this program.  You are forbidden to forbid anyone else to use,
42     share and improve what you give them.  Help stamp out
43     software-hoarding!  
44 */
45
46 #include "z80.h"
47 #include "SDCCicode.h"
48
49 /* Flags to turn off optimisations.
50  */
51 enum
52   {
53     DISABLE_PACK_ACC = 0,
54     DISABLE_PACK_ASSIGN = 0,
55     DISABLE_PACK_ONE_USE = 0,
56     DISABLE_PACK_HL = 1,
57     DISABLE_PACK_IY = 0
58   };
59
60 /* Flags to turn on debugging code.
61  */
62 enum
63   {
64     D_ALLOC = 0,
65     D_ALLOC2 = 0,
66     D_ACCUSE2 = 0,
67     D_ACCUSE2_VERBOSE = 0,
68     D_HLUSE = 0,
69     D_HLUSE2 = 0,
70     D_HLUSE2_VERBOSE = 0,
71     D_FILL_GAPS = 0,
72     D_PACK_IY = 0,
73     D_PACK_HLUSE3 = 0
74   };
75
76 #if 1
77 #define D(_a, _s)       if (_a)  { printf _s; fflush(stdout); }
78 #else
79 #define D(_a, _s)
80 #endif
81
82 #define DISABLE_PACKREGSFORSUPPORT      1
83 #define DISABLE_PACKREGSFORACCUSE       1
84
85 extern void genZ80Code (iCode *);
86
87 /** Local static variables */
88 static struct
89 {
90   bitVect *spiltSet;
91   set *stackSpil;
92   bitVect *regAssigned;
93   bitVect *totRegAssigned;    /* final set of LRs that got into registers */
94   short blockSpil;
95   int slocNum;
96   /* registers used in a function */
97   bitVect *funcrUsed;
98   int stackExtend;
99   int dataExtend;
100   int nRegs;
101 } _G;
102
103 static regs _gbz80_regs[] =
104 {
105   {REG_GPR, C_IDX, "c", 1},
106   {REG_GPR, B_IDX, "b", 1},
107   {REG_CND, CND_IDX, "c", 1}
108 };
109
110 static regs _z80_regs[] =
111 {
112   {REG_GPR, C_IDX, "c", 1},
113   {REG_GPR, B_IDX, "b", 1},
114   {REG_GPR, E_IDX, "e", 1},
115   {REG_GPR, D_IDX, "d", 1},
116   {REG_CND, CND_IDX, "c", 1}
117 };
118
119 regs *regsZ80;
120
121 /** Number of usable registers (all but C) */
122 #define Z80_MAX_REGS ((sizeof(_z80_regs)/sizeof(_z80_regs[0]))-1)
123 #define GBZ80_MAX_REGS ((sizeof(_gbz80_regs)/sizeof(_gbz80_regs[0]))-1)
124
125 static void spillThis (symbol *);
126 static void freeAllRegs ();
127
128 /** Allocates register of given type.
129     'type' is not used on the z80 version.  It was used to select
130     between pointer and general purpose registers on the mcs51 version.
131
132     @return             Pointer to the newly allocated register.
133  */
134 static regs *
135 allocReg (short type)
136 {
137   int i;
138
139   for (i = 0; i < _G.nRegs; i++)
140     {
141       /* For now we allocate from any free */
142       if (regsZ80[i].isFree)
143         {
144           regsZ80[i].isFree = 0;
145           if (currFunc)
146             {
147               currFunc->regsUsed = bitVectSetBit (currFunc->regsUsed, i);
148             }
149           D (D_ALLOC, ("allocReg: alloced %p\n", &regsZ80[i]));
150           return &regsZ80[i];
151         }
152     }
153   D (D_ALLOC, ("allocReg: No free.\n"));
154   return NULL;
155 }
156
157 /** Returns pointer to register wit index number
158  */
159 regs *
160 regWithIdx (int idx)
161 {
162   int i;
163
164   for (i = 0; i < _G.nRegs; i++)
165     {
166       if (regsZ80[i].rIdx == idx)
167         {
168           return &regsZ80[i];
169         }
170     }
171
172   wassertl (0, "regWithIdx not found");
173   exit (1);
174 }
175
176 /** Frees a register.
177  */
178 static void 
179 freeReg (regs * reg)
180 {
181   wassert (!reg->isFree);
182   reg->isFree = 1;
183   D (D_ALLOC, ("freeReg: freed %p\n", reg));
184 }
185
186
187 /** Returns number of free registers.
188  */
189 static int 
190 nFreeRegs (int type)
191 {
192   int i;
193   int nfr = 0;
194
195   for (i = 0; i < _G.nRegs; i++)
196     {
197       /* For now only one reg type */
198       if (regsZ80[i].isFree)
199         {
200           nfr++;
201         }
202     }
203   return nfr;
204 }
205
206 /** Free registers with type.
207  */
208 static int 
209 nfreeRegsType (int type)
210 {
211   int nfr;
212   if (type == REG_PTR)
213     {
214       if ((nfr = nFreeRegs (type)) == 0)
215         {
216           return nFreeRegs (REG_GPR);
217         }
218     }
219
220   return nFreeRegs (type);
221 }
222
223 /*-----------------------------------------------------------------*/
224 /* useReg - marks a register  as used                              */
225 /*-----------------------------------------------------------------*/
226 static void
227 useReg (regs * reg)
228 {
229   reg->isFree = 0;
230 }
231
232 /*-----------------------------------------------------------------*/
233 /* computeSpillable - given a point find the spillable live ranges */
234 /*-----------------------------------------------------------------*/
235 static bitVect *
236 computeSpillable (iCode * ic)
237 {
238   bitVect *spillable;
239
240   /* spillable live ranges are those that are live at this 
241      point . the following categories need to be subtracted
242      from this set. 
243      a) - those that are already spilt
244      b) - if being used by this one
245      c) - defined by this one */
246
247   spillable = bitVectCopy (ic->rlive);
248   spillable =
249     bitVectCplAnd (spillable, _G.spiltSet);     /* those already spilt */
250   spillable =
251     bitVectCplAnd (spillable, ic->uses);        /* used in this one */
252   bitVectUnSetBit (spillable, ic->defKey);
253   spillable = bitVectIntersect (spillable, _G.regAssigned);
254
255   return spillable;
256 }
257
258 /*-----------------------------------------------------------------*/
259 /* noSpilLoc - return true if a variable has no spil location      */
260 /*-----------------------------------------------------------------*/
261 static int 
262 noSpilLoc (symbol * sym, eBBlock * ebp, iCode * ic)
263 {
264   return (sym->usl.spillLoc ? 0 : 1);
265 }
266
267 /*-----------------------------------------------------------------*/
268 /* hasSpilLoc - will return 1 if the symbol has spil location      */
269 /*-----------------------------------------------------------------*/
270 static int 
271 hasSpilLoc (symbol * sym, eBBlock * ebp, iCode * ic)
272 {
273   return (sym->usl.spillLoc ? 1 : 0);
274 }
275
276 /** Will return 1 if the remat flag is set.
277     A symbol is rematerialisable if it doesnt need to be allocated
278     into registers at creation as it can be re-created at any time -
279     i.e. it's constant in some way.
280 */
281 static int 
282 rematable (symbol * sym, eBBlock * ebp, iCode * ic)
283 {
284   return sym->remat;
285 }
286
287 /*-----------------------------------------------------------------*/
288 /* allLRs - return true for all                                    */
289 /*-----------------------------------------------------------------*/
290 static int 
291 allLRs (symbol * sym, eBBlock * ebp, iCode * ic)
292 {
293   return 1;
294 }
295
296 /** liveRangesWith - applies function to a given set of live range 
297  */
298 static set *
299 liveRangesWith (bitVect * lrs, int (func) (symbol *, eBBlock *, iCode *),
300                 eBBlock * ebp, iCode * ic)
301 {
302   set *rset = NULL;
303   int i;
304
305   if (!lrs || !lrs->size)
306     return NULL;
307
308   for (i = 1; i < lrs->size; i++)
309     {
310       symbol *sym;
311       if (!bitVectBitValue (lrs, i))
312         continue;
313
314       /* if we don't find it in the live range 
315          hash table we are in serious trouble */
316       if (!(sym = hTabItemWithKey (liveRanges, i)))
317         {
318           wassertl (0, "liveRangesWith could not find liveRange");
319           exit (1);
320         }
321
322       if (func (sym, ebp, ic) && bitVectBitValue (_G.regAssigned, sym->key))
323         {
324           addSetHead (&rset, sym);
325         }
326     }
327
328   return rset;
329 }
330
331
332 /** leastUsedLR - given a set determines which is the least used 
333  */
334 static symbol *
335 leastUsedLR (set * sset)
336 {
337   symbol *sym = NULL, *lsym = NULL;
338
339   sym = lsym = setFirstItem (sset);
340
341   if (!lsym)
342     return NULL;
343
344   for (; lsym; lsym = setNextItem (sset))
345     {
346
347       /* if usage is the same then prefer
348          the spill the smaller of the two */
349       if (lsym->used == sym->used)
350         if (getSize (lsym->type) < getSize (sym->type))
351           sym = lsym;
352
353       /* if less usage */
354       if (lsym->used < sym->used)
355         sym = lsym;
356
357     }
358
359   setToNull ((void *) &sset);
360   sym->blockSpil = 0;
361   return sym;
362 }
363
364 /** noOverLap - will iterate through the list looking for over lap
365  */
366 static int 
367 noOverLap (set * itmpStack, symbol * fsym)
368 {
369   symbol *sym;
370
371   for (sym = setFirstItem (itmpStack); sym;
372        sym = setNextItem (itmpStack))
373     {
374       if (bitVectBitValue(sym->clashes,fsym->key)) 
375         return 0;
376 #if 0
377             // if sym starts before (or on) our end point
378             // and ends after (or on) our start point, 
379             // it is an overlap.
380             if (sym->liveFrom <= fsym->liveTo &&
381                 sym->liveTo   >= fsym->liveFrom)
382             {
383                 return 0;
384             }
385 #endif
386     }
387   return 1;
388 }
389
390 /*-----------------------------------------------------------------*/
391 /* isFree - will return 1 if the a free spil location is found     */
392 /*-----------------------------------------------------------------*/
393 DEFSETFUNC (isFree)
394 {
395   symbol *sym = item;
396   V_ARG (symbol **, sloc);
397   V_ARG (symbol *, fsym);
398
399   /* if already found */
400   if (*sloc)
401     return 0;
402
403   /* if it is free && and the itmp assigned to
404      this does not have any overlapping live ranges
405      with the one currently being assigned and
406      the size can be accomodated  */
407   if (sym->isFree &&
408       noOverLap (sym->usl.itmpStack, fsym) &&
409       getSize (sym->type) >= getSize (fsym->type))
410     {
411       *sloc = sym;
412       return 1;
413     }
414
415   return 0;
416 }
417
418 /*-----------------------------------------------------------------*/
419 /* createStackSpil - create a location on the stack to spil        */
420 /*-----------------------------------------------------------------*/
421 static symbol *
422 createStackSpil (symbol * sym)
423 {
424   symbol *sloc = NULL;
425
426   D (D_ALLOC, ("createStackSpil: for sym %p\n", sym));
427
428   /* first go try and find a free one that is already 
429      existing on the stack */
430   if (applyToSet (_G.stackSpil, isFree, &sloc, sym))
431     {
432       /* found a free one : just update & return */
433       sym->usl.spillLoc = sloc;
434       sym->stackSpil = 1;
435       sloc->isFree = 0;
436       addSetHead (&sloc->usl.itmpStack, sym);
437       D (D_ALLOC, ("createStackSpil: found existing\n"));
438       return sym;
439     }
440
441   /* could not then have to create one , this is the hard part
442      we need to allocate this on the stack : this is really a
443      hack!! but cannot think of anything better at this time */
444
445   sprintf (buffer, "sloc%d", _G.slocNum++);
446   sloc = newiTemp (buffer);
447
448   /* set the type to the spilling symbol */
449   sloc->type = copyLinkChain (sym->type);
450   sloc->etype = getSpec (sloc->type);
451   SPEC_SCLS (sloc->etype) = S_AUTO;
452   SPEC_EXTR (sloc->etype) = 0;
453   SPEC_STAT (sloc->etype) = 0;
454   SPEC_VOLATILE(sloc->etype) = 0;
455
456   allocLocal (sloc);
457
458   sloc->isref = 1;              /* to prevent compiler warning */
459
460   /* if it is on the stack then update the stack */
461   if (IN_STACK (sloc->etype))
462     {
463       currFunc->stack += getSize (sloc->type);
464       _G.stackExtend += getSize (sloc->type);
465     }
466   else
467     {
468       _G.dataExtend += getSize (sloc->type);
469     }
470
471   /* add it to the stackSpil set */
472   addSetHead (&_G.stackSpil, sloc);
473   sym->usl.spillLoc = sloc;
474   sym->stackSpil = 1;
475
476   /* add it to the set of itempStack set 
477      of the spill location */
478   addSetHead (&sloc->usl.itmpStack, sym);
479
480   D (D_ALLOC, ("createStackSpil: created new\n"));
481   return sym;
482 }
483
484 /*-----------------------------------------------------------------*/
485 /* spillThis - spils a specific operand                            */
486 /*-----------------------------------------------------------------*/
487 static void 
488 spillThis (symbol * sym)
489 {
490   int i;
491
492   D (D_ALLOC, ("spillThis: spilling %p\n", sym));
493
494   /* if this is rematerializable or has a spillLocation
495      we are okay, else we need to create a spillLocation
496      for it */
497   if (!(sym->remat || sym->usl.spillLoc))
498     {
499       createStackSpil (sym);
500     }
501
502   /* mark it has spilt & put it in the spilt set */
503   sym->isspilt = sym->spillA = 1;
504   _G.spiltSet = bitVectSetBit (_G.spiltSet, sym->key);
505
506   bitVectUnSetBit (_G.regAssigned, sym->key);
507   bitVectUnSetBit (_G.totRegAssigned, sym->key);
508
509   for (i = 0; i < sym->nRegs; i++)
510     {
511       if (sym->regs[i])
512         {
513           freeReg (sym->regs[i]);
514           sym->regs[i] = NULL;
515         }
516     }
517
518   if (sym->usl.spillLoc && !sym->remat)
519     {
520       sym->usl.spillLoc->allocreq++;
521     }
522   return;
523 }
524
525 #if DISABLED
526 /*-----------------------------------------------------------------*/
527 /* allDefsOutOfRange - all definitions are out of a range          */
528 /*-----------------------------------------------------------------*/
529 static bool
530 allDefsOutOfRange (bitVect * defs, int fseq, int toseq)
531 {
532   int i;
533
534   if (!defs)
535     return TRUE;
536
537   for (i = 0; i < defs->size; i++)
538     {
539       iCode *ic;
540
541       if (bitVectBitValue (defs, i) &&
542           (ic = hTabItemWithKey (iCodehTab, i)) &&
543           (ic->seq >= fseq && ic->seq <= toseq))
544
545         return FALSE;
546
547     }
548
549   return TRUE;
550 }
551
552 /*-----------------------------------------------------------------*/
553 /* hasSpilLocnoUptr - will return 1 if the symbol has spil location */
554 /*                    but is not used as a pointer                 */
555 /*-----------------------------------------------------------------*/
556 static int
557 hasSpilLocnoUptr (symbol * sym, eBBlock * ebp, iCode * ic)
558 {
559   return ((sym->usl.spillLoc && !sym->uptr) ? 1 : 0);
560 }
561
562 /*-----------------------------------------------------------------*/
563 /* notUsedInRemaining - not used or defined in remain of the block */
564 /*-----------------------------------------------------------------*/
565 static int
566 notUsedInRemaining (symbol * sym, eBBlock * ebp, iCode * ic)
567 {
568   return ((usedInRemaining (operandFromSymbol (sym), ic) ? 0 : 1) &&
569           allDefsOutOfRange (sym->defs, ebp->fSeq, ebp->lSeq));
570 }
571 #endif
572
573 /** Select a iTemp to spil : rather a simple procedure.
574  */
575 symbol *
576 selectSpil (iCode * ic, eBBlock * ebp, symbol * forSym)
577 {
578   bitVect *lrcs = NULL;
579   set *selectS;
580   symbol *sym;
581
582   D (D_ALLOC, ("selectSpil: finding spill for ic %p\n", ic));
583   /* get the spillable live ranges */
584   lrcs = computeSpillable (ic);
585
586   /* get all live ranges that are rematerizable */
587   if ((selectS = liveRangesWith (lrcs, rematable, ebp, ic)))
588     {
589       D (D_ALLOC, ("selectSpil: using remat.\n"));
590       /* return the least used of these */
591       return leastUsedLR (selectS);
592     }
593
594 #if 0
595   /* get live ranges with spillLocations in direct space */
596   if ((selectS = liveRangesWith (lrcs, directSpilLoc, ebp, ic)))
597     {
598       sym = leastUsedLR (selectS);
599       strcpy (sym->rname, (sym->usl.spillLoc->rname[0] ?
600                            sym->usl.spillLoc->rname :
601                            sym->usl.spillLoc->name));
602       sym->spildir = 1;
603       /* mark it as allocation required */
604       sym->usl.spillLoc->allocreq++;
605       return sym;
606     }
607
608   /* if the symbol is local to the block then */
609   if (forSym->liveTo < ebp->lSeq)
610     {
611
612       /* check if there are any live ranges allocated
613          to registers that are not used in this block */
614       if (!_G.blockSpil && (selectS = liveRangesWith (lrcs, notUsedInBlock, ebp, ic)))
615         {
616           sym = leastUsedLR (selectS);
617           /* if this is not rematerializable */
618           if (!sym->remat)
619             {
620               _G.blockSpil++;
621               wassertl (0, "Attempted to do an unsupported block spill");
622               sym->blockSpil = 1;
623             }
624           return sym;
625         }
626
627       /* check if there are any live ranges that not
628          used in the remainder of the block */
629       if (!_G.blockSpil && (selectS = liveRangesWith (lrcs, notUsedInRemaining, ebp, ic)))
630         {
631           sym = leastUsedLR (selectS);
632           if (sym != forSym)
633             {
634               if (!sym->remat)
635                 {
636                   wassertl (0, "Attempted to do an unsupported remain spill");
637                   sym->remainSpil = 1;
638                   _G.blockSpil++;
639                 }
640               return sym;
641             }
642         }
643     }
644   /* find live ranges with spillocation && not used as pointers */
645   if ((selectS = liveRangesWith (lrcs, hasSpilLocnoUptr, ebp, ic)))
646     {
647
648       sym = leastUsedLR (selectS);
649       /* mark this as allocation required */
650       sym->usl.spillLoc->allocreq++;
651       return sym;
652     }
653 #endif
654
655   /* find live ranges with spillocation */
656   if ((selectS = liveRangesWith (lrcs, hasSpilLoc, ebp, ic)))
657     {
658       D (D_ALLOC, ("selectSpil: using with spill.\n"));
659       sym = leastUsedLR (selectS);
660       sym->usl.spillLoc->allocreq++;
661       return sym;
662     }
663
664   /* couldn't find then we need to create a spil
665      location on the stack , for which one? the least
666      used ofcourse */
667   if ((selectS = liveRangesWith (lrcs, noSpilLoc, ebp, ic)))
668     {
669       D (D_ALLOC, ("selectSpil: creating new spill.\n"));
670       /* return a created spil location */
671       sym = createStackSpil (leastUsedLR (selectS));
672       sym->usl.spillLoc->allocreq++;
673       return sym;
674     }
675
676   /* this is an extreme situation we will spill
677      this one : happens very rarely but it does happen */
678   D (D_ALLOC, ("selectSpil: using spillThis.\n"));
679   spillThis (forSym);
680   return forSym;
681
682 }
683
684 /** Spil some variable & mark registers as free.
685     A spill occurs when an iTemp wont fit into the available registers.
686  */
687 bool 
688 spilSomething (iCode * ic, eBBlock * ebp, symbol * forSym)
689 {
690   symbol *ssym;
691   int i;
692
693   D (D_ALLOC, ("spilSomething: spilling on ic %p\n", ic));
694
695   /* get something we can spil */
696   ssym = selectSpil (ic, ebp, forSym);
697
698   /* mark it as spilt */
699   ssym->isspilt = ssym->spillA = 1;
700   _G.spiltSet = bitVectSetBit (_G.spiltSet, ssym->key);
701
702   /* mark it as not register assigned &
703      take it away from the set */
704   bitVectUnSetBit (_G.regAssigned, ssym->key);
705   bitVectUnSetBit (_G.totRegAssigned, ssym->key);
706
707   /* mark the registers as free */
708   for (i = 0; i < ssym->nRegs; i++)
709     if (ssym->regs[i])
710       freeReg (ssym->regs[i]);
711
712   wassertl (ssym->blockSpil == 0, "Encountered a sym with a block spill");
713   wassertl (ssym->remainSpil == 0, "Encountered a sym with a remain spill");
714 #if 0
715   /* if spilt on stack then free up r0 & r1 
716      if they could have been assigned to as gprs */
717   if (!ptrRegReq && isSpiltOnStack (ssym))
718     {
719       ptrRegReq++;
720       spillLRWithPtrReg (ssym);
721     }
722
723   /* if this was a block level spil then insert push & pop 
724      at the start & end of block respectively */
725   if (ssym->blockSpil)
726     {
727       iCode *nic = newiCode (IPUSH, operandFromSymbol (ssym), NULL);
728       /* add push to the start of the block */
729       addiCodeToeBBlock (ebp, nic, (ebp->sch->op == LABEL ?
730                                     ebp->sch->next : ebp->sch));
731       nic = newiCode (IPOP, operandFromSymbol (ssym), NULL);
732       /* add pop to the end of the block */
733       addiCodeToeBBlock (ebp, nic, NULL);
734     }
735
736   /* if spilt because not used in the remainder of the
737      block then add a push before this instruction and
738      a pop at the end of the block */
739   if (ssym->remainSpil)
740     {
741
742       iCode *nic = newiCode (IPUSH, operandFromSymbol (ssym), NULL);
743       /* add push just before this instruction */
744       addiCodeToeBBlock (ebp, nic, ic);
745
746       nic = newiCode (IPOP, operandFromSymbol (ssym), NULL);
747       /* add pop to the end of the block */
748       addiCodeToeBBlock (ebp, nic, NULL);
749     }
750 #endif
751
752   D (D_ALLOC, ("spilSomething: done.\n"));
753
754   if (ssym == forSym)
755     return FALSE;
756   else
757     return TRUE;
758 }
759
760 /** Will try for GPR if not spil.
761  */
762 regs *
763 getRegGpr (iCode * ic, eBBlock * ebp, symbol * sym)
764 {
765   regs *reg;
766   int j;
767
768   D (D_ALLOC, ("getRegGpr: on ic %p\n", ic));
769 tryAgain:
770   /* try for gpr type */
771   if ((reg = allocReg (REG_GPR)))
772     {
773       D (D_ALLOC, ("getRegGpr: got a reg.\n"));
774       return reg;
775     }
776
777   /* we have to spil */
778   if (!spilSomething (ic, ebp, sym))
779     {
780       D (D_ALLOC, ("getRegGpr: have to spill.\n"));
781       return NULL;
782     }
783   
784   /* make sure partially assigned registers aren't reused */
785   for (j=0; j<=sym->nRegs; j++)
786     if (sym->regs[j])
787       sym->regs[j]->isFree = 0;
788
789   /* this looks like an infinite loop but 
790      in really selectSpil will abort  */
791   goto tryAgain;
792 }
793
794 static regs *getRegGprNoSpil()
795 {
796   regs *reg;
797
798   /* try for gpr type */
799   if ((reg = allocReg (REG_GPR)))
800     {
801       D (D_ALLOC, ("getRegGprNoSpil: got a reg.\n"));
802       return reg;
803     }
804   assert(0);
805
806   /* just to make the compiler happy */
807   return 0;
808 }
809
810 /** Symbol has a given register.
811  */
812 static bool 
813 symHasReg (symbol * sym, regs * reg)
814 {
815   int i;
816
817   for (i = 0; i < sym->nRegs; i++)
818     if (sym->regs[i] == reg)
819       return TRUE;
820
821   return FALSE;
822 }
823
824 /** Check the live to and if they have registers & are not spilt then
825     free up the registers 
826 */
827 static void 
828 deassignLRs (iCode * ic, eBBlock * ebp)
829 {
830   symbol *sym;
831   int k;
832   symbol *result;
833
834   for (sym = hTabFirstItem (liveRanges, &k); sym;
835        sym = hTabNextItem (liveRanges, &k))
836     {
837
838       symbol *psym = NULL;
839       /* if it does not end here */
840       if (sym->liveTo > ic->seq)
841         continue;
842
843       /* if it was spilt on stack then we can 
844          mark the stack spil location as free */
845       if (sym->isspilt)
846         {
847           if (sym->stackSpil)
848             {
849               sym->usl.spillLoc->isFree = 1;
850               sym->stackSpil = 0;
851             }
852           continue;
853         }
854
855       if (!bitVectBitValue (_G.regAssigned, sym->key))
856         continue;
857
858       /* special case check if this is an IFX &
859          the privious one was a pop and the 
860          previous one was not spilt then keep track
861          of the symbol */
862       if (ic->op == IFX && ic->prev &&
863           ic->prev->op == IPOP &&
864           !ic->prev->parmPush &&
865           !OP_SYMBOL (IC_LEFT (ic->prev))->isspilt)
866         psym = OP_SYMBOL (IC_LEFT (ic->prev));
867
868       D (D_ALLOC, ("deassignLRs: in loop on sym %p nregs %u\n", sym, sym->nRegs));
869
870       if (sym->nRegs)
871         {
872           int i = 0;
873
874           bitVectUnSetBit (_G.regAssigned, sym->key);
875
876           /* if the result of this one needs registers
877              and does not have it then assign it right
878              away */
879           if (IC_RESULT (ic) &&
880               !(SKIP_IC2 (ic) ||        /* not a special icode */
881                 ic->op == JUMPTABLE ||
882                 ic->op == IFX ||
883                 ic->op == IPUSH ||
884                 ic->op == IPOP ||
885                 ic->op == RETURN) &&
886               (result = OP_SYMBOL (IC_RESULT (ic))) &&  /* has a result */
887               result->liveTo > ic->seq &&       /* and will live beyond this */
888               result->liveTo <= ebp->lSeq &&    /* does not go beyond this block */
889               result->regType == sym->regType &&        /* same register types */
890               result->nRegs &&  /* which needs registers */
891               !result->isspilt &&       /* and does not already have them */
892               !result->remat &&
893               !bitVectBitValue (_G.regAssigned, result->key) &&
894           /* the number of free regs + number of regs in this LR
895              can accomodate the what result Needs */
896               ((nfreeRegsType (result->regType) +
897                 sym->nRegs) >= result->nRegs)
898             )
899             {
900               for (i = 0; i < result->nRegs; i++)
901                 {
902                   if (i < sym->nRegs)
903                     result->regs[i] = sym->regs[i];
904                   else
905                     result->regs[i] = getRegGpr (ic, ebp, result);
906
907                   /* if the allocation falied which means
908                      this was spilt then break */
909                   if (!result->regs[i])
910                     {
911                       wassert (0);
912                       assert (0);
913                       break;
914                     }
915                 }
916
917               _G.regAssigned = bitVectSetBit (_G.regAssigned, result->key);
918               _G.totRegAssigned = bitVectSetBit (_G.totRegAssigned, result->key);
919             }
920
921           /* free the remaining */
922           for (; i < sym->nRegs; i++)
923             {
924               if (psym)
925                 {
926                   if (!symHasReg (psym, sym->regs[i]))
927                     freeReg (sym->regs[i]);
928                 }
929               else
930                 freeReg (sym->regs[i]);
931               //              sym->regs[i] = NULL;
932             }
933         }
934     }
935 }
936
937
938 /** Reassign this to registers.
939  */
940 static void 
941 reassignLR (operand * op)
942 {
943   symbol *sym = OP_SYMBOL (op);
944   int i;
945
946   D (D_ALLOC, ("reassingLR: on sym %p\n", sym));
947
948   /* not spilt any more */
949   sym->isspilt = sym->spillA = sym->blockSpil = sym->remainSpil = 0;
950   bitVectUnSetBit (_G.spiltSet, sym->key);
951
952   _G.regAssigned = bitVectSetBit (_G.regAssigned, sym->key);
953   _G.totRegAssigned = bitVectSetBit (_G.totRegAssigned, sym->key);
954
955   _G.blockSpil--;
956
957   for (i = 0; i < sym->nRegs; i++)
958     sym->regs[i]->isFree = 0;
959 }
960
961 /** Determines if allocating will cause a spill.
962  */
963 static int 
964 willCauseSpill (int nr, int rt)
965 {
966   /* first check if there are any avlb registers
967      of te type required */
968   if (nFreeRegs (0) >= nr)
969     return 0;
970
971   /* it will cause a spil */
972   return 1;
973 }
974
975 /** The allocator can allocate same registers to result and operand,
976     if this happens make sure they are in the same position as the operand
977     otherwise chaos results.
978 */
979 static int
980 positionRegs (symbol * result, symbol * opsym)
981 {
982   int count = min (result->nRegs, opsym->nRegs);
983   int i, j = 0, shared = 0;
984   int change = 0;
985
986   D (D_ALLOC, ("positionRegs: on result %p opsum %p line %u\n", result, opsym, lineno));
987
988   /* if the result has been spilt then cannot share */
989   if (opsym->isspilt)
990     return 0;
991 again:
992   shared = 0;
993   /* first make sure that they actually share */
994   for (i = 0; i < count; i++)
995     {
996       for (j = 0; j < count; j++)
997         {
998           if (result->regs[i] == opsym->regs[j] && i != j)
999             {
1000               shared = 1;
1001               goto xchgPositions;
1002             }
1003         }
1004     }
1005 xchgPositions:
1006   if (shared)
1007     {
1008       regs *tmp = result->regs[i];
1009       result->regs[i] = result->regs[j];
1010       result->regs[j] = tmp;
1011       change ++;
1012       goto again;
1013     }
1014   return change ;
1015 }
1016
1017 /** Try to allocate a pair of registers to the symbol.
1018  */
1019 bool 
1020 tryAllocatingRegPair (symbol * sym)
1021 {
1022   int i;
1023   wassert (sym->nRegs == 2);
1024   for (i = 0; i < _G.nRegs; i += 2)
1025     {
1026       if ((regsZ80[i].isFree) && (regsZ80[i + 1].isFree))
1027         {
1028           regsZ80[i].isFree = 0;
1029           sym->regs[0] = &regsZ80[i];
1030           regsZ80[i + 1].isFree = 0;
1031           sym->regs[1] = &regsZ80[i + 1];
1032           sym->regType = REG_PAIR;
1033
1034           if (currFunc)
1035             {
1036               currFunc->regsUsed =
1037                 bitVectSetBit (currFunc->regsUsed, i);
1038               currFunc->regsUsed =
1039                 bitVectSetBit (currFunc->regsUsed, i + 1);
1040             }
1041           D (D_ALLOC, ("tryAllocRegPair: succeded for sym %p\n", sym));
1042           return TRUE;
1043         }
1044     }
1045   D (D_ALLOC, ("tryAllocRegPair: failed on sym %p\n", sym));
1046   return FALSE;
1047 }
1048
1049 /*------------------------------------------------------------------*/
1050 /* verifyRegsAssigned - make sure an iTemp is properly initialized; */
1051 /* it should either have registers or have beed spilled. Otherwise, */
1052 /* there was an uninitialized variable, so just spill this to get   */
1053 /* the operand in a valid state.                                    */
1054 /*------------------------------------------------------------------*/
1055 static void
1056 verifyRegsAssigned (operand *op, iCode * ic)
1057 {
1058   symbol * sym;
1059   
1060   if (!op) return;
1061   if (!IS_ITEMP (op)) return;
1062   
1063   sym = OP_SYMBOL (op);
1064   if (sym->isspilt) return;
1065   if (!sym->nRegs) return;
1066   if (sym->regs[0]) return;
1067   
1068   werrorfl (ic->filename, ic->lineno, W_LOCAL_NOINIT, 
1069             sym->prereqv ? sym->prereqv->name : sym->name);
1070   spillThis (sym);
1071 }
1072
1073
1074 /** Serially allocate registers to the variables.
1075     This is the main register allocation function.  It is called after
1076     packing.
1077  */
1078 static void 
1079 serialRegAssign (eBBlock ** ebbs, int count)
1080 {
1081   int i;
1082
1083   /* for all blocks */
1084   for (i = 0; i < count; i++)
1085     {
1086
1087       iCode *ic;
1088
1089       if (ebbs[i]->noPath &&
1090           (ebbs[i]->entryLabel != entryLabel &&
1091            ebbs[i]->entryLabel != returnLabel))
1092         continue;
1093
1094       /* of all instructions do */
1095       for (ic = ebbs[i]->sch; ic; ic = ic->next)
1096         {
1097
1098           /* if this is an ipop that means some live
1099              range will have to be assigned again */
1100           if (ic->op == IPOP)
1101             {
1102               wassert (0);
1103               reassignLR (IC_LEFT (ic));
1104             }
1105
1106           /* if result is present && is a true symbol */
1107           if (IC_RESULT (ic) && ic->op != IFX &&
1108               IS_TRUE_SYMOP (IC_RESULT (ic)))
1109             OP_SYMBOL (IC_RESULT (ic))->allocreq++;
1110
1111           /* take away registers from live
1112              ranges that end at this instruction */
1113           deassignLRs (ic, ebbs[i]);
1114
1115           /* some don't need registers */
1116           /* MLH: removed RESULT and POINTER_SET condition */
1117           if (SKIP_IC2 (ic) ||
1118               ic->op == JUMPTABLE ||
1119               ic->op == IFX ||
1120               ic->op == IPUSH ||
1121               ic->op == IPOP)
1122             continue;
1123
1124           /* now we need to allocate registers only for the result */
1125           if (IC_RESULT (ic))
1126             {
1127               symbol *sym = OP_SYMBOL (IC_RESULT (ic));
1128               bitVect *spillable;
1129               int willCS;
1130               int j;
1131
1132               D (D_ALLOC, ("serialRegAssign: in loop on result %p\n", sym));
1133
1134               /* if it does not need or is spilt 
1135                  or is already assigned to registers
1136                  or will not live beyond this instructions */
1137               if (!sym->nRegs ||
1138                   sym->isspilt ||
1139                   bitVectBitValue (_G.regAssigned, sym->key) ||
1140                   sym->liveTo <= ic->seq)
1141                 {
1142                   D (D_ALLOC, ("serialRegAssign: wont live long enough.\n"));
1143                   continue;
1144                 }
1145
1146               /* if some liverange has been spilt at the block level
1147                  and this one live beyond this block then spil this
1148                  to be safe */
1149               if (_G.blockSpil && sym->liveTo > ebbs[i]->lSeq)
1150                 {
1151                   D (D_ALLOC, ("serialRegAssign: \"spilling to be safe.\"\n"));
1152                   spillThis (sym);
1153                   continue;
1154                 }
1155               /* if trying to allocate this will cause
1156                  a spill and there is nothing to spill 
1157                  or this one is rematerializable then
1158                  spill this one */
1159               willCS = willCauseSpill (sym->nRegs, sym->regType);
1160               spillable = computeSpillable (ic);
1161               if (sym->remat ||
1162                   (willCS && bitVectIsZero (spillable)))
1163                 {
1164
1165                   D (D_ALLOC, ("serialRegAssign: \"remat spill\"\n"));
1166                   spillThis (sym);
1167                   continue;
1168
1169                 }
1170
1171               /* if it has a spillocation & is used less than
1172                  all other live ranges then spill this */
1173               if (willCS) {
1174                       if (sym->usl.spillLoc) {
1175                               symbol *leastUsed = leastUsedLR (liveRangesWith (spillable,
1176                                                                                allLRs, ebbs[i], ic));
1177                               if (leastUsed && leastUsed->used > sym->used) {
1178                                       spillThis (sym);
1179                                       continue;
1180                               }
1181                       } else {
1182                               /* if none of the liveRanges have a spillLocation then better
1183                                  to spill this one than anything else already assigned to registers */
1184                               if (liveRangesWith(spillable,noSpilLoc,ebbs[i],ic)) {
1185                                   /* if this is local to this block then we might find a block spil */
1186                                   if (!(sym->liveFrom >= ebbs[i]->fSeq && sym->liveTo <= ebbs[i]->lSeq)) {
1187                                       spillThis (sym);
1188                                       continue;
1189                                   }
1190                               }
1191                       }
1192               }
1193
1194               /* else we assign registers to it */
1195               _G.regAssigned = bitVectSetBit (_G.regAssigned, sym->key);
1196               _G.totRegAssigned = bitVectSetBit (_G.totRegAssigned, sym->key);
1197
1198               /* Special case:  Try to fit into a reg pair if
1199                  available */
1200               D (D_ALLOC, ("serialRegAssign: actually allocing regs!\n"));
1201               if ((sym->nRegs == 2) && tryAllocatingRegPair (sym))
1202                 {
1203                 }
1204               else
1205                 {
1206                   for (j = 0; j < sym->nRegs; j++)
1207                     {
1208                       sym->regs[j] = getRegGpr (ic, ebbs[i], sym);
1209
1210                       /* if the allocation falied which means
1211                          this was spilt then break */
1212                       if (!sym->regs[j])
1213                         {
1214                           D (D_ALLOC, ("Couldnt alloc (spill)\n"))
1215                             break;
1216                         }
1217                     }
1218                 }
1219               /* if it shares registers with operands make sure
1220                  that they are in the same position */
1221               if (IC_LEFT (ic) && IS_SYMOP (IC_LEFT (ic)) &&
1222                   OP_SYMBOL (IC_LEFT (ic))->nRegs && ic->op != '=')
1223                 positionRegs (OP_SYMBOL (IC_RESULT (ic)),
1224                               OP_SYMBOL (IC_LEFT (ic)));
1225               /* do the same for the right operand */
1226               if (IC_RIGHT (ic) && IS_SYMOP (IC_RIGHT (ic)) &&
1227                   OP_SYMBOL (IC_RIGHT (ic))->nRegs)
1228                 positionRegs (OP_SYMBOL (IC_RESULT (ic)),
1229                               OP_SYMBOL (IC_RIGHT (ic)));
1230
1231             }
1232         }
1233     }
1234
1235     /* Check for and fix any problems with uninitialized operands */
1236     for (i = 0; i < count; i++)
1237       {
1238         iCode *ic;
1239
1240         if (ebbs[i]->noPath &&
1241             (ebbs[i]->entryLabel != entryLabel &&
1242              ebbs[i]->entryLabel != returnLabel))
1243             continue;
1244
1245         for (ic = ebbs[i]->sch; ic; ic = ic->next)
1246           {
1247             if (SKIP_IC2 (ic))
1248               continue;
1249
1250             if (ic->op == IFX)
1251               {
1252                 verifyRegsAssigned (IC_COND (ic), ic);
1253                 continue;
1254               }
1255
1256             if (ic->op == JUMPTABLE)
1257               {
1258                 verifyRegsAssigned (IC_JTCOND (ic), ic);
1259                 continue;
1260               }
1261
1262             verifyRegsAssigned (IC_RESULT (ic), ic);
1263             verifyRegsAssigned (IC_LEFT (ic), ic);
1264             verifyRegsAssigned (IC_RIGHT (ic), ic);
1265           }
1266       }    
1267
1268 }
1269
1270 /*-----------------------------------------------------------------*/
1271 /* fillGaps - Try to fill in the Gaps left by Pass1                */
1272 /*-----------------------------------------------------------------*/
1273 static void fillGaps()
1274 {
1275     symbol *sym =NULL;
1276     int key =0;    
1277     
1278     if (getenv("DISABLE_FILL_GAPS")) return;
1279     
1280     /* look for livernages that was spilt by the allocator */
1281     for (sym = hTabFirstItem(liveRanges,&key) ; sym ; 
1282          sym = hTabNextItem(liveRanges,&key)) {
1283
1284         int i;
1285         int pdone = 0;
1286
1287         if (!sym->spillA || !sym->clashes || sym->remat) continue ;
1288
1289         /* find the liveRanges this one clashes with, that are
1290            still assigned to registers & mark the registers as used*/
1291         for ( i = 0 ; i < sym->clashes->size ; i ++) {
1292             int k;
1293             symbol *clr;
1294
1295             if (bitVectBitValue(sym->clashes,i) == 0 ||    /* those that clash with this */
1296                 bitVectBitValue(_G.totRegAssigned,i) == 0) /* and are still assigned to registers */
1297                 continue ;
1298
1299             clr = hTabItemWithKey(liveRanges,i);
1300             assert(clr);
1301          
1302             /* mark these registers as used */
1303             for (k = 0 ; k < clr->nRegs ; k++ ) 
1304                 useReg(clr->regs[k]);
1305         }
1306
1307         if (willCauseSpill(sym->nRegs,sym->regType)) {
1308             /* NOPE :( clear all registers & and continue */
1309             freeAllRegs();
1310             continue ;
1311         }
1312
1313         /* THERE IS HOPE !!!! */
1314         for (i=0; i < sym->nRegs ; i++ ) {
1315                 sym->regs[i] = getRegGprNoSpil ();                
1316         }
1317
1318         /* for all its definitions check if the registers
1319            allocated needs positioning NOTE: we can position
1320            only ONCE if more than One positioning required 
1321            then give up */
1322         sym->isspilt = 0;
1323         for (i = 0 ; i < sym->defs->size ; i++ ) {
1324             if (bitVectBitValue(sym->defs,i)) {
1325                 iCode *ic;
1326                 if (!(ic = hTabItemWithKey(iCodehTab,i))) continue ;
1327                 if (SKIP_IC(ic)) continue;
1328                 assert(isSymbolEqual(sym,OP_SYMBOL(IC_RESULT(ic)))); /* just making sure */
1329                 /* if left is assigned to registers */
1330                 if (IS_SYMOP(IC_LEFT(ic)) && 
1331                     bitVectBitValue(_G.totRegAssigned,OP_SYMBOL(IC_LEFT(ic))->key)) {
1332                     pdone += positionRegs(sym,OP_SYMBOL(IC_LEFT(ic)));
1333                 }
1334                 if (IS_SYMOP(IC_RIGHT(ic)) && 
1335                     bitVectBitValue(_G.totRegAssigned,OP_SYMBOL(IC_RIGHT(ic))->key)) {
1336                     pdone += positionRegs(sym,OP_SYMBOL(IC_RIGHT(ic)));
1337                 }
1338                 if (pdone > 1) break;
1339             }
1340         }
1341         for (i = 0 ; i < sym->uses->size ; i++ ) {
1342             if (bitVectBitValue(sym->uses,i)) {
1343                 iCode *ic;
1344                 if (!(ic = hTabItemWithKey(iCodehTab,i))) continue ;
1345                 if (SKIP_IC(ic)) continue;
1346                 if (!IS_ASSIGN_ICODE(ic)) continue ;
1347
1348                 /* if result is assigned to registers */
1349                 if (IS_SYMOP(IC_RESULT(ic)) && 
1350                     bitVectBitValue(_G.totRegAssigned,OP_SYMBOL(IC_RESULT(ic))->key)) {
1351                     pdone += positionRegs(sym,OP_SYMBOL(IC_RESULT(ic)));
1352                 }
1353                 if (pdone > 1) break;
1354             }
1355         }
1356         /* had to position more than once GIVE UP */
1357         if (pdone > 1) {
1358             /* UNDO all the changes we made to try this */
1359             sym->isspilt = 1;
1360             for (i=0; i < sym->nRegs ; i++ ) {
1361                 sym->regs[i] = NULL;
1362             }
1363             freeAllRegs();
1364             D(D_FILL_GAPS,("Fill Gap gave up due to positioning for %s in function %s\n",sym->name, currFunc ? currFunc->name : "UNKNOWN"));
1365             continue ;      
1366         }
1367         D(D_FILL_GAPS,("FILLED GAP for %s in function %s\n",sym->name, currFunc ? currFunc->name : "UNKNOWN"));
1368         _G.totRegAssigned = bitVectSetBit(_G.totRegAssigned,sym->key);
1369         sym->isspilt = sym->spillA = 0 ;
1370         sym->usl.spillLoc->allocreq--;
1371         freeAllRegs();
1372     }
1373 }
1374
1375 /*-----------------------------------------------------------------*/
1376 /* rUmaskForOp :- returns register mask for an operand             */
1377 /*-----------------------------------------------------------------*/
1378 bitVect *
1379 rUmaskForOp (operand * op)
1380 {
1381   bitVect *rumask;
1382   symbol *sym;
1383   int j;
1384
1385   /* only temporaries are assigned registers */
1386   if (!IS_ITEMP (op))
1387     return NULL;
1388
1389   sym = OP_SYMBOL (op);
1390
1391   /* if spilt or no registers assigned to it
1392      then nothing */
1393   if (sym->isspilt || !sym->nRegs)
1394     return NULL;
1395
1396   rumask = newBitVect (_G.nRegs);
1397
1398   for (j = 0; j < sym->nRegs; j++)
1399     {
1400       rumask = bitVectSetBit (rumask, sym->regs[j]->rIdx);
1401     }
1402
1403   return rumask;
1404 }
1405
1406 bitVect *
1407 z80_rUmaskForOp (operand * op)
1408 {
1409   return rUmaskForOp (op);
1410 }
1411
1412 /** Returns bit vector of registers used in iCode.
1413  */
1414 bitVect *
1415 regsUsedIniCode (iCode * ic)
1416 {
1417   bitVect *rmask = newBitVect (_G.nRegs);
1418
1419   /* do the special cases first */
1420   if (ic->op == IFX)
1421     {
1422       rmask = bitVectUnion (rmask,
1423                             rUmaskForOp (IC_COND (ic)));
1424       goto ret;
1425     }
1426
1427   /* for the jumptable */
1428   if (ic->op == JUMPTABLE)
1429     {
1430       rmask = bitVectUnion (rmask,
1431                             rUmaskForOp (IC_JTCOND (ic)));
1432
1433       goto ret;
1434     }
1435
1436   /* of all other cases */
1437   if (IC_LEFT (ic))
1438     rmask = bitVectUnion (rmask,
1439                           rUmaskForOp (IC_LEFT (ic)));
1440
1441
1442   if (IC_RIGHT (ic))
1443     rmask = bitVectUnion (rmask,
1444                           rUmaskForOp (IC_RIGHT (ic)));
1445
1446   if (IC_RESULT (ic))
1447     rmask = bitVectUnion (rmask,
1448                           rUmaskForOp (IC_RESULT (ic)));
1449
1450 ret:
1451   return rmask;
1452 }
1453
1454 /** For each instruction will determine the regsUsed.
1455  */
1456 static void 
1457 createRegMask (eBBlock ** ebbs, int count)
1458 {
1459   int i;
1460
1461   /* for all blocks */
1462   for (i = 0; i < count; i++)
1463     {
1464       iCode *ic;
1465
1466       if (ebbs[i]->noPath &&
1467           (ebbs[i]->entryLabel != entryLabel &&
1468            ebbs[i]->entryLabel != returnLabel))
1469         continue;
1470
1471       /* for all instructions */
1472       for (ic = ebbs[i]->sch; ic; ic = ic->next)
1473         {
1474
1475           int j;
1476
1477           if (SKIP_IC2 (ic) || !ic->rlive)
1478             continue;
1479
1480           /* first mark the registers used in this
1481              instruction */
1482           ic->rUsed = regsUsedIniCode (ic);
1483           _G.funcrUsed = bitVectUnion (_G.funcrUsed, ic->rUsed);
1484
1485           /* now create the register mask for those 
1486              registers that are in use : this is a
1487              super set of ic->rUsed */
1488           ic->rMask = newBitVect (_G.nRegs + 1);
1489
1490           /* for all live Ranges alive at this point */
1491           for (j = 1; j < ic->rlive->size; j++)
1492             {
1493               symbol *sym;
1494               int k;
1495
1496               /* if not alive then continue */
1497               if (!bitVectBitValue (ic->rlive, j))
1498                 continue;
1499
1500               /* find the live range we are interested in */
1501               if (!(sym = hTabItemWithKey (liveRanges, j)))
1502                 {
1503                   werror (E_INTERNAL_ERROR, __FILE__, __LINE__,
1504                           "createRegMask cannot find live range");
1505                   exit (0);
1506                 }
1507
1508               /* if no register assigned to it */
1509               if (!sym->nRegs || sym->isspilt)
1510                 continue;
1511
1512               /* for all the registers allocated to it */
1513               for (k = 0; k < sym->nRegs; k++)
1514                 if (sym->regs[k])
1515                   ic->rMask =
1516                     bitVectSetBit (ic->rMask, sym->regs[k]->rIdx);
1517             }
1518         }
1519     }
1520 }
1521
1522 /** Returns the rematerialized string for a remat var.
1523  */
1524 char *
1525 rematStr (symbol * sym)
1526 {
1527   char *s = buffer;
1528   iCode *ic = sym->rematiCode;
1529
1530   while (1)
1531     {
1532
1533       /* if plus or minus print the right hand side */
1534       if (ic->op == '+' || ic->op == '-')
1535         {
1536           sprintf (s, "0x%04x %c ", (int) operandLitValue (IC_RIGHT (ic)),
1537                    ic->op);
1538           s += strlen (s);
1539           ic = OP_SYMBOL (IC_LEFT (ic))->rematiCode;
1540           continue;
1541         }
1542       /* we reached the end */
1543       sprintf (s, "%s", OP_SYMBOL (IC_LEFT (ic))->rname);
1544       break;
1545     }
1546
1547   return buffer;
1548 }
1549
1550 /*-----------------------------------------------------------------*/
1551 /* regTypeNum - computes the type & number of registers required   */
1552 /*-----------------------------------------------------------------*/
1553 static void 
1554 regTypeNum (void)
1555 {
1556   symbol *sym;
1557   int k;
1558
1559   /* for each live range do */
1560   for (sym = hTabFirstItem (liveRanges, &k); sym;
1561        sym = hTabNextItem (liveRanges, &k))
1562     {
1563
1564       /* if used zero times then no registers needed */
1565       if ((sym->liveTo - sym->liveFrom) == 0)
1566         continue;
1567
1568       D (D_ALLOC, ("regTypeNum: loop on sym %p\n", sym));
1569
1570       /* if the live range is a temporary */
1571       if (sym->isitmp)
1572         {
1573
1574           /* if the type is marked as a conditional */
1575           if (sym->regType == REG_CND)
1576             continue;
1577
1578           /* if used in return only then we don't 
1579              need registers */
1580           if (sym->ruonly || sym->accuse)
1581             {
1582               if (IS_AGGREGATE (sym->type) || sym->isptr)
1583                 sym->type = aggrToPtr (sym->type, FALSE);
1584               continue;
1585             }
1586
1587           /* if not then we require registers */
1588           D (D_ALLOC, ("regTypeNum: isagg %u nRegs %u type %p\n", IS_AGGREGATE (sym->type) || sym->isptr, sym->nRegs, sym->type));
1589           sym->nRegs = ((IS_AGGREGATE (sym->type) || sym->isptr) ?
1590                         getSize (sym->type = aggrToPtr (sym->type, FALSE)) :
1591                         getSize (sym->type));
1592           D (D_ALLOC, ("regTypeNum: setting nRegs of %s (%p) to %u\n", sym->name, sym, sym->nRegs));
1593
1594           D (D_ALLOC, ("regTypeNum: setup to assign regs sym %p\n", sym));
1595
1596           if (sym->nRegs > 4)
1597             {
1598               fprintf (stderr, "allocated more than 4 or 0 registers for type ");
1599               printTypeChain (sym->type, stderr);
1600               fprintf (stderr, "\n");
1601             }
1602
1603           /* determine the type of register required */
1604           /* Always general purpose */
1605           sym->regType = REG_GPR;
1606
1607         }
1608       else
1609         {
1610           /* for the first run we don't provide */
1611           /* registers for true symbols we will */
1612           /* see how things go                  */
1613           D (D_ALLOC, ("regTypeNum: #2 setting num of %p to 0\n", sym));
1614           sym->nRegs = 0;
1615         }
1616     }
1617
1618 }
1619
1620 /** Mark all registers as free.
1621  */
1622 static void 
1623 freeAllRegs ()
1624 {
1625   int i;
1626
1627   D (D_ALLOC, ("freeAllRegs: running.\n"));
1628
1629   for (i = 0; i < _G.nRegs; i++)
1630     regsZ80[i].isFree = 1;
1631 }
1632
1633 /*-----------------------------------------------------------------*/
1634 /* deallocStackSpil - this will set the stack pointer back         */
1635 /*-----------------------------------------------------------------*/
1636 DEFSETFUNC (deallocStackSpil)
1637 {
1638   symbol *sym = item;
1639
1640   deallocLocal (sym);
1641   return 0;
1642 }
1643
1644 /** Register reduction for assignment.
1645  */
1646 static int 
1647 packRegsForAssign (iCode * ic, eBBlock * ebp)
1648 {
1649   iCode *dic, *sic;
1650
1651   D (D_ALLOC, ("packRegsForAssign: running on ic %p\n", ic));
1652
1653   if (!IS_ITEMP (IC_RIGHT (ic)) ||
1654       OP_SYMBOL (IC_RIGHT (ic))->isind ||
1655       OP_LIVETO (IC_RIGHT (ic)) > ic->seq)
1656     {
1657       return 0;
1658     }
1659
1660   /* find the definition of iTempNN scanning backwards if we find a 
1661      a use of the true symbol in before we find the definition then 
1662      we cannot */
1663   for (dic = ic->prev; dic; dic = dic->prev)
1664     {
1665       /* PENDING: Don't pack across function calls. */
1666       if (dic->op == CALL || dic->op == PCALL)
1667         {
1668           dic = NULL;
1669           break;
1670         }
1671
1672       if (SKIP_IC2 (dic))
1673         continue;
1674
1675       if (IS_SYMOP (IC_RESULT (dic)) &&
1676           IC_RESULT (dic)->key == IC_RIGHT (ic)->key)
1677         {
1678           break;
1679         }
1680
1681       if (IS_SYMOP (IC_RIGHT (dic)) &&
1682           (IC_RIGHT (dic)->key == IC_RESULT (ic)->key ||
1683            IC_RIGHT (dic)->key == IC_RIGHT (ic)->key))
1684         {
1685           dic = NULL;
1686           break;
1687         }
1688
1689       if (IS_SYMOP (IC_LEFT (dic)) &&
1690           (IC_LEFT (dic)->key == IC_RESULT (ic)->key ||
1691            IC_LEFT (dic)->key == IC_RIGHT (ic)->key))
1692         {
1693           dic = NULL;
1694           break;
1695         }
1696     }
1697
1698   if (!dic)
1699     return 0;                   /* did not find */
1700
1701   /* if the result is on stack or iaccess then it must be
1702      the same atleast one of the operands */
1703   if (OP_SYMBOL (IC_RESULT (ic))->onStack ||
1704       OP_SYMBOL (IC_RESULT (ic))->iaccess)
1705     {
1706       /* the operation has only one symbol
1707          operator then we can pack */
1708       if ((IC_LEFT (dic) && !IS_SYMOP (IC_LEFT (dic))) ||
1709           (IC_RIGHT (dic) && !IS_SYMOP (IC_RIGHT (dic))))
1710         goto pack;
1711
1712       if (!((IC_LEFT (dic) &&
1713              IC_RESULT (ic)->key == IC_LEFT (dic)->key) ||
1714             (IC_RIGHT (dic) &&
1715              IC_RESULT (ic)->key == IC_RIGHT (dic)->key)))
1716         return 0;
1717     }
1718 pack:
1719   /* found the definition */
1720   /* replace the result with the result of */
1721   /* this assignment and remove this assignment */
1722   bitVectUnSetBit(OP_SYMBOL(IC_RESULT(dic))->defs,dic->key);
1723   IC_RESULT (dic) = IC_RESULT (ic);
1724
1725   if (IS_ITEMP (IC_RESULT (dic)) && OP_SYMBOL (IC_RESULT (dic))->liveFrom > dic->seq)
1726     {
1727       OP_SYMBOL (IC_RESULT (dic))->liveFrom = dic->seq;
1728     }
1729   /* delete from liverange table also 
1730      delete from all the points inbetween and the new
1731      one */
1732   for (sic = dic; sic != ic; sic = sic->next)
1733     {
1734       bitVectUnSetBit (sic->rlive, IC_RESULT (ic)->key);
1735       if (IS_ITEMP (IC_RESULT (dic)))
1736         bitVectSetBit (sic->rlive, IC_RESULT (dic)->key);
1737     }
1738
1739   remiCodeFromeBBlock (ebp, ic);
1740   // PENDING: Check vs mcs51
1741   bitVectUnSetBit(OP_SYMBOL(IC_RESULT(ic))->defs,ic->key);
1742   hTabDeleteItem (&iCodehTab, ic->key, ic, DELETE_ITEM, NULL);
1743   OP_DEFS(IC_RESULT (dic))=bitVectSetBit (OP_DEFS (IC_RESULT (dic)), dic->key);
1744   return 1;
1745 }
1746
1747 /** Scanning backwards looks for first assig found.
1748  */
1749 iCode *
1750 findAssignToSym (operand * op, iCode * ic)
1751 {
1752   iCode *dic;
1753
1754   for (dic = ic->prev; dic; dic = dic->prev)
1755     {
1756
1757       /* if definition by assignment */
1758       if (dic->op == '=' &&
1759           !POINTER_SET (dic) &&
1760           IC_RESULT (dic)->key == op->key)
1761         /*      &&  IS_TRUE_SYMOP(IC_RIGHT(dic)) */
1762         {
1763
1764           /* we are interested only if defined in far space */
1765           /* or in stack space in case of + & - */
1766
1767           /* if assigned to a non-symbol then return
1768              true */
1769           if (!IS_SYMOP (IC_RIGHT (dic)))
1770             break;
1771
1772           /* if the symbol is in far space then
1773              we should not */
1774           if (isOperandInFarSpace (IC_RIGHT (dic)))
1775             return NULL;
1776
1777           /* for + & - operations make sure that
1778              if it is on the stack it is the same
1779              as one of the three operands */
1780           if ((ic->op == '+' || ic->op == '-') &&
1781               OP_SYMBOL (IC_RIGHT (dic))->onStack)
1782             {
1783
1784               if (IC_RESULT (ic)->key != IC_RIGHT (dic)->key &&
1785                   IC_LEFT (ic)->key != IC_RIGHT (dic)->key &&
1786                   IC_RIGHT (ic)->key != IC_RIGHT (dic)->key)
1787                 return NULL;
1788             }
1789
1790           break;
1791
1792         }
1793
1794       /* if we find an usage then we cannot delete it */
1795       if (IC_LEFT (dic) && IC_LEFT (dic)->key == op->key)
1796         return NULL;
1797
1798       if (IC_RIGHT (dic) && IC_RIGHT (dic)->key == op->key)
1799         return NULL;
1800
1801       if (POINTER_SET (dic) && IC_RESULT (dic)->key == op->key)
1802         return NULL;
1803     }
1804
1805   /* now make sure that the right side of dic
1806      is not defined between ic & dic */
1807   if (dic)
1808     {
1809       iCode *sic = dic->next;
1810
1811       for (; sic != ic; sic = sic->next)
1812         if (IC_RESULT (sic) &&
1813             IC_RESULT (sic)->key == IC_RIGHT (dic)->key)
1814           return NULL;
1815     }
1816
1817   return dic;
1818
1819
1820 }
1821
1822 #if !DISABLE_PACKREGSFORSUPPORT
1823 // PENDING
1824
1825 /*-----------------------------------------------------------------*/
1826 /* packRegsForSupport :- reduce some registers for support calls   */
1827 /*-----------------------------------------------------------------*/
1828 static int 
1829 packRegsForSupport (iCode * ic, eBBlock * ebp)
1830 {
1831   int change = 0;
1832   /* for the left & right operand :- look to see if the
1833      left was assigned a true symbol in far space in that
1834      case replace them */
1835   D (D_ALLOC, ("packRegsForSupport: running on ic %p\n", ic));
1836
1837   if (IS_ITEMP (IC_LEFT (ic)) &&
1838       OP_SYMBOL (IC_LEFT (ic))->liveTo <= ic->seq)
1839     {
1840       iCode *dic = findAssignToSym (IC_LEFT (ic), ic);
1841       iCode *sic;
1842
1843       if (!dic)
1844         goto right;
1845
1846       /* found it we need to remove it from the
1847          block */
1848       for (sic = dic; sic != ic; sic = sic->next)
1849         bitVectUnSetBit (sic->rlive, IC_LEFT (ic)->key);
1850
1851       IC_LEFT (ic)->operand.symOperand =
1852         IC_RIGHT (dic)->operand.symOperand;
1853       IC_LEFT (ic)->key = IC_RIGHT (dic)->operand.symOperand->key;
1854       remiCodeFromeBBlock (ebp, dic);
1855       bitVectUnSetBit(OP_SYMBOL(IC_RESULT(dic))->defs,dic->key);
1856       hTabDeleteItem (&iCodehTab, dic->key, dic, DELETE_ITEM, NULL);
1857       // PENDING: Check vs mcs51
1858       change++;
1859     }
1860
1861   /* do the same for the right operand */
1862 right:
1863   if (!change &&
1864       IS_ITEMP (IC_RIGHT (ic)) &&
1865       OP_SYMBOL (IC_RIGHT (ic))->liveTo <= ic->seq)
1866     {
1867       iCode *dic = findAssignToSym (IC_RIGHT (ic), ic);
1868       iCode *sic;
1869
1870       if (!dic)
1871         return change;
1872
1873       /* found it we need to remove it from the block */
1874       for (sic = dic; sic != ic; sic = sic->next)
1875         bitVectUnSetBit (sic->rlive, IC_RIGHT (ic)->key);
1876
1877       IC_RIGHT (ic)->operand.symOperand =
1878         IC_RIGHT (dic)->operand.symOperand;
1879       IC_RIGHT (ic)->key = IC_RIGHT (dic)->operand.symOperand->key;
1880
1881       remiCodeFromeBBlock (ebp, dic);
1882       bitVectUnSetBit(OP_SYMBOL(IC_RESULT(dic))->defs,dic->key);
1883       hTabDeleteItem (&iCodehTab, dic->key, dic, DELETE_ITEM, NULL);
1884       // PENDING: vs mcs51
1885       change++;
1886     }
1887
1888   return change;
1889 }
1890 #endif
1891
1892 #define IS_OP_RUONLY(x) (x && IS_SYMOP(x) && OP_SYMBOL(x)->ruonly)
1893
1894 /** Will reduce some registers for single use.
1895  */
1896 static iCode *
1897 packRegsForOneuse (iCode * ic, operand * op, eBBlock * ebp)
1898 {
1899   bitVect *uses;
1900   iCode *dic, *sic;
1901
1902   // PENDING: Disable
1903   D (D_ALLOC, ("packRegsForOneUse: running on ic %p\n", ic));
1904
1905   /* if returning a literal then do nothing */
1906   if (!IS_SYMOP (op))
1907     return NULL;
1908
1909   /* only upto 2 bytes since we cannot predict
1910      the usage of b, & acc */
1911   if (getSize (operandType (op)) > 2)
1912     return NULL;
1913
1914   if (ic->op != RETURN &&
1915       ic->op != SEND)
1916     return NULL;
1917
1918   /* this routine will mark the a symbol as used in one 
1919      instruction use only && if the defintion is local 
1920      (ie. within the basic block) && has only one definition &&
1921      that definiion is either a return value from a 
1922      function or does not contain any variables in
1923      far space */
1924   uses = bitVectCopy (OP_USES (op));
1925   bitVectUnSetBit (uses, ic->key);      /* take away this iCode */
1926   if (!bitVectIsZero (uses))    /* has other uses */
1927     return NULL;
1928
1929   /* if it has only one defintion */
1930   if (bitVectnBitsOn (OP_DEFS (op)) > 1)
1931     return NULL;                /* has more than one definition */
1932
1933   /* get the that definition */
1934   if (!(dic =
1935         hTabItemWithKey (iCodehTab,
1936                          bitVectFirstBit (OP_DEFS (op)))))
1937     return NULL;
1938
1939   /* found the definition now check if it is local */
1940   if (dic->seq < ebp->fSeq ||
1941       dic->seq > ebp->lSeq)
1942     return NULL;                /* non-local */
1943
1944   /* now check if it is the return from a function call */
1945   if (dic->op == CALL || dic->op == PCALL)
1946     {
1947       if (ic->op != SEND && ic->op != RETURN &&
1948           !POINTER_SET(ic) && !POINTER_GET(ic))
1949         {
1950           OP_SYMBOL (op)->ruonly = 1;
1951           return dic;
1952         }
1953       dic = dic->next;
1954     }
1955
1956   /* otherwise check that the definition does
1957      not contain any symbols in far space */
1958   if (isOperandInFarSpace (IC_LEFT (dic)) ||
1959       isOperandInFarSpace (IC_RIGHT (dic)) ||
1960       IS_OP_RUONLY (IC_LEFT (ic)) ||
1961       IS_OP_RUONLY (IC_RIGHT (ic)))
1962     {
1963       return NULL;
1964     }
1965
1966   /* if pointer set then make sure the pointer is one byte */
1967   if (POINTER_SET (dic))
1968     return NULL;
1969
1970   if (POINTER_GET (dic))
1971     return NULL;
1972
1973   sic = dic;
1974
1975   /* also make sure the intervenening instructions
1976      don't have any thing in far space */
1977   for (dic = dic->next; dic && dic != ic; dic = dic->next)
1978     {
1979       /* if there is an intervening function call then no */
1980       if (dic->op == CALL || dic->op == PCALL)
1981         return NULL;
1982       /* if pointer set then make sure the pointer
1983          is one byte */
1984       if (POINTER_SET (dic))
1985         return NULL;
1986
1987       if (POINTER_GET (dic))
1988         return NULL;
1989
1990       /* if address of & the result is remat the okay */
1991       if (dic->op == ADDRESS_OF &&
1992           OP_SYMBOL (IC_RESULT (dic))->remat)
1993         continue;
1994
1995       /* if left or right or result is in far space */
1996       if (isOperandInFarSpace (IC_LEFT (dic)) ||
1997           isOperandInFarSpace (IC_RIGHT (dic)) ||
1998           isOperandInFarSpace (IC_RESULT (dic)) ||
1999           IS_OP_RUONLY (IC_LEFT (dic)) ||
2000           IS_OP_RUONLY (IC_RIGHT (dic)) ||
2001           IS_OP_RUONLY (IC_RESULT (dic)))
2002         {
2003           return NULL;
2004         }
2005     }
2006
2007   OP_SYMBOL (op)->ruonly = 1;
2008   return sic;
2009 }
2010
2011 /*-----------------------------------------------------------------*/
2012 /* isBitwiseOptimizable - requirements of JEAN LOUIS VERN          */
2013 /*-----------------------------------------------------------------*/
2014 static bool 
2015 isBitwiseOptimizable (iCode * ic)
2016 {
2017   sym_link *rtype = getSpec (operandType (IC_RIGHT (ic)));
2018
2019   /* bitwise operations are considered optimizable
2020      under the following conditions (Jean-Louis VERN) 
2021
2022      x & lit
2023      bit & bit
2024      bit & x
2025      bit ^ bit
2026      bit ^ x
2027      x   ^ lit
2028      x   | lit
2029      bit | bit
2030      bit | x
2031    */
2032   if (IS_LITERAL (rtype))
2033     return TRUE;
2034   return FALSE;
2035 }
2036
2037 /** Optimisations:
2038     Certian assignments involving pointers can be temporarly stored
2039     in HL.  Esp.
2040 genAssign
2041     ld  iy,#_Blah
2042     ld  bc,(iy)
2043 genAssign (ptr)
2044     ld  hl,bc
2045     ld  iy,#_Blah2
2046     ld  (iy),(hl)
2047 */
2048
2049 #if !DISABLE_PACKREGSFORACCUSE
2050 // PENDING
2051
2052 /** Pack registers for acc use.
2053     When the result of this operation is small and short lived it may
2054     be able to be stored in the accumelator.
2055  */
2056 static void 
2057 packRegsForAccUse (iCode * ic)
2058 {
2059   iCode *uic;
2060
2061   /* if this is an aggregate, e.g. a one byte char array */
2062   if (IS_AGGREGATE(operandType(IC_RESULT(ic)))) {
2063     return;
2064   }
2065
2066   /* if + or - then it has to be one byte result */
2067   if ((ic->op == '+' || ic->op == '-')
2068       && getSize (operandType (IC_RESULT (ic))) > 1)
2069     return;
2070
2071   /* if shift operation make sure right side is not a literal */
2072   if (ic->op == RIGHT_OP &&
2073       (isOperandLiteral (IC_RIGHT (ic)) ||
2074        getSize (operandType (IC_RESULT (ic))) > 1))
2075     return;
2076
2077   if (ic->op == LEFT_OP &&
2078       (isOperandLiteral (IC_RIGHT (ic)) ||
2079        getSize (operandType (IC_RESULT (ic))) > 1))
2080     return;
2081
2082   /* has only one definition */
2083   if (bitVectnBitsOn (OP_DEFS (IC_RESULT (ic))) > 1)
2084     return;
2085
2086   /* has only one use */
2087   if (bitVectnBitsOn (OP_USES (IC_RESULT (ic))) > 1)
2088     return;
2089
2090   /* and the usage immediately follows this iCode */
2091   if (!(uic = hTabItemWithKey (iCodehTab,
2092                                bitVectFirstBit (OP_USES (IC_RESULT (ic))))))
2093     return;
2094
2095   if (ic->next != uic)
2096     return;
2097
2098   /* if it is a conditional branch then we definitely can */
2099   if (uic->op == IFX)
2100     goto accuse;
2101
2102   if (uic->op == JUMPTABLE)
2103     return;
2104
2105 #if 0
2106   /* if the usage is not is an assignment or an 
2107      arithmetic / bitwise / shift operation then not */
2108   if (POINTER_SET (uic) &&
2109       getSize (aggrToPtr (operandType (IC_RESULT (uic)), FALSE)) > 1)
2110     return;
2111 #endif
2112
2113   if (uic->op != '=' &&
2114       !IS_ARITHMETIC_OP (uic) &&
2115       !IS_BITWISE_OP (uic) &&
2116       uic->op != LEFT_OP &&
2117       uic->op != RIGHT_OP)
2118     return;
2119
2120   /* if used in ^ operation then make sure right is not a 
2121      literl */
2122   if (uic->op == '^' && isOperandLiteral (IC_RIGHT (uic)))
2123     return;
2124
2125   /* if shift operation make sure right side is not a literal */
2126   if (uic->op == RIGHT_OP &&
2127       (isOperandLiteral (IC_RIGHT (uic)) ||
2128        getSize (operandType (IC_RESULT (uic))) > 1))
2129     return;
2130
2131   if (uic->op == LEFT_OP &&
2132       (isOperandLiteral (IC_RIGHT (uic)) ||
2133        getSize (operandType (IC_RESULT (uic))) > 1))
2134     return;
2135
2136 #if 0
2137   /* make sure that the result of this icode is not on the
2138      stack, since acc is used to compute stack offset */
2139   if (IS_TRUE_SYMOP (IC_RESULT (uic)) &&
2140       OP_SYMBOL (IC_RESULT (uic))->onStack)
2141     return;
2142 #endif
2143
2144 #if 0
2145   /* if either one of them in far space then we cannot */
2146   if ((IS_TRUE_SYMOP (IC_LEFT (uic)) &&
2147        isOperandInFarSpace (IC_LEFT (uic))) ||
2148       (IS_TRUE_SYMOP (IC_RIGHT (uic)) &&
2149        isOperandInFarSpace (IC_RIGHT (uic))))
2150     return;
2151 #endif
2152
2153   /* if the usage has only one operand then we can */
2154   if (IC_LEFT (uic) == NULL ||
2155       IC_RIGHT (uic) == NULL)
2156     goto accuse;
2157
2158   /* make sure this is on the left side if not
2159      a '+' since '+' is commutative */
2160   if (ic->op != '+' &&
2161       IC_LEFT (uic)->key != IC_RESULT (ic)->key)
2162     return;
2163
2164   // See mcs51 ralloc for reasoning
2165 #if 0
2166   /* if one of them is a literal then we can */
2167   if ((IC_LEFT (uic) && IS_OP_LITERAL (IC_LEFT (uic))) ||
2168       (IC_RIGHT (uic) && IS_OP_LITERAL (IC_RIGHT (uic))))
2169     {
2170       goto accuse;
2171       return;
2172     }
2173 #endif
2174
2175 /** This is confusing :)  Guess for now */
2176   if (IC_LEFT (uic)->key == IC_RESULT (ic)->key &&
2177       (IS_ITEMP (IC_RIGHT (uic)) ||
2178        (IS_TRUE_SYMOP (IC_RIGHT (uic)))))
2179     goto accuse;
2180
2181   if (IC_RIGHT (uic)->key == IC_RESULT (ic)->key &&
2182       (IS_ITEMP (IC_LEFT (uic)) ||
2183        (IS_TRUE_SYMOP (IC_LEFT (uic)))))
2184     goto accuse;
2185   return;
2186 accuse:
2187   OP_SYMBOL (IC_RESULT (ic))->accuse = ACCUSE_A;
2188 }
2189 #endif
2190
2191 static void 
2192 packRegsForHLUse (iCode * ic)
2193 {
2194   iCode *uic;
2195
2196   /* PENDING: Could do IFX */
2197   if (ic->op == IFX)
2198     {
2199       return;
2200     }
2201
2202   /* has only one definition */
2203   if (bitVectnBitsOn (OP_DEFS (IC_RESULT (ic))) > 1)
2204     {
2205       D (D_HLUSE, ("  + Dropping as has more than one def\n"));
2206       return;
2207     }
2208
2209   /* has only one use */
2210   if (bitVectnBitsOn (OP_USES (IC_RESULT (ic))) > 1)
2211     {
2212       D (D_HLUSE, ("  + Dropping as has more than one use\n"));
2213       return;
2214     }
2215
2216   /* and the usage immediately follows this iCode */
2217   if (!(uic = hTabItemWithKey (iCodehTab,
2218                                bitVectFirstBit (OP_USES (IC_RESULT (ic))))))
2219     {
2220       D (D_HLUSE, ("  + Dropping as usage isn't in this block\n"));
2221       return;
2222     }
2223
2224   if (ic->next != uic)
2225     {
2226       D (D_HLUSE, ("  + Dropping as usage doesn't follow this\n"));
2227       return;
2228     }
2229
2230   if (uic->op ==IFX)
2231     {
2232       return;
2233     }
2234
2235   if (getSize (operandType (IC_RESULT (ic))) != 2 ||
2236       (IC_LEFT(uic) && getSize (operandType (IC_LEFT (uic))) != 2) ||
2237       (IC_RIGHT(uic) && getSize (operandType (IC_RIGHT (uic))) != 2))
2238     {
2239       D (D_HLUSE, ("  + Dropping as the result size is not 2\n"));
2240       return;
2241     }
2242
2243   if (IS_Z80)
2244     {
2245       if (ic->op == CAST && uic->op == IPUSH)
2246         goto hluse;
2247       if (ic->op == ADDRESS_OF && uic->op == IPUSH)
2248         goto hluse;
2249       if (ic->op == ADDRESS_OF && POINTER_GET (uic) && IS_ITEMP( IC_RESULT (uic)))
2250         goto hluse;
2251       if (ic->op == CALL && ic->parmBytes == 0 && (uic->op == '-' || uic->op == '+'))
2252         goto hluse;
2253     }
2254   else if (IS_GB)
2255     {
2256       /* Case of assign a constant to offset in a static array. */
2257       if (ic->op == '+' && IS_VALOP (IC_RIGHT (ic)))
2258         {
2259           if (uic->op == '=' && POINTER_SET (uic))
2260             {
2261               goto hluse;
2262             }
2263           else if (uic->op == IPUSH && getSize (operandType (IC_LEFT (uic))) == 2)
2264             {
2265               goto hluse;
2266             }
2267         }
2268     }
2269
2270   D (D_HLUSE, ("  + Dropping as it's a bad op\n"));
2271   return;
2272 hluse:
2273   OP_SYMBOL (IC_RESULT (ic))->accuse = ACCUSE_SCRATCH;
2274 }
2275
2276 static iCode *
2277 packRegsForHLUse3 (iCode * lic, operand * op, eBBlock * ebp)
2278 {
2279   int i, key;
2280   symbol *sym;
2281   iCode *ic, *dic;
2282   bool isFirst = TRUE;
2283
2284   D (D_PACK_HLUSE3, ("Checking HL on %p lic key %u first def %u line %u:\n", OP_SYMBOL(op), lic->key, bitVectFirstBit(OP_DEFS(op)), lic->lineno));
2285   if (D_PACK_HLUSE3)
2286     piCode(lic, NULL);
2287
2288   if ( OP_SYMBOL(op)->accuse)
2289     {
2290       return NULL;
2291     }
2292
2293   if (OP_SYMBOL(op)->remat)
2294     {
2295       return NULL; 
2296     }
2297
2298   /* Only defined once */
2299   if (bitVectnBitsOn (OP_DEFS (op)) > 1)
2300     return NULL;
2301
2302   if (getSize (operandType (op)) > 2)
2303     return NULL;
2304
2305   /* And this is the definition */
2306   if (bitVectFirstBit (OP_DEFS (op)) != lic->key)
2307     return NULL;
2308
2309   /* first check if any overlapping liverange has already been
2310      assigned to DPTR */
2311   if (OP_SYMBOL(op)->clashes) 
2312     {
2313       for (i = 0 ; i < OP_SYMBOL(op)->clashes->size ; i++ ) 
2314         {
2315           if (bitVectBitValue(OP_SYMBOL(op)->clashes,i)) 
2316             {
2317               sym = hTabItemWithKey(liveRanges,i);
2318               if (sym->accuse == ACCUSE_SCRATCH)
2319                 {
2320                   return NULL;
2321                 }
2322             }
2323         }
2324     }
2325
2326   /* Nothing else that clashes with this is using the scratch
2327      register.  Scan through all of the intermediate instructions and
2328      see if any of them could nuke HL.
2329   */
2330   dic = ic = hTabFirstItemWK(iCodeSeqhTab,OP_SYMBOL(op)->liveFrom);
2331
2332   for (; ic && ic->seq <= OP_SYMBOL(op)->liveTo;
2333        ic = hTabNextItem(iCodeSeqhTab, &key)) 
2334     {
2335       if (D_PACK_HLUSE3)
2336         piCode(ic, NULL);
2337       D (D_PACK_HLUSE3, ("(On %p: op: %u next: %p)\n", ic, ic->op, ic->next));
2338
2339       if (isFirst)
2340         {
2341           isFirst = FALSE;
2342           if (ic->op == ADDRESS_OF)
2343             continue;
2344           if (POINTER_GET (ic))
2345             continue;
2346           if (ic->op == '=' && !POINTER_SET(ic))
2347             continue;
2348         }
2349
2350       if (IC_RESULT(ic) && IS_SYMOP(IC_RESULT(ic))
2351           && isOperandInDirSpace (IC_RESULT (ic)))
2352         return NULL;
2353
2354       if (IC_LEFT(ic) && IS_SYMOP(IC_LEFT(ic))
2355           && isOperandInDirSpace (IC_LEFT (ic)))
2356         return NULL;
2357
2358       if (IC_RIGHT(ic) && IS_SYMOP(IC_RIGHT(ic))
2359           && isOperandInDirSpace (IC_RIGHT (ic)))
2360         return NULL;
2361
2362       /* Handle the non left/right/result ones first */
2363       if (ic->op == IFX)
2364         continue;
2365       if (ic->op == JUMPTABLE)
2366         return NULL;
2367
2368       if (SKIP_IC2(ic))
2369         continue;
2370
2371       if (ic->op == CAST)
2372         continue;
2373
2374       if (ic->op == IPUSH && isOperandEqual (op, IC_LEFT (ic)))
2375         continue;
2376
2377       if (ic->op == SEND && isOperandEqual (op, IC_LEFT (ic)))
2378         continue;
2379
2380       if (ic->op == CALL && isOperandEqual (op, IC_RESULT (ic)))
2381         continue;
2382
2383       if (ic->op == LEFT_OP && isOperandLiteral (IC_RIGHT (ic)))
2384         continue;
2385
2386       if ((ic->op == '=' && !POINTER_SET(ic)) ||
2387           ic->op == UNARYMINUS ||
2388           ic->op == '+' ||
2389           ic->op == '-' ||
2390           ic->op == '>' ||
2391           ic->op == '<' ||
2392           ic->op == EQ_OP ||
2393           0)
2394         continue;
2395
2396       if (ic->op == '*' && isOperandEqual (op, IC_LEFT (ic)))
2397         continue;
2398
2399       if (POINTER_SET (ic) && isOperandEqual (op, IC_RESULT (ic)))
2400         continue;
2401
2402       if (POINTER_GET (ic) && isOperandEqual (op, IC_LEFT (ic)))
2403         continue;
2404
2405       if (IS_VALOP (IC_RIGHT (ic)) &&
2406           (ic->op == EQ_OP ||
2407            0))
2408         {
2409           continue;
2410         }
2411
2412       /* By default give up */
2413       return NULL;
2414     }
2415
2416   D (D_PACK_HLUSE3, ("Succeeded!\n"))
2417
2418   OP_SYMBOL (op)->accuse = ACCUSE_SCRATCH;
2419   return dic;
2420 }
2421
2422 static iCode *
2423 packRegsForIYUse (iCode * lic, operand * op, eBBlock * ebp)
2424 {
2425   int i, key;
2426   symbol *sym;
2427   iCode *ic, *dic;
2428   bitVect *uses;
2429
2430   D (D_PACK_IY, ("Checking IY on %p lic key %u first def %u line %u:\n", OP_SYMBOL(op), lic->key, bitVectFirstBit(OP_DEFS(op)), lic->lineno));
2431   if (D_PACK_IY)
2432     piCode(lic, NULL);
2433
2434   if ( OP_SYMBOL(op)->accuse)
2435     {
2436       return NULL;
2437     }
2438
2439   if (OP_SYMBOL(op)->remat)
2440     {
2441       return NULL; 
2442     }
2443
2444   /* Only defined once */
2445   if (bitVectnBitsOn (OP_DEFS (op)) > 1)
2446     return NULL;
2447
2448   /* And this is the definition */
2449   if (bitVectFirstBit (OP_DEFS (op)) != lic->key)
2450     return NULL;
2451
2452   /* first check if any overlapping liverange has already been
2453      assigned to DPTR */
2454   if (OP_SYMBOL(op)->clashes) 
2455     {
2456       for (i = 0 ; i < OP_SYMBOL(op)->clashes->size ; i++ ) 
2457         {
2458           if (bitVectBitValue(OP_SYMBOL(op)->clashes,i)) 
2459             {
2460               sym = hTabItemWithKey(liveRanges,i);
2461               if (sym->accuse == ACCUSE_IY)
2462                 {
2463                   return NULL;
2464                 }
2465             }
2466         }
2467     }
2468
2469   /* Only a few instructions can load into IY */
2470   if (lic->op != '=')
2471     {
2472       return NULL;
2473     }
2474
2475   if (getSize (operandType (op)) != 2)
2476     {
2477       D (D_ACCUSE2, ("  + Dropping as operation has size is too big\n"));
2478       return FALSE;
2479     }
2480
2481   /* Nothing else that clashes with this is using the scratch
2482      register.  Scan through all of the intermediate instructions and
2483      see if any of them could nuke HL.
2484   */
2485   dic = ic = hTabFirstItemWK(iCodeSeqhTab,OP_SYMBOL(op)->liveFrom);
2486   uses = OP_USES(op);
2487
2488   for (; ic && ic->seq <= OP_SYMBOL(op)->liveTo;
2489        ic = hTabNextItem(iCodeSeqhTab,&key)) 
2490     {
2491       if (D_PACK_IY)
2492         piCode(ic, NULL);
2493
2494       if (ic->op == PCALL || 
2495           ic->op == CALL ||
2496           ic->op == JUMPTABLE
2497           )
2498         return NULL;
2499
2500       if (SKIP_IC2(ic))
2501         continue;
2502
2503       /* Be pessamistic. */
2504       if (ic->op == IFX)
2505         return NULL;
2506
2507       D (D_PACK_IY, ("  op: %u uses %u result: %d left: %d right: %d\n", ic->op, bitVectBitValue(uses, ic->key),
2508                      IC_RESULT(ic) && IS_SYMOP(IC_RESULT(ic)) ? isOperandInDirSpace(IC_RESULT(ic)) : -1,
2509                      IC_LEFT(ic) && IS_SYMOP(IC_LEFT(ic)) ? isOperandInDirSpace(IC_LEFT(ic)) : -1,
2510                      IC_RIGHT(ic) && IS_SYMOP(IC_RIGHT(ic)) ? isOperandInDirSpace(IC_RIGHT(ic)) : -1
2511                      ));
2512
2513       if (IC_RESULT(ic) && IS_SYMOP(IC_RESULT(ic)) && 
2514           isOperandInDirSpace(IC_RESULT(ic)))
2515         return NULL;
2516       
2517       if (IC_RIGHT(ic) && IS_SYMOP(IC_RIGHT(ic)) && 
2518           isOperandInDirSpace(IC_RIGHT(ic)))
2519         return NULL;
2520       
2521       if (IC_LEFT(ic) && IS_SYMOP(IC_LEFT(ic)) && 
2522           isOperandInDirSpace(IC_LEFT(ic)))
2523         return NULL;
2524
2525       /* Only certain rules will work against IY.  Check if this iCode uses
2526          this symbol. */
2527       if (bitVectBitValue(uses, ic->key) != 0)
2528         {
2529           if (ic->op == '=' &&
2530               isOperandEqual(IC_RESULT(ic), op))
2531             continue;
2532
2533           if (ic->op == GET_VALUE_AT_ADDRESS &&
2534               isOperandEqual(IC_LEFT(ic), op))
2535             continue;
2536
2537           if (isOperandEqual(IC_RESULT(ic), IC_LEFT(ic)) == FALSE)
2538             return NULL;
2539
2540           if (IC_RIGHT (ic) && IS_VALOP (IC_RIGHT (ic)))
2541             {
2542               if (ic->op == '+' ||
2543                   ic->op == '-')
2544                 {
2545                   /* Only works if the constant is small */
2546                   if (operandLitValue (IC_RIGHT (ic)) < 4)
2547                     continue;
2548                 }
2549             }
2550
2551           return NULL;
2552         }
2553       else
2554         {
2555           /* This iCode doesn't use the sym.  See if this iCode preserves IY.
2556            */
2557           continue;
2558         }
2559
2560       /* By default give up */
2561       return NULL;
2562     }
2563
2564   D (D_PACK_IY, ("Succeeded IY!\n"));
2565
2566   OP_SYMBOL (op)->accuse = ACCUSE_IY;
2567   return dic;
2568 }
2569
2570 /** Returns TRUE if this operation can use acc and if it preserves the value.
2571  */
2572 static bool 
2573 opPreservesA (iCode * uic)
2574 {
2575   if (uic->op == IFX)
2576     {
2577       /* If we've gotten this far then the thing to compare must be
2578          small enough and must be in A.
2579       */
2580       return TRUE;
2581     }
2582
2583   if (uic->op == JUMPTABLE)
2584     {
2585       D (D_ACCUSE2, ("  + Dropping as operation is a Jumptable\n"));
2586       return FALSE;
2587     }
2588
2589   /* A pointer assign preserves A if A is the left value. */
2590   if (uic->op == '=' && POINTER_SET (uic))
2591     {
2592       return TRUE;
2593     }
2594
2595   /* if the usage has only one operand then we can */
2596   /* PENDING: check */
2597   if (IC_LEFT (uic) == NULL ||
2598       IC_RIGHT (uic) == NULL)
2599     {
2600       D (D_ACCUSE2, ("  + Dropping as operation has only one operand\n"));
2601       return FALSE;
2602     }
2603
2604   /* PENDING: check this rule */
2605   if (getSize (operandType (IC_RESULT (uic))) > 1)
2606     {
2607       D (D_ACCUSE2, ("  + Dropping as operation has size is too big\n"));
2608       return FALSE;
2609     }
2610
2611
2612   /* Disabled all of the old rules as they weren't verified and have
2613      caused at least one problem.
2614    */
2615   return FALSE;
2616 }
2617
2618 /** Returns true if this operand preserves the value of A.
2619  */
2620 static bool
2621 opIgnoresA (iCode * ic, iCode * uic)
2622 {
2623   /* A increment of an iTemp by a constant is OK. */
2624   if ( uic->op == '+' &&
2625        IS_ITEMP (IC_LEFT (uic)) &&
2626        IS_ITEMP (IC_RESULT (uic)) &&
2627        IS_OP_LITERAL (IC_RIGHT (uic)))
2628     {
2629       unsigned int icount = (unsigned int) floatFromVal (IC_RIGHT (uic)->operand.valOperand);
2630
2631       /* Being an ITEMP means that we're already a symbol. */
2632       if (icount == 1 &&
2633           IC_RESULT (uic)->operand.symOperand->key == IC_LEFT (uic)->operand.symOperand->key
2634           )
2635         {
2636           return TRUE;
2637         }
2638     }
2639   else if (uic->op == '=' && !POINTER_SET (uic))
2640     {
2641       /* If they are equal and get optimised out then things are OK. */
2642       if (isOperandEqual (IC_RESULT (uic), IC_RIGHT (uic)))
2643         {
2644           /* Straight assign is OK. */
2645           return TRUE;
2646         }
2647     }
2648
2649   return FALSE;
2650 }
2651
2652
2653 /* Some optimisation cases:
2654
2655    1. Part of memcpy
2656 ;       genPointerGet
2657         ld      l,-4(ix)
2658         ld      h,-3(ix)
2659         ld      c,(hl)
2660 ;       genPlus
2661         inc     -4(ix)
2662         jp      nz,00108$
2663         inc     -3(ix)
2664 00108$:
2665 ;       genAssign (pointer)
2666         ld      a,c
2667         ld      (de),a
2668  
2669       want to optimise down to:
2670         ld       hl,-4(ix) ...
2671         ld       a,(hl)
2672         inc      -4(ix).w  ...
2673         ld       (de),a
2674
2675       So genPointer get is OK
2676       genPlus where the right is constant, left is iTemp, and result is same as left
2677       genAssign (pointer) is OK
2678
2679     2. Part of _strcpy
2680 ;       genPointerGet
2681         ld      a,(de)
2682         ld      c,a
2683 ;       genIfx
2684         xor     a,a
2685         or      a,c
2686         jp      z,00103$
2687 ;       _strcpy.c 40
2688 ;       genAssign (pointer)
2689 ;       AOP_STK for _strcpy_to_1_1
2690         ld      l,-2(ix)
2691         ld      h,-1(ix)
2692         ld      (hl),c
2693
2694       want to optimise down to:
2695         ld      a,(de)
2696         or      a,a
2697         jp      z,00103$
2698         ld      (bc),a
2699       
2700       So genIfx where IC_COND has size of 1 and is a constant.
2701 */
2702
2703 /** Pack registers for acc use.
2704     When the result of this operation is small and short lived it may
2705     be able to be stored in the accumulator.
2706
2707     Note that the 'A preserving' list is currently emperical :)
2708  */
2709 static void 
2710 packRegsForAccUse2 (iCode * ic)
2711 {
2712   iCode *uic;
2713
2714   D (D_ACCUSE2, ("packRegsForAccUse2: running on ic %p line %u\n", ic, ic->lineno));
2715   if (D_ACCUSE2)
2716     piCode (ic, NULL);
2717
2718   /* Filter out all but those 'good' commands */
2719   if (
2720        !POINTER_GET (ic) &&
2721        ic->op != '+' &&
2722        ic->op != '-' &&
2723        !IS_BITWISE_OP (ic) &&
2724        ic->op != '=' &&
2725        ic->op != EQ_OP &&
2726        ic->op != '<' &&
2727        ic->op != '>' &&
2728        ic->op != CAST &&
2729        ic->op != GETHBIT &&
2730        1)
2731     {
2732       D (D_ACCUSE2, ("  + Dropping as not a 'good' source command\n"));
2733       return;
2734     }
2735
2736   /* if + or - then it has to be one byte result.
2737      MLH: Ok.
2738    */
2739   if ((ic->op == '+' || ic->op == '-')
2740       && getSize (operandType (IC_RESULT (ic))) > 1)
2741     {
2742       D (D_ACCUSE2, ("  + Dropping as it's a big + or -\n"));
2743       return;
2744     }
2745
2746   /* has only one definition */
2747   if (bitVectnBitsOn (OP_DEFS (IC_RESULT (ic))) > 1)
2748     {
2749       D (D_ACCUSE2, ("  + Dropping as it has more than one definition\n"));
2750       return;
2751     }
2752
2753   /* Right.  We may be able to propagate it through if:
2754      For each in the chain of uses the intermediate is OK.
2755    */
2756   /* Get next with 'uses result' bit on
2757      If this->next == next
2758      Validate use of next
2759      If OK, increase count
2760    */
2761   /* and the usage immediately follows this iCode */
2762   if (!(uic = hTabItemWithKey (iCodehTab,
2763                                bitVectFirstBit (OP_USES (IC_RESULT (ic))))))
2764     {
2765       D (D_ACCUSE2, ("  + Dropping as usage does not follow first\n"));
2766       return;
2767     }
2768
2769   {
2770     /* Create a copy of the OP_USES bit vect */
2771     bitVect *uses = bitVectCopy (OP_USES (IC_RESULT (ic)));
2772     int setBit;
2773     iCode *scan = ic, *next;
2774
2775     do
2776       {
2777         setBit = bitVectFirstBit (uses);
2778         next = hTabItemWithKey (iCodehTab, setBit);
2779         if (scan->next == next)
2780           {
2781             D (D_ACCUSE2_VERBOSE, ("  ! Is next in line\n"));
2782
2783             bitVectUnSetBit (uses, setBit);
2784             /* Still contigous. */
2785             if (!opPreservesA (next))
2786               {
2787                 D (D_ACCUSE2, ("  + Dropping as operation doesn't preserve A\n"));
2788                 return;
2789               }
2790             D (D_ACCUSE2_VERBOSE, ("  ! Preserves A, so continue scanning\n"));
2791             scan = next;
2792           }
2793         else if (scan->next == NULL && bitVectnBitsOn (uses) == 1 && next != NULL)
2794           {
2795             if (next->prev == NULL)
2796               {
2797                 if (!opPreservesA (next))
2798                   {
2799                     D (D_ACCUSE2, ("  + Dropping as operation doesn't preserve A #2\n"));
2800                     return;
2801                   }
2802                 bitVectUnSetBit (uses, setBit);
2803                 scan = next;
2804               }
2805             else 
2806               {
2807                 D (D_ACCUSE2, ("  + Dropping as last in list and next doesn't start a block\n"));
2808                 return;
2809               }
2810           }
2811         else if (scan->next == NULL)
2812           {
2813             D (D_ACCUSE2, ("  + Dropping as hit the end of the list\n"));
2814             D (D_ACCUSE2, ("  + Next in htab: %p\n", next));
2815             return;
2816           }
2817         else
2818           {
2819             if (opIgnoresA (ic, scan->next))
2820               {
2821                 /* Safe for now. */
2822                 scan = scan->next;
2823                 D (D_ACCUSE2_VERBOSE, ("  ! Op ignores A, so continue scanning\n"));
2824               }
2825             else
2826               {
2827                 D (D_ACCUSE2, ("  + Dropping as parts are not consecuitive and intermediate might use A\n"));
2828                 return;
2829               }
2830           }
2831       }
2832     while (!bitVectIsZero (uses));
2833
2834     OP_SYMBOL (IC_RESULT (ic))->accuse = ACCUSE_A;
2835     return;
2836   }
2837 }
2838
2839 /** Does some transformations to reduce register pressure.
2840  */
2841 static void 
2842 packRegisters (eBBlock * ebp)
2843 {
2844   iCode *ic;
2845   int change = 0;
2846
2847   D (D_ALLOC, ("packRegisters: entered.\n"));
2848
2849   while (1 && !DISABLE_PACK_ASSIGN)
2850     {
2851       change = 0;
2852       /* look for assignments of the form */
2853       /* iTempNN = TRueSym (someoperation) SomeOperand */
2854       /*       ....                       */
2855       /* TrueSym := iTempNN:1             */
2856       for (ic = ebp->sch; ic; ic = ic->next)
2857         {
2858           /* find assignment of the form TrueSym := iTempNN:1 */
2859           if (ic->op == '=' && !POINTER_SET (ic))
2860             change += packRegsForAssign (ic, ebp);
2861         }
2862       if (!change)
2863         break;
2864     }
2865
2866   for (ic = ebp->sch; ic; ic = ic->next)
2867     {
2868       /* Safe: address of a true sym is always constant. */
2869       /* if this is an itemp & result of a address of a true sym 
2870          then mark this as rematerialisable   */
2871       D (D_ALLOC, ("packRegisters: looping on ic %p\n", ic));
2872
2873       if (ic->op == ADDRESS_OF &&
2874           IS_ITEMP (IC_RESULT (ic)) &&
2875           IS_TRUE_SYMOP (IC_LEFT (ic)) &&
2876           bitVectnBitsOn (OP_DEFS (IC_RESULT (ic))) == 1 &&
2877           !OP_SYMBOL (IC_LEFT (ic))->onStack)
2878         {
2879
2880           OP_SYMBOL (IC_RESULT (ic))->remat = 1;
2881           OP_SYMBOL (IC_RESULT (ic))->rematiCode = ic;
2882           OP_SYMBOL (IC_RESULT (ic))->usl.spillLoc = NULL;
2883         }
2884
2885       /* Safe: just propagates the remat flag */
2886       /* if straight assignment then carry remat flag if this is the
2887          only definition */
2888       if (ic->op == '=' &&
2889           !POINTER_SET (ic) &&
2890           IS_SYMOP (IC_RIGHT (ic)) &&
2891           OP_SYMBOL (IC_RIGHT (ic))->remat &&
2892           bitVectnBitsOn (OP_SYMBOL (IC_RESULT (ic))->defs) <= 1)
2893         {
2894
2895           OP_SYMBOL (IC_RESULT (ic))->remat =
2896             OP_SYMBOL (IC_RIGHT (ic))->remat;
2897           OP_SYMBOL (IC_RESULT (ic))->rematiCode =
2898             OP_SYMBOL (IC_RIGHT (ic))->rematiCode;
2899         }
2900
2901       /* if the condition of an if instruction is defined in the
2902          previous instruction then mark the itemp as a conditional */
2903       if ((IS_CONDITIONAL (ic) ||
2904            ((ic->op == BITWISEAND ||
2905              ic->op == '|' ||
2906              ic->op == '^') &&
2907             isBitwiseOptimizable (ic))) &&
2908           ic->next && ic->next->op == IFX &&
2909           bitVectnBitsOn (OP_USES(IC_RESULT(ic)))==1 &&
2910           isOperandEqual (IC_RESULT (ic), IC_COND (ic->next)) &&
2911           OP_SYMBOL (IC_RESULT (ic))->liveTo <= ic->next->seq)
2912         {
2913
2914           OP_SYMBOL (IC_RESULT (ic))->regType = REG_CND;
2915           continue;
2916         }
2917
2918 #if 0
2919       /* reduce for support function calls */
2920       if (ic->supportRtn || ic->op == '+' || ic->op == '-')
2921         packRegsForSupport (ic, ebp);
2922 #endif
2923
2924       /* some cases the redundant moves can
2925          can be eliminated for return statements */
2926       if (ic->op == RETURN || ic->op == SEND)
2927         {
2928           packRegsForOneuse (ic, IC_LEFT (ic), ebp);
2929         }
2930
2931       /* if pointer set & left has a size more than
2932          one and right is not in far space */
2933       if (!DISABLE_PACK_ONE_USE &&
2934           POINTER_SET (ic) &&
2935           /* MLH: no such thing.
2936              !isOperandInFarSpace(IC_RIGHT(ic)) && */
2937           !OP_SYMBOL (IC_RESULT (ic))->remat &&
2938           !IS_OP_RUONLY (IC_RIGHT (ic)) &&
2939           getSize (aggrToPtr (operandType (IC_RESULT (ic)), FALSE)) > 1)
2940         {
2941
2942           packRegsForOneuse (ic, IC_RESULT (ic), ebp);
2943         }
2944
2945       /* if pointer get */
2946       if (!DISABLE_PACK_ONE_USE &&
2947           POINTER_GET (ic) &&
2948           IS_SYMOP (IC_LEFT (ic)) &&
2949       /* MLH: dont have far space
2950          !isOperandInFarSpace(IC_RESULT(ic))&& */
2951           !OP_SYMBOL (IC_LEFT (ic))->remat &&
2952           !IS_OP_RUONLY (IC_RESULT (ic)) &&
2953           getSize (aggrToPtr (operandType (IC_LEFT (ic)), FALSE)) > 1)
2954         {
2955
2956           packRegsForOneuse (ic, IC_LEFT (ic), ebp);
2957         }
2958
2959       /* pack registers for accumulator use, when the result of an
2960          arithmetic or bit wise operation has only one use, that use is
2961          immediately following the defintion and the using iCode has
2962          only one operand or has two operands but one is literal & the
2963          result of that operation is not on stack then we can leave the
2964          result of this operation in acc:b combination */
2965
2966       if (!DISABLE_PACK_HL && IS_ITEMP (IC_RESULT (ic)))
2967         {
2968           /* PENDING */
2969           if (IS_GB)
2970             {
2971               if (0)
2972                 packRegsForHLUse (ic);
2973             }
2974           else
2975             {
2976               packRegsForHLUse3 (ic, IC_RESULT (ic), ebp);
2977             }
2978         }
2979
2980       if (!DISABLE_PACK_IY && IS_ITEMP (IC_RESULT (ic)) && IS_Z80)
2981         {
2982           packRegsForIYUse (ic, IC_RESULT (ic), ebp);
2983         }
2984
2985       if (!DISABLE_PACK_ACC && IS_ITEMP (IC_RESULT (ic)) &&
2986           getSize (operandType (IC_RESULT (ic))) == 1)
2987         {
2988           packRegsForAccUse2 (ic);
2989         }
2990     }
2991 }
2992
2993 /** Joins together two byte constant pushes into one word push.
2994  */
2995 static iCode *
2996 joinPushes (iCode *lic)
2997 {
2998   iCode *ic, *uic;
2999
3000   for (ic = lic; ic; ic = ic->next)
3001     {
3002       int first, second;
3003       value *val;
3004
3005       uic = ic->next;
3006
3007       /* Anything past this? */
3008       if (uic == NULL)
3009         {
3010           continue;
3011         }
3012       /* This and the next pushes? */
3013       if (ic->op != IPUSH || uic->op != IPUSH)
3014         {
3015           continue;
3016         }
3017       /* Both literals? */
3018       if ( !IS_OP_LITERAL (IC_LEFT (ic)) || !IS_OP_LITERAL (IC_LEFT (uic)))
3019         {
3020           continue;
3021         }
3022       /* Both characters? */
3023       if ( getSize (operandType (IC_LEFT (ic))) != 1 || getSize (operandType (IC_LEFT (uic))) != 1)
3024         {
3025           continue;
3026         }
3027       /* Pull out the values, make a new type, and create the new iCode for it.
3028        */
3029       first = (int)operandLitValue ( IC_LEFT (ic));
3030       second = (int)operandLitValue ( IC_LEFT (uic));
3031
3032       sprintf (buffer, "%uu", ((first << 8) | (second & 0xFF)) & 0xFFFFU);
3033       val = constVal (buffer);
3034       SPEC_NOUN (val->type) = V_INT;
3035       IC_LEFT (ic) = operandFromOperand (IC_LEFT (ic));
3036       IC_LEFT (ic)->operand.valOperand = val;
3037       
3038       /* Now remove the second one from the list. */
3039       ic->next = uic->next;
3040       if (uic->next)
3041         {
3042           /* Patch up the reverse link */
3043           uic->next->prev = ic;
3044         }
3045     }
3046
3047   return lic;
3048 }
3049
3050 /*-----------------------------------------------------------------*/
3051 /* assignRegisters - assigns registers to each live range as need  */
3052 /*-----------------------------------------------------------------*/
3053 void 
3054 z80_assignRegisters (eBBlock ** ebbs, int count)
3055 {
3056   iCode *ic;
3057   int i;
3058
3059   D (D_ALLOC, ("\n-> z80_assignRegisters: entered.\n"));
3060
3061   setToNull ((void *) &_G.funcrUsed);
3062   setToNull ((void *) &_G.totRegAssigned);  
3063   _G.stackExtend = _G.dataExtend = 0;
3064
3065   if (IS_GB)
3066     {
3067       /* DE is required for the code gen. */
3068       _G.nRegs = GBZ80_MAX_REGS;
3069       regsZ80 = _gbz80_regs;
3070     }
3071   else
3072     {
3073       _G.nRegs = Z80_MAX_REGS;
3074       regsZ80 = _z80_regs;
3075     }
3076
3077   /* change assignments this will remove some
3078      live ranges reducing some register pressure */
3079   for (i = 0; i < count; i++)
3080     packRegisters (ebbs[i]);
3081
3082   /* liveranges probably changed by register packing
3083      so we compute them again */
3084   recomputeLiveRanges (ebbs, count);
3085
3086   if (options.dump_pack)
3087     dumpEbbsToFileExt (DUMP_PACK, ebbs, count);
3088
3089   /* first determine for each live range the number of 
3090      registers & the type of registers required for each */
3091   regTypeNum ();
3092
3093   /* and serially allocate registers */
3094   serialRegAssign (ebbs, count);
3095
3096   freeAllRegs ();
3097   fillGaps();
3098
3099   /* if stack was extended then tell the user */
3100   if (_G.stackExtend)
3101     {
3102 /*      werror(W_TOOMANY_SPILS,"stack", */
3103 /*             _G.stackExtend,currFunc->name,""); */
3104       _G.stackExtend = 0;
3105     }
3106
3107   if (_G.dataExtend)
3108     {
3109 /*      werror(W_TOOMANY_SPILS,"data space", */
3110 /*             _G.dataExtend,currFunc->name,""); */
3111       _G.dataExtend = 0;
3112     }
3113
3114   if (options.dump_rassgn) {
3115     dumpEbbsToFileExt (DUMP_RASSGN, ebbs, count);
3116     dumpLiveRanges (DUMP_LRANGE, liveRanges);
3117   }
3118
3119   /* after that create the register mask
3120      for each of the instruction */
3121   createRegMask (ebbs, count);
3122
3123   /* now get back the chain */
3124   ic = iCodeLabelOptimize (iCodeFromeBBlock (ebbs, count));
3125
3126   ic = joinPushes (ic);
3127
3128   /* redo that offsets for stacked automatic variables */
3129   redoStackOffsets ();
3130
3131   genZ80Code (ic);
3132
3133   /* free up any stackSpil locations allocated */
3134   applyToSet (_G.stackSpil, deallocStackSpil);
3135   _G.slocNum = 0;
3136   setToNull ((void *) &_G.stackSpil);
3137   setToNull ((void *) &_G.spiltSet);
3138   /* mark all registers as free */
3139   freeAllRegs ();
3140
3141   return;
3142 }