* src/pic16/gen.c: applied patch
authorborutr <borutr@4a8a32a2-be11-0410-ad9d-d568d2c75423>
Sat, 23 Aug 2008 11:44:54 +0000 (11:44 +0000)
committerborutr <borutr@4a8a32a2-be11-0410-ad9d-d568d2c75423>
Sat, 23 Aug 2008 11:44:54 +0000 (11:44 +0000)
  2048464: PIC16: fix genUminus - addresses not.c regression test
  thanks Mauro Giachero

git-svn-id: https://sdcc.svn.sourceforge.net/svnroot/sdcc/trunk/sdcc@5218 4a8a32a2-be11-0410-ad9d-d568d2c75423

ChangeLog
src/pic16/gen.c

index 2218b51ee5bc60e2a917e4d2b732e1225a4abde5..8aea57389515cd165e8c5566b7ebecef0c129614 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,7 +1,13 @@
+2008-08-23 Borut Razem <borut.razem AT siol.net>
+
+       * src/pic16/gen.c: applied patch
+         2048464: PIC16: fix genUminus - addresses not.c regression test
+         thanks Mauro Giachero
+
 2008-08-22 Borut Razem <borut.razem AT siol.net>
 
        * device/lib/pic16/configure, device/lib/pic16/configure.ac,
-          src/pic16/main.c: allow spaces in gpasm and gplink paths
+         src/pic16/main.c: allow spaces in gpasm and gplink paths
 
 2008-08-15 Philipp Klaus Krause <pkk AT spth.de>
 
index 46f7b482c65561e005473421f457efe59a3f00d1..c298845c2a788c79ed0184921efccba7c7689d3f 100644 (file)
@@ -2296,7 +2296,7 @@ static void genUminusFloat(operand *op,operand *result)
 /*-----------------------------------------------------------------*/
 static void genUminus (iCode *ic)
 {
-  int size, i;
+  int lsize, rsize, i;
   sym_link *optype, *rtype;
   symbol *label;
   int needLabel=0;
@@ -2331,40 +2331,65 @@ static void genUminus (iCode *ic)
     }
 
     /* otherwise subtract from zero by taking the 2's complement */
