pike.git / src / pike_types.c

version» Context lines:

pike.git/src/pike_types.c:317:    return ba_alloc(&type_allocator);   }      PMOD_EXPORT void count_memory_in_pike_types(size_t *n, size_t *s) {    ba_count_all(&type_allocator, n, s);   }      struct pike_type **pike_type_hash = NULL;   size_t pike_type_hash_size = 0;    - void debug_free_type(struct pike_type *t) + static void unlink_type(struct pike_type *t)   { - #ifdef DEBUG_MALLOC -  if (t == (struct pike_type *)(size_t)0x55555555) { -  Pike_fatal("Freeing dead type.\n"); -  } - #endif /* DEBUG_MALLOC */ -  loop: -  if (!sub_ref(t)) { +     unsigned INT32 hash = t->hash & pike_type_hash_size;    struct pike_type **t2 = pike_type_hash + hash; -  struct pike_type *car, *cdr; -  unsigned INT32 type; +    #ifdef PIKE_DEBUG    /* PIKE_DEBUG code */    if (hash > pike_type_hash_size) {    Pike_fatal("Modulo operation failed for hash:%u, index:%u, size:%u.\n",    t->hash, hash, pike_type_hash_size);    }    /* End PIKE_DEBUG code */   #endif    while (*t2) {    if (*t2 == t) {    *t2 = t->next;    break;    }    t2 = &((*t2)->next);    } -  + }    -  + void debug_free_type(struct pike_type *t) + { + #ifdef DEBUG_MALLOC +  if (t == (struct pike_type *)(size_t)0x55555555) { +  Pike_fatal("Freeing dead type.\n"); +  } + #endif /* DEBUG_MALLOC */ +  while(1) { +  struct pike_type *car, *cdr; +  unsigned INT32 type; +  const struct pike_type_def *def; +  +  if (!t || sub_ref(t)) return; +  +  unlink_type(t); +     car = t->car;    cdr = t->cdr;    type = t->type;       really_free_pike_type((struct pike_type*)debug_malloc_pass(t));    -  /* FIXME: Recursion: Should we use a stack? */ -  switch(type) { -  case T_FUNCTION: -  case T_MANY: -  case T_TUPLE: -  case T_MAPPING: -  case T_OR: -  case T_AND: -  case PIKE_T_RING: -  /* Free car & cdr */ -  free_type(car); -  t = (struct pike_type *) cdr; -  debug_free_type_preamble (t); -  goto loop; +  def = pike_type_defs[type];    -  case T_ARRAY: -  case T_MULTISET: -  case T_NOT: -  case T_TYPE: -  case T_PROGRAM: -  case T_STRING: -  /* Free car */ -  t = (struct pike_type *) car; -  debug_free_type_preamble (t); -  goto loop; -  -  case T_SCOPE: -  case T_ASSIGN: -  /* Free cdr */ -  t = (struct pike_type *) cdr; -  debug_free_type_preamble (t); -  goto loop; -  -  case PIKE_T_ATTRIBUTE: -  case PIKE_T_NAME: -  free_string((struct pike_string *)car); -  t = (struct pike_type *) cdr; -  debug_free_type_preamble (t); -  goto loop; -  +    #ifdef PIKE_DEBUG -  case '0': -  case '1': -  case '2': -  case '3': -  case '4': -  case '5': -  case '6': -  case '7': -  case '8': -  case '9': -  case T_FLOAT: -  case T_MIXED: -  case T_VOID: -  case T_ZERO: -  case PIKE_T_UNKNOWN: -  case T_INT: -  case T_OBJECT: -  break; -  -  default: +  if (!def) {    Pike_fatal("free_type(): Unhandled type-node: %d\n", type); -  break; +  }   #endif /* PIKE_DEBUG */ -  +  +  if (def->free_type_car) { +  (def->free_type_car)(car);    } -  +  +  if (def->free_type_cdr) { +  (def->free_type_cdr)(cdr);    } -  +  +  /* FIXME: Recursion: Should we use a stack? */ +  switch(def->flags) { +  case TYPE_FLAG_IS_LEAF: +  return; +  case TYPE_FLAG_CAR_IS_TYPE: +  t = car; +  debug_free_type_preamble(t); +  continue; +  case TYPE_FLAG_BOTH_ARE_TYPES: +  if (car) { +  if (!cdr) { +  t = car; +  debug_free_type_preamble(t); +  continue;    } -  +  free_type(car); +  } +  /* FALL_THROUGH */ +  case TYPE_FLAG_CDR_IS_TYPE: +  t = cdr; +  debug_free_type_preamble(t); +  continue; +  } +  } + }      static inline struct pike_type *debug_mk_type(unsigned INT32 type,    struct pike_type *car,    struct pike_type *cdr,    int flag_method)   {    /* FIXME: The hash ought to be based on the tree contents, regardless    * of what the adresses of the type nodes are.    */    struct pike_type *t;
pike.git/src/pike_types.c:521: Inside #if defined(PIKE_EXTRA_DEBUG)
   " t->cdr: %p (%p)\n"    " t->next:%p\n",    t->type, get_name_of_type(t->type),    t->car, car,    t->cdr, cdr,    t->next);    }   #endif /* PIKE_EXTRA_DEBUG */    if ((t->hash == hash) && (t->type == type) &&    (t->car == car) && (t->cdr == cdr)) { -  /* Free car & cdr as appropriate. */ -  switch(type) { -  case T_FUNCTION: -  case T_MANY: -  case T_TUPLE: -  case T_MAPPING: -  case T_OR: -  case T_AND: -  case PIKE_T_RING: -  /* Free car & cdr */ -  free_type((struct pike_type *)debug_malloc_pass(car)); -  free_type((struct pike_type *)debug_malloc_pass(cdr)); -  break; -  -  case T_ARRAY: -  case T_MULTISET: -  case T_NOT: -  case T_TYPE: -  case T_PROGRAM: -  case T_STRING: -  /* Free car */ -  free_type((struct pike_type *)debug_malloc_pass(car)); -  break; -  -  case T_SCOPE: -  case T_ASSIGN: -  /* Free cdr */ -  free_type((struct pike_type *)debug_malloc_pass(cdr)); -  break; -  -  case PIKE_T_ATTRIBUTE: -  case PIKE_T_NAME: -  free_string((struct pike_string *)debug_malloc_pass(car)); -  free_type((struct pike_type *)debug_malloc_pass(cdr)); -  break; +  /* Found! -- Free car & cdr as appropriate. */ +  const struct pike_type_def *def = pike_type_defs[type];   #ifdef PIKE_DEBUG -  case '0': -  case '1': -  case '2': -  case '3': -  case '4': -  case '5': -  case '6': -  case '7': -  case '8': -  case '9': -  case T_FLOAT: -  case T_MIXED: -  case T_VOID: -  case T_ZERO: -  case PIKE_T_UNKNOWN: -  case T_INT: -  case T_OBJECT: -  break; -  -  default: +  if (!def) {    Pike_fatal("mk_type(): Unhandled type-node: %d\n", type); -  break; +  }   #endif /* PIKE_DEBUG */ -  +  if (def->free_type_car) { +  def->free_type_car(car);    } -  +  if (def->free_type_cdr) { +  def->free_type_cdr(cdr); +  } +  if (def->flags & TYPE_FLAG_CAR_IS_TYPE) { +  free_type(car); +  } +  if (def->flags & TYPE_FLAG_CDR_IS_TYPE) { +  free_type(cdr); +  }    add_ref((struct pike_type *)debug_malloc_pass(t));    return t;    }    }      #ifdef PIKE_DEBUG    if ((type == T_OR) && (car->type == T_OR)) {    Pike_fatal("Invalid CAR to OR node.\n");    }   #endif
pike.git/src/pike_types.c:8814:   /* Marker */      static const struct pike_type_def pike_marker_type_def = {    .flags = TYPE_FLAG_IS_LEAF,   };      /* Attribute */      static const struct pike_type_def pike_attribute_type_def = {    .flags = TYPE_FLAG_CDR_IS_TYPE, +  .free_type_car = (void (*)(void *))do_free_string,   };      /* Ring */      static const struct pike_type_def pike_ring_type_def = {    .flags = TYPE_FLAG_BOTH_ARE_TYPES,   };      /* Name */      static const struct pike_type_def pike_name_type_def = {    .flags = TYPE_FLAG_CDR_IS_TYPE, -  +  .free_type_car = (void (*)(void *))do_free_string,   };      /* Scope */      static const struct pike_type_def pike_scope_type_def = {    .flags = TYPE_FLAG_CDR_IS_TYPE,   };      /* Tuple */