static void test_timeval_cmp(void)
{
	static struct timeval input[] = {
		{ 0, 0 }, { 0, 0 },
		{ INT_MAX, 999999 }, { INT_MAX, 999999 },
		{ 0, 0 }, { 0, 1 },
		{ 0, 0 }, { 1, 0 },
		{ 0, 999999 }, { 1, 0 },
		{ 1, 0 }, { 1, 1 },
		{ -INT_MAX, 0 }, { INT_MAX, 0 }
	};
	static int output[] = {
		0,
		0,
		-1,
		-1,
		-1,
		-1,
		-1
	};
	unsigned int i;

	test_begin("timeval_cmp()");
	for (i = 0; i < N_ELEMENTS(input); i += 2) {
		test_assert(timeval_cmp(&input[i], &input[i+1]) == output[i/2]);
		test_assert(timeval_cmp(&input[i+1], &input[i]) == -output[i/2]);
	}
	test_end();
}
Exemplo n.º 2
0
/*
 * scamper_fds_poll
 *
 * the money function: this function polls the file descriptors held by
 * scamper.  for each fd with an event, it calls the callback registered
 * with the fd.
 */
int scamper_fds_poll(struct timeval *timeout)
{
  scamper_fd_t *fdn;
  struct timeval tv;

  /*
   * if there are fds that can be reaped, then do so.
   * if there are fds left over after, use that to guide the select timeout.
   */
  if(dlist_count(refcnt_0) > 0)
    {
      gettimeofday_wrap(&tv);

      while((fdn = (scamper_fd_t *)dlist_head_get(refcnt_0)) != NULL)
	{
	  assert(fdn->refcnt == 0);

	  if(timeval_cmp(&fdn->tv, &tv) > 0)
	    break;

	  fd_close(fdn);
	  fd_free(fdn);
	}

      if(fdn != NULL)
	{
	  timeval_diff_tv(&tv, &tv, &fdn->tv);
	  if(timeout == NULL || timeval_cmp(&tv, timeout) < 0)
	    timeout = &tv;
	}
    }

  return pollfunc(timeout);
}
Exemplo n.º 3
0
static int login_proxy_connect(struct login_proxy *proxy)
{
	struct login_proxy_record *rec;

	rec = login_proxy_state_get(proxy_state, &proxy->ip, proxy->port);
	if (timeval_cmp(&rec->last_failure, &rec->last_success) > 0 &&
	    rec->last_failure.tv_sec - rec->last_success.tv_sec > PROXY_IMMEDIATE_FAILURE_SECS &&
	    rec->num_waiting_connections != 0) {
		/* the server is down. fail immediately */
		i_error("proxy(%s): Host %s:%u is down",
			proxy->client->virtual_user, proxy->host, proxy->port);
		login_proxy_free(&proxy);
		return -1;
	}

	proxy->server_fd = net_connect_ip(&proxy->ip, proxy->port, NULL);
	if (proxy->server_fd == -1) {
		proxy_log_connect_error(proxy);
		login_proxy_free(&proxy);
		return -1;
	}
	proxy->server_io = io_add(proxy->server_fd, IO_WRITE,
				  proxy_wait_connect, proxy);
	if (proxy->connect_timeout_msecs != 0) {
		proxy->to = timeout_add(proxy->connect_timeout_msecs,
					proxy_connect_timeout, proxy);
	}

	proxy->state_rec = rec;
	proxy->state_rec->num_waiting_connections++;
	return 0;
}
Exemplo n.º 4
0
static void __agent_schedule_abs(struct ice_agent *ag, const struct timeval *tv) {
	struct timeval nxt;
	long long diff;

	if (!ag) {
		ilog(LOG_ERR, "ice ag is NULL");
		return;
	}

	nxt = *tv;

	mutex_lock(&ice_agents_timers_lock);
	if (ag->last_run.tv_sec) {
		/* make sure we don't run more often than we should */
		diff = timeval_diff(&nxt, &ag->last_run);
		if (diff < TIMER_RUN_INTERVAL * 1000)
			timeval_add_usec(&nxt, TIMER_RUN_INTERVAL * 1000 - diff);
	}
	if (ag->next_check.tv_sec && timeval_cmp(&ag->next_check, &nxt) <= 0)
		goto nope; /* already scheduled sooner */
	if (!g_tree_remove(ice_agents_timers, ag))
		obj_hold(ag); /* if it wasn't removed, we make a new reference */
	ag->next_check = nxt;
	g_tree_insert(ice_agents_timers, ag, ag);
	cond_broadcast(&ice_agents_timers_cond);
nope:
	mutex_unlock(&ice_agents_timers_lock);
}
Exemplo n.º 5
0
static void
thread_add_timer_common (struct thread_master *m, struct thread *thread)
{
#ifndef TIMER_NO_SORT
  struct thread *tt;
#endif /* TIMER_NO_SORT */

  /* Set index.  */
  thread->index = m->index;

  /* Sort by timeval. */
#ifdef TIMER_NO_SORT
  thread_list_add (&m->timer[m->index], thread);
#else
  for (tt = m->timer[m->index].tail; tt; tt = tt->prev)
    if (timeval_cmp (thread->u.sands, tt->u.sands) >= 0)
      break;

  thread_list_add_after (&m->timer[m->index], tt, thread);
#endif /* TIMER_NO_SORT */

  /* Increment timer slot index.  */
  m->index++;
  m->index %= THREAD_TIMER_SLOT;
}
Exemplo n.º 6
0
/*
 * sort_struct_cmp
 *
 * prioritise sort_struct objects for output to file.
 */
