if (ic->op == SEND || ic->op == RECEIVE) {
fprintf(of,"{argreg = %d}",ic->argreg);
}
+ if (ic->op == IPUSH) {
+ fprintf(of,"{parmPush = %d}",ic->parmPush);
+ }
fprintf (of, "\n");
}
of = stdout;
icTab = getTableEntry (ic->op);
- fprintf (stdout, "%s(%d:%d:%d:%d:%d)\t",
+ fprintf (of, "%s(%d:%d:%d:%d:%d)\t",
ic->filename, ic->lineno,
ic->seq, ic->key, ic->depth, ic->supportRtn);
icTab->iCodePrint (of, ic, icTab->printName);
{
symbol *itmplbl;
- /* check if this alredy exists */
+ /* check if this already exists */
if (s && (itmplbl = findSym (LabelTab, NULL, s)))
return itmplbl;
return IN_FARSPACE (oclass);
}
+/*-----------------------------------------------------------------*/
+/* isiCodeInFunctionCall - return TRUE if an iCode is between a */
+/* CALL/PCALL and the first IPUSH/SEND associated with the call */
+/*-----------------------------------------------------------------*/
+int
+isiCodeInFunctionCall (iCode * ic)
+{
+ iCode * lic = ic;
+
+ /* Find the next CALL/PCALL */
+ while (lic)
+ {
+ if (lic->op == CALL || lic->op == PCALL)
+ break;
+ lic = lic->next;
+ }
+
+ if (!lic)
+ return FALSE;
+
+ /* A function call was found. Scan backwards and see if an */
+ /* IPUSH or SEND is encountered */
+ while (ic)
+ {
+ if (lic != ic && (ic->op == CALL || ic->op == PCALL))
+ return FALSE;
+ if (ic->op == SEND || (ic->op == IPUSH && ic->parmPush))
+ return TRUE;
+ ic = ic->prev;
+ }
+
+ return FALSE;
+}
+
/*-----------------------------------------------------------------*/
/* operandLitValue - literal value of an operand */
/*-----------------------------------------------------------------*/
restype = getSpec (operandType (IC_RESULT (ic)));
if (!IS_LITERAL(opetype) &&
!IS_BIT(opetype))
+ {
SPEC_SCLS (restype) = SPEC_SCLS (opetype);
- SPEC_OCLS (restype) = SPEC_OCLS (opetype);
-
+ SPEC_OCLS (restype) = SPEC_OCLS (opetype);
+ }
ADDTOCHAIN (ic);
return IC_RESULT (ic);
}
/* hack don't like this but too lazy to think of
something better */
if (IS_ADDRESS_OF_OP (parms))
- parms->left->lvalue = 1;
+ parms->left->lvalue = 1;
if (IS_CAST_OP (parms) &&
- IS_PTR (parms->ftype) &&
- IS_ADDRESS_OF_OP (parms->right))
- parms->right->left->lvalue = 1;
+ IS_PTR (parms->ftype) &&
+ IS_ADDRESS_OF_OP (parms->right))
+ parms->right->left->lvalue = 1;
pval = geniCodeRValue (ast2iCode (parms,lvl+1), FALSE);
}
{
/* now decide whether to push or assign */
if (!(options.stackAuto || IFFUNC_ISREENT (ftype)))
- {
+ {
- /* assign */
- operand *top = operandFromSymbol (argVals->sym);
- /* clear useDef and other bitVectors */
- OP_USES(top)=OP_DEFS(top)=OP_SYMBOL(top)->clashes = NULL;
- geniCodeAssign (top, pval, 1, 0);
- }
+ /* assign */
+ operand *top = operandFromSymbol (argVals->sym);
+ /* clear useDef and other bitVectors */
+ OP_USES(top)=OP_DEFS(top)=OP_SYMBOL(top)->clashes = NULL;
+ geniCodeAssign (top, pval, 1, 0);
+ }
else
- {
- sym_link *p = operandType (pval);
- /* push */
- ic = newiCode (IPUSH, pval, NULL);
- ic->parmPush = 1;
- /* update the stack adjustment */
- *stack += getSize (IS_AGGREGATE (p) ? aggrToPtr (p, FALSE) : p);
- ADDTOCHAIN (ic);
- }
+ {
+ sym_link *p = operandType (pval);
+ /* push */
+ ic = newiCode (IPUSH, pval, NULL);
+ ic->parmPush = 1;
+ /* update the stack adjustment */
+ *stack += getSize (IS_AGGREGATE (p) ? aggrToPtr (p, FALSE) : p);
+ ADDTOCHAIN (ic);
+ }
}
argVals=argVals->next;
int needRangeCheck = !optimize.noJTabBoundary
|| tree->values.switchVals.swDefault;
sym_link *cetype = getSpec (operandType (cond));
- int sizeofMinCost, sizeofMaxCost;
+ int sizeofMinCost, sizeofZeroMinCost, sizeofMaxCost;
int sizeofMatchJump, sizeofJumpTable;
int sizeIndex;
/* Compute the size cost of the range check and subtraction. */
sizeofMinCost = 0;
+ sizeofZeroMinCost = 0;
sizeofMaxCost = 0;
if (needRangeCheck)
{
if (!(min==0 && IS_UNSIGNED (cetype)))
sizeofMinCost = port->jumptableCost.sizeofRangeCompare[sizeIndex];
+ if (!IS_UNSIGNED (cetype))
+ sizeofZeroMinCost = port->jumptableCost.sizeofRangeCompare[sizeIndex];
sizeofMaxCost = port->jumptableCost.sizeofRangeCompare[sizeIndex];
}
if (min)
/* If the size cost of handling a non-zero minimum exceeds the */
/* cost of extending the range down to zero, then it might be */
/* better to extend the range to zero. */
- if (min > 0 && sizeofMinCost >= (min * port->jumptableCost.sizeofElement))
+ if (min > 0 && (sizeofMinCost-sizeofZeroMinCost)
+ >= (min * port->jumptableCost.sizeofElement))
{
/* Only extend the jump table if it would still be manageable. */
if (1 + max <= port->jumptableCost.maxCount)
- min = 0;
+ {
+ min = 0;
+ if (IS_UNSIGNED (cetype))
+ sizeofMinCost = 0;
+ else
+ sizeofMinCost = port->jumptableCost.sizeofRangeCompare[sizeIndex];
+ }
}
/* Compute the total size cost of a jump table. */
/* Compute the total size cost of a match & jump sequence */
sizeofMatchJump = cnt * port->jumptableCost.sizeofMatchJump[sizeIndex];
-
+
/* If the size cost of the jump table is uneconomical then exit */
if (sizeofMatchJump < sizeofJumpTable)
return 0;
{
iCode *ic;
operand *op = NULL;
+ sym_link *type;
+
+ if (!options.stackAuto)
+ {
+ type = newLink(SPECIFIER);
+ SPEC_VOLATILE(type) = 1;
+ SPEC_NOUN(type) = V_BIT;
+ SPEC_SCLS(type) = S_BIT;
+ SPEC_BLEN(type) = 1;
+ SPEC_BSTR(type) = 0;
+ op = newiTempOperand(type, 1);
+ }
/* If op is NULL, the original interrupt state will saved on */
/* the stack. Otherwise, it will be saved in op. */
- /* Generate a save of the current interrupt state & disabled */
+ /* Generate a save of the current interrupt state & disable */
ic = newiCode (CRITICAL, NULL, NULL);
IC_RESULT (ic) = op;
ADDTOCHAIN (ic);