X-Git-Url: https://git.gag.com/?a=blobdiff_plain;ds=sidebyside;f=src%2FSDCCast.c;h=15f59285a84add354e7611937d698e1eadc1f75c;hb=6cf005ad44bcebf9a5d6f6b8efdac2f85488cfa8;hp=26f59d09957b9cb66d39ae3c9e8ed3a8456d7620;hpb=f266c4a6123b86ddb2399d2cc23ab5df02430582;p=fw%2Fsdcc diff --git a/src/SDCCast.c b/src/SDCCast.c index 26f59d09..15f59285 100644 --- a/src/SDCCast.c +++ b/src/SDCCast.c @@ -50,6 +50,7 @@ int noAlloc = 0; symbol *currFunc; static ast *createIval (ast *, sym_link *, initList *, ast *); static ast *createIvalCharPtr (ast *, sym_link *, ast *); +static ast *optimizeCompare (ast *); ast *optimizeRRCRLC (ast *); ast *optimizeGetHbit (ast *); ast *backPatchLabels (ast *, symbol *, symbol *); @@ -1146,6 +1147,66 @@ processBlockVars (ast * tree, int *stack, int action) return tree; } +/*-------------------------------------------------------------*/ +/* constExprTree - returns TRUE if this tree is a constant */ +/* expression */ +/*-------------------------------------------------------------*/ +bool constExprTree (ast *cexpr) { + + if (!cexpr) { + return TRUE; + } + + cexpr = decorateType (resolveSymbols (cexpr)); + + switch (cexpr->type) + { + case EX_VALUE: + if (IS_AST_LIT_VALUE(cexpr)) { + // this is a literal + return TRUE; + } + if (IS_AST_SYM_VALUE(cexpr) && IS_FUNC(AST_SYMBOL(cexpr)->type)) { + // a function's address will never change + return TRUE; + } + if (IS_AST_SYM_VALUE(cexpr) && + IN_CODESPACE(SPEC_OCLS(AST_SYMBOL(cexpr)->etype))) { + // a symbol in code space will never change + // This is only for the 'char *s="hallo"' case and will have to leave + return TRUE; + } + return FALSE; + case EX_LINK: + werror (E_INTERNAL_ERROR, __FILE__, __LINE__, + "unexpected link in expression tree\n"); + return FALSE; + case EX_OP: + if (cexpr->opval.op==ARRAYINIT) { + fprintf (stderr, "skipping arrayinit\n"); + // this is a list of literals + return TRUE; + } + if (cexpr->opval.op=='=') { + return constExprTree(cexpr->right); + } + if (cexpr->opval.op==CAST) { + // jwk: cast ignored, maybe we should throw a warning here + return constExprTree(cexpr->right); + } + if (cexpr->opval.op=='&') { + return TRUE; + } + if (cexpr->opval.op==CALL || cexpr->opval.op==PCALL) { + return FALSE; + } + if (constExprTree(cexpr->left) && constExprTree(cexpr->right)) { + return TRUE; + } + } + return FALSE; +} + /*-----------------------------------------------------------------*/ /* constExprValue - returns the value of a constant expression */ /* or NULL if it is not a constant expression */ @@ -3904,7 +3965,7 @@ tryNext2: /*-----------------------------------------------------------------*/ /* optimizeCompare - otimizes compares for bit variables */ /*-----------------------------------------------------------------*/ -ast * +static ast * optimizeCompare (ast * root) { ast *optExpr = NULL;