X-Git-Url: https://git.gag.com/?a=blobdiff_plain;f=src%2Fmcs51%2Fgen.c;h=9375087a431f1cae78da365a154314d34869efed;hb=b1a10c8ec5142594ec5698fa241d7433873ce710;hp=9db691c3917305b244b58a6d05f6645a4393de48;hpb=05e1b5ab697301a5fc525957cee1a9c7837f99c4;p=fw%2Fsdcc diff --git a/src/mcs51/gen.c b/src/mcs51/gen.c index 9db691c3..9375087a 100644 --- a/src/mcs51/gen.c +++ b/src/mcs51/gen.c @@ -1671,6 +1671,7 @@ aopPut (operand * result, const char *s, int offset) case AOP_CRY: // destination is carry for return-use-only d = (IS_OP_RUONLY (result)) ? "c" : aop->aopu.aop_dir; + // source is no literal and not in carry if ((s != zero) && (s != one) && strcmp (s, "c")) { @@ -1786,15 +1787,13 @@ reAdjustPreg (asmop * aop) } /*-----------------------------------------------------------------*/ -/* opIsGptr: returns non-zero if the passed operand is */ -/* a generic pointer type. */ +/* opIsGptr: returns non-zero if the passed operand is */ +/* a generic pointer type. */ /*-----------------------------------------------------------------*/ static int opIsGptr (operand * op) { - sym_link *type = operandType (op); - - if ((AOP_SIZE (op) == GPTRSIZE) && IS_GENPTR (type)) + if (op && IS_GENPTR (operandType (op)) && (AOP_SIZE (op) == GPTRSIZE)) { return 1; } @@ -1807,8 +1806,8 @@ opIsGptr (operand * op) static int getDataSize (operand * op) { - int size; - size = AOP_SIZE (op); + int size = AOP_SIZE (op); + if (size == GPTRSIZE) { sym_link *type = operandType (op); @@ -2173,7 +2172,7 @@ genUminus (iCode * ic) if (offset == 0) SETC; emitcode ("cpl", "a"); - emitcode ("addc", "a,#0"); + emitcode ("addc", "a,#0x00"); } else { @@ -2277,7 +2276,7 @@ saveRegisters (iCode * lic) } emitcode ("mov", "r0,%s", spname); MOVA ("r0"); - emitcode ("add", "a,#%d", count); + emitcode ("add", "a,#0x%02x", count); emitcode ("mov", "%s,a", spname); for (i = 0; i < mcs51_nRegs; i++) { @@ -2523,7 +2522,7 @@ genXpush (iCode * ic) // allocate space first emitcode ("mov", "%s,%s", r->name, spname); MOVA (r->name); - emitcode ("add", "a,#%d", size); + emitcode ("add", "a,#0x%02x", size); emitcode ("mov", "%s,a", spname); while (size--) @@ -2640,6 +2639,21 @@ genIpop (iCode * ic) freeAsmop (IC_LEFT (ic), NULL, ic, TRUE); } +/*-----------------------------------------------------------------*/ +/* popForBranch - recover the spilt registers for a branch */ +/*-----------------------------------------------------------------*/ +static void +popForBranch (iCode * ic, bool markGenerated) +{ + while (ic && ic->op == IPOP) + { + genIpop (ic); + if (markGenerated) + ic->generated = 1; /* mark the icode as generated */ + ic = ic->next; + } +} + /*-----------------------------------------------------------------*/ /* saveRBank - saves an entire register bank on the stack */ /*-----------------------------------------------------------------*/ @@ -2666,7 +2680,7 @@ saveRBank (int bank, iCode * ic, bool pushPsw) // allocate space first emitcode ("mov", "%s,%s", r->name, spname); MOVA (r->name); - emitcode ("add", "a,#%d", count); + emitcode ("add", "a,#0x%02x", count); emitcode ("mov", "%s,a", spname); } @@ -2817,9 +2831,13 @@ static void genSend(set *sendSet) } } - if (bit_count) + if (options.useXstack || bit_count) { saveRegisters (setFirstItem (sendSet)); + } + + if (bit_count) + { emitcode ("mov", "bits,b"); } @@ -2924,8 +2942,7 @@ genCall (iCode * ic) if (swapBanks) { - emitcode ("mov", "psw,#0x%02x", - ((FUNC_REGBANK(dtype)) << 3) & 0xff); + emitcode ("mov", "psw,#0x%02x", ((FUNC_REGBANK(dtype)) << 3) & 0xff); } /* make the call */ @@ -3430,10 +3447,12 @@ genFunction (iCode * ic) /* this function has a function call. We cannot determine register usage so we will have to push the entire bank */ - saveRBank (0, ic, FALSE); - if (options.parms_in_bank1) { - for (i=0; i < 8 ; i++ ) { - emitcode ("push","%s",rb1regs[i]); + saveRBank (0, ic, FALSE); + if (options.parms_in_bank1) + { + for (i=0; i < 8 ; i++ ) + { + emitcode ("push","%s",rb1regs[i]); } } } @@ -3854,18 +3873,20 @@ genEndFunction (iCode * ic) } else { - if (options.parms_in_bank1) { - for (i = 7 ; i >= 0 ; i-- ) { + if (options.parms_in_bank1) + { + for (i = 7 ; i >= 0 ; i-- ) + { emitcode ("pop","%s",rb1regs[i]); - } - } + } + } /* this function has a function call. We cannot determine register usage so we will have to pop the entire bank */ unsaveRBank (0, ic, FALSE); } } - else + else { /* This ISR uses a non-zero bank. * @@ -4201,6 +4222,7 @@ genPlusIncr (iCode * ic) symbol *tlbl; int emitTlbl; int labelRange; + char *l; /* If the next instruction is a goto and the goto target * is < 10 instructions previous to this, we can generate @@ -4219,49 +4241,58 @@ genPlusIncr (iCode * ic) tlbl = newiTempLabel (NULL); emitTlbl = 1; } - emitcode ("inc", "%s", aopGet (IC_RESULT (ic), LSB, FALSE, FALSE)); + l = aopGet (IC_RESULT (ic), LSB, FALSE, FALSE); + emitcode ("inc", "%s", l); if (AOP_TYPE (IC_RESULT (ic)) == AOP_REG || IS_AOP_PREG (IC_RESULT (ic))) - emitcode ("cjne", "%s,#0x00,%05d$", - aopGet (IC_RESULT (ic), LSB, FALSE, FALSE), - tlbl->key + 100); + { + emitcode ("cjne", "%s,#0x00,%05d$", l, tlbl->key + 100); + } else { emitcode ("clr", "a"); - emitcode ("cjne", "a,%s,%05d$", - aopGet (IC_RESULT (ic), LSB, FALSE, FALSE), - tlbl->key + 100); + emitcode ("cjne", "a,%s,%05d$", l, tlbl->key + 100); } - emitcode ("inc", "%s", aopGet (IC_RESULT (ic), MSB16, FALSE, FALSE)); + l = aopGet (IC_RESULT (ic), MSB16, FALSE, FALSE); + emitcode ("inc", "%s", l); if (size > 2) { - if (AOP_TYPE (IC_RESULT (ic)) == AOP_REG || - IS_AOP_PREG (IC_RESULT (ic))) - emitcode ("cjne", "%s,#0x00,%05d$", - aopGet (IC_RESULT (ic), MSB16, FALSE, FALSE), - tlbl->key + 100); + 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,#0x00,%05d$", l, tlbl->key + 100); + } else - emitcode ("cjne", "a,%s,%05d$", - aopGet (IC_RESULT (ic), MSB16, FALSE, FALSE), - tlbl->key + 100); + { + emitcode ("cjne", "a,%s,%05d$", l, tlbl->key + 100); + } - emitcode ("inc", "%s", aopGet (IC_RESULT (ic), MSB24, FALSE, FALSE)); + l = aopGet (IC_RESULT (ic), MSB24, FALSE, FALSE); + emitcode ("inc", "%s", l); } if (size > 3) { - if (AOP_TYPE (IC_RESULT (ic)) == AOP_REG || - IS_AOP_PREG (IC_RESULT (ic))) - emitcode ("cjne", "%s,#0x00,%05d$", - aopGet (IC_RESULT (ic), MSB24, FALSE, FALSE), - tlbl->key + 100); + 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,#0x00,%05d$", l, tlbl->key + 100); + } else { - emitcode ("cjne", "a,%s,%05d$", - aopGet (IC_RESULT (ic), MSB24, FALSE, FALSE), - tlbl->key + 100); + emitcode ("cjne", "a,%s,%05d$", l, tlbl->key + 100); } - emitcode ("inc", "%s", aopGet (IC_RESULT (ic), MSB32, FALSE, FALSE)); + + l = aopGet (IC_RESULT (ic), MSB32, FALSE, FALSE); + emitcode ("inc", "%s", l); } if (emitTlbl) @@ -4427,34 +4458,58 @@ adjustArithmeticResult (iCode * ic) static void adjustArithmeticResult (iCode * ic) { - if (opIsGptr (IC_RESULT (ic)) && - opIsGptr (IC_LEFT (ic)) && - !sameRegs (AOP (IC_RESULT (ic)), AOP (IC_LEFT (ic)))) + if (opIsGptr (IC_RESULT (ic))) { - aopPut (IC_RESULT (ic), - aopGet (IC_LEFT (ic), GPTRSIZE - 1, FALSE, FALSE), - GPTRSIZE - 1); - } + char buffer[10]; - if (opIsGptr (IC_RESULT (ic)) && - opIsGptr (IC_RIGHT (ic)) && - !sameRegs (AOP (IC_RESULT (ic)), AOP (IC_RIGHT (ic)))) - { - aopPut (IC_RESULT (ic), - aopGet (IC_RIGHT (ic), GPTRSIZE - 1, FALSE, FALSE), - GPTRSIZE - 1); - } + if (opIsGptr (IC_LEFT (ic))) + { + if (!sameRegs (AOP (IC_RESULT (ic)), AOP (IC_LEFT (ic)))) + { + aopPut (IC_RESULT (ic), + aopGet (IC_LEFT (ic), GPTRSIZE - 1, FALSE, FALSE), + GPTRSIZE - 1); + } + return; + } - if (opIsGptr (IC_RESULT (ic)) && - AOP_SIZE (IC_LEFT (ic)) < GPTRSIZE && - AOP_SIZE (IC_RIGHT (ic)) < GPTRSIZE && - !sameRegs (AOP (IC_RESULT (ic)), AOP (IC_LEFT (ic))) && - !sameRegs (AOP (IC_RESULT (ic)), AOP (IC_RIGHT (ic)))) - { - char buffer[5]; - SNPRINTF (buffer, sizeof(buffer), - "#%d", pointerTypeToGPByte (pointerCode (getSpec (operandType (IC_LEFT (ic)))), NULL, NULL)); - aopPut (IC_RESULT (ic), buffer, GPTRSIZE - 1); + if (opIsGptr (IC_RIGHT (ic))) + { + if (!sameRegs (AOP (IC_RESULT (ic)), AOP (IC_RIGHT (ic)))) + { + aopPut (IC_RESULT (ic), + aopGet (IC_RIGHT (ic), GPTRSIZE - 1, FALSE, FALSE), + GPTRSIZE - 1); + } + return; + } + + if (IC_LEFT (ic) && AOP_SIZE (IC_LEFT (ic)) < GPTRSIZE && + IC_RIGHT (ic) && AOP_SIZE (IC_RIGHT (ic)) < GPTRSIZE && + !sameRegs (AOP (IC_RESULT (ic)), AOP (IC_LEFT (ic))) && + !sameRegs (AOP (IC_RESULT (ic)), AOP (IC_RIGHT (ic)))) + { + SNPRINTF (buffer, sizeof(buffer), + "#0x%02x", pointerTypeToGPByte (pointerCode (getSpec (operandType (IC_LEFT (ic)))), NULL, NULL)); + aopPut (IC_RESULT (ic), buffer, GPTRSIZE - 1); + return; + } + if (IC_LEFT (ic) && AOP_SIZE (IC_LEFT (ic)) < GPTRSIZE && + !sameRegs (AOP (IC_RESULT (ic)), AOP (IC_LEFT (ic)))) + { + SNPRINTF (buffer, sizeof(buffer), + "#0x%02x", pointerTypeToGPByte (pointerCode (getSpec (operandType (IC_LEFT (ic)))), NULL, NULL)); + aopPut (IC_RESULT (ic), buffer, GPTRSIZE - 1); + return; + } + if (IC_RIGHT (ic) && AOP_SIZE (IC_RIGHT (ic)) < GPTRSIZE && + !sameRegs (AOP (IC_RESULT (ic)), AOP (IC_RIGHT (ic)))) + { + SNPRINTF (buffer, sizeof(buffer), + "#0x%02x", pointerTypeToGPByte (pointerCode (getSpec (operandType (IC_RIGHT (ic)))), NULL, NULL)); + aopPut (IC_RESULT (ic), buffer, GPTRSIZE - 1); + return; + } } } #endif @@ -4667,8 +4722,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 <= 10 instructions previous to this, we can generate @@ -4688,49 +4744,56 @@ genMinusDec (iCode * ic) emitTlbl = 1; } - emitcode ("dec", "%s", aopGet (IC_RESULT (ic), LSB, FALSE, FALSE)); + l = aopGet (IC_RESULT (ic), LSB, FALSE, FALSE); + emitcode ("dec", "%s", l); + if (AOP_TYPE (IC_RESULT (ic)) == AOP_REG || IS_AOP_PREG (IC_RESULT (ic))) - emitcode ("cjne", "%s,#0xff,%05d$" - ,aopGet (IC_RESULT (ic), LSB, FALSE, FALSE) - ,tlbl->key + 100); + { + emitcode ("cjne", "%s,#0xff,%05d$", l, tlbl->key + 100); + } else { emitcode ("mov", "a,#0xff"); - emitcode ("cjne", "a,%s,%05d$" - ,aopGet (IC_RESULT (ic), LSB, FALSE, FALSE) - ,tlbl->key + 100); + emitcode ("cjne", "a,%s,%05d$", l, tlbl->key + 100); } - emitcode ("dec", "%s", aopGet (IC_RESULT (ic), MSB16, FALSE, FALSE)); + l = aopGet (IC_RESULT (ic), MSB16, FALSE, FALSE); + emitcode ("dec", "%s", l); if (size > 2) { - if (AOP_TYPE (IC_RESULT (ic)) == AOP_REG || - IS_AOP_PREG (IC_RESULT (ic))) - emitcode ("cjne", "%s,#0xff,%05d$" - ,aopGet (IC_RESULT (ic), MSB16, FALSE, FALSE) - ,tlbl->key + 100); + 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,#0xff,%05d$", l, tlbl->key + 100); + } else { - emitcode ("cjne", "a,%s,%05d$" - ,aopGet (IC_RESULT (ic), MSB16, FALSE, FALSE) - ,tlbl->key + 100); + emitcode ("cjne", "a,%s,%05d$", l, tlbl->key + 100); } - emitcode ("dec", "%s", aopGet (IC_RESULT (ic), MSB24, FALSE, FALSE)); + l = aopGet (IC_RESULT (ic), MSB24, FALSE, FALSE); + emitcode ("dec", "%s", l); } if (size > 3) { - if (AOP_TYPE (IC_RESULT (ic)) == AOP_REG || - IS_AOP_PREG (IC_RESULT (ic))) - emitcode ("cjne", "%s,#0xff,%05d$" - ,aopGet (IC_RESULT (ic), MSB24, FALSE, FALSE) - ,tlbl->key + 100); + 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,#0xff,%05d$", l, tlbl->key + 100); + } else { - emitcode ("cjne", "a,%s,%05d$" - ,aopGet (IC_RESULT (ic), MSB24, FALSE, FALSE) - ,tlbl->key + 100); + emitcode ("cjne", "a,%s,%05d$", l, tlbl->key + 100); } - emitcode ("dec", "%s", aopGet (IC_RESULT (ic), MSB32, FALSE, FALSE)); + l = aopGet (IC_RESULT (ic), MSB32, FALSE, FALSE); + emitcode ("dec", "%s", l); } if (emitTlbl) { @@ -5154,7 +5217,7 @@ genMultOneByte (operand * left, lbl = newiTempLabel (NULL); emitcode ("jnb", "acc.7,%05d$", (lbl->key + 100)); emitcode ("cpl", "F0"); /* complement sign flag */ - emitcode ("cpl", "a"); /* 2's complement */ + emitcode ("cpl", "a"); /* 2's complement */ emitcode ("inc", "a"); emitLabel (lbl); } @@ -5172,10 +5235,10 @@ genMultOneByte (operand * left, emitcode ("inc", "a"); /* inc doesn't set carry flag */ else { - emitcode ("add", "a,#1"); /* this sets carry flag */ + emitcode ("add", "a,#0x01"); /* this sets carry flag */ emitcode ("xch", "a,b"); emitcode ("cpl", "a"); /* msb 2's complement */ - emitcode ("addc", "a,#0"); + emitcode ("addc", "a,#0x00"); emitcode ("xch", "a,b"); } emitLabel (lbl); @@ -5458,7 +5521,7 @@ genDivOneByte (operand * left, } else /* compiletimeSign */ { - if (aopPutUsesAcc (result, "#0xFF", offset)) + if (aopPutUsesAcc (result, "#0xff", offset)) { emitcode ("push", "acc"); pushedA = TRUE; @@ -5730,7 +5793,7 @@ genModOneByte (operand * left, /* msb is 0x00 or 0xff depending on the sign */ if (runtimeSign) { - emitcode ("mov", "c,F0"); + emitcode ("mov", "c,F0"); emitcode ("subb", "a,acc"); while (size--) aopPut (result, "a", offset++); @@ -5797,12 +5860,15 @@ release: /* genIfxJump :- will create a jump depending on the ifx */ /*-----------------------------------------------------------------*/ static void -genIfxJump (iCode * ic, char *jval, operand *left, operand *right, operand *result) +genIfxJump (iCode * ic, char *jval, operand *left, operand *right, operand *result, iCode *popIc) { symbol *jlbl; symbol *tlbl = newiTempLabel (NULL); char *inst; + /* if there is something to be popped then do it first */ + popForBranch (popIc, TRUE); + D (emitcode (";", "genIfxJump")); /* if true label then we jump if condition @@ -5889,7 +5955,7 @@ genCmp (operand * left, operand * right, MOVA (aopGet (left, AOP_SIZE (left) - 1, FALSE, FALSE)); if (!(AOP_TYPE (result) == AOP_CRY && AOP_SIZE (result)) && ifx) { - genIfxJump (ifx, "acc.7", left, right, result); + genIfxJump (ifx, "acc.7", left, right, result, ic->next); freeAsmop (right, NULL, ic, TRUE); freeAsmop (left, NULL, ic, TRUE); @@ -5981,7 +6047,7 @@ release: code a little differently */ if (ifx) { - genIfxJump (ifx, "c", NULL, NULL, result); + genIfxJump (ifx, "c", NULL, NULL, result, ic->next); } else { @@ -6164,6 +6230,7 @@ genCmpEq (iCode * ic, iCode * ifx) { bool swappedLR = FALSE; operand *left, *right, *result; + iCode * popIc = ic->next; D (emitcode (";", "genCmpEq")); @@ -6225,6 +6292,7 @@ genCmpEq (iCode * ic, iCode * ifx) freeForBranchAsmop (result); freeForBranchAsmop (right); freeForBranchAsmop (left); + popForBranch (popIc, FALSE); emitcode ("ljmp", "%05d$", IC_TRUE (ifx)->key + 100); } else @@ -6233,6 +6301,7 @@ genCmpEq (iCode * ic, iCode * ifx) freeForBranchAsmop (result); freeForBranchAsmop (right); freeForBranchAsmop (left); + popForBranch (popIc, FALSE); emitcode ("ljmp", "%05d$", IC_FALSE (ifx)->key + 100); } emitLabel (tlbl); @@ -6246,6 +6315,7 @@ genCmpEq (iCode * ic, iCode * ifx) freeForBranchAsmop (result); freeForBranchAsmop (right); freeForBranchAsmop (left); + popForBranch (popIc, FALSE); emitcode ("ljmp", "%05d$", IC_TRUE (ifx)->key + 100); emitLabel (tlbl); } @@ -6257,6 +6327,7 @@ genCmpEq (iCode * ic, iCode * ifx) freeForBranchAsmop (result); freeForBranchAsmop (right); freeForBranchAsmop (left); + popForBranch (popIc, FALSE); emitcode ("ljmp", "%05d$", IC_FALSE (ifx)->key + 100); emitLabel (lbl); } @@ -6304,7 +6375,7 @@ genCmpEq (iCode * ic, iCode * ifx) } if (ifx) { - genIfxJump (ifx, "c", left, right, result); + genIfxJump (ifx, "c", left, right, result, popIc); goto release; } /* if the result is used in an arithmetic operation @@ -6322,7 +6393,7 @@ genCmpEq (iCode * ic, iCode * ifx) gencjne (left, right, newiTempLabel (NULL), FALSE); if (ifx) { - genIfxJump (ifx, "a", left, right, result); + genIfxJump (ifx, "a", left, right, result, popIc); goto release; } /* if the result is used in an arithmetic operation @@ -6352,18 +6423,21 @@ release: static iCode * ifxForOp (operand * op, iCode * ic) { + iCode *ifxIc; + /* if true symbol then needs to be assigned */ if (IS_TRUE_SYMOP (op)) return NULL; /* if this has register type condition and + while skipping ipop's (see bug 1509084), the next instruction is ifx with the same operand and live to of the operand is upto the ifx only then */ - if (ic->next && - ic->next->op == IFX && - IC_COND (ic->next)->key == op->key && - OP_SYMBOL (op)->liveTo <= ic->next->seq) - return ic->next; + for (ifxIc = ic->next; ifxIc && ifxIc->op == IPOP; ifxIc = ifxIc->next); + if (ifxIc && ifxIc->op == IFX && + IC_COND (ifxIc)->key == op->key && + OP_SYMBOL (op)->liveTo <= ifxIc->seq) + return ifxIc; return NULL; } @@ -6386,22 +6460,25 @@ hasInc (operand *op, iCode *ic, int osize) if (IS_AGGREGATE(type->next)) return NULL; if (osize != (isize = getSize(type->next))) return NULL; - while (lic) { - /* if operand of the form op = op + */ - if (lic->op == '+' && isOperandEqual(IC_LEFT(lic),op) && - isOperandEqual(IC_RESULT(lic),op) && - isOperandLiteral(IC_RIGHT(lic)) && - operandLitValue(IC_RIGHT(lic)) == isize) { - return lic; - } - /* if the operand used or deffed */ - if (bitVectBitValue(OP_USES(op),lic->key) || lic->defKey == op->key) { - return NULL; + while (lic) + { + /* if operand of the form op = op + */ + if (lic->op == '+' && isOperandEqual(IC_LEFT(lic),op) && + isOperandEqual(IC_RESULT(lic),op) && + isOperandLiteral(IC_RIGHT(lic)) && + operandLitValue(IC_RIGHT(lic)) == isize) + { + return lic; + } + /* if the operand used or deffed */ + if (bitVectBitValue(OP_USES(op),lic->key) || lic->defKey == op->key) + { + return NULL; + } + /* if GOTO or IFX */ + if (lic->op == IFX || lic->op == GOTO || lic->op == LABEL) break; + lic = lic->next; } - /* if GOTO or IFX */ - if (lic->op == IFX || lic->op == GOTO || lic->op == LABEL) break; - lic = lic->next; - } return NULL; } @@ -6678,7 +6755,7 @@ genAnd (iCode * ic, iCode * ifx) outBitC (result); // if(bit & ...) else if ((AOP_TYPE (result) == AOP_CRY) && ifx) - genIfxJump (ifx, "c", left, right, result); + genIfxJump (ifx, "c", left, right, result, ic->next); goto release; } @@ -6714,7 +6791,7 @@ genAnd (iCode * ic, iCode * ifx) { SNPRINTF (buffer, sizeof(buffer), "acc.%d", posbit & 0x07); - genIfxJump (ifx, buffer, left, right, result); + genIfxJump (ifx, buffer, left, right, result, ic->next); } else {// what is this case? just found it in ds390/gen.c @@ -6880,7 +6957,7 @@ genAnd (iCode * ic, iCode * ifx) { MOVA (aopGet (left, offset, FALSE, FALSE)); emitcode ("anl", "a,%s", aopGet (right, offset, FALSE, FALSE)); - } + } else { MOVA (aopGet (right, offset, FALSE, FALSE)); @@ -7118,7 +7195,7 @@ genOr (iCode * ic, iCode * ifx) outBitC (result); // if(bit | ...) else if ((AOP_TYPE (result) == AOP_CRY) && ifx) - genIfxJump (ifx, "c", left, right, result); + genIfxJump (ifx, "c", left, right, result, ic->next); goto release; } @@ -7133,7 +7210,7 @@ genOr (iCode * ic, iCode * ifx) // result = 1 if (size) emitcode ("setb", "%s", AOP (result)->aopu.aop_dir); - else + else if(ifx) continueIfTrue (ifx); goto release; } @@ -7151,8 +7228,8 @@ genOr (iCode * ic, iCode * ifx) emitLabel (tlbl); } else - { - genIfxJump (ifx, "a", left, right, result); + { /* FIXME, thats pretty fishy, check for ifx!=0, testcase .. */ + genIfxJump (ifx, "a", left, right, result, ic->next); goto release; } } @@ -7178,7 +7255,7 @@ genOr (iCode * ic, iCode * ifx) } else if (bytelit == 0x0FF) { - aopPut (result, "#0xFF", offset); + aopPut (result, "#0xff", offset); } else if (IS_AOP_PREG (left)) { @@ -7319,7 +7396,7 @@ genOr (iCode * ic, iCode * ifx) /* dummy read of volatile operand */ if (isOperandVolatile (left, FALSE)) MOVA (aopGet (left, offset, FALSE, FALSE)); - aopPut (result, "#0xFF", offset); + aopPut (result, "#0xff", offset); continue; } } @@ -7512,7 +7589,7 @@ genXor (iCode * ic, iCode * ifx) outBitC (result); // if(bit ^ ...) else if ((AOP_TYPE (result) == AOP_CRY) && ifx) - genIfxJump (ifx, "c", left, right, result); + genIfxJump (ifx, "c", left, right, result, ic->next); goto release; } @@ -7783,8 +7860,8 @@ static void genRRC (iCode * ic) { operand *left, *result; - int size, offset; - char *l; + int size, offset; + char *l; D (emitcode (";", "genRRC")); @@ -8357,16 +8434,16 @@ AccAXLsh (char *x, int shCount) break; case 3: case 4: - case 5: // AAAAABBB:CCCCCDDD + case 5: // AAAAABBB:CCCCCDDD - AccRol (shCount); // BBBAAAAA:CCCCCDDD + AccRol (shCount); // BBBAAAAA:CCCCCDDD emitcode ("anl", "a,#0x%02x", SLMask[shCount]); // BBB00000:CCCCCDDD emitcode ("xch", "a,%s", x); // CCCCCDDD:BBB00000 - AccRol (shCount); // DDDCCCCC:BBB00000 + AccRol (shCount); // DDDCCCCC:BBB00000 emitcode ("xch", "a,%s", x); // BBB00000:DDDCCCCC @@ -8382,14 +8459,14 @@ AccAXLsh (char *x, int shCount) emitcode ("xrl", "a,%s", x); // BBBCCCCC:DDD00000 break; - case 6: // AAAAAABB:CCCCCCDD + case 6: // AAAAAABB:CCCCCCDD emitcode ("anl", "a,#0x%02x", SRMask[shCount]); // 000000BB:CCCCCCDD emitcode ("mov", "c,acc.0"); // c = B emitcode ("xch", "a,%s", x); // CCCCCCDD:000000BB #if 0 // REMOVE ME - AccAXRrl1 (x); // BCCCCCCD:D000000B - AccAXRrl1 (x); // BBCCCCCC:DD000000 + AccAXRrl1 (x); // BCCCCCCD:D000000B + AccAXRrl1 (x); // BBCCCCCC:DD000000 #else emitcode("rrc","a"); emitcode("xch","a,%s", x); @@ -8403,7 +8480,7 @@ AccAXLsh (char *x, int shCount) emitcode("xch","a,%s", x); #endif break; - case 7: // a:x <<= 7 + case 7: // a:x <<= 7 emitcode ("anl", "a,#0x%02x", SRMask[shCount]); // 0000000B:CCCCCCCD @@ -8412,7 +8489,7 @@ AccAXLsh (char *x, int shCount) emitcode ("xch", "a,%s", x); // CCCCCCCD:0000000B - AccAXRrl1 (x); // BCCCCCCC:D0000000 + AccAXRrl1 (x); // BCCCCCCC:D0000000 break; default: @@ -8432,26 +8509,26 @@ AccAXRsh (char *x, int shCount) break; case 1: CLRC; - AccAXRrl1 (x); // 0->a:x + AccAXRrl1 (x); // 0->a:x break; case 2: CLRC; - AccAXRrl1 (x); // 0->a:x + AccAXRrl1 (x); // 0->a:x CLRC; - AccAXRrl1 (x); // 0->a:x + AccAXRrl1 (x); // 0->a:x break; case 3: case 4: - case 5: // AAAAABBB:CCCCCDDD = a:x + case 5: // AAAAABBB:CCCCCDDD = a:x - AccRol (8 - shCount); // BBBAAAAA:DDDCCCCC + AccRol (8 - shCount); // BBBAAAAA:DDDCCCCC emitcode ("xch", "a,%s", x); // CCCCCDDD:BBBAAAAA - AccRol (8 - shCount); // DDDCCCCC:BBBAAAAA + AccRol (8 - shCount); // DDDCCCCC:BBBAAAAA emitcode ("anl", "a,#0x%02x", SRMask[shCount]); // 000CCCCC:BBBAAAAA @@ -8470,13 +8547,13 @@ AccAXRsh (char *x, int shCount) emitcode ("xch", "a,%s", x); // 000AAAAA:BBBCCCCC break; - case 6: // AABBBBBB:CCDDDDDD + case 6: // AABBBBBB:CCDDDDDD emitcode ("mov", "c,acc.7"); - AccAXLrl1 (x); // ABBBBBBC:CDDDDDDA + AccAXLrl1 (x); // ABBBBBBC:CDDDDDDA emitcode ("mov", "c,acc.7"); - AccAXLrl1 (x); // BBBBBBCC:DDDDDDAA + AccAXLrl1 (x); // BBBBBBCC:DDDDDDAA emitcode ("xch", "a,%s", x); // DDDDDDAA:BBBBBBCC @@ -8484,11 +8561,11 @@ AccAXRsh (char *x, int shCount) SRMask[shCount]); // 000000AA:BBBBBBCC break; - case 7: // ABBBBBBB:CDDDDDDD + case 7: // ABBBBBBB:CDDDDDDD emitcode ("mov", "c,acc.7"); // c = A - AccAXLrl1 (x); // BBBBBBBC:DDDDDDDA + AccAXLrl1 (x); // BBBBBBBC:DDDDDDDA emitcode ("xch", "a,%s", x); // DDDDDDDA:BBBBBBCC @@ -8514,27 +8591,27 @@ AccAXRshS (char *x, int shCount) break; case 1: emitcode ("mov", "c,acc.7"); - AccAXRrl1 (x); // s->a:x + AccAXRrl1 (x); // s->a:x break; case 2: emitcode ("mov", "c,acc.7"); - AccAXRrl1 (x); // s->a:x + AccAXRrl1 (x); // s->a:x emitcode ("mov", "c,acc.7"); - AccAXRrl1 (x); // s->a:x + AccAXRrl1 (x); // s->a:x break; case 3: case 4: - case 5: // AAAAABBB:CCCCCDDD = a:x + case 5: // AAAAABBB:CCCCCDDD = a:x tlbl = newiTempLabel (NULL); - AccRol (8 - shCount); // BBBAAAAA:CCCCCDDD + AccRol (8 - shCount); // BBBAAAAA:CCCCCDDD emitcode ("xch", "a,%s", x); // CCCCCDDD:BBBAAAAA - AccRol (8 - shCount); // DDDCCCCC:BBBAAAAA + AccRol (8 - shCount); // DDDCCCCC:BBBAAAAA emitcode ("anl", "a,#0x%02x", SRMask[shCount]); // 000CCCCC:BBBAAAAA @@ -8557,16 +8634,16 @@ AccAXRshS (char *x, int shCount) (unsigned char) ~SRMask[shCount]); // 111AAAAA:BBBCCCCC emitLabel (tlbl); - break; // SSSSAAAA:BBBCCCCC + break; // SSSSAAAA:BBBCCCCC - case 6: // AABBBBBB:CCDDDDDD + case 6: // AABBBBBB:CCDDDDDD tlbl = newiTempLabel (NULL); emitcode ("mov", "c,acc.7"); - AccAXLrl1 (x); // ABBBBBBC:CDDDDDDA + AccAXLrl1 (x); // ABBBBBBC:CDDDDDDA emitcode ("mov", "c,acc.7"); - AccAXLrl1 (x); // BBBBBBCC:DDDDDDAA + AccAXLrl1 (x); // BBBBBBCC:DDDDDDAA emitcode ("xch", "a,%s", x); // DDDDDDAA:BBBBBBCC @@ -8579,12 +8656,12 @@ AccAXRshS (char *x, int shCount) emitLabel (tlbl); break; - case 7: // ABBBBBBB:CDDDDDDD + case 7: // ABBBBBBB:CDDDDDDD tlbl = newiTempLabel (NULL); emitcode ("mov", "c,acc.7"); // c = A - AccAXLrl1 (x); // BBBBBBBC:DDDDDDDA + AccAXLrl1 (x); // BBBBBBBC:DDDDDDDA emitcode ("xch", "a,%s", x); // DDDDDDDA:BBBBBBCC @@ -8785,9 +8862,13 @@ genlshTwo (operand * result, operand * left, int shCount) if (size > 1) { if (shCount) - shiftL1Left2Result (left, LSB, result, MSB16, shCount); + { + shiftL1Left2Result (left, LSB, result, MSB16, shCount); + } else - movLeft2Result (left, LSB, result, MSB16, 0); + { + movLeft2Result (left, LSB, result, MSB16, 0); + } } aopPut (result, zero, LSB); } @@ -9389,7 +9470,6 @@ genRightShiftLiteral (operand * left, while (size--) movLeft2Result (left, size, result, size, 0); } - else if (shCount >= (size * 8)) { if (sign) @@ -9935,10 +10015,16 @@ genNearPointerGet (operand * left, { // Aha, it is a pointer, just in disguise. rname = aopGet (left, 0, FALSE, FALSE); - if (*rname != '@') + if (strcmp (rname, "a") == 0) { - fprintf(stderr, "probable internal error: unexpected rname @ %s:%d\n", - __FILE__, __LINE__); + // It's in pdata or on xstack + rname = AOP (left)->aopu.aop_ptr->name; + emitcode ("mov", "%s,a", rname); + } + else if (*rname != '@') + { + fprintf(stderr, "probable internal error: unexpected rname '%s' @ %s:%d\n", + rname, __FILE__, __LINE__); } else { @@ -9993,7 +10079,7 @@ genNearPointerGet (operand * left, } /* now some housekeeping stuff */ - if (aop) /* we had to allocate for this iCode */ + if (aop) /* we had to allocate for this iCode */ { if (pi) { /* post increment present */ aopPut (left, rname, 0); @@ -10021,7 +10107,7 @@ genNearPointerGet (operand * left, if (ifx && !ifx->generated) { - genIfxJump (ifx, ifxCond, left, NULL, result); + genIfxJump (ifx, ifxCond, left, NULL, result, ic->next); } /* done */ @@ -10094,7 +10180,7 @@ genPagedPointerGet (operand * left, } /* now some housekeeping stuff */ - if (aop) /* we had to allocate for this iCode */ + if (aop) /* we had to allocate for this iCode */ { if (pi) aopPut (left, rname, 0); @@ -10121,7 +10207,7 @@ genPagedPointerGet (operand * left, if (ifx && !ifx->generated) { - genIfxJump (ifx, ifxCond, left, NULL, result); + genIfxJump (ifx, ifxCond, left, NULL, result, ic->next); } /* done */ @@ -10236,7 +10322,7 @@ genFarPointerGet (operand * left, if (ifx && !ifx->generated) { - genIfxJump (ifx, ifxCond, left, NULL, result); + genIfxJump (ifx, ifxCond, left, NULL, result, ic->next); } freeAsmop (result, NULL, ic, TRUE); @@ -10290,7 +10376,7 @@ genCodePointerGet (operand * left, if (ifx && !ifx->generated) { - genIfxJump (ifx, ifxCond, left, NULL, result); + genIfxJump (ifx, ifxCond, left, NULL, result, ic->next); } freeAsmop (result, NULL, ic, TRUE); @@ -10345,7 +10431,7 @@ genGenPointerGet (operand * left, if (ifx && !ifx->generated) { - genIfxJump (ifx, ifxCond, left, NULL, result); + genIfxJump (ifx, ifxCond, left, NULL, result, ic->next); } freeAsmop (result, NULL, ic, TRUE); @@ -10629,7 +10715,13 @@ genNearPointerSet (operand * right, { // Aha, it is a pointer, just in disguise. rname = aopGet (result, 0, FALSE, FALSE); - if (*rname != '@') + if (strcmp (rname, "a") == 0) + { + // It's in pdata or on xstack + rname = AOP (result)->aopu.aop_ptr->name; + emitcode ("mov", "%s,a", rname); + } + else if (*rname != '@') { fprintf(stderr, "probable internal error: unexpected rname @ %s:%d\n", __FILE__, __LINE__); @@ -10685,7 +10777,7 @@ genNearPointerSet (operand * right, } /* now some housekeeping stuff */ - if (aop) /* we had to allocate for this iCode */ + if (aop) /* we had to allocate for this iCode */ { if (pi) aopPut (result, rname, 0); @@ -11016,19 +11108,15 @@ genIfx (iCode * ic, iCode * popIc) /* the result is now in the accumulator or a directly addressable bit */ freeAsmop (cond, NULL, ic, TRUE); - /* if there was something to be popped then do it */ - if (popIc) - genIpop (popIc); - /* if the condition is a bit variable */ if (isbit && dup) - genIfxJump(ic, dup, NULL, NULL, NULL); + genIfxJump(ic, dup, NULL, NULL, NULL, popIc); else if (isbit && IS_ITEMP (cond) && SPIL_LOC (cond)) - genIfxJump (ic, SPIL_LOC (cond)->rname, NULL, NULL, NULL); + genIfxJump (ic, SPIL_LOC (cond)->rname, NULL, NULL, NULL, popIc); else if (isbit && !IS_ITEMP (cond)) - genIfxJump (ic, OP_SYMBOL (cond)->rname, NULL, NULL, NULL); + genIfxJump (ic, OP_SYMBOL (cond)->rname, NULL, NULL, NULL, popIc); else - genIfxJump (ic, "a", NULL, NULL, NULL); + genIfxJump (ic, "a", NULL, NULL, NULL, popIc); ic->generated = 1; } @@ -11091,24 +11179,34 @@ genAddrOf (iCode * ic) } /* object not on stack then we need the name */ - size = AOP_SIZE (IC_RESULT (ic)); + size = getDataSize (IC_RESULT (ic)); offset = 0; while (size--) { char s[SDCC_NAME_MAX]; if (offset) - sprintf (s, "#(%s >> %d)", - sym->rname, - offset * 8); + { + sprintf (s, "#(%s >> %d)", + sym->rname, + offset * 8); + } else - SNPRINTF (s, sizeof(s), "#%s", sym->rname); + { + SNPRINTF (s, sizeof(s), "#%s", sym->rname); + } aopPut (IC_RESULT (ic), s, offset++); } + if (opIsGptr (IC_RESULT (ic))) + { + char buffer[10]; + SNPRINTF (buffer, sizeof(buffer), + "#0x%02x", pointerTypeToGPByte (pointerCode (getSpec (operandType (IC_LEFT (ic)))), NULL, NULL)); + aopPut (IC_RESULT (ic), buffer, GPTRSIZE - 1); + } release: freeAsmop (IC_RESULT (ic), NULL, ic, TRUE); - } /*-----------------------------------------------------------------*/ @@ -11192,7 +11290,7 @@ genAssign (iCode * ic) /* bit variables done */ /* general case */ - size = AOP_SIZE (result); + size = getDataSize (result); offset = 0; if (AOP_TYPE (right) == AOP_LIT) lit = ulFromVal (AOP (right)->aopu.aop_lit); @@ -11233,6 +11331,7 @@ genAssign (iCode * ic) offset++; } } + adjustArithmeticResult (ic); release: freeAsmop (result, NULL, ic, TRUE); @@ -11268,7 +11367,7 @@ genJumpTab (iCode * ic) /* multiply by three */ if (aopGetUsesAcc (IC_JTCOND (ic), 0)) { - emitcode ("mov", "b,#3"); + emitcode ("mov", "b,#0x03"); emitcode ("mul", "ab"); } else @@ -11402,7 +11501,6 @@ genCast (iCode * ic) /* if the result is of type pointer */ if (IS_PTR (ctype)) { - int p_type; sym_link *type = operandType (right); sym_link *etype = getSpec (type); @@ -11446,7 +11544,7 @@ genCast (iCode * ic) exit(1); } - sprintf(gpValStr, "#0x%x", gpVal); + sprintf(gpValStr, "#0x%02x", gpVal); aopPut (result, gpValStr, GPTRSIZE - 1); } goto release; @@ -11919,18 +12017,25 @@ gen51Code (iCode * lic) break; case IPOP: - /* IPOP happens only when trying to restore a - spilt live range, if there is an ifx statement - following this pop then the if statement might - be using some of the registers being popped which - would destory the contents of the register so - we need to check for this condition and handle it */ - if (ic->next && - ic->next->op == IFX && - regsInCommon (IC_LEFT (ic), IC_COND (ic->next))) - genIfx (ic->next, ic); - else - genIpop (ic); + { + iCode *ifxIc, *popIc; + bool CommonRegs = FALSE; + + /* IPOP happens only when trying to restore a + spilt live range, if there is an ifx statement + following this pop (or several) then the if statement might + be using some of the registers being popped which + would destory the contents of the register so + we need to check for this condition and handle it */ + for (ifxIc = ic->next; ifxIc && ifxIc->op == IPOP; ifxIc = ifxIc->next); + for (popIc = ic; popIc && popIc->op == IPOP; popIc = popIc->next) + CommonRegs |= (ifxIc && ifxIc->op == IFX && !ifxIc->generated && + regsInCommon (IC_LEFT (popIc), IC_COND (ifxIc))); + if (CommonRegs) + genIfx (ifxIc, ic); + else + genIpop (ic); + } break; case CALL: