* src/diff.1 (Index): Many, many optmisiations. Dhrystone up to 201.
authormichaelh <michaelh@4a8a32a2-be11-0410-ad9d-d568d2c75423>
Thu, 6 Dec 2001 03:07:04 +0000 (03:07 +0000)
committermichaelh <michaelh@4a8a32a2-be11-0410-ad9d-d568d2c75423>
Thu, 6 Dec 2001 03:07:04 +0000 (03:07 +0000)
git-svn-id: https://sdcc.svn.sourceforge.net/svnroot/sdcc/trunk/sdcc@1663 4a8a32a2-be11-0410-ad9d-d568d2c75423

ChangeLog
doc/choices.txt
src/z80/gen.c
src/z80/peeph-z80.def
src/z80/peeph.def
src/z80/ralloc.c

index 4590279114e6d28aa43af2aad6033c337c3ce560..164cf7777a21c0dc29c7954e062e95f848c5dfb2 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,13 @@
+2001-12-05  Michael Hope  <michaelh@juju.net.nz>
+
+       * src/diff.1 (Index): Many, many optmisiations.  Dhrystone up to 201.
+
+1904-01-06  Michael Hope  <michaelh@juju.net.nz>
+
+       * src/z80/ralloc.c (packRegsForIYUse): Fixed the case where an operand is in direct space.
+
+       * src/z80/gen.c (makeFreePairId): Optimised IY load by using a spare pair.
+
 2001-12-02  Bernhard Held  <bernhard@bernhardheld.de>
 
        * src/mcs51/gen.c (genFunction): avoid excess "inc sp"
 2001-12-02  Bernhard Held  <bernhard@bernhardheld.de>
 
        * src/mcs51/gen.c (genFunction): avoid excess "inc sp"
index d6fbe90c9b05b3e43273b0616e16ccffae8c351c..1442eca452e5bed8306897b5062f5c87fce84d0b 100644 (file)
@@ -218,4 +218,25 @@ Cleaning up the arguments to a call:
          pop    af              ; 5/byte
 
 
          pop    af              ; 5/byte
 
 
-So for 8 bytes and above use the first form.
\ No newline at end of file
+So for 8 bytes and above use the first form.
+
+Pointer assign:
+        ld      hl,bc           ; 4+4
+        ld      e,(hl)          ; 7
+        inc     hl              ; 6
+        ld      d,(hl)          ; 7
+
+vs:
+        ld      a,(bc)          ; 7
+        ld      e,a             ; 4
+        inc     bc              ; 6
+        ld      a,(bc)          ; 7
+        ld      d,a             ; 4
+
+Same cost.  Not worth it, although is does free up HL.
+
+Shift left signed on HL
+      sla  l
+      rl   h                    ; 8+8 = 16
+
+      add  hl,hl                ; 11
index 76345de7343a5bceb258c931099238aa31b68887..1ac58abf97b3b3da1baf7cb53cf2766f53c449d5 100644 (file)
@@ -60,7 +60,9 @@
   9. With asm optimised strings                17030 192 2223
 
   10 and below are with asm strings off.
   9. With asm optimised strings                17030 192 2223
 
   10 and below are with asm strings off.
-  
+
+  10 Mucho optimisations               13562 201 1FCC
+
   Apparent advantage of turning on regparams:
   1.  Cost of push
         Decent case is push of a constant 
   Apparent advantage of turning on regparams:
   1.  Cost of push
         Decent case is push of a constant 
@@ -252,6 +254,30 @@ static const char *aopNames[] = {
   "AOP_PAIRPT"
 };
 
   "AOP_PAIRPT"
 };
 
+static bool
+isLastUse (iCode *ic, operand *op)
+{
+  bitVect *uses = bitVectCopy (OP_USES (op));
+
+  while (!bitVectIsZero (uses))
+    {
+      if (bitVectFirstBit (uses) == ic->key)
+        {
+          if (bitVectnBitsOn (uses) == 1)
+            {
+              return TRUE;
+            }
+          else
+            {
+              return FALSE;
+            }
+        }
+      bitVectUnSetBit (uses, bitVectFirstBit (uses));
+    }
+
+  return FALSE;
+}
+
 static PAIR_ID
 _getTempPairId(void)
 {
 static PAIR_ID
 _getTempPairId(void)
 {
@@ -271,14 +297,50 @@ _getTempPairName(void)
   return _pairs[_getTempPairId()].name;
 }
 
   return _pairs[_getTempPairId()].name;
 }
 
