1 //#define LIVERANGEHUNT
7 /*-------------------------------------------------------------------------
8 SDCCcse.c - source file for Common Subexpressions and other utility
10 Written By - Sandeep Dutta . sandeep.dutta@usa.net (1998)
12 This program is free software; you can redistribute it and/or modify it
13 under the terms of the GNU General Public License as published by the
14 Free Software Foundation; either version 2, or (at your option) any
17 This program is distributed in the hope that it will be useful,
18 but WITHOUT ANY WARRANTY; without even the implied warranty of
19 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 GNU General Public License for more details.
22 You should have received a copy of the GNU General Public License
23 along with this program; if not, write to the Free Software
24 Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
26 In other words, you are welcome to use, share and improve this program.
27 You are forbidden to forbid anyone else to use, share and improve
28 what you give them. Help stamp out software-hoarding!
29 -------------------------------------------------------------------------*/
34 /*-----------------------------------------------------------------*/
35 /* newCseDef - new cseDef */
36 /*-----------------------------------------------------------------*/
38 newCseDef (operand * sym, iCode * ic)
43 cdp = Safe_alloc (sizeof (cseDef));
54 /*-----------------------------------------------------------------*/
55 /* int isCseDefEqual - two definitions are equal */
56 /*-----------------------------------------------------------------*/
58 isCseDefEqual (void *vsrc, void *vdest)
66 return (src->key == dest->key &&
67 src->diCode == dest->diCode);
71 /*-----------------------------------------------------------------*/
72 /* pcseDef - in the cseDef */
73 /*-----------------------------------------------------------------*/
75 pcseDef (void *item, va_list ap)
83 fprintf (stdout, "**null op**");
84 printOperand (cdp->sym, stdout);
85 icTab = getTableEntry (cdp->diCode->op);
86 icTab->iCodePrint (stdout, cdp->diCode, icTab->printName);
90 void ReplaceOpWithCheaperOp(operand **op, operand *cop) {
92 printf ("ReplaceOpWithCheaperOp (%s:%d with %s:%d): ",
93 OP_SYMBOL((*op))->name, OP_SYMBOL((*op))->isreqv,
94 OP_SYMBOL(cop)->name, OP_SYMBOL(cop)->isreqv);
95 // if op is a register equivalent
96 if (IS_ITEMP(cop) && OP_SYMBOL((*op))->isreqv) {
97 operand **rop = &OP_SYMBOL((*op))->usl.spillLoc->reqv;
98 if (isOperandEqual(*rop, *op)) {
101 OP_SYMBOL((*op))->isreqv=0;
102 OP_SYMBOL(cop)->isreqv=1;
112 /*-----------------------------------------------------------------*/
113 /* replaceAllSymBySym - replaces all operands by operand in an */
114 /* instruction chain */
115 /*-----------------------------------------------------------------*/
117 replaceAllSymBySym (iCode * ic, operand * from, operand * to, bitVect ** ndpset)
121 LRH(printf ("replaceAllSymBySym: from %s to %s\n", OP_SYMBOL(from)->name, OP_SYMBOL(to)->name));
122 for (lic = ic; lic; lic = lic->next)
126 /* do the special cases first */
130 IC_COND (lic)->key == from->key)
133 bitVectUnSetBit (OP_USES (from), lic->key);
134 OP_USES(to)=bitVectSetBit (OP_USES (to), lic->key);
135 siaddr = IC_COND (lic)->isaddr;
136 IC_COND (lic) = operandFromOperand (to);
137 IC_COND (lic)->isaddr = siaddr;
143 if (lic->op == JUMPTABLE)
146 IC_JTCOND (lic)->key == from->key)
149 bitVectUnSetBit (OP_USES (from), lic->key);
150 OP_USES(to)=bitVectSetBit (OP_USES (to), lic->key);
151 siaddr = IC_COND (lic)->isaddr;
152 IC_JTCOND (lic) = operandFromOperand (to);
153 IC_JTCOND (lic)->isaddr = siaddr;
159 if (IC_RESULT (lic) && IC_RESULT (lic)->key == from->key)
161 /* maintain du chains */
162 if (POINTER_SET (lic))
164 bitVectUnSetBit (OP_USES (from), lic->key);
165 OP_USES(to)=bitVectSetBit (OP_USES (to), lic->key);
167 /* also check if the "from" was in the non-dominating
168 pointer sets and replace it with "to" in the bitVector */
169 if (bitVectBitValue (*ndpset, from->key))
171 bitVectUnSetBit (*ndpset, from->key);
172 bitVectSetBit (*ndpset, to->key);
178 bitVectUnSetBit (OP_DEFS (from), lic->key);
179 OP_DEFS(to)=bitVectSetBit (OP_DEFS (to), lic->key);
181 siaddr = IC_RESULT (lic)->isaddr;
182 IC_RESULT (lic) = operandFromOperand (to);
183 IC_RESULT (lic)->isaddr = siaddr;
187 IC_RIGHT (lic) && IC_RIGHT (lic)->key == from->key)
189 bitVectUnSetBit (OP_USES (from), lic->key);
190 OP_USES(to)=bitVectSetBit (OP_USES (to), lic->key);
191 siaddr = IC_RIGHT (lic)->isaddr;
192 IC_RIGHT (lic) = operandFromOperand (to);
193 IC_RIGHT (lic)->isaddr = siaddr;
197 IC_LEFT (lic) && IC_LEFT (lic)->key == from->key)
199 bitVectUnSetBit (OP_USES (from), lic->key);
200 OP_USES(to)=bitVectSetBit (OP_USES (to), lic->key);
201 siaddr = IC_LEFT (lic)->isaddr;
202 IC_LEFT (lic) = operandFromOperand (to);
203 IC_LEFT (lic)->isaddr = siaddr;
208 /*-----------------------------------------------------------------*/
209 /* iCodeKeyIs - if the icode keys match then return 1 */
210 /*-----------------------------------------------------------------*/
211 DEFSETFUNC (iCodeKeyIs)
216 if (cdp->diCode->key == key)
222 /*-----------------------------------------------------------------*/
223 /* removeFromInExprs - removes an icode from inexpressions */
224 /*-----------------------------------------------------------------*/
225 DEFSETFUNC (removeFromInExprs)
229 V_ARG (operand *, from);
230 V_ARG (operand *, to);
231 V_ARG (eBBlock *, cbp);
237 deleteItemIf (&ebp->inExprs, iCodeKeyIs, ic->key);
238 if (ebp != cbp && !bitVectBitValue (cbp->domVect, ebp->bbnum))
239 replaceAllSymBySym (ebp->sch, from, to, &ebp->ndompset);
241 applyToSet (ebp->succList, removeFromInExprs, ic, from, to, cbp);
245 /*-----------------------------------------------------------------*/
246 /* isGlobalInNearSpace - return TRUE if valriable is a globalin data */
247 /*-----------------------------------------------------------------*/
249 isGlobalInNearSpace (operand * op)
251 sym_link *type = getSpec (operandType (op));
252 /* this is 8051 specific: optimization
253 suggested by Jean-Louis VERN, with 8051s we have no
254 advantage of putting variables in near space into
256 if (isOperandGlobal (op) && !IN_FARSPACE (SPEC_OCLS (type)) &&
257 IN_DIRSPACE (SPEC_OCLS (type)))
263 /*-----------------------------------------------------------------*/
264 /* findCheaperOp - cseBBlock support routine, will check to see if */
265 /* we have a operand previously defined */
266 /*-----------------------------------------------------------------*/
267 DEFSETFUNC (findCheaperOp)
270 V_ARG (operand *, cop);
271 V_ARG (operand **, opp);
272 V_ARG (int, checkSign);
274 /* if we have already found it */
278 /* not found it yet check if this is the one */
279 /* and this is not the defining one */
280 if (cop->key == cdp->key)
283 /* do a special check this will help in */
284 /* constant propagation & dead code elim */
285 /* for assignments only */
286 if (cdp->diCode->op == '=') {
287 /* if the result is volatile then return result */
288 if (IS_OP_VOLATILE (IC_RESULT (cdp->diCode)))
289 *opp = IC_RESULT (cdp->diCode);
291 /* if this is a straight assignment and
292 left is a temp then prefer the temporary to the
294 if (!POINTER_SET (cdp->diCode) &&
295 IS_ITEMP (IC_RESULT (cdp->diCode)) &&
296 IS_TRUE_SYMOP (IC_RIGHT (cdp->diCode)))
297 *opp = IC_RESULT (cdp->diCode);
299 /* if straight assignement && and both
300 are temps then prefer the one that
301 will not need extra space to spil, also
302 take into consideration if right side
303 an induction variable
305 if (!POINTER_SET (cdp->diCode) &&
306 IS_ITEMP (IC_RESULT (cdp->diCode)) &&
307 IS_ITEMP (IC_RIGHT (cdp->diCode)) &&
308 !OP_SYMBOL (IC_RIGHT (cdp->diCode))->isind &&
309 !OP_SYMBOL(IC_RIGHT (cdp->diCode))->isreqv &&
310 ((!SPIL_LOC (IC_RIGHT (cdp->diCode)) &&
311 SPIL_LOC (IC_RESULT (cdp->diCode))) ||
312 (SPIL_LOC (IC_RESULT (cdp->diCode)) &&
313 SPIL_LOC (IC_RESULT (cdp->diCode)) ==
314 SPIL_LOC (IC_RIGHT (cdp->diCode)))))
315 *opp = IC_RESULT (cdp->diCode);
317 *opp = IC_RIGHT (cdp->diCode);
321 *opp = IC_RESULT (cdp->diCode);
324 /* if this is an assign to a temp. then check
325 if the right side is this then return this */
326 if (IS_TRUE_SYMOP (cop) &&
327 cdp->diCode->op == '=' &&
328 !POINTER_SET (cdp->diCode) &&
329 cop->key == IC_RIGHT (cdp->diCode)->key &&
330 !isGlobalInNearSpace (IC_RIGHT (cdp->diCode)) &&
331 IS_ITEMP (IC_RESULT (cdp->diCode)))
332 *opp = IC_RESULT (cdp->diCode);
335 (isOperandLiteral(*opp) || !checkSign ||
337 IS_SPEC(operandType (cop)) && IS_SPEC(operandType (*opp)) &&
338 (SPEC_USIGN(operandType (cop))==SPEC_USIGN(operandType (*opp)) &&
339 (SPEC_LONG(operandType (cop))==SPEC_LONG(operandType (*opp)))))))
342 if ((isGlobalInNearSpace (cop) &&
343 !isOperandLiteral (*opp)) ||
344 isOperandVolatile (*opp, FALSE)
351 if (cop->key == (*opp)->key)
357 if ((*opp)->isaddr != cop->isaddr && IS_ITEMP (cop))
359 *opp = operandFromOperand (*opp);
360 (*opp)->isaddr = cop->isaddr;
363 if (IS_SPEC(operandType (cop)) && IS_SPEC(operandType (*opp)) &&
364 SPEC_NOUN(operandType(cop)) != SPEC_NOUN(operandType(*opp)))
368 // "was about to replace %s with %s, Kev says no.\n",
369 // nounName(operandType(cop)),
370 // nounName(operandType(*opp)));
375 LRH(printf ("findCheaperOp: %s < %s\n",\
376 IS_SYMOP((*opp)) ? OP_SYMBOL((*opp))->name : "!SYM",\
377 OP_SYMBOL(cop)->name));
385 /*-----------------------------------------------------------------*/
386 /* findPointerSet - finds the right side of a pointer set op */
387 /*-----------------------------------------------------------------*/
388 DEFSETFUNC (findPointerSet)
391 V_ARG (operand *, op);
392 V_ARG (operand **, opp);
393 V_ARG (operand *, rop);
395 if (POINTER_SET (cdp->diCode) &&
396 IC_RESULT (cdp->diCode)->key == op->key &&
397 !isOperandVolatile (IC_RESULT (cdp->diCode), TRUE) &&
398 !isOperandVolatile (IC_RIGHT (cdp->diCode), TRUE) &&
399 getSize (operandType (IC_RIGHT (cdp->diCode))) ==
400 getSize (operandType (rop)))
402 *opp = IC_RIGHT (cdp->diCode);
409 /*-----------------------------------------------------------------*/
410 /* findPrevIc - cseBBlock support function will return the iCode */
411 /* which matches the current one */
412 /*-----------------------------------------------------------------*/
413 DEFSETFUNC (findPrevIc)
417 V_ARG (iCode **, icp);
419 /* if already found */
423 /* if the iCodes are the same */
424 if (isiCodeEqual (ic, cdp->diCode) &&
425 isOperandEqual (cdp->sym, IC_RESULT (cdp->diCode)))
427 LRH(printf ("findPrevIc same: %d %d\n", ic->key, cdp->diCode->key));
432 /* if iCodes are not the same */
433 /* see the operands maybe interchanged */
434 if (ic->op == cdp->diCode->op &&
435 (ic->op == '+' || ic->op == '*') &&
436 isOperandEqual (IC_LEFT (ic), IC_RIGHT (cdp->diCode)) &&
437 isOperandEqual (IC_RIGHT (ic), IC_LEFT (cdp->diCode)))
439 LRH(printf ("findPrevIc inter: %d %d\n", ic->key, cdp->diCode->key));
447 /*-------------------------------------------------------------------*/
448 /* ifAssignedFromGlobal - if definition is an assignment from global */
449 /*-------------------------------------------------------------------*/
450 DEFSETFUNC (ifAssignedFromGlobal)
453 iCode *dic=cdp->diCode;
455 if (dic->op=='=' && isOperandGlobal(IC_RIGHT(dic))) {
461 /*-----------------------------------------------------------------*/
462 /* ifDefGlobal - if definition is global */
463 /*-----------------------------------------------------------------*/
464 DEFSETFUNC (ifDefGlobal)
468 return (isOperandGlobal (cdp->sym));
471 /*-----------------------------------------------------------------*/
472 /* ifAnyGetPointer - if get pointer icode */
473 /*-----------------------------------------------------------------*/
474 DEFSETFUNC (ifAnyGetPointer)
478 if (cdp->diCode && POINTER_GET (cdp->diCode))
483 /*-----------------------------------------------------------------*/
484 /* ifOperandsHave - if any of the operand are the same as this */
485 /*-----------------------------------------------------------------*/
486 DEFSETFUNC (ifOperandsHave)
489 V_ARG (operand *, op);
492 if (IC_LEFT (cdp->diCode) &&
493 IS_SYMOP (IC_LEFT (cdp->diCode)) &&
494 IC_LEFT (cdp->diCode)->key == op->key)
497 if (IC_RIGHT (cdp->diCode) &&
498 IS_SYMOP (IC_RIGHT (cdp->diCode)) &&
499 IC_RIGHT (cdp->diCode)->key == op->key)
502 /* or if any of the operands are volatile */
503 if (IC_LEFT (cdp->diCode) &&
504 IS_OP_VOLATILE (IC_LEFT (cdp->diCode)))
507 if (IC_RIGHT (cdp->diCode) &&
508 IS_OP_VOLATILE (IC_RIGHT (cdp->diCode)))
512 if (IC_RESULT (cdp->diCode) &&
513 IS_OP_VOLATILE (IC_RESULT (cdp->diCode)))
519 /*-----------------------------------------------------------------*/
520 /* ifDefSymIs - if a definition is found in the set */
521 /*-----------------------------------------------------------------*/
523 ifDefSymIs (set * cseSet, operand * sym)
528 if (!sym || !IS_SYMOP (sym))
530 for (sl = cseSet; sl; sl = sl->next)
533 if (loop->sym->key == sym->key)
540 /*-----------------------------------------------------------------*/
541 /* ifDefSymIsX - will return 1 if the symbols match */
542 /*-----------------------------------------------------------------*/
543 DEFSETFUNC (ifDefSymIsX)
546 V_ARG (operand *, op);
549 return cdp->sym->key == op->key;
551 return (isOperandEqual (cdp->sym, op));
556 /*-----------------------------------------------------------------*/
557 /* ifDiCodeIs - returns truw if diCode is same */
558 /*-----------------------------------------------------------------*/
560 ifDiCodeIs (set * cseSet, iCode * ic)
568 for (sl = cseSet; sl; sl = sl->next)
571 if (loop->diCode == ic)
578 /*-----------------------------------------------------------------*/
579 /* ifPointerGet - returns true if the icode is pointer get sym */
580 /*-----------------------------------------------------------------*/
581 DEFSETFUNC (ifPointerGet)
584 V_ARG (operand *, op);
585 iCode *dic = cdp->diCode;
586 operand *left = IC_LEFT (cdp->diCode);
588 if (POINTER_GET (dic) && left->key == op->key)
594 /*-----------------------------------------------------------------*/
595 /* ifPointerSet - returns true if the icode is pointer set sym */
596 /*-----------------------------------------------------------------*/
597 DEFSETFUNC (ifPointerSet)
600 V_ARG (operand *, op);
602 if (POINTER_SET (cdp->diCode) &&
603 IC_RESULT (cdp->diCode)->key == op->key)
609 /*-----------------------------------------------------------------*/
610 /* ifDiCodeIsX - will return 1 if the symbols match */
611 /*-----------------------------------------------------------------*/
612 DEFSETFUNC (ifDiCodeIsX)
617 return cdp->diCode == ic;
621 /*-----------------------------------------------------------------*/
622 /* findBackwardDef - scan backwards to find deinition of operand */
623 /*-----------------------------------------------------------------*/
624 iCode *findBackwardDef(operand *op,iCode *ic)
628 for (lic = ic; lic ; lic = lic->prev) {
629 if (IC_RESULT(lic) && isOperandEqual(op,IC_RESULT(lic)))
635 /*-----------------------------------------------------------------*/
636 /* algebraicOpts - does some algebraic optimizations */
637 /*-----------------------------------------------------------------*/
639 algebraicOpts (iCode * ic)
641 /* we don't deal with the following iCodes
652 /* if both operands present & ! IFX */
653 /* then if they are both literal we */
654 /* perform the operation right now */
655 if (IC_RESULT (ic) &&
658 IS_OP_LITERAL (IC_LEFT (ic)) &&
659 IS_OP_LITERAL (IC_RIGHT (ic)))
662 IC_RIGHT (ic) = operandOperation (IC_LEFT (ic),
665 operandType (IC_RESULT (ic)));
668 SET_RESULT_RIGHT (ic);
672 /* if not ifx & only one operand present */
673 if (IC_RESULT (ic) &&
675 IS_OP_LITERAL (IC_LEFT (ic)) &&
679 IC_RIGHT (ic) = operandOperation (IC_LEFT (ic),
682 operandType (IC_RESULT (ic)));
685 SET_RESULT_RIGHT (ic);
690 /* a special case : or in short a kludgy solution will think
691 about a better solution over a glass of wine someday */
692 if (ic->op == GET_VALUE_AT_ADDRESS)
695 if (IS_ITEMP (IC_RESULT (ic)) &&
696 IS_TRUE_SYMOP (IC_LEFT (ic)))
700 IC_RIGHT (ic) = operandFromOperand (IC_LEFT (ic));
701 IC_RIGHT (ic)->isaddr = 0;
703 IC_RESULT (ic) = operandFromOperand (IC_RESULT (ic));
704 IC_RESULT (ic)->isaddr = 0;
705 setOperandType (IC_RESULT (ic), operandType (IC_RIGHT (ic)));
709 if (IS_ITEMP (IC_LEFT (ic)) &&
710 IS_ITEMP (IC_RESULT (ic)) &&
711 /* !OP_SYMBOL(IC_RESULT(ic))->isreqv && */
712 /* !OP_SYMBOL(IC_LEFT(ic))->isreqv && */
713 !IC_LEFT (ic)->isaddr)
716 IC_RIGHT (ic) = operandFromOperand (IC_LEFT (ic));
717 IC_RIGHT (ic)->isaddr = 0;
718 IC_RESULT (ic) = operandFromOperand (IC_RESULT (ic));
719 IC_RESULT (ic)->isaddr = 0;
727 /* depending on the operation */
731 /* if adding the same thing change to left shift by 1 */
732 if (IC_LEFT (ic)->key == IC_RIGHT (ic)->key &&
733 !IS_FLOAT (operandType (IC_RESULT (ic))))
736 IC_RIGHT (ic) = operandFromLit (1);
739 /* if addition then check if one of them is a zero */
740 /* if yes turn it into assignmnt */
741 if (IS_OP_LITERAL (IC_LEFT (ic)) &&
742 operandLitValue (IC_LEFT (ic)) == 0.0)
747 SET_ISADDR (IC_RESULT (ic), 0);
748 SET_ISADDR (IC_RIGHT (ic), 0);
751 if (IS_OP_LITERAL (IC_RIGHT (ic)) &&
752 operandLitValue (IC_RIGHT (ic)) == 0.0)
756 IC_RIGHT (ic) = IC_LEFT (ic);
758 SET_ISADDR (IC_RIGHT (ic), 0);
759 SET_ISADDR (IC_RESULT (ic), 0);
764 /* if subtracting the the same thing then zero */
765 if (IC_LEFT (ic)->key == IC_RIGHT (ic)->key)
768 IC_RIGHT (ic) = operandFromLit (0);
770 IC_RESULT (ic) = operandFromOperand (IC_RESULT (ic));
771 IC_RESULT (ic)->isaddr = 0;
775 /* if subtraction then check if one of the operand */
776 /* is zero then depending on which operand change */
777 /* to assignment or unary minus */
778 if (IS_OP_LITERAL (IC_RIGHT (ic)) &&
779 operandLitValue (IC_RIGHT (ic)) == 0.0)
781 /* right size zero change to assignment */
783 IC_RIGHT (ic) = IC_LEFT (ic);
785 SET_ISADDR (IC_RIGHT (ic), 0);
786 SET_ISADDR (IC_RESULT (ic), 0);
789 if (IS_OP_LITERAL (IC_LEFT (ic)) &&
790 operandLitValue (IC_LEFT (ic)) == 0.0)
792 /* left zero turn into an unary minus */
794 IC_LEFT (ic) = IC_RIGHT (ic);
795 IC_RIGHT (ic) = NULL;
799 /* if multiplication then check if either of */
800 /* them is zero then the result is zero */
801 /* if either of them is one then result is */
804 if (IS_OP_LITERAL (IC_LEFT (ic)))
807 if (operandLitValue (IC_LEFT (ic)) == 0.0)
810 IC_RIGHT (ic) = IC_LEFT (ic);
812 SET_RESULT_RIGHT (ic);
815 if (operandLitValue (IC_LEFT (ic)) == 1.0)
819 SET_RESULT_RIGHT (ic);
824 if (IS_OP_LITERAL (IC_RIGHT (ic)))
827 if (operandLitValue (IC_RIGHT (ic)) == 0.0)
831 SET_RESULT_RIGHT (ic);
835 if (operandLitValue (IC_RIGHT (ic)) == 1.0)
838 IC_RIGHT (ic) = IC_LEFT (ic);
840 SET_RESULT_RIGHT (ic);
846 /* if division by self then 1 */
847 if (IC_LEFT (ic)->key == IC_RIGHT (ic)->key)
850 IC_RIGHT (ic) = operandFromLit (1);
852 IC_RESULT (ic) = operandFromOperand (IC_RESULT (ic));
853 IC_RESULT (ic)->isaddr = 0;
856 /* if this is a division then check if right */
857 /* is one then change it to an assignment */
858 if (IS_OP_LITERAL (IC_RIGHT (ic)) &&
859 operandLitValue (IC_RIGHT (ic)) == 1.0)
863 IC_RIGHT (ic) = IC_LEFT (ic);
865 SET_RESULT_RIGHT (ic);
869 /* if both are the same for an comparison operators */
873 if (isOperandEqual (IC_LEFT (ic), IC_RIGHT (ic)))
876 IC_RIGHT (ic) = operandFromLit (1);
878 SET_RESULT_RIGHT (ic);
884 if (isOperandEqual (IC_LEFT (ic), IC_RIGHT (ic)))
887 IC_RIGHT (ic) = operandFromLit (0);
889 SET_RESULT_RIGHT (ic);
894 sym_link *otype = operandType(IC_RIGHT(ic));
895 sym_link *ctype = operandType(IC_LEFT(ic));
896 /* if this is a cast of a literal value */
897 if (IS_OP_LITERAL (IC_RIGHT (ic)) &&
898 !(IS_GENPTR(ctype) && (IS_PTR(otype) && !IS_GENPTR(otype)))) {
901 operandFromValue (valCastLiteral (operandType (IC_LEFT (ic)),
902 operandLitValue (IC_RIGHT (ic))));
904 SET_ISADDR (IC_RESULT (ic), 0);
906 /* if casting to the same */
907 if (compareType (operandType (IC_RESULT (ic)),
908 operandType (IC_RIGHT (ic))) == 1) {
911 SET_ISADDR (IC_RESULT (ic), 0);
916 if (IS_OP_LITERAL (IC_LEFT (ic)))
920 (operandLitValue (IC_LEFT (ic)) == 0 ?
921 operandFromLit (1) : operandFromLit (0));
923 SET_ISADDR (IC_RESULT (ic), 0);
929 #define OTHERS_PARM(s) (s->_isparm && !s->ismyparm)
930 /*-----------------------------------------------------------------*/
931 /* updateSpillLocation - keeps track of register spill location */
932 /*-----------------------------------------------------------------*/
934 updateSpillLocation (iCode * ic, int induction)
938 if (POINTER_SET (ic))
944 /* for the form true_symbol := iTempNN */
945 if (ASSIGN_ITEMP_TO_SYM (ic) &&
946 !SPIL_LOC (IC_RIGHT (ic))) {
948 setype = getSpec (operandType (IC_RESULT (ic)));
950 if (!OP_SYMBOL(IC_RIGHT (ic))->noSpilLoc &&
951 !IS_VOLATILE (setype) &&
952 !IN_FARSPACE (SPEC_OCLS (setype)) &&
953 !OTHERS_PARM (OP_SYMBOL (IC_RESULT (ic))))
955 wassert(IS_SYMOP(IC_RESULT (ic)));
956 wassert(IS_SYMOP(IC_RIGHT (ic)));
957 SPIL_LOC (IC_RIGHT (ic)) =
958 IC_RESULT (ic)->operand.symOperand;
963 #if 0 /* this needs furthur investigation can save a lot of code */
964 if (ASSIGN_SYM_TO_ITEMP(ic) &&
965 !SPIL_LOC(IC_RESULT(ic))) {
966 if (!OTHERS_PARM (OP_SYMBOL (IC_RIGHT (ic))))
967 SPIL_LOC (IC_RESULT (ic)) =
968 IC_RIGHT (ic)->operand.symOperand;
971 if (ASSIGN_ITEMP_TO_ITEMP (ic)) {
973 if (!SPIL_LOC (IC_RIGHT (ic)) &&
974 !bitVectBitsInCommon (OP_DEFS (IC_RIGHT (ic)), OP_USES (IC_RESULT (ic))) &&
975 OP_SYMBOL (IC_RESULT (ic))->isreqv) {
977 setype = getSpec (operandType (IC_RESULT (ic)));
979 if (!OP_SYMBOL(IC_RIGHT (ic))->noSpilLoc &&
980 !IS_VOLATILE (setype) &&
981 !IN_FARSPACE (SPEC_OCLS (setype)) &&
982 !OTHERS_PARM (OP_SYMBOL (IC_RESULT (ic))))
984 SPIL_LOC (IC_RIGHT (ic)) =
985 SPIL_LOC (IC_RESULT (ic));
987 /* special case for inductions */
989 OP_SYMBOL(IC_RIGHT(ic))->isreqv &&
990 !OP_SYMBOL(IC_RESULT (ic))->noSpilLoc &&
991 !SPIL_LOC(IC_RESULT(ic))) {
992 SPIL_LOC (IC_RESULT (ic)) = SPIL_LOC (IC_RIGHT (ic));
996 /*-----------------------------------------------------------------*/
997 /* setUsesDef - sets the uses def bitvector for a given operand */
998 /*-----------------------------------------------------------------*/
1000 setUsesDefs (operand * op, bitVect * bdefs,
1001 bitVect * idefs, bitVect ** oud)
1003 /* compute the definitions alive at this point */
1004 bitVect *adefs = bitVectUnion (bdefs, idefs);
1006 /* of these definitions find the ones that are */
1007 /* for this operand */
1008 adefs = bitVectIntersect (adefs, OP_DEFS (op));
1010 /* these are the definitions that this operand can use */
1011 op->usesDefs = adefs;
1013 /* the out defs is an union */
1014 *oud = bitVectUnion (*oud, adefs);
1017 /*-----------------------------------------------------------------*/
1018 /* unsetDefsAndUses - clear this operation for the operands */
1019 /*-----------------------------------------------------------------*/
1021 unsetDefsAndUses (iCode * ic)
1023 if (ic->op == JUMPTABLE)
1026 /* take away this definition from the def chain of the */
1027 /* result & take away from use set of the operands */
1030 /* turn off def set */
1031 if (IS_SYMOP (IC_RESULT (ic)))
1033 if (!POINTER_SET (ic))
1034 bitVectUnSetBit (OP_DEFS (IC_RESULT (ic)), ic->key);
1036 bitVectUnSetBit (OP_USES (IC_RESULT (ic)), ic->key);
1038 /* turn off the useSet for the operands */
1039 if (IS_SYMOP (IC_LEFT (ic)))
1040 bitVectUnSetBit (OP_USES (IC_LEFT (ic)), ic->key);
1042 if (IS_SYMOP (IC_RIGHT (ic)))
1043 bitVectUnSetBit (OP_USES (IC_RIGHT (ic)), ic->key);
1046 /* must be ifx turn off the use */ if (IS_SYMOP (IC_COND (ic)))
1047 bitVectUnSetBit (OP_USES (IC_COND (ic)), ic->key);
1050 /*-----------------------------------------------------------------*/
1051 /* ifxOptimize - changes ifx conditions if it can */
1052 /*-----------------------------------------------------------------*/
1054 ifxOptimize (iCode * ic, set * cseSet,
1056 eBBlock * ebb, int *change,
1057 eBBlock ** ebbs, int count)
1062 /* if the condition can be replaced */
1066 applyToSetFTrue (cseSet, findCheaperOp, IC_COND (ic), &pdop, 0);
1069 ReplaceOpWithCheaperOp(&IC_COND (ic), pdop);
1074 /* if the conditional is a literal then */
1075 if (IS_OP_LITERAL (IC_COND (ic)))
1078 if ((operandLitValue (IC_COND (ic)) != 0.0) && IC_TRUE (ic))
1081 /* change to a goto */
1083 IC_LABEL (ic) = IC_TRUE (ic);
1090 if (!operandLitValue (IC_COND (ic)) && IC_FALSE (ic))
1093 IC_LABEL (ic) = IC_FALSE (ic);
1099 /* then kill this if condition */
1100 remiCodeFromeBBlock (ebb, ic);
1104 /* now we need to recompute the control flow */
1105 /* since the control flow has changed */
1106 /* this is very expensive but it does not happen */
1107 /* too often, if it does happen then the user pays */
1109 computeControlFlow (ebbs, count, 1);
1110 if (!options.lessPedantic) {
1111 werror (W_CONTROL_FLOW, ic->filename, ic->lineno);
1116 /* if there is only one successor and that successor
1117 is the same one we are conditionally going to then
1118 we can remove this conditional statement */
1119 label = (IC_TRUE (ic) ? IC_TRUE (ic) : IC_FALSE (ic));
1120 if (elementsInSet (ebb->succList) == 1 &&
1121 isinSet (ebb->succList, eBBWithEntryLabel (ebbs, label, count)))
1124 remiCodeFromeBBlock (ebb, ic);
1125 computeControlFlow (ebbs, count, 1);
1126 if (!options.lessPedantic) {
1127 werror (W_CONTROL_FLOW, ic->filename, ic->lineno);
1133 /* if it remains an IFX the update the use Set */
1134 OP_USES(IC_COND (ic))=bitVectSetBit (OP_USES (IC_COND (ic)), ic->key);
1135 setUsesDefs (IC_COND (ic), ebb->defSet, ebb->outDefs, &ebb->usesDefs);
1139 /*-----------------------------------------------------------------*/
1140 /* diCodeForSym - finds the definiting instruction for a symbol */
1141 /*-----------------------------------------------------------------*/
1142 DEFSETFUNC (diCodeForSym)
1145 V_ARG (operand *, sym);
1146 V_ARG (iCode **, dic);
1148 /* if already found */
1152 /* if not if this is the defining iCode */
1153 if (sym->key == cdp->key)
1162 /*-----------------------------------------------------------------*/
1163 /* constFold - does some constant folding */
1164 /*-----------------------------------------------------------------*/
1166 constFold (iCode * ic, set * cseSet)
1170 /* this routine will change
1176 /* deal with only + & - */
1177 if (ic->op != '+' &&
1181 /* this check is a hueristic to prevent live ranges
1182 from becoming too long */
1183 if (IS_PTR (operandType (IC_RESULT (ic))))
1186 /* check if operation with a literal */
1187 if (!IS_OP_LITERAL (IC_RIGHT (ic)))
1190 /* check if we can find a definition for the
1192 if (!(applyToSet (cseSet, diCodeForSym, IC_LEFT (ic), &dic)))
1195 /* check that this is also a +/- */
1196 if (dic->op != '+' && dic->op != '-')
1199 /* with a literal */
1200 if (!IS_OP_LITERAL (IC_RIGHT (dic)))
1203 /* find the definition of the left operand
1204 of dic.then check if this defined with a
1205 get_pointer return 0 if the pointer size is
1206 less than 2 (MCS51 specific) */
1207 if (!(applyToSet (cseSet, diCodeForSym, IC_LEFT (dic), &ldic)))
1210 if (POINTER_GET (ldic) && getSize (operandType (IC_LEFT (ldic))) <= 1)
1213 /* it is if the operations are the same */
1214 /* the literal parts need to be added */
1215 IC_LEFT (ic) = operandFromOperand (IC_LEFT (dic));
1216 if (ic->op == dic->op)
1217 IC_RIGHT (ic) = operandFromLit (operandLitValue (IC_RIGHT (ic)) +
1218 operandLitValue (IC_RIGHT (dic)));
1220 IC_RIGHT (ic) = operandFromLit (operandLitValue (IC_RIGHT (ic)) -
1221 operandLitValue (IC_RIGHT (dic)));
1223 if (IS_ITEMP (IC_RESULT (ic)))
1225 SPIL_LOC (IC_RESULT (ic)) = NULL;
1226 OP_SYMBOL(IC_RESULT (ic))->noSpilLoc = 1;
1233 /*-----------------------------------------------------------------*/
1234 /* deleteGetPointers - called when a pointer is passed as parm */
1235 /* will delete from cseSet all get pointers computed from this */
1236 /* pointer. A simple ifOperandsHave is not good enough here */
1237 /*-----------------------------------------------------------------*/
1239 deleteGetPointers (set ** cseSet, set ** pss, operand * op, eBBlock * ebb)
1241 set *compItems = NULL;
1246 if (!*cseSet && !*pss)
1249 /* first find all items computed from this operand .
1250 This done fairly simply go thru the list and find
1251 those that are computed by arthimetic with this
1253 for (cdp = setFirstItem (*cseSet); cdp; cdp = setNextItem (*cseSet))
1255 if (IS_ARITHMETIC_OP (cdp->diCode))
1257 if (isOperandEqual (IC_LEFT (cdp->diCode), op) ||
1258 isOperandEqual (IC_RIGHT (cdp->diCode), op))
1260 /* save it in our list of items */
1261 addSet (&compItems, IC_RESULT (cdp->diCode));
1263 /* also check for those computed from our computed
1264 list . This will take care of situations like
1265 iTemp1 = iTemp0 + 8;
1266 iTemp2 = iTemp1 + 8; */
1267 if (isinSetWith (compItems, (void*)IC_LEFT (cdp->diCode),
1268 (insetwithFunc)isOperandEqual) ||
1269 isinSetWith (compItems, (void*)IC_RIGHT (cdp->diCode),
1270 (insetwithFunc)isOperandEqual))
1272 addSet (&compItems, IC_RESULT (cdp->diCode));
1277 /* now delete all pointer gets with this op */
1278 deleteItemIf (cseSet, ifPointerGet, op);
1279 deleteItemIf (pss, ifPointerSet, op);
1281 /* set the bit vector used by dataFlow computation later */
1282 ebb->ptrsSet = bitVectSetBit (ebb->ptrsSet, op->key);
1283 /* now for the computed items */
1284 for (cop = setFirstItem (compItems); cop; cop = setNextItem (compItems))
1286 ebb->ptrsSet = bitVectSetBit (ebb->ptrsSet, cop->key);
1287 deleteItemIf (cseSet, ifPointerGet, cop);
1288 deleteItemIf (pss, ifPointerSet, cop);
1292 /*-----------------------------------------------------------------*/
1293 /* delGetPointerSucc - delete get pointer from inExprs of succ with */
1294 /* dfnum > supplied */
1295 /*-----------------------------------------------------------------*/
1296 DEFSETFUNC (delGetPointerSucc)
1298 eBBlock *ebp = item;
1299 V_ARG (operand *, op);
1306 if (ebp->dfnum > dfnum)
1308 deleteItemIf (&ebp->inExprs, ifPointerGet, op);
1311 return applyToSet (ebp->succList, delGetPointerSucc, op, dfnum);
1314 /*-----------------------------------------------------------------*/
1315 /* fixUpTypes - KLUGE HACK fixup a lowering problem */
1316 /*-----------------------------------------------------------------*/
1318 fixUpTypes (iCode * ic)
1320 sym_link *t1 = operandType (IC_LEFT (ic)), *t2;
1322 /* if (TARGET_IS_DS390) */
1323 if (options.model == MODEL_FLAT24)
1329 /* for pointer_gets if the types of result & left r the
1330 same then change it type of result to next */
1332 compareType (t2 = operandType (IC_RESULT (ic)), t1) == 1)
1334 setOperandType (IC_RESULT (ic), t2->next);
1338 /*-----------------------------------------------------------------*/
1339 /* isSignedOp - will return 1 if sign is important to operation */
1340 /*-----------------------------------------------------------------*/
1341 static int isSignedOp (iCode *ic)
1362 case GET_VALUE_AT_ADDRESS:
1388 /*-----------------------------------------------------------------*/
1389 /* cseBBlock - common subexpression elimination for basic blocks */
1390 /* this is the hackiest kludgiest routine in the whole */
1391 /* system. also the most important, since almost all */
1392 /* data flow related information is computed by it */
1393 /*-----------------------------------------------------------------*/
1395 cseBBlock (eBBlock * ebb, int computeOnly,
1396 eBBlock ** ebbs, int count)
1402 set *ptrSetSet = NULL;
1404 /* if this block is not reachable */
1408 /* set of common subexpressions */
1409 cseSet = setFromSet (ebb->inExprs);
1411 /* these will be computed by this routine */
1412 setToNull ((void **) &ebb->outDefs);
1413 setToNull ((void **) &ebb->defSet);
1414 setToNull ((void **) &ebb->usesDefs);
1415 setToNull ((void **) &ebb->ptrsSet);
1416 setToNull ((void **) &ebb->addrOf);
1417 setToNull ((void **) &ebb->ldefs);
1419 ebb->outDefs = bitVectCopy (ebb->inDefs);
1420 bitVectDefault = iCodeKey;
1421 ebb->defSet = newBitVect (iCodeKey);
1422 ebb->usesDefs = newBitVect (iCodeKey);
1424 /* for all the instructions in this block do */
1425 for (ic = ebb->sch; ic; ic = ic->next)
1432 ic->eBBlockNum = ebb->bbnum;
1437 /* if this is an assignment from true symbol
1438 to a temp then do pointer post inc/dec optimzation */
1439 if (ic->op == '=' && !POINTER_SET (ic) &&
1440 IS_PTR (operandType (IC_RESULT (ic))))
1442 ptrPostIncDecOpt (ic);
1445 /* clear the def & use chains for the operands involved */
1446 /* in this operation . since it can change due to opts */
1447 unsetDefsAndUses (ic);
1449 if (ic->op == PCALL || ic->op == CALL || ic->op == RECEIVE)
1451 /* add to defSet of the symbol */
1452 OP_DEFS(IC_RESULT (ic))=
1453 bitVectSetBit (OP_DEFS (IC_RESULT (ic)), ic->key);
1454 /* add to the definition set of this block */
1455 ebb->defSet = bitVectSetBit (ebb->defSet, ic->key);
1456 ebb->ldefs = bitVectSetBit (ebb->ldefs, ic->key);
1457 ebb->outDefs = bitVectCplAnd (ebb->outDefs, OP_DEFS (IC_RESULT (ic)));
1458 setUsesDefs (IC_RESULT (ic), ebb->defSet, ebb->outDefs, &ebb->usesDefs);
1459 /* delete global variables from the cseSet
1460 since they can be modified by the function call */
1461 deleteItemIf (&cseSet, ifDefGlobal);
1463 /* and also itemps assigned from globals */
1464 deleteItemIf (&cseSet, ifAssignedFromGlobal);
1466 /* delete all getpointer iCodes from cseSet, this should
1467 be done only for global arrays & pointers but at this
1468 point we don't know if globals, so to be safe do all */
1469 deleteItemIf (&cseSet, ifAnyGetPointer);
1472 /* for pcall & ipush we need to add to the useSet */
1473 if ((ic->op == PCALL ||
1477 IS_SYMOP (IC_LEFT (ic)))
1480 /* check if they can be replaced */
1484 applyToSetFTrue (cseSet, findCheaperOp, IC_LEFT (ic), &pdop, 0);
1486 ReplaceOpWithCheaperOp(&IC_LEFT(ic), pdop);
1488 /* the lookup could have changed it */
1489 if (IS_SYMOP (IC_LEFT (ic)))
1491 OP_USES(IC_LEFT (ic))=
1492 bitVectSetBit (OP_USES (IC_LEFT (ic)), ic->key);
1493 setUsesDefs (IC_LEFT (ic), ebb->defSet,
1494 ebb->outDefs, &ebb->usesDefs);
1498 /* if we a sending a pointer as a parameter
1499 then kill all cse since the pointed to item
1500 might be changed in the function being called */
1501 if ((ic->op == IPUSH || ic->op == SEND) &&
1502 IS_PTR (operandType (IC_LEFT (ic))))
1504 deleteGetPointers (&cseSet, &ptrSetSet, IC_LEFT (ic), ebb);
1505 ebb->ptrsSet = bitVectSetBit (ebb->ptrsSet, IC_LEFT (ic)->key);
1506 for (i = 0; i < count; ebbs[i++]->visited = 0);
1507 applyToSet (ebb->succList, delGetPointerSucc,
1508 IC_LEFT (ic), ebb->dfnum);
1513 /* if jumptable then mark the usage */
1514 if (ic->op == JUMPTABLE)
1516 OP_USES(IC_JTCOND (ic))=
1517 bitVectSetBit (OP_USES (IC_JTCOND (ic)), ic->key);
1518 setUsesDefs (IC_JTCOND (ic), ebb->defSet,
1519 ebb->outDefs, &ebb->usesDefs);
1526 /* do some algebraic optimizations if possible */
1528 while (constFold (ic, cseSet));
1531 if (POINTER_GET (ic) && !IS_PTR (operandType (IC_LEFT (ic))))
1533 setOperandType (IC_LEFT (ic),
1534 aggrToPtr (operandType (IC_LEFT (ic)), FALSE));
1538 if (POINTER_SET (ic) && !IS_PTR (operandType (IC_RESULT (ic))))
1540 setOperandType (IC_RESULT (ic),
1541 aggrToPtr (operandType (IC_RESULT (ic)), FALSE));
1544 /* if this is a condition statment then */
1545 /* check if the condition can be replaced */
1548 ifxOptimize (ic, cseSet, computeOnly,
1554 /* if the assignment & result is a temp */
1555 /* see if we can replace it */
1559 /* update the spill location for this */
1560 updateSpillLocation (ic,0);
1562 if (POINTER_SET (ic) &&
1563 !(IS_BITFIELD (OP_SYMBOL (IC_RESULT (ic))->etype)))
1566 applyToSetFTrue (cseSet, findCheaperOp, IC_RESULT (ic), &pdop, 0);
1567 if (pdop && IS_ITEMP (pdop) && !computeOnly)
1568 ReplaceOpWithCheaperOp (&IC_RESULT(ic), pdop);
1572 checkSign = isSignedOp(ic);
1574 /* do the operand lookup i.e. for both the */
1575 /* right & left operand : check the cseSet */
1576 /* to see if they have been replaced if yes */
1577 /* then replace them with those from cseSet */
1579 /* and left is a symbol */
1580 if (IS_SYMOP (IC_LEFT (ic)) &&
1581 !computeOnly && ic->op != ADDRESS_OF)
1585 applyToSetFTrue (cseSet, findCheaperOp, IC_LEFT (ic), &pdop, checkSign);
1588 if (POINTER_GET (ic))
1590 if (IS_ITEMP (pdop) || IS_OP_LITERAL (pdop))
1592 /* some non dominating block does POINTER_SET with
1593 this variable .. unsafe to remove any POINTER_GETs */
1594 if (bitVectBitValue(ebb->ndompset,IC_LEFT(ic)->key))
1595 ebb->ptrsSet = bitVectSetBit(ebb->ptrsSet,pdop->key);
1596 ReplaceOpWithCheaperOp(&IC_LEFT(ic), pdop);
1599 /* check if there is a pointer set
1600 for the same pointer visible if yes
1601 then change this into an assignment */
1603 if (applyToSetFTrue (cseSet, findPointerSet, IC_LEFT (ic), &pdop, IC_RESULT (ic)) &&
1604 !bitVectBitValue (ebb->ptrsSet, pdop->key))
1607 IC_LEFT (ic) = NULL;
1608 ReplaceOpWithCheaperOp(&IC_RIGHT(ic), pdop);
1609 SET_ISADDR (IC_RESULT (ic), 0);
1615 ReplaceOpWithCheaperOp(&IC_LEFT(ic), pdop);
1622 if (IS_SYMOP (IC_RIGHT (ic)) && !computeOnly)
1626 applyToSetFTrue (cseSet, findCheaperOp, IC_RIGHT (ic), &pdop, checkSign);
1628 ReplaceOpWithCheaperOp(&IC_RIGHT(ic), pdop);
1633 /* if left or right changed then do algebraic */
1637 while (constFold (ic, cseSet));
1640 /* if after all this it becomes a assignment to self
1641 then delete it and continue */
1642 if (ASSIGNMENT_TO_SELF (ic))
1644 remiCodeFromeBBlock (ebb, ic);
1648 /* now we will check to see if the entire */
1649 /* operation has been performed before */
1650 /* and is available */
1651 /* don't do assignments they will be killed */
1652 /* by dead code elimination if required do */
1653 /* it only if result is a temporary */
1655 if (!(POINTER_GET (ic) &&
1656 (IS_BITFIELD (OP_SYMBOL (IC_RESULT (ic))->etype) ||
1657 isOperandVolatile (IC_LEFT (ic), TRUE) ||
1658 bitVectBitValue (ebb->ndompset, IC_LEFT (ic)->key))) &&
1660 IS_ITEMP (IC_RESULT (ic)) &&
1663 applyToSet (cseSet, findPrevIc, ic, &pdic);
1664 if (pdic && compareType (operandType (IC_RESULT (pdic)),
1665 operandType (IC_RESULT (ic))) != 1)
1667 if (pdic && port->cseOk && (*port->cseOk)(ic,pdic) == 0)
1671 /* Alternate code */
1672 if (pdic && IS_ITEMP(IC_RESULT(ic))) {
1673 if (POINTER_GET(ic) && bitVectBitValue(ebb->ptrsSet,IC_LEFT(ic)->key)) {
1674 /* Mmm, found an equivalent pointer get at a lower level.
1675 This could be a loop however with the same pointer set
1678 /* if previous definition found change this to an assignment */
1681 IC_RIGHT(ic) = operandFromOperand(IC_RESULT(pdic));
1682 SET_ISADDR(IC_RESULT(ic),0);
1683 SET_ISADDR(IC_RIGHT (ic),0);
1687 if (!(POINTER_SET (ic)) && IC_RESULT (ic)) {
1688 deleteItemIf (&cseSet, ifDefSymIsX, IC_RESULT (ic));
1689 addSetHead (&cseSet, newCseDef (IC_RESULT (ic), ic));
1693 /* if assignment to a parameter which is not
1694 mine and type is a pointer then delete
1695 pointerGets to take care of aliasing */
1696 if (ASSIGNMENT (ic) &&
1697 OTHERS_PARM (OP_SYMBOL (IC_RESULT (ic))) &&
1698 IS_PTR (operandType (IC_RESULT (ic))))
1700 deleteGetPointers (&cseSet, &ptrSetSet, IC_RIGHT (ic), ebb);
1701 for (i = 0; i < count; ebbs[i++]->visited = 0);
1702 applyToSet (ebb->succList, delGetPointerSucc, IC_RIGHT (ic), ebb->dfnum);
1703 ebb->ptrsSet = bitVectSetBit (ebb->ptrsSet, IC_RIGHT (ic)->key);
1706 /* if this is a pointerget then see if we can replace
1707 this with a previously assigned pointer value */
1708 if (POINTER_GET (ic) &&
1709 !(IS_BITFIELD (OP_SYMBOL (IC_RESULT (ic))->etype) ||
1710 isOperandVolatile (IC_LEFT (ic), TRUE)))
1713 applyToSet (ptrSetSet, findPointerSet, IC_LEFT (ic), &pdop, IC_RESULT (ic));
1714 /* if we find it then locally replace all
1715 references to the result with what we assigned */
1718 replaceAllSymBySym (ic->next, IC_RESULT (ic), pdop, &ebb->ndompset);
1722 /* delete from the cseSet anything that has */
1723 /* operands matching the result of this */
1724 /* except in case of pointer access */
1725 if (!(POINTER_SET (ic)) && IC_RESULT (ic))
1727 deleteItemIf (&cseSet, ifOperandsHave, IC_RESULT (ic));
1728 /* delete any previous definitions */
1729 ebb->defSet = bitVectCplAnd (ebb->defSet, OP_DEFS (IC_RESULT (ic)));
1733 /* add the left & right to the defUse set */
1734 if (IC_LEFT (ic) && IS_SYMOP (IC_LEFT (ic)))
1736 OP_USES(IC_LEFT (ic))=
1737 bitVectSetBit (OP_USES (IC_LEFT (ic)), ic->key);
1738 setUsesDefs (IC_LEFT (ic), ebb->defSet, ebb->outDefs, &ebb->usesDefs);
1742 if (IC_RIGHT (ic) && IS_SYMOP (IC_RIGHT (ic)))
1744 OP_USES(IC_RIGHT (ic))=
1745 bitVectSetBit (OP_USES (IC_RIGHT (ic)), ic->key);
1746 setUsesDefs (IC_RIGHT (ic), ebb->defSet, ebb->outDefs, &ebb->usesDefs);
1750 /* for the result it is special case, put the result */
1751 /* in the defuseSet if it a pointer or array access */
1752 if (POINTER_SET (defic))
1754 OP_USES(IC_RESULT (ic))=
1755 bitVectSetBit (OP_USES (IC_RESULT (ic)), ic->key);
1756 setUsesDefs (IC_RESULT (ic), ebb->defSet, ebb->outDefs, &ebb->usesDefs);
1757 deleteItemIf (&cseSet, ifPointerGet, IC_RESULT (ic));
1758 ebb->ptrsSet = bitVectSetBit (ebb->ptrsSet, IC_RESULT (ic)->key);
1759 /* delete from inexpressions of all successors which
1760 have dfNum > than this block */
1761 for (i = 0; i < count; ebbs[i++]->visited = 0);
1762 applyToSet (ebb->succList, delGetPointerSucc, IC_RESULT (ic), ebb->dfnum);
1764 /* delete from cseSet all other pointer sets
1766 deleteItemIf (&ptrSetSet, ifPointerSet, IC_RESULT (ic));
1767 /* add to the local pointerset set */
1768 addSetHead (&ptrSetSet, newCseDef (IC_RESULT (ic), ic));
1771 /* add the result to defintion set */ if (IC_RESULT (ic))
1773 OP_DEFS(IC_RESULT (ic))=
1774 bitVectSetBit (OP_DEFS (IC_RESULT (ic)), ic->key);
1775 ebb->defSet = bitVectSetBit (ebb->defSet, ic->key);
1776 ebb->outDefs = bitVectCplAnd (ebb->outDefs, OP_DEFS (IC_RESULT (ic)));
1777 ebb->ldefs = bitVectSetBit (ebb->ldefs, ic->key);
1781 /* if this is an addressof instruction then */
1782 /* put the symbol in the address of list & */
1783 /* delete it from the cseSet */
1784 if (defic->op == ADDRESS_OF)
1786 addSetHead (&ebb->addrOf, IC_LEFT (ic));
1787 deleteItemIf (&cseSet, ifDefSymIsX, IC_LEFT (ic));
1791 setToNull ((void **) &ebb->outExprs);
1792 ebb->outExprs = cseSet;
1793 ebb->outDefs = bitVectUnion (ebb->outDefs, ebb->defSet);
1794 ebb->ptrsSet = bitVectUnion (ebb->ptrsSet, ebb->inPtrsSet);
1798 /*-----------------------------------------------------------------*/
1799 /* cseAllBlocks - will sequentially go thru & do cse for all blocks */
1800 /*-----------------------------------------------------------------*/
1802 cseAllBlocks (eBBlock ** ebbs, int count)
1807 /* if optimization turned off */
1809 for (i = 0; i < count; i++)
1810 change += cseBBlock (ebbs[i], FALSE, ebbs, count);