ebp->depth = depth;
/* put the loop region info in the block */
- /* NOTE: here we will update only the inner most loop
- that it is a part of */
- if (!ebp->partOfLoop)
- ebp->partOfLoop = lr;
+ if (!isinSet (ebp->partOfLoop, lr))
+ addSetHead (&ebp->partOfLoop, lr);
/* if any of the successors go out of the loop then */
/* we add this one to the exits */
V_ARG (int, count);
addSetHead (&ebp->inExprs, cdp);
- cseBBlock (ebp, 0, ebbs, count);
+ cseBBlock (ebp, optimize.global_cse, ebbs, count);
return 0;
}
int lin, rin;
cseDef *ivar;
- /* if there are function calls in this block and this
- is a pointer get, the function could have changed it
- so skip, ISO-C99 according to David A. Long */
- if (fCallsInBlock && POINTER_GET(ic)) {
- continue;
+ /* TODO this is only needed if the call is between
+ here and the definition, but I am too lazy to do that now */
+
+ /* if there are function calls in this block */
+ if (fCallsInBlock) {
+
+ /* if this is a pointer get */
+ if (POINTER_GET(ic)) {
+ continue;
+ }
+
+ /* if this is an assignment from a global */
+ if (ic->op=='=' && isOperandGlobal(IC_RIGHT(ic))) {
+ continue;
+ }
}
if (SKIP_IC (ic) || POINTER_SET (ic) || ic->op == IFX)
iCode *newic = newiCode ('=', NULL,
operandFromOperand (IC_RIGHT (ic)));
IC_RESULT (newic) = operandFromOperand (IC_RESULT (ic));
- OP_DEFS (IC_RESULT (newic)) =
+ OP_DEFS(IC_RESULT (newic))=
bitVectSetBit (OP_DEFS (IC_RESULT (newic)), newic->key);
- OP_USES (IC_RIGHT (newic)) =
+ OP_USES(IC_RIGHT (newic))=
bitVectSetBit (OP_USES (IC_RIGHT (newic)), newic->key);
/* and add it */
if (eblock->sch && eblock->sch->op == LABEL)
/* add the induction variable vector to the last
block in the loop */
lastBlock->isLastInLoop = 1;
- lastBlock->linds = indVect;
+ lastBlock->linds = bitVectUnion(lastBlock->linds,indVect);
}
setToNull ((void **) &indVars);
if (lp->entry == theLoop->entry)
{
theLoop->regBlocks = unionSets (theLoop->regBlocks,
- lp->regBlocks, THROW_BOTH);
+ lp->regBlocks, THROW_DEST);
lp->merged = 1;
}
}
applyToSet (allRegion, mergeInnerLoops, allRegion, &maxDepth);
maxDepth++;
+
/* now create all the exits .. also */
/* create an ordered set of loops */
/* i.e. we process loops in the inner to outer order */
return change;
}
+
+/*-----------------------------------------------------------------*/
+/* addLoopBlocks - will add all blocks inside a loop to this loop */
+/* this should fix most of the liverange problems */
+/*-----------------------------------------------------------------*/
+void
+addLoopBlocks (eBBlock ** ebbs, int count)
+{
+ region *aloop;
+ struct eBBlock *block;
+ int seqMin, seqMax;
+ int i, j;
+
+ for (i = 0; i < count; i++)
+ {
+ if (!ebbs[i]->partOfLoop)
+ continue;
+
+ /* for all loops this block belongs to */
+ /* add inner block not already marked as part of this loop */
+ aloop = setFirstItem (ebbs[i]->partOfLoop);
+ for (; aloop; aloop = setNextItem (ebbs[i]->partOfLoop))
+ {
+
+ if (aloop->visited)
+ continue;
+
+ aloop->visited = 1;
+
+ /* set max & min Seq for loopRegion */
+ block = setFirstItem (aloop->regBlocks);
+ seqMax = block->lSeq;
+ seqMin = block->fSeq;
+ for (; block; block = setNextItem (aloop->regBlocks))
+ {
+ if (block->lSeq > seqMax)
+ seqMax = block->lSeq;
+ if (block->fSeq < seqMin)
+ seqMin = block->fSeq;
+ }
+
+ /* add all blocks between seqMin, seqMax to loop */
+ for (j = 0; j < count; j++)
+ {
+ if (ebbs[j]->fSeq > seqMin && ebbs[j]->lSeq < seqMax &&
+ !isinSet (aloop->regBlocks, ebbs[j]))
+ {
+ if (!isinSet (ebbs[i]->partOfLoop, aloop))
+ addSetHead (&ebbs[j]->partOfLoop, aloop);
+ }
+ }
+ }
+ }
+}