Exemplo n.º 1
0
// Invoke timers
static void
timer_dispatch(void)
{
    struct timespec tru = timer_repeat_until;
    for (;;) {
        // Run the next software timer
        uint32_t next = sched_timer_dispatch();
        struct timespec nt = timespec_from_time(next);

        struct timespec now = timespec_read();
        if (!timespec_is_before(nt, timespec_add(now, TIMER_MIN_TRY_NS))) {
            // Schedule next timer normally.
            next_wake_time = nt;
            return;
        }

        if (unlikely(timespec_is_before(tru, now))) {
            // Check if there are too many repeat timers
            if (unlikely(timespec_is_before(timespec_add(nt, 100000000), now)))
                try_shutdown("Rescheduled timer in the past");
            if (sched_tasks_busy()) {
                timer_repeat_until = timespec_add(now, TIMER_REPEAT_NS);
                next_wake_time = timespec_add(now, TIMER_DEFER_REPEAT_NS);
                return;
            }
            timer_repeat_until = timespec_add(now, TIMER_IDLE_REPEAT_NS);
        }

        // Next timer in the past or near future - wait for it to be ready
        while (unlikely(timespec_is_before(now, nt)))
            now = timespec_read();
    }
}
Exemplo n.º 2
0
// Check if a given time has past
int
timer_check_periodic(struct timespec *ts)
{
    if (timespec_is_before(next_wake_time, *ts))
        return 0;
    *ts = next_wake_time;
    ts->tv_sec += 2;
    return 1;
}
Exemplo n.º 3
0
int pfring_bundle_read(pfring_bundle *bundle,
		       u_char** buffer, u_int buffer_len,
		       struct pfring_pkthdr *hdr,
		       u_int8_t wait_for_incoming_packet) {
  int i, sock_id = -1, found, rc, empty_rings, scans;
  struct timespec ts = { 0 };
  struct timespec tmpts;
  u_int8_t founds[32] = { 0 };

redo_pfring_bundle_read:

  switch(bundle->policy) {
  case pick_round_robin:
    for(i=0; i<bundle->num_sockets; i++) {
      rc = pfring_recv(bundle->sockets[bundle->last_read_socket], buffer, buffer_len, hdr, 0);
      if(++bundle->last_read_socket == bundle->num_sockets) bundle->last_read_socket = 0;
      if(rc > 0) return(rc);
    }
    break;

  case pick_fifo:
    found = 0;
    empty_rings = 0;
    scans = 0;

  sockets_scan:
    scans++;
    for(i=0; i<bundle->num_sockets; i++) {
      if(founds[i] == 0) {
	pfring *ring = bundle->sockets[i];

	rc = pfring_next_pkt_time(ring, &tmpts);

	if(rc == 0) {
	  if(!found || timespec_is_before(&tmpts, &ts)) {
	    memcpy(&ts, &tmpts, sizeof(struct timespec));
	    found = 1, founds[i] = 1;
	    sock_id = i;
	  }
	} else if (rc == PF_RING_ERROR_NO_PKT_AVAILABLE) {
	  empty_rings = 1;
	} else {
	  /* error */
	}
      }
    }

    if(found) {
#ifdef EXTRA_SAFE
      if(empty_rings && (scans == 1))
        goto sockets_scan; /* scanning ring twice (safety check) */
#endif

      return(pfring_recv(bundle->sockets[sock_id], buffer, buffer_len, hdr, 0));
    }
    break;
  }

  if(wait_for_incoming_packet) {
    rc = pfring_bundle_poll(bundle, bundle->sockets[0]->poll_duration);

    if(rc > 0) goto redo_pfring_bundle_read;
    else return(rc);
  }

  return(0);
}
Exemplo n.º 4
0
void
irq_poll(void)
{
    if (!timespec_is_before(timespec_read(), next_wake_time))
        timer_dispatch();
}