X-Git-Url: https://git.gag.com/?a=blobdiff_plain;f=src%2Fds390%2Fgen.c;h=e5670acc03530c9791114e466cfdc17316beaeed;hb=353ff1ac97be2a4c6fb07f88607dffaebe20590e;hp=4c9de425e4e0ca9b35ff75f3348a9669fccc2217;hpb=cf4a675d7443245fea639d0b7a1b8b6b4b8265a9;p=fw%2Fsdcc diff --git a/src/ds390/gen.c b/src/ds390/gen.c index 4c9de425..e5670acc 100644 --- a/src/ds390/gen.c +++ b/src/ds390/gen.c @@ -31,28 +31,12 @@ #include #include "common.h" +#include "main.h" #include "ralloc.h" #include "gen.h" #include "SDCCglobl.h" #include "newalloc.h" -#ifdef HAVE_SYS_ISA_DEFS_H -#include -#else -#ifdef HAVE_MACHINE_ENDIAN_H -#include -#else -#ifdef HAVE_ENDIAN_H -#include -#else -#if !defined(__BORLANDC__) && !defined(_MSC_VER) && !defined(__MINGW32__) && !defined(__CYGWIN__) -#warning "Cannot determine ENDIANESS of this machine assuming LITTLE_ENDIAN" -#warning "If you running sdcc on an INTEL 80x86 Platform you are okay" -#endif -#endif -#endif -#endif - #define BETTER_LITERAL_SHIFT char *aopLiteral (value * val, int offset); @@ -96,6 +80,7 @@ static struct short dptrInUse; short dptr1InUse; set *sendSet; + iCode *current_iCode; } _G; @@ -109,14 +94,9 @@ static void saveRBank (int, iCode *, bool); (IC_RESULT(x) && IC_RESULT(x)->aop && \ IC_RESULT(x)->aop->type == AOP_STK ) -/* #define MOVA(x) if (strcmp(x,"a") && strcmp(x,"acc")) emitcode("mov","a,%s",x); */ -#define MOVA(x) { char *_mova_tmp = strdup(x); \ - if (strcmp(_mova_tmp,"a") && strcmp(_mova_tmp,"acc")) \ - { \ - emitcode("mov","a,%s",_mova_tmp); \ - } \ - free(_mova_tmp); \ - } +#define MOVA(x) _movA(x) +#define MOVB(x) _movB(x) + #define CLRC emitcode("clr","c") #define SETC emitcode("setb","c") @@ -152,6 +132,9 @@ static unsigned char SRMask[] = emitcode ("","!tlabeldef",lbl->key+100); \ }} +static int _currentDPS; /* Current processor DPS. */ +static int _desiredDPS; /* DPS value compiler thinks we should be using. */ +static int _lazyDPS = 0; /* if non-zero, we are doing lazy evaluation of DPS changes. */ /*-----------------------------------------------------------------*/ /* emitcode - writes the code into a file : for now it is simple */ @@ -199,17 +182,43 @@ emitcode (char *inst, char *fmt,...) lineCurr->isInline = _G.inLine; lineCurr->isDebug = _G.debugLine; + lineCurr->ic = _G.current_iCode; + lineCurr->aln = ds390newAsmLineNode(_currentDPS); va_end (ap); } +// +// Move the passed value into A unless it is already there. +// +static void +_movA(const char *s) +{ + if (strcmp(s,"a") && strcmp(s,"acc")) + { + emitcode("mov","a,%s",s); + } +} + +// +// Move the passed value into B unless it is already there. +// +static void +_movB(const char *s) +{ + if (strcmp(s,"b")) + { + emitcode("mov","b,%s",s); + } +} + /*-----------------------------------------------------------------*/ /* getFreePtr - returns r0 or r1 whichever is free or can be pushed */ /*-----------------------------------------------------------------*/ static regs * getFreePtr (iCode * ic, asmop ** aopp, bool result) { - bool r0iu = FALSE, r1iu = FALSE; - bool r0ou = FALSE, r1ou = FALSE; + bool r0iu, r1iu; + bool r0ou, r1ou; /* the logic: if r0 & r1 used in the instruction then we are in trouble otherwise */ @@ -291,6 +300,8 @@ endOfWorld: werror (E_INTERNAL_ERROR, __FILE__, __LINE__, "getFreePtr should never reach here"); exit (1); + + return NULL; // notreached, but makes compiler happy. } /*-----------------------------------------------------------------*/ @@ -306,9 +317,6 @@ newAsmop (short type) return aop; } -static int _currentDPS; /* Current processor DPS. */ -static int _desiredDPS; /* DPS value compiler thinks we should be using. */ -static int _lazyDPS = 0; /* if non-zero, we are doing lazy evaluation of DPS changes. */ /*-----------------------------------------------------------------*/ /* genSetDPTR: generate code to select which DPTR is in use (zero */ @@ -434,6 +442,72 @@ pointerCode (sym_link * etype) } +/*-----------------------------------------------------------------*/ +/* leftRightUseAcc - returns size of accumulator use by operands */ +/*-----------------------------------------------------------------*/ +static int +leftRightUseAcc(iCode *ic) +{ + operand *op; + int size; + int accuseSize = 0; + int accuse = 0; + + if (!ic) + { + werror (E_INTERNAL_ERROR, __FILE__, __LINE__, + "null iCode pointer"); + return 0; + } + + if (ic->op == IFX) + { + op = IC_COND (ic); + if (IS_SYMOP (op) && OP_SYMBOL (op) && OP_SYMBOL (op)->accuse) + { + accuse = 1; + size = getSize (OP_SYMBOL (op)->type); + if (size>accuseSize) + accuseSize = size; + } + } + else if (ic->op == JUMPTABLE) + { + op = IC_JTCOND (ic); + if (IS_SYMOP (op) && OP_SYMBOL (op) && OP_SYMBOL (op)->accuse) + { + accuse = 1; + size = getSize (OP_SYMBOL (op)->type); + if (size>accuseSize) + accuseSize = size; + } + } + else + { + op = IC_LEFT (ic); + if (IS_SYMOP (op) && OP_SYMBOL (op) && OP_SYMBOL (op)->accuse) + { + accuse = 1; + size = getSize (OP_SYMBOL (op)->type); + if (size>accuseSize) + accuseSize = size; + } + op = IC_RIGHT (ic); + if (IS_SYMOP (op) && OP_SYMBOL (op) && OP_SYMBOL (op)->accuse) + { + accuse = 1; + size = getSize (OP_SYMBOL (op)->type); + if (size>accuseSize) + accuseSize = size; + } + } + + if (accuseSize) + return accuseSize; + else + return accuse; +} + /*-----------------------------------------------------------------*/ /* aopForSym - for a true symbol */ /*-----------------------------------------------------------------*/ @@ -442,10 +516,17 @@ aopForSym (iCode * ic, symbol * sym, bool result, bool useDP2) { asmop *aop; memmap *space = SPEC_OCLS (sym->etype); + int accuse = leftRightUseAcc (ic); /* if already has one */ if (sym->aop) - return sym->aop; + { + if ((sym->aop->type == AOP_DPTR && useDP2) + || (sym->aop->type == AOP_DPTR2 && !useDP2)) + sym->aop = NULL; + else + return sym->aop; + } /* assign depending on the storage class */ /* if it is on the stack or indirectly addressable */ @@ -463,10 +544,10 @@ aopForSym (iCode * ic, symbol * sym, bool result, bool useDP2) if (sym->onStack) { - if (_G.accInUse) + if (_G.accInUse || accuse) emitcode ("push", "acc"); - if (_G.bInUse) + if (_G.bInUse || (accuse>1)) emitcode ("push", "b"); emitcode ("mov", "a,_bp"); @@ -477,10 +558,10 @@ aopForSym (iCode * ic, symbol * sym, bool result, bool useDP2) emitcode ("mov", "%s,a", aop->aopu.aop_ptr->name); - if (_G.bInUse) + if (_G.bInUse || (accuse>1)) emitcode ("pop", "b"); - if (_G.accInUse) + if (_G.accInUse || accuse) emitcode ("pop", "acc"); } else @@ -514,14 +595,20 @@ aopForSym (iCode * ic, symbol * sym, bool result, bool useDP2) if (stack_val < 0 && stack_val > -5) { /* between -5 & -1 */ if (useDP2) { if (options.model == MODEL_FLAT24) - emitcode ("mov", "dpx1,#!constbyte", (options.stack_loc >> 16) & 0xff); - TR_DPTR("#2"); + { + emitcode ("mov", "dpx1,#!constbyte", + (options.stack_loc >> 16) & 0xff); + } emitcode ("mov", "dph1,_bpx+1"); + emitcode ("mov", "dpl1,_bpx"); emitcode ("mov","dps,#1"); } else { if (options.model == MODEL_FLAT24) - emitcode ("mov", "dpx,#!constbyte", (options.stack_loc >> 16) & 0xff); + { + emitcode ("mov", "dpx,#!constbyte", + (options.stack_loc >> 16) & 0xff); + } emitcode ("mov", "dph,_bpx+1"); emitcode ("mov", "dpl,_bpx"); } @@ -533,10 +620,10 @@ aopForSym (iCode * ic, symbol * sym, bool result, bool useDP2) emitcode("mov","dps,#0"); } } else { - if (_G.accInUse) + if (_G.accInUse || accuse) emitcode ("push", "acc"); - if (_G.bInUse) + if (_G.bInUse || (accuse>1)) emitcode ("push", "b"); emitcode ("mov", "a,_bpx"); @@ -547,21 +634,26 @@ aopForSym (iCode * ic, symbol * sym, bool result, bool useDP2) emitcode ("subb","a,#!constbyte",(stack_val >> 8) & 0xff); if (useDP2) { if (options.model == MODEL_FLAT24) - emitcode ("mov", "dpx1,#!constbyte", (options.stack_loc >> 16) & 0xff); - TR_DPTR("#2"); + { + emitcode ("mov", "dpx1,#!constbyte", + (options.stack_loc >> 16) & 0xff); + } emitcode ("mov", "dph1,a"); emitcode ("mov", "dpl1,b"); } else { if (options.model == MODEL_FLAT24) - emitcode ("mov", "dpx,#!constbyte", (options.stack_loc >> 16) & 0xff); + { + emitcode ("mov", "dpx,#!constbyte", + (options.stack_loc >> 16) & 0xff); + } emitcode ("mov", "dph,a"); emitcode ("mov", "dpl,b"); } - if (_G.bInUse) + if (_G.bInUse || (accuse>1)) emitcode ("pop", "b"); - if (_G.accInUse) + if (_G.accInUse || accuse) emitcode ("pop", "acc"); } sym->aop = aop = newAsmop ((short) (useDP2 ? AOP_DPTR2 : AOP_DPTR)); @@ -587,14 +679,14 @@ aopForSym (iCode * ic, symbol * sym, bool result, bool useDP2) } /* special case for a function */ - if (IS_FUNC (sym->type)) + if (IS_FUNC (sym->type) && !(sym->isitmp)) { sym->aop = aop = newAsmop (AOP_IMMD); - aop->aopu.aop_immd.aop_immd1 = Safe_strdup(sym->rname); + aop->aopu.aop_immd.aop_immd1 = Safe_strdup(sym->rname); aop->size = FPTRSIZE; return aop; } - + /* only remaining is far space */ /* in which case DPTR gets the address */ sym->aop = aop = newAsmop ((short) (useDP2 ? AOP_DPTR2 : AOP_DPTR)); @@ -656,7 +748,7 @@ aopForRemat (symbol * sym) "(%s %c 0x%04x)", OP_SYMBOL (IC_LEFT (ic))->rname, val >= 0 ? '+' : '-', - abs (val) & 0xffff); + abs (val) & 0xffffff); } else { @@ -780,6 +872,14 @@ operandsEqu (operand * op1, operand * op2) (sym2->usl.spillLoc == sym1)) return TRUE; + /* are they spilt to the same location */ + if (IS_ITEMP (op2) && + IS_ITEMP (op1) && + sym2->isspilt && + sym1->isspilt && + (sym1->usl.spillLoc == sym2->usl.spillLoc)) + return TRUE; + return FALSE; } @@ -839,13 +939,23 @@ aopOp (operand * op, iCode * ic, bool result, bool useDP2) /* if already has a asmop then continue */ if (op->aop) - return; + { + if ((op->aop->type == AOP_DPTR && useDP2) + || (op->aop->type == AOP_DPTR2 && !useDP2)) + op->aop = NULL; + else + return; + } /* if the underlying symbol has a aop */ if (IS_SYMOP (op) && OP_SYMBOL (op)->aop) { op->aop = OP_SYMBOL (op)->aop; - return; + if ((op->aop->type == AOP_DPTR && useDP2) + || (op->aop->type == AOP_DPTR2 && !useDP2)) + op->aop = NULL; + else + return; } /* if this is a true symbol */ @@ -924,13 +1034,22 @@ aopOp (operand * op, iCode * ic, bool result, bool useDP2) aop->aopu.dptr = sym->dptr; return ; } - /* else spill location */ - if (sym->usl.spillLoc && getSize(sym->type) != getSize(sym->usl.spillLoc->type)) { - /* force a new aop if sizes differ */ - sym->usl.spillLoc->aop = NULL; - } - sym->aop = op->aop = aop = - aopForSym (ic, sym->usl.spillLoc, result, useDP2); + + if (sym->usl.spillLoc) + { + if (getSize(sym->type) != getSize(sym->usl.spillLoc->type)) + { + /* force a new aop if sizes differ */ + sym->usl.spillLoc->aop = NULL; + } + sym->aop = op->aop = aop = + aopForSym (ic, sym->usl.spillLoc, result, useDP2); + aop->size = getSize (sym->type); + return; + } + + /* else must be a dummy iTemp */ + sym->aop = op->aop = aop = newAsmop (AOP_DUMMY); aop->size = getSize (sym->type); return; } @@ -1072,20 +1191,24 @@ dealloc: } } -/*------------------------------------------------------------------*/ -/* aopGet - for fetching value of the aop */ -/* */ -/* Set canClobberACC if you are sure it is OK to clobber the value */ -/* in the accumulator. Set it FALSE otherwise; FALSE is always safe, */ -/* just less efficient. */ -/*------------------------------------------------------------------*/ +#define DEFAULT_ACC_WARNING 0 +static int saveAccWarn = DEFAULT_ACC_WARNING; + +/*-------------------------------------------------------------------*/ +/* aopGet - for fetching value of the aop */ +/* */ +/* Set saveAcc to NULL if you are sure it is OK to clobber the value */ +/* in the accumulator. Set it to the name of a free register */ +/* if acc must be preserved; the register will be used to preserve */ +/* acc temporarily and to return the result byte. */ +/*-------------------------------------------------------------------*/ static char * -aopGet (asmop * aop, - int offset, - bool bit16, - bool dname, - bool canClobberACC) +aopGet (asmop *aop, + int offset, + bool bit16, + bool dname, + char *saveAcc) { /* offset is greater than size then zero */ @@ -1096,6 +1219,8 @@ aopGet (asmop * aop, /* depending on type */ switch (aop->type) { + case AOP_DUMMY: + return zero; case AOP_R0: case AOP_R1: @@ -1131,11 +1256,18 @@ aopGet (asmop * aop, if (aop->type == AOP_DPTR2) { genSetDPTR (1); - if (!canClobberACC) - { - TR_AP("#1"); - emitcode ("xch", "a, %s", DP2_RESULT_REG); - } + } + + if (saveAcc) + { + TR_AP("#1"); +// if (aop->type != AOP_DPTR2) +// { +// if (saveAccWarn) { fprintf(stderr, "saveAcc for DPTR...\n"); } +// emitcode(";", "spanky: saveAcc for DPTR"); +// } + + emitcode ("xch", "a, %s", saveAcc); } _flushLazyDPS (); @@ -1166,12 +1298,18 @@ aopGet (asmop * aop, if (aop->type == AOP_DPTR2) { genSetDPTR (0); - if (!canClobberACC) - { + } + + if (saveAcc) + { TR_AP("#2"); - emitcode ("xch", "a, %s", DP2_RESULT_REG); - return DP2_RESULT_REG; - } + emitcode ("xch", "a, %s", saveAcc); +// if (strcmp(saveAcc, "_ap")) +// { +// emitcode(";", "spiffy: non _ap return from aopGet."); +// } + + return saveAcc; } return (dname ? "acc" : "a"); @@ -1264,6 +1402,8 @@ aopGet (asmop * aop, werror (E_INTERNAL_ERROR, __FILE__, __LINE__, "aopget got unsupported aop->type"); exit (1); + + return NULL; // not reached, but makes compiler happy. } /*-----------------------------------------------------------------*/ /* aopPut - puts a string for a aop */ @@ -1282,6 +1422,10 @@ aopPut (asmop * aop, char *s, int offset) /* depending on where it is ofcourse */ switch (aop->type) { + case AOP_DUMMY: + MOVA (s); /* read s in case it was volatile */ + break; + case AOP_DIR: if (offset) { @@ -1559,62 +1703,20 @@ reAdjustPreg (asmop * aop) * thus avoiding touching A right before the div. \ */ \ D(emitcode(";", "DS80C390 div bug: rearranged ops.");); \ - L = aopGet(AOP(LEFT),0,FALSE,FALSE,TRUE); \ + L = aopGet(AOP(LEFT),0,FALSE,FALSE,NULL); \ MOVA(L); \ - emitcode("mov","b,%s",aopGet(AOP(RIGHT),0,FALSE,FALSE,FALSE));\ + L = aopGet(AOP(RIGHT),0,FALSE,FALSE,"b"); \ + MOVB(L); \ } \ else \ { \ /* Just stuff in a nop after loading A. */ \ - emitcode("mov","b,%s",aopGet(AOP(RIGHT),0,FALSE,FALSE,FALSE));\ - L = aopGet(AOP(LEFT),0,FALSE,FALSE,TRUE); \ + emitcode("mov","b,%s",aopGet(AOP(RIGHT),0,FALSE,FALSE,NULL));\ + L = aopGet(AOP(LEFT),0,FALSE,FALSE,NULL); \ MOVA(L); \ emitcode("nop", "; workaround for DS80C390 div bug."); \ } -/*-----------------------------------------------------------------*/ -/* genNotFloat - generates not for float operations */ -/*-----------------------------------------------------------------*/ -static void -genNotFloat (operand * op, operand * res) -{ - int size, offset; - char *l; - symbol *tlbl; - - D (emitcode (";", "genNotFloat "); - ); - - /* we will put 127 in the first byte of - the result */ - aopPut (AOP (res), "#127", 0); - size = AOP_SIZE (op) - 1; - offset = 1; - - _startLazyDPSEvaluation (); - l = aopGet (op->aop, offset++, FALSE, FALSE, TRUE); - MOVA (l); - - while (size--) - { - emitcode ("orl", "a,%s", - aopGet (op->aop, - offset++, FALSE, FALSE, FALSE)); - } - _endLazyDPSEvaluation (); - - tlbl = newiTempLabel (NULL); - aopPut (res->aop, one, 1); - emitcode ("jz", "!tlabel", (tlbl->key + 100)); - aopPut (res->aop, zero, 1); - emitcode ("", "!tlabeldef", (tlbl->key + 100)); - - size = res->aop->size - 2; - offset = 2; - /* put zeros in the rest */ - while (size--) - aopPut (res->aop, zero, offset++); -} /*-----------------------------------------------------------------*/ /* opIsGptr: returns non-zero if the passed operand is */ @@ -1719,22 +1821,28 @@ toBoolean (operand * oper) if (AOP_NEEDSACC (oper) && size) { usedB = TRUE; - emitcode ("push", "b"); - emitcode ("mov", "b, %s", aopGet (AOP (oper), 0, FALSE, FALSE, FALSE)); + if (_G.bInUse) + { + emitcode ("push", "b"); + } + MOVB (aopGet (AOP (oper), 0, FALSE, FALSE, NULL)); } else { - MOVA (aopGet (AOP (oper), 0, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (oper), 0, FALSE, FALSE, NULL)); } + while (size--) { if (usedB) { - emitcode ("orl", "b,%s", aopGet (AOP (oper), offset++, FALSE, FALSE, FALSE)); + emitcode ("orl", "b,%s", + aopGet (AOP (oper), offset++, FALSE, FALSE, NULL)); } else { - emitcode ("orl", "a,%s", aopGet (AOP (oper), offset++, FALSE, FALSE, FALSE)); + emitcode ("orl", "a,%s", + aopGet (AOP (oper), offset++, FALSE, FALSE, NULL)); } } _endLazyDPSEvaluation (); @@ -1742,7 +1850,11 @@ toBoolean (operand * oper) if (usedB) { emitcode ("mov", "a,b"); - emitcode ("pop", "b"); + if (_G.bInUse) + { + emitcode ("pop", "b"); + } + } } @@ -1754,14 +1866,12 @@ static void genNot (iCode * ic) { symbol *tlbl; - sym_link *optype = operandType (IC_LEFT (ic)); - D (emitcode (";", "genNot "); - ); + D (emitcode (";", "genNot ");); /* assign asmOps to operand & result */ aopOp (IC_LEFT (ic), ic, FALSE, FALSE); - aopOp (IC_RESULT (ic), ic, TRUE, AOP_TYPE (IC_LEFT (ic)) == AOP_DPTR); + aopOp (IC_RESULT (ic), ic, TRUE, AOP_USESDPTR(IC_LEFT (ic))); /* if in bit space then a special case */ if (AOP_TYPE (IC_LEFT (ic)) == AOP_CRY) @@ -1772,13 +1882,6 @@ genNot (iCode * ic) goto release; } - /* if type float then do float */ - if (IS_FLOAT (optype)) - { - genNotFloat (IC_LEFT (ic), IC_RESULT (ic)); - goto release; - } - toBoolean (IC_LEFT (ic)); tlbl = newiTempLabel (NULL); @@ -1803,13 +1906,12 @@ genCpl (iCode * ic) int size; symbol *tlbl; - D (emitcode (";", "genCpl "); - ); + D (emitcode (";", "genCpl ");); /* assign asmOps to operand & result */ aopOp (IC_LEFT (ic), ic, FALSE, FALSE); - aopOp (IC_RESULT (ic), ic, TRUE, AOP_TYPE (IC_LEFT (ic)) == AOP_DPTR); + aopOp (IC_RESULT (ic), ic, TRUE, AOP_USESDPTR(IC_LEFT (ic))); /* special case if in bit space */ if (AOP_TYPE (IC_RESULT (ic)) == AOP_CRY) { @@ -1821,7 +1923,7 @@ genCpl (iCode * ic) } tlbl=newiTempLabel(NULL); emitcode ("cjne", "%s,#0x01,%05d$", - aopGet(AOP(IC_LEFT(ic)), 0, FALSE,FALSE,TRUE), tlbl->key+100); + aopGet(AOP(IC_LEFT(ic)), 0, FALSE,FALSE,NULL), tlbl->key+100); emitcode ("", "%05d$:", tlbl->key+100); outBitC (IC_RESULT(ic)); goto release; @@ -1831,8 +1933,7 @@ genCpl (iCode * ic) _startLazyDPSEvaluation (); while (size--) { - char *l = aopGet (AOP (IC_LEFT (ic)), offset, FALSE, FALSE, TRUE); - MOVA (l); + MOVA (aopGet (AOP (IC_LEFT (ic)), offset, FALSE, FALSE, NULL)); emitcode ("cpl", "a"); aopPut (AOP (IC_RESULT (ic)), "a", offset++); } @@ -1863,12 +1964,12 @@ genUminusFloat (operand * op, operand * result) while (size--) { aopPut (AOP (result), - aopGet (AOP (op), offset, FALSE, FALSE, FALSE), + aopGet (AOP (op), offset, FALSE, FALSE, NULL), offset); offset++; } - MOVA(aopGet (AOP (op), offset, FALSE, FALSE, TRUE)); + MOVA(aopGet (AOP (op), offset, FALSE, FALSE, NULL)); emitcode ("cpl", "acc.7"); aopPut (AOP (result), "a", offset); @@ -1882,15 +1983,13 @@ static void genUminus (iCode * ic) { int offset, size; - sym_link *optype, *rtype; - - D (emitcode (";", "genUminus "); - ); + sym_link *optype; + D (emitcode (";", "genUminus ");); /* assign asmops */ aopOp (IC_LEFT (ic), ic, FALSE, FALSE); - aopOp (IC_RESULT (ic), ic, TRUE, AOP_TYPE (IC_LEFT (ic)) == AOP_DPTR); + aopOp (IC_RESULT (ic), ic, TRUE, (AOP_TYPE(IC_LEFT (ic)) == AOP_DPTR)); /* if both in bit space then special case */ @@ -1905,7 +2004,6 @@ genUminus (iCode * ic) } optype = operandType (IC_LEFT (ic)); - rtype = operandType (IC_RESULT (ic)); /* if float then do float stuff */ if (IS_FLOAT (optype)) @@ -1920,7 +2018,7 @@ genUminus (iCode * ic) _startLazyDPSEvaluation (); while (size--) { - char *l = aopGet (AOP (IC_LEFT (ic)), offset, FALSE, FALSE, TRUE); + char *l = aopGet (AOP (IC_LEFT (ic)), offset, FALSE, FALSE, NULL); if (!strcmp (l, "a")) { if (offset == 0) @@ -1941,7 +2039,7 @@ genUminus (iCode * ic) /* if any remaining bytes in the result */ /* we just need to propagate the sign */ - if ((size = (AOP_SIZE (IC_RESULT (ic)) - AOP_SIZE (IC_LEFT (ic))))) + if ((size = (AOP_SIZE(IC_RESULT(ic)) - AOP_SIZE(IC_LEFT(ic)))) != 0) { emitcode ("rlc", "a"); emitcode ("subb", "a,acc"); @@ -2008,12 +2106,15 @@ saveRegisters (iCode * lic) /* if the registers have been saved already then do nothing */ - if (ic->regsSaved || IFFUNC_ISNAKED(OP_SYM_TYPE(IC_LEFT(ic)))) return ; + if (ic->regsSaved + || (IS_SYMOP(IC_LEFT(ic)) && IFFUNC_ISNAKED(OP_SYM_TYPE(IC_LEFT(ic))) && !TARGET_IS_DS400) ) + return ; /* special case if DPTR alive across a function call then must save it even though callee saves */ - if (IFFUNC_CALLEESAVES(OP_SYMBOL (IC_LEFT (ic))->type)) { - int i =0; + if (IS_SYMOP(IC_LEFT(ic)) && + IFFUNC_CALLEESAVES(OP_SYMBOL (IC_LEFT (ic))->type)) { + int i; rsave = newBitVect(ic->rMask->size); for (i = DPL_IDX ; i <= B_IDX ; i++ ) { if (bitVectBitValue(ic->rMask,i)) @@ -2068,7 +2169,7 @@ unsaveRegisters (iCode * ic) bitVect *rsave; if (IFFUNC_CALLEESAVES(OP_SYMBOL (IC_LEFT (ic))->type)) { - int i =0; + int i; rsave = newBitVect(ic->rMask->size); for (i = DPL_IDX ; i <= B_IDX ; i++ ) { if (bitVectBitValue(ic->rMask,i)) @@ -2095,7 +2196,7 @@ pushSide (operand * oper, int size) _startLazyDPSEvaluation (); while (size--) { - char *l = aopGet (AOP (oper), offset++, FALSE, TRUE, FALSE); + char *l = aopGet (AOP (oper), offset++, FALSE, TRUE, NULL); if (AOP_TYPE (oper) != AOP_REG && AOP_TYPE (oper) != AOP_DIR && strcmp (l, "a")) @@ -2117,7 +2218,24 @@ assignResultValue (operand * oper) { int offset = 0; int size = AOP_SIZE (oper); + bool pushedAcc = FALSE; + if (size == fReturnSizeDS390) + { + /* I don't think this case can ever happen... */ + /* ACC is the last part of this. If writing the result + * uses AC, we must preserve it. + */ + if (AOP_NEEDSACC(oper)) + { + emitcode(";", "assignResultValue special case for ACC."); + emitcode("push", "acc"); + pushedAcc = TRUE; + size--; + } + } + + _startLazyDPSEvaluation (); while (size--) { @@ -2125,6 +2243,12 @@ assignResultValue (operand * oper) offset++; } _endLazyDPSEvaluation (); + + if (pushedAcc) + { + emitcode("pop", "acc"); + aopPut(AOP(oper), "a", offset); + } } @@ -2152,9 +2276,8 @@ genXpush (iCode * ic) while (size--) { - char *l = aopGet (AOP (IC_LEFT (ic)), - offset++, FALSE, FALSE, TRUE); - MOVA (l); + MOVA (aopGet (AOP (IC_LEFT (ic)), + offset++, FALSE, FALSE, NULL)); emitcode ("movx", "@%s,a", r->name); emitcode ("inc", "%s", r->name); @@ -2169,7 +2292,7 @@ genXpush (iCode * ic) } /*-----------------------------------------------------------------*/ -/* genIpush - genrate code for pushing this gets a little complex */ +/* genIpush - generate code for pushing this gets a little complex */ /*-----------------------------------------------------------------*/ static void genIpush (iCode * ic) @@ -2195,7 +2318,7 @@ genIpush (iCode * ic) _startLazyDPSEvaluation (); while (size--) { - l = aopGet (AOP (IC_LEFT (ic)), offset++, FALSE, TRUE, TRUE); + l = aopGet (AOP (IC_LEFT (ic)), offset++, FALSE, TRUE, NULL); if (*l == '#') { MOVA (l); @@ -2229,16 +2352,18 @@ genIpush (iCode * ic) _startLazyDPSEvaluation (); while (size--) { - l = aopGet (AOP (IC_LEFT (ic)), offset++, FALSE, TRUE, FALSE); + l = aopGet (AOP (IC_LEFT (ic)), offset++, FALSE, TRUE, NULL); if (AOP_TYPE (IC_LEFT (ic)) != AOP_REG && AOP_TYPE (IC_LEFT (ic)) != AOP_DIR && - strcmp (l, "a")) + strcmp (l, "acc")) { emitcode ("mov", "a,%s", l); emitcode ("push", "acc"); } else - emitcode ("push", "%s", l); + { + emitcode ("push", "%s", l); + } } _endLazyDPSEvaluation (); @@ -2268,7 +2393,7 @@ genIpop (iCode * ic) while (size--) { emitcode ("pop", "%s", aopGet (AOP (IC_LEFT (ic)), offset--, - FALSE, TRUE, TRUE)); + FALSE, TRUE, NULL)); } _endLazyDPSEvaluation (); @@ -2434,7 +2559,7 @@ static void genSend(set *sendSet) } while (size--) { char *l = aopGet (AOP (IC_LEFT (sic)), offset, - FALSE, FALSE, TRUE); + FALSE, FALSE, NULL); if (strcmp (l, fReturn[offset])) { emitcode ("mov", "%s,%s", fReturn[offset], @@ -2449,7 +2574,7 @@ static void genSend(set *sendSet) aopOp (IC_LEFT (sic), sic, FALSE, TRUE); while (size--) { emitcode ("mov","b1_%d,%s",rb1_count++,aopGet (AOP (IC_LEFT (sic)), offset++, - FALSE, FALSE, TRUE)); + FALSE, FALSE, NULL)); } freeAsmop (IC_LEFT (sic), NULL, sic, TRUE); } @@ -2457,6 +2582,18 @@ static void genSend(set *sendSet) } } +static void +adjustEsp(const char *reg) +{ + emitcode ("anl","%s,#3", reg); + if (TARGET_IS_DS400) + { + emitcode ("orl","%s,#!constbyte", + reg, + (options.stack_loc >> 8) & 0xff); + } +} + /*-----------------------------------------------------------------*/ /* genCall - generates a call statement */ /*-----------------------------------------------------------------*/ @@ -2473,7 +2610,7 @@ genCall (iCode * ic) the same register bank then we need to save the destination registers on the stack */ dtype = operandType (IC_LEFT (ic)); - if (currFunc && dtype && !IFFUNC_ISNAKED(dtype) && + if (currFunc && dtype && (!IFFUNC_ISNAKED(dtype) || TARGET_IS_DS400) && (FUNC_REGBANK (currFunc->type) != FUNC_REGBANK (dtype)) && IFFUNC_ISISR (currFunc->type)) { @@ -2542,9 +2679,16 @@ genCall (iCode * ic) if (size > 1) { emitcode ("mov", "b,%s", fReturn[1]); + _G.bInUse++; } + _G.accInUse++; aopOp (IC_RESULT (ic), ic, FALSE, FALSE); + _G.accInUse--; + + if (size > 1) + _G.bInUse--; + aopPut (AOP (IC_RESULT (ic)), "a", 0); if (size > 1) @@ -2555,9 +2699,9 @@ genCall (iCode * ic) } else { - _G.accInUse++; + _G.bInUse++; aopOp (IC_RESULT (ic), ic, FALSE, TRUE); - _G.accInUse--; + _G.bInUse--; assignResultValue (IC_RESULT (ic)); @@ -2582,7 +2726,7 @@ genCall (iCode * ic) emitcode ("subb","a,#!constbyte",ic->parmBytes & 0xff); emitcode ("mov","sp,a"); emitcode ("mov","a,esp"); - emitcode ("anl","a,#3"); + adjustEsp("a"); emitcode ("subb","a,#!constbyte",(ic->parmBytes >> 8) & 0xff); emitcode ("mov","esp,a"); UNPROTECT_SP; @@ -2629,7 +2773,7 @@ genPcall (iCode * ic) the same register bank then we need to save the destination registers on the stack */ dtype = operandType (IC_LEFT (ic)); - if (currFunc && dtype && !IFFUNC_ISNAKED(dtype) && + if (currFunc && dtype && (!IFFUNC_ISNAKED(dtype) || TARGET_IS_DS400) && IFFUNC_ISISR (currFunc->type) && (FUNC_REGBANK (currFunc->type) != FUNC_REGBANK (dtype))) { saveRBank (FUNC_REGBANK (dtype), ic, TRUE); @@ -2700,7 +2844,7 @@ genPcall (iCode * ic) emitcode ("subb","a,#!constbyte",ic->parmBytes & 0xff); emitcode ("mov","sp,a"); emitcode ("mov","a,esp"); - emitcode ("anl","a,#3"); + adjustEsp("a"); emitcode ("subb","a,#!constbyte",(ic->parmBytes >> 8) & 0xff); emitcode ("mov","esp,a"); UNPROTECT_SP; @@ -2756,22 +2900,22 @@ resultRemat (iCode * ic) /*-----------------------------------------------------------------*/ /* inExcludeList - return 1 if the string is in exclude Reg list */ /*-----------------------------------------------------------------*/ +static int +regsCmp(void *p1, void *p2) +{ + return (STRCASECMP((char *)p1, (char *)(p2)) == 0); +} + static bool inExcludeList (char *s) { - int i = 0; + const char *p = setFirstItem(options.excludeRegsSet); - if (options.excludeRegs[i] && - STRCASECMP (options.excludeRegs[i], "none") == 0) + if (p == NULL || STRCASECMP(p, "none") == 0) return FALSE; - for (i = 0; options.excludeRegs[i]; i++) - { - if (options.excludeRegs[i] && - STRCASECMP (s, options.excludeRegs[i]) == 0) - return TRUE; - } - return FALSE; + + return isinSetWith(options.excludeRegsSet, s, regsCmp); } /*-----------------------------------------------------------------*/ @@ -2803,9 +2947,6 @@ genFunction (iCode * ic) if (options.stack_probe) emitcode ("lcall","__stack_probe"); - /* if critical function then turn interrupts off */ - if (IFFUNC_ISCRITICAL (ftype)) - emitcode ("clr", "ea"); /* here we need to generate the equates for the register bank if required */ @@ -2876,12 +3017,10 @@ genFunction (iCode * ic) /* save the registers used */ for (i = 0; i < sym->regsUsed->size; i++) { - if (bitVectBitValue (sym->regsUsed, i) || - (ds390_ptrRegReq && (i == R0_IDX || i == R1_IDX))) + if (bitVectBitValue (sym->regsUsed, i)) emitcode ("push", "%s", ds390_regWithIdx (i)->dname); } } - } else { @@ -2983,7 +3122,7 @@ genFunction (iCode * ic) } } } - // jwk: this needs a closer look + // TODO: this needs a closer look SPEC_ISR_SAVED_BANKS(currFunc->etype) = banksToSave; } } @@ -3001,8 +3140,7 @@ genFunction (iCode * ic) /* save the registers used */ for (i = 0; i < sym->regsUsed->size; i++) { - if (bitVectBitValue (sym->regsUsed, i) || - (ds390_ptrRegReq && (i == R0_IDX || i == R1_IDX))) + if (bitVectBitValue (sym->regsUsed, i)) { emitcode ("push", "%s", ds390_regWithIdx (i)->dname); _G.nRegsSaved++; @@ -3027,7 +3165,7 @@ genFunction (iCode * ic) emitcode ("push","_bpx+1"); emitcode ("mov","_bpx,%s",spname); emitcode ("mov","_bpx+1,esp"); - emitcode ("anl","_bpx+1,#3"); + adjustEsp("_bpx+1"); } else { if (options.useXstack) { emitcode ("mov", "r0,%s", spname); @@ -3056,7 +3194,7 @@ genFunction (iCode * ic) emitcode ("add","a,#!constbyte", ((short) sym->stack & 0xff)); emitcode ("mov","sp,a"); emitcode ("mov","a,esp"); - emitcode ("anl","a,#3"); + adjustEsp("a"); emitcode ("addc","a,#!constbyte", (((short) sym->stack) >> 8) & 0xff); emitcode ("mov","esp,a"); UNPROTECT_SP; @@ -3084,6 +3222,17 @@ genFunction (iCode * ic) emitcode ("add", "a,#!constbyte", ((char) sym->xstack & 0xff)); emitcode ("mov", "_spx,a"); } + + /* if critical function then turn interrupts off */ + if (IFFUNC_ISCRITICAL (ftype)) + { + symbol *tlbl = newiTempLabel (NULL); + emitcode ("setb", "c"); + emitcode ("jbc", "ea,%05d$", (tlbl->key + 100)); /* atomic test & clear */ + emitcode ("clr", "c"); + emitcode ("", "%05d$:", (tlbl->key + 100)); + emitcode ("push", "psw"); /* save old ea via c in psw */ + } } @@ -3094,6 +3243,11 @@ static void genEndFunction (iCode * ic) { symbol *sym = OP_SYMBOL (IC_LEFT (ic)); + lineNode *lnp = lineCurr; + bitVect *regsUsed; + bitVect *regsUsedPrologue; + bitVect *regsUnneeded; + int idx; D (emitcode (";", "genEndFunction ");); @@ -3103,6 +3257,12 @@ genEndFunction (iCode * ic) return; } + if (IFFUNC_ISCRITICAL (sym->type)) + { + emitcode ("pop", "psw"); /* restore ea via c in psw */ + emitcode ("mov", "ea,c"); + } + if ((IFFUNC_ISREENT (sym->type) || options.stackAuto) && (sym->stack || FUNC_HASSTACKPARM(sym->type))) { @@ -3179,12 +3339,10 @@ genEndFunction (iCode * ic) /* save the registers used */ for (i = sym->regsUsed->size; i >= 0; i--) { - if (bitVectBitValue (sym->regsUsed, i) || - (ds390_ptrRegReq && (i == R0_IDX || i == R1_IDX))) + if (bitVectBitValue (sym->regsUsed, i)) emitcode ("pop", "%s", ds390_regWithIdx (i)->dname); } } - } else { @@ -3206,7 +3364,6 @@ genEndFunction (iCode * ic) * Restore any register banks saved by genFunction * in reverse order. */ - // jwk: this needs a closer look unsigned savedBanks = SPEC_ISR_SAVED_BANKS(currFunc->etype); int ix; @@ -3248,9 +3405,6 @@ genEndFunction (iCode * ic) if (!inExcludeList ("acc")) emitcode ("pop", "acc"); - if (IFFUNC_ISCRITICAL (sym->type)) - emitcode ("setb", "ea"); - /* if debug then send end of function */ if (options.debug && currFunc) { _G.debugLine = 1; @@ -3268,9 +3422,6 @@ genEndFunction (iCode * ic) } else { - if (IFFUNC_ISCRITICAL (sym->type)) - emitcode ("setb", "ea"); - if (IFFUNC_CALLEESAVES(sym->type)) { int i; @@ -3281,12 +3432,10 @@ genEndFunction (iCode * ic) /* save the registers used */ for (i = sym->regsUsed->size; i >= 0; i--) { - if (bitVectBitValue (sym->regsUsed, i) || - (ds390_ptrRegReq && (i == R0_IDX || i == R1_IDX))) + if (bitVectBitValue (sym->regsUsed, i)) emitcode ("pop", "%s", ds390_regWithIdx (i)->dname); } } - } /* if debug then send end of function */ @@ -3306,6 +3455,111 @@ genEndFunction (iCode * ic) emitcode ("ret", ""); } + if (!port->peep.getRegsRead || !port->peep.getRegsWritten) + return; + + /* If this was an interrupt handler using bank 0 that called another */ + /* function, then all registers must be saved; nothing to optimized. */ + if (IFFUNC_ISISR (sym->type) && IFFUNC_HASFCALL(sym->type) + && !FUNC_REGBANK(sym->type)) + return; + + /* There are no push/pops to optimize if not callee-saves or ISR */ + if (!(FUNC_CALLEESAVES (sym->type) || FUNC_ISISR (sym->type))) + return; + + /* If there were stack parameters, we cannot optimize without also */ + /* fixing all of the stack offsets; this is too dificult to consider. */ + if (FUNC_HASSTACKPARM(sym->type)) + return; + + /* Compute the registers actually used */ + regsUsed = newBitVect (ds390_nRegs); + regsUsedPrologue = newBitVect (ds390_nRegs); + while (lnp) + { + if (lnp->ic && lnp->ic->op == FUNCTION) + regsUsedPrologue = bitVectUnion (regsUsedPrologue, port->peep.getRegsWritten(lnp)); + else + regsUsed = bitVectUnion (regsUsed, port->peep.getRegsWritten(lnp)); + + if (lnp->ic && lnp->ic->op == FUNCTION && lnp->prev + && lnp->prev->ic && lnp->prev->ic->op == ENDFUNCTION) + break; + if (!lnp->prev) + break; + lnp = lnp->prev; + } + + if (bitVectBitValue (regsUsedPrologue, DPS_IDX) + && !bitVectBitValue (regsUsed, DPS_IDX)) + { + bitVectUnSetBit (regsUsedPrologue, DPS_IDX); + } + + if (bitVectBitValue (regsUsedPrologue, CND_IDX) + && !bitVectBitValue (regsUsed, CND_IDX)) + { + regsUsed = bitVectUnion (regsUsed, regsUsedPrologue); + if (IFFUNC_ISISR (sym->type) && !FUNC_REGBANK(sym->type) + && !sym->stack) + bitVectUnSetBit (regsUsed, CND_IDX); + } + else + regsUsed = bitVectUnion (regsUsed, regsUsedPrologue); + + /* If this was an interrupt handler that called another function */ + /* function, then assume working registers may be modified by it. */ + if (IFFUNC_ISISR (sym->type) && IFFUNC_HASFCALL(sym->type)) + { + regsUsed = bitVectSetBit (regsUsed, AP_IDX); + regsUsed = bitVectSetBit (regsUsed, DPX1_IDX); + regsUsed = bitVectSetBit (regsUsed, DPL1_IDX); + regsUsed = bitVectSetBit (regsUsed, DPH1_IDX); + regsUsed = bitVectSetBit (regsUsed, DPX_IDX); + regsUsed = bitVectSetBit (regsUsed, DPL_IDX); + regsUsed = bitVectSetBit (regsUsed, DPH_IDX); + regsUsed = bitVectSetBit (regsUsed, DPS_IDX); + regsUsed = bitVectSetBit (regsUsed, B_IDX); + regsUsed = bitVectSetBit (regsUsed, A_IDX); + regsUsed = bitVectSetBit (regsUsed, CND_IDX); + } + + /* Remove the unneeded push/pops */ + regsUnneeded = newBitVect (ds390_nRegs); + while (lnp) + { + if (lnp->ic && (lnp->ic->op == FUNCTION || lnp->ic->op == ENDFUNCTION)) + { + if (!strncmp(lnp->line, "push", 4)) + { + idx = bitVectFirstBit (port->peep.getRegsRead(lnp)); + if (idx>=0 && !bitVectBitValue (regsUsed, idx)) + { + connectLine (lnp->prev, lnp->next); + regsUnneeded = bitVectSetBit (regsUnneeded, idx); + } + } + if (!strncmp(lnp->line, "pop", 3) || !strncmp(lnp->line, "mov", 3)) + { + idx = bitVectFirstBit (port->peep.getRegsWritten(lnp)); + if (idx>=0 && !bitVectBitValue (regsUsed, idx)) + { + connectLine (lnp->prev, lnp->next); + regsUnneeded = bitVectSetBit (regsUnneeded, idx); + } + } + } + lnp = lnp->next; + } + + for (idx = 0; idx < regsUnneeded->size; idx++) + if (bitVectBitValue (regsUnneeded, idx)) + emitcode ("", ";\teliminated unneeded push/pop %s", ds390_regWithIdx (idx)->dname); + + freeBitVect (regsUnneeded); + freeBitVect (regsUsed); + freeBitVect (regsUsedPrologue); } /*-----------------------------------------------------------------*/ @@ -3325,14 +3579,16 @@ static void genJavaNativeRet(iCode *ic) if (aopHasRegs(AOP(IC_LEFT(ic)),R0_IDX,R1_IDX) || aopHasRegs(AOP(IC_LEFT(ic)),R2_IDX,R3_IDX)) { for (i = 0 ; i < size ; i++ ) { - emitcode ("push","%s",aopGet(AOP(IC_LEFT(ic)),i,FALSE,TRUE,FALSE)); + emitcode ("push","%s", + aopGet(AOP(IC_LEFT(ic)),i,FALSE,TRUE,DP2_RESULT_REG)); } for (i = (size-1) ; i >= 0 ; i--) { emitcode ("pop","a%s",javaRet[i]); } } else { for (i = 0 ; i < size ; i++) - emitcode ("mov","%s,%s",javaRet[i],aopGet(AOP(IC_LEFT(ic)),i,FALSE,TRUE,FALSE)); + emitcode ("mov","%s,%s",javaRet[i], + aopGet(AOP(IC_LEFT(ic)),i,FALSE,TRUE,DP2_RESULT_REG)); } for (i = size ; i < 4 ; i++ ) emitcode ("mov","%s,#0",javaRet[i]); @@ -3347,8 +3603,7 @@ genRet (iCode * ic) { int size, offset = 0, pushed = 0; - D (emitcode (";", "genRet "); - ); + D (emitcode (";", "genRet ");); /* if we have no return value then just generate the "ret" */ @@ -3374,7 +3629,7 @@ genRet (iCode * ic) if (AOP_TYPE (IC_LEFT (ic)) == AOP_DPTR) { l = aopGet (AOP (IC_LEFT (ic)), offset++, - FALSE, TRUE, FALSE); + FALSE, TRUE, NULL); emitcode ("push", "%s", l); pushed++; } @@ -3384,7 +3639,7 @@ genRet (iCode * ic) * is is OK to clobber it in the aopGet. */ l = aopGet (AOP (IC_LEFT (ic)), offset, - FALSE, FALSE, TRUE); + FALSE, FALSE, NULL); if (strcmp (fReturn[offset], l)) emitcode ("mov", "%s,%s", fReturn[offset++], l); } @@ -3497,7 +3752,7 @@ genPlusIncr (iCode * ic) if (size == 1 && AOP(IC_LEFT(ic)) == AOP(IC_RESULT(ic)) && AOP_TYPE(IC_LEFT(ic)) == AOP_DIR ) { while (icount--) { - emitcode("inc","%s",aopGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE,FALSE)); + emitcode("inc","%s",aopGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE,NULL)); } return TRUE; } @@ -3509,9 +3764,10 @@ genPlusIncr (iCode * ic) (size > 1) && (icount == 1)) { - symbol *tlbl; - int emitTlbl; - int labelRange; + symbol *tlbl; + int emitTlbl; + int labelRange; + char *l; /* If the next instruction is a goto and the goto target * is <= 5 instructions previous to this, we can generate @@ -3521,7 +3777,7 @@ genPlusIncr (iCode * ic) && (labelRange = findLabelBackwards (ic, IC_LABEL (ic->next)->key)) != 0 && labelRange <= 5) { - emitcode (";", "tail increment optimized (range %d)", labelRange); + D(emitcode (";", "tail increment optimized (range %d)", labelRange);); tlbl = IC_LABEL (ic->next); emitTlbl = 0; } @@ -3530,50 +3786,60 @@ genPlusIncr (iCode * ic) tlbl = newiTempLabel (NULL); emitTlbl = 1; } - emitcode ("inc", "%s", aopGet (AOP (IC_RESULT (ic)), LSB, FALSE, FALSE, FALSE)); + + l = aopGet (AOP (IC_RESULT (ic)), LSB, FALSE, FALSE, NULL); + emitcode ("inc", "%s", l); + if (AOP_TYPE (IC_RESULT (ic)) == AOP_REG || IS_AOP_PREG (IC_RESULT (ic))) - emitcode ("cjne", "%s,#0,!tlabel" - ,aopGet (AOP (IC_RESULT (ic)), LSB, FALSE, FALSE, FALSE) - ,tlbl->key + 100); + { + emitcode ("cjne", "%s,#0,!tlabel", l, tlbl->key + 100); + } else - { + { emitcode ("clr", "a"); - emitcode ("cjne", "a,%s,!tlabel" - ,aopGet (AOP (IC_RESULT (ic)), LSB, FALSE, FALSE, FALSE) - ,tlbl->key + 100); - } + emitcode ("cjne", "a,%s,!tlabel", l, tlbl->key + 100); + } - emitcode ("inc", "%s", aopGet (AOP (IC_RESULT (ic)), MSB16, FALSE, FALSE, FALSE)); + l = aopGet (AOP (IC_RESULT (ic)), MSB16, FALSE, FALSE, NULL); + emitcode ("inc", "%s", l); if (size > 2) { - if (AOP_TYPE (IC_RESULT (ic)) == AOP_REG || - IS_AOP_PREG (IC_RESULT (ic))) - emitcode ("cjne", "%s,#0,!tlabel" - ,aopGet (AOP (IC_RESULT (ic)), MSB16, FALSE, FALSE, FALSE) - ,tlbl->key + 100); - else - emitcode ("cjne", "a,%s,!tlabel" - ,aopGet (AOP (IC_RESULT (ic)), MSB16, FALSE, FALSE, FALSE) - ,tlbl->key + 100); - - emitcode ("inc", "%s", aopGet (AOP (IC_RESULT (ic)), MSB24, FALSE, FALSE, FALSE)); - } - if (size > 3) - { - if (AOP_TYPE (IC_RESULT (ic)) == AOP_REG || - IS_AOP_PREG (IC_RESULT (ic))) - emitcode ("cjne", "%s,#0,!tlabel" - ,aopGet (AOP (IC_RESULT (ic)), MSB24, FALSE, FALSE, FALSE) - ,tlbl->key + 100); - else + if (!strcmp(l, "acc")) { - emitcode ("cjne", "a,%s,!tlabel" - ,aopGet (AOP (IC_RESULT (ic)), MSB24, FALSE, FALSE, FALSE) - ,tlbl->key + 100); + emitcode("jnz", "!tlabel", tlbl->key + 100); } - emitcode ("inc", "%s", aopGet (AOP (IC_RESULT (ic)), MSB32, FALSE, FALSE, FALSE)); - } + else if (AOP_TYPE (IC_RESULT (ic)) == AOP_REG || + IS_AOP_PREG (IC_RESULT (ic))) + { + emitcode ("cjne", "%s,#0,!tlabel", l, tlbl->key + 100); + } + else + { + emitcode ("cjne", "a,%s,!tlabel", l, tlbl->key + 100); + } + + l = aopGet (AOP (IC_RESULT (ic)), MSB24, FALSE, FALSE, NULL); + emitcode ("inc", "%s", l); + } + if (size > 3) + { + if (!strcmp(l, "acc")) + { + emitcode("jnz", "!tlabel", tlbl->key + 100); + } + else if (AOP_TYPE (IC_RESULT (ic)) == AOP_REG || + IS_AOP_PREG (IC_RESULT (ic))) + { + emitcode ("cjne", "%s,#0,!tlabel", l, tlbl->key + 100); + } + else + { + emitcode ("cjne", "a,%s,!tlabel", l, tlbl->key + 100); + } + + l = aopGet (AOP (IC_RESULT (ic)), MSB32, FALSE, FALSE, NULL); + emitcode ("inc", "%s", l); } if (emitTlbl) { @@ -3588,11 +3854,11 @@ genPlusIncr (iCode * ic) switch (size) { case 3: - emitcode ("mov","dpx,%s",aopGet(AOP (IC_LEFT (ic)), 2, FALSE, FALSE, FALSE)); + emitcode ("mov","dpx,%s",aopGet(AOP (IC_LEFT (ic)), 2, FALSE, FALSE, NULL)); case 2: - emitcode ("mov","dph,%s",aopGet(AOP (IC_LEFT (ic)), 1, FALSE, FALSE, FALSE)); + emitcode ("mov","dph,%s",aopGet(AOP (IC_LEFT (ic)), 1, FALSE, FALSE, NULL)); case 1: - emitcode ("mov","dpl,%s",aopGet(AOP (IC_LEFT (ic)), 0, FALSE, FALSE, FALSE)); + emitcode ("mov","dpl,%s",aopGet(AOP (IC_LEFT (ic)), 0, FALSE, FALSE, NULL)); break; } while (icount--) emitcode ("inc","dptr"); @@ -3624,7 +3890,7 @@ genPlusIncr (iCode * ic) if (icount > 3) { - MOVA (aopGet (AOP (IC_LEFT (ic)), 0, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (IC_LEFT (ic)), 0, FALSE, FALSE, NULL)); emitcode ("add", "a,#!constbyte", ((char) icount) & 0xff); aopPut (AOP (IC_RESULT (ic)), "a", 0); } @@ -3634,7 +3900,7 @@ genPlusIncr (iCode * ic) _startLazyDPSEvaluation (); while (icount--) { - emitcode ("inc", "%s", aopGet (AOP (IC_LEFT (ic)), 0, FALSE, FALSE, FALSE)); + emitcode ("inc", "%s", aopGet (AOP (IC_LEFT (ic)), 0, FALSE, FALSE, NULL)); } _endLazyDPSEvaluation (); } @@ -3672,8 +3938,8 @@ outBitAcc (operand * result) static void genPlusBits (iCode * ic) { - D (emitcode (";", "genPlusBits "); - ); + D (emitcode (";", "genPlusBits ");); + if (AOP_TYPE (IC_RESULT (ic)) == AOP_CRY) { symbol *lbl = newiTempLabel (NULL); @@ -3702,7 +3968,7 @@ adjustArithmeticResult (iCode * ic) !sameRegs (AOP (IC_RESULT (ic)), AOP (IC_LEFT (ic)))) { aopPut (AOP (IC_RESULT (ic)), - aopGet (AOP (IC_LEFT (ic)), GPTRSIZE - 1, FALSE, FALSE, FALSE), + aopGet (AOP (IC_LEFT (ic)), GPTRSIZE - 1, FALSE, FALSE, NULL), GPTRSIZE - 1); } @@ -3711,7 +3977,7 @@ adjustArithmeticResult (iCode * ic) !sameRegs (AOP (IC_RESULT (ic)), AOP (IC_RIGHT (ic)))) { aopPut (AOP (IC_RESULT (ic)), - aopGet (AOP (IC_RIGHT (ic)), GPTRSIZE - 1, FALSE, FALSE, FALSE), + aopGet (AOP (IC_RIGHT (ic)), GPTRSIZE - 1, FALSE, FALSE, NULL), GPTRSIZE - 1); } @@ -3735,7 +4001,7 @@ bool aopOp3(iCode * ic) { bool dp1InUse, dp2InUse; bool useDp2; - + // First, generate the right opcode. DPTR may be used if neither left nor result are // of type AOP_STR. @@ -3748,11 +4014,21 @@ bool aopOp3(iCode * ic) // AOP_IS_DPTRn(IC_LEFT(ic)) ? "true" : "false", // AOP_IS_DPTRn(IC_RIGHT(ic)) ? "true" : "false", // AOP_IS_DPTRn(IC_RESULT(ic)) ? "true" : "false"); -// ); - +// ); - // Right uses DPTR unless left or result is an AOP_STR. - aopOp (IC_RIGHT(ic),ic,FALSE, AOP_IS_STR(IC_LEFT(ic)) || AOP_IS_STR(IC_RESULT(ic))); + // Right uses DPTR unless left or result is an AOP_STR; however, + // if right is an AOP_STR, it must use DPTR regardless. + if ((AOP_IS_STR(IC_LEFT(ic)) || AOP_IS_STR(IC_RESULT(ic))) + && !AOP_IS_STR(IC_RIGHT(ic))) + { + useDp2 = TRUE; + } + else + { + useDp2 = FALSE; + } + + aopOp (IC_RIGHT(ic),ic,FALSE, useDp2); // if the right used DPTR, left MUST use DPTR2. // if the right used DPTR2, left MUST use DPTR. @@ -3781,16 +4057,34 @@ bool aopOp3(iCode * ic) } aopOp(IC_LEFT(ic), ic, FALSE, useDp2); - + + // We've op'd the left & right. So, if left or right are the same operand as result, // we know aopOp will succeed, and we can just do it & bail. - if (isOperandEqual(IC_LEFT(ic),IC_RESULT(ic)) || - isOperandEqual(IC_RIGHT(ic),IC_RESULT(ic))) - { + if (isOperandEqual(IC_LEFT(ic),IC_RESULT(ic))) + { + aopOp (IC_RESULT (ic), ic, TRUE, AOP_USESDPTR2 (IC_LEFT (ic))); + return TRUE; + } + if (isOperandEqual(IC_RIGHT(ic),IC_RESULT(ic))) + { // D(emitcode(";", "aopOp3: (left | right) & result equal");); - aopOp(IC_RESULT(ic),ic,TRUE, FALSE); + aopOp(IC_RESULT(ic),ic,TRUE, AOP_USESDPTR2 (IC_RIGHT (ic))); return TRUE; - } + } + + // Operands may be equivalent (but not equal) if they share a spill location. If + // so, use the same DPTR or DPTR2. + if (operandsEqu (IC_LEFT(ic), IC_RESULT(ic))) + { + aopOp (IC_RESULT (ic), ic, TRUE, AOP_USESDPTR2 (IC_LEFT (ic))); + return TRUE; + } + if (operandsEqu (IC_RIGHT(ic), IC_RESULT(ic))) + { + aopOp (IC_RESULT (ic), ic, TRUE, AOP_USESDPTR2 (IC_RIGHT (ic))); + return TRUE; + } // Note which dptrs are currently in use. dp1InUse = AOP_USESDPTR(IC_LEFT(ic)) || AOP_USESDPTR(IC_RIGHT(ic)); @@ -3894,7 +4188,7 @@ static void genPlus (iCode * ic) { int size, offset = 0; - bool pushResult = FALSE; + bool pushResult; int rSize; D (emitcode (";", "genPlus ");); @@ -3903,7 +4197,7 @@ genPlus (iCode * ic) if ( AOP_IS_STR(IC_LEFT(ic)) && isOperandLiteral(IC_RIGHT(ic)) && OP_SYMBOL(IC_RESULT(ic))->ruonly) { aopOp (IC_RIGHT (ic), ic, TRUE, FALSE); - size = floatFromVal (AOP (IC_RIGHT(ic))->aopu.aop_lit); + size = (int)floatFromVal (AOP (IC_RIGHT(ic))->aopu.aop_lit); if (size <= 9) { while (size--) emitcode ("inc","dptr"); } else { @@ -3977,7 +4271,7 @@ genPlus (iCode * ic) _startLazyDPSEvaluation (); while (size--) { - MOVA (aopGet (AOP (IC_RIGHT (ic)), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (IC_RIGHT (ic)), offset, FALSE, FALSE, NULL)); emitcode ("addc", "a,#0"); aopPut (AOP (IC_RESULT (ic)), "a", offset++); } @@ -4002,13 +4296,13 @@ genPlus (iCode * ic) { if (AOP_TYPE(IC_LEFT(ic)) == AOP_ACC && !AOP_NEEDSACC(IC_RIGHT(ic))) { - MOVA (aopGet (AOP (IC_LEFT (ic)), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (IC_LEFT (ic)), offset, FALSE, FALSE, NULL)); if (offset == 0) emitcode ("add", "a,%s", - aopGet (AOP (IC_RIGHT (ic)), offset, FALSE, FALSE, FALSE)); + aopGet (AOP (IC_RIGHT (ic)), offset, FALSE, FALSE, NULL)); else emitcode ("addc", "a,%s", - aopGet (AOP (IC_RIGHT (ic)), offset, FALSE, FALSE, FALSE)); + aopGet (AOP (IC_RIGHT (ic)), offset, FALSE, FALSE, NULL)); } else { @@ -4022,7 +4316,7 @@ genPlus (iCode * ic) D(emitcode(";", "+ AOP_ACC special case.");); emitcode("xch", "a, %s", DP2_RESULT_REG); } - MOVA (aopGet (AOP (IC_RIGHT (ic)), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (IC_RIGHT (ic)), offset, FALSE, FALSE, NULL)); if (offset == 0) { if (AOP_TYPE(IC_LEFT(ic)) == AOP_ACC) @@ -4033,13 +4327,15 @@ genPlus (iCode * ic) else { emitcode ("add", "a,%s", - aopGet (AOP(IC_LEFT(ic)), offset, FALSE, FALSE, FALSE)); + aopGet (AOP(IC_LEFT(ic)), offset, FALSE, FALSE, + DP2_RESULT_REG)); } } else { emitcode ("addc", "a,%s", - aopGet (AOP (IC_LEFT (ic)), offset, FALSE, FALSE, FALSE)); + aopGet (AOP (IC_LEFT (ic)), offset, FALSE, FALSE, + DP2_RESULT_REG)); } } if (!pushResult) @@ -4103,7 +4399,7 @@ genMinusDec (iCode * ic) if (size == 1 && AOP(IC_LEFT(ic)) == AOP(IC_RESULT(ic)) && AOP_TYPE(IC_LEFT(ic)) == AOP_DIR ) { while (icount--) { - emitcode("dec","%s",aopGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE,FALSE)); + emitcode("dec","%s",aopGet(AOP(IC_RESULT(ic)),0,FALSE,FALSE,NULL)); } return TRUE; } @@ -4115,8 +4411,9 @@ genMinusDec (iCode * ic) (icount == 1)) { symbol *tlbl; - int emitTlbl; - int labelRange; + int emitTlbl; + int labelRange; + char *l; /* If the next instruction is a goto and the goto target * is <= 5 instructions previous to this, we can generate @@ -4136,52 +4433,61 @@ genMinusDec (iCode * ic) emitTlbl = 1; } - emitcode ("dec", "%s", aopGet (AOP (IC_RESULT (ic)), LSB, FALSE, FALSE, FALSE)); + l = aopGet (AOP (IC_RESULT (ic)), LSB, FALSE, FALSE, NULL); + emitcode ("dec", "%s", l); + if (AOP_TYPE (IC_RESULT (ic)) == AOP_REG || AOP_TYPE (IC_RESULT (ic)) == AOP_DPTR || IS_AOP_PREG (IC_RESULT (ic))) - emitcode ("cjne", "%s,#!constbyte,!tlabel" - ,aopGet (AOP (IC_RESULT (ic)), LSB, FALSE, FALSE, FALSE), 0xff - ,tlbl->key + 100); + { + emitcode ("cjne", "%s,#!constbyte,!tlabel", l, 0xff, tlbl->key + 100); + } else - { + { emitcode ("mov", "a,#!constbyte",0xff); - emitcode ("cjne", "a,%s,!tlabel" - ,aopGet (AOP (IC_RESULT (ic)), LSB, FALSE, FALSE, FALSE) - ,tlbl->key + 100); - } - emitcode ("dec", "%s", aopGet (AOP (IC_RESULT (ic)), MSB16, FALSE, FALSE, FALSE)); + emitcode ("cjne", "a,%s,!tlabel", l, tlbl->key + 100); + } + l = aopGet (AOP (IC_RESULT (ic)), MSB16, FALSE, FALSE, NULL); + emitcode ("dec", "%s", l); if (size > 2) { - if (AOP_TYPE (IC_RESULT (ic)) == AOP_REG || - AOP_TYPE (IC_RESULT (ic)) == AOP_DPTR || - IS_AOP_PREG (IC_RESULT (ic))) - emitcode ("cjne", "%s,#!constbyte,!tlabel" - ,aopGet (AOP (IC_RESULT (ic)), MSB16, FALSE, FALSE, FALSE),0xff - ,tlbl->key + 100); - else + if (!strcmp(l, "acc")) + { + emitcode("jnz", "!tlabel", tlbl->key + 100); + } + else if (AOP_TYPE (IC_RESULT (ic)) == AOP_REG || + AOP_TYPE (IC_RESULT (ic)) == AOP_DPTR || + IS_AOP_PREG (IC_RESULT (ic))) + { + emitcode ("cjne", "%s,#!constbyte,!tlabel", l, 0xff, tlbl->key + 100); + } + else { - emitcode ("cjne", "a,%s,!tlabel" - ,aopGet (AOP (IC_RESULT (ic)), MSB16, FALSE, FALSE, FALSE) - ,tlbl->key + 100); + emitcode ("mov", "a,#!constbyte",0xff); + emitcode ("cjne", "a,%s,!tlabel", l, tlbl->key + 100); } - emitcode ("dec", "%s", aopGet (AOP (IC_RESULT (ic)), MSB24, FALSE, FALSE, FALSE)); + l = aopGet (AOP (IC_RESULT (ic)), MSB24, FALSE, FALSE, NULL); + emitcode ("dec", "%s", l); } if (size > 3) { - if (AOP_TYPE (IC_RESULT (ic)) == AOP_REG || - AOP_TYPE (IC_RESULT (ic)) == AOP_DPTR || - IS_AOP_PREG (IC_RESULT (ic))) - emitcode ("cjne", "%s,#!constbyte,!tlabel" - ,aopGet (AOP (IC_RESULT (ic)), MSB24, FALSE, FALSE, FALSE),0xff - ,tlbl->key + 100); - else + if (!strcmp(l, "acc")) { - emitcode ("cjne", "a,%s,!tlabel" - ,aopGet (AOP (IC_RESULT (ic)), MSB24, FALSE, FALSE, FALSE) - ,tlbl->key + 100); + emitcode("jnz", "!tlabel", tlbl->key + 100); + } + else if (AOP_TYPE (IC_RESULT (ic)) == AOP_REG || + AOP_TYPE (IC_RESULT (ic)) == AOP_DPTR || + IS_AOP_PREG (IC_RESULT (ic))) + { + emitcode ("cjne", "%s,#!constbyte,!tlabel", l, 0xff, tlbl->key + 100); } - emitcode ("dec", "%s", aopGet (AOP (IC_RESULT (ic)), MSB32, FALSE, FALSE, FALSE)); + else + { + emitcode ("mov", "a,#!constbyte",0xff); + emitcode ("cjne", "a,%s,!tlabel", l, tlbl->key + 100); + } + l = aopGet (AOP (IC_RESULT (ic)), MSB32, FALSE, FALSE, NULL); + emitcode ("dec", "%s", l); } if (emitTlbl) { @@ -4207,7 +4513,8 @@ genMinusDec (iCode * ic) _startLazyDPSEvaluation (); while (icount--) { - emitcode ("dec", "%s", aopGet (AOP (IC_RESULT (ic)), 0, FALSE, FALSE, FALSE)); + emitcode ("dec", "%s", + aopGet (AOP (IC_RESULT (ic)), 0, FALSE, FALSE, NULL)); } _endLazyDPSEvaluation (); @@ -4285,8 +4592,8 @@ genMinus (iCode * ic) { int size, offset = 0; int rSize; - unsigned long lit = 0L; - bool pushResult = FALSE; + long lit = 0L; + bool pushResult; D (emitcode (";", "genMinus ");); @@ -4318,8 +4625,8 @@ genMinus (iCode * ic) } else { - lit = (unsigned long) floatFromVal (AOP (IC_RIGHT (ic))->aopu.aop_lit); - lit = -(long) lit; + lit = (long) floatFromVal (AOP (IC_RIGHT (ic))->aopu.aop_lit); + lit = -lit; } @@ -4329,16 +4636,17 @@ genMinus (iCode * ic) if (AOP_TYPE (IC_RIGHT (ic)) != AOP_LIT) { if (AOP_USESDPTR(IC_RIGHT(ic))) { emitcode ("mov","b,%s", - aopGet (AOP (IC_RIGHT (ic)), offset, FALSE, FALSE, TRUE)); - MOVA(aopGet (AOP (IC_LEFT (ic)), offset, FALSE, FALSE, TRUE)); + aopGet (AOP (IC_RIGHT (ic)), offset, FALSE, FALSE, NULL)); + MOVA(aopGet (AOP (IC_LEFT (ic)), offset, FALSE, FALSE, NULL)); emitcode ("subb","a,b"); } else { - MOVA (aopGet (AOP (IC_LEFT (ic)), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (IC_LEFT (ic)), offset, FALSE, FALSE, NULL)); emitcode ("subb", "a,%s", - aopGet (AOP (IC_RIGHT (ic)), offset, FALSE, FALSE, FALSE)); + aopGet (AOP (IC_RIGHT (ic)), offset, FALSE, FALSE, + DP2_RESULT_REG)); } } else { - MOVA (aopGet (AOP (IC_LEFT (ic)), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (IC_LEFT (ic)), offset, FALSE, FALSE, NULL)); /* first add without previous c */ if (!offset) { if (!size && lit==-1) { @@ -4414,9 +4722,11 @@ genMultOneByte (operand * left, operand * result, iCode * ic) { - sym_link *opetype = operandType (result); + int size; symbol *lbl; - + bool runtimeSign, compiletimeSign; + bool lUnsigned, rUnsigned; + /* (if two literals: the value is computed before) */ /* if one literal, literal on the right */ @@ -4428,105 +4738,197 @@ genMultOneByte (operand * left, emitcode (";", "swapped left and right"); } - if (SPEC_USIGN(opetype) - // ignore the sign of left and right, what else can we do? - || (SPEC_USIGN(operandType(left)) && - SPEC_USIGN(operandType(right)))) { - // just an unsigned 8*8=8/16 multiply - //emitcode (";","unsigned"); - emitcode ("mov", "b,%s", aopGet (AOP (right), 0, FALSE, FALSE, TRUE)); - MOVA (aopGet (AOP (left), 0, FALSE, FALSE, TRUE)); - emitcode ("mul", "ab"); - - _G.accInUse++; _G.bInUse++; - aopOp(result, ic, TRUE, FALSE); - - if (AOP_SIZE(result)<1 || AOP_SIZE(result)>2) - { - // this should never happen - fprintf (stderr, "size!=1||2 (%d) in %s at line:%d \n", - AOP_SIZE(result), __FILE__, lineno); - exit (1); - } - - aopPut (AOP (result), "a", 0); - _G.accInUse--; _G.bInUse--; - if (AOP_SIZE(result)==2) + /* (if two literals: the value is computed before) */ + /* if one literal, literal on the right */ + if (AOP_TYPE (left) == AOP_LIT) { - aopPut (AOP (result), "b", 1); + operand *t = right; + right = left; + left = t; + /* emitcode (";", "swapped left and right"); */ + } + /* if no literal, unsigned on the right: shorter code */ + if ( AOP_TYPE (right) != AOP_LIT + && SPEC_USIGN (getSpec (operandType (left)))) + { + operand *t = right; + right = left; + left = t; + } + + lUnsigned = SPEC_USIGN (getSpec (operandType (left))); + rUnsigned = SPEC_USIGN (getSpec (operandType (right))); + + if ((lUnsigned && rUnsigned) +/* sorry, I don't know how to get size + without calling aopOp (result,...); + see Feature Request */ + /* || size == 1 */ ) /* no, this is not a bug; with a 1 byte result there's + no need to take care about the signedness! */ + { + /* just an unsigned 8 * 8 = 8 multiply + or 8u * 8u = 16u */ + /* emitcode (";","unsigned"); */ + emitcode ("mov", "b,%s", aopGet (AOP (right), 0, FALSE, FALSE, NULL)); + MOVA (aopGet (AOP (left), 0, FALSE, FALSE, NULL)); + emitcode ("mul", "ab"); + + _G.accInUse++; _G.bInUse++; + aopOp (result, ic, TRUE, FALSE); + size = AOP_SIZE (result); + + if (size < 1 || size > 2) + { + /* this should never happen */ + fprintf (stderr, "size!=1||2 (%d) in %s at line:%d \n", + size, __FILE__, lineno); + exit (1); + } + + aopPut (AOP (result), "a", 0); + _G.accInUse--; _G.bInUse--; + if (size == 2) + aopPut (AOP (result), "b", 1); + return; } - return; - } - // we have to do a signed multiply + /* we have to do a signed multiply */ + /* emitcode (";", "signed"); */ + + /* now sign adjust for both left & right */ - emitcode (";", "signed"); - emitcode ("clr", "F0"); // reset sign flag - MOVA (aopGet (AOP (left), 0, FALSE, FALSE, TRUE)); + /* let's see what's needed: */ + /* apply negative sign during runtime */ + runtimeSign = FALSE; + /* negative sign from literals */ + compiletimeSign = FALSE; - lbl=newiTempLabel(NULL); - emitcode ("jnb", "acc.7,!tlabel", lbl->key+100); - // left side is negative, 8-bit two's complement, this fails for -128 - emitcode ("setb", "F0"); // set sign flag - emitcode ("cpl", "a"); - emitcode ("inc", "a"); + if (!lUnsigned) + { + if (AOP_TYPE(left) == AOP_LIT) + { + /* signed literal */ + signed char val = (char) floatFromVal (AOP (left)->aopu.aop_lit); + if (val < 0) + compiletimeSign = TRUE; + } + else + /* signed but not literal */ + runtimeSign = TRUE; + } - emitcode ("", "!tlabeldef", lbl->key+100); + if (!rUnsigned) + { + if (AOP_TYPE(right) == AOP_LIT) + { + /* signed literal */ + signed char val = (char) floatFromVal (AOP (right)->aopu.aop_lit); + if (val < 0) + compiletimeSign ^= TRUE; + } + else + /* signed but not literal */ + runtimeSign = TRUE; + } - /* if literal */ - if (AOP_TYPE(right)==AOP_LIT) { - signed char val=floatFromVal (AOP (right)->aopu.aop_lit); - /* AND literal negative */ - if ((int) val < 0) { - emitcode ("cpl", "F0"); // complement sign flag - emitcode ("mov", "b,#!constbyte", -val); - } else { - emitcode ("mov", "b,#!constbyte", val); + /* initialize F0, which stores the runtime sign */ + if (runtimeSign) + { + if (compiletimeSign) + emitcode ("setb", "F0"); /* set sign flag */ + else + emitcode ("clr", "F0"); /* reset sign flag */ } - } else { - lbl=newiTempLabel(NULL); - emitcode ("mov", "b,a"); - emitcode ("mov", "a,%s", aopGet (AOP (right), 0, FALSE, FALSE, TRUE)); - emitcode ("jnb", "acc.7,!tlabel", lbl->key+100); - // right side is negative, 8-bit two's complement - emitcode ("cpl", "F0"); // complement sign flag - emitcode ("cpl", "a"); - emitcode ("inc", "a"); - emitcode ("", "!tlabeldef", lbl->key+100); - } + + /* save the signs of the operands */ + if (AOP_TYPE(right) == AOP_LIT) + { + signed char val = (char) floatFromVal (AOP (right)->aopu.aop_lit); + + if (!rUnsigned && val < 0) + emitcode ("mov", "b,#!constbyte", -val); + else + emitcode ("mov", "b,#!constbyte", (unsigned char) val); + } + else /* ! literal */ + { + if (rUnsigned) /* emitcode (";", "signed"); */ + emitcode ("mov", "b,%s", aopGet (AOP (right), 0, FALSE, FALSE, NULL)); + else + { + MOVA (aopGet (AOP (right), 0, FALSE, FALSE, NULL)); + lbl = newiTempLabel (NULL); + emitcode ("jnb", "acc.7,!tlabel", lbl->key + 100); + emitcode ("cpl", "F0"); /* complement sign flag */ + emitcode ("cpl", "a"); /* 2's complement */ + emitcode ("inc", "a"); + emitcode ("", "!tlabeldef", lbl->key + 100); + emitcode ("mov", "b,a"); + } + } + + if (AOP_TYPE(left) == AOP_LIT) + { + signed char val = (char) floatFromVal (AOP (left)->aopu.aop_lit); + + if (!lUnsigned && val < 0) + emitcode ("mov", "a,#!constbyte", -val); + else + emitcode ("mov", "a,#!constbyte", (unsigned char) val); + } + else /* ! literal */ + { + if (lUnsigned) /* emitcode (";", "signed"); */ + + emitcode ("mov", "a,%s", aopGet (AOP (left), 0, FALSE, FALSE, NULL)); + else + { + MOVA (aopGet (AOP (left), 0, FALSE, FALSE, NULL)); + lbl = newiTempLabel (NULL); + emitcode ("jnb", "acc.7,!tlabel", lbl->key + 100); + emitcode ("cpl", "F0"); /* complement sign flag */ + emitcode ("cpl", "a"); /* 2's complement */ + emitcode ("inc", "a"); + emitcode ("", "!tlabeldef", lbl->key + 100); + } + } + + /* now the multiplication */ emitcode ("mul", "ab"); - _G.accInUse++;_G.bInUse++; aopOp(result, ic, TRUE, FALSE); - - if (AOP_SIZE(result)<1 || AOP_SIZE(result)>2) - { - // this should never happen + size = AOP_SIZE (result); + + if (size < 1 || size > 2) + { + /* this should never happen */ fprintf (stderr, "size!=1||2 (%d) in %s at line:%d \n", - AOP_SIZE(result), __FILE__, lineno); + size, __FILE__, lineno); exit (1); - } + } - lbl=newiTempLabel(NULL); - emitcode ("jnb", "F0,!tlabel", lbl->key+100); - // only ONE op was negative, we have to do a 8/16-bit two's complement - emitcode ("cpl", "a"); // lsb - if (AOP_SIZE(result)==1) { - emitcode ("inc", "a"); - } else { - emitcode ("add", "a,#1"); - emitcode ("xch", "a,b"); - emitcode ("cpl", "a"); // msb - emitcode ("addc", "a,#0"); - emitcode ("xch", "a,b"); - } - - emitcode ("", "!tlabeldef", lbl->key+100); + if (runtimeSign || compiletimeSign) + { + lbl = newiTempLabel (NULL); + if (runtimeSign) + emitcode ("jnb", "F0,!tlabel", lbl->key + 100); + emitcode ("cpl", "a"); /* lsb 2's complement */ + if (size != 2) + emitcode ("inc", "a"); /* inc doesn't set carry flag */ + else + { + emitcode ("add", "a,#1"); /* this sets carry flag */ + emitcode ("xch", "a,b"); + emitcode ("cpl", "a"); /* msb 2's complement */ + emitcode ("addc", "a,#0"); + emitcode ("xch", "a,b"); + } + emitcode ("", "!tlabeldef", lbl->key + 100); + } aopPut (AOP (result), "a", 0); _G.accInUse--;_G.bInUse--; - if (AOP_SIZE(result)==2) { + if (size == 2) aopPut (AOP (result), "b", 1); - } } /*-----------------------------------------------------------------*/ @@ -4556,7 +4958,7 @@ static void genMultTwoByte (operand *left, operand *right, if (!umult) { emitcode("clr","F0"); if (AOP_TYPE(right) == AOP_LIT) { - int val=floatFromVal (AOP (right)->aopu.aop_lit); + int val=(int)floatFromVal (AOP (right)->aopu.aop_lit); if (val < 0) { emitcode("setb","F0"); val = -val; @@ -4565,8 +4967,8 @@ static void genMultTwoByte (operand *left, operand *right, emitcode ("mov","mb,#!constbyte",(val >> 8) & 0xff); } else { lbl = newiTempLabel(NULL); - emitcode ("mov","b,%s",aopGet(AOP(right),0,FALSE,FALSE,TRUE)); - emitcode ("mov","a,%s",aopGet(AOP(right),1,FALSE,FALSE,TRUE)); + emitcode ("mov","b,%s",aopGet(AOP(right),0,FALSE,FALSE,NULL)); + emitcode ("mov","a,%s",aopGet(AOP(right),1,FALSE,FALSE,NULL)); emitcode ("jnb","acc.7,!tlabel",lbl->key+100); emitcode ("xch", "a,b"); emitcode ("cpl","a"); @@ -4580,14 +4982,14 @@ static void genMultTwoByte (operand *left, operand *right, emitcode ("mov","mb,a"); } } else { - emitcode ("mov","mb,%s",aopGet(AOP(right),0,FALSE,FALSE,TRUE)); - emitcode ("mov","mb,%s",aopGet(AOP(right),1,FALSE,FALSE,TRUE)); + emitcode ("mov","mb,%s",aopGet(AOP(right),0,FALSE,FALSE,NULL)); + emitcode ("mov","mb,%s",aopGet(AOP(right),1,FALSE,FALSE,NULL)); } /* load up MA with left */ if (!umult) { lbl = newiTempLabel(NULL); - emitcode ("mov","b,%s",aopGet(AOP(left),0,FALSE,FALSE,TRUE)); - emitcode ("mov","a,%s",aopGet(AOP(left),1,FALSE,FALSE,TRUE)); + emitcode ("mov","b,%s",aopGet(AOP(left),0,FALSE,FALSE,NULL)); + emitcode ("mov","a,%s",aopGet(AOP(left),1,FALSE,FALSE,NULL)); emitcode ("jnb","acc.7,!tlabel",lbl->key+100); emitcode ("xch", "a,b"); emitcode ("cpl","a"); @@ -4601,8 +5003,8 @@ static void genMultTwoByte (operand *left, operand *right, emitcode ("mov","ma,b"); emitcode ("mov","ma,a"); } else { - emitcode ("mov","ma,%s",aopGet(AOP(left),0,FALSE,FALSE,TRUE)); - emitcode ("mov","ma,%s",aopGet(AOP(left),1,FALSE,FALSE,TRUE)); + emitcode ("mov","ma,%s",aopGet(AOP(left),0,FALSE,FALSE,NULL)); + emitcode ("mov","ma,%s",aopGet(AOP(left),1,FALSE,FALSE,NULL)); } /* wait for multiplication to finish */ lbl = newiTempLabel(NULL); @@ -4765,97 +5167,182 @@ genDivOneByte (operand * left, operand * result, iCode * ic) { - sym_link *opetype = operandType (result); + bool lUnsigned, rUnsigned; + bool runtimeSign, compiletimeSign; char *l; symbol *lbl; int size, offset; offset = 1; + lUnsigned = SPEC_USIGN (getSpec (operandType (left))); + rUnsigned = SPEC_USIGN (getSpec (operandType (right))); + /* signed or unsigned */ - if (SPEC_USIGN (opetype)) + if (lUnsigned && rUnsigned) { - /* unsigned is easy */ - LOAD_AB_FOR_DIV (left, right, l); - emitcode ("div", "ab"); + /* unsigned is easy */ + LOAD_AB_FOR_DIV (left, right, l); + emitcode ("div", "ab"); - _G.accInUse++; - aopOp(result, ic, TRUE, FALSE); - aopPut (AOP (result), "a", 0); - _G.accInUse--; + _G.accInUse++; + aopOp (result, ic, TRUE, FALSE); + aopPut (AOP (result), "a", 0); + _G.accInUse--; - size = AOP_SIZE (result) - 1; - - while (size--) - { - aopPut (AOP (result), zero, offset++); - } + size = AOP_SIZE (result) - 1; + + while (size--) + aopPut (AOP (result), zero, offset++); return; } /* signed is a little bit more difficult */ - /* save the signs of the operands */ - l = aopGet (AOP (left), 0, FALSE, FALSE, TRUE); - MOVA (l); - emitcode ("xrl", "a,%s", aopGet (AOP (right), 0, FALSE, TRUE, FALSE)); - emitcode ("push", "acc"); /* save it on the stack */ - /* now sign adjust for both left & right */ - l = aopGet (AOP (right), 0, FALSE, FALSE, TRUE); - MOVA (l); - lbl = newiTempLabel (NULL); - emitcode ("jnb", "acc.7,!tlabel", (lbl->key + 100)); - emitcode ("cpl", "a"); - emitcode ("inc", "a"); - emitcode ("", "!tlabeldef", (lbl->key + 100)); - emitcode ("mov", "b,a"); - /* sign adjust left side */ - l = aopGet (AOP (left), 0, FALSE, FALSE, TRUE); - MOVA (l); + /* let's see what's needed: */ + /* apply negative sign during runtime */ + runtimeSign = FALSE; + /* negative sign from literals */ + compiletimeSign = FALSE; - lbl = newiTempLabel (NULL); - emitcode ("jnb", "acc.7,!tlabel", (lbl->key + 100)); - emitcode ("cpl", "a"); - emitcode ("inc", "a"); - emitcode ("", "!tlabeldef", (lbl->key + 100)); + if (!lUnsigned) + { + if (AOP_TYPE(left) == AOP_LIT) + { + /* signed literal */ + signed char val = (char) floatFromVal (AOP (left)->aopu.aop_lit); + if (val < 0) + compiletimeSign = TRUE; + } + else + /* signed but not literal */ + runtimeSign = TRUE; + } + if (!rUnsigned) + { + if (AOP_TYPE(right) == AOP_LIT) + { + /* signed literal */ + signed char val = (char) floatFromVal (AOP (right)->aopu.aop_lit); + if (val < 0) + compiletimeSign ^= TRUE; + } + else + /* signed but not literal */ + runtimeSign = TRUE; + } + + /* initialize F0, which stores the runtime sign */ + if (runtimeSign) + { + if (compiletimeSign) + emitcode ("setb", "F0"); /* set sign flag */ + else + emitcode ("clr", "F0"); /* reset sign flag */ + } + + /* save the signs of the operands */ + if (AOP_TYPE(right) == AOP_LIT) + { + signed char val = (char) floatFromVal (AOP (right)->aopu.aop_lit); + + if (!rUnsigned && val < 0) + emitcode ("mov", "b,#0x%02x", -val); + else + emitcode ("mov", "b,#0x%02x", (unsigned char) val); + } + else /* ! literal */ + { + if (rUnsigned) + emitcode ("mov", "b,%s", aopGet (AOP (right), 0, FALSE, FALSE, NULL)); + else + { + MOVA (aopGet (AOP (right), 0, FALSE, FALSE, NULL)); + lbl = newiTempLabel (NULL); + emitcode ("jnb", "acc.7,!tlabel", lbl->key + 100); + emitcode ("cpl", "F0"); /* complement sign flag */ + emitcode ("cpl", "a"); /* 2's complement */ + emitcode ("inc", "a"); + emitcode ("", "!tlabeldef", lbl->key + 100); + emitcode ("mov", "b,a"); + } + } + + if (AOP_TYPE(left) == AOP_LIT) + { + signed char val = (char) floatFromVal (AOP (left)->aopu.aop_lit); + + if (!lUnsigned && val < 0) + emitcode ("mov", "a,#0x%02x", -val); + else + emitcode ("mov", "a,#0x%02x", (unsigned char) val); + } + else /* ! literal */ + { + if (lUnsigned) + emitcode ("mov", "a,%s", aopGet (AOP (left), 0, FALSE, FALSE, NULL)); + else + { + MOVA (aopGet (AOP (left), 0, FALSE, FALSE, NULL)); + lbl = newiTempLabel (NULL); + emitcode ("jnb", "acc.7,!tlabel", lbl->key + 100); + emitcode ("cpl", "F0"); /* complement sign flag */ + emitcode ("cpl", "a"); /* 2's complement */ + emitcode ("inc", "a"); + emitcode ("", "!tlabeldef", lbl->key + 100); + } + } + /* now the division */ emitcode ("nop", "; workaround for DS80C390 div bug."); emitcode ("div", "ab"); - /* we are interested in the lower order - only */ - emitcode ("mov", "b,a"); - lbl = newiTempLabel (NULL); - emitcode ("pop", "acc"); - /* if there was an over flow we don't - adjust the sign of the result */ - emitcode ("jb", "ov,!tlabel", (lbl->key + 100)); - emitcode ("jnb", "acc.7,!tlabel", (lbl->key + 100)); - CLRC; - emitcode ("clr", "a"); - emitcode ("subb", "a,b"); - emitcode ("mov", "b,a"); - emitcode ("", "!tlabeldef", (lbl->key + 100)); - - /* now we are done */ - _G.accInUse++; _G.bInUse++; - aopOp(result, ic, TRUE, FALSE); - - aopPut (AOP (result), "b", 0); - - size = AOP_SIZE (result) - 1; - - if (size > 0) + + if (runtimeSign || compiletimeSign) { - emitcode ("mov", "c,b.7"); - emitcode ("subb", "a,acc"); + lbl = newiTempLabel (NULL); + if (runtimeSign) + emitcode ("jnb", "F0,!tlabel", lbl->key + 100); + emitcode ("cpl", "a"); /* lsb 2's complement */ + emitcode ("inc", "a"); + emitcode ("", "!tlabeldef", lbl->key + 100); + + _G.accInUse++; _G.bInUse++; + aopOp (result, ic, TRUE, FALSE); + size = AOP_SIZE (result) - 1; + + if (size > 0) + { + /* 123 look strange, but if (OP_SYMBOL (op)->accuse == 1) + then the result will be in b, a */ + emitcode ("mov", "b,a"); /* 1 */ + /* msb is 0x00 or 0xff depending on the sign */ + if (runtimeSign) + { + emitcode ("mov", "c,F0"); + emitcode ("subb", "a,acc"); + emitcode ("xch", "a,b"); /* 2 */ + while (size--) + aopPut (AOP (result), "b", offset++); /* write msb's */ + } + else /* compiletimeSign */ + while (size--) + aopPut (AOP (result), "#0xff", offset++); /* write msb's */ + } + aopPut (AOP (result), "a", 0); /* 3: write lsb */ } - while (size--) + else { - aopPut (AOP (result), "a", offset++); + _G.accInUse++; _G.bInUse++; + aopOp(result, ic, TRUE, FALSE); + size = AOP_SIZE (result) - 1; + + aopPut (AOP (result), "a", 0); + while (size--) + aopPut (AOP (result), zero, offset++); } - _G.accInUse--; _G.bInUse--; + _G.accInUse--; _G.bInUse--; } @@ -4881,8 +5368,8 @@ static void genDivTwoByte (operand *left, operand *right, if (!umult) { emitcode("clr","F0"); lbl = newiTempLabel(NULL); - emitcode ("mov","b,%s",aopGet(AOP(left),0,FALSE,FALSE,TRUE)); - emitcode ("mov","a,%s",aopGet(AOP(left),1,FALSE,FALSE,TRUE)); + emitcode ("mov","b,%s",aopGet(AOP(left),0,FALSE,FALSE,NULL)); + emitcode ("mov","a,%s",aopGet(AOP(left),1,FALSE,FALSE,NULL)); emitcode ("jnb","acc.7,!tlabel",lbl->key+100); emitcode ("xch", "a,b"); emitcode ("cpl","a"); @@ -4895,14 +5382,14 @@ static void genDivTwoByte (operand *left, operand *right, emitcode ("mov","ma,b"); emitcode ("mov","ma,a"); } else { - emitcode ("mov","ma,%s",aopGet(AOP(left),0,FALSE,FALSE,TRUE)); - emitcode ("mov","ma,%s",aopGet(AOP(left),1,FALSE,FALSE,TRUE)); + emitcode ("mov","ma,%s",aopGet(AOP(left),0,FALSE,FALSE,NULL)); + emitcode ("mov","ma,%s",aopGet(AOP(left),1,FALSE,FALSE,NULL)); } /* load up MB with right */ if (!umult) { if (AOP_TYPE(right) == AOP_LIT) { - int val=floatFromVal (AOP (right)->aopu.aop_lit); + int val=(int)floatFromVal (AOP (right)->aopu.aop_lit); if (val < 0) { lbl = newiTempLabel(NULL); emitcode ("jbc","F0,!tlabel",lbl->key+100); @@ -4914,8 +5401,8 @@ static void genDivTwoByte (operand *left, operand *right, emitcode ("mov","mb,#!constbyte",(val >> 8) & 0xff); } else { lbl = newiTempLabel(NULL); - emitcode ("mov","b,%s",aopGet(AOP(right),0,FALSE,FALSE,TRUE)); - emitcode ("mov","a,%s",aopGet(AOP(right),1,FALSE,FALSE,TRUE)); + emitcode ("mov","b,%s",aopGet(AOP(right),0,FALSE,FALSE,NULL)); + emitcode ("mov","a,%s",aopGet(AOP(right),1,FALSE,FALSE,NULL)); emitcode ("jnb","acc.7,!tlabel",lbl->key+100); emitcode ("xch", "a,b"); emitcode ("cpl","a"); @@ -4930,8 +5417,8 @@ static void genDivTwoByte (operand *left, operand *right, emitcode ("mov","mb,a"); } } else { - emitcode ("mov","mb,%s",aopGet(AOP(right),0,FALSE,FALSE,TRUE)); - emitcode ("mov","mb,%s",aopGet(AOP(right),1,FALSE,FALSE,TRUE)); + emitcode ("mov","mb,%s",aopGet(AOP(right),0,FALSE,FALSE,NULL)); + emitcode ("mov","mb,%s",aopGet(AOP(right),1,FALSE,FALSE,NULL)); } /* wait for multiplication to finish */ @@ -5051,73 +5538,146 @@ genModOneByte (operand * left, operand * result, iCode * ic) { - sym_link *opetype = operandType (result); + bool lUnsigned, rUnsigned; + bool runtimeSign, compiletimeSign; char *l; symbol *lbl; + int size, offset; + offset = 1; + lUnsigned = SPEC_USIGN (getSpec (operandType (left))); + rUnsigned = SPEC_USIGN (getSpec (operandType (right))); + /* signed or unsigned */ - if (SPEC_USIGN (opetype)) + if (lUnsigned && rUnsigned) { /* unsigned is easy */ LOAD_AB_FOR_DIV (left, right, l); emitcode ("div", "ab"); - aopOp(result, ic, TRUE, FALSE); + aopOp (result, ic, TRUE, FALSE); aopPut (AOP (result), "b", 0); + + for (size = AOP_SIZE (result) - 1; size--;) + aopPut (AOP (result), zero, offset++); return; } /* signed is a little bit more difficult */ - /* save the signs of the operands */ - l = aopGet (AOP (left), 0, FALSE, FALSE, TRUE); - MOVA (l); - - emitcode ("xrl", "a,%s", aopGet (AOP (right), 0, FALSE, FALSE, FALSE)); - emitcode ("push", "acc"); /* save it on the stack */ - /* now sign adjust for both left & right */ - l = aopGet (AOP (right), 0, FALSE, FALSE, TRUE); - MOVA (l); - lbl = newiTempLabel (NULL); - emitcode ("jnb", "acc.7,!tlabel", (lbl->key + 100)); - emitcode ("cpl", "a"); - emitcode ("inc", "a"); - emitcode ("", "!tlabeldef", (lbl->key + 100)); - emitcode ("mov", "b,a"); + /* modulus: sign of the right operand has no influence on the result! */ + if (AOP_TYPE(right) == AOP_LIT) + { + signed char val = (char) floatFromVal (AOP (right)->aopu.aop_lit); - /* sign adjust left side */ - l = aopGet (AOP (left), 0, FALSE, FALSE, TRUE); - MOVA (l); + if (!rUnsigned && val < 0) + emitcode ("mov", "b,#0x%02x", -val); + else + emitcode ("mov", "b,#0x%02x", (unsigned char) val); + } + else /* ! literal */ + { + if (rUnsigned) + emitcode ("mov", "b,%s", aopGet (AOP (right), 0, FALSE, FALSE, NULL)); + else + { + MOVA (aopGet (AOP (right), 0, FALSE, FALSE, NULL)); + lbl = newiTempLabel (NULL); + emitcode ("jnb", "acc.7,!tlabel", lbl->key + 100); + emitcode ("cpl", "a"); /* 2's complement */ + emitcode ("inc", "a"); + emitcode ("", "!tlabeldef", lbl->key + 100); + emitcode ("mov", "b,a"); + } + } + + /* let's see what's needed: */ + /* apply negative sign during runtime */ + runtimeSign = FALSE; + /* negative sign from literals */ + compiletimeSign = FALSE; - lbl = newiTempLabel (NULL); - emitcode ("jnb", "acc.7,!tlabel", (lbl->key + 100)); - emitcode ("cpl", "a"); - emitcode ("inc", "a"); - emitcode ("", "!tlabeldef", (lbl->key + 100)); + /* sign adjust left side */ + if (AOP_TYPE(left) == AOP_LIT) + { + signed char val = (char) floatFromVal (AOP (left)->aopu.aop_lit); - /* now the multiplication */ + if (!lUnsigned && val < 0) + { + compiletimeSign = TRUE; /* set sign flag */ + emitcode ("mov", "a,#0x%02x", -val); + } + else + emitcode ("mov", "a,#0x%02x", (unsigned char) val); + } + else /* ! literal */ + { + MOVA (aopGet (AOP (left), 0, FALSE, FALSE, NULL)); + + if (!lUnsigned) + { + runtimeSign = TRUE; + emitcode ("clr", "F0"); /* clear sign flag */ + + lbl = newiTempLabel (NULL); + emitcode ("jnb", "acc.7,!tlabel", lbl->key + 100); + emitcode ("setb", "F0"); /* set sign flag */ + emitcode ("cpl", "a"); /* 2's complement */ + emitcode ("inc", "a"); + emitcode ("", "!tlabeldef", lbl->key + 100); + } + } + + /* now the modulus */ emitcode ("nop", "; workaround for DS80C390 div bug."); emitcode ("div", "ab"); - /* we are interested in the lower order - only */ - lbl = newiTempLabel (NULL); - emitcode ("pop", "acc"); - /* if there was an over flow we don't - adjust the sign of the result */ - emitcode ("jb", "ov,!tlabel", (lbl->key + 100)); - emitcode ("jnb", "acc.7,!tlabel", (lbl->key + 100)); - CLRC; - emitcode ("clr", "a"); - emitcode ("subb", "a,b"); - emitcode ("mov", "b,a"); - emitcode ("", "!tlabeldef", (lbl->key + 100)); - _G.bInUse++; - /* now we are done */ - aopOp(result, ic, TRUE, FALSE); - aopPut (AOP (result), "b", 0); - _G.bInUse--; + if (runtimeSign || compiletimeSign) + { + emitcode ("mov", "a,b"); + lbl = newiTempLabel (NULL); + if (runtimeSign) + emitcode ("jnb", "F0,!tlabel", lbl->key + 100); + emitcode ("cpl", "a"); /* lsb 2's complement */ + emitcode ("inc", "a"); + emitcode ("", "!tlabeldef", lbl->key + 100); + + _G.accInUse++; _G.bInUse++; + aopOp (result, ic, TRUE, FALSE); + size = AOP_SIZE (result) - 1; + + if (size > 0) + { + /* 123 look strange, but if (OP_SYMBOL (op)->accuse == 1) + then the result will be in b, a */ + emitcode ("mov", "b,a"); /* 1 */ + /* msb is 0x00 or 0xff depending on the sign */ + if (runtimeSign) + { + emitcode ("mov", "c,F0"); + emitcode ("subb", "a,acc"); + emitcode ("xch", "a,b"); /* 2 */ + while (size--) + aopPut (AOP (result), "b", offset++); /* write msb's */ + } + else /* compiletimeSign */ + while (size--) + aopPut (AOP (result), "#0xff", offset++); /* write msb's */ + } + aopPut (AOP (result), "a", 0); /* 3: write lsb */ + } + else + { + _G.accInUse++; _G.bInUse++; + aopOp(result, ic, TRUE, FALSE); + size = AOP_SIZE (result) - 1; + + aopPut (AOP (result), "b", 0); + while (size--) + aopPut (AOP (result), zero, offset++); + } + _G.accInUse--; _G.bInUse--; } @@ -5142,8 +5702,8 @@ static void genModTwoByte (operand *left, operand *right, if (!umult) { lbl = newiTempLabel(NULL); - emitcode ("mov","b,%s",aopGet(AOP(left),0,FALSE,FALSE,TRUE)); - emitcode ("mov","a,%s",aopGet(AOP(left),1,FALSE,FALSE,TRUE)); + emitcode ("mov","b,%s",aopGet(AOP(left),0,FALSE,FALSE,NULL)); + emitcode ("mov","a,%s",aopGet(AOP(left),1,FALSE,FALSE,NULL)); emitcode ("jnb","acc.7,!tlabel",lbl->key+100); emitcode ("xch", "a,b"); emitcode ("cpl","a"); @@ -5155,14 +5715,14 @@ static void genModTwoByte (operand *left, operand *right, emitcode ("mov","ma,b"); emitcode ("mov","ma,a"); } else { - emitcode ("mov","ma,%s",aopGet(AOP(left),0,FALSE,FALSE,TRUE)); - emitcode ("mov","ma,%s",aopGet(AOP(left),1,FALSE,FALSE,TRUE)); + emitcode ("mov","ma,%s",aopGet(AOP(left),0,FALSE,FALSE,NULL)); + emitcode ("mov","ma,%s",aopGet(AOP(left),1,FALSE,FALSE,NULL)); } /* load up MB with right */ if (!umult) { if (AOP_TYPE(right) == AOP_LIT) { - int val=floatFromVal (AOP (right)->aopu.aop_lit); + int val=(int)floatFromVal (AOP (right)->aopu.aop_lit); if (val < 0) { val = -val; } @@ -5170,8 +5730,8 @@ static void genModTwoByte (operand *left, operand *right, emitcode ("mov","mb,#!constbyte",(val >> 8) & 0xff); } else { lbl = newiTempLabel(NULL); - emitcode ("mov","b,%s",aopGet(AOP(right),0,FALSE,FALSE,TRUE)); - emitcode ("mov","a,%s",aopGet(AOP(right),1,FALSE,FALSE,TRUE)); + emitcode ("mov","b,%s",aopGet(AOP(right),0,FALSE,FALSE,NULL)); + emitcode ("mov","a,%s",aopGet(AOP(right),1,FALSE,FALSE,NULL)); emitcode ("jnb","acc.7,!tlabel",lbl->key+100); emitcode ("xch", "a,b"); emitcode ("cpl","a"); @@ -5184,8 +5744,8 @@ static void genModTwoByte (operand *left, operand *right, emitcode ("mov","mb,a"); } } else { - emitcode ("mov","mb,%s",aopGet(AOP(right),0,FALSE,FALSE,TRUE)); - emitcode ("mov","mb,%s",aopGet(AOP(right),1,FALSE,FALSE,TRUE)); + emitcode ("mov","mb,%s",aopGet(AOP(right),0,FALSE,FALSE,NULL)); + emitcode ("mov","mb,%s",aopGet(AOP(right),1,FALSE,FALSE,NULL)); } /* wait for multiplication to finish */ @@ -5307,8 +5867,7 @@ genCmp (operand * left, operand * right, unsigned long lit = 0L; operand *result; - D (emitcode (";", "genCmp"); - ); + D (emitcode (";", "genCmp");); result = IC_RESULT (ic); @@ -5317,7 +5876,7 @@ genCmp (operand * left, operand * right, AOP_TYPE (right) == AOP_CRY) { emitcode ("mov", "c,%s", AOP (right)->aopu.aop_dir); - emitcode ("anl", "c,/%s", AOP (left)->aopu.aop_dir); + emitcode ("anl", "c,%s", AOP (left)->aopu.aop_dir); } else { @@ -5327,13 +5886,13 @@ genCmp (operand * left, operand * right, size = max (AOP_SIZE (left), AOP_SIZE (right)); /* if unsigned char cmp with lit, do cjne left,#right,zz */ - if ((size == 1) && !sign && - (AOP_TYPE (right) == AOP_LIT && AOP_TYPE (left) != AOP_DIR && AOP_TYPE (left) != AOP_STR)) + if ((size == 1) && !sign + && (AOP_TYPE (right) == AOP_LIT && AOP_TYPE (left) != AOP_DIR && AOP_TYPE (left) != AOP_STR)) { symbol *lbl = newiTempLabel (NULL); emitcode ("cjne", "%s,%s,!tlabel", - aopGet (AOP (left), offset, FALSE, FALSE, FALSE), - aopGet (AOP (right), offset, FALSE, FALSE, FALSE), + aopGet (AOP (left), offset, FALSE, FALSE, NULL), + aopGet (AOP (right), offset, FALSE, FALSE, NULL), lbl->key + 100); emitcode ("", "!tlabeldef", lbl->key + 100); } @@ -5351,7 +5910,7 @@ genCmp (operand * left, operand * right, } else { - MOVA (aopGet (AOP (left), AOP_SIZE (left) - 1, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (left), AOP_SIZE (left) - 1, FALSE, FALSE, NULL)); freeAsmop (left, NULL, ic, (RESULTONSTACK (ic) ? FALSE : TRUE)); freeAsmop (right, NULL, ic, (RESULTONSTACK (ic) ? FALSE : TRUE)); @@ -5376,35 +5935,28 @@ genCmp (operand * left, operand * right, CLRC; while (size--) { - //emitcode (";", "genCmp #1: %d/%d/%d", size, sign, offset); - MOVA (aopGet (AOP (left), offset, FALSE, FALSE, TRUE)); - //emitcode (";", "genCmp #2"); + // emitcode (";", "genCmp #1: %d/%d/%d", size, sign, offset); + MOVA (aopGet (AOP (left), offset, FALSE, FALSE, NULL)); + // emitcode (";", "genCmp #2"); if (sign && (size == 0)) { - //emitcode (";", "genCmp #3"); + // emitcode (";", "genCmp #3"); emitcode ("xrl", "a,#!constbyte",0x80); if (AOP_TYPE (right) == AOP_LIT) { unsigned long lit = (unsigned long) floatFromVal (AOP (right)->aopu.aop_lit); - //emitcode (";", "genCmp #3.1"); + // emitcode (";", "genCmp #3.1"); emitcode ("subb", "a,#!constbyte", 0x80 ^ (unsigned int) ((lit >> (offset * 8)) & 0x0FFL)); } else { - //emitcode (";", "genCmp #3.2"); - if (AOP_NEEDSACC (right)) - { - emitcode ("push", "acc"); - } - emitcode ("mov", "b,%s", aopGet (AOP (right), offset++, - FALSE, FALSE, FALSE)); + // emitcode (";", "genCmp #3.2"); + saveAccWarn = 0; + MOVB(aopGet (AOP (right), offset++, FALSE, FALSE, "b")); + saveAccWarn = DEFAULT_ACC_WARNING; emitcode ("xrl", "b,#!constbyte",0x80); - if (AOP_NEEDSACC (right)) - { - emitcode ("pop", "acc"); - } emitcode ("subb", "a,b"); } } @@ -5412,21 +5964,10 @@ genCmp (operand * left, operand * right, { const char *s; - //emitcode (";", "genCmp #4"); - if (AOP_NEEDSACC (right)) - { - /* Yuck!! */ - //emitcode (";", "genCmp #4.1"); - emitcode ("xch", "a, b"); - MOVA (aopGet (AOP (right), offset++, FALSE, FALSE, TRUE)); - emitcode ("xch", "a, b"); - s = "b"; - } - else - { - //emitcode (";", "genCmp #4.2"); - s = aopGet (AOP (right), offset++, FALSE, FALSE, FALSE); - } + // emitcode (";", "genCmp #4"); + saveAccWarn = 0; + s = aopGet (AOP (right), offset++, FALSE, FALSE, "b"); + saveAccWarn = DEFAULT_ACC_WARNING; emitcode ("subb", "a,%s", s); } @@ -5533,6 +6074,7 @@ gencjneshort (operand * left, operand * right, symbol * lbl) if the right is in a pointer register and left is not */ if ((AOP_TYPE (left) == AOP_LIT) || + (AOP_TYPE (left) == AOP_IMMD) || (IS_AOP_PREG (right) && !IS_AOP_PREG (left))) { operand *t = right; @@ -5549,8 +6091,7 @@ gencjneshort (operand * left, operand * right, symbol * lbl) * Exclude the generic type byte from the comparison. */ size--; - D (emitcode (";", "cjneshort: generic ptr special case."); - ) + D (emitcode (";", "cjneshort: generic ptr special case.");); } @@ -5560,10 +6101,9 @@ gencjneshort (operand * left, operand * right, symbol * lbl) { while (size--) { - char *l = aopGet (AOP (left), offset, FALSE, FALSE, TRUE); - MOVA (l); + MOVA (aopGet (AOP (left), offset, FALSE, FALSE, NULL)); emitcode ("cjne", "a,%s,!tlabel", - aopGet (AOP (right), offset, FALSE, FALSE, FALSE), + aopGet (AOP (right), offset, FALSE, FALSE, NULL), lbl->key + 100); offset++; } @@ -5573,18 +6113,20 @@ gencjneshort (operand * left, operand * right, symbol * lbl) if the left is a pointer register & right is not */ else if (AOP_TYPE (right) == AOP_REG || AOP_TYPE (right) == AOP_DIR || + AOP_TYPE (right) == AOP_LIT || + AOP_TYPE (right) == AOP_IMMD || (AOP_TYPE (left) == AOP_DIR && AOP_TYPE (right) == AOP_LIT) || (IS_AOP_PREG (left) && !IS_AOP_PREG (right))) { while (size--) { - MOVA (aopGet (AOP (left), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (left), offset, FALSE, FALSE, NULL)); if ((AOP_TYPE (left) == AOP_DIR && AOP_TYPE (right) == AOP_LIT) && ((unsigned int) ((lit >> (offset * 8)) & 0x0FFL) == 0)) emitcode ("jnz", "!tlabel", lbl->key + 100); else emitcode ("cjne", "a,%s,!tlabel", - aopGet (AOP (right), offset, FALSE, TRUE, FALSE), + aopGet (AOP (right), offset, FALSE, TRUE, DP2_RESULT_REG), lbl->key + 100); offset++; } @@ -5594,10 +6136,8 @@ gencjneshort (operand * left, operand * right, symbol * lbl) /* right is a pointer reg need both a & b */ while (size--) { - char *l = aopGet (AOP (left), offset, FALSE, FALSE, TRUE); - if (strcmp (l, "b")) - emitcode ("mov", "b,%s", l); - MOVA (aopGet (AOP (right), offset, FALSE, FALSE, TRUE)); + MOVB (aopGet (AOP (left), offset, FALSE, FALSE, NULL)); + MOVA (aopGet (AOP (right), offset, FALSE, FALSE, NULL)); emitcode ("cjne", "a,b,!tlabel", lbl->key + 100); offset++; } @@ -6044,9 +6584,9 @@ genFarFarLogicOp(iCode *ic, char *logicOp) _startLazyDPSEvaluation(); for (size = compSize; (size--); offset++) { - MOVA (aopGet (AOP (IC_LEFT(ic)), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (IC_LEFT(ic)), offset, FALSE, FALSE, NULL)); emitcode ("mov", "%s, acc", DP2_RESULT_REG); - MOVA (aopGet (AOP (IC_RIGHT(ic)), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (IC_RIGHT(ic)), offset, FALSE, FALSE, NULL)); emitcode (logicOp, "a,%s", DP2_RESULT_REG); emitcode ("push", "acc"); @@ -6081,7 +6621,7 @@ genAnd (iCode * ic, iCode * ifx) operand *left, *right, *result; int size, offset = 0; unsigned long lit = 0L; - int bytelit = 0; + int bytelit; char buff[10]; bool pushResult; @@ -6179,7 +6719,7 @@ genAnd (iCode * ic, iCode * ifx) else { // c = bit & val; - MOVA (aopGet (AOP (right), 0, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (right), 0, FALSE, FALSE, NULL)); // c = lsb emitcode ("rrc", "a"); emitcode ("anl", "c,%s", AOP (left)->aopu.aop_dir); @@ -6206,7 +6746,7 @@ genAnd (iCode * ic, iCode * ifx) if (posbit) { posbit--; - MOVA (aopGet (AOP (left), posbit >> 3, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (left), posbit >> 3, FALSE, FALSE, NULL)); // bit = left & 2^n if (size) emitcode ("mov", "c,acc.%d", posbit & 0x07); @@ -6236,7 +6776,7 @@ genAnd (iCode * ic, iCode * ifx) { if ((bytelit = ((lit >> (offset * 8)) & 0x0FFL)) != 0x0L) { - MOVA (aopGet (AOP (left), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (left), offset, FALSE, FALSE, NULL)); // byte == 2^n ? if ((posbit = isLiteralBit (bytelit)) != 0) emitcode ("jb", "acc.%d,!tlabel", (posbit - 1) & 0x07, tlbl->key + 100); @@ -6244,7 +6784,7 @@ genAnd (iCode * ic, iCode * ifx) { if (bytelit != 0x0FFL) emitcode ("anl", "a,%s", - aopGet (AOP (right), offset, FALSE, TRUE, FALSE)); + aopGet (AOP (right), offset, FALSE, TRUE, DP2_RESULT_REG)); emitcode ("jnz", "!tlabel", tlbl->key + 100); } } @@ -6261,6 +6801,8 @@ genAnd (iCode * ic, iCode * ifx) { if (ifx) jmpTrueOrFalse (ifx, tlbl); + else + emitcode ("", "!tlabeldef", tlbl->key + 100); goto release; } } @@ -6281,31 +6823,33 @@ genAnd (iCode * ic, iCode * ifx) aopPut (AOP (result), zero, offset); else if (IS_AOP_PREG (result)) { - MOVA (aopGet (AOP (right), offset, FALSE, FALSE, TRUE)); - emitcode ("anl", "a,%s", aopGet (AOP (left), offset, FALSE, TRUE, FALSE)); + MOVA (aopGet (AOP (right), offset, FALSE, FALSE, NULL)); + emitcode ("anl", "a,%s", + aopGet (AOP (left), offset, FALSE, TRUE, DP2_RESULT_REG)); aopPut (AOP (result), "a", offset); } else emitcode ("anl", "%s,%s", - aopGet (AOP (left), offset, FALSE, TRUE, FALSE), - aopGet (AOP (right), offset, FALSE, FALSE, FALSE)); + aopGet (AOP (left), offset, FALSE, TRUE, NULL), + aopGet (AOP (right), offset, FALSE, FALSE, NULL)); } else { if (AOP_TYPE (left) == AOP_ACC) - emitcode ("anl", "a,%s", aopGet (AOP (right), offset, FALSE, FALSE, FALSE)); + emitcode ("anl", "a,%s", + aopGet (AOP (right), offset, FALSE, FALSE, DP2_RESULT_REG)); else { - MOVA (aopGet (AOP (right), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (right), offset, FALSE, FALSE, NULL)); if (IS_AOP_PREG (result)) { - emitcode ("anl", "a,%s", aopGet (AOP (left), offset, FALSE, TRUE, FALSE)); + emitcode ("anl", "a,%s", + aopGet (AOP (left), offset, FALSE, TRUE, DP2_RESULT_REG)); aopPut (AOP (result), "a", offset); - } else emitcode ("anl", "%s,a", - aopGet (AOP (left), offset, FALSE, TRUE, FALSE)); + aopGet (AOP (left), offset, FALSE, TRUE, DP2_RESULT_REG)); } } } @@ -6326,16 +6870,16 @@ genAnd (iCode * ic, iCode * ifx) { if (AOP_TYPE(right)==AOP_REG && AOP_TYPE(left)==AOP_ACC) { emitcode ("anl", "a,%s", - aopGet (AOP (right), offset, FALSE, FALSE, FALSE)); + aopGet (AOP (right), offset, FALSE, FALSE, DP2_RESULT_REG)); } else { if (AOP_TYPE(left)==AOP_ACC) { emitcode("mov", "b,a"); - MOVA (aopGet (AOP (right), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (right), offset, FALSE, FALSE, NULL)); emitcode("anl", "a,b"); }else { - MOVA (aopGet (AOP (right), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (right), offset, FALSE, FALSE, NULL)); emitcode ("anl", "a,%s", - aopGet (AOP (left), offset, FALSE, FALSE, FALSE)); + aopGet (AOP (left), offset, FALSE, FALSE, DP2_RESULT_REG)); } } emitcode ("jnz", "!tlabel", tlbl->key + 100); @@ -6349,6 +6893,8 @@ genAnd (iCode * ic, iCode * ifx) } else if (ifx) jmpTrueOrFalse (ifx, tlbl); + else + emitcode ("", "!tlabeldef", tlbl->key + 100); } else { @@ -6361,7 +6907,7 @@ genAnd (iCode * ic, iCode * ifx) if ((bytelit = (int) ((lit >> (offset * 8)) & 0x0FFL)) == 0x0FF) { aopPut (AOP (result), - aopGet (AOP (left), offset, FALSE, FALSE, FALSE), + aopGet (AOP (left), offset, FALSE, FALSE, NULL), offset); continue; } @@ -6371,9 +6917,9 @@ genAnd (iCode * ic, iCode * ifx) continue; } D (emitcode (";", "better literal AND.");); - MOVA (aopGet (AOP (left), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (left), offset, FALSE, FALSE, NULL)); emitcode ("anl", "a, %s", aopGet (AOP (right), offset, - FALSE, FALSE, FALSE)); + FALSE, FALSE, DP2_RESULT_REG)); } else @@ -6382,19 +6928,19 @@ genAnd (iCode * ic, iCode * ifx) // and better if result is SFR if (AOP_TYPE (left) == AOP_ACC) { - emitcode ("anl", "a,%s", aopGet (AOP (right), offset, - FALSE, FALSE, FALSE)); + emitcode ("anl", "a,%s", + aopGet (AOP (right), offset, FALSE, FALSE, DP2_RESULT_REG)); } else { - char *rOp = aopGet (AOP (right), offset, FALSE, FALSE, TRUE); + char *rOp = aopGet (AOP (right), offset, FALSE, FALSE, NULL); if (!strcmp(rOp, "a") || !strcmp(rOp, "acc")) { emitcode("mov", "b,a"); rOp = "b"; } - MOVA (aopGet (AOP (left), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (left), offset, FALSE, FALSE, NULL)); emitcode ("anl", "a,%s", rOp); } } @@ -6596,15 +7142,16 @@ genOr (iCode * ic, iCode * ifx) { if (IS_AOP_PREG (left)) { - MOVA (aopGet (AOP (right), offset, FALSE, FALSE, TRUE)); - emitcode ("orl", "a,%s", aopGet (AOP (left), offset, FALSE, TRUE, FALSE)); + MOVA (aopGet (AOP (right), offset, FALSE, FALSE, NULL)); + emitcode ("orl", "a,%s", + aopGet (AOP (left), offset, FALSE, TRUE, DP2_RESULT_REG)); aopPut (AOP (result), "a", offset); } else { emitcode ("orl", "%s,%s", - aopGet (AOP (left), offset, FALSE, TRUE, FALSE), - aopGet (AOP (right), offset, FALSE, FALSE, FALSE)); + aopGet (AOP (left), offset, FALSE, TRUE, NULL), + aopGet (AOP (right), offset, FALSE, FALSE, DP2_RESULT_REG)); } } } @@ -6612,20 +7159,22 @@ genOr (iCode * ic, iCode * ifx) { if (AOP_TYPE (left) == AOP_ACC) { - emitcode ("orl", "a,%s", aopGet (AOP (right), offset, FALSE, FALSE, FALSE)); + emitcode ("orl", "a,%s", + aopGet (AOP (right), offset, FALSE, FALSE, DP2_RESULT_REG)); } else { - MOVA (aopGet (AOP (right), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (right), offset, FALSE, FALSE, NULL)); if (IS_AOP_PREG (left)) { - emitcode ("orl", "a,%s", aopGet (AOP (left), offset, FALSE, TRUE, FALSE)); + emitcode ("orl", "a,%s", + aopGet (AOP (left), offset, FALSE, TRUE, DP2_RESULT_REG)); aopPut (AOP (result), "a", offset); } else { emitcode ("orl", "%s,a", - aopGet (AOP (left), offset, FALSE, TRUE, FALSE)); + aopGet (AOP (left), offset, FALSE, TRUE, DP2_RESULT_REG)); } } } @@ -6647,11 +7196,11 @@ genOr (iCode * ic, iCode * ifx) { if (AOP_TYPE(right)==AOP_REG && AOP_TYPE(left)==AOP_ACC) { emitcode ("orl", "a,%s", - aopGet (AOP (right), offset, FALSE, FALSE, FALSE)); + aopGet (AOP (right), offset, FALSE, FALSE, DP2_RESULT_REG)); } else { - MOVA (aopGet (AOP (right), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (right), offset, FALSE, FALSE, NULL)); emitcode ("orl", "a,%s", - aopGet (AOP (left), offset, FALSE, FALSE, FALSE)); + aopGet (AOP (left), offset, FALSE, FALSE, DP2_RESULT_REG)); } emitcode ("jnz", "!tlabel", tlbl->key + 100); offset++; @@ -6664,6 +7213,8 @@ genOr (iCode * ic, iCode * ifx) } else if (ifx) jmpTrueOrFalse (ifx, tlbl); + else + emitcode ("", "!tlabeldef", tlbl->key + 100); } else { @@ -6677,14 +7228,15 @@ genOr (iCode * ic, iCode * ifx) if (((lit >> (offset * 8)) & 0x0FFL) == 0x00L) { aopPut (AOP (result), - aopGet (AOP (left), offset, FALSE, FALSE, FALSE), + aopGet (AOP (left), offset, FALSE, FALSE, NULL), offset); continue; } D (emitcode (";", "better literal OR.");); - MOVA (aopGet (AOP (left), offset, FALSE, FALSE, TRUE)); - emitcode ("orl", "a, %s", aopGet (AOP (right), offset, - FALSE, FALSE, FALSE)); + MOVA (aopGet (AOP (left), offset, FALSE, FALSE, NULL)); + emitcode ("orl", "a, %s", + aopGet (AOP (right), offset, + FALSE, FALSE, DP2_RESULT_REG)); } else @@ -6693,12 +7245,13 @@ genOr (iCode * ic, iCode * ifx) // and better if result is SFR if (AOP_TYPE (left) == AOP_ACC) { - emitcode ("orl", "a,%s", aopGet (AOP (right), offset, - FALSE, FALSE, FALSE)); + emitcode ("orl", "a,%s", + aopGet (AOP (right), offset, + FALSE, FALSE, DP2_RESULT_REG)); } else { - char *rOp = aopGet (AOP (right), offset, FALSE, FALSE, TRUE); + char *rOp = aopGet (AOP (right), offset, FALSE, FALSE, NULL); if (!strcmp(rOp, "a") || !strcmp(rOp, "acc")) { @@ -6706,7 +7259,7 @@ genOr (iCode * ic, iCode * ifx) rOp = "b"; } - MOVA (aopGet (AOP (left), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (left), offset, FALSE, FALSE, NULL)); emitcode ("orl", "a,%s", rOp); } } @@ -6851,7 +7404,7 @@ genXor (iCode * ic, iCode * ifx) emitcode ("setb", "c"); while (sizer) { - MOVA (aopGet (AOP (right), sizer - 1, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (right), sizer - 1, FALSE, FALSE, NULL)); if (sizer == 1) // test the msb of the lsb emitcode ("anl", "a,#!constbyte",0xfe); @@ -6886,30 +7439,33 @@ genXor (iCode * ic, iCode * ifx) continue; else if (IS_AOP_PREG (left)) { - MOVA (aopGet (AOP (right), offset, FALSE, FALSE, TRUE)); - emitcode ("xrl", "a,%s", aopGet (AOP (left), offset, FALSE, TRUE, FALSE)); + MOVA (aopGet (AOP (right), offset, FALSE, FALSE, NULL)); + emitcode ("xrl", "a,%s", + aopGet (AOP (left), offset, FALSE, TRUE, DP2_RESULT_REG)); aopPut (AOP (result), "a", offset); } else emitcode ("xrl", "%s,%s", - aopGet (AOP (left), offset, FALSE, TRUE, FALSE), - aopGet (AOP (right), offset, FALSE, FALSE, FALSE)); + aopGet (AOP (left), offset, FALSE, TRUE, NULL), + aopGet (AOP (right), offset, FALSE, FALSE, DP2_RESULT_REG)); } else { if (AOP_TYPE (left) == AOP_ACC) - emitcode ("xrl", "a,%s", aopGet (AOP (right), offset, FALSE, FALSE, FALSE)); + emitcode ("xrl", "a,%s", + aopGet (AOP (right), offset, FALSE, FALSE, DP2_RESULT_REG)); else { - MOVA (aopGet (AOP (right), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (right), offset, FALSE, FALSE, NULL)); if (IS_AOP_PREG (left)) { - emitcode ("xrl", "a,%s", aopGet (AOP (left), offset, FALSE, TRUE, FALSE)); + emitcode ("xrl", "a,%s", + aopGet (AOP (left), offset, FALSE, TRUE, DP2_RESULT_REG)); aopPut (AOP (result), "a", offset); } else emitcode ("xrl", "%s,a", - aopGet (AOP (left), offset, FALSE, TRUE, FALSE)); + aopGet (AOP (left), offset, FALSE, TRUE, DP2_RESULT_REG)); } } } @@ -6932,22 +7488,22 @@ genXor (iCode * ic, iCode * ifx) if ((AOP_TYPE (right) == AOP_LIT) && (((lit >> (offset * 8)) & 0x0FFL) == 0x00L)) { - MOVA (aopGet (AOP (left), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (left), offset, FALSE, FALSE, NULL)); } else { if (AOP_TYPE(right)==AOP_REG && AOP_TYPE(left)==AOP_ACC) { emitcode ("xrl", "a,%s", - aopGet (AOP (right), offset, FALSE, FALSE, FALSE)); + aopGet (AOP (right), offset, FALSE, FALSE, DP2_RESULT_REG)); } else { - char *rOp = aopGet (AOP (right), offset, FALSE, FALSE, TRUE); + char *rOp = aopGet (AOP (right), offset, FALSE, FALSE, NULL); if (!strcmp(rOp, "a") || !strcmp(rOp, "acc")) { emitcode("mov", "b,a"); rOp = "b"; } - MOVA (aopGet (AOP (left), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (left), offset, FALSE, FALSE, NULL)); emitcode ("xrl", "a,%s", rOp); } } @@ -6974,14 +7530,14 @@ genXor (iCode * ic, iCode * ifx) if (((lit >> (offset * 8)) & 0x0FFL) == 0x00L) { aopPut (AOP (result), - aopGet (AOP (left), offset, FALSE, FALSE, FALSE), + aopGet (AOP (left), offset, FALSE, FALSE, NULL), offset); continue; } D (emitcode (";", "better literal XOR.");); - MOVA (aopGet (AOP (left), offset, FALSE, FALSE, TRUE)); - emitcode ("xrl", "a, %s", aopGet (AOP (right), offset, - FALSE, FALSE, FALSE)); + MOVA (aopGet (AOP (left), offset, FALSE, FALSE, NULL)); + emitcode ("xrl", "a, %s", + aopGet (AOP (right), offset, FALSE, FALSE, DP2_RESULT_REG)); } else { @@ -6989,19 +7545,20 @@ genXor (iCode * ic, iCode * ifx) // and better if result is SFR if (AOP_TYPE (left) == AOP_ACC) { - emitcode ("xrl", "a,%s", aopGet (AOP (right), offset, - FALSE, FALSE, FALSE)); + emitcode ("xrl", "a,%s", + aopGet (AOP (right), offset, + FALSE, FALSE, DP2_RESULT_REG)); } else { - char *rOp = aopGet (AOP (right), offset, FALSE, FALSE, TRUE); + char *rOp = aopGet (AOP (right), offset, FALSE, FALSE, NULL); if (!strcmp(rOp, "a") || !strcmp(rOp, "acc")) { emitcode("mov", "b,a"); rOp = "b"; } - MOVA (aopGet (AOP (left), offset, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (left), offset, FALSE, FALSE, NULL)); emitcode ("xrl", "a,%s", rOp); } } @@ -7069,17 +7626,15 @@ static void genRRC (iCode * ic) { operand *left, *result; - int size, offset = 0; - char *l; + int size, offset; - D (emitcode (";", "genRRC "); - ); + D (emitcode (";", "genRRC ");); /* rotate right with carry */ left = IC_LEFT (ic); result = IC_RESULT (ic); aopOp (left, ic, FALSE, FALSE); - aopOp (result, ic, FALSE, AOP_TYPE (left) == AOP_DPTR); + aopOp (result, ic, FALSE, AOP_USESDPTR(left)); /* move it to the result */ size = AOP_SIZE (result); @@ -7089,8 +7644,7 @@ genRRC (iCode * ic) _startLazyDPSEvaluation (); while (size--) { - l = aopGet (AOP (left), offset, FALSE, FALSE, TRUE); - MOVA (l); + MOVA (aopGet (AOP (left), offset, FALSE, FALSE, NULL)); emitcode ("rrc", "a"); if (AOP_SIZE (result) > 1) aopPut (AOP (result), "a", offset--); @@ -7101,8 +7655,7 @@ genRRC (iCode * ic) highest order byte of the result */ if (AOP_SIZE (result) > 1) { - l = aopGet (AOP (result), AOP_SIZE (result) - 1, FALSE, FALSE, TRUE); - MOVA (l); + MOVA (aopGet (AOP (result), AOP_SIZE (result) - 1, FALSE, FALSE, NULL)); } emitcode ("mov", "acc.7,c"); aopPut (AOP (result), "a", AOP_SIZE (result) - 1); @@ -7117,24 +7670,23 @@ static void genRLC (iCode * ic) { operand *left, *result; - int size, offset = 0; + int size, offset; char *l; - D (emitcode (";", "genRLC "); - ); + D (emitcode (";", "genRLC ");); /* rotate right with carry */ left = IC_LEFT (ic); result = IC_RESULT (ic); aopOp (left, ic, FALSE, FALSE); - aopOp (result, ic, FALSE, AOP_TYPE (left) == AOP_DPTR); + aopOp (result, ic, FALSE, AOP_USESDPTR(left)); /* move it to the result */ size = AOP_SIZE (result); offset = 0; if (size--) { - l = aopGet (AOP (left), offset, FALSE, FALSE, TRUE); + l = aopGet (AOP (left), offset, FALSE, FALSE, NULL); MOVA (l); emitcode ("add", "a,acc"); if (AOP_SIZE (result) > 1) @@ -7145,7 +7697,7 @@ genRLC (iCode * ic) _startLazyDPSEvaluation (); while (size--) { - l = aopGet (AOP (left), offset, FALSE, FALSE, TRUE); + l = aopGet (AOP (left), offset, FALSE, FALSE, NULL); MOVA (l); emitcode ("rlc", "a"); if (AOP_SIZE (result) > 1) @@ -7157,7 +7709,7 @@ genRLC (iCode * ic) highest order byte of the result */ if (AOP_SIZE (result) > 1) { - l = aopGet (AOP (result), 0, FALSE, FALSE, TRUE); + l = aopGet (AOP (result), 0, FALSE, FALSE, NULL); MOVA (l); } emitcode ("mov", "acc.0,c"); @@ -7176,13 +7728,12 @@ genGetHbit (iCode * ic) left = IC_LEFT (ic); result = IC_RESULT (ic); aopOp (left, ic, FALSE, FALSE); - aopOp (result, ic, FALSE, AOP_TYPE (left) == AOP_DPTR); + aopOp (result, ic, FALSE, AOP_USESDPTR(left)); - D (emitcode (";", "genGetHbit "); - ); + D (emitcode (";", "genGetHbit ");); /* get the highest order byte into a */ - MOVA (aopGet (AOP (left), AOP_SIZE (left) - 1, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (left), AOP_SIZE (left) - 1, FALSE, FALSE, NULL)); if (AOP_TYPE (result) == AOP_CRY) { emitcode ("rlc", "a"); @@ -7200,6 +7751,65 @@ genGetHbit (iCode * ic) freeAsmop (result, NULL, ic, TRUE); } +/*-----------------------------------------------------------------*/ +/* genSwap - generates code to swap nibbles or bytes */ +/*-----------------------------------------------------------------*/ +static void +genSwap (iCode * ic) +{ + operand *left, *result; + + D(emitcode ("; genSwap","")); + + left = IC_LEFT (ic); + result = IC_RESULT (ic); + aopOp (left, ic, FALSE, FALSE); + aopOp (result, ic, FALSE, AOP_USESDPTR(left)); + + _startLazyDPSEvaluation (); + switch (AOP_SIZE (left)) + { + case 1: /* swap nibbles in byte */ + MOVA (aopGet (AOP (left), 0, FALSE, FALSE, NULL)); + emitcode ("swap", "a"); + aopPut (AOP (result), "a", 0); + break; + case 2: /* swap bytes in word */ + if (AOP_TYPE(left) == AOP_REG && sameRegs(AOP(left), AOP(result))) + { + MOVA (aopGet (AOP (left), 0, FALSE, FALSE, NULL)); + aopPut (AOP (result), aopGet (AOP (left), 1, FALSE, FALSE, NULL), 0); + aopPut (AOP (result), "a", 1); + } + else if (operandsEqu (left, result)) + { + char * reg = "a"; + MOVA (aopGet (AOP (left), 0, FALSE, FALSE, NULL)); + if (AOP_NEEDSACC (left) || AOP_NEEDSACC (result)) + { + emitcode ("mov", "b,a"); + reg = "b"; + _G.bInUse=1; + } + aopPut (AOP (result), aopGet (AOP (left), 1, FALSE, FALSE, NULL), 0); + aopPut (AOP (result), reg, 1); + _G.bInUse=0; + } + else + { + aopPut (AOP (result), aopGet (AOP (left), 1, FALSE, FALSE, NULL), 0); + aopPut (AOP (result), aopGet (AOP (left), 0, FALSE, FALSE, NULL), 1); + } + break; + default: + wassertl(FALSE, "unsupported SWAP operand size"); + } + _endLazyDPSEvaluation (); + + freeAsmop (left, NULL, ic, TRUE); + freeAsmop (result, NULL, ic, TRUE); +} + /*-----------------------------------------------------------------*/ /* AccRol - rotate left accumulator by known count */ /*-----------------------------------------------------------------*/ @@ -7335,7 +7945,7 @@ shiftR1Left2Result (operand * left, int offl, operand * result, int offr, int shCount, int sign) { - MOVA (aopGet (AOP (left), offl, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (left), offl, FALSE, FALSE, NULL)); /* shift right accumulator */ if (sign) AccSRsh (shCount); @@ -7353,7 +7963,7 @@ static void shiftL1Left2Result (operand * left, int offl, operand * result, int offr, int shCount) { - MOVA(aopGet (AOP (left), offl, FALSE, FALSE, TRUE)); + MOVA(aopGet (AOP (left), offl, FALSE, FALSE, NULL)); /* shift left accumulator */ AccLsh (shCount); aopPut (AOP (result), "a", offr); @@ -7371,7 +7981,7 @@ movLeft2Result (operand * left, int offl, char *l; if (!sameRegs (AOP (left), AOP (result)) || (offl != offr)) { - l = aopGet (AOP (left), offl, FALSE, FALSE, TRUE); + l = aopGet (AOP (left), offl, FALSE, FALSE, NULL); if (*l == '@' && (IS_AOP_PREG (result))) { @@ -7735,22 +8345,22 @@ _loadLeftIntoAx(char **lsb, if (AOP_TYPE(left) == AOP_DPTR2) { // Get MSB in A. - MOVA(aopGet(AOP(left), offl + MSB16, FALSE, FALSE, TRUE)); + MOVA(aopGet(AOP(left), offl + MSB16, FALSE, FALSE, NULL)); // get LSB in DP2_RESULT_REG. - leftByte = aopGet(AOP(left), offl, FALSE, FALSE, FALSE); + leftByte = aopGet(AOP(left), offl, FALSE, FALSE, DP2_RESULT_REG); assert(!strcmp(leftByte, DP2_RESULT_REG)); } else { // get LSB into DP2_RESULT_REG - leftByte = aopGet (AOP(left), offl, FALSE, FALSE, TRUE); + leftByte = aopGet (AOP(left), offl, FALSE, FALSE, NULL); if (strcmp(leftByte, DP2_RESULT_REG)) { TR_AP("#7"); emitcode("mov","%s,%s", DP2_RESULT_REG, leftByte); } // And MSB in A. - leftByte = aopGet(AOP(left), offl + MSB16, FALSE, FALSE, TRUE); + leftByte = aopGet(AOP(left), offl + MSB16, FALSE, FALSE, NULL); assert(strcmp(leftByte, DP2_RESULT_REG)); MOVA(leftByte); } @@ -7763,16 +8373,16 @@ _loadLeftIntoAx(char **lsb, ((offl + MSB16) == offr)) { /* don't crash result[offr] */ - MOVA(aopGet(AOP(left), offl, FALSE, FALSE, TRUE)); + MOVA(aopGet(AOP(left), offl, FALSE, FALSE, NULL)); emitcode ("xch", "a,%s", - aopGet(AOP(left), offl + MSB16, FALSE, FALSE, FALSE)); + aopGet(AOP(left), offl + MSB16, FALSE, FALSE, DP2_RESULT_REG)); } else { movLeft2Result (left, offl, result, offr, 0); - MOVA (aopGet (AOP (left), offl + MSB16, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (left), offl + MSB16, FALSE, FALSE, NULL)); } - *lsb = aopGet(AOP (result), offr, FALSE, FALSE, FALSE); + *lsb = aopGet(AOP (result), offr, FALSE, FALSE, DP2_RESULT_REG); assert(strcmp(*lsb,"a")); } } @@ -7842,8 +8452,6 @@ shiftR2Left2Result (operand * left, int offl, } #endif -#if 0 -//REMOVE ME!!! /*-----------------------------------------------------------------*/ /* shiftLLeftOrResult - shift left one byte from left, or to result */ /*-----------------------------------------------------------------*/ @@ -7851,15 +8459,15 @@ static void shiftLLeftOrResult (operand * left, int offl, operand * result, int offr, int shCount) { - MOVA (aopGet (AOP (left), offl, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (left), offl, FALSE, FALSE, NULL)); /* shift left accumulator */ AccLsh (shCount); /* or with result */ - emitcode ("orl", "a,%s", aopGet (AOP (result), offr, FALSE, FALSE, FALSE)); + emitcode ("orl", "a,%s", + aopGet (AOP (result), offr, FALSE, FALSE, DP2_RESULT_REG)); /* back to result */ aopPut (AOP (result), "a", offr); } -#endif #if 0 //REMOVE ME!!! @@ -7870,11 +8478,12 @@ static void shiftRLeftOrResult (operand * left, int offl, operand * result, int offr, int shCount) { - MOVA (aopGet (AOP (left), offl, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (left), offl, FALSE, FALSE, NULL)); /* shift right accumulator */ AccRsh (shCount); /* or with result */ - emitcode ("orl", "a,%s", aopGet (AOP (result), offr, FALSE, FALSE, FALSE)); + emitcode ("orl", "a,%s", + aopGet (AOP (result), offr, FALSE, FALSE, DP2_RESULT_REG)); /* back to result */ aopPut (AOP (result), "a", offr); } @@ -7963,13 +8572,13 @@ shiftLLong (operand * left, operand * result, int offr) if (size >= LSB + offr) { - l = aopGet (AOP (left), LSB, FALSE, FALSE, TRUE); + l = aopGet (AOP (left), LSB, FALSE, FALSE, NULL); MOVA (l); emitcode ("add", "a,acc"); if (sameRegs (AOP (left), AOP (result)) && size >= MSB16 + offr && offr != LSB) emitcode ("xch", "a,%s", - aopGet (AOP (left), LSB + offr, FALSE, FALSE, FALSE)); + aopGet (AOP (left), LSB + offr, FALSE, FALSE, DP2_RESULT_REG)); else aopPut (AOP (result), "a", LSB + offr); } @@ -7978,14 +8587,13 @@ shiftLLong (operand * left, operand * result, int offr) { if (!(sameRegs (AOP (result), AOP (left)) && size >= MSB16 + offr && offr != LSB)) { - l = aopGet (AOP (left), MSB16, FALSE, FALSE, TRUE); - MOVA (l); + MOVA (aopGet (AOP (left), MSB16, FALSE, FALSE, TRUE)); } emitcode ("rlc", "a"); if (sameRegs (AOP (left), AOP (result)) && size >= MSB24 + offr && offr != LSB) emitcode ("xch", "a,%s", - aopGet (AOP (left), MSB16 + offr, FALSE, FALSE, FALSE)); + aopGet (AOP (left), MSB16 + offr, FALSE, FALSE, DP2_RESULT_REG)); else aopPut (AOP (result), "a", MSB16 + offr); } @@ -7994,14 +8602,13 @@ shiftLLong (operand * left, operand * result, int offr) { if (!(sameRegs (AOP (left), AOP (left)) && size >= MSB24 + offr && offr != LSB)) { - l = aopGet (AOP (left), MSB24, FALSE, FALSE, TRUE); - MOVA (l); + MOVA (aopGet (AOP (left), MSB24, FALSE, FALSE, NULL)); } emitcode ("rlc", "a"); if (sameRegs (AOP (left), AOP (result)) && size >= MSB32 + offr && offr != LSB) emitcode ("xch", "a,%s", - aopGet (AOP (left), MSB24 + offr, FALSE, FALSE, FALSE)); + aopGet (AOP (left), MSB24 + offr, FALSE, FALSE, DP2_RESULT_REG)); else aopPut (AOP (result), "a", MSB24 + offr); } @@ -8010,8 +8617,7 @@ shiftLLong (operand * left, operand * result, int offr) { if (!(sameRegs (AOP (result), AOP (left)) && size >= MSB32 + offr && offr != LSB)) { - l = aopGet (AOP (left), MSB32, FALSE, FALSE, TRUE); - MOVA (l); + MOVA (aopGet (AOP (left), MSB32, FALSE, FALSE, NULL)); } emitcode ("rlc", "a"); aopPut (AOP (result), "a", MSB32 + offr); @@ -8150,7 +8756,7 @@ genLeftShiftLiteral (operand * left, freeAsmop (right, NULL, ic, TRUE); aopOp(left, ic, FALSE, FALSE); - aopOp(result, ic, FALSE, (AOP_TYPE(left) == AOP_DPTR)); + aopOp(result, ic, FALSE, AOP_USESDPTR(left)); #if 0 // debug spew if (IS_SYMOP(left) && OP_SYMBOL(left)->aop) @@ -8271,12 +8877,12 @@ genLeftShift (iCode * ic) } else { - emitcode ("mov", "b,%s", aopGet (AOP (right), 0, FALSE, FALSE, FALSE)); - emitcode ("inc", "b"); + MOVB(aopGet (AOP (right), 0, FALSE, FALSE, "b")); + emitcode ("inc", "b"); } freeAsmop (right, NULL, ic, TRUE); aopOp (left, ic, FALSE, FALSE); - aopOp (result, ic, FALSE, AOP_TYPE (left) == AOP_DPTR); + aopOp (result, ic, FALSE, AOP_USESDPTR(left)); /* now move the left to the result if they are not the same */ @@ -8289,7 +8895,7 @@ genLeftShift (iCode * ic) _startLazyDPSEvaluation (); while (size--) { - l = aopGet (AOP (left), offset, FALSE, TRUE, FALSE); + l = aopGet (AOP (left), offset, FALSE, TRUE, NULL); if (*l == '@' && (IS_AOP_PREG (result))) { @@ -8313,8 +8919,7 @@ genLeftShift (iCode * ic) { symbol *tlbl1 = newiTempLabel (NULL); - l = aopGet (AOP (left), 0, FALSE, FALSE, TRUE); - MOVA (l); + MOVA (aopGet (AOP (left), 0, FALSE, FALSE, NULL)); emitcode ("sjmp", "!tlabel", tlbl1->key + 100); emitcode ("", "!tlabeldef", tlbl->key + 100); emitcode ("add", "a,acc"); @@ -8328,15 +8933,13 @@ genLeftShift (iCode * ic) emitcode ("sjmp", "!tlabel", tlbl1->key + 100); emitcode ("", "!tlabeldef", tlbl->key + 100); - l = aopGet (AOP (result), offset, FALSE, FALSE, TRUE); - MOVA (l); + MOVA (aopGet (AOP (result), offset, FALSE, FALSE, NULL)); emitcode ("add", "a,acc"); aopPut (AOP (result), "a", offset++); _startLazyDPSEvaluation (); while (--size) { - l = aopGet (AOP (result), offset, FALSE, FALSE, TRUE); - MOVA (l); + MOVA (aopGet (AOP (result), offset, FALSE, FALSE, NULL)); emitcode ("rlc", "a"); aopPut (AOP (result), "a", offset++); } @@ -8399,8 +9002,6 @@ genrshTwo (operand * result, operand * left, } #endif -#if 0 -//REMOVE ME!!! /*-----------------------------------------------------------------*/ /* shiftRLong - shift right one long from left to result */ /* offl = LSB or MSB16 */ @@ -8416,14 +9017,15 @@ shiftRLong (operand * left, int offl, werror(E_INTERNAL_ERROR, __FILE__, __LINE__); } - MOVA (aopGet (AOP (left), MSB32, FALSE, FALSE)); + MOVA (aopGet (AOP (left), MSB32, FALSE, FALSE, NULL)); if (offl==MSB16) { // shift is > 8 if (sign) { emitcode ("rlc", "a"); emitcode ("subb", "a,acc"); - emitcode ("xch", "a,%s", aopGet(AOP(left), MSB32, FALSE, FALSE)); + emitcode ("xch", "a,%s", + aopGet(AOP(left), MSB32, FALSE, FALSE, DP2_RESULT_REG)); } else { aopPut (AOP(result), zero, MSB32); } @@ -8438,33 +9040,32 @@ shiftRLong (operand * left, int offl, emitcode ("rrc", "a"); if (isSameRegs && offl==MSB16) { - emitcode ("xch", "a,%s",aopGet (AOP (left), MSB24, FALSE, FALSE)); + emitcode ("xch", + "a,%s",aopGet (AOP (left), MSB24, FALSE, FALSE, DP2_RESULT_REG)); } else { aopPut (AOP (result), "a", MSB32); - MOVA (aopGet (AOP (left), MSB24, FALSE, FALSE)); + MOVA (aopGet (AOP (left), MSB24, FALSE, FALSE, NULL)); } emitcode ("rrc", "a"); if (isSameRegs && offl==1) { - emitcode ("xch", "a,%s",aopGet (AOP (left), MSB16, FALSE, FALSE)); + emitcode ("xch", "a,%s", + aopGet (AOP (left), MSB16, FALSE, FALSE, DP2_RESULT_REG)); } else { aopPut (AOP (result), "a", MSB24); - MOVA (aopGet (AOP (left), MSB16, FALSE, FALSE)); + MOVA (aopGet (AOP (left), MSB16, FALSE, FALSE, NULL)); } emitcode ("rrc", "a"); aopPut (AOP (result), "a", MSB16 - offl); if (offl == LSB) { - MOVA (aopGet (AOP (left), LSB, FALSE, FALSE)); + MOVA (aopGet (AOP (left), LSB, FALSE, FALSE, NULL)); emitcode ("rrc", "a"); aopPut (AOP (result), "a", LSB); } } -#endif -#if 0 -//REMOVE ME!!! /*-----------------------------------------------------------------*/ /* genrshFour - shift four byte by a known amount != 0 */ /*-----------------------------------------------------------------*/ @@ -8472,22 +9073,24 @@ static void genrshFour (operand * result, operand * left, int shCount, int sign) { - D (emitcode (";", "genrshFour"); - ); + D (emitcode (";", "genrshFour");); /* if shifting more that 3 bytes */ if (shCount >= 24) { shCount -= 24; + _startLazyDPSEvaluation(); if (shCount) shiftR1Left2Result (left, MSB32, result, LSB, shCount, sign); else movLeft2Result (left, MSB32, result, LSB, sign); addSign (result, MSB16, sign); + _endLazyDPSEvaluation(); } else if (shCount >= 16) { shCount -= 16; + _startLazyDPSEvaluation(); if (shCount) shiftR2Left2Result (left, MSB24, result, LSB, shCount, sign); else @@ -8496,12 +9099,16 @@ genrshFour (operand * result, operand * left, movLeft2Result (left, MSB32, result, MSB16, sign); } addSign (result, MSB24, sign); + _endLazyDPSEvaluation(); } else if (shCount >= 8) { shCount -= 8; + _startLazyDPSEvaluation(); if (shCount == 1) - shiftRLong (left, MSB16, result, sign); + { + shiftRLong (left, MSB16, result, sign); + } else if (shCount == 0) { movLeft2Result (left, MSB16, result, LSB, 0); @@ -8517,9 +9124,11 @@ genrshFour (operand * result, operand * left, shiftR1Left2Result (left, MSB32, result, MSB24, shCount, sign); addSign (result, MSB32, sign); } + _endLazyDPSEvaluation(); } else - { /* 1 <= shCount <= 7 */ + { + /* 1 <= shCount <= 7 */ if (shCount <= 2) { shiftRLong (left, LSB, result, sign); @@ -8534,7 +9143,6 @@ genrshFour (operand * result, operand * left, } } } -#endif #ifdef BETTER_LITERAL_SHIFT /*-----------------------------------------------------------------*/ @@ -8558,16 +9166,17 @@ genRightShiftLiteral (operand * left, if ((shCount != 0) && (shCount < (size * 8)) && (size != 1) - && (size != 2)) + && (size != 2) + && (size != 4)) { - D(emitcode (";", "genRightShiftLiteral wimping out");); + D(emitcode (";", "genRightShiftLiteral wimping out");); return FALSE; } freeAsmop (right, NULL, ic, TRUE); aopOp (left, ic, FALSE, FALSE); - aopOp (result, ic, FALSE, AOP_TYPE (left) == AOP_DPTR); + aopOp (result, ic, FALSE, AOP_USESDPTR(left)); #if VIEW_SIZE emitcode ("; shift right ", "result %d, left %d", AOP_SIZE (result), @@ -8592,7 +9201,7 @@ genRightShiftLiteral (operand * left, if (sign) { /* get sign in acc.7 */ - MOVA (aopGet (AOP (left), size - 1, FALSE, FALSE, TRUE)); + MOVA (aopGet (AOP (left), size - 1, FALSE, FALSE, NULL)); } addSign (result, LSB, sign); } @@ -8607,7 +9216,7 @@ genRightShiftLiteral (operand * left, case 2: genrshTwo (result, left, shCount, sign); break; -#if 0 +#if 1 case 4: genrshFour (result, left, shCount, sign); break; @@ -8671,12 +9280,12 @@ genSignedRightShift (iCode * ic) } else { - emitcode ("mov", "b,%s", aopGet (AOP (right), 0, FALSE, FALSE, FALSE)); + MOVB(aopGet (AOP (right), 0, FALSE, FALSE, "b")); emitcode ("inc", "b"); } freeAsmop (right, NULL, ic, TRUE); aopOp (left, ic, FALSE, FALSE); - aopOp (result, ic, FALSE, AOP_TYPE (left) == AOP_DPTR); + aopOp (result, ic, FALSE, AOP_USESDPTR(left)); /* now move the left to the result if they are not the same */ @@ -8689,7 +9298,7 @@ genSignedRightShift (iCode * ic) _startLazyDPSEvaluation (); while (size--) { - l = aopGet (AOP (left), offset, FALSE, TRUE, FALSE); + l = aopGet (AOP (left), offset, FALSE, TRUE, NULL); if (*l == '@' && IS_AOP_PREG (result)) { @@ -8709,14 +9318,13 @@ genSignedRightShift (iCode * ic) size = AOP_SIZE (result); offset = size - 1; - emitcode ("mov", "a,%s", aopGet (AOP (left), offset, FALSE, FALSE, FALSE)); + MOVA (aopGet (AOP (left), offset, FALSE, FALSE, NULL)); emitcode ("rlc", "a"); emitcode ("mov", "ov,c"); /* if it is only one byte then */ if (size == 1) { - l = aopGet (AOP (left), 0, FALSE, FALSE, TRUE); - MOVA (l); + MOVA( aopGet (AOP (left), 0, FALSE, FALSE, NULL)); emitcode ("sjmp", "!tlabel", tlbl1->key + 100); emitcode ("", "!tlabeldef", tlbl->key + 100); emitcode ("mov", "c,ov"); @@ -8734,8 +9342,7 @@ genSignedRightShift (iCode * ic) _startLazyDPSEvaluation (); while (size--) { - l = aopGet (AOP (result), offset, FALSE, FALSE, TRUE); - MOVA (l); + MOVA (aopGet (AOP (result), offset, FALSE, FALSE, NULL)); emitcode ("rrc", "a"); aopPut (AOP (result), "a", offset--); } @@ -8756,7 +9363,7 @@ static void genRightShift (iCode * ic) { operand *right, *left, *result; - sym_link *retype; + sym_link *letype; int size, offset; char *l; symbol *tlbl, *tlbl1; @@ -8765,9 +9372,9 @@ genRightShift (iCode * ic) /* if signed then we do it the hard way preserve the sign bit moving it inwards */ - retype = getSpec (operandType (IC_RESULT (ic))); + letype = getSpec (operandType (IC_LEFT (ic))); - if (!SPEC_USIGN (retype)) + if (!SPEC_USIGN (letype)) { genSignedRightShift (ic); return; @@ -8815,12 +9422,12 @@ genRightShift (iCode * ic) } else { - emitcode ("mov", "b,%s", aopGet (AOP (right), 0, FALSE, FALSE, FALSE)); - emitcode ("inc", "b"); + MOVB(aopGet (AOP (right), 0, FALSE, FALSE, "b")); + emitcode ("inc", "b"); } freeAsmop (right, NULL, ic, TRUE); aopOp (left, ic, FALSE, FALSE); - aopOp (result, ic, FALSE, AOP_TYPE (left) == AOP_DPTR); + aopOp (result, ic, FALSE, AOP_USESDPTR(left)); /* now move the left to the result if they are not the same */ @@ -8833,7 +9440,7 @@ genRightShift (iCode * ic) _startLazyDPSEvaluation (); while (size--) { - l = aopGet (AOP (left), offset, FALSE, TRUE, FALSE); + l = aopGet (AOP (left), offset, FALSE, TRUE, NULL); if (*l == '@' && IS_AOP_PREG (result)) { @@ -8855,8 +9462,7 @@ genRightShift (iCode * ic) /* if it is only one byte then */ if (size == 1) { - l = aopGet (AOP (left), 0, FALSE, FALSE, TRUE); - MOVA (l); + MOVA (aopGet (AOP (left), 0, FALSE, FALSE, NULL)); emitcode ("sjmp", "!tlabel", tlbl1->key + 100); emitcode ("", "!tlabeldef", tlbl->key + 100); CLRC; @@ -8874,8 +9480,7 @@ genRightShift (iCode * ic) _startLazyDPSEvaluation (); while (size--) { - l = aopGet (AOP (result), offset, FALSE, FALSE, TRUE); - MOVA (l); + MOVA (aopGet (AOP (result), offset, FALSE, FALSE, NULL)); emitcode ("rrc", "a"); aopPut (AOP (result), "a", offset--); } @@ -8890,118 +9495,148 @@ release: freeAsmop (result, NULL, ic, TRUE); } + /*-----------------------------------------------------------------*/ -/* genUnpackBits - generates code for unpacking bits */ +/* emitPtrByteGet - emits code to get a byte into A through a */ +/* pointer register (R0, R1, or DPTR). The */ +/* original value of A can be preserved in B. */ /*-----------------------------------------------------------------*/ static void -genUnpackBits (operand * result, char *rname, int ptype) +emitPtrByteGet (char *rname, int p_type, bool preserveAinB) { - int shCnt; - int rlen = 0; - sym_link *etype; - int offset = 0; - - D (emitcode (";", "genUnpackBits "); - ); - - etype = getSpec (operandType (result)); - - /* read the first byte */ - switch (ptype) + switch (p_type) { - - case POINTER: case IPOINTER: + case POINTER: + if (preserveAinB) + emitcode ("mov", "b,a"); emitcode ("mov", "a,@%s", rname); break; case PPOINTER: + if (preserveAinB) + emitcode ("mov", "b,a"); emitcode ("movx", "a,@%s", rname); break; - + case FPOINTER: + if (preserveAinB) + emitcode ("mov", "b,a"); emitcode ("movx", "a,@dptr"); break; case CPOINTER: + if (preserveAinB) + emitcode ("mov", "b,a"); emitcode ("clr", "a"); emitcode ("movc", "a,@a+dptr"); break; case GPOINTER: + if (preserveAinB) + { + emitcode ("push", "b"); + emitcode ("push", "acc"); + } emitcode ("lcall", "__gptrget"); + if (preserveAinB) + emitcode ("pop", "b"); break; } +} - /* if we have bitdisplacement then it fits */ - /* into this byte completely or if length is */ - /* less than a byte */ - if ((shCnt = SPEC_BSTR (etype)) || - (SPEC_BLEN (etype) <= 8)) +/*-----------------------------------------------------------------*/ +/* emitPtrByteSet - emits code to set a byte from src through a */ +/* pointer register (R0, R1, or DPTR). */ +/*-----------------------------------------------------------------*/ +static void +emitPtrByteSet (char *rname, int p_type, char *src) +{ + switch (p_type) { + case IPOINTER: + case POINTER: + if (*src=='@') + { + MOVA (src); + emitcode ("mov", "@%s,a", rname); + } + else + emitcode ("mov", "@%s,%s", rname, src); + break; - /* shift right acc */ - AccRsh (shCnt); + case PPOINTER: + MOVA (src); + emitcode ("movx", "@%s,a", rname); + break; + + case FPOINTER: + MOVA (src); + emitcode ("movx", "@dptr,a"); + break; - emitcode ("anl", "a,#!constbyte", - ((unsigned char) -1) >> (8 - SPEC_BLEN (etype))); - aopPut (AOP (result), "a", offset); - return; + case GPOINTER: + MOVA (src); + emitcode ("lcall", "__gptrput"); + break; } +} - /* bit field did not fit in a byte */ - rlen = SPEC_BLEN (etype) - 8; - aopPut (AOP (result), "a", offset++); - - while (1) - { - - switch (ptype) - { - case POINTER: - case IPOINTER: - emitcode ("inc", "%s", rname); - emitcode ("mov", "a,@%s", rname); - break; - - case PPOINTER: - emitcode ("inc", "%s", rname); - emitcode ("movx", "a,@%s", rname); - break; - - case FPOINTER: - emitcode ("inc", "dptr"); - emitcode ("movx", "a,@dptr"); - break; - - case CPOINTER: - emitcode ("clr", "a"); - emitcode ("inc", "dptr"); - emitcode ("movc", "a,@a+dptr"); - break; +/*-----------------------------------------------------------------*/ +/* genUnpackBits - generates code for unpacking bits */ +/*-----------------------------------------------------------------*/ +static void +genUnpackBits (operand * result, char *rname, int ptype) +{ + int offset = 0; /* result byte offset */ + int rsize; /* result size */ + int rlen = 0; /* remaining bitfield length */ + sym_link *etype; /* bitfield type information */ + int blen; /* bitfield length */ + int bstr; /* bitfield starting bit within byte */ - case GPOINTER: - emitcode ("inc", "dptr"); - emitcode ("lcall", "__gptrget"); - break; - } + D(emitcode ("; genUnpackBits","")); - rlen -= 8; - /* if we are done */ - if (rlen < 8) - break; + etype = getSpec (operandType (result)); + rsize = getSize (operandType (result)); + blen = SPEC_BLEN (etype); + bstr = SPEC_BSTR (etype); + /* If the bitfield length is less than a byte */ + if (blen < 8) + { + emitPtrByteGet (rname, ptype, FALSE); + AccRsh (bstr); + emitcode ("anl", "a,#!constbyte", ((unsigned char) -1) >> (8 - blen)); aopPut (AOP (result), "a", offset++); + goto finish; + } + /* Bit field did not fit in a byte. Copy all + but the partial byte at the end. */ + for (rlen=blen;rlen>=8;rlen-=8) + { + emitPtrByteGet (rname, ptype, FALSE); + aopPut (AOP (result), "a", offset++); + if (rlen>8) + emitcode ("inc", "%s", rname); } + /* Handle the partial byte at the end */ if (rlen) { - emitcode ("anl", "a,#!constbyte", ((unsigned char) -1) >> (rlen)); - aopPut (AOP (result), "a", offset); + emitPtrByteGet (rname, ptype, FALSE); + emitcode ("anl", "a,#!constbyte", ((unsigned char) -1) >> (8-rlen)); + aopPut (AOP (result), "a", offset++); } - return; +finish: + if (offset < rsize) + { + rsize -= offset; + while (rsize--) + aopPut (AOP (result), zero, offset++); + } } @@ -9019,7 +9654,7 @@ genDataPointerGet (operand * left, aopOp (result, ic, TRUE, FALSE); /* get the string representation of the name */ - l = aopGet (AOP (left), 0, FALSE, TRUE, FALSE); + l = aopGet (AOP (left), 0, FALSE, TRUE, NULL); size = AOP_SIZE (result); _startLazyDPSEvaluation (); while (size--) @@ -9052,7 +9687,7 @@ genNearPointerGet (operand * left, iCode *pi) { asmop *aop = NULL; - regs *preg = NULL; + regs *preg; char *rname; sym_link *rtype, *retype, *letype; sym_link *ltype = operandType (left); @@ -9065,12 +9700,12 @@ genNearPointerGet (operand * left, aopOp (left, ic, FALSE, FALSE); /* if left is rematerialisable and - result is not bit variable type and + result is not bitfield variable type and the left is pointer to data space i.e lower 128 bytes of space */ if (AOP_TYPE (left) == AOP_IMMD && - !IS_BITVAR (retype) && - !IS_BITVAR (letype) && + !IS_BITFIELD (retype) && + !IS_BITFIELD (letype) && DCL_TYPE (ltype) == POINTER) { genDataPointerGet (left, result, ic); @@ -9086,17 +9721,17 @@ genNearPointerGet (operand * left, preg = getFreePtr (ic, &aop, FALSE); emitcode ("mov", "%s,%s", preg->name, - aopGet (AOP (left), 0, FALSE, TRUE, FALSE)); + aopGet (AOP (left), 0, FALSE, TRUE, DP2_RESULT_REG)); rname = preg->name; } else - rname = aopGet (AOP (left), 0, FALSE, FALSE, FALSE); + rname = aopGet (AOP (left), 0, FALSE, FALSE, DP2_RESULT_REG); freeAsmop (left, NULL, ic, TRUE); aopOp (result, ic, FALSE, FALSE); /* if bitfield then unpack the bits */ - if (IS_BITVAR (retype) || IS_BITVAR (letype)) + if (IS_BITFIELD (retype) || IS_BITFIELD (letype)) genUnpackBits (result, rname, POINTER); else { @@ -9168,7 +9803,7 @@ genPagedPointerGet (operand * left, iCode * pi) { asmop *aop = NULL; - regs *preg = NULL; + regs *preg; char *rname; sym_link *rtype, *retype, *letype; @@ -9186,17 +9821,17 @@ genPagedPointerGet (operand * left, preg = getFreePtr (ic, &aop, FALSE); emitcode ("mov", "%s,%s", preg->name, - aopGet (AOP (left), 0, FALSE, TRUE, FALSE)); + aopGet (AOP (left), 0, FALSE, TRUE, NULL)); rname = preg->name; } else - rname = aopGet (AOP (left), 0, FALSE, FALSE, FALSE); + rname = aopGet (AOP (left), 0, FALSE, FALSE, NULL); freeAsmop (left, NULL, ic, TRUE); aopOp (result, ic, FALSE, FALSE); /* if bitfield then unpack the bits */ - if (IS_BITVAR (retype) || IS_BITVAR (letype)) + if (IS_BITFIELD (retype) || IS_BITFIELD (letype)) genUnpackBits (result, rname, PPOINTER); else { @@ -9258,8 +9893,7 @@ genFarPointerGet (operand * left, int size, offset, dopi=1; sym_link *retype = getSpec (operandType (result)); sym_link *letype = getSpec (operandType (left)); - D (emitcode (";", "genFarPointerGet"); - ); + D (emitcode (";", "genFarPointerGet");); aopOp (left, ic, FALSE, FALSE); @@ -9270,7 +9904,7 @@ genFarPointerGet (operand * left, /* if this is remateriazable */ if (AOP_TYPE (left) == AOP_IMMD) { - emitcode ("mov", "dptr,%s", aopGet (AOP (left), 0, TRUE, FALSE, FALSE)); + emitcode ("mov", "dptr,%s", aopGet (AOP (left), 0, TRUE, FALSE, NULL)); } else { @@ -9278,20 +9912,19 @@ genFarPointerGet (operand * left, _startLazyDPSEvaluation (); if (AOP_TYPE (left) != AOP_DPTR) { - emitcode ("mov", "dpl,%s", aopGet (AOP (left), 0, FALSE, FALSE, TRUE)); - emitcode ("mov", "dph,%s", aopGet (AOP (left), 1, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpl,%s", aopGet (AOP (left), 0, FALSE, FALSE, NULL)); + emitcode ("mov", "dph,%s", aopGet (AOP (left), 1, FALSE, FALSE, NULL)); if (options.model == MODEL_FLAT24) - emitcode ("mov", "dpx,%s", aopGet (AOP (left), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP (left), 2, FALSE, FALSE, NULL)); } else { /* We need to generate a load to DPTR indirect through DPTR. */ - D (emitcode (";", "genFarPointerGet -- indirection special case."); - ); - emitcode ("push", "%s", aopGet (AOP (left), 0, FALSE, TRUE, TRUE)); - emitcode ("push", "%s", aopGet (AOP (left), 1, FALSE, TRUE, TRUE)); + D (emitcode (";", "genFarPointerGet -- indirection special case.");); + emitcode ("push", "%s", aopGet (AOP (left), 0, FALSE, TRUE, NULL)); + emitcode ("push", "%s", aopGet (AOP (left), 1, FALSE, TRUE, NULL)); if (options.model == MODEL_FLAT24) - emitcode ("mov", "dpx,%s", aopGet (AOP (left), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP (left), 2, FALSE, FALSE, NULL)); emitcode ("pop", "dph"); emitcode ("pop", "dpl"); dopi =0; @@ -9303,7 +9936,7 @@ genFarPointerGet (operand * left, aopOp (result, ic, FALSE, (AOP_INDPTRn(left) ? FALSE : TRUE)); /* if bit then unpack */ - if (IS_BITVAR (retype) || IS_BITVAR (letype)) { + if (IS_BITFIELD (retype) || IS_BITFIELD (letype)) { if (AOP_INDPTRn(left)) { genSetDPTR(AOP(left)->aopu.dptr); } @@ -9346,15 +9979,18 @@ genFarPointerGet (operand * left, } if (dopi && pi && AOP_TYPE (left) != AOP_IMMD) { if (!AOP_INDPTRn(left)) { + _startLazyDPSEvaluation (); aopPut ( AOP (left), "dpl", 0); aopPut ( AOP (left), "dph", 1); if (options.model == MODEL_FLAT24) aopPut ( AOP (left), "dpx", 2); + _endLazyDPSEvaluation (); } pi->generated = 1; - } else if ((OP_SYMBOL(left)->ruonly || AOP_INDPTRn(left)) && + } else if ((AOP_IS_STR(left) || AOP_INDPTRn(left)) && AOP_SIZE(result) > 1 && - (OP_SYMBOL (left)->liveTo > ic->seq || ic->depth)) { + IS_SYMOP(left) && + (OP_SYMBOL(left)->liveTo > ic->seq || ic->depth)) { size = AOP_SIZE (result) - 1; if (AOP_INDPTRn(left)) { @@ -9389,27 +10025,26 @@ genCodePointerGet (operand * left, /* if this is remateriazable */ if (AOP_TYPE (left) == AOP_IMMD) { - emitcode ("mov", "dptr,%s", aopGet (AOP (left), 0, TRUE, FALSE, FALSE)); + emitcode ("mov", "dptr,%s", aopGet (AOP (left), 0, TRUE, FALSE, NULL)); } else { /* we need to get it byte by byte */ _startLazyDPSEvaluation (); if (AOP_TYPE (left) != AOP_DPTR) { - emitcode ("mov", "dpl,%s", aopGet (AOP (left), 0, FALSE, FALSE, TRUE)); - emitcode ("mov", "dph,%s", aopGet (AOP (left), 1, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpl,%s", aopGet (AOP (left), 0, FALSE, FALSE, NULL)); + emitcode ("mov", "dph,%s", aopGet (AOP (left), 1, FALSE, FALSE, NULL)); if (options.model == MODEL_FLAT24) - emitcode ("mov", "dpx,%s", aopGet (AOP (left), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP (left), 2, FALSE, FALSE, NULL)); } else { /* We need to generate a load to DPTR indirect through DPTR. */ - D (emitcode (";", "gencodePointerGet -- indirection special case."); - ); - emitcode ("push", "%s", aopGet (AOP (left), 0, FALSE, TRUE, TRUE)); - emitcode ("push", "%s", aopGet (AOP (left), 1, FALSE, TRUE, TRUE)); + D (emitcode (";", "gencodePointerGet -- indirection special case.");); + emitcode ("push", "%s", aopGet (AOP (left), 0, FALSE, TRUE, NULL)); + emitcode ("push", "%s", aopGet (AOP (left), 1, FALSE, TRUE, NULL)); if (options.model == MODEL_FLAT24) - emitcode ("mov", "dpx,%s", aopGet (AOP (left), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP (left), 2, FALSE, FALSE, NULL)); emitcode ("pop", "dph"); emitcode ("pop", "dpl"); dopi=0; @@ -9421,7 +10056,7 @@ genCodePointerGet (operand * left, aopOp (result, ic, FALSE, (AOP_INDPTRn(left) ? FALSE : TRUE)); /* if bit then unpack */ - if (IS_BITVAR (retype)) { + if (IS_BITFIELD (retype)) { if (AOP_INDPTRn(left)) { genSetDPTR(AOP(left)->aopu.dptr); } @@ -9465,10 +10100,14 @@ genCodePointerGet (operand * left, } if (dopi && pi && AOP_TYPE (left) != AOP_IMMD) { if (!AOP_INDPTRn(left)) { + _startLazyDPSEvaluation (); + aopPut ( AOP (left), "dpl", 0); aopPut ( AOP (left), "dph", 1); if (options.model == MODEL_FLAT24) aopPut ( AOP (left), "dpx", 2); + + _endLazyDPSEvaluation (); } pi->generated = 1; } else if ((OP_SYMBOL(left)->ruonly || AOP_INDPTRn(left)) && @@ -9511,22 +10150,26 @@ genGenPointerGet (operand * left, /* if this is remateriazable */ if (AOP_TYPE (left) == AOP_IMMD) { - emitcode ("mov", "dptr,%s", aopGet (AOP (left), 0, TRUE, FALSE, FALSE)); + emitcode ("mov", "dptr,%s", aopGet (AOP (left), 0, TRUE, FALSE, NULL)); if (AOP(left)->aopu.aop_immd.from_cast_remat) - emitcode ("mov", "b,%s",aopGet(AOP (left), AOP_SIZE(left)-1, FALSE, FALSE, FALSE)); - else - emitcode ("mov", "b,#%d", pointerCode (retype)); + { + MOVB(aopGet(AOP (left), AOP_SIZE(left)-1, FALSE, FALSE, NULL)); + } + else + { + emitcode ("mov", "b,#%d", pointerCode (retype)); + } } else { /* we need to get it byte by byte */ _startLazyDPSEvaluation (); - emitcode ("mov", "dpl,%s", aopGet (AOP(left),0,FALSE,FALSE,TRUE)); - emitcode ("mov", "dph,%s", aopGet (AOP(left),1,FALSE,FALSE,TRUE)); + emitcode ("mov", "dpl,%s", aopGet (AOP(left),0,FALSE,FALSE,NULL)); + emitcode ("mov", "dph,%s", aopGet (AOP(left),1,FALSE,FALSE,NULL)); if (options.model == MODEL_FLAT24) { - emitcode ("mov", "dpx,%s", aopGet (AOP(left),2,FALSE,FALSE,TRUE)); - emitcode ("mov", "b,%s", aopGet (AOP(left),3,FALSE,FALSE,TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP(left),2,FALSE,FALSE,NULL)); + emitcode ("mov", "b,%s", aopGet (AOP(left),3,FALSE,FALSE,NULL)); } else { - emitcode ("mov", "b,%s", aopGet (AOP(left),2,FALSE,FALSE,TRUE)); + emitcode ("mov", "b,%s", aopGet (AOP(left),2,FALSE,FALSE,NULL)); } _endLazyDPSEvaluation (); } @@ -9538,7 +10181,7 @@ genGenPointerGet (operand * left, _G.bInUse--; /* if bit then unpack */ - if (IS_BITVAR (retype) || IS_BITVAR (letype)) + if (IS_BITFIELD (retype) || IS_BITFIELD (letype)) { genUnpackBits (result, "dptr", GPOINTER); } @@ -9577,12 +10220,17 @@ genGenPointerGet (operand * left, } if (pi && AOP_TYPE (left) != AOP_IMMD) { + _startLazyDPSEvaluation (); + aopPut ( AOP (left), "dpl", 0); aopPut ( AOP (left), "dph", 1); if (options.model == MODEL_FLAT24) { aopPut ( AOP (left), "dpx", 2); aopPut ( AOP (left), "b", 3); } else aopPut ( AOP (left), "b", 2); + + _endLazyDPSEvaluation (); + pi->generated = 1; } else if (OP_SYMBOL(left)->ruonly && AOP_SIZE(result) > 1 && (OP_SYMBOL (left)->liveTo > ic->seq || ic->depth)) { @@ -9636,197 +10284,156 @@ genPointerGet (iCode * ic, iCode *pi) { case POINTER: - case IPOINTER: - genNearPointerGet (left, result, ic, pi); - break; - - case PPOINTER: - genPagedPointerGet (left, result, ic, pi); - break; - - case FPOINTER: - genFarPointerGet (left, result, ic, pi); - break; - - case CPOINTER: - genCodePointerGet (left, result, ic, pi); - break; - - case GPOINTER: - genGenPointerGet (left, result, ic, pi); - break; - } - -} - -/*-----------------------------------------------------------------*/ -/* genPackBits - generates code for packed bit storage */ -/*-----------------------------------------------------------------*/ -static void -genPackBits (sym_link * etype, - operand * right, - char *rname, int p_type) -{ - int shCount = 0; - int offset = 0; - int rLen = 0; - int blen, bstr; - char *l; - - blen = SPEC_BLEN (etype); - bstr = SPEC_BSTR (etype); - - l = aopGet (AOP (right), offset++, FALSE, FALSE, TRUE); - MOVA (l); - - /* if the bit lenth is less than or */ - /* it exactly fits a byte then */ - if (SPEC_BLEN (etype) <= 8) - { - shCount = SPEC_BSTR (etype); - - /* shift left acc */ - AccLsh (shCount); - - if (SPEC_BLEN (etype) < 8) - { /* if smaller than a byte */ - - - switch (p_type) - { - case POINTER: - emitcode ("mov", "b,a"); - emitcode ("mov", "a,@%s", rname); - break; - - case FPOINTER: - emitcode ("mov", "b,a"); - emitcode ("movx", "a,@dptr"); - break; - - case GPOINTER: - emitcode ("push", "b"); - emitcode ("push", "acc"); - emitcode ("lcall", "__gptrget"); - emitcode ("pop", "b"); - break; - } - - emitcode ("anl", "a,#!constbyte", (unsigned char) - ((unsigned char) (0xFF << (blen + bstr)) | - (unsigned char) (0xFF >> (8 - bstr)))); - emitcode ("orl", "a,b"); - if (p_type == GPOINTER) - emitcode ("pop", "b"); - } - } - - switch (p_type) - { - case POINTER: - emitcode ("mov", "@%s,a", rname); + case IPOINTER: + genNearPointerGet (left, result, ic, pi); + break; + + case PPOINTER: + genPagedPointerGet (left, result, ic, pi); break; case FPOINTER: - emitcode ("movx", "@dptr,a"); + genFarPointerGet (left, result, ic, pi); + break; + + case CPOINTER: + genCodePointerGet (left, result, ic, pi); break; case GPOINTER: - emitcode ("lcall", "__gptrput"); + genGenPointerGet (left, result, ic, pi); break; } - /* if we r done */ - if (SPEC_BLEN (etype) <= 8) - return; - - emitcode ("inc", "%s", rname); - rLen = SPEC_BLEN (etype); +} - /* now generate for lengths greater than one byte */ - while (1) - { +/*-----------------------------------------------------------------*/ +/* genPackBits - generates code for packed bit storage */ +/*-----------------------------------------------------------------*/ +static void +genPackBits (sym_link * etype, + operand * right, + char *rname, int p_type) +{ + int offset = 0; /* source byte offset */ + int rlen = 0; /* remaining bitfield length */ + int blen; /* bitfield length */ + int bstr; /* bitfield starting bit within byte */ + int litval; /* source literal value (if AOP_LIT) */ + unsigned char mask; /* bitmask within current byte */ - l = aopGet (AOP (right), offset++, FALSE, TRUE, FALSE); + D(emitcode ("; genPackBits","")); - rLen -= 8; - if (rLen < 8) - break; + blen = SPEC_BLEN (etype); + bstr = SPEC_BSTR (etype); - switch (p_type) - { - case POINTER: - if (*l == '@') - { - MOVA (l); - emitcode ("mov", "@%s,a", rname); - } - else - emitcode ("mov", "@%s,%s", rname, l); - break; + /* If the bitfield length is less than a byte */ + if (blen < 8) + { + mask = ((unsigned char) (0xFF << (blen + bstr)) | + (unsigned char) (0xFF >> (8 - bstr))); - case FPOINTER: - MOVA (l); - emitcode ("movx", "@dptr,a"); - break; + if (AOP_TYPE (right) == AOP_LIT) + { + /* Case with a bitfield length <8 and literal source + */ + litval = (int) floatFromVal (AOP (right)->aopu.aop_lit); + litval <<= bstr; + litval &= (~mask) & 0xff; + emitPtrByteGet (rname, p_type, FALSE); + if ((mask|litval)!=0xff) + emitcode ("anl","a,#!constbyte", mask); + if (litval) + emitcode ("orl","a,#!constbyte", litval); + } + else + { + if ((blen==1) && (p_type!=GPOINTER)) + { + /* Case with a bitfield length == 1 and no generic pointer + */ + if (AOP_TYPE (right) == AOP_CRY) + emitcode ("mov", "c,%s", AOP(right)->aopu.aop_dir); + else + { + MOVA (aopGet (AOP (right), 0, FALSE, FALSE, NULL)); + emitcode ("rrc","a"); + } + emitPtrByteGet (rname, p_type, FALSE); + emitcode ("mov","acc.%d,c",bstr); + } + else + { + /* Case with a bitfield length < 8 and arbitrary source + */ + MOVA (aopGet (AOP (right), 0, FALSE, FALSE, NULL)); + /* shift and mask source value */ + AccLsh (bstr); + emitcode ("anl", "a,#!constbyte", (~mask) & 0xff); + + /* transfer A to B and get next byte */ + emitPtrByteGet (rname, p_type, TRUE); + + emitcode ("anl", "a,#!constbyte", mask); + emitcode ("orl", "a,b"); + if (p_type == GPOINTER) + emitcode ("pop", "b"); + } + } - case GPOINTER: - MOVA (l); - emitcode ("lcall", "__gptrput"); - break; - } - emitcode ("inc", "%s", rname); + emitPtrByteSet (rname, p_type, "a"); + return; } - MOVA (l); - - /* last last was not complete */ - if (rLen) + /* Bit length is greater than 7 bits. In this case, copy */ + /* all except the partial byte at the end */ + for (rlen=blen;rlen>=8;rlen-=8) { - /* save the byte & read byte */ - switch (p_type) - { - case POINTER: - emitcode ("mov", "b,a"); - emitcode ("mov", "a,@%s", rname); - break; - - case FPOINTER: - emitcode ("mov", "b,a"); - emitcode ("movx", "a,@dptr"); - break; - - case GPOINTER: - emitcode ("push", "b"); - emitcode ("push", "acc"); - emitcode ("lcall", "__gptrget"); - emitcode ("pop", "b"); - break; - } - - emitcode ("anl", "a,#!constbyte", ((unsigned char) -1 << rLen)); - emitcode ("orl", "a,b"); + emitPtrByteSet (rname, p_type, + aopGet (AOP (right), offset++, FALSE, TRUE, NULL) ); + if (rlen>8) + emitcode ("inc", "%s", rname); } - if (p_type == GPOINTER) - emitcode ("pop", "b"); - - switch (p_type) + /* If there was a partial byte at the end */ + if (rlen) { + mask = (((unsigned char) -1 << rlen) & 0xff); + + if (AOP_TYPE (right) == AOP_LIT) + { + /* Case with partial byte and literal source + */ + litval = (int) floatFromVal (AOP (right)->aopu.aop_lit); + litval >>= (blen-rlen); + litval &= (~mask) & 0xff; + emitPtrByteGet (rname, p_type, FALSE); + if ((mask|litval)!=0xff) + emitcode ("anl","a,#!constbyte", mask); + if (litval) + emitcode ("orl","a,#!constbyte", litval); + } + else + { + /* Case with partial byte and arbitrary source + */ + MOVA (aopGet (AOP (right), offset++, FALSE, FALSE, NULL)); + emitcode ("anl", "a,#!constbyte", (~mask) & 0xff); + + /* transfer A to B and get next byte */ + emitPtrByteGet (rname, p_type, TRUE); + + emitcode ("anl", "a,#!constbyte", mask); + emitcode ("orl", "a,b"); + if (p_type == GPOINTER) + emitcode ("pop", "b"); + } + emitPtrByteSet (rname, p_type, "a"); + } - case POINTER: - emitcode ("mov", "@%s,a", rname); - break; +} - case FPOINTER: - emitcode ("movx", "@dptr,a"); - break; - case GPOINTER: - emitcode ("lcall", "__gptrput"); - break; - } -} /*-----------------------------------------------------------------*/ /* genDataPointerSet - remat pointer to data space */ /*-----------------------------------------------------------------*/ @@ -9840,7 +10447,7 @@ genDataPointerSet (operand * right, aopOp (right, ic, FALSE, FALSE); - l = aopGet (AOP (result), 0, FALSE, TRUE, FALSE); + l = aopGet (AOP (result), 0, FALSE, TRUE, NULL); size = AOP_SIZE (right); while (size--) { @@ -9854,7 +10461,7 @@ genDataPointerSet (operand * right, } emitcode ("mov", "%s,%s", buff, - aopGet (AOP (right), offset++, FALSE, FALSE, FALSE)); + aopGet (AOP (right), offset++, FALSE, FALSE, NULL)); } freeAsmop (right, NULL, ic, TRUE); @@ -9871,7 +10478,6 @@ genNearPointerSet (operand * right, iCode * pi) { asmop *aop = NULL; - regs *preg = NULL; char *rname, *l; sym_link *retype, *letype; sym_link *ptype = operandType (result); @@ -9897,21 +10503,23 @@ genNearPointerSet (operand * right, if (!AOP_INPREG (AOP (result))) { /* otherwise get a free pointer register */ + regs *preg; + aop = newAsmop (0); preg = getFreePtr (ic, &aop, FALSE); emitcode ("mov", "%s,%s", preg->name, - aopGet (AOP (result), 0, FALSE, TRUE, FALSE)); + aopGet (AOP (result), 0, FALSE, TRUE, NULL)); rname = preg->name; } else - rname = aopGet (AOP (result), 0, FALSE, FALSE, FALSE); + rname = aopGet (AOP (result), 0, FALSE, FALSE, NULL); aopOp (right, ic, FALSE, FALSE); /* if bitfield then unpack the bits */ - if (IS_BITVAR (retype) || IS_BITVAR (letype)) - genPackBits ((IS_BITVAR (retype) ? retype : letype), right, rname, POINTER); + if (IS_BITFIELD (retype) || IS_BITFIELD (letype)) + genPackBits ((IS_BITFIELD (retype) ? retype : letype), right, rname, POINTER); else { /* we have can just get the values */ @@ -9920,7 +10528,7 @@ genNearPointerSet (operand * right, while (size--) { - l = aopGet (AOP (right), offset, FALSE, TRUE, FALSE); + l = aopGet (AOP (right), offset, FALSE, TRUE, NULL); if (*l == '@') { MOVA (l); @@ -9978,8 +10586,7 @@ genPagedPointerSet (operand * right, iCode *pi) { asmop *aop = NULL; - regs *preg = NULL; - char *rname, *l; + char *rname; sym_link *retype, *letype; retype = getSpec (operandType (right)); @@ -9992,21 +10599,23 @@ genPagedPointerSet (operand * right, if (!AOP_INPREG (AOP (result))) { /* otherwise get a free pointer register */ + regs *preg; + aop = newAsmop (0); preg = getFreePtr (ic, &aop, FALSE); emitcode ("mov", "%s,%s", preg->name, - aopGet (AOP (result), 0, FALSE, TRUE, FALSE)); + aopGet (AOP (result), 0, FALSE, TRUE, NULL)); rname = preg->name; } else - rname = aopGet (AOP (result), 0, FALSE, FALSE, FALSE); + rname = aopGet (AOP (result), 0, FALSE, FALSE, NULL); aopOp (right, ic, FALSE, FALSE); /* if bitfield then unpack the bits */ - if (IS_BITVAR (retype) || IS_BITVAR (letype)) - genPackBits ((IS_BITVAR (retype) ? retype : letype), right, rname, PPOINTER); + if (IS_BITFIELD (retype) || IS_BITFIELD (letype)) + genPackBits ((IS_BITFIELD (retype) ? retype : letype), right, rname, PPOINTER); else { /* we have can just get the values */ @@ -10015,9 +10624,8 @@ genPagedPointerSet (operand * right, while (size--) { - l = aopGet (AOP (right), offset, FALSE, TRUE, TRUE); + MOVA (aopGet (AOP (right), offset, FALSE, TRUE, NULL)); - MOVA (l); emitcode ("movx", "@%s,a", rname); if (size || pi) @@ -10080,27 +10688,28 @@ genFarPointerSet (operand * right, { /* if this is remateriazable */ if (AOP_TYPE (result) == AOP_IMMD) - emitcode ("mov", "dptr,%s", aopGet (AOP (result), 0, TRUE, FALSE, FALSE)); + emitcode ("mov", "dptr,%s", + aopGet (AOP (result), 0, TRUE, FALSE, NULL)); else { /* we need to get it byte by byte */ _startLazyDPSEvaluation (); if (AOP_TYPE (result) != AOP_DPTR) { - emitcode ("mov", "dpl,%s", aopGet (AOP (result), 0, FALSE, FALSE, TRUE)); - emitcode ("mov", "dph,%s", aopGet (AOP (result), 1, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpl,%s", aopGet (AOP (result), 0, FALSE, FALSE, NULL)); + emitcode ("mov", "dph,%s", aopGet (AOP (result), 1, FALSE, FALSE, NULL)); if (options.model == MODEL_FLAT24) - emitcode ("mov", "dpx,%s", aopGet (AOP (result), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP (result), 2, FALSE, FALSE, NULL)); } else { /* We need to generate a load to DPTR indirect through DPTR. */ - D (emitcode (";", "genFarPointerSet -- indirection special case."); - ); - emitcode ("push", "%s", aopGet (AOP (result), 0, FALSE, TRUE, TRUE)); - emitcode ("push", "%s", aopGet (AOP (result), 1, FALSE, TRUE, TRUE)); + D (emitcode (";", "genFarPointerSet -- indirection special case.");); + + emitcode ("push", "%s", aopGet (AOP (result), 0, FALSE, TRUE, NULL)); + emitcode ("push", "%s", aopGet (AOP (result), 1, FALSE, TRUE, NULL)); if (options.model == MODEL_FLAT24) - emitcode ("mov", "dpx,%s", aopGet (AOP (result), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP (result), 2, FALSE, FALSE, NULL)); emitcode ("pop", "dph"); emitcode ("pop", "dpl"); dopi=0; @@ -10112,11 +10721,11 @@ genFarPointerSet (operand * right, aopOp (right, ic, FALSE, (AOP_INDPTRn(result) ? FALSE : TRUE)); /* if bit then unpack */ - if (IS_BITVAR (retype) || IS_BITVAR (letype)) { + if (IS_BITFIELD (retype) || IS_BITFIELD (letype)) { if (AOP_INDPTRn(result)) { genSetDPTR(AOP(result)->aopu.dptr); } - genPackBits ((IS_BITVAR (retype) ? retype : letype), right, "dptr", FPOINTER); + genPackBits ((IS_BITFIELD (retype) ? retype : letype), right, "dptr", FPOINTER); if (AOP_INDPTRn(result)) { genSetDPTR(0); } @@ -10125,8 +10734,7 @@ genFarPointerSet (operand * right, offset = 0; if (AOP_INDPTRn(result) && AOP_USESDPTR(right)) { while (size--) { - char *l = aopGet (AOP (right), offset++, FALSE, FALSE, TRUE); - MOVA (l); + MOVA (aopGet (AOP (right), offset++, FALSE, FALSE, NULL)); genSetDPTR(AOP(result)->aopu.dptr); emitcode ("movx", "@dptr,a"); @@ -10137,8 +10745,7 @@ genFarPointerSet (operand * right, } else { _startLazyDPSEvaluation (); while (size--) { - char *l = aopGet (AOP (right), offset++, FALSE, FALSE, TRUE); - MOVA (l); + MOVA (aopGet (AOP (right), offset++, FALSE, FALSE, NULL)); if (AOP_INDPTRn(result)) { genSetDPTR(AOP(result)->aopu.dptr); @@ -10157,10 +10764,14 @@ genFarPointerSet (operand * right, if (dopi && pi && AOP_TYPE (result) != AOP_IMMD) { if (!AOP_INDPTRn(result)) { + _startLazyDPSEvaluation (); + aopPut (AOP(result),"dpl",0); aopPut (AOP(result),"dph",1); if (options.model == MODEL_FLAT24) aopPut (AOP(result),"dpx",2); + + _endLazyDPSEvaluation (); } pi->generated=1; } else if ((OP_SYMBOL(result)->ruonly || AOP_INDPTRn(result)) && @@ -10201,53 +10812,87 @@ genGenPointerSet (operand * right, /* if this is remateriazable */ if (AOP_TYPE (result) == AOP_IMMD) { - emitcode ("mov", "dptr,%s", aopGet (AOP (result), 0, TRUE, FALSE, FALSE)); + emitcode ("mov", "dptr,%s", aopGet (AOP (result), 0, TRUE, FALSE, NULL)); if (AOP(result)->aopu.aop_immd.from_cast_remat) - emitcode ("mov", "b,%s",aopGet(AOP (result), AOP_SIZE(result)-1, FALSE, FALSE, FALSE)); + { + MOVB(aopGet(AOP (result), AOP_SIZE(result)-1, FALSE, FALSE, NULL)); + } else - emitcode ("mov", "b,%s + 1", aopGet (AOP (result), 0, TRUE, FALSE, FALSE)); + { + emitcode ("mov", + "b,%s + 1", aopGet (AOP (result), 0, TRUE, FALSE, NULL)); + } } else { /* we need to get it byte by byte */ - emitcode ("mov", "dpl,%s", aopGet (AOP (result), 0, FALSE, FALSE, TRUE)); - emitcode ("mov", "dph,%s", aopGet (AOP (result), 1, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpl,%s", aopGet (AOP (result), 0, FALSE, FALSE, NULL)); + emitcode ("mov", "dph,%s", aopGet (AOP (result), 1, FALSE, FALSE, NULL)); if (options.model == MODEL_FLAT24) { - emitcode ("mov", "dpx,%s", aopGet (AOP (result), 2, FALSE, FALSE, TRUE)); - emitcode ("mov", "b,%s", aopGet (AOP (result), 3, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP (result), 2, FALSE, FALSE, NULL)); + emitcode ("mov", "b,%s", aopGet (AOP (result), 3, FALSE, FALSE, NULL)); } else { - emitcode ("mov", "b,%s", aopGet (AOP (result), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "b,%s", aopGet (AOP (result), 2, FALSE, FALSE, NULL)); } } _endLazyDPSEvaluation (); } - /* so dptr know contains the address */ + /* so dptr + b now contains the address */ + _G.bInUse++; aopOp (right, ic, FALSE, TRUE); + _G.bInUse--; + /* if bit then unpack */ - if (IS_BITVAR (retype) || IS_BITVAR (letype)) - genPackBits ((IS_BITVAR (retype) ? retype : letype), right, "dptr", GPOINTER); + if (IS_BITFIELD (retype) || IS_BITFIELD (letype)) + { + genPackBits ((IS_BITFIELD (retype) ? retype : letype), right, "dptr", GPOINTER); + } else { - size = AOP_SIZE (right); - offset = 0; + size = AOP_SIZE (right); + offset = 0; - _startLazyDPSEvaluation (); - while (size--) + _startLazyDPSEvaluation (); + while (size--) { - char *l = aopGet (AOP (right), offset++, FALSE, FALSE, TRUE); - MOVA (l); - - genSetDPTR (0); - _flushLazyDPS (); + if (size) + { + // Set two bytes at a time, passed in _AP & A. + // dptr will be incremented ONCE by __gptrputWord. + // + // Note: any change here must be coordinated + // with the implementation of __gptrputWord + // in device/lib/_gptrput.c + emitcode("mov", "_ap, %s", + aopGet (AOP (right), offset++, FALSE, FALSE, NULL)); + MOVA (aopGet (AOP (right), offset++, FALSE, FALSE, NULL)); + + genSetDPTR (0); + _flushLazyDPS (); + emitcode ("lcall", "__gptrputWord"); + size--; + } + else + { + // Only one byte to put. + MOVA (aopGet (AOP (right), offset++, FALSE, FALSE, NULL)); - emitcode ("lcall", "__gptrput"); - if (size || (pi && AOP_TYPE (result) != AOP_IMMD)) - emitcode ("inc", "dptr"); + genSetDPTR (0); + _flushLazyDPS (); + emitcode ("lcall", "__gptrput"); + } + + if (size || (pi && AOP_TYPE (result) != AOP_IMMD)) + { + emitcode ("inc", "dptr"); + } } - _endLazyDPSEvaluation (); + _endLazyDPSEvaluation (); } if (pi && AOP_TYPE (result) != AOP_IMMD) { + _startLazyDPSEvaluation (); + aopPut (AOP(result),"dpl",0); aopPut (AOP(result),"dph",1); if (options.model == MODEL_FLAT24) { @@ -10256,6 +10901,8 @@ genGenPointerSet (operand * right, } else { aopPut (AOP(result),"b",2); } + _endLazyDPSEvaluation (); + pi->generated=1; } else if (OP_SYMBOL(result)->ruonly && AOP_SIZE(right) > 1 && (OP_SYMBOL (result)->liveTo > ic->seq || ic->depth)) { @@ -10277,8 +10924,7 @@ genPointerSet (iCode * ic, iCode *pi) sym_link *type, *etype; int p_type; - D (emitcode (";", "genPointerSet "); - ); + D (emitcode (";", "genPointerSet ");); right = IC_RIGHT (ic); result = IC_RESULT (ic); @@ -10404,6 +11050,8 @@ genAddrOf (iCode * ic) /* if 10 bit stack */ if (options.stack10bit) { char buff[10]; + int offset; + tsprintf(buff, sizeof(buff), "#!constbyte",(options.stack_loc >> 16) & 0xff); /* if it has an offset then we need to compute it */ @@ -10422,9 +11070,13 @@ genAddrOf (iCode * ic) ((char) sym->stack )) & 0xff); emitcode ("mov", "b,a"); emitcode ("mov", "a,_bpx+1"); - emitcode ("addc","a,#!constbyte", (((sym->stack < 0) ? - ((short) (sym->stack - _G.nRegsSaved)) : - ((short) sym->stack )) >> 8) & 0xff); + + offset = (((sym->stack < 0) ? + ((short) (sym->stack - _G.nRegsSaved)) : + ((short) sym->stack )) >> 8) & 0xff; + + emitcode ("addc","a,#!constbyte", offset); + aopPut (AOP (IC_RESULT (ic)), "b", 0); aopPut (AOP (IC_RESULT (ic)), "a", 1); aopPut (AOP (IC_RESULT (ic)), buff, 2); @@ -10471,13 +11123,13 @@ genAddrOf (iCode * ic) if (offset) { switch (offset) { case 1: - tsprintf(s, sizeof(s), "!his",sym->rname); + tsprintf(s, sizeof(s), "#!his",sym->rname); break; case 2: - tsprintf(s, sizeof(s), "!hihis",sym->rname); + tsprintf(s, sizeof(s), "#!hihis",sym->rname); break; case 3: - tsprintf(s, sizeof(s), "!hihihis",sym->rname); + tsprintf(s, sizeof(s), "#!hihihis",sym->rname); break; default: /* should not need this (just in case) */ SNPRINTF (s, sizeof(s), "#(%s >> %d)", @@ -10498,6 +11150,7 @@ release: } +#if 0 // obsolete, and buggy for != xdata /*-----------------------------------------------------------------*/ /* genArrayInit - generates code for address of */ /*-----------------------------------------------------------------*/ @@ -10519,7 +11172,7 @@ genArrayInit (iCode * ic) { // Load immediate value into DPTR. emitcode("mov", "dptr, %s", - aopGet(AOP(IC_LEFT(ic)), 0, TRUE, FALSE, TRUE)); + aopGet(AOP(IC_LEFT(ic)), 0, TRUE, FALSE, NULL)); } else if (AOP_TYPE(IC_LEFT(ic)) != AOP_DPTR) { @@ -10529,10 +11182,10 @@ genArrayInit (iCode * ic) exit(1); #else // a regression because of SDCCcse.c:1.52 - emitcode ("mov", "dpl,%s", aopGet (AOP (left), 0, FALSE, FALSE, TRUE)); - emitcode ("mov", "dph,%s", aopGet (AOP (left), 1, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpl,%s", aopGet (AOP (left), 0, FALSE, FALSE, NULL)); + emitcode ("mov", "dph,%s", aopGet (AOP (left), 1, FALSE, FALSE, NULL)); if (options.model == MODEL_FLAT24) - emitcode ("mov", "dpx,%s", aopGet (AOP (left), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP (left), 2, FALSE, FALSE, NULL)); #endif } @@ -10606,6 +11259,7 @@ genArrayInit (iCode * ic) freeAsmop (IC_LEFT(ic), NULL, ic, TRUE); } +#endif /*-----------------------------------------------------------------*/ /* genFarFarAssign - assignment when both are in far space */ @@ -10621,7 +11275,7 @@ genFarFarAssign (operand * result, operand * right, iCode * ic) { /* quick & easy case. */ D(emitcode(";","genFarFarAssign (1 byte case)");); - MOVA(aopGet(AOP(right), 0, FALSE, FALSE, TRUE)); + MOVA(aopGet(AOP(right), 0, FALSE, FALSE, NULL)); freeAsmop (right, NULL, ic, FALSE); /* now assign DPTR to result */ _G.accInUse++; @@ -10698,7 +11352,7 @@ no time to test now, so later well put in...kpb while (size--) { aopPut (AOP (result), - aopGet (AOP (right), offset, FALSE, FALSE, FALSE), offset); + aopGet (AOP (right), offset, FALSE, FALSE, NULL), offset); offset++; } _endLazyDPSEvaluation (); @@ -10793,7 +11447,7 @@ genAssign (iCode * ic) while (size && ((unsigned int) (lit >> (offset * 8)) != 0)) { aopPut (AOP (result), - aopGet (AOP (right), offset, FALSE, FALSE, TRUE), + aopGet (AOP (right), offset, FALSE, FALSE, NULL), offset); offset++; size--; @@ -10815,7 +11469,7 @@ genAssign (iCode * ic) while (size--) { aopPut (AOP (result), - aopGet (AOP (right), offset, FALSE, FALSE, FALSE), + aopGet (AOP (right), offset, FALSE, FALSE, NULL), offset); offset++; } @@ -10841,7 +11495,7 @@ genJumpTab (iCode * ic) aopOp (IC_JTCOND (ic), ic, FALSE, FALSE); /* get the condition into accumulator */ - l = aopGet (AOP (IC_JTCOND (ic)), 0, FALSE, FALSE, TRUE); + l = aopGet (AOP (IC_JTCOND (ic)), 0, FALSE, FALSE, NULL); MOVA (l); /* multiply by four! */ emitcode ("add", "a,acc"); @@ -10871,19 +11525,18 @@ genCast (iCode * ic) operand *right = IC_RIGHT (ic); int size, offset; - D (emitcode (";", "genCast "); - ); + D (emitcode (";", "genCast ");); /* if they are equivalent then do nothing */ if (operandsEqu (IC_RESULT (ic), IC_RIGHT (ic))) return; - aopOp (right, ic, FALSE, FALSE); - aopOp (result, ic, FALSE, AOP_TYPE (right) == AOP_DPTR); + aopOp (right, ic, FALSE, AOP_IS_STR (result)); + aopOp (result, ic, FALSE, (AOP_TYPE(right) == AOP_DPTR)); /* if the result is a bit */ - // if (AOP_TYPE (result) == AOP_CRY) /* works only for true symbols */ - if (IS_BITVAR(OP_SYMBOL(result)->type)) + if (IS_BITVAR (OP_SYMBOL (result)->type) + && !IS_BITFIELD (OP_SYMBOL (result)->type) ) { /* if the right size is a literal then we know what the value is */ @@ -10926,7 +11579,7 @@ genCast (iCode * ic) while (size--) { aopPut (AOP (result), - aopGet (AOP (right), offset, FALSE, FALSE, FALSE), + aopGet (AOP (right), offset, FALSE, FALSE, NULL), offset); offset++; } @@ -10997,7 +11650,7 @@ genCast (iCode * ic) while (size--) { aopPut (AOP (result), - aopGet (AOP (right), offset, FALSE, FALSE, FALSE), + aopGet (AOP (right), offset, FALSE, FALSE, NULL), offset); offset++; } @@ -11027,7 +11680,7 @@ genCast (iCode * ic) while (size--) { aopPut (AOP (result), - aopGet (AOP (right), offset, FALSE, FALSE, FALSE), + aopGet (AOP (right), offset, FALSE, FALSE, NULL), offset); offset++; } @@ -11044,7 +11697,7 @@ genCast (iCode * ic) while (size--) { aopPut (AOP (result), - aopGet (AOP (right), offset, FALSE, FALSE, FALSE), + aopGet (AOP (right), offset, FALSE, FALSE, NULL), offset); offset++; } @@ -11056,7 +11709,7 @@ genCast (iCode * ic) /* also, if the source is a bit, we don't need to sign extend, because * it can't possibly have set the sign bit. */ - if (SPEC_USIGN (rtype) || !IS_SPEC (rtype) || AOP_TYPE (right) == AOP_CRY) + if (!IS_SPEC (rtype) || SPEC_USIGN (rtype) || AOP_TYPE (right) == AOP_CRY) { while (size--) { @@ -11066,9 +11719,8 @@ genCast (iCode * ic) else { /* we need to extend the sign :{ */ - char *l = aopGet (AOP (right), AOP_SIZE (right) - 1, - FALSE, FALSE, TRUE); - MOVA (l); + MOVA (aopGet (AOP (right), AOP_SIZE (right) - 1, + FALSE, FALSE, NULL)); emitcode ("rlc", "a"); emitcode ("subb", "a,acc"); while (size--) @@ -11126,7 +11778,7 @@ genDjnz (iCode * ic, iCode * ifx) * the accumulator, we must explicitly write * it back after the decrement. */ - char *rByte = aopGet(AOP(IC_RESULT(ic)), 0, FALSE, FALSE, TRUE); + char *rByte = aopGet(AOP(IC_RESULT(ic)), 0, FALSE, FALSE, NULL); if (strcmp(rByte, "a")) { @@ -11146,13 +11798,13 @@ genDjnz (iCode * ic, iCode * ifx) else if (IS_AOP_PREG (IC_RESULT (ic))) { emitcode ("dec", "%s", - aopGet (AOP (IC_RESULT (ic)), 0, FALSE, FALSE, FALSE)); - emitcode ("mov", "a,%s", aopGet (AOP (IC_RESULT (ic)), 0, FALSE, FALSE, FALSE)); + aopGet (AOP (IC_RESULT (ic)), 0, FALSE, FALSE, NULL)); + emitcode ("mov", "a,%s", aopGet (AOP (IC_RESULT (ic)), 0, FALSE, FALSE, NULL)); emitcode ("jnz", "!tlabel", lbl->key + 100); } else { - emitcode ("djnz", "%s,!tlabel", aopGet (AOP (IC_RESULT (ic)), 0, FALSE, TRUE, FALSE), + emitcode ("djnz", "%s,!tlabel", aopGet (AOP (IC_RESULT (ic)), 0, FALSE, TRUE, NULL), lbl->key + 100); } emitcode ("sjmp", "!tlabel", lbl1->key + 100); @@ -11171,53 +11823,55 @@ genDjnz (iCode * ic, iCode * ifx) static void genReceive (iCode * ic) { - int size = getSize (operandType (IC_RESULT (ic))); int offset = 0; int rb1off ; - D (emitcode (";", "genReceive "); - ); + D (emitcode (";", "genReceive ");); - if (ic->argreg == 1) { /* first parameter */ - if (isOperandInFarSpace (IC_RESULT (ic)) && - (OP_SYMBOL (IC_RESULT (ic))->isspilt || - IS_TRUE_SYMOP (IC_RESULT (ic)))) - { - offset = fReturnSizeDS390 - size; - while (size--) - { - emitcode ("push", "%s", (strcmp (fReturn[fReturnSizeDS390 - offset - 1], "a") ? - fReturn[fReturnSizeDS390 - offset - 1] : "acc")); - offset++; - } - aopOp (IC_RESULT (ic), ic, FALSE, FALSE); - size = AOP_SIZE (IC_RESULT (ic)); - offset = 0; - while (size--) - { - emitcode ("pop", "acc"); - aopPut (AOP (IC_RESULT (ic)), "a", offset++); - } - - } else { - _G.accInUse++; - aopOp (IC_RESULT (ic), ic, FALSE, FALSE); - _G.accInUse--; - assignResultValue (IC_RESULT (ic)); - } - } else { /* second receive onwards */ - /* this gets a little tricky since unused recevies will be + if (ic->argreg == 1) + { + /* first parameter */ + if (AOP_IS_STR(IC_RESULT(ic))) + { + /* Nothing to do: it's already in the proper place. */ + return; + } + else + { + bool useDp2; + + useDp2 = isOperandInFarSpace (IC_RESULT (ic)) && + (OP_SYMBOL (IC_RESULT (ic))->isspilt || + IS_TRUE_SYMOP (IC_RESULT (ic))); + + _G.accInUse++; + aopOp (IC_RESULT (ic), ic, FALSE, useDp2); + _G.accInUse--; + + /* Sanity checking... */ + if (AOP_USESDPTR(IC_RESULT(ic))) + { + werror (E_INTERNAL_ERROR, __FILE__, __LINE__, + "genReceive got unexpected DPTR."); + } + assignResultValue (IC_RESULT (ic)); + } + } + else + { + /* second receive onwards */ + /* this gets a little tricky since unused recevies will be eliminated, we have saved the reg in the type field . and we use that to figure out which register to use */ - aopOp (IC_RESULT (ic), ic, FALSE, FALSE); - rb1off = ic->argreg; - while (size--) { - aopPut (AOP (IC_RESULT (ic)), rb1regs[rb1off++ -5], offset++); - } - - } - freeAsmop (IC_RESULT (ic), NULL, ic, TRUE); + aopOp (IC_RESULT (ic), ic, FALSE, FALSE); + rb1off = ic->argreg; + while (size--) + { + aopPut (AOP (IC_RESULT (ic)), rb1regs[rb1off++ -5], offset++); + } + } + freeAsmop (IC_RESULT (ic), NULL, ic, TRUE); } /*-----------------------------------------------------------------*/ @@ -11250,10 +11904,10 @@ static void genMemcpyX2X( iCode *ic, int nparms, operand **parms, int fromc) aopOp (from, ic->next, FALSE, FALSE); /* get from into DPTR1 */ - emitcode ("mov", "dpl1,%s", aopGet (AOP (from), 0, FALSE, FALSE, TRUE)); - emitcode ("mov", "dph1,%s", aopGet (AOP (from), 1, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpl1,%s", aopGet (AOP (from), 0, FALSE, FALSE, NULL)); + emitcode ("mov", "dph1,%s", aopGet (AOP (from), 1, FALSE, FALSE, NULL)); if (options.model == MODEL_FLAT24) { - emitcode ("mov", "dpx1,%s", aopGet (AOP (from), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx1,%s", aopGet (AOP (from), 2, FALSE, FALSE, NULL)); } freeAsmop (from, NULL, ic, FALSE); @@ -11264,22 +11918,22 @@ static void genMemcpyX2X( iCode *ic, int nparms, operand **parms, int fromc) if (AOP_TYPE (to) != AOP_STR) { /* if already in DPTR then we need to push */ if (AOP_TYPE(to) == AOP_DPTR) { - emitcode ("push", "%s", aopGet (AOP (to), 0, FALSE, TRUE, TRUE)); - emitcode ("push", "%s", aopGet (AOP (to), 1, FALSE, TRUE, TRUE)); + emitcode ("push", "%s", aopGet (AOP (to), 0, FALSE, TRUE, NULL)); + emitcode ("push", "%s", aopGet (AOP (to), 1, FALSE, TRUE, NULL)); if (options.model == MODEL_FLAT24) - emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, NULL)); emitcode ("pop", "dph"); emitcode ("pop", "dpl"); } else { _startLazyDPSEvaluation (); /* if this is remateriazable */ if (AOP_TYPE (to) == AOP_IMMD) { - emitcode ("mov", "dptr,%s", aopGet (AOP (to), 0, TRUE, FALSE, FALSE)); + emitcode ("mov", "dptr,%s", aopGet (AOP (to), 0, TRUE, FALSE, NULL)); } else { /* we need to get it byte by byte */ - emitcode ("mov", "dpl,%s", aopGet (AOP (to), 0, FALSE, FALSE, TRUE)); - emitcode ("mov", "dph,%s", aopGet (AOP (to), 1, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpl,%s", aopGet (AOP (to), 0, FALSE, FALSE, NULL)); + emitcode ("mov", "dph,%s", aopGet (AOP (to), 1, FALSE, FALSE, NULL)); if (options.model == MODEL_FLAT24) { - emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, NULL)); } } _endLazyDPSEvaluation (); @@ -11293,7 +11947,7 @@ static void genMemcpyX2X( iCode *ic, int nparms, operand **parms, int fromc) /* now for the actual copy */ if (AOP_TYPE(count) == AOP_LIT && (int)floatFromVal (AOP(count)->aopu.aop_lit) <= 256) { - emitcode ("mov", "b,%s",aopGet(AOP(count),0,FALSE,FALSE,FALSE)); + emitcode ("mov", "b,%s",aopGet(AOP(count),0,FALSE,FALSE,NULL)); if (fromc) { emitcode ("lcall","__bi_memcpyc2x_s"); } else { @@ -11304,8 +11958,8 @@ static void genMemcpyX2X( iCode *ic, int nparms, operand **parms, int fromc) symbol *lbl1 = newiTempLabel(NULL); emitcode (";"," Auto increment but no djnz"); - emitcode ("mov","_ap,%s",aopGet (AOP (count), 0, FALSE, TRUE, TRUE)); - emitcode ("mov","b,%s",aopGet (AOP (count), 1, FALSE, TRUE, TRUE)); + emitcode ("mov","_ap,%s",aopGet (AOP (count), 0, FALSE, TRUE, NULL)); + emitcode ("mov","b,%s",aopGet (AOP (count), 1, FALSE, TRUE, NULL)); freeAsmop (count, NULL, ic, FALSE); emitcode ("mov", "dps,#!constbyte",0x21); /* Select DPTR2 & auto-toggle. */ emitcode ("","!tlabeldef",lbl->key+100); @@ -11365,10 +12019,10 @@ static void genMemcmpX2X( iCode *ic, int nparms, operand **parms, int fromc) aopOp (from, ic->next, FALSE, FALSE); /* get from into DPTR1 */ - emitcode ("mov", "dpl1,%s", aopGet (AOP (from), 0, FALSE, FALSE, TRUE)); - emitcode ("mov", "dph1,%s", aopGet (AOP (from), 1, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpl1,%s", aopGet (AOP (from), 0, FALSE, FALSE, NULL)); + emitcode ("mov", "dph1,%s", aopGet (AOP (from), 1, FALSE, FALSE, NULL)); if (options.model == MODEL_FLAT24) { - emitcode ("mov", "dpx1,%s", aopGet (AOP (from), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx1,%s", aopGet (AOP (from), 2, FALSE, FALSE, NULL)); } freeAsmop (from, NULL, ic, FALSE); @@ -11379,22 +12033,22 @@ static void genMemcmpX2X( iCode *ic, int nparms, operand **parms, int fromc) if (AOP_TYPE (to) != AOP_STR) { /* if already in DPTR then we need to push */ if (AOP_TYPE(to) == AOP_DPTR) { - emitcode ("push", "%s", aopGet (AOP (to), 0, FALSE, TRUE, TRUE)); - emitcode ("push", "%s", aopGet (AOP (to), 1, FALSE, TRUE, TRUE)); + emitcode ("push", "%s", aopGet (AOP (to), 0, FALSE, TRUE, NULL)); + emitcode ("push", "%s", aopGet (AOP (to), 1, FALSE, TRUE, NULL)); if (options.model == MODEL_FLAT24) - emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, NULL)); emitcode ("pop", "dph"); emitcode ("pop", "dpl"); } else { _startLazyDPSEvaluation (); /* if this is remateriazable */ if (AOP_TYPE (to) == AOP_IMMD) { - emitcode ("mov", "dptr,%s", aopGet (AOP (to), 0, TRUE, FALSE, FALSE)); + emitcode ("mov", "dptr,%s", aopGet (AOP (to), 0, TRUE, FALSE, NULL)); } else { /* we need to get it byte by byte */ - emitcode ("mov", "dpl,%s", aopGet (AOP (to), 0, FALSE, FALSE, TRUE)); - emitcode ("mov", "dph,%s", aopGet (AOP (to), 1, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpl,%s", aopGet (AOP (to), 0, FALSE, FALSE, NULL)); + emitcode ("mov", "dph,%s", aopGet (AOP (to), 1, FALSE, FALSE, NULL)); if (options.model == MODEL_FLAT24) { - emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, NULL)); } } _endLazyDPSEvaluation (); @@ -11409,7 +12063,7 @@ static void genMemcmpX2X( iCode *ic, int nparms, operand **parms, int fromc) /* now for the actual compare */ if (AOP_TYPE(count) == AOP_LIT && (int)floatFromVal (AOP(count)->aopu.aop_lit) <= 256) { - emitcode ("mov", "b,%s",aopGet(AOP(count),0,FALSE,FALSE,FALSE)); + emitcode ("mov", "b,%s",aopGet(AOP(count),0,FALSE,FALSE,NULL)); if (fromc) emitcode("lcall","__bi_memcmpc2x_s"); else @@ -11423,8 +12077,8 @@ static void genMemcmpX2X( iCode *ic, int nparms, operand **parms, int fromc) emitcode("push","ar0"); emitcode (";"," Auto increment but no djnz"); - emitcode ("mov","_ap,%s",aopGet (AOP (count), 0, FALSE, TRUE, TRUE)); - emitcode ("mov","b,%s",aopGet (AOP (count), 1, FALSE, TRUE, TRUE)); + emitcode ("mov","_ap,%s",aopGet (AOP (count), 0, FALSE, TRUE, NULL)); + emitcode ("mov","b,%s",aopGet (AOP (count), 1, FALSE, TRUE, NULL)); freeAsmop (count, NULL, ic, FALSE); emitcode ("mov", "dps,#!constbyte",0x21); /* Select DPTR2 & auto-toggle. */ emitcode ("","!tlabeldef",lbl->key+100); @@ -11496,10 +12150,10 @@ static void genInp( iCode *ic, int nparms, operand **parms) aopOp (from, ic->next, FALSE, FALSE); /* get from into DPTR1 */ - emitcode ("mov", "dpl1,%s", aopGet (AOP (from), 0, FALSE, FALSE, TRUE)); - emitcode ("mov", "dph1,%s", aopGet (AOP (from), 1, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpl1,%s", aopGet (AOP (from), 0, FALSE, FALSE, NULL)); + emitcode ("mov", "dph1,%s", aopGet (AOP (from), 1, FALSE, FALSE, NULL)); if (options.model == MODEL_FLAT24) { - emitcode ("mov", "dpx1,%s", aopGet (AOP (from), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx1,%s", aopGet (AOP (from), 2, FALSE, FALSE, NULL)); } freeAsmop (from, NULL, ic, FALSE); @@ -11510,22 +12164,22 @@ static void genInp( iCode *ic, int nparms, operand **parms) if (AOP_TYPE (to) != AOP_STR) { /* if already in DPTR then we need to push */ if (AOP_TYPE(to) == AOP_DPTR) { - emitcode ("push", "%s", aopGet (AOP (to), 0, FALSE, TRUE, TRUE)); - emitcode ("push", "%s", aopGet (AOP (to), 1, FALSE, TRUE, TRUE)); + emitcode ("push", "%s", aopGet (AOP (to), 0, FALSE, TRUE, NULL)); + emitcode ("push", "%s", aopGet (AOP (to), 1, FALSE, TRUE, NULL)); if (options.model == MODEL_FLAT24) - emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, NULL)); emitcode ("pop", "dph"); emitcode ("pop", "dpl"); } else { _startLazyDPSEvaluation (); /* if this is remateriazable */ if (AOP_TYPE (to) == AOP_IMMD) { - emitcode ("mov", "dptr,%s", aopGet (AOP (to), 0, TRUE, FALSE, FALSE)); + emitcode ("mov", "dptr,%s", aopGet (AOP (to), 0, TRUE, FALSE, NULL)); } else { /* we need to get it byte by byte */ - emitcode ("mov", "dpl,%s", aopGet (AOP (to), 0, FALSE, FALSE, TRUE)); - emitcode ("mov", "dph,%s", aopGet (AOP (to), 1, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpl,%s", aopGet (AOP (to), 0, FALSE, FALSE, NULL)); + emitcode ("mov", "dph,%s", aopGet (AOP (to), 1, FALSE, FALSE, NULL)); if (options.model == MODEL_FLAT24) { - emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, NULL)); } } _endLazyDPSEvaluation (); @@ -11542,7 +12196,7 @@ static void genInp( iCode *ic, int nparms, operand **parms) (int)floatFromVal (AOP(count)->aopu.aop_lit) <= 256) { emitcode (";","OH JOY auto increment with djnz (very fast)"); emitcode ("mov", "dps,#!constbyte",0x1); /* Select DPTR2 */ - emitcode ("mov", "b,%s",aopGet(AOP(count),0,FALSE,FALSE,FALSE)); + emitcode ("mov", "b,%s",aopGet(AOP(count),0,FALSE,FALSE,NULL)); freeAsmop (count, NULL, ic, FALSE); emitcode ("","!tlabeldef",lbl->key+100); emitcode ("movx", "a,@dptr"); /* read data from port */ @@ -11555,8 +12209,8 @@ static void genInp( iCode *ic, int nparms, operand **parms) symbol *lbl1 = newiTempLabel(NULL); emitcode (";"," Auto increment but no djnz"); - emitcode ("mov","_ap,%s",aopGet (AOP (count), 0, FALSE, TRUE, TRUE)); - emitcode ("mov","b,%s",aopGet (AOP (count), 1, FALSE, TRUE, TRUE)); + emitcode ("mov","_ap,%s",aopGet (AOP (count), 0, FALSE, TRUE, NULL)); + emitcode ("mov","b,%s",aopGet (AOP (count), 1, FALSE, TRUE, NULL)); freeAsmop (count, NULL, ic, FALSE); emitcode ("mov", "dps,#!constbyte",0x1); /* Select DPTR2 */ emitcode ("","!tlabeldef",lbl->key+100); @@ -11617,10 +12271,10 @@ static void genOutp( iCode *ic, int nparms, operand **parms) aopOp (from, ic->next, FALSE, FALSE); /* get from into DPTR1 */ - emitcode ("mov", "dpl1,%s", aopGet (AOP (from), 0, FALSE, FALSE, TRUE)); - emitcode ("mov", "dph1,%s", aopGet (AOP (from), 1, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpl1,%s", aopGet (AOP (from), 0, FALSE, FALSE, NULL)); + emitcode ("mov", "dph1,%s", aopGet (AOP (from), 1, FALSE, FALSE, NULL)); if (options.model == MODEL_FLAT24) { - emitcode ("mov", "dpx1,%s", aopGet (AOP (from), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx1,%s", aopGet (AOP (from), 2, FALSE, FALSE, NULL)); } freeAsmop (from, NULL, ic, FALSE); @@ -11631,22 +12285,22 @@ static void genOutp( iCode *ic, int nparms, operand **parms) if (AOP_TYPE (to) != AOP_STR) { /* if already in DPTR then we need to push */ if (AOP_TYPE(to) == AOP_DPTR) { - emitcode ("push", "%s", aopGet (AOP (to), 0, FALSE, TRUE, TRUE)); - emitcode ("push", "%s", aopGet (AOP (to), 1, FALSE, TRUE, TRUE)); + emitcode ("push", "%s", aopGet (AOP (to), 0, FALSE, TRUE, NULL)); + emitcode ("push", "%s", aopGet (AOP (to), 1, FALSE, TRUE, NULL)); if (options.model == MODEL_FLAT24) - emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, NULL)); emitcode ("pop", "dph"); emitcode ("pop", "dpl"); } else { _startLazyDPSEvaluation (); /* if this is remateriazable */ if (AOP_TYPE (to) == AOP_IMMD) { - emitcode ("mov", "dptr,%s", aopGet (AOP (to), 0, TRUE, FALSE, FALSE)); + emitcode ("mov", "dptr,%s", aopGet (AOP (to), 0, TRUE, FALSE, NULL)); } else { /* we need to get it byte by byte */ - emitcode ("mov", "dpl,%s", aopGet (AOP (to), 0, FALSE, FALSE, TRUE)); - emitcode ("mov", "dph,%s", aopGet (AOP (to), 1, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpl,%s", aopGet (AOP (to), 0, FALSE, FALSE, NULL)); + emitcode ("mov", "dph,%s", aopGet (AOP (to), 1, FALSE, FALSE, NULL)); if (options.model == MODEL_FLAT24) { - emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, NULL)); } } _endLazyDPSEvaluation (); @@ -11663,7 +12317,7 @@ static void genOutp( iCode *ic, int nparms, operand **parms) (int)floatFromVal (AOP(count)->aopu.aop_lit) <= 256) { emitcode (";","OH JOY auto increment with djnz (very fast)"); emitcode ("mov", "dps,#!constbyte",0x0); /* Select DPTR */ - emitcode ("mov", "b,%s",aopGet(AOP(count),0,FALSE,FALSE,FALSE)); + emitcode ("mov", "b,%s",aopGet(AOP(count),0,FALSE,FALSE,NULL)); emitcode ("","!tlabeldef",lbl->key+100); emitcode ("movx", "a,@dptr"); /* read data from port */ emitcode ("inc","dps"); /* switch to DPTR2 */ @@ -11676,8 +12330,8 @@ static void genOutp( iCode *ic, int nparms, operand **parms) symbol *lbl1 = newiTempLabel(NULL); emitcode (";"," Auto increment but no djnz"); - emitcode ("mov","_ap,%s",aopGet (AOP (count), 0, FALSE, TRUE, TRUE)); - emitcode ("mov","b,%s",aopGet (AOP (count), 1, FALSE, TRUE, TRUE)); + emitcode ("mov","_ap,%s",aopGet (AOP (count), 0, FALSE, TRUE, NULL)); + emitcode ("mov","b,%s",aopGet (AOP (count), 1, FALSE, TRUE, NULL)); freeAsmop (count, NULL, ic, FALSE); emitcode ("mov", "dps,#!constbyte",0x0); /* Select DPTR */ emitcode ("","!tlabeldef",lbl->key+100); @@ -11719,9 +12373,9 @@ static void genSwapW(iCode *ic, int nparms, operand **parms) assert(getSize(operandType(src))==2); aopOp (src, ic, FALSE, FALSE); - emitcode ("mov","a,%s",aopGet(AOP(src),0,FALSE,FALSE,TRUE)); + emitcode ("mov","a,%s",aopGet(AOP(src),0,FALSE,FALSE,NULL)); _G.accInUse++; - emitcode ("mov","b,%s",aopGet(AOP(src),1,FALSE,FALSE,FALSE)); + MOVB(aopGet(AOP(src),1,FALSE,FALSE,"b")); _G.accInUse--; freeAsmop (src, NULL, ic, FALSE); @@ -11740,7 +12394,7 @@ static void genMemsetX(iCode *ic, int nparms, operand **parms) symbol *lbl; char *l; int i; - bitVect *rsave = NULL; + bitVect *rsave; /* we know it has to be 3 parameters */ assert (nparms == 3); @@ -11766,22 +12420,22 @@ static void genMemsetX(iCode *ic, int nparms, operand **parms) if (AOP_TYPE (to) != AOP_STR) { /* if already in DPTR then we need to push */ if (AOP_TYPE(to) == AOP_DPTR) { - emitcode ("push", "%s", aopGet (AOP (to), 0, FALSE, TRUE, TRUE)); - emitcode ("push", "%s", aopGet (AOP (to), 1, FALSE, TRUE, TRUE)); + emitcode ("push", "%s", aopGet (AOP (to), 0, FALSE, TRUE, NULL)); + emitcode ("push", "%s", aopGet (AOP (to), 1, FALSE, TRUE, NULL)); if (options.model == MODEL_FLAT24) - emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, NULL)); emitcode ("pop", "dph"); emitcode ("pop", "dpl"); } else { _startLazyDPSEvaluation (); /* if this is remateriazable */ if (AOP_TYPE (to) == AOP_IMMD) { - emitcode ("mov", "dptr,%s", aopGet (AOP (to), 0, TRUE, FALSE, FALSE)); + emitcode ("mov", "dptr,%s", aopGet (AOP (to), 0, TRUE, FALSE, NULL)); } else { /* we need to get it byte by byte */ - emitcode ("mov", "dpl,%s", aopGet (AOP (to), 0, FALSE, FALSE, TRUE)); - emitcode ("mov", "dph,%s", aopGet (AOP (to), 1, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpl,%s", aopGet (AOP (to), 0, FALSE, FALSE, NULL)); + emitcode ("mov", "dph,%s", aopGet (AOP (to), 1, FALSE, FALSE, NULL)); if (options.model == MODEL_FLAT24) { - emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, TRUE)); + emitcode ("mov", "dpx,%s", aopGet (AOP (to), 2, FALSE, FALSE, NULL)); } } _endLazyDPSEvaluation (); @@ -11795,8 +12449,8 @@ static void genMemsetX(iCode *ic, int nparms, operand **parms) /* now for the actual copy */ if (AOP_TYPE(count) == AOP_LIT && (int)floatFromVal (AOP(count)->aopu.aop_lit) <= 256) { - l = aopGet(AOP (val), 0, FALSE, FALSE, TRUE); - emitcode ("mov", "b,%s",aopGet(AOP(count),0,FALSE,FALSE,FALSE)); + l = aopGet(AOP (val), 0, FALSE, FALSE, NULL); + emitcode ("mov", "b,%s",aopGet(AOP(count),0,FALSE,FALSE,NULL)); MOVA(l); emitcode ("","!tlabeldef",lbl->key+100); emitcode ("movx", "@dptr,a"); @@ -11805,11 +12459,10 @@ static void genMemsetX(iCode *ic, int nparms, operand **parms) } else { symbol *lbl1 = newiTempLabel(NULL); - emitcode ("mov","_ap,%s",aopGet (AOP (count), 0, FALSE, TRUE, TRUE)); - emitcode ("mov","b,%s",aopGet (AOP (count), 1, FALSE, TRUE, TRUE)); + emitcode ("mov","_ap,%s",aopGet (AOP (count), 0, FALSE, TRUE, NULL)); + emitcode ("mov","b,%s",aopGet (AOP (count), 1, FALSE, TRUE, NULL)); emitcode ("","!tlabeldef",lbl->key+100); - l = aopGet(AOP (val), 0, FALSE, FALSE, TRUE); - MOVA(l); + MOVA (aopGet(AOP (val), 0, FALSE, FALSE, NULL)); emitcode ("movx", "@dptr,a"); emitcode ("inc", "dptr"); emitcode ("mov","a,b"); @@ -11844,7 +12497,7 @@ static void genNatLibLoadPrimitive(iCode *ic, int nparms, operand **parms,int si pnum = parms[0]; aopOp (pnum, ic, FALSE, FALSE); - emitcode ("mov","a,%s",aopGet(AOP(pnum),0,FALSE,FALSE,FALSE)); + emitcode ("mov","a,%s",aopGet(AOP(pnum),0,FALSE,FALSE,DP2_RESULT_REG)); freeAsmop (pnum, NULL, ic, FALSE); emitcode ("lcall","NatLib_LoadPrimitive"); aopOp (result=IC_RESULT(ic), ic, FALSE, FALSE); @@ -11854,7 +12507,8 @@ static void genNatLibLoadPrimitive(iCode *ic, int nparms, operand **parms,int si emitcode ("push","a%s",javaRet[i]); } for (i=0; i < size ; i++ ) { - emitcode ("pop","a%s",aopGet(AOP(result),i,FALSE,FALSE,FALSE)); + emitcode ("pop","a%s", + aopGet(AOP(result),i,FALSE,FALSE,DP2_RESULT_REG)); } } else { for (i = 0 ; i < size ; i++ ) { @@ -11882,7 +12536,7 @@ static void genNatLibLoadPointer(iCode *ic, int nparms, operand **parms) pnum = parms[0]; aopOp (pnum, ic, FALSE, FALSE); - emitcode ("mov","a,%s",aopGet(AOP(pnum),0,FALSE,FALSE,FALSE)); + emitcode ("mov","a,%s",aopGet(AOP(pnum),0,FALSE,FALSE,DP2_RESULT_REG)); freeAsmop (pnum, NULL, ic, FALSE); emitcode ("lcall","NatLib_LoadPointer"); aopOp (result=IC_RESULT(ic), ic, FALSE, FALSE); @@ -11915,12 +12569,13 @@ static void genNatLibInstallStateBlock(iCode *ic, int nparms, aopOp (psb, ic, FALSE, FALSE); if (AOP_TYPE (psb) == AOP_IMMD) { emitcode ("mov","dps,#1"); - emitcode ("mov", "dptr,%s", aopGet (AOP (psb), 0, TRUE, FALSE, FALSE)); + emitcode ("mov", "dptr,%s", + aopGet (AOP (psb), 0, TRUE, FALSE, DP2_RESULT_REG)); emitcode ("mov","dps,#0"); } else { - emitcode ("mov","dpl1,%s",aopGet(AOP(psb),0,FALSE,FALSE,FALSE)); - emitcode ("mov","dph1,%s",aopGet(AOP(psb),1,FALSE,FALSE,FALSE)); - emitcode ("mov","dpx1,%s",aopGet(AOP(psb),2,FALSE,FALSE,FALSE)); + emitcode ("mov","dpl1,%s",aopGet(AOP(psb),0,FALSE,FALSE,DP2_RESULT_REG)); + emitcode ("mov","dph1,%s",aopGet(AOP(psb),1,FALSE,FALSE,DP2_RESULT_REG)); + emitcode ("mov","dpx1,%s",aopGet(AOP(psb),2,FALSE,FALSE,DP2_RESULT_REG)); } freeAsmop (psb, NULL, ic, FALSE); @@ -11930,13 +12585,13 @@ static void genNatLibInstallStateBlock(iCode *ic, int nparms, /* put handle into r3:r2 */ aopOp (handle, ic, FALSE, FALSE); if (aopHasRegs(AOP(handle),R2_IDX,R3_IDX)) { - emitcode ("push","%s",aopGet(AOP(handle),0,FALSE,TRUE,FALSE)); - emitcode ("push","%s",aopGet(AOP(handle),1,FALSE,TRUE,FALSE)); + emitcode ("push","%s",aopGet(AOP(handle),0,FALSE,TRUE,DP2_RESULT_REG)); + emitcode ("push","%s",aopGet(AOP(handle),1,FALSE,TRUE,DP2_RESULT_REG)); emitcode ("pop","ar3"); emitcode ("pop","ar2"); } else { - emitcode ("mov","r2,%s",aopGet(AOP(handle),0,FALSE,TRUE,FALSE)); - emitcode ("mov","r3,%s",aopGet(AOP(handle),1,FALSE,TRUE,FALSE)); + emitcode ("mov","r2,%s",aopGet(AOP(handle),0,FALSE,TRUE,DP2_RESULT_REG)); + emitcode ("mov","r3,%s",aopGet(AOP(handle),1,FALSE,TRUE,DP2_RESULT_REG)); } freeAsmop (psb, NULL, ic, FALSE); @@ -11997,8 +12652,10 @@ static void genNatLibGetStateBlock(iCode *ic,int nparms, if (aopHasRegs(AOP(IC_RESULT(ic)),R2_IDX,R3_IDX)) { emitcode ("push","ar3"); emitcode ("push","ar2"); - emitcode ("pop","%s",aopGet(AOP(IC_RESULT(ic)),0,FALSE,TRUE,FALSE)); - emitcode ("pop","%s",aopGet(AOP(IC_RESULT(ic)),1,FALSE,TRUE,FALSE)); + emitcode ("pop","%s", + aopGet(AOP(IC_RESULT(ic)),0,FALSE,TRUE,DP2_RESULT_REG)); + emitcode ("pop","%s", + aopGet(AOP(IC_RESULT(ic)),1,FALSE,TRUE,DP2_RESULT_REG)); } else { aopPut(AOP(IC_RESULT(ic)),"r2",0); aopPut(AOP(IC_RESULT(ic)),"r3",1); @@ -12029,19 +12686,19 @@ static void genMMMalloc (iCode *ic,int nparms, operand **parms, /* put the size in R4-R2 */ if (aopHasRegs(AOP(bsize),R2_IDX, (size==3 ? R4_IDX: R3_IDX))) { - emitcode("push","%s",aopGet(AOP(bsize),0,FALSE,TRUE,FALSE)); - emitcode("push","%s",aopGet(AOP(bsize),1,FALSE,TRUE,FALSE)); + emitcode("push","%s",aopGet(AOP(bsize),0,FALSE,TRUE,DP2_RESULT_REG)); + emitcode("push","%s",aopGet(AOP(bsize),1,FALSE,TRUE,DP2_RESULT_REG)); if (size==3) { - emitcode("push","%s",aopGet(AOP(bsize),2,FALSE,TRUE,FALSE)); + emitcode("push","%s",aopGet(AOP(bsize),2,FALSE,TRUE,DP2_RESULT_REG)); emitcode("pop","ar4"); } emitcode("pop","ar3"); emitcode("pop","ar2"); } else { - emitcode ("mov","r2,%s",aopGet(AOP(bsize),0,FALSE,TRUE,FALSE)); - emitcode ("mov","r3,%s",aopGet(AOP(bsize),1,FALSE,TRUE,FALSE)); + emitcode ("mov","r2,%s",aopGet(AOP(bsize),0,FALSE,TRUE,DP2_RESULT_REG)); + emitcode ("mov","r3,%s",aopGet(AOP(bsize),1,FALSE,TRUE,DP2_RESULT_REG)); if (size==3) { - emitcode("mov","r4,%s",aopGet(AOP(bsize),2,FALSE,TRUE,FALSE)); + emitcode("mov","r4,%s",aopGet(AOP(bsize),2,FALSE,TRUE,DP2_RESULT_REG)); } } freeAsmop (bsize, NULL, ic, FALSE); @@ -12059,8 +12716,10 @@ static void genMMMalloc (iCode *ic,int nparms, operand **parms, if (aopHasRegs(AOP(IC_RESULT(ic)),R2_IDX,R3_IDX)) { emitcode ("push","ar3"); emitcode ("push","ar2"); - emitcode ("pop","%s",aopGet(AOP(IC_RESULT(ic)),0,FALSE,TRUE,FALSE)); - emitcode ("pop","%s",aopGet(AOP(IC_RESULT(ic)),1,FALSE,TRUE,FALSE)); + emitcode ("pop","%s", + aopGet(AOP(IC_RESULT(ic)),0,FALSE,TRUE,DP2_RESULT_REG)); + emitcode ("pop","%s", + aopGet(AOP(IC_RESULT(ic)),1,FALSE,TRUE,DP2_RESULT_REG)); } else { aopPut(AOP(IC_RESULT(ic)),"r2",0); aopPut(AOP(IC_RESULT(ic)),"r3",1); @@ -12088,13 +12747,17 @@ static void genMMDeref (iCode *ic,int nparms, operand **parms) /* put the size in R4-R2 */ if (aopHasRegs(AOP(handle),R2_IDX,R3_IDX)) { - emitcode("push","%s",aopGet(AOP(handle),0,FALSE,TRUE,FALSE)); - emitcode("push","%s",aopGet(AOP(handle),1,FALSE,TRUE,FALSE)); + emitcode("push","%s", + aopGet(AOP(handle),0,FALSE,TRUE,DP2_RESULT_REG)); + emitcode("push","%s", + aopGet(AOP(handle),1,FALSE,TRUE,DP2_RESULT_REG)); emitcode("pop","ar3"); emitcode("pop","ar2"); } else { - emitcode ("mov","r2,%s",aopGet(AOP(handle),0,FALSE,TRUE,FALSE)); - emitcode ("mov","r3,%s",aopGet(AOP(handle),1,FALSE,TRUE,FALSE)); + emitcode ("mov","r2,%s", + aopGet(AOP(handle),0,FALSE,TRUE,DP2_RESULT_REG)); + emitcode ("mov","r3,%s", + aopGet(AOP(handle),1,FALSE,TRUE,DP2_RESULT_REG)); } freeAsmop (handle, NULL, ic, FALSE); @@ -12106,9 +12769,14 @@ static void genMMDeref (iCode *ic,int nparms, operand **parms) if (rsym->liveFrom != rsym->liveTo) { aopOp (IC_RESULT(ic),ic,FALSE,FALSE); if (AOP_TYPE(IC_RESULT(ic)) != AOP_STR) { + _startLazyDPSEvaluation (); + aopPut(AOP(IC_RESULT(ic)),"dpl",0); aopPut(AOP(IC_RESULT(ic)),"dph",1); aopPut(AOP(IC_RESULT(ic)),"dpx",2); + + _endLazyDPSEvaluation (); + } } } @@ -12134,13 +12802,17 @@ static void genMMUnrestrictedPersist(iCode *ic,int nparms, operand **parms) /* put the size in R3-R2 */ if (aopHasRegs(AOP(handle),R2_IDX,R3_IDX)) { - emitcode("push","%s",aopGet(AOP(handle),0,FALSE,TRUE,FALSE)); - emitcode("push","%s",aopGet(AOP(handle),1,FALSE,TRUE,FALSE)); + emitcode("push","%s", + aopGet(AOP(handle),0,FALSE,TRUE,DP2_RESULT_REG)); + emitcode("push","%s", + aopGet(AOP(handle),1,FALSE,TRUE,DP2_RESULT_REG)); emitcode("pop","ar3"); emitcode("pop","ar2"); } else { - emitcode ("mov","r2,%s",aopGet(AOP(handle),0,FALSE,TRUE,FALSE)); - emitcode ("mov","r3,%s",aopGet(AOP(handle),1,FALSE,TRUE,FALSE)); + emitcode ("mov","r2,%s", + aopGet(AOP(handle),0,FALSE,TRUE,DP2_RESULT_REG)); + emitcode ("mov","r3,%s", + aopGet(AOP(handle),1,FALSE,TRUE,DP2_RESULT_REG)); } freeAsmop (handle, NULL, ic, FALSE); @@ -12177,24 +12849,29 @@ static void genSystemExecJavaProcess(iCode *ic,int nparms, operand **parms) /* put the handle in R3-R2 */ aopOp (handle,ic,FALSE,FALSE); if (aopHasRegs(AOP(handle),R2_IDX,R3_IDX)) { - emitcode("push","%s",aopGet(AOP(handle),0,FALSE,TRUE,FALSE)); - emitcode("push","%s",aopGet(AOP(handle),1,FALSE,TRUE,FALSE)); + emitcode("push","%s", + aopGet(AOP(handle),0,FALSE,TRUE,DP2_RESULT_REG)); + emitcode("push","%s", + aopGet(AOP(handle),1,FALSE,TRUE,DP2_RESULT_REG)); emitcode("pop","ar3"); emitcode("pop","ar2"); } else { - emitcode ("mov","r2,%s",aopGet(AOP(handle),0,FALSE,TRUE,FALSE)); - emitcode ("mov","r3,%s",aopGet(AOP(handle),1,FALSE,TRUE,FALSE)); + emitcode ("mov","r2,%s", + aopGet(AOP(handle),0,FALSE,TRUE,DP2_RESULT_REG)); + emitcode ("mov","r3,%s", + aopGet(AOP(handle),1,FALSE,TRUE,DP2_RESULT_REG)); } freeAsmop (handle, NULL, ic, FALSE); /* put pointer in DPTR */ aopOp (pp,ic,FALSE,FALSE); if (AOP_TYPE(pp) == AOP_IMMD) { - emitcode ("mov", "dptr,%s", aopGet (AOP (pp), 0, TRUE, FALSE, FALSE)); + emitcode ("mov", "dptr,%s", + aopGet (AOP (pp), 0, TRUE, FALSE, NULL)); } else if (AOP_TYPE(pp) != AOP_STR) { /* not already in dptr */ - emitcode ("mov","dpl,%s",aopGet(AOP(pp),0,FALSE,FALSE,FALSE)); - emitcode ("mov","dph,%s",aopGet(AOP(pp),1,FALSE,FALSE,FALSE)); - emitcode ("mov","dpx,%s",aopGet(AOP(pp),2,FALSE,FALSE,FALSE)); + emitcode ("mov","dpl,%s",aopGet(AOP(pp),0,FALSE,FALSE,NULL)); + emitcode ("mov","dph,%s",aopGet(AOP(pp),1,FALSE,FALSE,NULL)); + emitcode ("mov","dpx,%s",aopGet(AOP(pp),2,FALSE,FALSE,NULL)); } freeAsmop (handle, NULL, ic, FALSE); @@ -12233,12 +12910,16 @@ static void genSystemRTCRegisters(iCode *ic,int nparms, operand **parms, aopOp (pp,ic,FALSE,FALSE); if (AOP_TYPE (pp) == AOP_IMMD) { emitcode ("mov","dps,#1"); - emitcode ("mov", "dptr,%s", aopGet (AOP (pp), 0, TRUE, FALSE, FALSE)); + emitcode ("mov", "dptr,%s", + aopGet (AOP (pp), 0, TRUE, FALSE, NULL)); emitcode ("mov","dps,#0"); } else { - emitcode ("mov","dpl1,%s",aopGet(AOP(pp),0,FALSE,FALSE,FALSE)); - emitcode ("mov","dph1,%s",aopGet(AOP(pp),1,FALSE,FALSE,FALSE)); - emitcode ("mov","dpx1,%s",aopGet(AOP(pp),2,FALSE,FALSE,FALSE)); + emitcode ("mov","dpl1,%s", + aopGet(AOP(pp),0,FALSE,FALSE,DP2_RESULT_REG)); + emitcode ("mov","dph1,%s", + aopGet(AOP(pp),1,FALSE,FALSE,DP2_RESULT_REG)); + emitcode ("mov","dpx1,%s", + aopGet(AOP(pp),2,FALSE,FALSE,DP2_RESULT_REG)); } freeAsmop (pp, NULL, ic, FALSE); @@ -12265,26 +12946,35 @@ static void genSystemThreadSleep(iCode *ic,int nparms, operand **parms, char *na aopOp(to,ic,FALSE,FALSE); if (aopHasRegs(AOP(to),R2_IDX,R3_IDX) || aopHasRegs(AOP(to),R0_IDX,R1_IDX) ) { - emitcode ("push","%s",aopGet(AOP(to),0,FALSE,TRUE,FALSE)); - emitcode ("push","%s",aopGet(AOP(to),1,FALSE,TRUE,FALSE)); - emitcode ("push","%s",aopGet(AOP(to),2,FALSE,TRUE,FALSE)); - emitcode ("push","%s",aopGet(AOP(to),3,FALSE,TRUE,FALSE)); + emitcode ("push","%s", + aopGet(AOP(to),0,FALSE,TRUE,DP2_RESULT_REG)); + emitcode ("push","%s", + aopGet(AOP(to),1,FALSE,TRUE,DP2_RESULT_REG)); + emitcode ("push","%s", + aopGet(AOP(to),2,FALSE,TRUE,DP2_RESULT_REG)); + emitcode ("push","%s", + aopGet(AOP(to),3,FALSE,TRUE,DP2_RESULT_REG)); emitcode ("pop","ar3"); emitcode ("pop","ar2"); emitcode ("pop","ar1"); emitcode ("pop","ar0"); } else { - emitcode ("mov","r0,%s",aopGet(AOP(to),0,FALSE,TRUE,FALSE)); - emitcode ("mov","r1,%s",aopGet(AOP(to),1,FALSE,TRUE,FALSE)); - emitcode ("mov","r2,%s",aopGet(AOP(to),2,FALSE,TRUE,FALSE)); - emitcode ("mov","r3,%s",aopGet(AOP(to),3,FALSE,TRUE,FALSE)); + emitcode ("mov","r0,%s", + aopGet(AOP(to),0,FALSE,TRUE,DP2_RESULT_REG)); + emitcode ("mov","r1,%s", + aopGet(AOP(to),1,FALSE,TRUE,DP2_RESULT_REG)); + emitcode ("mov","r2,%s", + aopGet(AOP(to),2,FALSE,TRUE,DP2_RESULT_REG)); + emitcode ("mov","r3,%s", + aopGet(AOP(to),3,FALSE,TRUE,DP2_RESULT_REG)); } freeAsmop (to, NULL, ic, FALSE); /* suspend in acc */ s = parms[1]; aopOp(s,ic,FALSE,FALSE); - emitcode ("mov","a,%s",aopGet(AOP(s),0,FALSE,TRUE,FALSE)); + emitcode ("mov","a,%s", + aopGet(AOP(s),0,FALSE,TRUE,NULL)); freeAsmop (s, NULL, ic, FALSE); /* make the call */ @@ -12311,12 +13001,14 @@ static void genSystemThreadResume(iCode *ic,int nparms, operand **parms) /* PID in R0 */ aopOp(pid,ic,FALSE,FALSE); - emitcode ("mov","r0,%s",aopGet(AOP(pid),0,FALSE,TRUE,FALSE)); + emitcode ("mov","r0,%s", + aopGet(AOP(pid),0,FALSE,TRUE,DP2_RESULT_REG)); freeAsmop (pid, NULL, ic, FALSE); /* tid into ACC */ aopOp(tid,ic,FALSE,FALSE); - emitcode ("mov","a,%s",aopGet(AOP(tid),0,FALSE,TRUE,FALSE)); + emitcode ("mov","a,%s", + aopGet(AOP(tid),0,FALSE,TRUE,DP2_RESULT_REG)); freeAsmop (tid, NULL, ic, FALSE); emitcode ("lcall","System_ThreadResume"); @@ -12350,7 +13042,8 @@ static void genSystemProcessResume(iCode *ic,int nparms, operand **parms) /* pid into ACC */ aopOp(pid,ic,FALSE,FALSE); - emitcode ("mov","a,%s",aopGet(AOP(pid),0,FALSE,TRUE,FALSE)); + emitcode ("mov","a,%s", + aopGet(AOP(pid),0,FALSE,TRUE,DP2_RESULT_REG)); freeAsmop (pid, NULL, ic, FALSE); emitcode ("lcall","System_ProcessResume"); @@ -12384,11 +13077,15 @@ static void genSystemPoll(iCode *ic,int nparms, operand **parms,char *name) fp = parms[0]; aopOp (fp,ic,FALSE,FALSE); if (AOP_TYPE (fp) == AOP_IMMD) { - emitcode ("mov", "dptr,%s", aopGet (AOP (fp), 0, TRUE, FALSE, FALSE)); + emitcode ("mov", "dptr,%s", + aopGet (AOP (fp), 0, TRUE, FALSE, DP2_RESULT_REG)); } else if (AOP_TYPE(fp) != AOP_STR) { /* not already in dptr */ - emitcode ("mov","dpl,%s",aopGet(AOP(fp),0,FALSE,FALSE,FALSE)); - emitcode ("mov","dph,%s",aopGet(AOP(fp),1,FALSE,FALSE,FALSE)); - emitcode ("mov","dpx,%s",aopGet(AOP(fp),2,FALSE,FALSE,FALSE)); + emitcode ("mov","dpl,%s", + aopGet(AOP(fp),0,FALSE,FALSE,DP2_RESULT_REG)); + emitcode ("mov","dph,%s", + aopGet(AOP(fp),1,FALSE,FALSE,DP2_RESULT_REG)); + emitcode ("mov","dpx,%s", + aopGet(AOP(fp),2,FALSE,FALSE,DP2_RESULT_REG)); } freeAsmop (fp, NULL, ic, FALSE); @@ -12425,6 +13122,127 @@ static void genSystemGetCurrentID(iCode *ic,int nparms, operand **parms,char *na } } +/*-----------------------------------------------------------------*/ +/* genDummyRead - generate code for dummy read of volatiles */ +/*-----------------------------------------------------------------*/ +static void +genDummyRead (iCode * ic) +{ + operand *op; + int size, offset; + + D(emitcode("; genDummyRead","")); + + op = IC_RIGHT (ic); + if (op && IS_SYMOP (op)) + { + aopOp (op, ic, FALSE, FALSE); + + /* if the result is a bit */ + if (AOP_TYPE (op) == AOP_CRY) + emitcode ("mov", "c,%s", AOP (op)->aopu.aop_dir); + else + { + /* bit variables done */ + /* general case */ + size = AOP_SIZE (op); + offset = 0; + while (size--) + { + MOVA (aopGet (AOP (op), offset, FALSE, FALSE, FALSE)); + offset++; + } + } + + freeAsmop (op, NULL, ic, TRUE); + } + + op = IC_LEFT (ic); + if (op && IS_SYMOP (op)) + { + aopOp (op, ic, FALSE, FALSE); + + /* if the result is a bit */ + if (AOP_TYPE (op) == AOP_CRY) + emitcode ("mov", "c,%s", AOP (op)->aopu.aop_dir); + else + { + /* bit variables done */ + /* general case */ + size = AOP_SIZE (op); + offset = 0; + while (size--) + { + MOVA (aopGet (AOP (op), offset, FALSE, FALSE, FALSE)); + offset++; + } + } + + freeAsmop (op, NULL, ic, TRUE); + } + +} + +/*-----------------------------------------------------------------*/ +/* genCritical - generate code for start of a critical sequence */ +/*-----------------------------------------------------------------*/ +static void +genCritical (iCode *ic) +{ + symbol *tlbl = newiTempLabel (NULL); + + D(emitcode("; genCritical","")); + + if (IC_RESULT (ic)) + aopOp (IC_RESULT (ic), ic, TRUE, FALSE); + + emitcode ("setb", "c"); + emitcode ("jbc", "ea,%05d$", (tlbl->key + 100)); /* atomic test & clear */ + emitcode ("clr", "c"); + emitcode ("", "%05d$:", (tlbl->key + 100)); + + if (IC_RESULT (ic)) + outBitC (IC_RESULT (ic)); /* save old ea in an operand */ + else + emitcode ("push", "psw"); /* save old ea via c in psw on top of stack*/ + + if (IC_RESULT (ic)) + freeAsmop (IC_RESULT (ic), NULL, ic, TRUE); +} + +/*-----------------------------------------------------------------*/ +/* genEndCritical - generate code for end of a critical sequence */ +/*-----------------------------------------------------------------*/ +static void +genEndCritical (iCode *ic) +{ + D(emitcode("; genEndCritical","")); + + if (IC_RIGHT (ic)) + { + aopOp (IC_RIGHT (ic), ic, FALSE, FALSE); + if (AOP_TYPE (IC_RIGHT (ic)) == AOP_CRY) + { + emitcode ("mov", "c,%s", IC_RIGHT (ic)->aop->aopu.aop_dir); + emitcode ("mov", "ea,c"); + } + else + { + MOVA (aopGet (AOP (IC_RIGHT (ic)), 0, FALSE, FALSE, FALSE)); + emitcode ("rrc", "a"); + emitcode ("mov", "ea,c"); + } + freeAsmop (IC_RIGHT (ic), NULL, ic, TRUE); + } + else + { + emitcode ("pop", "psw"); /* restore ea via c in psw on top of stack */ + emitcode ("mov", "ea,c"); + } +} + + + /*-----------------------------------------------------------------*/ /* genBuiltIn - calls the appropriate function to generating code */ /* for a built in function */ @@ -12559,13 +13377,13 @@ gen390Code (iCode * lic) } #if 1 /* print the allocation information */ - if (allocInfo) + if (allocInfo && currFunc) printAllocInfo (currFunc, codeOutFile); #endif /* if debug information required */ if (options.debug && currFunc) { - cdbSymbol (currFunc, cdbFile, FALSE, TRUE); + debugFile->writeFunction(currFunc); _G.debugLine = 1; if (IS_STATIC (currFunc->etype)) emitcode ("", "F%s$%s$0$0 ==.", moduleName, currFunc->name); @@ -12583,6 +13401,8 @@ gen390Code (iCode * lic) for (ic = lic; ic; ic = ic->next) { + _G.current_iCode = ic; + if (ic->lineno && cln != ic->lineno) { if (options.debug) @@ -12794,9 +13614,27 @@ gen390Code (iCode * lic) else addSet (&_G.sendSet, ic); break; + case DUMMY_READ_VOLATILE: + genDummyRead (ic); + break; + + case CRITICAL: + genCritical (ic); + break; + + case ENDCRITICAL: + genEndCritical (ic); + break; + + case SWAP: + genSwap (ic); + break; + +#if 0 // obsolete, and buggy for != xdata case ARRAYINIT: genArrayInit(ic); break; +#endif default: ic = ic;