+static bool
+isPairInUse (PAIR_ID id, iCode *ic)
+{
+  if (id == PAIR_DE)
+    {
+      return bitVectBitValue (ic->rMask, D_IDX) || bitVectBitValue(ic->rMask, E_IDX);
+    }
+  else if (id == PAIR_BC)
+    {
+      return bitVectBitValue (ic->rMask, B_IDX) || bitVectBitValue(ic->rMask, C_IDX);
+    }
+  else
+    {
+      wassertl (0, "Only implemented for DE and BC");
+      return TRUE;
+    }
+}
+
+static bool
+isPairInUseNotInRet(PAIR_ID id, iCode *ic)
+{
+  bitVect *rInUse;
+  
+  rInUse = bitVectCplAnd (bitVectCopy (ic->rMask), ic->rUsed);
+  
+  if (id == PAIR_DE)
+    {
+      return bitVectBitValue (rInUse, D_IDX) || bitVectBitValue(rInUse, E_IDX);
+    }
+  else
+    {
+      wassertl (0, "Only implemented for DE");
+      return TRUE;
+    }
+}
+
 static PAIR_ID
 getFreePairId (iCode *ic)
 {
 static PAIR_ID
 getFreePairId (iCode *ic)
 {
-  if (!(bitVectBitValue (ic->rMask, B_IDX) || bitVectBitValue(ic->rMask, C_IDX)))
+  if (!isPairInUse (PAIR_BC, ic))
     {
       return PAIR_BC;
     }
     {
       return PAIR_BC;
     }
-  else if (IS_Z80 && !(bitVectBitValue (ic->rMask, D_IDX) || bitVectBitValue(ic->rMask, E_IDX)))
+  else if (IS_Z80 && !isPairInUse (PAIR_DE, ic))
     {
       return PAIR_DE;
     }
     {
       return PAIR_DE;
     }
@@ -1175,8 +1237,36 @@ fetchLitPair (PAIR_ID pairId, asmop * left, int offset)
   emit2 ("ld %s,!hashedstr", pair, l);
 }
 
   emit2 ("ld %s,!hashedstr", pair, l);
 }
 
+static PAIR_ID
+makeFreePairId (iCode *ic, bool *pisUsed)
+{
+  *pisUsed = FALSE;
+
+  if (ic != NULL)
+    {
+      if (!bitVectBitValue (ic->rMask, B_IDX) && !bitVectBitValue(ic->rMask, C_IDX))
+        {
+          return PAIR_BC;
+        }
+      else if (IS_Z80 && !bitVectBitValue (ic->rMask, D_IDX) && !bitVectBitValue(ic->rMask, E_IDX))
+        {
+          return PAIR_DE;
+        }
+      else
+        {
+          *pisUsed = TRUE;
+          return PAIR_HL;
+        }
+    }
+  else
+    {
+      *pisUsed = TRUE;
+      return PAIR_HL;
+    }
+}
+
 static void
 static void
-fetchPairLong (PAIR_ID pairId, asmop * aop, int offset)
+fetchPairLong (PAIR_ID pairId, asmop * aop, iCode *ic, int offset)
 {
     /* if this is remateriazable */
     if (isLitWord (aop)) {
 {
     /* if this is remateriazable */
     if (isLitWord (aop)) {
@@ -1228,19 +1318,24 @@ fetchPairLong (PAIR_ID pairId, asmop * aop, int offset)
               }
             else
               {
               }
             else
               {
-                _push (PAIR_HL);
+                bool isUsed;
+                PAIR_ID id = makeFreePairId (ic, &isUsed);
+                if (isUsed)
+                  _push (id);
                 /* Can't load into parts, so load into HL then exchange. */
                 /* Can't load into parts, so load into HL then exchange. */
-                emit2 ("ld %s,%s", _pairs[PAIR_HL].l, aopGet (aop, offset, FALSE));
-                emit2 ("ld %s,%s", _pairs[PAIR_HL].h, aopGet (aop, offset + 1, FALSE));
-                emit2 ("push hl");
+                emit2 ("ld %s,%s", _pairs[id].l, aopGet (aop, offset, FALSE));
+                emit2 ("ld %s,%s", _pairs[id].h, aopGet (aop, offset + 1, FALSE));
+                emit2 ("push %s", _pairs[id].name);
                 emit2 ("pop iy");
                 emit2 ("pop iy");
-                _pop (PAIR_HL);
+                if (isUsed)
+                  _pop (id);
               }
           }
               }
           }
