2004-01-13 Vangelis Rokas <vrokas@otenet.gr>
[fw/sdcc] / src / pic16 / genarith.c
1 /*-------------------------------------------------------------------------
2
3  genarith.c - source file for code generation - arithmetic 
4   
5   Written By -  Sandeep Dutta . sandeep.dutta@usa.net (1998)
6          and -  Jean-Louis VERN.jlvern@writeme.com (1999)
7   Bug Fixes  -  Wojciech Stryjewski  wstryj1@tiger.lsu.edu (1999 v2.1.9a)
8   PIC port   -  Scott Dattalo scott@dattalo.com (2000)
9   PIC16 port   -  Martin Dubuc m.dubuc@rogers.com (2002)
10   
11   This program is free software; you can redistribute it and/or modify it
12   under the terms of the GNU General Public License as published by the
13   Free Software Foundation; either version 2, or (at your option) any
14   later version.
15   
16   This program is distributed in the hope that it will be useful,
17   but WITHOUT ANY WARRANTY; without even the implied warranty of
18   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19   GNU General Public License for more details.
20   
21   You should have received a copy of the GNU General Public License
22   along with this program; if not, write to the Free Software
23   Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
24   
25   In other words, you are welcome to use, share and improve this program.
26   You are forbidden to forbid anyone else to use, share and improve
27   what you give them.   Help stamp out software-hoarding!
28   
29   Notes:
30   000123 mlh    Moved aopLiteral to SDCCglue.c to help the split
31                 Made everything static
32 -------------------------------------------------------------------------*/
33
34 #include <stdio.h>
35 #include <stdlib.h>
36 #include <string.h>
37 #include <ctype.h>
38 #include "SDCCglobl.h"
39 #include "newalloc.h"
40
41 #if defined(_MSC_VER) && (_MSC_VER < 1300)
42 #define __FUNCTION__            __FILE__
43 #endif
44
45 #include "common.h"
46 #include "SDCCpeeph.h"
47 #include "ralloc.h"
48 #include "pcode.h"
49 #include "gen.h"
50
51 #if 1
52 #define pic16_emitcode  DEBUGpic16_emitcode
53 #endif
54
55 #define BYTEofLONG(l,b) ( (l>> (b<<3)) & 0xff)
56 void DEBUGpic16_pic16_AopType(int line_no, operand *left, operand *right, operand *result);
57
58 const char *pic16_AopType(short type)
59 {
60   switch(type) {
61   case AOP_LIT:
62     return "AOP_LIT";
63     break;
64   case AOP_REG:
65     return "AOP_REG";
66     break;
67   case AOP_DIR:
68     return "AOP_DIR";
69     break;
70   case AOP_DPTR:
71     return "AOP_DPTR";
72     break;
73   case AOP_DPTR2:
74     return "AOP_DPTR2";
75     break;
76   case AOP_R0:
77     return "AOP_R0";
78     break;
79   case AOP_R1:
80     return "AOP_R1";
81     break;
82   case AOP_STK:
83     return "AOP_STK";
84     break;
85   case AOP_IMMD:
86     return "AOP_IMMD";
87     break;
88   case AOP_STR:
89     return "AOP_STR";
90     break;
91   case AOP_CRY:
92     return "AOP_CRY";
93     break;
94   case AOP_ACC:
95     return "AOP_ACC";
96     break;
97   case AOP_PCODE:
98     return "AOP_PCODE";
99     break;
100   }
101
102   return "BAD TYPE";
103 }
104
105 const char *pic16_pCodeOpType(  pCodeOp *pcop)
106 {
107
108   if(pcop) {
109
110     switch(pcop->type) {
111
112     case  PO_NONE:
113       return "PO_NONE";
114     case  PO_W:
115       return  "PO_W";
116     case  PO_WREG:
117       return  "PO_WREG";
118     case  PO_STATUS:
119       return  "PO_STATUS";
120     case  PO_BSR:
121       return  "PO_BSR";
122     case  PO_FSR0:
123       return  "PO_FSR0";
124     case  PO_INDF0:
125       return  "PO_INDF0";
126     case  PO_INTCON:
127       return  "PO_INTCON";
128     case  PO_GPR_REGISTER:
129       return  "PO_GPR_REGISTER";
130     case  PO_GPR_BIT:
131       return  "PO_GPR_BIT";
132     case  PO_GPR_TEMP:
133       return  "PO_GPR_TEMP";
134     case  PO_SFR_REGISTER:
135       return  "PO_SFR_REGISTER";
136     case  PO_PCL:
137       return  "PO_PCL";
138     case  PO_PCLATH:
139       return  "PO_PCLATH";
140     case PO_LITERAL:
141       return  "PO_LITERAL";
142     case PO_REL_ADDR:
143       return "PO_REL_ADDR";
144     case  PO_IMMEDIATE:
145       return  "PO_IMMEDIATE";
146     case  PO_DIR:
147       return  "PO_DIR";
148     case  PO_CRY:
149       return  "PO_CRY";
150     case  PO_BIT:
151       return  "PO_BIT";
152     case  PO_STR:
153       return  "PO_STR";
154     case  PO_LABEL:
155       return  "PO_LABEL";
156     case  PO_WILD:
157       return  "PO_WILD";
158     }
159   }
160
161   return "BAD PO_TYPE";
162 }
163
164 /*-----------------------------------------------------------------*/
165 /* pic16_genPlusIncr :- does addition with increment if possible         */
166 /*-----------------------------------------------------------------*/
167 bool pic16_genPlusIncr (iCode *ic)
168 {
169     unsigned int icount ;
170     unsigned int size = pic16_getDataSize(IC_RESULT(ic));
171
172     DEBUGpic16_emitcode ("; ***","%s  %d",__FUNCTION__,__LINE__);
173     DEBUGpic16_emitcode ("; ","result %s, left %s, right %s",
174                          pic16_AopType(AOP_TYPE(IC_RESULT(ic))),
175                          pic16_AopType(AOP_TYPE(IC_LEFT(ic))),
176                          pic16_AopType(AOP_TYPE(IC_RIGHT(ic))));
177
178     /* will try to generate an increment */
179     /* if the right side is not a literal 
180        we cannot */
181     if (AOP_TYPE(IC_RIGHT(ic)) != AOP_LIT)
182         return FALSE ;
183     
184     DEBUGpic16_emitcode ("; ","%s  %d",__FUNCTION__,__LINE__);
185     /* if the literal value of the right hand side
186        is greater than 2 then it is faster to add */
187     if ((icount = (unsigned int) floatFromVal (AOP(IC_RIGHT(ic))->aopu.aop_lit)) > 2)
188         return FALSE ;
189     
190     /* if increment 16 bits in register */
191     if (pic16_sameRegs(AOP(IC_LEFT(ic)), AOP(IC_RESULT(ic))) &&
192         (icount == 1)) {
193
194       int offset = MSB16;
195
196       pic16_emitpcode(POC_INCF, pic16_popGet(AOP(IC_RESULT(ic)),LSB));
197       //pic16_emitcode("incf","%s,f",pic16_aopGet(AOP(IC_RESULT(ic)),LSB,FALSE,FALSE));
198
199       while(--size) {
200         emitSKPNZ;
201         pic16_emitpcode(POC_INCF, pic16_popGet(AOP(IC_RESULT(ic)),offset++));
202         //pic16_emitcode(" incf","%s,f",pic16_aopGet(AOP(IC_RESULT(ic)),offset++,FALSE,FALSE));
203       }
204
205       return TRUE;
206     }
207     
208     DEBUGpic16_emitcode ("; ","%s  %d",__FUNCTION__,__LINE__);
209     /* if left is in accumulator  - probably a bit operation*/                          // VR - why this is a bit operation?!
210     if( strcmp(pic16_aopGet(AOP(IC_LEFT(ic)),0,FALSE,FALSE),"a")  &&
211         (AOP_TYPE(IC_RESULT(ic)) == AOP_CRY) ) {
212       
213       pic16_emitpcode(POC_BCF, pic16_popGet(AOP(IC_RESULT(ic)),0));
214       pic16_emitcode("bcf","(%s >> 3), (%s & 7)",
215                AOP(IC_RESULT(ic))->aopu.aop_dir,
216                AOP(IC_RESULT(ic))->aopu.aop_dir);
217       if(icount)
218         pic16_emitpcode(POC_XORLW,pic16_popGetLit(1));
219       //pic16_emitcode("xorlw","1");
220       else
221         pic16_emitpcode(POC_ANDLW,pic16_popGetLit(1));
222       //pic16_emitcode("andlw","1");
223
224       emitSKPZ;
225       pic16_emitpcode(POC_BSF, pic16_popGet(AOP(IC_RESULT(ic)),0));
226       pic16_emitcode("bsf","(%s >> 3), (%s & 7)",
227                AOP(IC_RESULT(ic))->aopu.aop_dir,
228                AOP(IC_RESULT(ic))->aopu.aop_dir);
229
230       return TRUE;
231     }
232
233
234     /* if the sizes are greater than 1 then we cannot */
235     if (AOP_SIZE(IC_RESULT(ic)) > 1 ||
236         AOP_SIZE(IC_LEFT(ic)) > 1   )
237         return FALSE ;
238     
239     /* If we are incrementing the same register by two: */
240
241     if (pic16_sameRegs(AOP(IC_LEFT(ic)), AOP(IC_RESULT(ic))) ) {
242         
243       while (icount--) 
244         pic16_emitpcode(POC_INCF, pic16_popGet(AOP(IC_RESULT(ic)),0));
245       //pic16_emitcode("incf","%s,f",pic16_aopGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE));
246         
247       return TRUE ;
248     }
249     
250     DEBUGpic16_emitcode ("; ","couldn't increment ");
251
252     return FALSE ;
253 }
254
255 /*-----------------------------------------------------------------*/
256 /* pic16_outBitAcc - output a bit in acc                                 */
257 /*-----------------------------------------------------------------*/
258 void pic16_outBitAcc(operand *result)
259 {
260     symbol *tlbl = newiTempLabel(NULL);
261     /* if the result is a bit */
262     DEBUGpic16_emitcode ("; ***","%s  %d",__FUNCTION__,__LINE__);
263
264     if (AOP_TYPE(result) == AOP_CRY){
265         pic16_aopPut(AOP(result),"a",0);
266     }
267     else {
268         pic16_emitcode("jz","%05d_DS_",tlbl->key+100);
269         pic16_emitcode("mov","a,#01");
270         pic16_emitcode("","%05d_DS_:",tlbl->key+100);
271         pic16_outAcc(result);
272     }
273 }
274
275 /*-----------------------------------------------------------------*/
276 /* pic16_genPlusBits - generates code for addition of two bits           */
277 /*-----------------------------------------------------------------*/
278 void pic16_genPlusBits (iCode *ic)
279 {
280
281   DEBUGpic16_emitcode ("; ***","%s  %d",__FUNCTION__,__LINE__);
282
283   DEBUGpic16_emitcode ("; ","result %s, left %s, right %s",
284                        pic16_AopType(AOP_TYPE(IC_RESULT(ic))),
285                        pic16_AopType(AOP_TYPE(IC_LEFT(ic))),
286                        pic16_AopType(AOP_TYPE(IC_RIGHT(ic))));
287   /*
288     The following block of code will add two bits. 
289     Note that it'll even work if the destination is
290     the carry (C in the status register).
291     It won't work if the 'Z' bit is a source or destination.
292   */
293
294   /* If the result is stored in the accumulator (w) */
295   //if(strcmp(pic16_aopGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE),"a") == 0 ) {
296   switch(AOP_TYPE(IC_RESULT(ic))) {
297   case AOP_ACC:
298     pic16_emitpcode(POC_CLRF, pic16_popCopyReg(&pic16_pc_wreg));
299     pic16_emitpcode(POC_BTFSC, pic16_popGet(AOP(IC_RIGHT(ic)),0));
300     pic16_emitpcode(POC_XORLW, pic16_popGetLit(1));
301     pic16_emitpcode(POC_BTFSC, pic16_popGet(AOP(IC_LEFT(ic)),0));
302     pic16_emitpcode(POC_XORLW, pic16_popGetLit(1));
303
304     pic16_emitcode("clrw","");
305     pic16_emitcode("btfsc","(%s >> 3), (%s & 7)",
306                    AOP(IC_RIGHT(ic))->aopu.aop_dir,
307                    AOP(IC_RIGHT(ic))->aopu.aop_dir);
308     pic16_emitcode("xorlw","1");
309     pic16_emitcode("btfsc","(%s >> 3), (%s & 7)",
310                    AOP(IC_LEFT(ic))->aopu.aop_dir,
311                    AOP(IC_LEFT(ic))->aopu.aop_dir);
312     pic16_emitcode("xorlw","1");
313     break;
314   case AOP_REG:
315     pic16_emitpcode(POC_MOVLW, pic16_popGetLit(0));
316     pic16_emitpcode(POC_BTFSC, pic16_popGet(AOP(IC_RIGHT(ic)),0));
317     pic16_emitpcode(POC_XORLW, pic16_popGetLit(1));
318     pic16_emitpcode(POC_BTFSC, pic16_popGet(AOP(IC_LEFT(ic)),0));
319     pic16_emitpcode(POC_XORLW, pic16_popGetLit(1));
320     pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(IC_RESULT(ic)),0));
321     break;
322   default:
323     pic16_emitpcode(POC_MOVLW, pic16_popGet(AOP(IC_RESULT(ic)),0));
324     pic16_emitpcode(POC_BCF,   pic16_popGet(AOP(IC_RESULT(ic)),0));
325     pic16_emitpcode(POC_BTFSC, pic16_popGet(AOP(IC_RIGHT(ic)),0));
326     pic16_emitpcode(POC_XORWF, pic16_popGet(AOP(IC_RESULT(ic)),0));
327     pic16_emitpcode(POC_BTFSC, pic16_popGet(AOP(IC_LEFT(ic)),0));
328     pic16_emitpcode(POC_XORWF, pic16_popGet(AOP(IC_RESULT(ic)),0));
329
330     pic16_emitcode("movlw","(1 << (%s & 7))",
331                    AOP(IC_RESULT(ic))->aopu.aop_dir,
332                    AOP(IC_RESULT(ic))->aopu.aop_dir);
333     pic16_emitcode("bcf","(%s >> 3), (%s & 7)",
334                    AOP(IC_RESULT(ic))->aopu.aop_dir,
335                    AOP(IC_RESULT(ic))->aopu.aop_dir);
336     pic16_emitcode("btfsc","(%s >> 3), (%s & 7)",
337                    AOP(IC_RIGHT(ic))->aopu.aop_dir,
338                    AOP(IC_RIGHT(ic))->aopu.aop_dir);
339     pic16_emitcode("xorwf","(%s >>3),f",
340                    AOP(IC_RESULT(ic))->aopu.aop_dir);
341     pic16_emitcode("btfsc","(%s >> 3), (%s & 7)",
342                    AOP(IC_LEFT(ic))->aopu.aop_dir,
343                    AOP(IC_LEFT(ic))->aopu.aop_dir);
344     pic16_emitcode("xorwf","(%s>>3),f",
345                    AOP(IC_RESULT(ic))->aopu.aop_dir);
346     break;
347   }
348
349 }
350
351 #if 0
352 /* This is the original version of this code.
353  *
354  * This is being kept around for reference, 
355  * because I am not entirely sure I got it right...
356  */
357 static void adjustArithmeticResult(iCode *ic)
358 {
359     if (AOP_SIZE(IC_RESULT(ic)) == 3 && 
360         AOP_SIZE(IC_LEFT(ic)) == 3   &&
361         !pic16_sameRegs(AOP(IC_RESULT(ic)),AOP(IC_LEFT(ic))))
362         pic16_aopPut(AOP(IC_RESULT(ic)),
363                pic16_aopGet(AOP(IC_LEFT(ic)),2,FALSE,FALSE),
364                2);
365
366     if (AOP_SIZE(IC_RESULT(ic)) == 3 && 
367         AOP_SIZE(IC_RIGHT(ic)) == 3   &&
368         !pic16_sameRegs(AOP(IC_RESULT(ic)),AOP(IC_RIGHT(ic))))
369         pic16_aopPut(AOP(IC_RESULT(ic)),
370                pic16_aopGet(AOP(IC_RIGHT(ic)),2,FALSE,FALSE),
371                2);
372     
373     if (AOP_SIZE(IC_RESULT(ic)) == 3 &&
374         AOP_SIZE(IC_LEFT(ic)) < 3    &&
375         AOP_SIZE(IC_RIGHT(ic)) < 3   &&
376         !pic16_sameRegs(AOP(IC_RESULT(ic)),AOP(IC_LEFT(ic))) &&
377         !pic16_sameRegs(AOP(IC_RESULT(ic)),AOP(IC_RIGHT(ic)))) {
378         char buffer[5];
379         sprintf(buffer,"#%d",pointerCode(getSpec(operandType(IC_LEFT(ic)))));
380         pic16_aopPut(AOP(IC_RESULT(ic)),buffer,2);
381     }
382 }
383 //#else
384 /* This is the pure and virtuous version of this code.
385  * I'm pretty certain it's right, but not enough to toss the old 
386  * code just yet...
387  */
388 static void adjustArithmeticResult(iCode *ic)
389 {
390     if (opIsGptr(IC_RESULT(ic)) &&
391         opIsGptr(IC_LEFT(ic))   &&
392         !pic16_sameRegs(AOP(IC_RESULT(ic)),AOP(IC_LEFT(ic))))
393     {
394         pic16_aopPut(AOP(IC_RESULT(ic)),
395                pic16_aopGet(AOP(IC_LEFT(ic)), GPTRSIZE - 1,FALSE,FALSE),
396                GPTRSIZE - 1);
397     }
398
399     if (opIsGptr(IC_RESULT(ic)) &&
400         opIsGptr(IC_RIGHT(ic))   &&
401         !pic16_sameRegs(AOP(IC_RESULT(ic)),AOP(IC_RIGHT(ic))))
402     {
403         pic16_aopPut(AOP(IC_RESULT(ic)),
404                pic16_aopGet(AOP(IC_RIGHT(ic)),GPTRSIZE - 1,FALSE,FALSE),
405                GPTRSIZE - 1);
406     }
407
408     if (opIsGptr(IC_RESULT(ic))            &&
409         AOP_SIZE(IC_LEFT(ic)) < GPTRSIZE   &&
410         AOP_SIZE(IC_RIGHT(ic)) < GPTRSIZE  &&
411          !pic16_sameRegs(AOP(IC_RESULT(ic)),AOP(IC_LEFT(ic))) &&
412          !pic16_sameRegs(AOP(IC_RESULT(ic)),AOP(IC_RIGHT(ic)))) {
413          char buffer[5];
414          sprintf(buffer,"#%d",pointerCode(getSpec(operandType(IC_LEFT(ic)))));
415          pic16_aopPut(AOP(IC_RESULT(ic)),buffer,GPTRSIZE - 1);
416      }
417 }
418 #endif
419
420 /*-----------------------------------------------------------------*/
421 /* genAddlit - generates code for addition                         */
422 /*-----------------------------------------------------------------*/
423 static void genAddLit2byte (operand *result, int offr, int lit)
424 {
425
426   switch(lit & 0xff) {
427   case 0:
428     break;
429   case 1:
430     pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),offr));
431     break;
432   case 0xff:
433     pic16_emitpcode(POC_DECF, pic16_popGet(AOP(result),offr));
434     break;
435   default:
436     pic16_emitpcode(POC_MOVLW,pic16_popGetLit(lit&0xff));
437     pic16_emitpcode(POC_ADDWF,pic16_popGet(AOP(result),offr));
438   }
439
440 }
441
442 static void emitMOVWF(operand *reg, int offset)
443 {
444   if(!reg)
445     return;
446
447   if (AOP_TYPE(reg) == AOP_ACC) {
448     DEBUGpic16_emitcode ("; ***","%s  %d ignoring mov into W",__FUNCTION__,__LINE__);
449     return;
450   }
451
452   pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(reg),offset));
453
454 }
455
456 static void genAddLit (iCode *ic, int lit)
457 {
458
459   int size,same;
460   int lo;
461
462   operand *result;
463   operand *left;
464
465   DEBUGpic16_emitcode ("; ***","%s  %d",__FUNCTION__,__LINE__);
466
467
468   left = IC_LEFT(ic);
469   result = IC_RESULT(ic);
470   same = pic16_sameRegs(AOP(left), AOP(result));
471   size = pic16_getDataSize(result);
472
473   if(same) {
474
475     /* Handle special cases first */
476     if(size == 1) 
477       genAddLit2byte (result, 0, lit);
478      
479     else if(size == 2) {
480       int hi = 0xff & (lit >> 8);
481       lo = lit & 0xff;
482
483       switch(hi) {
484       case 0: 
485
486         /* lit = 0x00LL */
487         DEBUGpic16_emitcode ("; hi = 0","%s  %d",__FUNCTION__,__LINE__);
488         switch(lo) {
489         case 0:
490           break;
491         case 1:
492           pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),0));
493           emitSKPNZ;
494           pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),MSB16));
495           break;
496         case 0xff:
497           pic16_emitpcode(POC_DECF, pic16_popGet(AOP(result),0));
498           pic16_emitpcode(POC_INCFSZW, pic16_popGet(AOP(result),0));
499           pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),MSB16));
500
501           break;
502         default:
503           pic16_emitpcode(POC_MOVLW,pic16_popGetLit(lit&0xff));
504           pic16_emitpcode(POC_ADDWF,pic16_popGet(AOP(result),0));
505           emitSKPNC;
506           pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),MSB16));
507
508
509         }
510         break;
511
512       case 1:
513         /* lit = 0x01LL */
514         DEBUGpic16_emitcode ("; hi = 1","%s  %d",__FUNCTION__,__LINE__);
515         switch(lo) {
516         case 0:  /* 0x0100 */
517           pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),MSB16));
518           break;
519         case 1:  /* 0x0101  */
520           pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),MSB16));
521           pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),0));
522           emitSKPNZ;
523           pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),MSB16));
524           break;
525         case 0xff: /* 0x01ff */
526           pic16_emitpcode(POC_DECF, pic16_popGet(AOP(result),0));
527           pic16_emitpcode(POC_INCFSZW, pic16_popGet(AOP(result),0));
528           pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),MSB16));
529           pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),MSB16));
530         }         
531         break;
532
533       case 0xff:
534         DEBUGpic16_emitcode ("; hi = ff","%s  %d",__FUNCTION__,__LINE__);
535         /* lit = 0xffLL */
536         switch(lo) {
537         case 0:  /* 0xff00 */
538           pic16_emitpcode(POC_DECF, pic16_popGet(AOP(result),MSB16));
539           break;
540         case 1:  /*0xff01 */
541           pic16_emitpcode(POC_INCFSZ, pic16_popGet(AOP(result),0));
542           pic16_emitpcode(POC_DECF, pic16_popGet(AOP(result),MSB16));
543           break;
544 /*      case 0xff: * 0xffff *
545           pic16_emitpcode(POC_INCFSZW, pic16_popGet(AOP(result),0,FALSE,FALSE));
546           pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),MSB16,FALSE,FALSE));
547           pic16_emitpcode(POC_DECF, pic16_popGet(AOP(result),0,FALSE,FALSE));
548           break;
549 */
550         default:
551           pic16_emitpcode(POC_MOVLW,pic16_popGetLit(lo));
552           pic16_emitpcode(POC_ADDWF,pic16_popGet(AOP(result),0));
553           emitSKPC;
554           pic16_emitpcode(POC_DECF, pic16_popGet(AOP(result),MSB16));
555           
556         }
557
558         break;
559         
560       default:
561         DEBUGpic16_emitcode ("; hi is generic","%d   %s  %d",hi,__FUNCTION__,__LINE__);
562
563         /* lit = 0xHHLL */
564         switch(lo) {
565         case 0:  /* 0xHH00 */
566           genAddLit2byte (result, MSB16, hi);
567           break;
568         case 1:  /* 0xHH01 */
569           pic16_emitpcode(POC_MOVLW,pic16_popGetLit((hi+1)&0xff));
570           pic16_emitpcode(POC_INCFSZ, pic16_popGet(AOP(result),0));
571           pic16_emitpcode(POC_MOVLW,pic16_popGetLit(hi));
572           pic16_emitpcode(POC_ADDWF,pic16_popGet(AOP(result),MSB16));
573           break;
574 /*      case 0xff: * 0xHHff *
575           pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(result),0,FALSE,FALSE));
576           pic16_emitpcode(POC_DECF, pic16_popGet(AOP(result),MSB16,FALSE,FALSE));
577           pic16_emitpcode(POC_MOVLW,pic16_popGetLit(hi));
578           pic16_emitpcode(POC_ADDWF,pic16_popGet(AOP(result),MSB16,FALSE,FALSE));
579           break;
580 */      default:  /* 0xHHLL */
581           pic16_emitpcode(POC_MOVLW,pic16_popGetLit(lo));
582           pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(result),0));
583           pic16_emitpcode(POC_MOVLW,pic16_popGetLit(hi));
584           emitSKPNC;
585           pic16_emitpcode(POC_MOVLW,pic16_popGetLit((hi+1) & 0xff));
586           pic16_emitpcode(POC_ADDWF,pic16_popGet(AOP(result),MSB16));
587           break;
588         }
589
590       }
591     } else {
592       int carry_info = 0;
593       int offset = 0;
594       /* size > 2 */
595       DEBUGpic16_emitcode (";  add lit to long","%s  %d",__FUNCTION__,__LINE__);
596
597       while(size--) {
598         lo = BYTEofLONG(lit,0);
599
600         if(carry_info) {
601           switch(lo) {
602           case 0:
603             switch(carry_info) {
604             case 1:
605               emitSKPNZ;
606               pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),offset));
607               break;
608             case 2:
609               pic16_emitpcode(POC_RLCFW, pic16_popGet(AOP(result),offset));
610               pic16_emitpcode(POC_ANDLW, pic16_popGetLit(1));
611               pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(result),offset));
612               break;
613             default: /* carry_info = 3  */
614               emitSKPNC;
615               pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),offset));
616               carry_info = 1;
617               break;
618             }
619             break;
620           case 0xff:
621             pic16_emitpcode(POC_MOVLW,pic16_popGetLit(lo));
622             if(carry_info==1) 
623               emitSKPZ;
624             else
625               emitSKPC;
626             pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(result),offset));
627             break;
628           default:
629             pic16_emitpcode(POC_MOVLW,pic16_popGetLit(lo));
630             if(carry_info==1) 
631               emitSKPNZ;
632             else
633               emitSKPNC;
634             pic16_emitpcode(POC_MOVLW,pic16_popGetLit(lo+1));
635             pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(result),offset));
636             carry_info=2;
637             break;
638           }
639         }else {
640           /* no carry info from previous step */
641           /* this means this is the first time to add */
642           switch(lo) {
643           case 0:
644             break;
645           case 1:
646             pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),offset));
647             carry_info=1;
648             break;
649           default:
650             pic16_emitpcode(POC_MOVLW,pic16_popGetLit(lo));
651             pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(result),offset));
652             if(lit <0x100) 
653               carry_info = 3;  /* Were adding only one byte and propogating the carry */
654             else
655               carry_info = 2;
656             break;
657           }
658         }
659         offset++;
660         lit >>= 8;
661       }
662     
663 /*
664       lo = BYTEofLONG(lit,0);
665
666       if(lit < 0x100) {
667         if(lo) {
668           if(lo == 1) {
669             pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),0,FALSE,FALSE));
670             emitSKPNZ;
671           } else {
672             pic16_emitpcode(POC_MOVLW,pic16_popGetLit(lo));
673             pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(result),0,FALSE,FALSE));
674             emitSKPNC;
675           }
676           pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),1,FALSE,FALSE));
677           emitSKPNZ;
678           pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),2,FALSE,FALSE));
679           emitSKPNZ;
680           pic16_emitpcode(POC_INCF, pic16_popGet(AOP(result),3,FALSE,FALSE));
681
682         } 
683       } 
684     }
685
686 */
687     }
688   } else {
689     int offset = 1;
690     DEBUGpic16_emitcode (";  left and result aren't same","%s  %d",__FUNCTION__,__LINE__);
691
692     if(size == 1) {
693
694       if(AOP_TYPE(left) == AOP_ACC) {
695         /* left addend is already in accumulator */
696         switch(lit & 0xff) {
697         case 0:
698           //pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(result),0,FALSE,FALSE));
699           emitMOVWF(result,0);
700           break;
701         default:
702           pic16_emitpcode(POC_ADDLW, pic16_popGetLit(lit & 0xff));
703           //pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(result),0,FALSE,FALSE));
704           emitMOVWF(result,0);
705         }
706       } else {
707         /* left addend is in a register */
708         switch(lit & 0xff) {
709         case 0:
710           pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
711           emitMOVWF(result, 0);
712           //pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(result),0,FALSE,FALSE));
713           emitMOVWF(result,0);
714           break;
715         case 1:
716           pic16_emitpcode(POC_INCFW, pic16_popGet(AOP(left),0));
717           //pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(result),0,FALSE,FALSE));
718           emitMOVWF(result,0);
719           break;
720         case 0xff:
721           pic16_emitpcode(POC_DECFW, pic16_popGet(AOP(left),0));
722           //pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(result),0,FALSE,FALSE));
723           emitMOVWF(result,0);
724           break;
725         default:
726           pic16_emitpcode(POC_MOVLW, pic16_popGetLit(lit & 0xff));
727           pic16_emitpcode(POC_ADDFW, pic16_popGet(AOP(left),0));
728           //pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(result),0,FALSE,FALSE));
729           emitMOVWF(result,0);
730         }
731       }
732
733     } else {
734       int clear_carry=0;
735
736       /* left is not the accumulator */
737       if(lit & 0xff) {
738         pic16_emitpcode(POC_MOVLW, pic16_popGetLit(lit & 0xff));
739         pic16_emitpcode(POC_ADDFW, pic16_popGet(AOP(left),0));
740       } else {
741         pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
742         /* We don't know the state of the carry bit at this point */
743         clear_carry = 1;
744       }
745       //pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(result),0,FALSE,FALSE));
746       emitMOVWF(result,0);
747       while(--size) {
748       
749         lit >>= 8;
750         if(lit & 0xff) {
751           if(clear_carry) {
752             /* The ls byte of the lit must've been zero - that 
753                means we don't have to deal with carry */
754
755             pic16_emitpcode(POC_MOVLW, pic16_popGetLit(lit & 0xff));
756             pic16_emitpcode(POC_ADDFW,  pic16_popGet(AOP(left),offset));
757             pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(left),offset));
758
759             clear_carry = 0;
760
761           } else {
762             pic16_emitpcode(POC_MOVLW, pic16_popGetLit(lit & 0xff));
763             //pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(result),offset,FALSE,FALSE));
764             emitMOVWF(result,offset);
765             pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),offset));
766             emitSKPNC;
767             pic16_emitpcode(POC_INCFSZW,pic16_popGet(AOP(left),offset));
768             pic16_emitpcode(POC_ADDWF,  pic16_popGet(AOP(result),offset));
769           }
770
771         } else {
772           pic16_emitpcode(POC_CLRF,  pic16_popGet(AOP(result),offset));
773           pic16_emitpcode(POC_RLCF,  pic16_popGet(AOP(result),offset));
774           pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),offset));
775           pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(result),offset));
776         }
777         offset++;
778       }
779     }
780   }
781 }
782
783 /*-----------------------------------------------------------------*/
784 /* pic16_genPlus - generates code for addition                     */
785 /*-----------------------------------------------------------------*/
786 void pic16_genPlus (iCode *ic)
787 {
788   int size, offset = 0;
789   operand *result, *left, *right;
790   
791   /* special cases :- */
792   DEBUGpic16_emitcode ("; ***","%s  %d",__FUNCTION__,__LINE__);
793
794
795 #if 1
796         result = IC_RESULT(ic);
797         left = IC_LEFT(ic);
798         right = IC_RIGHT(ic);
799   pic16_aopOp (left,ic,FALSE);
800   pic16_aopOp (right,ic,FALSE);
801   pic16_aopOp (result,ic,TRUE);
802   DEBUGpic16_pic16_AopType(__LINE__,left, right, result);
803
804 #else
805   pic16_aopOp (IC_LEFT(ic),ic,FALSE);
806   pic16_aopOp (IC_RIGHT(ic),ic,FALSE);
807   pic16_aopOp (IC_RESULT(ic),ic,TRUE);
808   DEBUGpic16_pic16_AopType(__LINE__,IC_LEFT(ic),IC_RIGHT(ic),IC_RESULT(ic));
809 #endif
810
811
812   /* if literal, literal on the right or
813      if left requires ACC or right is already
814      in ACC */
815
816   if (AOP_TYPE(IC_LEFT(ic)) == AOP_LIT) {
817     operand *t = IC_RIGHT(ic);
818     IC_RIGHT(ic) = IC_LEFT(ic);
819     IC_LEFT(ic) = t;
820   }
821
822   /* if both left & right are in bit space */
823   if (AOP_TYPE(IC_LEFT(ic)) == AOP_CRY &&
824       AOP_TYPE(IC_RIGHT(ic)) == AOP_CRY) {
825     pic16_genPlusBits (ic);
826     goto release ;
827   }
828
829   /* if left in bit space & right literal */
830   if (AOP_TYPE(IC_LEFT(ic)) == AOP_CRY &&
831       AOP_TYPE(IC_RIGHT(ic)) == AOP_LIT) {
832     /* if result in bit space */
833     if(AOP_TYPE(IC_RESULT(ic)) == AOP_CRY){
834       if((unsigned long)floatFromVal(AOP(IC_RIGHT(ic))->aopu.aop_lit) != 0L) {
835         pic16_emitpcode(POC_MOVLW, pic16_popGet(AOP(IC_RESULT(ic)),0));
836         if (!pic16_sameRegs(AOP(IC_LEFT(ic)), AOP(IC_RESULT(ic))) )
837           pic16_emitpcode(POC_BTFSC, pic16_popGet(AOP(IC_LEFT(ic)),0));
838         pic16_emitpcode(POC_XORWF, pic16_popGet(AOP(IC_RESULT(ic)),0));
839       }
840     } else {
841       size = pic16_getDataSize(IC_RESULT(ic));
842       while (size--) {
843         MOVA(pic16_aopGet(AOP(IC_RIGHT(ic)),offset,FALSE,FALSE));  
844         pic16_emitcode("addc","a,#00  ;%d",__LINE__);
845         pic16_aopPut(AOP(IC_RESULT(ic)),"a",offset++);
846       }
847     }
848     goto release ;
849   }
850
851   /* if I can do an increment instead
852      of add then GOOD for ME */
853   if (pic16_genPlusIncr (ic) == TRUE)
854     goto release;   
855
856   size = pic16_getDataSize(IC_RESULT(ic));
857
858   if(AOP(IC_RIGHT(ic))->type == AOP_LIT) {
859     /* Add a literal to something else */
860     //bool know_W=0;
861     unsigned lit = (unsigned) floatFromVal(AOP(IC_RIGHT(ic))->aopu.aop_lit);
862     //      unsigned l1=0;
863
864     //      offset = 0;
865     DEBUGpic16_emitcode(";","adding lit to something. size %d",size);
866
867     genAddLit (ic,  lit);
868     goto release;
869
870   } else if(AOP_TYPE(IC_RIGHT(ic)) == AOP_CRY) {
871
872     pic16_emitcode(";bitadd","right is bit: %s",pic16_aopGet(AOP(IC_RIGHT(ic)),0,FALSE,FALSE));
873     pic16_emitcode(";bitadd","left is bit: %s",pic16_aopGet(AOP(IC_LEFT(ic)),0,FALSE,FALSE));
874     pic16_emitcode(";bitadd","result is bit: %s",pic16_aopGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE));
875
876     /* here we are adding a bit to a char or int */
877     if(size == 1) {
878       if (pic16_sameRegs(AOP(IC_LEFT(ic)), AOP(IC_RESULT(ic))) ) {
879
880         pic16_emitpcode(POC_BTFSC , pic16_popGet(AOP(IC_RIGHT(ic)),0));
881         pic16_emitpcode(POC_INCF ,  pic16_popGet(AOP(IC_RESULT(ic)),0));
882
883         pic16_emitcode("btfsc","(%s >> 3), (%s & 7)",
884                        AOP(IC_RIGHT(ic))->aopu.aop_dir,
885                        AOP(IC_RIGHT(ic))->aopu.aop_dir);
886         pic16_emitcode(" incf","%s,f", pic16_aopGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE));
887       } else {
888
889         if(AOP_TYPE(IC_LEFT(ic)) == AOP_ACC) {
890           pic16_emitpcode(POC_BTFSC , pic16_popGet(AOP(IC_RIGHT(ic)),0));
891           pic16_emitpcode(POC_XORLW , pic16_popGetLit(1));
892
893           pic16_emitcode("btfsc","(%s >> 3), (%s & 7)",
894                          AOP(IC_RIGHT(ic))->aopu.aop_dir,
895                          AOP(IC_RIGHT(ic))->aopu.aop_dir);
896           pic16_emitcode(" xorlw","1");
897         } else {
898           pic16_emitpcode(POC_MOVFW , pic16_popGet(AOP(IC_LEFT(ic)),0));
899           pic16_emitpcode(POC_BTFSC , pic16_popGet(AOP(IC_RIGHT(ic)),0));
900           pic16_emitpcode(POC_INCFW , pic16_popGet(AOP(IC_LEFT(ic)),0));
901
902           pic16_emitcode("movf","%s,w", pic16_aopGet(AOP(IC_LEFT(ic)),0,FALSE,FALSE));
903           pic16_emitcode("btfsc","(%s >> 3), (%s & 7)",
904                          AOP(IC_RIGHT(ic))->aopu.aop_dir,
905                          AOP(IC_RIGHT(ic))->aopu.aop_dir);
906           pic16_emitcode(" incf","%s,w", pic16_aopGet(AOP(IC_LEFT(ic)),0,FALSE,FALSE));
907         }
908           
909         if(AOP_TYPE(IC_RESULT(ic)) != AOP_ACC) {
910             
911           if(AOP_TYPE(IC_RESULT(ic)) == AOP_CRY) {
912             pic16_emitpcode(POC_ANDLW , pic16_popGetLit(1));
913             pic16_emitpcode(POC_BCF ,   pic16_popGet(AOP(IC_RESULT(ic)),0));
914             emitSKPZ;
915             pic16_emitpcode(POC_BSF ,   pic16_popGet(AOP(IC_RESULT(ic)),0));
916           } else {
917             pic16_emitpcode(POC_MOVWF ,   pic16_popGet(AOP(IC_RESULT(ic)),0));
918             pic16_emitcode("movwf","%s", pic16_aopGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE));
919           }
920         }
921       }
922
923     } else {
924       int offset = 1;
925       DEBUGpic16_emitcode ("; ***","%s  %d",__FUNCTION__,__LINE__);
926       if (pic16_sameRegs(AOP(IC_LEFT(ic)), AOP(IC_RESULT(ic))) ) {
927         emitCLRZ;
928         pic16_emitpcode(POC_BTFSC, pic16_popGet(AOP(IC_RIGHT(ic)),0));
929         pic16_emitpcode(POC_INCF,  pic16_popGet(AOP(IC_RESULT(ic)),0));
930
931         pic16_emitcode("clrz","");
932
933         pic16_emitcode("btfsc","(%s >> 3), (%s & 7)",
934                        AOP(IC_RIGHT(ic))->aopu.aop_dir,
935                        AOP(IC_RIGHT(ic))->aopu.aop_dir);
936         pic16_emitcode(" incf","%s,f", pic16_aopGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE));
937
938       } else {
939
940         pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(IC_LEFT(ic)),0));
941         pic16_emitpcode(POC_BTFSC, pic16_popGet(AOP(IC_RIGHT(ic)),0));
942         pic16_emitpcode(POC_INCFW, pic16_popGet(AOP(IC_LEFT(ic)),0));
943         //pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(IC_RIGHT(ic)),0,FALSE,FALSE));
944         emitMOVWF(IC_RIGHT(ic),0);
945
946         pic16_emitcode("movf","%s,w", pic16_aopGet(AOP(IC_LEFT(ic)),0,FALSE,FALSE));
947         pic16_emitcode("btfsc","(%s >> 3), (%s & 7)",
948                        AOP(IC_RIGHT(ic))->aopu.aop_dir,
949                        AOP(IC_RIGHT(ic))->aopu.aop_dir);
950         pic16_emitcode(" incf","%s,w", pic16_aopGet(AOP(IC_LEFT(ic)),0,FALSE,FALSE));
951         pic16_emitcode("movwf","%s", pic16_aopGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE));
952
953       }
954
955       while(--size){
956         emitSKPZ;
957         pic16_emitpcode(POC_INCF,  pic16_popGet(AOP(IC_RESULT(ic)),offset++));
958         //pic16_emitcode(" incf","%s,f", pic16_aopGet(AOP(IC_RIGHT(ic)),offset++,FALSE,FALSE));
959       }
960
961     }
962       
963   } else {
964     DEBUGpic16_emitcode ("; ***","%s  %d",__FUNCTION__,__LINE__);    
965
966     /* Add the first bytes */
967
968     if(strcmp(pic16_aopGet(AOP(IC_LEFT(ic)),0,FALSE,FALSE),"a") == 0 ) {
969       pic16_emitpcode(POC_ADDFW, pic16_popGet(AOP(IC_RIGHT(ic)),0));
970       pic16_emitpcode(POC_MOVWF,pic16_popGet(AOP(IC_RESULT(ic)),0));
971     } else {
972
973       if ( AOP_TYPE(IC_LEFT(ic)) == AOP_ACC) {
974         pic16_emitpcode(POC_ADDFW, pic16_popGet(AOP(IC_RIGHT(ic)),0));
975         if ( AOP_TYPE(IC_RESULT(ic)) != AOP_ACC)
976           pic16_emitpcode(POC_MOVWF,pic16_popGet(AOP(IC_RESULT(ic)),0));
977       } else {
978
979         pic16_emitpcode(POC_MOVFW,pic16_popGet(AOP(IC_RIGHT(ic)),0));
980
981         if (pic16_sameRegs(AOP(IC_LEFT(ic)), AOP(IC_RESULT(ic))) )
982           pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(IC_LEFT(ic)),0));
983         else {
984           PIC_OPCODE poc = POC_ADDFW;
985
986           if ((AOP_TYPE(IC_LEFT(ic)) == AOP_PCODE) && (
987               (AOP(IC_LEFT(ic))->aopu.pcop->type == PO_LITERAL) || 
988               (AOP(IC_LEFT(ic))->aopu.pcop->type == PO_IMMEDIATE)))
989             poc = POC_ADDLW;
990           pic16_emitpcode(poc, pic16_popGet(AOP(IC_LEFT(ic)),0));
991           if ( AOP_TYPE(IC_RESULT(ic)) != AOP_ACC)
992             pic16_emitpcode(POC_MOVWF,pic16_popGet(AOP(IC_RESULT(ic)),0));
993         }
994       }
995     }
996
997     size = min( AOP_SIZE(IC_RESULT(ic)), AOP_SIZE(IC_RIGHT(ic))) - 1;
998     offset = 1;
999
1000
1001     while(size--){
1002       if (!pic16_sameRegs(AOP(IC_LEFT(ic)), AOP(IC_RESULT(ic))) ) {
1003         pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(IC_LEFT(ic)),offset));
1004         pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(IC_RESULT(ic)),offset));
1005
1006         pic16_emitcode("movf","%s,w",  pic16_aopGet(AOP(IC_LEFT(ic)),offset,FALSE,FALSE));
1007         pic16_emitcode("movwf","%s",  pic16_aopGet(AOP(IC_RESULT(ic)),offset,FALSE,FALSE));
1008       }
1009
1010       pic16_emitpcode(POC_MOVFW,   pic16_popGet(AOP(IC_RIGHT(ic)),offset));
1011       emitSKPNC;
1012       pic16_emitpcode(POC_INCFSZW, pic16_popGet(AOP(IC_RIGHT(ic)),offset));
1013       pic16_emitpcode(POC_ADDWF,   pic16_popGet(AOP(IC_RESULT(ic)),offset));
1014
1015       /*
1016         pic16_emitcode("movf","%s,w",  pic16_aopGet(AOP(IC_RIGHT(ic)),offset,FALSE,FALSE));
1017         emitSKPNC;
1018         pic16_emitcode("incfsz","%s,w",pic16_aopGet(AOP(IC_RIGHT(ic)),offset,FALSE,FALSE));
1019         pic16_emitcode("addwf","%s,f", pic16_aopGet(AOP(IC_RESULT(ic)),offset,FALSE,FALSE));
1020       */
1021
1022       offset++;
1023     }
1024
1025   }
1026
1027   if (AOP_SIZE(IC_RESULT(ic)) > AOP_SIZE(IC_RIGHT(ic))) {
1028     int sign =  !(SPEC_USIGN(getSpec(operandType(IC_LEFT(ic)))) |
1029                   SPEC_USIGN(getSpec(operandType(IC_RIGHT(ic)))) );
1030
1031
1032     /* Need to extend result to higher bytes */
1033     size = AOP_SIZE(IC_RESULT(ic)) - AOP_SIZE(IC_RIGHT(ic)) - 1;
1034
1035     /* First grab the carry from the lower bytes */
1036     pic16_emitpcode(POC_CLRF, pic16_popGet(AOP(IC_RESULT(ic)),offset));
1037     pic16_emitpcode(POC_RLCF,  pic16_popGet(AOP(IC_RESULT(ic)),offset));
1038
1039
1040     if(sign) {
1041       /* Now this is really horrid. Gotta check the sign of the addends and propogate
1042        * to the result */
1043
1044       pic16_emitpcode(POC_BTFSC, pic16_newpCodeOpBit(pic16_aopGet(AOP(IC_LEFT(ic)),offset-1,FALSE,FALSE),7,0));
1045       pic16_emitpcode(POC_DECF,  pic16_popGet(AOP(IC_RESULT(ic)),offset));
1046       pic16_emitpcode(POC_BTFSC, pic16_newpCodeOpBit(pic16_aopGet(AOP(IC_RIGHT(ic)),offset-1,FALSE,FALSE),7,0));
1047       pic16_emitpcode(POC_DECF,  pic16_popGet(AOP(IC_RESULT(ic)),offset));
1048
1049       /* if chars or ints or being signed extended to longs: */
1050       if(size) {
1051         pic16_emitpcode(POC_MOVLW, pic16_popGetLit(0));
1052         pic16_emitpcode(POC_BTFSC, pic16_newpCodeOpBit(pic16_aopGet(AOP(IC_RESULT(ic)),offset,FALSE,FALSE),7,0));
1053         pic16_emitpcode(POC_MOVLW, pic16_popGetLit(0xff));
1054       }
1055     }
1056
1057     offset++;
1058     while(size--) {
1059       
1060       if(sign)
1061         pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(IC_RESULT(ic)),offset));
1062       else
1063         pic16_emitpcode(POC_CLRF,  pic16_popGet(AOP(IC_RESULT(ic)),offset));
1064
1065       offset++;
1066     }
1067   }
1068
1069
1070   //adjustArithmeticResult(ic);
1071
1072  release:
1073   pic16_freeAsmop(IC_LEFT(ic),NULL,ic,(RESULTONSTACK(ic) ? FALSE : TRUE));
1074   pic16_freeAsmop(IC_RIGHT(ic),NULL,ic,(RESULTONSTACK(ic) ? FALSE : TRUE));
1075   pic16_freeAsmop(IC_RESULT(ic),NULL,ic,TRUE);
1076 }
1077
1078 /*-----------------------------------------------------------------*/
1079 /* pic16_genMinusDec :- does subtraction with decrement if possible     */
1080 /*-----------------------------------------------------------------*/
1081 bool pic16_genMinusDec (iCode *ic)
1082 {
1083     unsigned int icount ;
1084     unsigned int size = pic16_getDataSize(IC_RESULT(ic));
1085
1086     DEBUGpic16_emitcode ("; ***","%s  %d",__FUNCTION__,__LINE__);
1087     /* will try to generate an increment */
1088     /* if the right side is not a literal 
1089     we cannot */
1090     if ((AOP_TYPE(IC_RIGHT(ic)) != AOP_LIT) || 
1091         (AOP_TYPE(IC_LEFT(ic)) == AOP_CRY) || 
1092         (AOP_TYPE(IC_RESULT(ic)) == AOP_CRY) )
1093         return FALSE ;
1094
1095     DEBUGpic16_emitcode ("; lit val","%d",(unsigned int) floatFromVal (AOP(IC_RIGHT(ic))->aopu.aop_lit));
1096
1097     /* if the literal value of the right hand side
1098     is greater than 4 then it is not worth it */
1099     if ((icount = (unsigned int) floatFromVal (AOP(IC_RIGHT(ic))->aopu.aop_lit)) > 2)
1100         return FALSE ;
1101
1102     /* if decrement 16 bits in register */
1103     if (pic16_sameRegs(AOP(IC_LEFT(ic)), AOP(IC_RESULT(ic))) &&
1104         (size > 1) &&
1105         (icount == 1)) {
1106
1107       if(size == 2) { 
1108         pic16_emitpcode(POC_DECF,    pic16_popGet(AOP(IC_RESULT(ic)),LSB));
1109         pic16_emitpcode(POC_INCFSZW, pic16_popGet(AOP(IC_RESULT(ic)),LSB));
1110         pic16_emitpcode(POC_INCF,    pic16_popGet(AOP(IC_RESULT(ic)),MSB16));
1111         pic16_emitpcode(POC_DECF,    pic16_popGet(AOP(IC_RESULT(ic)),MSB16));
1112
1113         pic16_emitcode("decf","%s,f",pic16_aopGet(AOP(IC_RESULT(ic)),LSB,FALSE,FALSE));
1114         pic16_emitcode("incfsz","%s,w",pic16_aopGet(AOP(IC_RESULT(ic)),LSB,FALSE,FALSE));
1115         pic16_emitcode(" decf","%s,f",pic16_aopGet(AOP(IC_RESULT(ic)),MSB16,FALSE,FALSE));
1116       } else {
1117         /* size is 3 or 4 */
1118         pic16_emitpcode(POC_MOVLW,  pic16_popGetLit(0xff));
1119         pic16_emitpcode(POC_ADDWF,  pic16_popGet(AOP(IC_RESULT(ic)),LSB));
1120         emitSKPNC;
1121         pic16_emitpcode(POC_ADDWF,  pic16_popGet(AOP(IC_RESULT(ic)),MSB16));
1122         emitSKPNC;
1123         pic16_emitpcode(POC_ADDWF,  pic16_popGet(AOP(IC_RESULT(ic)),MSB24));
1124
1125         pic16_emitcode("movlw","0xff");
1126         pic16_emitcode("addwf","%s,f",pic16_aopGet(AOP(IC_RESULT(ic)),LSB,FALSE,FALSE));
1127
1128         emitSKPNC;
1129         pic16_emitcode("addwf","%s,f",pic16_aopGet(AOP(IC_RESULT(ic)),MSB16,FALSE,FALSE));
1130         emitSKPNC;
1131         pic16_emitcode("addwf","%s,f",pic16_aopGet(AOP(IC_RESULT(ic)),MSB24,FALSE,FALSE));
1132
1133         if(size > 3) {
1134           emitSKPNC;
1135           pic16_emitpcode(POC_ADDWF,  pic16_popGet(AOP(IC_RESULT(ic)),MSB32));
1136
1137           pic16_emitcode("skpnc","");
1138           emitSKPNC;
1139           pic16_emitcode("addwf","%s,f",pic16_aopGet(AOP(IC_RESULT(ic)),MSB32,FALSE,FALSE));
1140         }
1141
1142       }
1143
1144       return TRUE;
1145
1146     }
1147
1148     /* if the sizes are greater than 1 then we cannot */
1149     if (AOP_SIZE(IC_RESULT(ic)) > 1 ||
1150         AOP_SIZE(IC_LEFT(ic)) > 1   )
1151         return FALSE ;
1152
1153     /* we can if the aops of the left & result match or
1154     if they are in registers and the registers are the
1155     same */
1156     if (pic16_sameRegs(AOP(IC_LEFT(ic)), AOP(IC_RESULT(ic)))) {
1157
1158       while (icount--) 
1159         pic16_emitpcode(POC_DECF, pic16_popGet(AOP(IC_RESULT(ic)),0));
1160
1161         //pic16_emitcode ("decf","%s,f",pic16_aopGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE));
1162
1163         return TRUE ;
1164     }
1165
1166     DEBUGpic16_emitcode ("; returning"," result=%s, left=%s",
1167                    pic16_aopGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE),
1168                    pic16_aopGet(AOP(IC_LEFT(ic)),0,FALSE,FALSE));
1169     if(size==1) {
1170
1171       pic16_emitcode("decf","%s,w",pic16_aopGet(AOP(IC_LEFT(ic)),0,FALSE,FALSE));
1172       pic16_emitcode("movwf","%s",pic16_aopGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE));
1173
1174       pic16_emitpcode(POC_DECFW,  pic16_popGet(AOP(IC_LEFT(ic)),0));
1175       pic16_emitpcode(POC_MOVWF,  pic16_popGet(AOP(IC_RESULT(ic)),0));
1176
1177       return TRUE;
1178     }
1179
1180     return FALSE ;
1181 }
1182
1183 /*-----------------------------------------------------------------*/
1184 /* pic16_addSign - propogate sign bit to higher bytes                    */
1185 /*-----------------------------------------------------------------*/
1186 void pic16_addSign(operand *result, int offset, int sign)
1187 {
1188   int size = (pic16_getDataSize(result) - offset);
1189   DEBUGpic16_emitcode ("; ***","%s  %d",__FUNCTION__,__LINE__);
1190
1191   if(size > 0){
1192     if(sign && offset) {
1193
1194       if(size == 1) {
1195         pic16_emitpcode(POC_CLRF,pic16_popGet(AOP(result),offset));
1196         pic16_emitpcode(POC_BTFSC,pic16_newpCodeOpBit(pic16_aopGet(AOP(result),offset-1,FALSE,FALSE),7,0));
1197         pic16_emitpcode(POC_DECF, pic16_popGet(AOP(result),offset));
1198       } else {
1199
1200         pic16_emitpcode(POC_MOVLW, pic16_popGetLit(0));
1201         pic16_emitpcode(POC_BTFSC, pic16_newpCodeOpBit(pic16_aopGet(AOP(result),offset-1,FALSE,FALSE),7,0));
1202         pic16_emitpcode(POC_MOVLW, pic16_popGetLit(0xff));
1203         while(size--)
1204           pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(result),size));
1205
1206       }
1207     } else
1208       while(size--)
1209         pic16_emitpcode(POC_CLRF,pic16_popGet(AOP(result),offset++));
1210   }
1211 }
1212
1213 /*-----------------------------------------------------------------*/
1214 /* pic16_genMinusBits - generates code for subtraction  of two bits      */
1215 /*-----------------------------------------------------------------*/
1216 void pic16_genMinusBits (iCode *ic)
1217 {
1218     symbol *lbl = newiTempLabel(NULL);
1219     DEBUGpic16_emitcode ("; ***","%s  %d",__FUNCTION__,__LINE__);
1220     if (AOP_TYPE(IC_RESULT(ic)) == AOP_CRY){
1221         pic16_emitcode("mov","c,%s",AOP(IC_LEFT(ic))->aopu.aop_dir);
1222         pic16_emitcode("jnb","%s,%05d_DS_",AOP(IC_RIGHT(ic))->aopu.aop_dir,(lbl->key+100));
1223         pic16_emitcode("cpl","c");
1224         pic16_emitcode("","%05d_DS_:",(lbl->key+100));
1225         pic16_outBitC(IC_RESULT(ic));
1226     }
1227     else{
1228         pic16_emitcode("mov","c,%s",AOP(IC_RIGHT(ic))->aopu.aop_dir);
1229         pic16_emitcode("subb","a,acc");
1230         pic16_emitcode("jnb","%s,%05d_DS_",AOP(IC_LEFT(ic))->aopu.aop_dir,(lbl->key+100));
1231         pic16_emitcode("inc","a");
1232         pic16_emitcode("","%05d_DS_:",(lbl->key+100));
1233         pic16_aopPut(AOP(IC_RESULT(ic)),"a",0);
1234         pic16_addSign(IC_RESULT(ic), MSB16, SPEC_USIGN(getSpec(operandType(IC_RESULT(ic)))));
1235     }
1236 }
1237
1238 /*-----------------------------------------------------------------*/
1239 /* pic16_genMinus - generates code for subtraction                       */
1240 /*-----------------------------------------------------------------*/
1241 void pic16_genMinus (iCode *ic)
1242 {
1243   int size, offset = 0, same=0;
1244   unsigned long lit = 0L;
1245
1246   DEBUGpic16_emitcode ("; ***","%s  %d",__FUNCTION__,__LINE__);
1247   pic16_aopOp (IC_LEFT(ic),ic,FALSE);
1248   pic16_aopOp (IC_RIGHT(ic),ic,FALSE);
1249   pic16_aopOp (IC_RESULT(ic),ic,TRUE);
1250
1251   if (AOP_TYPE(IC_RESULT(ic)) == AOP_CRY  &&
1252       AOP_TYPE(IC_RIGHT(ic)) == AOP_LIT) {
1253     operand *t = IC_RIGHT(ic);
1254     IC_RIGHT(ic) = IC_LEFT(ic);
1255     IC_LEFT(ic) = t;
1256   }
1257
1258   DEBUGpic16_emitcode ("; ","result %s, left %s, right %s",
1259                    pic16_AopType(AOP_TYPE(IC_RESULT(ic))),
1260                    pic16_AopType(AOP_TYPE(IC_LEFT(ic))),
1261                    pic16_AopType(AOP_TYPE(IC_RIGHT(ic))));
1262
1263   /* special cases :- */
1264   /* if both left & right are in bit space */
1265   if (AOP_TYPE(IC_LEFT(ic)) == AOP_CRY &&
1266       AOP_TYPE(IC_RIGHT(ic)) == AOP_CRY) {
1267     pic16_genPlusBits (ic);
1268     goto release ;
1269   }
1270
1271   /* if I can do an decrement instead
1272      of subtract then GOOD for ME */
1273   //  if (pic16_genMinusDec (ic) == TRUE)
1274   //    goto release;   
1275
1276   size = pic16_getDataSize(IC_RESULT(ic));   
1277   same = pic16_sameRegs(AOP(IC_RIGHT(ic)), AOP(IC_RESULT(ic)));
1278
1279   if(AOP(IC_RIGHT(ic))->type == AOP_LIT) {
1280     /* Add a literal to something else */
1281
1282     lit = (unsigned long)floatFromVal(AOP(IC_RIGHT(ic))->aopu.aop_lit);
1283     lit = - (long)lit;
1284
1285     genAddLit ( ic,  lit);
1286     
1287 #if 0
1288     /* add the first byte: */
1289     pic16_emitcode("movlw","0x%x", lit & 0xff);
1290     pic16_emitcode("addwf","%s,f", pic16_aopGet(AOP(IC_LEFT(ic)),0,FALSE,FALSE));
1291     pic16_emitpcode(POC_MOVLW,  pic16_popGetLit(lit & 0xff));
1292     pic16_emitpcode(POC_ADDWF,  pic16_popGet(AOP(IC_LEFT(ic)),0));
1293
1294
1295     offset = 1;
1296     size--;
1297
1298     while(size-- > 0) {
1299
1300       lit >>= 8;
1301
1302       if(lit & 0xff) {
1303
1304         if((lit & 0xff) == 0xff) {
1305           pic16_emitpcode(POC_MOVLW,  pic16_popGetLit(0xff));
1306           emitSKPC;
1307           pic16_emitpcode(POC_ADDWF,  pic16_popGet(AOP(IC_LEFT(ic)),offset));
1308         } else {
1309           pic16_emitpcode(POC_MOVLW,  pic16_popGetLit(lit & 0xff));
1310           emitSKPNC;
1311           pic16_emitpcode(POC_MOVLW,  pic16_popGetLit((lit+1) & 0xff));
1312           pic16_emitpcode(POC_ADDWF,  pic16_popGet(AOP(IC_LEFT(ic)),offset));
1313         }
1314
1315       } else {
1316         /* do the rlf known zero trick here */
1317         pic16_emitpcode(POC_MOVLW,  pic16_popGetLit(1));
1318         emitSKPNC;
1319         pic16_emitpcode(POC_ADDWF,  pic16_popGet(AOP(IC_LEFT(ic)),offset));
1320       }
1321       offset++;
1322     }
1323 #endif
1324   } else if(AOP_TYPE(IC_RIGHT(ic)) == AOP_CRY) {
1325     // bit subtraction
1326
1327     pic16_emitcode(";bitsub","right is bit: %s",pic16_aopGet(AOP(IC_RIGHT(ic)),0,FALSE,FALSE));
1328     pic16_emitcode(";bitsub","left is bit: %s",pic16_aopGet(AOP(IC_LEFT(ic)),0,FALSE,FALSE));
1329     pic16_emitcode(";bitsub","result is bit: %s",pic16_aopGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE));
1330
1331     /* here we are subtracting a bit from a char or int */
1332     if(size == 1) {
1333       if (pic16_sameRegs(AOP(IC_LEFT(ic)), AOP(IC_RESULT(ic))) ) {
1334
1335         pic16_emitpcode(POC_BTFSC , pic16_popGet(AOP(IC_RIGHT(ic)),0));
1336         pic16_emitpcode(POC_DECF ,  pic16_popGet(AOP(IC_RESULT(ic)),0));
1337
1338         pic16_emitcode("btfsc","(%s >> 3), (%s & 7)",
1339                  AOP(IC_RIGHT(ic))->aopu.aop_dir,
1340                  AOP(IC_RIGHT(ic))->aopu.aop_dir);
1341         pic16_emitcode(" incf","%s,f", pic16_aopGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE));
1342       } else {
1343
1344         if(AOP_TYPE(IC_LEFT(ic)) == AOP_ACC) {
1345           pic16_emitpcode(POC_BTFSC , pic16_popGet(AOP(IC_RIGHT(ic)),0));
1346           pic16_emitpcode(POC_XORLW , pic16_popGetLit(1));
1347         }else  if( (AOP_TYPE(IC_LEFT(ic)) == AOP_IMMD) ||
1348               (AOP_TYPE(IC_LEFT(ic)) == AOP_LIT) ) {
1349
1350           lit = (unsigned long)floatFromVal(AOP(IC_LEFT(ic))->aopu.aop_lit);
1351
1352           if(AOP_TYPE(IC_RESULT(ic)) == AOP_CRY) {
1353             if (pic16_sameRegs(AOP(IC_RIGHT(ic)), AOP(IC_RESULT(ic))) ) {
1354               if(lit & 1) {
1355                 pic16_emitpcode(POC_MOVLW , pic16_popGet(AOP(IC_RIGHT(ic)),0));
1356                 pic16_emitpcode(POC_XORWF , pic16_popGet(AOP(IC_RIGHT(ic)),0));
1357               }
1358             }else{
1359               pic16_emitpcode(POC_BCF ,     pic16_popGet(AOP(IC_RESULT(ic)),0));
1360               if(lit & 1) 
1361                 pic16_emitpcode(POC_BTFSS , pic16_popGet(AOP(IC_RIGHT(ic)),0));
1362               else
1363                 pic16_emitpcode(POC_BTFSC , pic16_popGet(AOP(IC_RIGHT(ic)),0));
1364               pic16_emitpcode(POC_BSF ,     pic16_popGet(AOP(IC_RESULT(ic)),0));
1365             }
1366             goto release;
1367           } else {
1368             pic16_emitpcode(POC_MOVLW , pic16_popGetLit(lit & 0xff));
1369             pic16_emitpcode(POC_BTFSC , pic16_popGet(AOP(IC_RIGHT(ic)),0));
1370             pic16_emitpcode(POC_MOVLW , pic16_popGetLit((lit-1) & 0xff));
1371             pic16_emitpcode(POC_MOVWF , pic16_popGet(AOP(IC_RESULT(ic)),0));
1372
1373           }
1374
1375         } else {
1376           pic16_emitpcode(POC_MOVFW , pic16_popGet(AOP(IC_LEFT(ic)),0));
1377           pic16_emitpcode(POC_BTFSC , pic16_popGet(AOP(IC_RIGHT(ic)),0));
1378           pic16_emitpcode(POC_DECFW , pic16_popGet(AOP(IC_LEFT(ic)),0));
1379         }
1380           
1381         if(AOP_TYPE(IC_RESULT(ic)) != AOP_ACC) {
1382             
1383           pic16_emitpcode(POC_MOVWF ,   pic16_popGet(AOP(IC_RESULT(ic)),0));
1384
1385         } else  {
1386           pic16_emitpcode(POC_ANDLW , pic16_popGetLit(1));
1387 /*
1388           pic16_emitpcode(POC_BCF ,   pic16_popGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE));
1389           emitSKPZ;
1390           pic16_emitpcode(POC_BSF ,   pic16_popGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE));
1391 */
1392         }
1393
1394       }
1395
1396     }
1397   } else   if(// (AOP_TYPE(IC_LEFT(ic)) == AOP_IMMD) || 
1398               (AOP(IC_LEFT(ic))->type == AOP_LIT) &&
1399               (AOP_TYPE(IC_RIGHT(ic)) != AOP_ACC)) {
1400
1401     lit = (unsigned long)floatFromVal(AOP(IC_LEFT(ic))->aopu.aop_lit);
1402     DEBUGpic16_emitcode ("; left is lit","line %d result %s, left %s, right %s",__LINE__,
1403                    pic16_AopType(AOP_TYPE(IC_RESULT(ic))),
1404                    pic16_AopType(AOP_TYPE(IC_LEFT(ic))),
1405                    pic16_AopType(AOP_TYPE(IC_RIGHT(ic))));
1406
1407
1408     if( (size == 1) && ((lit & 0xff) == 0) ) {
1409       /* res = 0 - right */
1410       if (pic16_sameRegs(AOP(IC_RIGHT(ic)), AOP(IC_RESULT(ic))) ) {
1411         pic16_emitpcode(POC_COMF,  pic16_popGet(AOP(IC_RIGHT(ic)),0));
1412         pic16_emitpcode(POC_INCF,  pic16_popGet(AOP(IC_RIGHT(ic)),0));
1413       } else { 
1414         pic16_emitpcode(POC_COMFW,  pic16_popGet(AOP(IC_RIGHT(ic)),0));
1415         pic16_emitpcode(POC_MOVWF,  pic16_popGet(AOP(IC_RESULT(ic)),0));
1416         pic16_emitpcode(POC_INCF,   pic16_popGet(AOP(IC_RESULT(ic)),0));
1417       }
1418       goto release;
1419     }
1420
1421     pic16_emitpcode(POC_MOVFW,  pic16_popGet(AOP(IC_RIGHT(ic)),0));
1422     pic16_emitpcode(POC_SUBLW, pic16_popGetLit(lit & 0xff));    
1423     pic16_emitpcode(POC_MOVWF,pic16_popGet(AOP(IC_RESULT(ic)),0));
1424
1425
1426     offset = 1;
1427     while(--size) {
1428       lit >>= 8;
1429
1430       if(size == 1) {
1431         /* This is the last byte in a multibyte subtraction 
1432          * There are a couple of tricks we can do by not worrying about 
1433          * propogating the carry */
1434         if(lit == 0xff) {
1435           /* 0xff - x == ~x */
1436           if(same) {
1437             pic16_emitpcode(POC_COMF,  pic16_popGet(AOP(IC_RESULT(ic)),offset));
1438             emitSKPC;
1439             pic16_emitpcode(POC_DECF,  pic16_popGet(AOP(IC_RESULT(ic)),offset));
1440           } else {
1441             pic16_emitpcode(POC_COMFW, pic16_popGet(AOP(IC_RIGHT(ic)),offset));
1442             pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(IC_RESULT(ic)),offset));
1443             emitSKPC;
1444             pic16_emitpcode(POC_DECF,  pic16_popGet(AOP(IC_RESULT(ic)),offset));
1445           }
1446         } else {
1447             pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(IC_RIGHT(ic)),offset));
1448             emitSKPC;
1449             pic16_emitpcode(POC_INCFW, pic16_popGet(AOP(IC_RIGHT(ic)),offset));
1450             pic16_emitpcode(POC_SUBLW, pic16_popGetLit(lit & 0xff));
1451             pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(IC_RESULT(ic)),offset));
1452         }
1453
1454         goto release;
1455       }
1456
1457       if(same) {
1458
1459         if(lit & 0xff) {
1460           pic16_emitpcode(POC_MOVLW, pic16_popGetLit(lit & 0xff));
1461           emitSKPC;
1462           pic16_emitpcode(POC_MOVLW, pic16_popGetLit((lit & 0xff)-1));
1463           pic16_emitpcode(POC_SUBWF,  pic16_popGet(AOP(IC_RESULT(ic)),offset));
1464         } else {
1465           emitSKPNC;
1466           pic16_emitpcode(POC_SUBWF,  pic16_popGet(AOP(IC_RESULT(ic)),offset));
1467
1468         }
1469       } else {
1470
1471         if(lit & 0xff) {
1472           pic16_emitpcode(POC_MOVLW, pic16_popGetLit(lit & 0xff));
1473           pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(IC_RESULT(ic)),offset));
1474         } else
1475           pic16_emitpcode(POC_CLRF, pic16_popGet(AOP(IC_RESULT(ic)),offset));
1476
1477         pic16_emitpcode(POC_MOVFW,  pic16_popGet(AOP(IC_RIGHT(ic)),offset));
1478         emitSKPC;
1479         pic16_emitpcode(POC_INCFSZW,pic16_popGet(AOP(IC_RIGHT(ic)),offset));
1480         pic16_emitpcode(POC_SUBWF,  pic16_popGet(AOP(IC_RESULT(ic)),offset));
1481       }
1482     }
1483   
1484
1485   } else {
1486
1487     DEBUGpic16_emitcode ("; ","line %d result %s, left %s, right %s",__LINE__,
1488                    pic16_AopType(AOP_TYPE(IC_RESULT(ic))),
1489                    pic16_AopType(AOP_TYPE(IC_LEFT(ic))),
1490                    pic16_AopType(AOP_TYPE(IC_RIGHT(ic))));
1491
1492     if(strcmp(pic16_aopGet(AOP(IC_LEFT(ic)),0,FALSE,FALSE),"a") == 0 ) {
1493       DEBUGpic16_emitcode ("; ***","%s  %d",__FUNCTION__,__LINE__);
1494       pic16_emitpcode(POC_SUBFW, pic16_popGet(AOP(IC_RIGHT(ic)),0));
1495       pic16_emitpcode(POC_SUBLW, pic16_popGetLit(0));
1496       pic16_emitpcode(POC_MOVWF,pic16_popGet(AOP(IC_RESULT(ic)),0));
1497     } else {
1498
1499       if ( AOP_TYPE(IC_LEFT(ic)) == AOP_ACC) {
1500         pic16_emitpcode(POC_SUBFW, pic16_popGet(AOP(IC_RIGHT(ic)),0));
1501         pic16_emitpcode(POC_SUBLW, pic16_popGetLit(0));
1502         if ( AOP_TYPE(IC_RESULT(ic)) != AOP_ACC)
1503           pic16_emitpcode(POC_MOVWF,pic16_popGet(AOP(IC_RESULT(ic)),0));
1504       } else {
1505
1506         DEBUGpic16_emitcode ("; ***","%s  %d",__FUNCTION__,__LINE__);
1507         if(AOP_TYPE(IC_RIGHT(ic)) != AOP_ACC) 
1508           pic16_emitpcode(POC_MOVFW,pic16_popGet(AOP(IC_RIGHT(ic)),0));
1509
1510         if (pic16_sameRegs(AOP(IC_LEFT(ic)), AOP(IC_RESULT(ic))) )
1511           pic16_emitpcode(POC_SUBWF, pic16_popGet(AOP(IC_LEFT(ic)),0));
1512         else {
1513           if( (AOP_TYPE(IC_LEFT(ic)) == AOP_IMMD) ||
1514               (AOP_TYPE(IC_LEFT(ic)) == AOP_LIT) ) {
1515             pic16_emitpcode(POC_SUBLW, pic16_popGet(AOP(IC_LEFT(ic)),0));
1516           } else {
1517             pic16_emitpcode(POC_SUBFW, pic16_popGet(AOP(IC_LEFT(ic)),0));
1518           }
1519           if ( AOP_TYPE(IC_RESULT(ic)) != AOP_ACC) {
1520             if ( AOP_TYPE(IC_RESULT(ic)) == AOP_CRY) {
1521               pic16_emitpcode(POC_BCF ,   pic16_popGet(AOP(IC_RESULT(ic)),0));
1522               emitSKPZ;
1523               pic16_emitpcode(POC_BSF ,   pic16_popGet(AOP(IC_RESULT(ic)),0));
1524             }else
1525               pic16_emitpcode(POC_MOVWF,pic16_popGet(AOP(IC_RESULT(ic)),0));
1526           }
1527         }
1528       }
1529     }
1530
1531     /*
1532       pic16_emitpcode(POC_MOVFW,  pic16_popGet(AOP(IC_RIGHT(ic)),0,FALSE,FALSE));
1533
1534       if (pic16_sameRegs(AOP(IC_LEFT(ic)), AOP(IC_RESULT(ic))) ) {
1535       pic16_emitpcode(POC_SUBFW,  pic16_popGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE));
1536       } else {
1537       pic16_emitpcode(POC_SUBFW,  pic16_popGet(AOP(IC_LEFT(ic)),0,FALSE,FALSE));
1538       pic16_emitpcode(POC_MOVWF,  pic16_popGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE));
1539       }
1540     */
1541     offset = 1;
1542     size--;
1543
1544     while(size--){
1545       if (!pic16_sameRegs(AOP(IC_LEFT(ic)), AOP(IC_RESULT(ic))) ) {
1546         pic16_emitpcode(POC_MOVFW,  pic16_popGet(AOP(IC_LEFT(ic)),offset));
1547         pic16_emitpcode(POC_MOVWF,  pic16_popGet(AOP(IC_RESULT(ic)),offset));
1548       }
1549       pic16_emitpcode(POC_MOVFW,  pic16_popGet(AOP(IC_RIGHT(ic)),offset));
1550       emitSKPC;
1551       pic16_emitpcode(POC_INCFSZW,pic16_popGet(AOP(IC_RIGHT(ic)),offset));
1552       pic16_emitpcode(POC_SUBWF,  pic16_popGet(AOP(IC_RESULT(ic)),offset));
1553
1554       offset++;
1555     }
1556
1557   }
1558
1559
1560   //    adjustArithmeticResult(ic);
1561         
1562  release:
1563   pic16_freeAsmop(IC_LEFT(ic),NULL,ic,(RESULTONSTACK(ic) ? FALSE : TRUE));
1564   pic16_freeAsmop(IC_RIGHT(ic),NULL,ic,(RESULTONSTACK(ic) ? FALSE : TRUE));
1565   pic16_freeAsmop(IC_RESULT(ic),NULL,ic,TRUE);
1566 }
1567 /*-----------------------------------------------------------------*
1568  * pic_genUMult8XLit_16 - unsigned multiplication of two 8-bit numbers.
1569  * 
1570  * 
1571  *-----------------------------------------------------------------*/
1572 void pic16_genUMult8XLit_16 (operand *left,
1573                              operand *right,
1574                              operand *result,
1575                              pCodeOpReg *result_hi)
1576
1577 {
1578
1579   unsigned int lit;
1580   unsigned int i,have_first_bit;
1581   int same;
1582   pCodeOp *temp;
1583
1584   if (AOP_TYPE(right) != AOP_LIT){
1585     fprintf(stderr,"%s %d - right operand is not a literal\n",__FILE__,__LINE__);
1586     exit(1);
1587   }
1588
1589
1590   if(!result_hi) {
1591     result_hi = PCOR(pic16_popGet(AOP(result),1));
1592   }
1593
1594   lit = (unsigned int)floatFromVal(AOP(right)->aopu.aop_lit);
1595   lit &= 0xff;
1596   pic16_emitcode(";","Unrolled 8 X 8 multiplication");
1597
1598   same = pic16_sameRegs(AOP(left), AOP(result));
1599
1600   if(same) {
1601     switch(lit) {
1602     case 0:
1603       pic16_emitpcode(POC_CLRF,  pic16_popGet(AOP(left),0));
1604       return;
1605     case 2:
1606       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1607       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));
1608       return;
1609     case 3:
1610       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1611       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));
1612       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));
1613       return;
1614     case 4:
1615       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1616       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));
1617       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));
1618       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));
1619       return;
1620     case 5:
1621       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1622       pic16_emitpcode(POC_ADDFW, pic16_popGet(AOP(left),0));  // W = 2*F
1623       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));  // F = 3*F
1624       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));  // F = 5*F
1625       return;
1626     case 6:
1627       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1628       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));
1629       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));
1630       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1631       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));
1632       return;
1633     case 7:
1634       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1635       pic16_emitpcode(POC_ADDFW, pic16_popGet(AOP(left),0));  // W = 2*F
1636       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));  // F = 3*F
1637       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));  // F = 5*F
1638       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));  // F = 7*F
1639       return;
1640     case 8:
1641       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1642       pic16_emitpcode(POC_ADDFW, pic16_popGet(AOP(left),0));  // W = 2*F
1643       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));  // F = 3*F
1644       pic16_emitpcode(POC_ADDFW, pic16_popGet(AOP(left),0));  // W = 5*F
1645       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));  // F = 8*F
1646       return;
1647     case 9:
1648       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1649       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));
1650       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));
1651       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1652       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));
1653       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));
1654       return;
1655     case 10:
1656       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1657       pic16_emitpcode(POC_ADDFW, pic16_popGet(AOP(left),0));  // W = 2*F
1658       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));  // F = 3*F
1659       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));  // F = 5*F
1660       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1661       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));
1662       return;
1663     case 11:
1664       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1665       pic16_emitpcode(POC_ADDFW, pic16_popGet(AOP(left),0));  // W = 2*F
1666       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));  // F = 3*F
1667       pic16_emitpcode(POC_ADDFW, pic16_popGet(AOP(left),0));  // W = 5*F
1668       pic16_emitpcode(POC_ADDFW, pic16_popGet(AOP(left),0));  // W = 8*F
1669       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));  // F = 11*F
1670       return;
1671     case 12:
1672       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1673       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));
1674       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));
1675       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1676       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));
1677       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1678       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));
1679       return;
1680     case 13:
1681       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1682       pic16_emitpcode(POC_ADDFW, pic16_popGet(AOP(left),0));  // W = 2*F
1683       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));  // F = 3*F
1684       pic16_emitpcode(POC_ADDFW, pic16_popGet(AOP(left),0));  // W = 5*F
1685       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));  // F = 8*F
1686       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));  // F = 13*F
1687       return;
1688     case 14:
1689       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1690       pic16_emitpcode(POC_ADDFW, pic16_popGet(AOP(left),0));  // W = 2*F
1691       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));  // F = 3*F
1692       pic16_emitpcode(POC_ADDFW, pic16_popGet(AOP(left),0));  // W = 5*F
1693       pic16_emitpcode(POC_ADDFW, pic16_popGet(AOP(left),0));  // W = 8*F
1694       pic16_emitpcode(POC_ADDFW, pic16_popGet(AOP(left),0));  // W = 11*F
1695       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(left),0));  // F = 14*F
1696       return;
1697     case 15:
1698       temp = pic16_popGetTempReg();
1699       if(!temp) {
1700         fprintf(stderr,"ERROR: unable to allocate register. %s:%d\n",__FUNCTION__,__LINE__);
1701         exit(1);
1702       }
1703       pic16_emitpcode(POC_SWAPFW, pic16_popGet(AOP(left),0));
1704       pic16_emitpcode(POC_MOVWF,  temp);
1705       pic16_emitpcode(POC_ANDLW,  pic16_popGetLit(0xf0));
1706       pic16_emitpcode(POC_MOVWF,  pic16_popGet(AOP(left),0));
1707       pic16_emitpcode(POC_SWAPFW, temp);
1708       pic16_emitpcode(POC_SUBWF,  pic16_popGet(AOP(left),0));
1709       pic16_popReleaseTempReg(temp);
1710       return;
1711     case 16:
1712       pic16_emitpcode(POC_SWAPFW, pic16_popGet(AOP(left),0));
1713       pic16_emitpcode(POC_ANDLW,  pic16_popGetLit(0xf0));
1714       pic16_emitpcode(POC_MOVWF,  pic16_popGet(AOP(left),0));
1715       return;
1716     case 17:
1717       pic16_emitpcode(POC_SWAPFW, pic16_popGet(AOP(left),0));
1718       pic16_emitpcode(POC_ANDLW,  pic16_popGetLit(0xf0));
1719       pic16_emitpcode(POC_ADDWF,  pic16_popGet(AOP(left),0));
1720       return;
1721     case 32:
1722       pic16_emitpcode(POC_SWAPF,  pic16_popGet(AOP(left),0));
1723       pic16_emitpcode(POC_RLCFW,  pic16_popGet(AOP(left),0));
1724       pic16_emitpcode(POC_ANDLW,  pic16_popGetLit(0xe0));
1725       pic16_emitpcode(POC_MOVWF,  pic16_popGet(AOP(left),0));
1726       return;
1727     case 64:
1728       pic16_emitpcode(POC_SWAPF,  pic16_popGet(AOP(left),0));
1729       pic16_emitpcode(POC_RLCF,   pic16_popGet(AOP(left),0));
1730       pic16_emitpcode(POC_RLCFW,  pic16_popGet(AOP(left),0));
1731       pic16_emitpcode(POC_ANDLW,  pic16_popGetLit(0xc0));
1732       pic16_emitpcode(POC_MOVWF,  pic16_popGet(AOP(left),0));
1733       return;
1734     case 128:
1735       pic16_emitpcode(POC_RRCFW,  pic16_popGet(AOP(left),0));
1736       pic16_emitpcode(POC_CLRF,   pic16_popGet(AOP(left),0));
1737       pic16_emitpcode(POC_RRCF,   pic16_popGet(AOP(left),0));
1738       return;
1739
1740     }
1741   } else {
1742
1743     switch(lit) {
1744     case 0:
1745       pic16_emitpcode(POC_CLRF,  pic16_popGet(AOP(result),0));
1746       pic16_emitpcode(POC_CLRF,  pic16_popCopyReg(result_hi));
1747       return;
1748     case 2:
1749       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1750       pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(result),0));
1751       pic16_emitpcode(POC_ADDWF, pic16_popGet(AOP(result),0));
1752       pic16_emitpcode(POC_CLRF,  pic16_popCopyReg(result_hi));
1753       pic16_emitpcode(POC_RLCF,  pic16_popCopyReg(result_hi));
1754       return;
1755     }
1756
1757   }
1758
1759   pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1760   pic16_emitpcode(POC_CLRF,  pic16_popGet(AOP(result),0));
1761   pic16_emitpcode(POC_CLRF,  pic16_popCopyReg(result_hi));
1762
1763   have_first_bit = 0;
1764   for(i=0; i<8; i++) {
1765
1766     if(lit & 1) {
1767       pic16_emitpcode(POC_ADDWF, pic16_popCopyReg(result_hi));
1768       have_first_bit = 1;
1769     }
1770
1771     if(have_first_bit) {
1772       pic16_emitpcode(POC_RRCF,  pic16_popCopyReg(result_hi));
1773       pic16_emitpcode(POC_RRCF,  pic16_popGet(AOP(result),0));
1774     }
1775
1776     lit >>= 1;
1777   }
1778
1779 }
1780
1781 /*-----------------------------------------------------------------*
1782  * genUMult8X8_16 - unsigned multiplication of two 8-bit numbers.
1783  * 
1784  * 
1785  *-----------------------------------------------------------------*/
1786 void pic16_genUMult8X8_16 (operand *left,
1787                            operand *right,
1788                            operand *result,
1789                            pCodeOpReg *result_hi)
1790
1791 {
1792
1793   int i;
1794   int looped = 1;
1795
1796   if(!result_hi) {
1797     result_hi = PCOR(pic16_popGet(AOP(result),1));
1798   }
1799
1800   if (AOP_TYPE(right) == AOP_LIT) {
1801     pic16_genUMult8XLit_16(left,right,result,result_hi);
1802     return;
1803   }
1804
1805   if(!looped) {
1806     pic16_emitcode(";","Unrolled 8 X 8 multiplication");
1807
1808     pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(right),0));
1809     pic16_emitpcode(POC_CLRF,  pic16_popGet(AOP(result),0));
1810     pic16_emitpcode(POC_CLRF,  pic16_popCopyReg(result_hi));
1811     emitCLRC;
1812
1813     for(i=0; i<8; i++) {
1814       pic16_emitpcode(POC_BTFSC,  pic16_newpCodeOpBit(pic16_aopGet(AOP(left),0,FALSE,FALSE),i,0));
1815       pic16_emitpcode(POC_ADDWF, pic16_popCopyReg(result_hi));
1816       pic16_emitpcode(POC_RRCF,  pic16_popCopyReg(result_hi));
1817       pic16_emitpcode(POC_RRCF,  pic16_popGet(AOP(result),0));
1818     }
1819
1820
1821     /*
1822       Here's another version that does the same thing and takes the 
1823       same number of instructions. The one above is slightly better
1824       because the entry instructions have a higher probability of
1825       being optimized out.
1826     */
1827     /*
1828       pic16_emitpcode(POC_CLRF,  pic16_popCopyReg(result_hi));
1829       pic16_emitpcode(POC_RRCFW, pic16_popGet(AOP(left),0));
1830       pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(result),0));
1831       pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(right),0));
1832
1833       for(i=0; i<8; i++) {
1834       emitSKPNC;
1835       pic16_emitpcode(POC_ADDWF, pic16_popCopyReg(result_hi));
1836       pic16_emitpcode(POC_RRCF,  pic16_popCopyReg(result_hi));
1837       pic16_emitpcode(POC_RRCF,  pic16_popGet(AOP(result),0));
1838       }
1839     */
1840
1841   } else {
1842     symbol  *tlbl = newiTempLabel(NULL);
1843     pCodeOp *temp;
1844
1845
1846     pic16_emitcode(";","Looped 8 X 8 multiplication");
1847
1848     pic16_emitpcode(POC_CLRF,  pic16_popGet(AOP(result),0));
1849     pic16_emitpcode(POC_CLRF,  pic16_popCopyReg(result_hi));
1850
1851     pic16_emitpcode(POC_BSF,   pic16_newpCodeOpBit(pic16_aopGet(AOP(result),0,FALSE,FALSE),7,0));
1852
1853     pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(right),0));
1854
1855     temp = pic16_popGetTempReg();
1856     pic16_emitpcode(POC_MOVWF, pic16_popCopyReg(PCOR(temp)));
1857
1858     pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1859
1860     pic16_emitpLabel(tlbl->key);
1861
1862     pic16_emitpcode(POC_RRCF,  pic16_popCopyReg(PCOR(temp)));
1863     emitSKPNC;
1864     pic16_emitpcode(POC_ADDWF, pic16_popCopyReg(result_hi));
1865
1866     pic16_emitpcode(POC_RRCF,  pic16_popCopyReg(result_hi));
1867     pic16_emitpcode(POC_RRCF,  pic16_popGet(AOP(result),0));
1868
1869     emitSKPC;
1870     pic16_emitpcode(POC_GOTO,  pic16_popGetLabel(tlbl->key));
1871
1872     pic16_popReleaseTempReg(temp);
1873
1874   }
1875 }
1876
1877 /*-----------------------------------------------------------------*
1878  * pic16_genSMult8X8_16 - signed multiplication of two 8-bit numbers
1879  *
1880  *  this routine will call the unsigned multiply routine and then
1881  * post-fix the sign bit.
1882  *-----------------------------------------------------------------*/
1883 void pic16_genSMult8X8_16 (operand *left,
1884                            operand *right,
1885                            operand *result,
1886                            pCodeOpReg *result_hi)
1887 {
1888
1889   if(!result_hi) {
1890     result_hi = PCOR(pic16_popGet(AOP(result),1));
1891   }
1892
1893   pic16_genUMult8X8_16(left,right,result,result_hi);
1894
1895   pic16_emitpcode(POC_BTFSC, pic16_newpCodeOpBit(pic16_aopGet(AOP(left),0,FALSE,FALSE),7,0));
1896   pic16_emitpcode(POC_SUBWF, pic16_popCopyReg(result_hi));
1897   pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
1898   pic16_emitpcode(POC_BTFSC, pic16_newpCodeOpBit(pic16_aopGet(AOP(right),0,FALSE,FALSE),7,0));
1899   pic16_emitpcode(POC_SUBWF, pic16_popGet(AOP(result),1));
1900   
1901 }
1902
1903 /*-----------------------------------------------------------------*
1904  * pic16_genMult8X8_8 - multiplication of two 8-bit numbers
1905  *
1906  *  this routine will call the unsigned multiply 8X8=>16 routine and
1907  * then throw away the high byte of the result.
1908  *
1909  *-----------------------------------------------------------------*/
1910 void pic16_genMult8X8_8 (operand *left,
1911                          operand *right,
1912                          operand *result)
1913 {
1914   pCodeOp *result_hi = pic16_popGetTempReg();
1915
1916   if (AOP_TYPE(right) == AOP_LIT)
1917     pic16_genUMult8XLit_16(left,right,result,PCOR(result_hi));
1918   else
1919     pic16_genUMult8X8_16(left,right,result,PCOR(result_hi));
1920
1921   pic16_popReleaseTempReg(result_hi);
1922 }
1923 #if 0
1924 /*-----------------------------------------------------------------*/
1925 /* constMult - generates code for multiplication by a constant     */
1926 /*-----------------------------------------------------------------*/
1927 void genMultConst(unsigned C)
1928 {
1929
1930   unsigned lit;
1931   unsigned sr3; // Shift right 3
1932   unsigned mask;
1933
1934   int size = 1;
1935
1936   /*
1937     Convert a string of 3 binary 1's in the lit into
1938     0111 = 1000 - 1;
1939   */
1940
1941   mask = 7 << ( (size*8) - 3);
1942   lit = C;
1943   sr3 = 0;
1944
1945   while(mask < (1<<size*8)) {
1946
1947     if( (mask & lit) == lit) {
1948       unsigned lsb;
1949
1950       /* We found 3 (or more) consecutive 1's */
1951
1952       lsb = mask & ~(mask & (mask-1));  // lsb of mask.
1953
1954       consecutive_bits = ((lit + lsb) & lit) ^ lit;
1955
1956       lit ^= consecutive_bits;
1957
1958       mask <<= 3;
1959
1960       sr3 |= (consecutive + lsb);
1961
1962     }
1963
1964     mask >>= 1;
1965
1966   }
1967
1968 }
1969
1970 #endif