diff --git a/src/treeopt.in b/src/treeopt.in index 6bdd54aae11559928e3a4dbd5ed8fdad98e4fba0..aac66cbaf214b1c674a19a35ed3138c3457e8fd3 100644 --- a/src/treeopt.in +++ b/src/treeopt.in @@ -1,6 +1,6 @@ // -*- c -*- // -// $Id: treeopt.in,v 1.41 2000/09/23 12:41:51 grubba Exp $ +// $Id: treeopt.in,v 1.42 2000/09/23 15:58:39 grubba Exp $ // // The tree optimizer // @@ -58,12 +58,32 @@ F_PUSH_ARRAY(0 = F_CONSTANT[$$->u.sval.type == T_ARRAY], *): ; // `+(`+(a,b),c) => `+(a, b, c) +// NOTE: We do some ugly stuff here to avoid +// resolving the resulting type multiple times. F_APPLY(0 = F_CONSTANT - [$$->u.sval.type == T_FUNCTION] - [$$->u.sval.subtype == FUNCTION_BUILTIN] - [$$->u.sval.u.efun->function == f_add], - F_ARG_LIST(F_APPLY($0, 1), 2)): - F_APPLY($0, F_ARG_LIST($1, $2)); + [$$->u.sval.type == T_FUNCTION] + [$$->u.sval.subtype == FUNCTION_BUILTIN] + [$$->u.sval.u.efun->function == f_add], + 2 = F_ARG_LIST(3 = F_APPLY($0, 1), *)): + { + node *arglist = $2; + node *old_apply = $3; + ADD_NODE_REF2($1, _CAR(arglist) = $1); +#ifdef SHARED_NODES + arglist->hash = hash_node(arglist); + arglist->node_info |= OPT_DEFROSTED; +#endif /* SHARED_NODES */ + free_node(old_apply); +#ifdef PIKE_DEBUG + if (l_flag > 4) { + fprintf(stderr, "Result: "); + print_tree(n); + } +#endif /* PIKE_DEBUG */ + n = arglist; + continue; + } + ; // Similar rule for `*() disabled, since the type for '*() isn't // correct for all cases.