-        else {
+        else 
+          {
             emit2 ("ld %s,%s", _pairs[pairId].l, aopGet (aop, offset, FALSE));
             emit2 ("ld %s,%s", _pairs[pairId].h, aopGet (aop, offset + 1, FALSE));
             emit2 ("ld %s,%s", _pairs[pairId].l, aopGet (aop, offset, FALSE));
             emit2 ("ld %s,%s", _pairs[pairId].h, aopGet (aop, offset + 1, FALSE));
-        }
+          }
         /* PENDING: check? */
         if (pairId == PAIR_HL)
             spillPair (PAIR_HL);
         /* PENDING: check? */
         if (pairId == PAIR_HL)
             spillPair (PAIR_HL);
@@ -1250,7 +1345,7 @@ fetchPairLong (PAIR_ID pairId, asmop * aop, int offset)
 static void
 fetchPair (PAIR_ID pairId, asmop * aop)
 {
 static void
 fetchPair (PAIR_ID pairId, asmop * aop)
 {
-  fetchPairLong (pairId, aop, 0);
+  fetchPairLong (pairId, aop, NULL, 0);
 }
 
 static void
 }
 
 static void
@@ -2044,7 +2139,7 @@ _gbz80_emitAddSubLongLong (iCode *ic, asmop *left, asmop *right, bool isAdd)
   aopPut ( AOP (IC_RESULT (ic)), "a", MSB16);
   aopPut ( AOP (IC_RESULT (ic)), "e", LSB);
 
   aopPut ( AOP (IC_RESULT (ic)), "a", MSB16);
   aopPut ( AOP (IC_RESULT (ic)), "e", LSB);
 
-  fetchPairLong (PAIR_DE, left, MSB24);
+  fetchPairLong (PAIR_DE, left, NULL, MSB24);
   aopGet (right, MSB24, FALSE);
 
   _pop (PAIR_AF);
   aopGet (right, MSB24, FALSE);
 
   _pop (PAIR_AF);
