예제 #1
0
/**
 * Start a new timer.
 *
 * @param relative time expressed in milliseconds
 * @param jitter expressed in percent
 * @param timer callback function
 * @param context for the callback function
 * @return a pointer to the created entry
 */
struct timer_entry *
olsr_start_timer(unsigned int rel_time,
                 uint8_t jitter_pct, bool periodical, timer_cb_func cb_func, void *context, struct olsr_cookie_info *ci)
{
  struct timer_entry *timer;

  if (ci == NULL) {
    ci = def_timer_ci;
  }
  assert(cb_func);

  timer = olsr_cookie_malloc(timer_mem_cookie);

  /*
   * Compute random numbers only once.
   */
  if (!timer->timer_random) {
    timer->timer_random = random();
  }

  /* Fill entry */
  timer->timer_clock = calc_jitter(rel_time, jitter_pct, timer->timer_random);
  timer->timer_cb = cb_func;
  timer->timer_cb_context = context;
  timer->timer_jitter_pct = jitter_pct;
  timer->timer_flags = OLSR_TIMER_RUNNING;

  /* The cookie is used for debugging to traceback the originator */
  timer->timer_cookie = ci;
  olsr_cookie_usage_incr(ci->ci_id);

  /* Singleshot or periodical timer ? */
  timer->timer_period = periodical ? rel_time : 0;

  /*
   * Now insert in the respective timer_wheel slot.
   */
  list_add_before(&timer_wheel[timer->timer_clock & TIMER_WHEEL_MASK], &timer->timer_list);

  OLSR_PRINTF(7, "TIMER: start %s timer %p firing in %s, ctx %p\n",
             ci->ci_name, timer, olsr_clock_string(timer->timer_clock), context);

  return timer;
}
예제 #2
0
파일: olsr_cookie.c 프로젝트: Dany3R9/Proj
/*
 * Allocate a fixed amount of memory based on a passed in cookie type.
 */
void *
olsr_cookie_malloc(struct olsr_cookie_info *ci)
{
  void *ptr;
  struct olsr_cookie_mem_brand *branding;
  struct list_node *free_list_node;

#ifdef OLSR_COOKIE_DEBUG
  bool reuse = false;
#endif

  /*
   * Check first if we have reusable memory.
   */
  if (!ci->ci_free_list_usage) {

    /*
     * No reusable memory block on the free_list.
     */
    ptr = calloc(1, ci->ci_size + sizeof(struct olsr_cookie_mem_brand));

    if (!ptr) {
      const char *const err_msg = strerror(errno);
      OLSR_PRINTF(1, "OUT OF MEMORY: %s\n", err_msg);
      olsr_syslog(OLSR_LOG_ERR, "olsrd: out of memory!: %s\n", err_msg);
      olsr_exit(ci->ci_name, EXIT_FAILURE);
    }
  } else {

    /*
     * There is a memory block on the free list.
     * Carve it out of the list, and clean.
     */
    free_list_node = ci->ci_free_list.next;
    list_remove(free_list_node);
    ptr = (void *)free_list_node;
    memset(ptr, 0, ci->ci_size);
    ci->ci_free_list_usage--;
#ifdef OLSR_COOKIE_DEBUG
    reuse = true;
#endif
  }

  /*
   * Now brand mark the end of the memory block with a short signature
   * indicating presence of a cookie. This will be checked against
   * When the block is freed to detect corruption.
   */
  branding = (struct olsr_cookie_mem_brand *)ARM_NOWARN_ALIGN(((unsigned char *)ptr + ci->ci_size));
  memcpy(&branding->cmb_sig, "cookie", 6);
  branding->cmb_id = ci->ci_id;

  /* Stats keeping */
  olsr_cookie_usage_incr(ci->ci_id);

#ifdef OLSR_COOKIE_DEBUG
  OLSR_PRINTF(1, "MEMORY: alloc %s, %p, %u bytes%s\n", ci->ci_name, ptr, ci->ci_size, reuse ? ", reuse" : "");
#endif

  return ptr;
}