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