@@ -2333,11 +2428,11 @@ genIpush (iCode * ic)
        }
       if (size == 4)
        {
        }
       if (size == 4)
        {
-         fetchPairLong (PAIR_HL, AOP (IC_LEFT (ic)), 2);
+         fetchPairLong (PAIR_HL, AOP (IC_LEFT (ic)), ic, 2);
          emit2 ("push hl");
          spillPair (PAIR_HL);
          _G.stack.pushed += 2;
          emit2 ("push hl");
          spillPair (PAIR_HL);
          _G.stack.pushed += 2;
-         fetchPairLong (PAIR_HL, AOP (IC_LEFT (ic)), 0);
+         fetchPairLong (PAIR_HL, AOP (IC_LEFT (ic)), ic, 0);
          emit2 ("push hl");
          spillPair (PAIR_HL);
          _G.stack.pushed += 2;
          emit2 ("push hl");
          spillPair (PAIR_HL);
          _G.stack.pushed += 2;
@@ -2952,7 +3047,7 @@ genRet (iCode * ic)
       if (IS_GB && size == 4 && requiresHL (AOP (IC_LEFT (ic))))
        {
          fetchPair (PAIR_DE, AOP (IC_LEFT (ic)));
       if (IS_GB && size == 4 && requiresHL (AOP (IC_LEFT (ic))))
        {
          fetchPair (PAIR_DE, AOP (IC_LEFT (ic)));
-         fetchPairLong (PAIR_HL, AOP (IC_LEFT (ic)), 2);
+         fetchPairLong (PAIR_HL, AOP (IC_LEFT (ic)), ic, 2);
        }
       else
        {
        }
       else
        {
@@ -3690,8 +3785,9 @@ genMult (iCode * ic)
   //  wassertl (val > 0, "Multiply must be positive");
   wassertl (val != 1, "Can't multiply by 1");
 
   //  wassertl (val > 0, "Multiply must be positive");
   wassertl (val != 1, "Can't multiply by 1");
 
-  if (IS_Z80) {
+  if (IS_Z80 && isPairInUseNotInRet (PAIR_DE, ic)) {
     _push (PAIR_DE);
     _push (PAIR_DE);
+    _G.stack.pushedDE = TRUE;
   }
 
   if ( AOP_SIZE (IC_LEFT (ic)) == 1 && !SPEC_USIGN (getSpec (operandType ( IC_LEFT (ic)))))
   }
 
   if ( AOP_SIZE (IC_LEFT (ic)) == 1 && !SPEC_USIGN (getSpec (operandType ( IC_LEFT (ic)))))
@@ -3735,9 +3831,10 @@ genMult (iCode * ic)
 
   spillCached();
 
 
   spillCached();
 
-  if (IS_Z80)
+  if (IS_Z80 && _G.stack.pushedDE)
     {
       _pop (PAIR_DE);
     {
       _pop (PAIR_DE);
+      _G.stack.pushedDE = FALSE;
     }
 
   commitPair ( AOP (IC_RESULT (ic)), PAIR_HL);
     }
 
   commitPair ( AOP (IC_RESULT (ic)), PAIR_HL);
@@ -5273,9 +5370,13 @@ shiftL2Left2Result (operand * left, int offl,
       movLeft2Result (left, offl, result, offr, 0);
       movLeft2Result (left, offl + 1, result, offr + 1, 0);
     }
       movLeft2Result (left, offl, result, offr, 0);
       movLeft2Result (left, offl + 1, result, offr + 1, 0);
     }
-  /* PENDING: for now just see if it'll work. */
-  /*if (AOP(result)->type == AOP_REG) { */
-  {
+
+  if (shCount == 1 && getPairId (AOP (result)) == PAIR_HL)
+    {
+      emit2 ("add hl,hl");
+    }
+  else
+    {
     int size = 2;
     int offset = 0;
     symbol *tlbl, *tlbl1;
     int size = 2;
     int offset = 0;
     symbol *tlbl, *tlbl1;
@@ -5897,7 +5998,7 @@ genGenPointerGet (operand * left,
       goto release;
     }
 
       goto release;
     }
 
-  if ( getPairId( AOP (left)) == PAIR_IY)
+  if (getPairId (AOP (left)) == PAIR_IY)
     {
       /* Just do it */
       offset = 0;
     {
       /* Just do it */
       offset = 0;
@@ -5917,14 +6018,12 @@ genGenPointerGet (operand * left,
   /* if this is remateriazable */
   fetchPair (pair, AOP (left));
 
   /* if this is remateriazable */
   fetchPair (pair, AOP (left));
 
-  freeAsmop (left, NULL, ic);
-
   /* if bit then unpack */
   if (IS_BITVAR (retype))
     {
       wassert (0);
     }
   /* if bit then unpack */
   if (IS_BITVAR (retype))
     {
       wassert (0);
     }
-  else if ( getPairId( AOP (result)) == PAIR_HL)
+  else if (getPairId (AOP (result)) == PAIR_HL)
     {
       wassertl (size == 2, "HL must be of size 2");
       emit2 ("ld a,!*hl");
     {
       wassertl (size == 2, "HL must be of size 2");
       emit2 ("ld a,!*hl");
@@ -5932,6 +6031,35 @@ genGenPointerGet (operand * left,
       emit2 ("ld h,!*hl");
       emit2 ("ld l,a");
     }
       emit2 ("ld h,!*hl");
       emit2 ("ld l,a");
     }
+  else if (getPairId (AOP (left)) == PAIR_HL && !isLastUse (ic, left))
+    {
+      size = AOP_SIZE (result);
+      offset = 0;
+
+      while (size--)
+       {
+         /* PENDING: make this better */
+         if (!IS_GB && AOP_TYPE (result) == AOP_REG)
+           {
+             aopPut (AOP (result), "!*hl", offset++);
+           }
+         else
+           {
+             emit2 ("ld a,!*pair", _pairs[pair].name);
+             aopPut (AOP (result), "a", offset++);
+           }
+         if (size)
+           {
+             emit2 ("inc %s", _pairs[pair].name);
+             _G.pairs[pair].offset++;
+           }
+       }
+      /* Fixup HL back down */
+      for (size = AOP_SIZE (result)-1; size; size--)
+        {
+          emit2 ("dec %s", _pairs[pair].name);
+        }
+    }
   else
     {
       size = AOP_SIZE (result);
   else
     {
       size = AOP_SIZE (result);
@@ -5940,7 +6068,8 @@ genGenPointerGet (operand * left,
       while (size--)
        {
          /* PENDING: make this better */
       while (size--)
        {
          /* PENDING: make this better */
-         if (!IS_GB && AOP (result)->type == AOP_REG)
+         if (!IS_GB && 
+              (AOP_TYPE (result) == AOP_REG || AOP_TYPE (result) == AOP_HLREG))
            {
              aopPut (AOP (result), "!*hl", offset++);
            }
            {
              aopPut (AOP (result), "!*hl", offset++);
            }
@@ -5957,6 +6086,8 @@ genGenPointerGet (operand * left,
        }
     }
 
        }
     }
 
+  freeAsmop (left, NULL, ic);
+
 release:
   freeAsmop (result, NULL, ic);
 }
 release:
   freeAsmop (result, NULL, ic);
 }
@@ -6047,6 +6178,37 @@ genGenPointerSet (operand * right,
         }
       goto release;
     }
         }
       goto release;
     }
+  else if (getPairId (AOP (result)) == PAIR_HL && !isLastUse (ic, result))
+    {
+      offset = 0;
+
+      while (size--)
+       {
+         const char *l = aopGet (AOP (right), offset, FALSE);
+         if (isRegOrLit (AOP (right)) && !IS_GB)
+           {
+             emit2 ("ld !*pair,%s", _pairs[PAIR_HL].name, l);
+           }
+         else
+           {
+             _moveA (l);
+             emit2 ("ld !*pair,a", _pairs[PAIR_HL].name);
+           }
+         if (size)
+           {
+             emit2 ("inc %s", _pairs[PAIR_HL].name);
+             _G.pairs[PAIR_HL].offset++;
+           }
+         offset++;
+       }
+
+      /* Fixup HL back down */
+      for (size = AOP_SIZE (right)-1; size; size--)
+        {
+          emit2 ("dec %s", _pairs[PAIR_HL].name);
+        }
+      goto release;
+    }
 
   /* if the operand is already in dptr
      then we do nothing else we move the value to dptr */
 
   /* if the operand is already in dptr
      then we do nothing else we move the value to dptr */
@@ -6242,12 +6404,12 @@ genAssign (iCode * ic)
 
   if (AOP_TYPE (right) == AOP_LIT)
     {
 
   if (AOP_TYPE (right) == AOP_LIT)
     {
-    lit = (unsigned long) floatFromVal (AOP (right)->aopu.aop_lit);
+      lit = (unsigned long) floatFromVal (AOP (right)->aopu.aop_lit);
     }
 
   if (isPair (AOP (result)))
     {
     }
 
   if (isPair (AOP (result)))
     {
-      fetchPair (getPairId (AOP (result)), AOP (right));
+      fetchPairLong (getPairId (AOP (result)), AOP (right), ic, LSB);
     }
   else if ((size > 1) &&
           (AOP_TYPE (result) != AOP_REG) &&
     }
   else if ((size > 1) &&
           (AOP_TYPE (result) != AOP_REG) &&
index 2bba126095efb9e69a256d089f82ed425b4adece..63c89a44e18ccf4087ba132d937af645417b868b 100644 (file)
@@ -31,3 +31,15 @@ replace {
        rlca
         and     a,#0x01
 }
        rlca
         and     a,#0x01
 }
+replace {
+       ld      %3,a
+       ld      l,%1)
+       ld      h,%2)
+       ld      l,(hl)
+       ld      a,%3
+} by {
+       ld      %3,a
+       ld      l,%1)
+       ld      h,%2)
+       ld      l,(hl)
+}
index d865c3a93031f86ea982e4c0951466745d992bac..ee3597876774958cbecbefd1aae2be36fa12f299 100644 (file)
@@ -3,7 +3,7 @@ replace {
 } by {
        ERROR - peephole - caught (hl),(hl)
 }
 } by {
        ERROR - peephole - caught (hl),(hl)
 }
