#define FUNCTION_LABEL_INC 20
static int labelOffset=0;
-static int debug_verbose=1;
+static int debug_verbose=0;
/*-----------------------------------------------------------------*/
if (strcmp(d,s)) {
DEBUGemitcode(";","%d",__LINE__);
- emitcode("movf","%s,w",s);
+ if(strcmp(s,"W"))
+ emitcode("movf","%s,w",s);
emitcode("movwf","%s",d);
}
break;
case AOP_REG:
if (strcmp(aop->aopu.aop_reg[offset]->name,s) != 0 &&
strcmp(aop->aopu.aop_reg[offset]->dname,s)!= 0){
+ /*
if (*s == '@' ||
strcmp(s,"r0") == 0 ||
strcmp(s,"r1") == 0 ||
emitcode("mov","%s,%s ; %d",
aop->aopu.aop_reg[offset]->dname,s,__LINE__);
else
- emitcode("mov","%s,%s ; %d",
- aop->aopu.aop_reg[offset]->name,s,__LINE__);
+ */
+
+ if(strcmp(s,"W"))
+ emitcode("movf","%s,w ; %d",s,__LINE__);
+
+ emitcode("movwf","%s",
+ aop->aopu.aop_reg[offset]->name);
+
}
break;
DEBUGemitcode ("; ***","%s %d",__FUNCTION__,__LINE__);
- while (size--) {
- aopPut(AOP(oper),fReturn[offset],offset);
- offset++;
- }
+ // The last byte in the assignment is in W
+ aopPut(AOP(oper),"W",size-1);
+
+ if(size>1) {
+ while (--size) {
+ aopPut(AOP(oper),fReturn[offset],offset);
+ offset++;
+
+ }
+ }
}
for (i = (pic14_nRegs - 1) ; i >= 0 ;i--) {
if (options.useXstack) {
emitcode("movx","a,@%s",r->name);
- emitcode("mov","(%s+%d),a",
- regspic14[i].base,8*bank+regspic14[i].offset);
+ //emitcode("mov","(%s+%d),a",
+ // regspic14[i].base,8*bank+regspic14[i].offset);
emitcode("dec","%s",r->name);
} else
- emitcode("pop","(%s+%d)",
- regspic14[i].base,8*bank+regspic14[i].offset);
+ emitcode("pop",""); //"(%s+%d)",
+ //regspic14[i].base,8*bank); //+regspic14[i].offset);
}
if (options.useXstack) {
for (i = 0 ; i < pic14_nRegs ;i++) {
if (options.useXstack) {
emitcode("inc","%s",r->name);
- emitcode("mov","a,(%s+%d)",
- regspic14[i].base,8*bank+regspic14[i].offset);
+ //emitcode("mov","a,(%s+%d)",
+ // regspic14[i].base,8*bank+regspic14[i].offset);
emitcode("movx","@%s,a",r->name);
} else
- emitcode("push","(%s+%d)",
- regspic14[i].base,8*bank+regspic14[i].offset);
+ emitcode("push","");// "(%s+%d)",
+ //regspic14[i].base,8*bank+regspic14[i].offset);
}
if (pushPsw) {
while (size--) {
char *l = aopGet(AOP(IC_LEFT(sic)),offset,
FALSE,FALSE);
- DEBUGemitcode(";","%d",__LINE__);
+ DEBUGemitcode(";","%d - left type %d",__LINE__,AOP(IC_LEFT(sic))->type);
if (strcmp(l,fReturn[offset])) {
- if ( (AOP(IC_LEFT(sic))->type) == AOP_IMMD)
+ if ( ((AOP(IC_LEFT(sic))->type) == AOP_IMMD) ||
+ ((AOP(IC_LEFT(sic))->type) == AOP_LIT) )
emitcode("movlw","%s",l);
else
emitcode("movf","%s,w",l);
- emitcode("movwf","%s",fReturn[offset]);
+ // The last one is past in W
+ if(size)
+ emitcode("movwf","%s",fReturn[offset]);
}
offset++;
}
/* if (options.debug && currFunc) { */
if (currFunc) {
_G.debugLine = 1;
- emitcode(";","C_DS_%s_DS_%d_DS_%d_DS_%d ==.",
+ emitcode(";","C$%s$%d$%d$%d ==.",
ic->filename,currFunc->lastLine,
ic->level,ic->block);
if (IS_STATIC(currFunc->etype))
- emitcode(";","XF%s_DS_%s_DS_0_DS_0 ==.",moduleName,currFunc->name);
+ emitcode(";","XF%s$%s$0$0 ==.",moduleName,currFunc->name);
else
- emitcode(";","XG_DS_%s_DS_0_DS_0 ==.",currFunc->name);
+ emitcode(";","XG$%s$0$0 ==.",currFunc->name);
_G.debugLine = 0;
}
/* if debug then send end of function */
if (currFunc) {
_G.debugLine = 1;
- emitcode(";","C_DS_%s_DS_%d_DS_%d_DS_%d ==.",
+ emitcode(";","C$%s$%d$%d$%d ==.",
ic->filename,currFunc->lastLine,
ic->level,ic->block);
if (IS_STATIC(currFunc->etype))
- emitcode(";","XF%s_DS_%s_DS_0_DS_0 ==.",moduleName,currFunc->name);
+ emitcode(";","XF%s$%s$0$0 ==.",moduleName,currFunc->name);
else
- emitcode(";","XG_DS_%s_DS_0_DS_0 ==.",currFunc->name);
+ emitcode(";","XG$%s$0$0 ==.",currFunc->name);
_G.debugLine = 0;
}
l = aopGet(AOP(IC_LEFT(ic)),offset,
FALSE,FALSE);
if (strcmp(fReturn[offset],l)) {
- if ( (AOP(IC_LEFT(ic))->type) == AOP_IMMD)
+ if( ( (AOP(IC_LEFT(ic))->type) == AOP_IMMD) ||
+ ((AOP(IC_LEFT(ic))->type) == AOP_LIT) )
emitcode("movlw","%s",l);
else
emitcode("movf","%s,w",l);
- emitcode("movwf","%s",fReturn[offset++]);
+ if(size)
+ emitcode("movwf","%s",fReturn[offset]);
+ offset++;
}
}
}
else {
know_W = 0;
emitcode("incf","%s,w", aopGet(AOP(IC_LEFT(ic)),offset,FALSE,FALSE));
- emitcode("movwf","%s", aopGet(AOP(IC_RESULT(ic)),offset,FALSE,FALSE));
+ if(AOP_TYPE(IC_RESULT(ic)) != AOP_ACC)
+ emitcode("movwf","%s", aopGet(AOP(IC_RESULT(ic)),offset,FALSE,FALSE));
}
break;
case 0xff:
else {
know_W = 0;
emitcode("decf","%s,w", aopGet(AOP(IC_LEFT(ic)),offset,FALSE,FALSE));
- emitcode("movwf","%s", aopGet(AOP(IC_RESULT(ic)),offset,FALSE,FALSE));
+ if(AOP_TYPE(IC_RESULT(ic)) != AOP_ACC)
+ emitcode("movwf","%s", aopGet(AOP(IC_RESULT(ic)),offset,FALSE,FALSE));
}
break;
default:
if (sameRegs(AOP(IC_LEFT(ic)), AOP(IC_RESULT(ic))) )
emitcode("addwf","%s,f", aopGet(AOP(IC_LEFT(ic)),0,FALSE,FALSE));
else {
- emitcode(";ic_left type","%d",AOP_TYPE(IC_LEFT(ic)));
- if(AOP_TYPE(IC_LEFT(ic)) == AOP_IMMD) {
+ if( (AOP_TYPE(IC_LEFT(ic)) == AOP_IMMD) ||
+ (AOP_TYPE(IC_LEFT(ic)) == AOP_LIT) ) {
emitcode("addlw","%s", aopGet(AOP(IC_LEFT(ic)),0,FALSE,FALSE));
} else {
emitcode("addwf","%s,w", aopGet(AOP(IC_LEFT(ic)),0,FALSE,FALSE));
emitcode("mov","b,%s + 1",aopGet(AOP(result),0,TRUE,FALSE));
}
else { /* we need to get it byte by byte */
- emitcode("movlw","%s",aopGet(AOP(result),0,FALSE,FALSE));
- emitcode("movwf","fsr");
-
- //emitcode("mov","dpl,%s",aopGet(AOP(result),0,FALSE,FALSE));
- //emitcode("mov","dph,%s",aopGet(AOP(result),1,FALSE,FALSE));
- //if (options.model == MODEL_FLAT24)
- //{
- // emitcode("mov", "dpx,%s",aopGet(AOP(result),2,FALSE,FALSE));
- // emitcode("mov","b,%s",aopGet(AOP(result),3,FALSE,FALSE));
- //}
- //else
- //{
- // emitcode("mov","b,%s",aopGet(AOP(result),2,FALSE,FALSE));
- //}
+ char *l = aopGet(AOP(result),0,FALSE,FALSE);
+ if(strcmp("FSR",l))
+ emitcode("movlw","%s",aopGet(AOP(result),0,FALSE,FALSE));
+
+ emitcode("movwf","INDF");
}
}
/* so dptr know contains the address */
size = AOP_SIZE(right);
offset = 0 ;
- while (size--) {
+ while (--size) {
char *l = aopGet(AOP(right),offset++,FALSE,FALSE);
- //emitcode("movf","%s,w",aopGet(AOP(right),offset++,FALSE,FALSE));
- emitcode("movwf","indf");
if(size)
emitcode("incf","fsr,f");
+ emitcode("movf","%s,w",aopGet(AOP(right),offset++,FALSE,FALSE));
+ emitcode("movwf","indf");
//MOVA(l);
//DEBUGemitcode(";lcall","__gptrput");
//if (size)
cdbSymbol(currFunc,cdbFile,FALSE,TRUE);
_G.debugLine = 1;
if (IS_STATIC(currFunc->etype))
- emitcode("",";F%s_DS_%s_DS_0_DS_0 %d",moduleName,currFunc->name,__LINE__);
+ emitcode("",";F%s$%s$0$0 %d",moduleName,currFunc->name,__LINE__);
else
- emitcode("",";G_DS_%s_DS_0_DS_0 %d",currFunc->name,__LINE__);
+ emitcode("",";G$%s$0$0 %d",currFunc->name,__LINE__);
_G.debugLine = 0;
}
if ( cln != ic->lineno ) {
if ( options.debug ) {
_G.debugLine = 1;
- emitcode("",";C_DS_%s_DS_%d_DS_%d_DS_%d ==.",
+ emitcode("",";C$%s$%d$%d$%d ==.",
ic->filename,ic->lineno,
ic->level,ic->block);
_G.debugLine = 0;
regs regspic14[] =
{
- {PIC_INDF, 0, "INDF", "INDR", "0", 0, 1},
- {PIC_GPR, 0, "r0x0C", "r0x0C", "0x0C", 0x0C, 1},
- {PIC_GPR, 0, "r0x0D", "r0x0C", "0x0D", 0x0D, 1},
- {PIC_GPR, 0, "r0x0E", "r0x0C", "0x0E", 0x0E, 1},
- {PIC_GPR, 0, "r0x0F", "r0x0C", "0x0F", 0x0F, 1},
- {PIC_GPR, 0, "r0x10", "r0x10", "0x10", 0x10, 1},
- {PIC_GPR, 0, "r0x11", "r0x11", "0x11", 0x11, 1},
- {PIC_GPR, 0, "r0x12", "r0x12", "0x12", 0x12, 1},
- {PIC_GPR, 0, "r0x13", "r0x13", "0x13", 0x13, 1},
- {PIC_GPR, 0, "r0x14", "r0x14", "0x14", 0x14, 1},
- {PIC_GPR, 0, "r0x15", "r0x15", "0x15", 0x15, 1},
- {PIC_GPR, 0, "r0x16", "r0x16", "0x16", 0x16, 1},
- {PIC_GPR, 0, "r0x17", "r0x17", "0x17", 0x17, 1},
- {PIC_GPR, 0, "r0x18", "r0x18", "0x18", 0x18, 1},
- {PIC_GPR, 0, "r0x19", "r0x19", "0x19", 0x19, 1},
- {PIC_GPR, 0, "r0x1A", "r0x1A", "0x1A", 0x1A, 1},
- {PIC_GPR, 0, "r0x1B", "r0x1B", "0x1B", 0x1B, 1},
- {PIC_GPR, 0, "r0x1C", "r0x1C", "0x1C", 0x1C, 1},
- {PIC_GPR, 0, "r0x1D", "r0x1D", "0x1D", 0x1D, 1},
- {PIC_GPR, 0, "r0x1E", "r0x1E", "0x1E", 0x1E, 1},
- {PIC_GPR, 0, "r0x1F", "r0x1F", "0x1F", 0x1F, 1},
+ {REG_GPR, 0x0C, "r0x0C", "r0x0C", 0x0C, 1, 0},
+ {REG_GPR, 0x0D, "r0x0D", "r0x0C", 0x0D, 1, 0},
+ {REG_GPR, 0x0E, "r0x0E", "r0x0C", 0x0E, 1, 0},
+ {REG_GPR, 0x0F, "r0x0F", "r0x0C", 0x0F, 1, 0},
+ {REG_GPR, 0x10, "r0x10", "r0x10", 0x10, 1, 0},
+ {REG_GPR, 0x11, "r0x11", "r0x11", 0x11, 1, 0},
+ {REG_GPR, 0x12, "r0x12", "r0x12", 0x12, 1, 0},
+ {REG_GPR, 0x13, "r0x13", "r0x13", 0x13, 1, 0},
+ {REG_GPR, 0x14, "r0x14", "r0x14", 0x14, 1, 0},
+ {REG_GPR, 0x15, "r0x15", "r0x15", 0x15, 1, 0},
+ {REG_GPR, 0x16, "r0x16", "r0x16", 0x16, 1, 0},
+ {REG_GPR, 0x17, "r0x17", "r0x17", 0x17, 1, 0},
+ {REG_GPR, 0x18, "r0x18", "r0x18", 0x18, 1, 0},
+ {REG_GPR, 0x19, "r0x19", "r0x19", 0x19, 1, 0},
+ {REG_GPR, 0x1A, "r0x1A", "r0x1A", 0x1A, 1, 0},
+ {REG_GPR, 0x1B, "r0x1B", "r0x1B", 0x1B, 1, 0},
+ {REG_GPR, 0x1C, "r0x1C", "r0x1C", 0x1C, 1, 0},
+ {REG_GPR, 0x1D, "r0x1D", "r0x1D", 0x1D, 1, 0},
+ {REG_GPR, 0x1E, "r0x1E", "r0x1E", 0x1E, 1, 0},
+ {REG_GPR, 0x1F, "r0x1F", "r0x1F", 0x1F, 1, 0},
+ {REG_PTR, 4, "FSR", "FSR", 4, 1,0},
};
int pic14_nRegs = sizeof(regspic14) / sizeof(regs);
static void spillThis (symbol *);
+static int debug=1;
+static FILE *debugF=NULL;
+/*-----------------------------------------------------------------*/
+/* debugLog - open a file for debugging information */
+/*-----------------------------------------------------------------*/
+//static void debugLog(char *inst,char *fmt, ...)
+static void debugLog(char *fmt, ...)
+{
+ static int append = 0; // First time through, open the file without append.
+ char buffer[256];
+ //char *bufferP=buffer;
+ va_list ap;
+
+ if(!debug)
+ return;
+
+
+ if (!debugF) {
+ /* create the file name */
+ strcpy(buffer,srcFileName);
+ strcat(buffer,".d");
+
+ if( !(debugF = fopen(buffer, (append ? "a+" : "w") ))) {
+ werror(E_FILE_OPEN_ERR,buffer);
+ exit(1);
+ }
+ append = 1; // Next time debubLog is called, we'll append the debug info
+ }
+
+ va_start(ap,fmt);
+
+ vsprintf(buffer,fmt,ap);
+
+ fprintf(debugF,"%s",buffer);
+/*
+ while (isspace(*bufferP)) bufferP++;
+
+ if (bufferP && *bufferP)
+ lineCurr = (lineCurr ?
+ connectLine(lineCurr,newLineNode(lb)) :
+ (lineHead = newLineNode(lb)));
+ lineCurr->isInline = _G.inLine;
+ lineCurr->isDebug = _G.debugLine;
+*/
+ va_end(ap);
+
+}
+
+static void debugNewLine(void)
+{
+ if(debugF)
+ fputc('\n',debugF);
+}
+/*-----------------------------------------------------------------*/
+/* debugLogClose - closes the debug log file (if opened) */
+/*-----------------------------------------------------------------*/
+static void debugLogClose(void)
+{
+ if(debugF) {
+ fclose(debugF);
+ debugF = NULL;
+ }
+}
+#define AOP(op) op->aop
+
+static char *debugAopGet(char *str,operand *op)
+{
+ if(str)
+ debugLog(str);
+
+ printOperand(op,debugF);debugNewLine();
+
+ return NULL;
+
+}
+
+static char * decodeOp(unsigned int op)
+{
+
+ if(op<128 && op>' ') {
+ buffer[0] = (op & 0xff);
+ buffer[1] = 0;
+ return buffer;
+ }
+
+ switch(op) {
+ case IDENTIFIER:
+ return "IDENTIFIER";
+ case TYPE_NAME:
+ return "TYPE_NAME";
+ case CONSTANT:
+ return "CONSTANT";
+ case STRING_LITERAL:
+ return "STRING_LITERAL";
+ case SIZEOF:
+ return "SIZEOF";
+ case PTR_OP:
+ return "PTR_OP";
+ case INC_OP:
+ return "INC_OP";
+ case DEC_OP:
+ return "DEC_OP";
+ case LEFT_OP:
+ return "LEFT_OP";
+ case RIGHT_OP:
+ return "RIGHT_OP";
+ case LE_OP:
+ return "LE_OP";
+ case GE_OP:
+ return "GE_OP";
+ case EQ_OP:
+ return "EQ_OP";
+ case NE_OP:
+ return "NE_OP";
+ case AND_OP:
+ return "AND_OP";
+ case OR_OP:
+ return "OR_OP";
+ case MUL_ASSIGN:
+ return "MUL_ASSIGN";
+ case DIV_ASSIGN:
+ return "DIV_ASSIGN";
+ case MOD_ASSIGN:
+ return "MOD_ASSIGN";
+ case ADD_ASSIGN:
+ return "ADD_ASSIGN";
+ case SUB_ASSIGN:
+ return "SUB_ASSIGN";
+ case LEFT_ASSIGN:
+ return "LEFT_ASSIGN";
+ case RIGHT_ASSIGN:
+ return "RIGHT_ASSIGN";
+ case AND_ASSIGN:
+ return "AND_ASSIGN";
+ case XOR_ASSIGN:
+ return "XOR_ASSIGN";
+ case OR_ASSIGN:
+ return "OR_ASSIGN";
+ case TYPEDEF:
+ return "TYPEDEF";
+ case EXTERN:
+ return "EXTERN";
+ case STATIC:
+ return "STATIC";
+ case AUTO:
+ return "AUTO";
+ case REGISTER:
+ return "REGISTER";
+ case CODE:
+ return "CODE";
+ case EEPROM:
+ return "EEPROM";
+ case INTERRUPT:
+ return "INTERRUPT";
+ case SFR:
+ return "SFR";
+ case AT:
+ return "AT";
+ case SBIT:
+ return "SBIT";
+ case REENTRANT:
+ return "REENTRANT";
+ case USING:
+ return "USING";
+ case XDATA:
+ return "XDATA";
+ case DATA:
+ return "DATA";
+ case IDATA:
+ return "IDATA";
+ case PDATA:
+ return "PDATA";
+ case VAR_ARGS:
+ return "VAR_ARGS";
+ case CRITICAL:
+ return "CRITICAL";
+ case NONBANKED:
+ return "NONBANKED";
+ case BANKED:
+ return "BANKED";
+ case CHAR:
+ return "CHAR";
+ case SHORT:
+ return "SHORT";
+ case INT:
+ return "INT";
+ case LONG:
+ return "LONG";
+ case SIGNED:
+ return "SIGNED";
+ case UNSIGNED:
+ return "UNSIGNED";
+ case FLOAT:
+ return "FLOAT";
+ case DOUBLE:
+ return "DOUBLE";
+ case CONST:
+ return "CONST";
+ case VOLATILE:
+ return "VOLATILE";
+ case VOID:
+ return "VOID";
+ case BIT:
+ return "BIT";
+ case STRUCT:
+ return "STRUCT";
+ case UNION:
+ return "UNION";
+ case ENUM:
+ return "ENUM";
+ case ELIPSIS:
+ return "ELIPSIS";
+ case RANGE:
+ return "RANGE";
+ case FAR:
+ return "FAR";
+ case _XDATA:
+ return "_XDATA";
+ case _CODE:
+ return "_CODE";
+ case _GENERIC:
+ return "_GENERIC";
+ case _NEAR:
+ return "_NEAR";
+ case _PDATA:
+ return "_PDATA";
+ case _IDATA:
+ return "_IDATA";
+ case _EEPROM:
+ return "_EEPROM";
+ case CASE:
+ return "CASE";
+ case DEFAULT:
+ return "DEFAULT";
+ case IF:
+ return "IF";
+ case ELSE:
+ return "ELSE";
+ case SWITCH:
+ return "SWITCH";
+ case WHILE:
+ return "WHILE";
+ case DO:
+ return "DO";
+ case FOR:
+ return "FOR";
+ case GOTO:
+ return "GOTO";
+ case CONTINUE:
+ return "CONTINUE";
+ case BREAK:
+ return "BREAK";
+ case RETURN:
+ return "RETURN";
+ case INLINEASM:
+ return "INLINEASM";
+ case IFX:
+ return "IFX";
+ case ADDRESS_OF:
+ return "ADDRESS_OF";
+ case GET_VALUE_AT_ADDRESS:
+ return "GET_VALUE_AT_ADDRESS";
+ case SPIL:
+ return "SPIL";
+ case UNSPIL:
+ return "UNSPIL";
+ case GETHBIT:
+ return "GETHBIT";
+ case BITWISEAND:
+ return "BITWISEAND";
+ case UNARYMINUS:
+ return "UNARYMINUS";
+ case IPUSH:
+ return "IPUSH";
+ case IPOP:
+ return "IPOP";
+ case PCALL:
+ return "PCALL";
+ case ENDFUNCTION:
+ return "ENDFUNCTION";
+ case JUMPTABLE:
+ return "JUMPTABLE";
+ case RRC:
+ return "RRC";
+ case RLC:
+ return "RLC";
+ case CAST:
+ return "CAST";
+ case CALL:
+ return "CALL";
+ case PARAM:
+ return "PARAM ";
+ case NULLOP:
+ return "NULLOP";
+ case BLOCK:
+ return "BLOCK";
+ case LABEL:
+ return "LABEL";
+ case RECEIVE:
+ return "RECEIVE";
+ case SEND:
+ return "SEND";
+ }
+ sprintf(buffer,"unkown op %d %c",op, op&0xff);
+ return buffer;
+}
+/*-----------------------------------------------------------------*/
+/*-----------------------------------------------------------------*/
+static char * debugLogRegType(short type)
+{
+
+ switch(type) {
+ case REG_GPR:
+ return "REG_GPR";
+ case REG_PTR:
+ return "REG_PTR";
+ case REG_CND:
+ return "REG_CND";
+ }
+
+ sprintf(buffer,"unkown reg type %d",type);
+ return buffer;
+}
/*-----------------------------------------------------------------*/
/* allocReg - allocates register of given type */
{
int i;
+ debugLog("%s of type %s\n",__FUNCTION__,debugLogRegType(type));
+
for ( i = 0 ; i < pic14_nRegs ; i++ ) {
/* if type is given as 0 then any
if (!type &&
regspic14[i].isFree ) {
regspic14[i].isFree = 0;
+ regspic14[i].wasUsed = 1;
if (currFunc)
currFunc->regsUsed =
bitVectSetBit(currFunc->regsUsed,i);
+ debugLog(" returning %s\n",regspic14[i].name);
return ®spic14[i];
}
/* other wise look for specific type
if (regspic14[i].isFree &&
regspic14[i].type == type) {
regspic14[i].isFree = 0;
+ regspic14[i].wasUsed = 1;
if (currFunc)
currFunc->regsUsed =
bitVectSetBit(currFunc->regsUsed,i);
+ debugLog(" returning %s\n",regspic14[i].name);
return ®spic14[i];
}
}
{
int i ;
- printf("%s - idx=%d\n",__FUNCTION__,idx);
+ debugLog("%s\n",__FUNCTION__);
for (i=0;i < pic14_nRegs;i++)
if (regspic14[i].rIdx == idx)
/*-----------------------------------------------------------------*/
static void freeReg (regs *reg)
{
+ debugLog("%s\n",__FUNCTION__);
reg->isFree = 1;
}
int i;
int nfr=0;
+ debugLog("%s\n",__FUNCTION__);
for (i = 0 ; i < pic14_nRegs; i++ )
if (regspic14[i].isFree && regspic14[i].type == type)
nfr++;
static int nfreeRegsType (int type)
{
int nfr ;
+ debugLog("%s\n",__FUNCTION__);
if (type == REG_PTR) {
if ((nfr = nFreeRegs(type)) == 0)
return nFreeRegs(REG_GPR);
{
int i ;
+ debugLog("%s\n",__FUNCTION__);
if (!defs)
return TRUE ;
{
bitVect *spillable ;
+ debugLog("%s\n",__FUNCTION__);
/* spillable live ranges are those that are live at this
point . the following categories need to be subtracted
from this set.
/*-----------------------------------------------------------------*/
static int noSpilLoc (symbol *sym, eBBlock *ebp,iCode *ic)
{
+ debugLog("%s\n",__FUNCTION__);
return (sym->usl.spillLoc ? 0 : 1);
}
/*-----------------------------------------------------------------*/
static int hasSpilLoc (symbol *sym, eBBlock *ebp, iCode *ic)
{
+ debugLog("%s\n",__FUNCTION__);
return (sym->usl.spillLoc ? 1 : 0);
}
/*-----------------------------------------------------------------*/
static int directSpilLoc (symbol *sym, eBBlock *ebp, iCode *ic)
{
+ debugLog("%s\n",__FUNCTION__);
if ( sym->usl.spillLoc &&
(IN_DIRSPACE(SPEC_OCLS(sym->usl.spillLoc->etype))))
return 1;
/*-----------------------------------------------------------------*/
static int hasSpilLocnoUptr (symbol *sym, eBBlock *ebp, iCode *ic)
{
+ debugLog("%s\n",__FUNCTION__);
return ((sym->usl.spillLoc && !sym->uptr) ? 1 : 0);
}
/*-----------------------------------------------------------------*/
static int rematable (symbol *sym, eBBlock *ebp, iCode *ic)
{
+ debugLog("%s\n",__FUNCTION__);
return sym->remat;
}
/*-----------------------------------------------------------------*/
static int notUsedInBlock (symbol *sym, eBBlock *ebp, iCode *ic)
{
+ debugLog("%s\n",__FUNCTION__);
return (!bitVectBitsInCommon(sym->defs,ebp->usesDefs) &&
allDefsOutOfRange (sym->defs,ebp->fSeq,ebp->lSeq));
/* return (!bitVectBitsInCommon(sym->defs,ebp->usesDefs)); */
/*-----------------------------------------------------------------*/
static int notUsedInRemaining (symbol *sym, eBBlock *ebp, iCode *ic)
{
+ debugLog("%s\n",__FUNCTION__);
return ((usedInRemaining (operandFromSymbol(sym),ic) ? 0 : 1) &&
allDefsOutOfRange (sym->defs,ebp->fSeq,ebp->lSeq));
}
/*-----------------------------------------------------------------*/
static int allLRs (symbol *sym, eBBlock *ebp, iCode *ic)
{
+ debugLog("%s\n",__FUNCTION__);
return 1;
}
set *rset = NULL;
int i;
+ debugLog("%s\n",__FUNCTION__);
if (!lrs || !lrs->size)
return NULL;
{
symbol *sym = NULL, *lsym = NULL ;
+ debugLog("%s\n",__FUNCTION__);
sym = lsym = setFirstItem(sset);
if (!lsym)
static int noOverLap (set *itmpStack, symbol *fsym)
{
symbol *sym;
+ debugLog("%s\n",__FUNCTION__);
for (sym = setFirstItem(itmpStack); sym;
V_ARG(symbol **,sloc);
V_ARG(symbol *,fsym);
+ debugLog("%s\n",__FUNCTION__);
/* if already found */
if (*sloc)
return 0;
regs *r0,*r1;
int k;
+ debugLog("%s\n",__FUNCTION__);
if (!_G.regAssigned ||
bitVectIsZero(_G.regAssigned))
return;
int useXstack, model, noOverlay;
char slocBuffer[30];
+ debugLog("%s\n",__FUNCTION__);
/* first go try and find a free one that is already
existing on the stack */
if (sprintf(slocBuffer,"sloc%d",_G.slocNum++) >= sizeof(slocBuffer))
{
- fprintf(stderr, "***Internal error: slocBuffer overflowed: %s:%d\n",
+ fprintf(stderr, "kkkInternal error: slocBuffer overflowed: %s:%d\n",
__FILE__, __LINE__);
exit(1);
}
{
sym_link *etype;
+ debugLog("%s\n",__FUNCTION__);
if (!sym)
return FALSE ;
static void spillThis (symbol *sym)
{
int i;
+ debugLog("%s : %s\n",__FUNCTION__, sym->rname);
+
/* if this is rematerializable or has a spillLocation
we are okay, else we need to create a spillLocation
for it */
set *selectS ;
symbol *sym;
+ debugLog("%s\n",__FUNCTION__);
/* get the spillable live ranges */
lrcs = computeSpillable (ic);
symbol *ssym;
int i ;
+ debugLog("%s\n",__FUNCTION__);
/* get something we can spil */
ssym = selectSpil(ic,ebp,forSym);
{
regs *reg;
+ debugLog("%s\n",__FUNCTION__);
tryAgain:
/* try for a ptr type */
if ((reg = allocReg(REG_PTR)))
{
regs *reg;
+ debugLog("%s\n",__FUNCTION__);
tryAgain:
/* try for gpr type */
if ((reg = allocReg(REG_GPR)))
{
int i;
+ debugLog("%s\n",__FUNCTION__);
for ( i = 0 ; i < sym->nRegs ; i++)
if (sym->regs[i] == reg)
return TRUE;
int k;
symbol *result;
+ debugLog("%s\n",__FUNCTION__);
for (sym = hTabFirstItem(liveRanges,&k); sym;
sym = hTabNextItem(liveRanges,&k)) {
symbol *sym = OP_SYMBOL(op);
int i;
+ debugLog("%s\n",__FUNCTION__);
/* not spilt any more */
sym->isspilt = sym->blockSpil = sym->remainSpil = 0;
bitVectUnSetBit(_G.spiltSet,sym->key);
/*-----------------------------------------------------------------*/
static int willCauseSpill ( int nr, int rt)
{
+ debugLog("%s\n",__FUNCTION__);
/* first check if there are any avlb registers
of te type required */
if (rt == REG_PTR) {
}
}
+ debugLog(" ... yep it will (cause a spill)\n");
/* it will cause a spil */
return 1;
}
int count = min(result->nRegs,opsym->nRegs);
int i , j = 0, shared = 0;
+ debugLog("%s\n",__FUNCTION__);
/* if the result has been spilt then cannot share */
if (opsym->isspilt)
return ;
{
int i;
+ debugLog("%s\n",__FUNCTION__);
/* for all blocks */
for (i = 0; i < count ; i++ ) {
/* of all instructions do */
for (ic = ebbs[i]->sch ; ic ; ic = ic->next) {
+ debugLog(" op: %s\n", decodeOp(ic->op));
+
/* if this is an ipop that means some live
range will have to be assigned again */
if (ic->op == IPOP)
}
}
+ if(ic->op == RECEIVE)
+ debugLog("When I get clever, I'll optimize the receive logic\n");
+
/* if we need ptr regs for the right side
then mark it */
if (POINTER_GET(ic) && getSize(OP_SYMBOL(IC_LEFT(ic))->type)
/* else we assign registers to it */
_G.regAssigned = bitVectSetBit(_G.regAssigned,sym->key);
+ debugLog(" %d - \n",__LINE__);
+
for (j = 0 ; j < sym->nRegs ;j++ ) {
if (sym->regType == REG_PTR)
sym->regs[j] = getRegPtr(ic,ebbs[i],sym);
if (!sym->regs[j])
break;
}
+ debugLog(" %d - \n",__LINE__);
+
/* if it shares registers with operands make sure
that they are in the same position */
if (IC_LEFT(ic) && IS_SYMOP(IC_LEFT(ic)) &&
positionRegs(OP_SYMBOL(IC_RESULT(ic)),
OP_SYMBOL(IC_RIGHT(ic)),ic->lineno);
+ debugLog(" %d - \n",__LINE__);
if (ptrRegSet) {
+ debugLog(" %d - \n",__LINE__);
pic14_ptrRegReq--;
ptrRegSet = 0;
}
symbol *sym;
int j;
+ debugLog("%s\n",__FUNCTION__);
/* only temporaries are assigned registers */
if (!IS_ITEMP(op))
return NULL;
{
bitVect *rmask = newBitVect(pic14_nRegs);
+ debugLog("%s\n",__FUNCTION__);
/* do the special cases first */
if (ic->op == IFX ) {
rmask = bitVectUnion(rmask,
{
int i;
+ debugLog("%s\n",__FUNCTION__);
/* for all blocks */
for (i = 0; i < count ; i++ ) {
iCode *ic ;
char *s = buffer;
iCode *ic = sym->rematiCode;
+ debugLog("%s\n",__FUNCTION__);
while (1) {
printf("%s\n",s);
}
/* we reached the end */
- sprintf(s,"%s",OP_SYMBOL(IC_LEFT(ic))->rname);
+ sprintf(s,"%s\n",OP_SYMBOL(IC_LEFT(ic))->rname);
break;
}
int k;
iCode *ic;
+ debugLog("%s\n",__FUNCTION__);
/* for each live range do */
for ( sym = hTabFirstItem(liveRanges,&k); sym ;
sym = hTabNextItem(liveRanges,&k)) {
+ debugLog(" %d - %s\n",__LINE__ , sym->rname);
+
/* if used zero times then no registers needed */
if ((sym->liveTo - sym->liveFrom) == 0)
continue ;
/* if the live range is a temporary */
if (sym->isitmp) {
+ debugLog(" %d - \n",__LINE__);
+
/* if the type is marked as a conditional */
if (sym->regType == REG_CND)
continue ;
if (sym->ruonly || sym->accuse) {
if (IS_AGGREGATE(sym->type) || sym->isptr)
sym->type = aggrToPtr(sym->type,FALSE);
+ debugLog(" %d - \n",__LINE__);
+
continue ;
}
POINTER_GET(ic) &&
!IS_BITVAR(sym->etype)) {
+ debugLog(" %d - \n",__LINE__);
/* if remat in data space */
if (OP_SYMBOL(IC_LEFT(ic))->remat &&
printTypeChain(sym->type,stderr);fprintf(stderr,"\n");
}
+ debugLog(" %d - \n",__LINE__);
+
/* determine the type of register required */
if (sym->nRegs == 1 &&
IS_PTR(sym->type) &&
sym->regType = REG_PTR ;
else
sym->regType = REG_GPR ;
-
+ debugLog(" reg type %s\n",debugLogRegType(sym->regType));
+
} else
/* for the first run we don't provide */
/* registers for true symbols we will */
{
int i;
+ debugLog("%s\n",__FUNCTION__);
for (i=0;i< pic14_nRegs;i++ )
regspic14[i].isFree = 1;
}
{
symbol *sym = item;
+ debugLog("%s\n",__FUNCTION__);
deallocLocal(sym);
return 0;
}
{
iCode *dic ;
+ debugLog("%s\n",__FUNCTION__);
/* go thru till we find a definition for the
symbol on the right */
for ( dic = ic->prev ; dic ; dic = dic->prev) {
iCode *dic, *sic;
+ debugLog("%s\n",__FUNCTION__);
+
+ debugAopGet(" result:",IC_RESULT(ic));
+ debugAopGet(" left:",IC_LEFT(ic));
+ debugAopGet(" right:",IC_RIGHT(ic));
+
if (!IS_ITEMP(IC_RIGHT(ic)) ||
OP_SYMBOL(IC_RIGHT(ic))->isind ||
OP_LIVETO(IC_RIGHT(ic)) > ic->seq) {
}
/* find the definition of iTempNN scanning backwards if we find a
- a use of the true symbol in before we find the definition then
- we cannot */
+ a use of the true symbol before we find the definition then
+ we cannot pack */
for ( dic = ic->prev ; dic ; dic = dic->prev) {
/* if there is a function call and this is
if ( (dic->op == CALL || dic->op == PCALL) &&
(OP_SYMBOL(IC_RESULT(ic))->_isparm &&
!OP_SYMBOL(IC_RESULT(ic))->ismyparm)) {
+ debugLog(" %d - \n",__LINE__);
dic = NULL;
break;
}
if (IS_TRUE_SYMOP(IC_RESULT(dic)) &&
IS_OP_VOLATILE(IC_RESULT(dic))) {
+ debugLog(" %d - \n",__LINE__);
dic = NULL;
break;
}
if (IS_SYMOP(IC_RESULT(dic)) &&
IC_RESULT(dic)->key == IC_RIGHT(ic)->key) {
+ debugLog(" %d - dic key == ic key -- pointer set=%c\n",__LINE__,((POINTER_SET(dic)) ? 'Y' :'N') );
if (POINTER_SET(dic))
dic = NULL;
if (IS_SYMOP(IC_RIGHT(dic)) &&
(IC_RIGHT(dic)->key == IC_RESULT(ic)->key ||
IC_RIGHT(dic)->key == IC_RIGHT(ic)->key)) {
+ debugLog(" %d - \n",__LINE__);
dic = NULL;
break;
}
if (IS_SYMOP(IC_LEFT(dic)) &&
(IC_LEFT(dic)->key == IC_RESULT(ic)->key ||
IC_LEFT(dic)->key == IC_RIGHT(ic)->key)) {
+ debugLog(" %d - \n",__LINE__);
dic = NULL;
break;
}
if (POINTER_SET(dic) &&
IC_RESULT(dic)->key == IC_RESULT(ic)->key ) {
+ debugLog(" %d - \n",__LINE__);
dic = NULL ;
break;
}
return 0;
}
pack:
+ debugLog(" packing. removing %s\n",OP_SYMBOL(IC_RIGHT(ic))->rname);
/* found the definition */
/* replace the result with the result of */
/* this assignment and remove this assignment */
{
iCode *dic;
+ debugLog("%s\n",__FUNCTION__);
for (dic = ic->prev ; dic ; dic = dic->prev) {
/* if definition by assignment */
static int packRegsForSupport (iCode *ic, eBBlock *ebp)
{
int change = 0 ;
+
+ debugLog("%s\n",__FUNCTION__);
/* for the left & right operand :- look to see if the
left was assigned a true symbol in far space in that
case replace them */
if (!dic)
goto right ;
+ debugAopGet("removing left:",IC_LEFT(ic));
+
/* found it we need to remove it from the
block */
for ( sic = dic; sic != ic ; sic = sic->next )
if (IN_FARSPACE(SPEC_OCLS(etype)))
return change ;
}
+
+ debugAopGet("removing right:",IC_RIGHT(ic));
+
/* found it we need to remove it from the
block */
for ( sic = dic; sic != ic ; sic = sic->next )
bitVect *uses ;
iCode *dic, *sic;
+ debugLog("%s\n",__FUNCTION__);
/* if returning a literal then do nothing */
if (!IS_SYMOP(op))
return NULL;
return NULL;
/* this routine will mark the a symbol as used in one
- instruction use only && if the defintion is local
+ instruction use only && if the definition is local
(ie. within the basic block) && has only one definition &&
- that definiion is either a return value from a
+ that definition is either a return value from a
function or does not contain any variables in
far space */
uses = bitVectCopy(OP_USES(op));
if (bitVectnBitsOn(OP_DEFS(op)) > 1)
return NULL ; /* has more than one definition */
- /* get the that definition */
+ /* get that definition */
if (!(dic =
hTabItemWithKey(iCodehTab,
bitVectFirstBit(OP_DEFS(op)))))
!IS_DATA_PTR(aggrToPtr(operandType(IC_LEFT(dic)),FALSE)))
return NULL ;
- /* if address of & the result is remat the okay */
+ /* if address of & the result is remat then okay */
if (dic->op == ADDRESS_OF &&
OP_SYMBOL(IC_RESULT(dic))->remat)
continue ;
sym_link *ltype = getSpec(operandType(IC_LEFT(ic)));
sym_link *rtype = getSpec(operandType(IC_RIGHT(ic)));
+ debugLog("%s\n",__FUNCTION__);
/* bitwise operations are considered optimizable
under the following conditions (Jean-Louis VERN)
{
iCode *uic;
+ debugLog("%s\n",__FUNCTION__);
/* if + or - then it has to be one byte result */
if ((ic->op == '+' || ic->op == '-')
&& getSize(operandType(IC_RESULT(ic))) > 1)
}
+/*-----------------------------------------------------------------*/
+/* packForPush - hueristics to reduce iCode for pushing */
+/*-----------------------------------------------------------------*/
+static void packForReceive(iCode *ic, eBBlock *ebp)
+{
+ iCode *dic;
+ bool can_remove=1; // assume that we can remove temporary
+
+ debugLog("%s\n",__FUNCTION__);
+ debugAopGet(" result:",IC_RESULT(ic));
+ debugAopGet(" left:",IC_LEFT(ic));
+ debugAopGet(" right:",IC_RIGHT(ic));
+
+ if(!ic->next)
+ return;
+
+ for ( dic = ic->next ; dic ; dic = dic->next ) {
+
+
+
+ if(IC_LEFT(dic) && (IC_RESULT(ic)->key == IC_LEFT(dic)->key) )
+ debugLog(" used on left\n");
+ if(IC_RIGHT(dic) && IC_RESULT(ic)->key == IC_RIGHT(dic)->key)
+ debugLog(" used on right\n");
+ if(IC_RESULT(dic) && IC_RESULT(ic)->key == IC_RESULT(dic)->key)
+ debugLog(" used on result\n");
+
+ if( (IC_LEFT(dic) && (IC_RESULT(ic)->key == IC_LEFT(dic)->key) ) ||
+ (IC_RESULT(dic) && IC_RESULT(ic)->key == IC_RESULT(dic)->key) )
+ return;
+
+ }
+
+ debugLog(" hey we can remove this unnecessary assign\n");
+}
/*-----------------------------------------------------------------*/
/* packForPush - hueristics to reduce iCode for pushing */
/*-----------------------------------------------------------------*/
{
iCode *dic;
+ debugLog("%s\n",__FUNCTION__);
if (ic->op != IPUSH || !IS_ITEMP(IC_LEFT(ic)))
return ;
iCode *ic ;
int change = 0 ;
+ debugLog("%s\n",__FUNCTION__);
+
while (1) {
change = 0;
/* TrueSym := iTempNN:1 */
for ( ic = ebp->sch ; ic ; ic = ic->next ) {
-
/* find assignment of the form TrueSym := iTempNN:1 */
if (ic->op == '=' && !POINTER_SET(ic))
change += packRegsForAssign(ic,ebp);
+ /* debug stuff */
+ if (ic->op == '=') {
+ if(POINTER_SET(ic))
+ debugLog("pointer is set\n");
+ debugAopGet(" result:",IC_RESULT(ic));
+ debugAopGet(" left:",IC_LEFT(ic));
+ debugAopGet(" right:",IC_RIGHT(ic));
+ }
+
}
if (!change)
}
/* mark the pointer usages */
- if (POINTER_SET(ic))
+ if (POINTER_SET(ic)) {
OP_SYMBOL(IC_RESULT(ic))->uptr = 1;
-
- if (POINTER_GET(ic))
+ debugLog(" marking as a pointer (set)\n");
+ }
+ if (POINTER_GET(ic)) {
OP_SYMBOL(IC_LEFT(ic))->uptr = 1;
-
+ debugLog(" marking as a pointer (get)\n");
+ }
+
if (!SKIP_IC2(ic)) {
/* if we are using a symbol on the stack
then we should say pic14_ptrRegReq */
/* reduce for support function calls */
if (ic->supportRtn || ic->op == '+' || ic->op == '-' )
packRegsForSupport (ic,ebp);
-
+
+ /* if a parameter is passed, it's in W, so we may not
+ need to place a copy in a register */
+ if(ic->op == RECEIVE)
+ packForReceive(ic,ebp);
+
/* some cases the redundant moves can
can be eliminated for return statements */
if ((ic->op == RETURN || ic->op == SEND) &&
}
}
-
+
+static void dumpEbbsToDebug(eBBlock **ebbs, int count)
+{
+ int i;
+
+ if(!debug || !debugF)
+ return;
+
+ for (i=0; i < count ; i++ ) {
+ fprintf(debugF,"\n----------------------------------------------------------------\n");
+ fprintf(debugF,"Basic Block %s : loop Depth = %d noPath = %d , lastinLoop = %d\n",
+ ebbs[i]->entryLabel->name,
+ ebbs[i]->depth,
+ ebbs[i]->noPath,
+ ebbs[i]->isLastInLoop);
+ fprintf(debugF,"depth 1st num %d : bbnum = %d 1st iCode = %d , last iCode = %d\n",
+ ebbs[i]->dfnum,
+ ebbs[i]->bbnum,
+ ebbs[i]->fSeq,
+ ebbs[i]->lSeq);
+ fprintf(debugF,"visited %d : hasFcall = %d\n",
+ ebbs[i]->visited,
+ ebbs[i]->hasFcall);
+
+ fprintf(debugF,"\ndefines bitVector :");
+ bitVectDebugOn(ebbs[i]->defSet,debugF);
+ fprintf(debugF,"\nlocal defines bitVector :");
+ bitVectDebugOn(ebbs[i]->ldefs,debugF);
+ fprintf(debugF,"\npointers Set bitvector :");
+ bitVectDebugOn(ebbs[i]->ptrsSet,debugF);
+ fprintf(debugF,"\nin pointers Set bitvector :");
+ bitVectDebugOn(ebbs[i]->inPtrsSet,debugF);
+ fprintf(debugF,"\ninDefs Set bitvector :");
+ bitVectDebugOn(ebbs[i]->inDefs,debugF);
+ fprintf(debugF,"\noutDefs Set bitvector :");
+ bitVectDebugOn(ebbs[i]->outDefs,debugF);
+ fprintf(debugF,"\nusesDefs Set bitvector :");
+ bitVectDebugOn(ebbs[i]->usesDefs,debugF);
+ fprintf(debugF,"\n----------------------------------------------------------------\n");
+ printiCChain(ebbs[i]->sch,debugF);
+ }
+}
/*-----------------------------------------------------------------*/
/* assignRegisters - assigns registers to each live range as need */
/*-----------------------------------------------------------------*/
iCode *ic;
int i ;
- fprintf(stderr,"%s:%s",__FILE__,__FUNCTION__);
+ debugLog("<><><><><><><><><><><><><><><><><>\nstarting\t%s:%s",__FILE__,__FUNCTION__);
+ debugLog("ebbs before optimizing:\n");
+ dumpEbbsToDebug(ebbs,count);
setToNull((void *)&_G.funcrUsed);
pic14_ptrRegReq = _G.stackExtend = _G.dataExtend = 0;
/* now get back the chain */
ic = iCodeLabelOptimize(iCodeFromeBBlock (ebbs,count));
+ debugLog("ebbs after optimizing:\n");
+ dumpEbbsToDebug(ebbs,count);
+
genpic14Code(ic);
/* mark all registers as free */
freeAllRegs();
+ debugLog("leaving\n<><><><><><><><><><><><><><><><><>\n");
+ debugLogClose();
return ;
}