-    size = AOP_SIZE(IC_LEFT(ic));
-    assert( size == AOP_SIZE(IC_RESULT(ic)) );
+    lsize = AOP_SIZE(IC_LEFT(ic));
+    rsize = AOP_SIZE(IC_RESULT(ic));
     label = newiTempLabel ( NULL );
 
     if (pic16_sameRegs (AOP(IC_LEFT(ic)), AOP(IC_RESULT(ic)))) {
-      for (i=size-1; i > 0; i--) {
-        pic16_emitpcode (POC_COMF, pic16_popGet (AOP(IC_LEFT(ic)), i));
+      /* If the result is longer than the operand,
+         store sign extension (0x00 or 0xff) in W */
+      if (rsize > lsize) {
+        pic16_emitpcode (POC_MOVLW, pic16_popGetLit(0x00));
+        pic16_emitpcode (POC_BTFSS, pic16_popCopyGPR2Bit(pic16_popGet(AOP(IC_LEFT(ic)), lsize-1), 7));
+        pic16_emitpcode (POC_MOVLW, pic16_popGetLit(0xFF));
+      }
+      for (i = rsize - 1; i > 0; --i) {
+        if (i > lsize - 1) {
+          pic16_emitpcode (POC_MOVWF, pic16_popGet (AOP(IC_RESULT(ic)), i));
+        } else {
+          pic16_emitpcode (POC_COMF, pic16_popGet (AOP(IC_RESULT(ic)), i));
+        } // if
       } // for
-      pic16_emitpcode (POC_NEGF, pic16_popGet (AOP(IC_LEFT(ic)), 0));
-      for (i=1; i < size; i++) {
-        if (i == size - 1) { emitSKPNZ; } else { pic16_emitpcode (POC_BNZ, pic16_popGetLabel (label->key)); needLabel++; }
-        pic16_emitpcode (POC_INCF, pic16_popGet (AOP(IC_LEFT(ic)), i));
+      pic16_emitpcode (POC_NEGF, pic16_popGet (AOP(IC_RESULT(ic)), 0));
+      for (i = 1; i < rsize; ++i) {
+        if (i == rsize - 1) {
+          emitSKPNZ;
+        } else {
+          pic16_emitpcode (POC_BNZ, pic16_popGetLabel (label->key)); needLabel++;
+        }
+        pic16_emitpcode (POC_INCF, pic16_popGet (AOP(IC_RESULT(ic)), i));
       } // for
     } else {
-      for (i=size-1; i >= 0; i--) {
+      for (i = min(rsize, lsize) - 1; i >= 0; i--) {
         pic16_emitpcode (POC_COMFW, pic16_popGet (AOP(IC_LEFT(ic)), i));
         pic16_emitpcode (POC_MOVWF, pic16_popGet (AOP(IC_RESULT(ic)), i));
       } // for
-      if (size > 1) {
-        for (i=0; i < size-2; i++) {
+      /* Sign extend if the result is longer than the operand */
+      if (rsize > lsize) {
+        pic16_emitpcode (POC_MOVLW, pic16_popGetLit(0x00));
+        pic16_emitpcode (POC_BTFSC, pic16_popCopyGPR2Bit(pic16_popGet(AOP(IC_RESULT(ic)), lsize - 1), 7));
+        pic16_emitpcode (POC_MOVLW, pic16_popGetLit(0xFF));
+        for (i = rsize - 1; i > lsize - 1; --i) {
+          pic16_emitpcode (POC_MOVWF, pic16_popGet (AOP(IC_RESULT(ic)), i));
+        } // for
+      } // if
+      if (rsize > 1) {
+        for (i = 0; i < rsize - 2; i++) {
           pic16_emitpcode (POC_INCF, pic16_popGet (AOP(IC_RESULT(ic)),i));
-          pic16_emitpcode (POC_BNZ, pic16_popGetLabel (label->key)); needLabel++;
+          pic16_emitpcode (POC_BNZ, pic16_popGetLabel (label->key));
+          needLabel++;
         } // for
-        pic16_emitpcode (POC_INFSNZ, pic16_popGet (AOP(IC_RESULT(ic)), size-2));
+        pic16_emitpcode (POC_INFSNZ, pic16_popGet (AOP(IC_RESULT(ic)), rsize - 2));
       } // if
-      pic16_emitpcode (POC_INCF, pic16_popGet(AOP(IC_RESULT(ic)), size-1));
+      pic16_emitpcode (POC_INCF, pic16_popGet(AOP(IC_RESULT(ic)), rsize - 1));
     }
     if (needLabel)
       pic16_emitpLabel (label->key);
 
 release:
     /* release the aops */
-    pic16_freeAsmop(IC_LEFT(ic),NULL,ic,(RESULTONSTACK(ic) ? 0 : 1));
-    pic16_freeAsmop(IC_RESULT(ic),NULL,ic,TRUE);
+    pic16_freeAsmop(IC_LEFT(ic), NULL, ic, (RESULTONSTACK(ic) ? 0 : 1));
+    pic16_freeAsmop(IC_RESULT(ic), NULL, ic, TRUE);
 }
 
 void pic16_loadFromReturn(operand *op, int offset, pCodeOp *src)
@@ -6142,10 +6167,10 @@ static void genXor (iCode *ic, iCode *ifx)
               if  (t == 0x00L)
                 continue;
               else
-               {
-                 pic16_emitpcode(POC_MOVLW, pic16_popGetLit(t));
-                 pic16_emitpcode(POC_XORWF, pic16_popGet(AOP(left), offset));
-               }
+                {
+                  pic16_emitpcode(POC_MOVLW, pic16_popGetLit(t));
+                  pic16_emitpcode(POC_XORWF, pic16_popGet(AOP(left), offset));
+                }
             }
           else
             {
@@ -6607,9 +6632,9 @@ static void AccRsh (int shCount, int andmask)
                 case 7 :
                         pic16_emitpcode(POC_RLNCFW,pic16_popCopyReg(&pic16_pc_wreg));
                         break;
-               default:
-                       // Rotating by 8 is a NOP.
-                       break;
+                default:
+                        // Rotating by 8 is a NOP.
+                        break;
         }
 
         if (andmask)
@@ -7664,7 +7689,7 @@ static void genRightShiftLiteral (operand *left,
     } // for
   } else if (shCount >= (lsize * 8)) {
     if (sign) {
-      /* 
+      /*
        * Do NOT use
        *    CLRF    result
        *    BTFSC   left, 7