+2005-05-16 Raphael Neider <rneider AT web.de>
+ * src/pic16/gen.{c,h}: s/mov2f/pic16_mov2f made public
+ * src/pic16/genarith.c (genAddit): fixed bug 1202480
+ * src/pic16/pcode.{c,h} (pic16_newpCodeOpBit_simple): NEW
+ convenience function for bit access
+
2005-05-15 Maarten Brock <sourceforge.brock AT dse.nl>
* device/lib/printf_large.c: fixed bug 1193299
static asmop *newAsmop (short type);
static pCodeOp *pic16_popRegFromString(char *str, int size, int offset, operand *op);
extern pCode *pic16_newpCodeAsmDir(char *asdir, char *argfmt, ...);
-static void mov2f(asmop *dst, asmop *src, int offset);
static void mov2fp(pCodeOp *dst, asmop *src, int offset);
static pCodeOp *pic16_popRegFromIdx(int rIdx);
pic16_emitpcode(POC_MOVFW,pic16_popGet(aop,offset));
}
-static void mov2f(asmop *dst, asmop *src, int offset)
+void pic16_mov2f(asmop *dst, asmop *src, int offset)
{
if(is_LitAOp(src)) {
pic16_emitpcode(POC_MOVLW, pic16_popGet(src, offset));
size = AOP_SIZE(op);
while(size--) {
- mov2f(AOP(result), AOP(op), offset);
+ pic16_mov2f(AOP(result), AOP(op), offset);
offset++;
}
pctemp = pic16_popGetTempReg(1);
pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),size));
- pic16_emitpcode(POC_MOVWF, pctemp); //pic16_pic16_popRegFromIdx(pic16_Gstack_base_addr));
+ pic16_emitpcode(POC_MOVWF, pctemp); //pic16_popRegFromIdx(pic16_Gstack_base_addr));
pic16_emitpcode(POC_MOVLW, pic16_popGetLit(0x80));
pic16_emitpcode(POC_XORWF, pctemp); //pic16_popRegFromIdx(pic16_Gstack_base_addr));
pic16_emitpcode(POC_XORFW, pic16_popGet(AOP(right),size));
#endif
{
/* we don't know if left is a literal or a register, take care -- VR */
- mov2f(AOP(result), AOP(left), offset);
+ pic16_mov2f(AOP(result), AOP(left), offset);
}
offset++;
}
#if 1
/* this is already done, why change it? */
if (!pic16_sameRegs(AOP(left),AOP(result))) {
- mov2f(AOP(result), AOP(left), 0);
+ pic16_mov2f(AOP(result), AOP(left), 0);
}
#endif
} else {
/* we don't know if left is a literal or a register, take care -- VR */
- mov2f(AOP(result), AOP(left), offset);
+ pic16_mov2f(AOP(result), AOP(left), offset);
}
offset++;
}
tlbl = newiTempLabel(NULL);
if (!pic16_sameRegs(AOP(left),AOP(result))) {
- mov2f(AOP(result), AOP(left), 0);
+ pic16_mov2f(AOP(result), AOP(left), 0);
// pic16_emitpcode(POC_MOVFW, pic16_popGet(AOP(left),0));
// pic16_emitpcode(POC_MOVWF, pic16_popGet(AOP(result),0));
if(shCount == 0){
assert (res_size <= lsize);
while (res_size--) {
- mov2f (AOP(result), AOP(left), res_size);
+ pic16_mov2f (AOP(result), AOP(left), res_size);
} // for
}
// (e.g. char c = 0x100 << -3 will become c = 0x00 >> 3 == 0x00 instad of 0x20)
// This is fine, as it only occurs for left shifting with negative count which is not standardized!
for (offset=0; offset < min(AOP_SIZE(left), AOP_SIZE(result)); offset++) {
- mov2f (AOP(result),AOP(left), offset);
+ pic16_mov2f (AOP(result),AOP(left), offset);
} // for
// if result is longer than left, fill with zeros (or sign)
while (size--) {
if(offset < AOP_SIZE(right)) {
DEBUGpic16_emitcode("; ***","%s %d - pointer cast3 ptype = 0x%x",__FUNCTION__,__LINE__, p_type);
- mov2f(AOP(result), AOP(right), offset);
+ pic16_mov2f(AOP(result), AOP(right), offset);
/*
if ((AOP_TYPE(right) == AOP_PCODE) &&
AOP(right)->aopu.pcop->type == PO_IMMEDIATE) {
while (size--) {
if(!_G.resDirect)
- mov2f(AOP(result), AOP(right), offset);
+ pic16_mov2f(AOP(result), AOP(right), offset);
offset++;
}
int pic16_my_powof2 (unsigned long num);
void pic16_mov2w (asmop *aop, int offset);
+void pic16_mov2f(asmop *dst, asmop *src, int offset);
void dumpiCode(iCode *lic);
}
#endif
+#if 0
/*-----------------------------------------------------------------*/
/* genAddlit - generates code for addition */
/*-----------------------------------------------------------------*/
}
}
+#endif
static void emitMOVWF(operand *reg, int offset)
{
static void genAddLit (iCode *ic, int lit)
{
- int size,same;
- int lo;
+ int size,sizeL,same;
+ int i, llit;
operand *result;
operand *left;
+ sym_link *lleft;
FENTRY;
left = IC_LEFT(ic);
+ lleft = operandType (left);
result = IC_RESULT(ic);
same = pic16_sameRegs(AOP(left), AOP(result));
size = pic16_getDataSize(result);
+ sizeL = pic16_getDataSize(left);
+ llit = lit;
+
+#define MIN(a,b) (((a) < (b)) ? (a) : (b))
+ /* move left to result -- possibly sign extend */
+ for (i=0; i < MIN(size, sizeL); i++) {
+ pic16_mov2f (AOP(result), AOP(left), i);
+ } // for i
+#undef MIN
+
+ /* extend to result size */
+ if (IS_UNSIGNED(lleft)) {
+ /* zero-extend */
+ for (i = sizeL; i < size; i++) {
+ pic16_emitpcode (POC_CLRF, pic16_popGet (AOP(result), i));
+ } // for i
+ } else {
+ /* sign-extend */
+ if (size == sizeL + 1) {
+ pic16_emitpcode (POC_CLRF, pic16_popGet (AOP(result), sizeL));
+ pic16_emitpcode (POC_BTFSC, pic16_newpCodeOpBit_simple (AOP(left),sizeL-1,7));
+ pic16_emitpcode (POC_SETF, pic16_popGet (AOP(result), sizeL));
+ } else {
+ pic16_emitpcode (POC_CLRF, pic16_popCopyReg (&pic16_pc_wreg));
+ pic16_emitpcode (POC_BTFSC, pic16_newpCodeOpBit_simple (AOP(left),sizeL-1,7));
+ pic16_emitpcode (POC_SETF, pic16_popCopyReg (&pic16_pc_wreg));
+
+ for (i=sizeL; i < size; i++) {
+ pic16_emitpcode (POC_MOVWF, pic16_popGet (AOP(result), i));
+ } // for i
+ } // if
+ } // if (SIGNED)
+
+ /* special cases */
+ if (lit == 0) {
+ /* nothing to do */
+ } else if (lit == 1) {
+ switch (size) {
+ case 1:
+ /* handled below */
+ break;
+ case 2:
+ pic16_emitpcode (POC_INFSNZ, pic16_popGet (AOP(result), 0));
+ break;
+ default:
+ assert (size > 2);
+ pic16_emitpcode (POC_INCF, pic16_popGet(AOP(result), 0));
+ for (i=1; i < size-1; i++) {
+ emitSKPNC; /* a jump here saves up to 2(size-2)cycles */
+ pic16_emitpcode (POC_INCF, pic16_popGet(AOP(result), i));
+ } // for i
+ emitSKPNC;
+ break;
+ } // switch
+
+ pic16_emitpcode (POC_INCF, pic16_popGet (AOP(result), size-1));
+ } else {
+ /* general case */
+
+ /* add literal to result */
+ for (i=0; i < size; i++) {
+ pic16_emitpcode (POC_MOVLW, pic16_popGetLit (llit));
+ llit >>= 8; /* FIXME: arithmetic right shift for signed literals? */
+ pic16_emitpcode (i == 0 ? POC_ADDWF : POC_ADDWFC,
+ pic16_popGet (AOP(result), i));
+ }
+ }
+
+#if 0
if(same) {
}
}
}
+#endif
}
/*-----------------------------------------------------------------*/
#include "ralloc.h"
#include "device.h"
+extern char *pic16_aopGet (struct asmop *aop, int offset, bool bit16, bool dname);
+
#if defined(__BORLANDC__) || defined(_MSC_VER)
#define STRCASECMP stricmp
#define inline
return pcop;
}
+pCodeOp *pic16_newpCodeOpBit_simple (struct asmop *op, int offs, int bit)
+{
+ return pic16_newpCodeOpBit (pic16_aopGet(op,offs,FALSE,FALSE),
+ bit, 0, PO_GPR_REGISTER);
+}
+
/*-----------------------------------------------------------------*
* pCodeOp *pic16_newpCodeOpReg(int rIdx) - allocate a new register
pCodeOp *pic16_newpCodeOpLit(int lit);
pCodeOp *pic16_newpCodeOpLit2(int lit, pCodeOp *arg2);
pCodeOp *pic16_newpCodeOpBit(char *name, int bit,int inBitSpace, PIC_OPTYPE subt);
+pCodeOp *pic16_newpCodeOpBit_simple (struct asmop *op, int offs, int bit);
pCodeOp *pic16_newpCodeOpRegFromStr(char *name);
pCodeOp *pic16_newpCodeOpReg(int rIdx);
pCodeOp *pic16_newpCodeOp(char *name, PIC_OPTYPE p);