-replace {
+replace restart {
        ld %1,%1
 } by {
         ; Removed redundent load
        ld %1,%1
 } by {
         ; Removed redundent load
@@ -192,3 +192,12 @@ replace {
        cp      a,#%4
        jp      p,%5
 }
        cp      a,#%4
        jp      p,%5
 }
+replace {
+       ld      e,l
+       ld      d,h
+       ld      l,e
+       ld      h,d
+} by {
+       ld      e,l
+       ld      d,h
+}
index e8d338fa9d409da4f53d03dff5114c8457b231af..9d58ded2361927dd8445fdcd0910ed2dd9f21ad8 100644 (file)
@@ -54,6 +54,7 @@ enum
     DISABLE_PACK_ASSIGN = 0,
     DISABLE_PACK_ONE_USE = 0,
     DISABLE_PACK_HL = 0,
     DISABLE_PACK_ASSIGN = 0,
     DISABLE_PACK_ONE_USE = 0,
     DISABLE_PACK_HL = 0,
+    DISABLE_PACK_IY = 0
   };
 
 /* Flags to turn on debugging code.
   };
 
 /* Flags to turn on debugging code.
@@ -67,7 +68,9 @@ enum
     D_HLUSE = 0,
     D_HLUSE2 = 0,
     D_HLUSE2_VERBOSE = 0,
     D_HLUSE = 0,
     D_HLUSE2 = 0,
     D_HLUSE2_VERBOSE = 0,
-    D_FILL_GAPS = 0
+    D_FILL_GAPS = 0,
+    D_PACK_IY = 0,
+    D_PACK_HLUSE3 = 0
   };
 
 #if 1
   };
 
 #if 1
@@ -2232,10 +2235,9 @@ packRegsForHLUse3 (iCode * lic, operand * op, eBBlock * ebp)
   iCode *ic, *dic;
   bool isFirst = TRUE;
 
   iCode *ic, *dic;
   bool isFirst = TRUE;
 
-#if 0
-  printf("Checking:\n");
-  piCode(lic, NULL);
-#endif
+  D (D_PACK_HLUSE3, ("Checking HL on %p lic key %u first def %u line %u:\n", OP_SYMBOL(op), lic->key, bitVectFirstBit(OP_DEFS(op)), lic->lineno));
+  if (D_PACK_HLUSE3)
+    piCode(lic, NULL);
 
   if ( OP_SYMBOL(op)->accuse)
     {
 
   if ( OP_SYMBOL(op)->accuse)
     {
@@ -2282,12 +2284,12 @@ packRegsForHLUse3 (iCode * lic, operand * op, eBBlock * ebp)
   dic = ic = hTabFirstItemWK(iCodeSeqhTab,OP_SYMBOL(op)->liveFrom);
 
   for (; ic && ic->seq <= OP_SYMBOL(op)->liveTo;
   dic = ic = hTabFirstItemWK(iCodeSeqhTab,OP_SYMBOL(op)->liveFrom);
 
   for (; ic && ic->seq <= OP_SYMBOL(op)->liveTo;
-       ic = hTabNextItem(iCodeSeqhTab,&key)) 
+       ic = hTabNextItem(iCodeSeqhTab, &key)) 
     {
     {
-#if 0
-      piCode(ic, NULL);
-      printf("(op: %u)\n", ic->op);
-#endif
+      if (D_PACK_HLUSE3)
+        piCode(ic, NULL);
+      D (D_PACK_HLUSE3, ("(On %p: op: %u next: %p)\n", ic, ic->op, ic->next));
+
       if (isFirst)
         {
           isFirst = FALSE;
       if (isFirst)
         {
           isFirst = FALSE;
@@ -2295,6 +2297,8 @@ packRegsForHLUse3 (iCode * lic, operand * op, eBBlock * ebp)
             continue;
           if (POINTER_GET (ic))
             continue;
             continue;
           if (POINTER_GET (ic))
             continue;
+          if (ic->op == '=' && !POINTER_SET(ic))
+            continue;
         }
 
       if (IC_RESULT(ic) && IS_SYMOP(IC_RESULT(ic))
         }
 
       if (IC_RESULT(ic) && IS_SYMOP(IC_RESULT(ic))
@@ -2330,13 +2334,25 @@ packRegsForHLUse3 (iCode * lic, operand * op, eBBlock * ebp)
       if (ic->op == CALL && isOperandEqual (op, IC_RESULT (ic)))
         continue;
 
       if (ic->op == CALL && isOperandEqual (op, IC_RESULT (ic)))
         continue;
 
+      if (ic->op == LEFT_OP && isOperandLiteral (IC_RIGHT (ic)))
+        continue;
+
       if ((ic->op == '=' && !POINTER_SET(ic)) ||
           ic->op == UNARYMINUS ||
           ic->op == '+' ||
           ic->op == '-' ||
       if ((ic->op == '=' && !POINTER_SET(ic)) ||
           ic->op == UNARYMINUS ||
           ic->op == '+' ||
           ic->op == '-' ||
+          ic->op == '>' ||
+          ic->op == '<' ||
+          ic->op == EQ_OP ||
           0)
         continue;
 
           0)
         continue;
 
+      if (ic->op == '*' && isOperandEqual (op, IC_LEFT (ic)))
+        continue;
+
+      if (POINTER_SET (ic) && isOperandEqual (op, IC_RESULT (ic)))
+        continue;
+
       if (POINTER_GET (ic) && isOperandEqual (op, IC_LEFT (ic)))
         continue;
 
       if (POINTER_GET (ic) && isOperandEqual (op, IC_LEFT (ic)))
         continue;
 
@@ -2351,11 +2367,9 @@ packRegsForHLUse3 (iCode * lic, operand * op, eBBlock * ebp)
       return NULL;
     }
 
       return NULL;
     }
 
-#if 0
-  printf("Succeeded!\n");
-#endif
-  OP_SYMBOL (op)->accuse = ACCUSE_SCRATCH;
+  D (D_PACK_HLUSE3, ("Succeeded!\n"))
 
 
+  OP_SYMBOL (op)->accuse = ACCUSE_SCRATCH;
   return dic;
 }
 
   return dic;
 }
 
@@ -2367,10 +2381,9 @@ packRegsForIYUse (iCode * lic, operand * op, eBBlock * ebp)
   iCode *ic, *dic;
   bitVect *uses;
 
   iCode *ic, *dic;
   bitVect *uses;
 
-#if 0
-  printf("Checking IY on %p lic key %u first def %u:\n", OP_SYMBOL(op), lic->key, bitVectFirstBit(OP_DEFS(op)));
-  piCode(lic, NULL);
-#endif
+  D (D_PACK_IY, ("Checking IY on %p lic key %u first def %u line %u:\n", OP_SYMBOL(op), lic->key, bitVectFirstBit(OP_DEFS(op)), lic->lineno));
+  if (D_PACK_IY)
+    piCode(lic, NULL);
 
   if ( OP_SYMBOL(op)->accuse)
     {
 
   if ( OP_SYMBOL(op)->accuse)
     {
@@ -2423,10 +2436,8 @@ packRegsForIYUse (iCode * lic, operand * op, eBBlock * ebp)
   for (; ic && ic->seq <= OP_SYMBOL(op)->liveTo;
        ic = hTabNextItem(iCodeSeqhTab,&key)) 
     {
   for (; ic && ic->seq <= OP_SYMBOL(op)->liveTo;
        ic = hTabNextItem(iCodeSeqhTab,&key)) 
     {
-#if 0
-      piCode(ic, NULL);
-      printf("(op: %u uses %u)\n", ic->op, bitVectBitValue(uses, ic->key));
-#endif
+      if (D_PACK_IY)
+        piCode(ic, NULL);
 
       if (ic->op == PCALL || 
           ic->op == CALL ||
 
       if (ic->op == PCALL || 
           ic->op == CALL ||
@@ -2437,13 +2448,32 @@ packRegsForIYUse (iCode * lic, operand * op, eBBlock * ebp)
       if (SKIP_IC2(ic))
         continue;
 
       if (SKIP_IC2(ic))
         continue;
 
+      /* Be pessamistic. */
+      if (ic->op == IFX)
+        return NULL;
+
+      D (D_PACK_IY, ("  op: %u uses %u result: %d left: %d right: %d\n", ic->op, bitVectBitValue(uses, ic->key),
+                     IC_RESULT(ic) && IS_SYMOP(IC_RESULT(ic)) ? isOperandInDirSpace(IC_RESULT(ic)) : -1,
+                     IC_LEFT(ic) && IS_SYMOP(IC_LEFT(ic)) ? isOperandInDirSpace(IC_LEFT(ic)) : -1,
+                     IC_RIGHT(ic) && IS_SYMOP(IC_RIGHT(ic)) ? isOperandInDirSpace(IC_RIGHT(ic)) : -1
+                     ));
+
+      if (IC_RESULT(ic) && IS_SYMOP(IC_RESULT(ic)) && 
+          isOperandInDirSpace(IC_RESULT(ic)))
+        return NULL;
+      
+      if (IC_RIGHT(ic) && IS_SYMOP(IC_RIGHT(ic)) && 
+          isOperandInDirSpace(IC_RIGHT(ic)))
+        return NULL;
+      
+      if (IC_LEFT(ic) && IS_SYMOP(IC_LEFT(ic)) && 
+          isOperandInDirSpace(IC_LEFT(ic)))
+        return NULL;
+
       /* Only certain rules will work against IY.  Check if this iCode uses
          this symbol. */
       if (bitVectBitValue(uses, ic->key) != 0)
         {
       /* Only certain rules will work against IY.  Check if this iCode uses
          this symbol. */
       if (bitVectBitValue(uses, ic->key) != 0)
         {
-          if (ic->op == IFX)
-            return NULL;
-
           if (ic->op == '=' &&
               isOperandEqual(IC_RESULT(ic), op))
             continue;
           if (ic->op == '=' &&
               isOperandEqual(IC_RESULT(ic), op))
             continue;
@@ -2470,23 +2500,8 @@ packRegsForIYUse (iCode * lic, operand * op, eBBlock * ebp)
         }
       else
         {
         }
       else
         {
-          if (ic->op == IFX)
-            continue;
-
           /* This iCode doesn't use the sym.  See if this iCode preserves IY.
            */
           /* This iCode doesn't use the sym.  See if this iCode preserves IY.
            */
-          if (IC_RESULT(ic) && IS_SYMOP(IC_RESULT(ic)) && 
-              isOperandInDirSpace(IC_RESULT(ic)))
-            return NULL;
-          
-          if (IC_RIGHT(ic) && IS_SYMOP(IC_RIGHT(ic)) && 
-              isOperandInFarSpace(IC_RIGHT(ic)))
-            return NULL;
-
-          if (IC_LEFT(ic) && IS_SYMOP(IC_LEFT(ic)) && 
-              isOperandInFarSpace(IC_LEFT(ic)))
-            return NULL;
-          
           continue;
         }
 
           continue;
         }
 
