bool opt_verbose = false;
+#define HIST_MAX_US 1000000
+#define HIST_RES_US 10
+
+struct histogram {
+ unsigned cnt[(HIST_MAX_US+1)/HIST_RES_US];
+ unsigned max;
+};
+
+/* static void hist_init(struct histogram *h) */
+/* { */
+/* memset(h, 0, sizeof(*h)); */
+/* } */
+
+static void hist_add(struct histogram *h, int us)
+{
+ assert(us > 0);
+ if (us > HIST_MAX_US)
+ us = HIST_MAX_US;
+ __sync_fetch_and_add(&h->cnt[us/HIST_RES_US], 1);
+
+ unsigned max;
+ do {
+ max = h->max;
+ } while (us > max && ! __sync_bool_compare_and_swap(&h->max, max, us));
+
+}
+
+static unsigned hist_get_percentile(struct histogram *h, unsigned p)
+{
+ uint64_t sum = 0, psum;
+ int i;
+ for (i=0; i<(HIST_MAX_US+1)/HIST_RES_US; i++)
+ sum += h->cnt[i];
+
+ psum = sum * p / 100;
+ sum = 0;
+ for (i=0; i<(HIST_MAX_US+1)/HIST_RES_US; i++) {
+ sum += h->cnt[i];
+ if (sum >= psum)
+ break;
+ }
+ return i*HIST_RES_US;
+}
+
struct stats {
-
+ uint32_t sent;
+ uint32_t received;
+ uint32_t lost;
} stats;
+struct histogram hist;
+
void set_rt_prio(int priority)
{
int maxpri, minpri;
return ts2d(&r);
}
+static inline int tsdiff2us(struct timespec *x,
+ struct timespec *y)
+{
+ struct timespec r;
+ timespec_subtract(&r, x, y);
+ return r.tv_sec*1000000 + r.tv_nsec/1000;
+}
+
struct msg {
int cnt;
struct timespec ts;
ret = frsh_receive_sync(epdst, msg, rp->budget, &mlen, NULL);
clock_gettime(CLOCK_MONOTONIC, &tsr);
tss = msg->ts;
- if (msg->cnt != last_cnt+1)
+ if (msg->cnt != last_cnt+1) {
printf("%3d: packet(s) lost!\n", rp->id);
+ __sync_fetch_and_add(&stats.lost, msg->cnt - last_cnt+1);
+ } else {
+ hist_add(&hist, tsdiff2us(&tsr, &tss));
+ __sync_fetch_and_add(&stats.received, 1);
+ }
if (opt_verbose)
printf("%3d: %10d: %10.3lf ms\n",
rp->id, msg->cnt, tsdiff2d(&tsr, &tss)*1000);
ret = frsh_send_sync(epsrc, msg, p->budget);
clock_gettime(CLOCK_MONOTONIC, &next_period);
}
+ __sync_fetch_and_add(&stats.sent, 1);
next_period.tv_sec += (p->period_ms/1000);
next_period.tv_nsec += (p->period_ms%1000) * 1000000;
if (next_period.tv_nsec >= 1000000000) {
return NULL;
}
+void print_stat(bool full)
+{
+ printf("Sent: %5d Received: %5d Lost: %5d Max: %6.3f ms",
+ stats.sent, stats.received, stats.lost, hist.max/1000.0);
+ if (full) {
+ printf(" Max: %6.3f ms 90%%: %6.3f ms",
+ hist_get_percentile(&hist, 100)/1000.0,
+ hist_get_percentile(&hist, 90)/1000.0);
+ }
+ printf("\r");
+ fflush(stdout);
+}
+
int main(int argc, char *argv[])
{
int ret;
}
} while(ret == 0);
+ while (!exit_flag) {
+ int v;
+ print_stat(false);
+ sem_getvalue(&finished, &v);
+ if (v == num)
+ break;
+ usleep(100000);
+ }
+
while (num--)
sem_wait(&finished);
+
+ print_stat(true);
+ printf("\n");
return 0;
}