static int sort_struct_cmp(const void *va, const void *vb)
{
  const sort_struct_t *a = (const sort_struct_t *)va;
  const sort_struct_t *b = (const sort_struct_t *)vb;
  int i;

  if((i = timeval_cmp(&b->tv, &a->tv)) != 0)
    {
      return i;
    }

  /* if timestamps are identical, cycle start objects have first priority */
  if(a->type == SCAMPER_FILE_OBJ_CYCLE_START)
    {
      if(b->type == SCAMPER_FILE_OBJ_CYCLE_START) return 0;
      else return 1;
    }
  if(b->type == SCAMPER_FILE_OBJ_CYCLE_START) return -1;

  /* if timestamps are identical, cycle start objects have second priority */
  if(a->type == SCAMPER_FILE_OBJ_CYCLE_STOP)
    {
      if(b->type == SCAMPER_FILE_OBJ_CYCLE_STOP) return 0;
      else return 1;
    }
  if(b->type == SCAMPER_FILE_OBJ_CYCLE_STOP) return -1;

  return 0;
}
Exemplo n.º 7
0
 /* ? a > b */
static int pkt_slot_cmp(const void *a, const void *b)
{
	struct timeval *left = &((struct pkt_slot*)a)->ts;
	struct timeval *right = &((struct pkt_slot*)b)->ts;
	/* We compare the slots based on their (future) expiration date */
	return timeval_cmp(left, right);
}
Exemplo n.º 8
0
int
has_progress(struct progress *progress)
{
	timeval_T current_speed_after;

	timeval_from_milliseconds(&current_speed_after, CURRENT_SPD_AFTER);

	return (timeval_cmp(&progress->elapsed, &current_speed_after) >= 0);
}
Exemplo n.º 9
0
void ice_thread_run(void *p) {
	struct ice_agent *ag;
	struct call *call;
	long long sleeptime;
	struct timeval tv;

	mutex_lock(&ice_agents_timers_lock);

	while (!g_shutdown) {
		gettimeofday(&g_now, NULL);

		/* lock our list and get the first element */
		ag = g_tree_find_first(ice_agents_timers, NULL, NULL);
		/* scheduled to run? if not, we just go to sleep, otherwise we remove it from the tree,
		 * steal the reference and run it */
		if (!ag)
			goto sleep;
		if (timeval_cmp(&g_now, &ag->next_check) < 0)
			goto sleep;

		g_tree_remove(ice_agents_timers, ag);
		ZERO(ag->next_check);
		ag->last_run = g_now;
		mutex_unlock(&ice_agents_timers_lock);

		/* this agent is scheduled to run right now */

		/* lock the call */
		call = ag->call;
		log_info_ice_agent(ag);
		rwlock_lock_r(&call->master_lock);

		/* and run our checks */
		__do_ice_checks(ag);

		/* finally, release our reference and start over */
		log_info_clear();
		rwlock_unlock_r(&call->master_lock);
		obj_put(ag);
		mutex_lock(&ice_agents_timers_lock);
		continue;

sleep:
		/* figure out how long we should sleep */
		sleeptime = ag ? timeval_diff(&ag->next_check, &g_now) : 100000;
		sleeptime = MIN(100000, sleeptime); /* 100 ms at the most */
		tv = g_now;
		timeval_add_usec(&tv, sleeptime);
		cond_timedwait(&ice_agents_timers_cond, &ice_agents_timers_lock, &tv);
		continue;
	}

	mutex_unlock(&ice_agents_timers_lock);
}
Exemplo n.º 10
0
static void proxy_fail_connect(struct login_proxy *proxy)
{
	if (timeval_cmp(&proxy->created, &proxy->state_rec->last_success) < 0) {
		/* there was a successful connection done since we started
		   connecting. perhaps this is just a temporary one-off
		   failure. */
	} else {
		proxy->state_rec->last_failure = ioloop_timeval;
	}
	proxy->state_rec->num_waiting_connections--;
	proxy->state_rec = NULL;
}
Exemplo n.º 11
0
static int login_proxy_connect(struct login_proxy *proxy)
{
	struct login_proxy_record *rec = proxy->state_rec;

	/* this needs to be done early, since login_proxy_free() shrinks
	   num_waiting_connections. */
	proxy->num_waiting_connections_updated = FALSE;
	rec->num_waiting_connections++;

	if (proxy->ip.family == 0 &&
	    net_addr2ip(proxy->host, &proxy->ip) < 0) {
		client_log_err(proxy->client, t_strdup_printf(
			"proxy(%s): BUG: host %s is not an IP "
			"(auth should have changed it)",
			proxy->client->virtual_user, proxy->host));
		return -1;
	}

	if (rec->last_success.tv_sec == 0) {
		/* first connect to this IP. don't start immediately failing
		   the check below. */
		rec->last_success.tv_sec = ioloop_timeval.tv_sec - 1;
	}
	if (timeval_cmp(&rec->last_failure, &rec->last_success) > 0 &&
	    rec->last_failure.tv_sec - rec->last_success.tv_sec > PROXY_IMMEDIATE_FAILURE_SECS &&
	    rec->num_waiting_connections > 1) {
		/* the server is down. fail immediately */
		client_log_err(proxy->client, t_strdup_printf(
			"proxy(%s): Host %s:%u is down",
			proxy->client->virtual_user, proxy->host, proxy->port));
		return -1;
	}

	proxy->server_fd = net_connect_ip(&proxy->ip, proxy->port,
					  proxy->source_ip.family == 0 ? NULL :
					  &proxy->source_ip);
	if (proxy->server_fd == -1) {
		proxy_log_connect_error(proxy);
		return -1;
	}
	proxy->server_io = io_add(proxy->server_fd, IO_WRITE,
				  proxy_wait_connect, proxy);
	if (proxy->connect_timeout_msecs != 0) {
		proxy->to = timeout_add(proxy->connect_timeout_msecs,
					proxy_connect_timeout, proxy);
	}
	return 0;
}
Exemplo n.º 12
0
void timerthread_obj_schedule_abs_nl(struct timerthread_obj *tt_obj, const struct timeval *tv) {
	if (!tt_obj)
		return;

	ilog(LOG_DEBUG, "scheduling timer object at %llu.%06lu", (unsigned long long) tv->tv_sec,
			(unsigned long) tv->tv_usec);

	struct timerthread *tt = tt_obj->tt;
	if (tt_obj->next_check.tv_sec && timeval_cmp(&tt_obj->next_check, tv) <= 0)
		return; /* already scheduled sooner */
	if (!g_tree_remove(tt->tree, tt_obj))
		obj_hold(tt_obj); /* if it wasn't removed, we make a new reference */
	tt_obj->next_check = *tv;
	g_tree_insert(tt->tree, tt_obj, tt_obj);
	cond_broadcast(&tt->cond);
}
Exemplo n.º 13
0
/* Usually called from the timer callback of @progress->timer.  */
void
update_progress(struct progress *progress, off_t loaded, off_t size, off_t pos)
{
	off_t bytes_delta;
	timeval_T now, elapsed, dis_b_max, dis_b_interval;

	timeval_now(&now);
	timeval_sub(&elapsed, &progress->last_time, &now);
	timeval_copy(&progress->last_time, &now);

	progress->loaded = loaded;
	bytes_delta = progress->loaded - progress->last_loaded;
	progress->last_loaded = progress->loaded;

	timeval_add_interval(&progress->elapsed, &elapsed);

	timeval_add_interval(&progress->dis_b, &elapsed);
	timeval_from_milliseconds(&dis_b_max, mult_ms(SPD_DISP_TIME, CURRENT_SPD_SEC));
	timeval_from_milliseconds(&dis_b_interval, SPD_DISP_TIME);

	while (timeval_cmp(&progress->dis_b, &dis_b_max) >= 0) {
		progress->cur_loaded -= progress->data_in_secs[0];
		memmove(progress->data_in_secs, progress->data_in_secs + 1,
			sizeof(*progress->data_in_secs) * (CURRENT_SPD_SEC - 1));
		progress->data_in_secs[CURRENT_SPD_SEC - 1] = 0;
		timeval_sub_interval(&progress->dis_b, &dis_b_interval);
	}
	progress->data_in_secs[CURRENT_SPD_SEC - 1] += bytes_delta;
	progress->cur_loaded += bytes_delta;

	progress->current_speed = progress->cur_loaded / (CURRENT_SPD_SEC * ((long) SPD_DISP_TIME) / 1000);

	progress->pos = pos;
	progress->size = size;
	if (progress->size != -1 && progress->size < progress->pos)
		progress->size = progress->pos;

	progress->average_speed = timeval_div_off_t(progress->loaded, &progress->elapsed);
	if (progress->average_speed)	/* Division by zero risk */
		timeval_from_seconds(&progress->estimated_time,
				   (progress->size - progress->pos) / progress->average_speed);

	install_timer(&progress->timer, SPD_DISP_TIME,
		      progress_timeout, progress);
}
Exemplo n.º 14
0
void timerthread_run(void *p) {
	struct timerthread *tt = p;

	mutex_lock(&tt->lock);

	while (!rtpe_shutdown) {
		gettimeofday(&rtpe_now, NULL);

		/* lock our list and get the first element */
		struct timerthread_obj *tt_obj = g_tree_find_first(tt->tree, NULL, NULL);
		/* scheduled to run? if not, we just go to sleep, otherwise we remove it from the tree,
		 * steal the reference and run it */
		if (!tt_obj)
			goto sleep;
		if (timeval_cmp(&rtpe_now, &tt_obj->next_check) < 0)
			goto sleep;

		// steal reference
		g_tree_remove(tt->tree, tt_obj);
		ZERO(tt_obj->next_check);
		tt_obj->last_run = rtpe_now;
		mutex_unlock(&tt->lock);

		// run and release
		tt->func(tt_obj);
		obj_put(tt_obj);

		mutex_lock(&tt->lock);
		continue;

sleep:;
		/* figure out how long we should sleep */
		long long sleeptime = tt_obj ? timeval_diff(&tt_obj->next_check, &rtpe_now) : 100000;
		sleeptime = MIN(100000, sleeptime); /* 100 ms at the most */
		struct timeval tv = rtpe_now;
		timeval_add_usec(&tv, sleeptime);
		cond_timedwait(&tt->cond, &tt->lock, &tv);
	}

	mutex_unlock(&tt->lock);
}
Exemplo n.º 15
0
/* Deliver all queued packets whose timestamps have expired */
static int deliver_delayed_pkt()
{
	struct pkt_slot *p = (struct pkt_slot*)minq_peek(pkt_queue);
	/* We have a packet and its timestamp is < current time */
	while (p && timeval_cmp(&last_clock, &p->ts)) {
		/* Send it */
		if (write_out(p->buf, p->size)) {
			/* We can try again later for these errors
			 * (send bunf is full, or ...) */
			if (errno == EWOULDBLOCK || errno == EINTR || errno == EAGAIN)
				return EXIT_SUCCESS;
			/* Otherwise propagate error */
			perror("Failed to write all delayed bytes");
			return EXIT_FAILURE;
		}
		minq_pop(pkt_queue);
		free(p);
		p = (struct pkt_slot*)minq_peek(pkt_queue);
	}
	return EXIT_SUCCESS;
}
Exemplo n.º 16
0
const char *maildir_filename_generate(void)
{
	static struct timeval last_tv = { 0, 0 };
	struct timeval tv;

	/* use secs + usecs to guarantee uniqueness within this process. */
	if (timeval_cmp(&ioloop_timeval, &last_tv) > 0)
		tv = ioloop_timeval;
	else {
		tv = last_tv;
		if (++tv.tv_usec == 1000000) {
			tv.tv_sec++;
			tv.tv_usec = 0;
		}
	}
	last_tv = tv;

	return t_strdup_printf("%s.M%sP%s.%s",
			       dec2str(tv.tv_sec), dec2str(tv.tv_usec),
			       my_pid, my_hostname);
}
Exemplo n.º 17
0
static int __ice_agent_timer_cmp(const void *a, const void *b) {
	const struct ice_agent *A = a, *B = b;
	int ret;
	/* zero timevals go last */
	if (A->next_check.tv_sec == 0 && B->next_check.tv_sec != 0)
		return 1;
	if (B->next_check.tv_sec == 0 && A->next_check.tv_sec == 0)
		return -1;
	if (A->next_check.tv_sec == 0 && B->next_check.tv_sec == 0)
		goto ptr;
	/* earlier timevals go first */
	ret = timeval_cmp(&A->next_check, &B->next_check);
	if (ret)
		return ret;
	/* equal timeval, so use pointer as tie breaker */
ptr:
	if (A < B)
		return -1;
	if (A > B)
		return 1;
	return 0;
}
Exemplo n.º 18
0
Arquivo: util.c Projeto: acml/cvsnt
int wait_for_read(sock_t fd, struct timeval *end) {
    struct timeval now;

    if (end)
        gettimeofday(&now, NULL);

    for (;;) {
        struct timeval tv;
        fd_set fds;
        int r;
        
        FD_ZERO(&fds);
        FD_SET(fd, &fds);

        if (end) {
            if (timeval_cmp(&now, end) >= 0)
                return 1;
            
            tv.tv_sec = tv.tv_usec = 0;
            timeval_add(&tv, timeval_diff(end, &now));
        }
        
        if ((r = select((int)fd+1, &fds, NULL, NULL, end ? &tv : NULL)) < 0) {
            if (errno != EINTR) {
                fprintf(stderr, "select() failed: %s\n", strerror(errno));
                return -1;
            }
        } else if (r == 0) 
            return 1;
        else {
            
            if (FD_ISSET(fd, &fds))
                return 0;
        }

        if (end)
            gettimeofday(&now, NULL);
    }
}
Exemplo n.º 19
0
static int login_proxy_connect(struct login_proxy *proxy)
{
	struct login_proxy_record *rec = proxy->state_rec;

	if (rec->last_success.tv_sec == 0) {
		/* first connect to this IP. don't start immediately failing
		   the check below. */
		rec->last_success.tv_sec = ioloop_timeval.tv_sec - 1;
	}
	if (timeval_cmp(&rec->last_failure, &rec->last_success) > 0 &&
	    rec->last_failure.tv_sec - rec->last_success.tv_sec > PROXY_IMMEDIATE_FAILURE_SECS &&
	    rec->num_waiting_connections != 0) {
		/* the server is down. fail immediately */
		i_error("proxy(%s): Host %s:%u is down",
			proxy->client->virtual_user, proxy->host, proxy->port);
		login_proxy_free(&proxy);
		return -1;
	}

	proxy->server_fd = net_connect_ip(&proxy->ip, proxy->port,
					  proxy->source_ip.family == 0 ? NULL :
					  &proxy->source_ip);
	if (proxy->server_fd == -1) {
		proxy_log_connect_error(proxy);
		login_proxy_free(&proxy);
		return -1;
	}
	proxy->server_io = io_add(proxy->server_fd, IO_WRITE,
				  proxy_wait_connect, proxy);
	if (proxy->connect_timeout_msecs != 0) {
		proxy->to = timeout_add(proxy->connect_timeout_msecs,
					proxy_connect_timeout, proxy);
	}

	proxy->num_waiting_connections_updated = FALSE;
	proxy->state_rec = rec;
	proxy->state_rec->num_waiting_connections++;
	return 0;
}
Exemplo n.º 20
0
// st->stream->out_lock (or call->master_lock/W) must be held already
static int send_timer_send(struct send_timer *st, struct codec_packet *cp) {
	if (cp->to_send.tv_sec && timeval_cmp(&cp->to_send, &rtpe_now) > 0)
		return -1; // not yet

	if (!st->sink->selected_sfd)
		goto out;

	struct rtp_header *rh = (void *) cp->s.s;
	ilog(LOG_DEBUG, "Forward to sink endpoint: %s%s:%d%s (RTP seq %u TS %u)",
			FMT_M(sockaddr_print_buf(&st->sink->endpoint.address),
			st->sink->endpoint.port),
			ntohs(rh->seq_num),
			ntohl(rh->timestamp));

	socket_sendto(&st->sink->selected_sfd->socket,
			cp->s.s, cp->s.len, &st->sink->endpoint);

out:
	codec_packet_free(cp);

	return 0;
}
Exemplo n.º 21
0
/* Pick up smallest timer.  */
struct pal_timeval *
thread_timer_wait (struct thread_master *m, struct pal_timeval *timer_val)
{
  struct pal_timeval timer_now;
  struct pal_timeval timer_min;
  struct pal_timeval *timer_wait;
  struct thread *thread;
  int i;

  timer_wait = NULL;

  for (i = 0; i < THREAD_TIMER_SLOT; i++)
    if ((thread = m->timer[i].head) != NULL)
      {
        if (! timer_wait)
          timer_wait = &thread->u.sands;
        else if (timeval_cmp (thread->u.sands, *timer_wait) < 0)
          timer_wait = &thread->u.sands;
      }

  if (timer_wait)
    {
      timer_min = *timer_wait;

      pal_time_tzcurrent (&timer_now, NULL);
      timer_min = timeval_subtract (timer_min, timer_now);

      if (timer_min.tv_sec < 0)
        {
          timer_min.tv_sec = 0;
          timer_min.tv_usec = 10;
        }

      *timer_val = timer_min;
      return timer_val;
    }
  return NULL;
}
Exemplo n.º 22
0
Arquivo: util.c Projeto: acml/cvsnt
/* Calculate the difference between the two specfified timeval
 * timestamsps. */