@@ -2494,11 +2509,9 @@ packRegsForIYUse (iCode * lic, operand * op, eBBlock * ebp)
       return NULL;
     }
 
       return NULL;
     }
 
-#if 0
-  printf("Succeeded IY!\n");
-#endif
-  OP_SYMBOL (op)->accuse = ACCUSE_IY;
+  D (D_PACK_IY, ("Succeeded IY!\n"));
 
 
+  OP_SYMBOL (op)->accuse = ACCUSE_IY;
   return dic;
 }
 
   return dic;
 }
 
@@ -2647,11 +2660,14 @@ packRegsForAccUse2 (iCode * ic)
   iCode *uic;
 
   D (D_ACCUSE2, ("packRegsForAccUse2: running on ic %p line %u\n", ic, ic->lineno));
   iCode *uic;
 
   D (D_ACCUSE2, ("packRegsForAccUse2: running on ic %p line %u\n", ic, ic->lineno));
+  if (D_ACCUSE2)
+    piCode (ic, NULL);
 
   /* Filter out all but those 'good' commands */
   if (
        !POINTER_GET (ic) &&
        ic->op != '+' &&
 
   /* Filter out all but those 'good' commands */
   if (
        !POINTER_GET (ic) &&
        ic->op != '+' &&
+       ic->op != '-' &&
        !IS_BITWISE_OP (ic) &&
        ic->op != '=' &&
        ic->op != EQ_OP &&
        !IS_BITWISE_OP (ic) &&
        ic->op != '=' &&
        ic->op != EQ_OP &&
@@ -2902,7 +2918,7 @@ packRegisters (eBBlock * ebp)
             packRegsForHLUse3 (ic, IC_RESULT (ic), ebp);
        }
 
             packRegsForHLUse3 (ic, IC_RESULT (ic), ebp);
        }
 
-      if (!DISABLE_PACK_HL && IS_ITEMP (IC_RESULT (ic)) && IS_Z80)
+      if (!DISABLE_PACK_IY && IS_ITEMP (IC_RESULT (ic)) && IS_Z80)
        {
           packRegsForIYUse (ic, IC_RESULT (ic), ebp);
        }
        {
           packRegsForIYUse (ic, IC_RESULT (ic), ebp);
        }