pike.git / src / las.c

version» Context lines:

pike.git/src/las.c:1:   /*\   ||| This file a part of Pike, and is copyright by Fredrik Hubinette   ||| Pike is distributed as GPL (General Public License)   ||| See the files COPYING and DISCLAIMER for more information.   \*/   #include "global.h" - RCSID("$Id: las.c,v 1.44 1998/01/26 02:34:50 grubba Exp $"); + RCSID("$Id: las.c,v 1.45 1998/01/26 19:59:54 hubbe Exp $");      #include "language.h"   #include "interpret.h"   #include "las.h"   #include "array.h"   #include "object.h"   #include "stralloc.h"   #include "dynamic_buffer.h"   #include "lex.h"   #include "pike_types.h"
pike.git/src/las.c:66:    case F_CONSTANT:    case F_LOCAL:    case F_CAST:    return 0;       default:    return !!CDR(n);    }   }    + #ifdef DEBUG + void check_tree(node *n, int depth) + { +  if(!d_flag) return; +  if(!n) return; +  if(n->token==USHRT_MAX) +  fatal("Free node in tree.\n"); +  +  if(!(depth & 1023)) +  { +  node *q; +  for(q=n->parent;q;q=q->parent) +  if(q->parent==n) +  fatal("Cyclic node structure found.\n"); +  } +  depth++; +  +  if(car_is_node(n)) +  { +  if(CAR(n)->parent != n) +  fatal("Parent is wrong.\n"); +  +  check_tree(CAR(n),depth); +  } +  +  if(cdr_is_node(n)) +  { +  if(CDR(n)->parent != n) +  fatal("Parent is wrong.\n"); +  +  check_tree(CDR(n),depth); +  } + } + #endif +    INT32 count_args(node *n)   {    int a,b; -  +  check_tree(n,0);    if(!n) return 0;    switch(n->token)    {    case F_VAL_LVAL:    case F_ARG_LIST:    a=count_args(CAR(n));    if(a==-1) return -1;    b=count_args(CDR(n));    if(b==-1) return -1;    return a+b;
pike.git/src/las.c:122:    default:    if(n->type == void_type_string) return 0;    return 1;    }   }      struct pike_string *find_return_type(node *n)   {    struct pike_string *a,*b;    +  check_tree(n,0); +     if(!n) return 0;    if(!(n->tree_info & OPT_RETURN)) return 0;    if(car_is_node(n))    a=find_return_type(CAR(n));    else    a=0;       if(cdr_is_node(n))    b=find_return_type(CDR(n));    else
pike.git/src/las.c:162:   static node *free_nodes=0;      void free_all_nodes()   {    if(!compiler_frame)    {    node *tmp;    struct node_chunk *tmp2;    int e=0;    -  + #ifndef DEBUG    if(cumulative_parse_error)    { -  + #endif       for(tmp2=node_chunks;tmp2;tmp2=tmp2->next) e+=NODES;    for(tmp=free_nodes;tmp;tmp=CAR(tmp)) e--;    if(e)    {    int e2=e;    for(tmp2=node_chunks;tmp2;tmp2=tmp2->next)    {    for(e=0;e<NODES;e++)    {    for(tmp=free_nodes;tmp;tmp=CAR(tmp))    if(tmp==tmp2->nodes+e)    break;       if(!tmp)    {    tmp=tmp2->nodes+e;   #ifdef DEBUG    if(!cumulative_parse_error)    { -  fprintf(stderr,"Free node at %p.\n",tmp); +  fprintf(stderr,"Free node at %p, (%s:%d) (token=%d).\n",tmp, tmp->current_file->str, tmp->line_number, tmp->token); +  if(tmp->token==F_CONSTANT) +  print_tree(tmp);    }    else   #endif    {    /* Free the node and be happy */    /* Make sure we don't free any nodes twice */    if(car_is_node(tmp)) CAR(tmp)=0;    if(cdr_is_node(tmp)) CDR(tmp)=0; -  +  debug_malloc_touch(tmp->type);    free_node(tmp);    }    }    }    }   #ifdef DEBUG    if(!cumulative_parse_error)    fatal("Failed to free %d nodes when compiling!\n",e2);   #endif    } -  + #ifndef DEBUG    } -  + #endif    while(node_chunks)    {    tmp2=node_chunks;    node_chunks=tmp2->next;    free((char *)tmp2);    }    free_nodes=0;    cumulative_parse_error=0;    }   }
pike.git/src/las.c:235:    case F_CONSTANT:    free_svalue(&(n->u.sval));    break;       default:    if(car_is_node(n)) free_node(CAR(n));    if(cdr_is_node(n)) free_node(CDR(n));    }    n->token=USHRT_MAX;    if(n->type) free_string(n->type); + #ifdef DEBUG +  if(n->current_file) free_string(n->current_file); + #endif    CAR(n)=free_nodes;    free_nodes=n;   }         /* here starts routines to make nodes */   static node *mkemptynode(void)   {    node *res;    if(!free_nodes)
pike.git/src/las.c:260:       for(e=0;e<NODES-1;e++)    CAR(tmp->nodes+e)=tmp->nodes+e+1;    CAR(tmp->nodes+e)=0;    free_nodes=tmp->nodes;    }    res=free_nodes;    free_nodes=CAR(res);    res->token=0;    res->line_number=lex.current_line; + #ifdef DEBUG +  copy_shared_string(res->current_file, lex.current_file); + #endif    res->type=0;    res->node_info=0;    res->tree_info=0;    res->parent=0;    return res;   }      node *mknode(short token,node *a,node *b)   {    node *res; -  +  check_tree(a,0); +  check_tree(b,0);    res = mkemptynode();    CAR(res) = a;    CDR(res) = b;    res->node_info = 0;    res->tree_info = 0;    switch(token)    {    case F_CATCH:    res->node_info |= OPT_SIDE_EFFECT;    break;
pike.git/src/las.c:335:    res->type = 0;       /* We try to optimize most things, but argument lists are hard... */    if(token != F_ARG_LIST && (a || b))    res->node_info |= OPT_TRY_OPTIMIZE;       if(a) a->parent = res;    if(b) b->parent = res;       if(!num_parse_error && compiler_pass==2) +  { +  check_tree(res,0);    optimize(res); -  +  check_tree(res,0); +  }      #ifdef DEBUG    if(d_flag > 3)    verify_shared_strings_tables();   #endif       return res;   }      node *mkstrnode(struct pike_string *str)
pike.git/src/las.c:447:    res->node_info = OPT_EXTERNAL_DEPEND;    }else{    res->node_info = OPT_NOT_CONST;    }    res->tree_info=res->node_info;      #ifdef __CHECKER__    CDR(res)=0;   #endif    res->u.number = i; +  check_tree(res,0);    return res;   }      node *mkexternalnode(int level,    int i,    struct identifier *id)   {    node *res = mkemptynode();    res->token = F_EXTERNAL;   
pike.git/src/las.c:498:    n->parent=res;    return res;   }      void resolv_constant(node *n)   {    struct identifier *i;    struct program *p;    INT32 numid;    +  check_tree(n,0); +     if(!n)    {    push_int(0);    }else{    switch(n->token)    {    case F_CONSTANT:    push_svalue(& n->u.sval);    return;   
pike.git/src/las.c:555:    i->func.offset);    }else{    yyerror("Identifier is not a constant");    push_int(0);    }    }   }      void resolv_program(node *n)   { +  check_tree(n,0); +     resolv_constant(n);    switch(sp[-1].type)    {    case T_OBJECT:    if(!sp[-1].u.object->prog)    {    pop_stack();    push_int(0);    }else{    f_object_program(1);
pike.git/src/las.c:588:    break;    }   }            node *index_node(node *n, struct pike_string * id)   {    node *ret;    JMP_BUF tmp; +  +  check_tree(n,0); +     if(SETJMP(tmp))    {    ONERROR tmp;    SET_ONERROR(tmp,exit_on_error,"Error in handle_error in master object!");    assign_svalue_no_free(sp++, & throw_value);    APPLY_MASTER("handle_error", 1);    pop_stack();    UNSET_ONERROR(tmp);       yyerror("Couldn't index module.");
pike.git/src/las.c:637:    }    UNSETJMP(tmp);    ret=mkconstantsvaluenode(sp-1);    pop_stack();    return ret;   }         int node_is_eq(node *a,node *b)   { +  check_tree(a,0); +  check_tree(b,0); +     if(a == b) return 1;    if(!a || !b) return 0;    if(a->token != b->token) return 0;       switch(a->token)    {    case F_LOCAL:    case F_IDENTIFIER:    return a->u.number == b->u.number;   
pike.git/src/las.c:730:   }         /* these routines operates on parsetrees and are mostly used by the    * optimizer    */      node *copy_node(node *n)   {    node *b; +  check_tree(n,0);    if(!n) return n;    switch(n->token)    {    case F_LOCAL:    case F_IDENTIFIER:    b=mkintnode(0);    *b=*n;    copy_shared_string(b->type, n->type);    return b;   
pike.git/src/las.c:982:    if(car_is_node(foo) && cdr_is_node(foo))    putchar(',');    if(cdr_is_node(foo)) low_print_tree(CDR(foo),0);    printf(")");    return;    }   }      void print_tree(node *n)   { +  check_tree(n,0);    low_print_tree(n,0);    printf("\n");    fflush(stdout);   }         /* The following routines needs much better commenting */   struct used_vars   {    int err;
pike.git/src/las.c:1533:    (CDR(n)->tree_info & OPT_TRY_OPTIMIZE) &&    CDR(n)->token != ':')    {    CDR(n) = eval(CDR(n));    if(CDR(n)) CDR(n)->parent = n;    zapp_try_optimize(CDR(n)); /* avoid infinite loops */    continue;    }    }    fix_type_field(n); +  debug_malloc_touch(n->type);      #ifdef DEBUG    if(l_flag > 3 && n)    {    fprintf(stderr,"Optimizing (tree info=%x):",n->tree_info);    print_tree(n);    }   #endif       switch(n->token)
pike.git/src/las.c:2146:      int dooptcode(struct pike_string *name,    node *n,    struct pike_string *type,    int modifiers)   {    union idptr tmp;    int args, vargs, ret;    struct svalue *foo;    +  check_tree(n,0); +    #ifdef DEBUG    if(a_flag > 1)    fprintf(stderr,"Doing function '%s' at %x\n",name->str,PC);   #endif       args=count_arguments(type);    if(args < 0)    {    args=~args;    vargs=IDENTIFIER_VARARGS;