usec_t timeval_diff(const struct timeval *a, const struct timeval *b) {
    usec_t r;
    assert(a && b);

    /* Check which whan is the earlier time and swap the two arguments if reuqired. */
    if (timeval_cmp(a, b) < 0) {
        const struct timeval *c;
        c = a;
        a = b;
        b = c;
    }

    /* Calculate the second difference*/
    r = ((usec_t) a->tv_sec - b->tv_sec)* 1000000;

    /* Calculate the microsecond difference */
    if (a->tv_usec > b->tv_usec)
        r += ((usec_t) a->tv_usec - b->tv_usec);
    else if (a->tv_usec < b->tv_usec)
        r -= ((usec_t) b->tv_usec - a->tv_usec);

    return r;
}
Exemplo n.º 23
0
int wait_for_write(int fd, struct timeval *end) {
    struct timeval now;

    if (end)
        gettimeofday(&now, NULL);
    
    for (;;) {
        struct timeval tv;
        fd_set fds;
        int r;
        
        FD_ZERO(&fds);
        FD_SET(fd, &fds);

        if (end) {
            if (timeval_cmp(&now, end) >= 0)
                return 1;

            tv.tv_sec = tv.tv_usec = 0;
            timeval_add(&tv, timeval_diff(end, &now));
        }

        if ((r = select(fd+1, NULL, &fds, NULL, end ? &tv : NULL)) < 0) {
            if (errno != EINTR)
                return -1;
        } else if (r == 0)
            return 1;
        else {
            if (FD_ISSET(fd, &fds))
                return 0;
        }

        if (end)
            gettimeofday(&now, NULL);
    }
}
Exemplo n.º 24
0
static int dealias_probe_tx_cmp(const scamper_dealias_probe_t *a,
				const scamper_dealias_probe_t *b)
{
  return timeval_cmp(&a->tx, &b->tx);
}
Exemplo n.º 25
0
void isis_pdu_runner(u_char *user, const struct pcap_pkthdr *pkthdr, const u_char *buf)
{
  struct pcap_isis_callback_data *cb_data = (struct pcap_isis_callback_data *) user;
  struct pcap_device *device = cb_data->device;
  struct isis_circuit *circuit = cb_data->circuit;
  struct packet_ptrs pptrs;
  struct thread thread;
  int ret;

  struct stream stm;
  char *ssnpa;

  /* Let's export a time reference */
  memcpy(&isis_now, &pkthdr->ts, sizeof(struct timeval));

  /* check if we have to expire adjacency first */
  if (circuit && circuit->u.p2p.neighbor) {
    if (timeval_cmp(&isis_now, &circuit->u.p2p.neighbor->expire) >= 0)
      isis_adj_expire(circuit->u.p2p.neighbor);
  }

  memset(&pptrs, 0, sizeof(pptrs));
  memset(&stm, 0, sizeof(stm));

  if (buf) {
    pptrs.pkthdr = (struct pcap_pkthdr *) pkthdr;
    pptrs.packet_ptr = (u_char *) buf;

    (*device->data->handler)(pkthdr, &pptrs);
    if (pptrs.iph_ptr) {
      if ((*pptrs.l3_handler)(&pptrs)) {

	/*assembling handover to isis_handle_pdu() */
	stm.data = pptrs.iph_ptr;
	stm.getp = 0;
	stm.endp = pkthdr->caplen - (pptrs.iph_ptr - pptrs.packet_ptr);
	stm.size = pkthdr->caplen - (pptrs.iph_ptr - pptrs.packet_ptr);
	ssnpa = pptrs.packet_ptr;
	circuit->rcv_stream = &stm;
	circuit->interface->mtu = config.nfacctd_isis_mtu;

	/* process IS-IS packet */
	isis_handle_pdu (circuit, ssnpa);
      }
    }
  }

  /* check if it's time to run SPF */
  if (timeval_cmp(&isis_now, &isis_spf_deadline) >= 0) {
    if (circuit->area->is_type & IS_LEVEL_1) {
      if (circuit->area->ip_circuits) {
	ret = isis_run_spf(circuit->area, 1, AF_INET);
	isis_route_validate_table (circuit->area, circuit->area->route_table[0]);
      }
      /* XXX: IPv6 handled here */
    }

    if (circuit->area->is_type & IS_LEVEL_2) {
      if (circuit->area->ip_circuits) {
	ret = isis_run_spf(circuit->area, 2, AF_INET);
	isis_route_validate_table (circuit->area, circuit->area->route_table[1]);
      }
      /* XXX: IPv6 handled here */
    }

    isis_route_validate_merge (circuit->area, AF_INET);

    dyn_cache_cleanup();

    isis_spf_deadline.tv_sec = isis_now.tv_sec + isis_jitter(PERIODIC_SPF_INTERVAL, 10);
    isis_spf_deadline.tv_usec = 0;
  }

  if (timeval_cmp(&isis_now, &isis_psnp_deadline) >= 0) {
    send_psnp(1, circuit);
    send_psnp(2, circuit);

    isis_psnp_deadline.tv_sec = isis_now.tv_sec + isis_jitter(PSNP_INTERVAL, PSNP_JITTER);
    isis_psnp_deadline.tv_usec = 0;
  }
}
Exemplo n.º 26
0
/* Fetch next ready thread. */
struct thread *
thread_fetch (struct lib_globals *zg, struct thread *fetch)
{
  struct thread_master *m = zg->master;
  int num;
  struct thread *thread;
  struct thread *next;
  pal_sock_set_t readfd;
  pal_sock_set_t writefd;
  pal_sock_set_t exceptfd;
  struct pal_timeval timer_now;
  struct pal_timeval timer_val;
  struct pal_timeval *timer_wait;
  struct pal_timeval timer_nowait;
  int i;

#ifdef RTOS_DEFAULT_WAIT_TIME
  /* 1 sec might not be optimized */
  timer_nowait.tv_sec = 1;
  timer_nowait.tv_usec = 0;
#else
  timer_nowait.tv_sec = 0;
  timer_nowait.tv_usec = 0;
#endif /* RTOS_DEFAULT_WAIT_TIME */

  /* Set the global VR context to PVR. */
  zg->vr_in_cxt = ipi_vr_get_privileged(zg);

  while (1)
    {
      /* Pending read is exception. */
      if ((thread = thread_trim_head (&m->read_pend)) != NULL)
        return thread_run (m, thread, fetch);

      /* Check ready queue.  */
      if ((thread = thread_trim_head (&m->queue_high)) != NULL)
        return thread_run (m, thread, fetch);

      if ((thread = thread_trim_head (&m->queue_middle)) != NULL)
        return thread_run (m, thread, fetch);

      if ((thread = thread_trim_head (&m->queue_low)) != NULL)
        return thread_run (m, thread, fetch);

      /* Check all of available events.  */

      /* Check events.  */
      while ((thread = thread_trim_head (&m->event)) != NULL)
        thread_enqueue_high (m, thread);

      /* Check timer.  */
      pal_time_tzcurrent (&timer_now, NULL);

      for (i = 0; i < THREAD_TIMER_SLOT; i++)
        for (thread = m->timer[i].head; thread; thread = next)
          {
            next = thread->next;
            if (timeval_cmp (timer_now, thread->u.sands) >= 0)
              {
                thread_list_delete (&m->timer[i], thread);
                thread_enqueue_middle (m, thread);
              }
#ifndef TIMER_NO_SORT
            else
              break;
#endif /* TIMER_NO_SORT */
          }

      /* Structure copy.  */
      readfd = m->readfd;
      writefd = m->writefd;
      exceptfd = m->exceptfd;

      /* Check any thing to be execute.  */
      if (m->queue_high.head || m->queue_middle.head || m->queue_low.head)
        timer_wait = &timer_nowait;
      else
        timer_wait = thread_timer_wait (m, &timer_val);

      /* First check for sockets.  Return immediately.  */
      num = pal_sock_select (m->max_fd + 1, &readfd, &writefd, &exceptfd,
                             timer_wait);

      /* Error handling.  */
      if (num < 0)
        {
          if (errno == EINTR)
            continue;
          return NULL;
        }

      /* File descriptor is readable/writable.  */
      if (num > 0)
        {
          /* High priority read thead. */
          thread_process_fd (m, &m->read_high, &readfd, &m->readfd);

          /* Normal priority read thead. */
          thread_process_fd (m, &m->read, &readfd, &m->readfd);

          /* Write thead. */
          thread_process_fd (m, &m->write, &writefd, &m->writefd);
        }

      /* Low priority events. */
      if ((thread = thread_trim_head (&m->event_low)) != NULL)
        thread_enqueue_low (m, thread);
    }
}
Exemplo n.º 27
0
/* call must be locked R or W, agent must not be locked */
static void __do_ice_checks(struct ice_agent *ag) {
	GList *l;
	struct ice_candidate_pair *pair, *highest = NULL, *frozen = NULL, *valid;
	struct packet_stream *ps;
	GQueue retransmits = G_QUEUE_INIT;
	struct timeval next_run = {0,0};
	int have_more = 0;

	if (!ag) {
		ilog(LOG_ERR, "ice ag is NULL");
		return;
	}

	if (!ag->pwd[0].s)
		return;

	atomic64_set(&ag->last_activity, poller_now);

	__DBG("running checks, call "STR_FORMAT" tag "STR_FORMAT"", STR_FMT(&ag->call->callid),
			STR_FMT(&ag->media->monologue->tag));

	mutex_lock(&ag->lock);

	/* check if we're done and should start nominating pairs */
	if (AGENT_ISSET(ag, CONTROLLING) && !AGENT_ISSET(ag, NOMINATING) && ag->start_nominating.tv_sec) {
		if (timeval_cmp(&g_now, &ag->start_nominating) >= 0)
			__nominate_pairs(ag);
		timeval_lowest(&next_run, &ag->start_nominating);
	}

	/* triggered checks are preferred */
	pair = g_queue_pop_head(&ag->triggered);
	if (pair) {
		PAIR_CLEAR(pair, TRIGGERED);
		next_run = g_now;
		goto check;
	}

	/* find the highest-priority non-frozen non-in-progress pair */
	for (l = ag->all_pairs_list.head; l; l = l->next) {
		pair = l->data;

		/* skip dead streams */
		ps = pair->packet_stream;
		if (!ps || !ps->sfd)
			continue;
		if (PAIR_ISSET(pair, FAILED))
			continue;
		if (PAIR_ISSET(pair, SUCCEEDED) && !PAIR_ISSET(pair, TO_USE))
			continue;

		valid = __get_pair_by_component(ag->valid_pairs, pair->remote_candidate->component_id);

		if (PAIR_ISSET(pair, IN_PROGRESS)) {
			/* handle retransmits */
			/* but only if our priority is lower than any valid pair */
			if (valid && valid->pair_priority > pair->pair_priority)
				continue;

			if (timeval_cmp(&pair->retransmit, &g_now) <= 0)
				g_queue_push_tail(&retransmits, pair); /* can't run check directly
									  due to locks */
			else
				timeval_lowest(&next_run, &pair->retransmit);
			continue;
		}

		/* don't do anything else if we already have a valid pair */
		if (valid)
			continue;
		/* or if we're in or past the final phase */
		if (AGENT_ISSET2(ag, NOMINATING, COMPLETED))
			continue;

		have_more = 1;

		/* remember the first frozen pair in case we find nothing else */
		if (PAIR_ISSET(pair, FROZEN)) {
			if (!frozen)
				frozen = pair;
			continue;
		}

		if (!highest)
			highest = pair;
	}

	if (highest)
		pair = highest;
	else if (frozen)
		pair = frozen;
	else
		pair = NULL;

check:
	mutex_unlock(&ag->lock);

	if (pair)
		__do_ice_check(pair);

	while ((pair = g_queue_pop_head(&retransmits)))
		__do_ice_check(pair);


	/* determine when to run next */
	if (have_more)
		__agent_schedule(ag, 0);
	else if (next_run.tv_sec)
		__agent_schedule_abs(ag, &next_run); /* for retransmits */
}
Exemplo n.º 28
0
void writeToSessionFile(struct session_entry *sesh_entry)
{
	//writes session entry to file, rectifies any ties
	
	printf("\t\tWriting session key to file...\n");
	FILE* fp;
	fp= fopen("/tmp/sesh_keys","r");
	int file_exists=1;
	if(fp==NULL){
		file_exists=0;
	}	
	//first check for existing session for this host
	struct session_entry *line=malloc(sizeof(struct session_entry));
	struct session_entry *file_entry=NULL;
	
	int line_index = 0;
	int foundDup = 0;
	if(file_exists){
	   while (!feof(fp)) {
			fread(line, sizeof(struct session_entry), 1, fp);
			file_entry = (struct session_entry*) line;
			
			if (file_entry->host_id == sesh_entry->host_id)
			{
		//		printf("\tAlready have an entry for host %hu...\n",sesh_entry->host_id);
				//got a match, check timestamps.
				if (timeval_cmp(&(sesh_entry->timestamp),&(file_entry->timestamp)) ==-1)
				{
					fclose(fp);
		//			printf("\tCurrent entry is newer, not going to overwrite\n");
					return; //keep entry in file
				}
				else if (timeval_cmp(&(sesh_entry->timestamp),&(file_entry->timestamp)) == 1)
				{
					foundDup = 1;
		//			printf("\tCurrent entry is older, going to overwrite it\n");
					break; //we will assume there weren't TWO duplicates, because then something is wrong
				}
				else
				{
					printf("\tTimestamps are the same. This shouldn't happen!!\n");
					//check first 4 bytes of sesh_entry. very unlikely they will be equal
					if (memcmp((sesh_entry->sym_key),file_entry->sym_key,sizeof(file_entry->sym_key)) > 0)
					{
						fclose(fp);
						return; //keep entry in file
					}
					else if (memcmp((sesh_entry->sym_key),file_entry->sym_key,sizeof(file_entry->sym_key)) < 0)
					{
						foundDup = 1;
						break; //we will assume there weren't TWO duplicates, because then something is wrong
					}
					else
					{
						printf("\nDuplicate error. Session already was in file with same timestamp and key\n");
						fclose(fp);
						return;
					}
				}
			}
			else
			{
				line_index++;
			}
	    }
	}
	if(fp!=NULL){
		fclose(fp);
	}
	
	if (!foundDup)
	{
		//append sesh_entry to end of file
	//	printf("\tAppending to session keys file\n");
		FILE *append_sesh_file;
		append_sesh_file = fopen("/tmp/sesh_keys", "a+");
		int bytes_written=fwrite(sesh_entry, sizeof(char),sizeof(struct session_entry), append_sesh_file);
		if(bytes_written<0){
			printf("Error writing to sesh_keys file");
		}
		fclose(append_sesh_file);
		return;
	}
	
	
	//now delete and replace with sesh entry, unless there was a 'better' existing version in the file
//	printf("\tReplacing session key...\n");	
	fp = fopen("/tmp/sesh_keys", "r+");
	if(fp==NULL){
		printf("Error opening session keys file to replace\n");
	}
	//fseek to line where we found duplicate to replace
	fseek(fp,line_index*sizeof(struct session_entry),SEEK_SET);
	fwrite(sesh_entry,sizeof(char),sizeof(struct session_entry),fp);
	fclose(fp);
	free(line);
	
//	printf("\tReplaced duplicate for host %d\n",sesh_entry->host_id);
	return;
}
Exemplo n.º 29
0
int scamper_dealias_radargun_fudge(scamper_dealias_t *dealias,
				   scamper_dealias_probedef_t *def,
				   scamper_dealias_probedef_t **defs, int *cnt,
				   int fudge)
{
  scamper_dealias_radargun_t *rg = dealias->data;
  scamper_dealias_probe_t *pr, *pr_a, *pr_b;
  scamper_dealias_reply_t *re, *re_a, *re_b, *re_c;
  dealias_resolv_t *dr = NULL;
  dealias_resolv_t *drd;
  uint32_t pid, x;
  int i, j, k, bs, inseq, d = 0;

  if(dealias->method != SCAMPER_DEALIAS_METHOD_RADARGUN)
    goto err;

  if((dr = malloc_zero(sizeof(dealias_resolv_t) * rg->probedefc)) == NULL)
    goto err;

  for(x=0; x<dealias->probec; x++)
    {
      pr = dealias->probes[x];
      pid = pr->def->id;

      /*
       * if this probedef has already been determined to be useless for
       * alias resolution, skip it
       */
      if(dr[pid].probec < 0)
	continue;

      if(pr->replyc > 1)
	{
	  if(dr[pid].probes != NULL)
	    free(dr[pid].probes);
	  dr[pid].probec = -1;

	  if(pr->def == def)
	    goto done;
	  continue;
	}

      /* total number of probes transmitted */
      dr[pid].probet++;

      if(pr->replyc == 0)
	continue;

      re = pr->replies[0];

      /*
       * with three replies, do some basic checks to see if we should
       * continue considering this probedef.
       */
      if(dr[pid].probec == 2)
	{
	  pr_a = dr[pid].probes[0];
	  pr_b = dr[pid].probes[1];
	  re_a = pr_a->replies[0];
	  re_b = pr_b->replies[0];

	  if((re->ipid == pr->ipid && re_a->ipid == pr_a->ipid &&
	      re_b->ipid == pr_b->ipid) ||
	     (re->ipid == re_a->ipid && re->ipid == re_b->ipid))
	    {
	      free(dr[pid].probes);
	      dr[pid].probec = -1;

	      if(pr->def == def)
		goto done;
	      continue;
	    }
	}

      if(array_insert((void ***)&dr[pid].probes,&dr[pid].probec,pr,NULL) != 0)
	goto err;
    }

  /* figure out if we should byteswap the ipid sequence */
  if(dr[def->id].probec < 3)
    goto done;
  re_a = dr[def->id].probes[0]->replies[0];
  re_b = dr[def->id].probes[1]->replies[0];
  re_c = dr[def->id].probes[2]->replies[0];
  if(re_a->ipid < re_b->ipid)
    i = re_b->ipid - re_a->ipid;
  else
    i = 0x10000 + re_b->ipid - re_a->ipid;
  if(re_b->ipid < re_c->ipid)
    i += re_c->ipid - re_b->ipid;
  else
    i += 0x10000 + re_c->ipid - re_b->ipid;
  if(byteswap16(re_a->ipid) < byteswap16(re_b->ipid))
    j = byteswap16(re_b->ipid) - byteswap16(re_a->ipid);
  else
    j = 0x10000 + byteswap16(re_b->ipid) - byteswap16(re_a->ipid);
  if(byteswap16(re_b->ipid) < byteswap16(re_c->ipid))
    j += byteswap16(re_c->ipid) - byteswap16(re_b->ipid);
  else
    j += 0x10000 + byteswap16(re_c->ipid) - byteswap16(re_b->ipid);
  if(i < j)
    bs = 0;
  else
    bs = 1;

  /* for each probedef, consider if it could be an alias */
  drd = &dr[def->id]; d = 0;
  for(pid=0; pid<rg->probedefc; pid++)
    {
      if(&rg->probedefs[pid] == def || dr[pid].probec < 3)
	continue;

      j = 0; k = 0;

      /* get the first ipid */
      if(timeval_cmp(&drd->probes[j]->tx, &dr[pid].probes[k]->tx) < 0)
	pr_a = drd->probes[j++];
      else
	pr_a = dr[pid].probes[k++];

      for(;;)
	{
	  if(timeval_cmp(&drd->probes[j]->tx, &dr[pid].probes[k]->tx) < 0)
	    pr_b = drd->probes[j++];
	  else
	    pr_b = dr[pid].probes[k++];

	  if((inseq = dealias_fudge_inseq(pr_a, pr_b, bs, fudge)) == 0)
	    break;

	  if(j == drd->probec || k == dr[pid].probec)
	    break;
	}

      /*
       * if the pairs do not appear to have insequence IP-ID values, then
       * abandon
       */
      if(inseq == 0)
	continue;

      defs[d++] = &rg->probedefs[pid];
      if(d == *cnt)
	break;
    }

 done:
  *cnt = d;
  for(x=0; x<rg->probedefc; x++)
    if(dr[x].probec > 0)
      free(dr[x].probes);
  return 0;

 err:
  if(dr != NULL)
    {
      for(x=0; x<rg->probedefc; x++)
	if(dr[x].probec > 0)
	  free(dr[x].probes);
    }
  return -1;
}
Exemplo n.º 30
0
static int multimeter_read_value(double *value) {
  int retry = 3; /* sometimes we receive garbadge */

  do {
    struct timeval time_end;

    tcflush(fd, TCIFLUSH);

    if (gettimeofday(&time_end, NULL) < 0) {
      char errbuf[1024];
      ERROR("multimeter plugin: gettimeofday failed: %s",
            sstrerror(errno, errbuf, sizeof(errbuf)));
      return -1;
    }
    time_end.tv_sec++;

    while (1) {
      char buf[LINE_LENGTH];
      char *range;
      int status;
      fd_set rfds;
      struct timeval timeout;
      struct timeval time_now;

      status = swrite(fd, "D", 1);
      if (status < 0) {
        ERROR("multimeter plugin: swrite failed.");
        return -1;
      }

      FD_ZERO(&rfds);
      FD_SET(fd, &rfds);

      if (gettimeofday(&time_now, NULL) < 0) {
        char errbuf[1024];
        ERROR("multimeter plugin: "
              "gettimeofday failed: %s",
              sstrerror(errno, errbuf, sizeof(errbuf)));
        return -1;
      }
      if (timeval_cmp(time_end, time_now, &timeout) < 0)
        break;

      status = select(fd + 1, &rfds, NULL, NULL, &timeout);

      if (status > 0) /* usually we succeed */
      {
        status = read(fd, buf, LINE_LENGTH);

        if ((status < 0) && ((errno == EAGAIN) || (errno == EINTR)))
          continue;

        /* Format: "DC 00.000mV  \r" */
        if (status > 0 && status == LINE_LENGTH) {
          *value = strtod(buf + 2, &range);

          if (range > (buf + 6)) {
            range = buf + 9;

            switch (*range) {
            case 'p':
              *value *= 1.0E-12;
              break;
            case 'n':
              *value *= 1.0E-9;
              break;
            case 'u':
              *value *= 1.0E-6;
              break;
            case 'm':
              *value *= 1.0E-3;
              break;
            case 'k':
              *value *= 1.0E3;
              break;
            case 'M':
              *value *= 1.0E6;
              break;
            case 'G':
              *value *= 1.0E9;
              break;
            }
          } else
            return -1; /* Overflow */

          return 0; /* value received */
        } else
          break;
      } else if (!status) /* Timeout */
      {
        break;
      } else if ((status == -1) && ((errno == EAGAIN) || (errno == EINTR))) {
        continue;
      } else /* status == -1 */
      {
        char errbuf[1024];
        ERROR("multimeter plugin: "
              "select failed: %s",
              sstrerror(errno, errbuf, sizeof(errbuf)));
        break;
      }
    }
  } while (--retry);

  return -2; /* no value received */
} /* int multimeter_read_value */