home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
ftp.ee.lbl.gov
/
2014.05.ftp.ee.lbl.gov.tar
/
ftp.ee.lbl.gov
/
acld-1.11.tar.gz
/
acld-1.11.tar
/
acld-1.11
/
stats.c
< prev
next >
Wrap
C/C++ Source or Header
|
2012-01-18
|
4KB
|
181 lines
/*
* Copyright (c) 2007, 2008, 2010, 2011, 2012
* The Regents of the University of California. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that: (1) source code distributions
* retain the above copyright notice and this paragraph in its entirety, (2)
* distributions including binary code include the above copyright notice and
* this paragraph in its entirety in the documentation or other materials
* provided with the distribution, and (3) all advertising materials mentioning
* features or use of this software display the following acknowledgement:
* ``This product includes software developed by the University of California,
* Lawrence Berkeley Laboratory and its contributors.'' Neither the name of
* the University nor the names of its contributors may be used to endorse
* or promote products derived from this software without specific prior
* written permission.
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*/
#ifndef lint
static const char rcsid[] =
"@(#) $Id: stats.c 804 2012-01-18 08:45:27Z leres $ (LBL)";
#endif
#include <sys/types.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <syslog.h>
#include "acld.h"
#include "util.h"
static long now = 0;
/* Forwards */
static int stats_bucket(struct stats *);
static void stats_now(void);
static void stats_updateptrs(struct stats *);
/* Return index to bucket defined by the specificed time */
static int
stats_bucket(struct stats *st)
{
return ((now % (st->len * st->secs)) / st->secs);
}
void
stats_free(struct stats *st)
{
if (st->buckets != NULL)
free(st->buckets);
memset(st, 0, sizeof(*st));
}
int
stats_gethiwater(struct stats *st)
{
int i, hiwater;
struct bucket *p;
if (st->buckets == NULL)
return (0);
/* Update pointers and potentially zero out stale data */
stats_updateptrs(st);
hiwater = 0;
for (i = 0, p = st->buckets; i < st->len; ++i, ++p)
if (hiwater < p->hiwater)
hiwater = p->hiwater;
return (hiwater);
}
/* Returns rate in packets/min */
int
stats_getrate(struct stats *st, const char *what)
{
int i, count, secs;
struct bucket *p;
if (st->buckets == NULL)
return (0);
/* Update pointers and potentially zero out stale data */
stats_updateptrs(st);
/*
* Calculate the seconds in current bucket plus seconds for
* the other buckets
*/
secs = ((now % (st->len * st->secs)) % st->secs) +
((st->len - 1) * st->secs);
count = 0;
for (i = 0, p = st->cur; i < st->len; ++i, ++p) {
if (p >= st->buckets + st->len)
p = st->buckets;
count += p->count;
}
lg(LOG_DEBUG, "stats_rate: %s %d/%d seconds (%d/(%d/60) == %f/min)",
what,
secs, (int)st->len * st->secs,
count, secs,
((secs == 0) ? 0.0 : (double)count / (((double)secs) / 60.0)));
return ((secs == 0) ? 0 : (count * 60) / secs);
}
/*
* Passed in the number of buckets and width in seconds of each
*/
void
stats_init(struct stats *st, size_t len, int secs, const char *what)
{
if (len < 1)
abort();
stats_free(st);
st->len = len;
st->secs = secs;
st->buckets = new(len, sizeof(*st->buckets), what);
st->cur = st->buckets;
stats_now();
st->cur += stats_bucket(st);
st->lasttime = now;
}
static void
stats_now()
{
struct timeval tv;
getts(&tv);
now = tv.tv_sec;
}
/* This gets called when an an addition is made */
void
stats_sethiwater(struct stats *st, int len)
{
/* Update pointers and potentially zero out stale data */
stats_updateptrs(st);
if (st->cur->hiwater < len)
st->cur->hiwater = len;
}
/* This gets called when a block or nullzero is added */
void
stats_setrate(struct stats *st)
{
/* Update pointers and potentially zero out stale data */
stats_updateptrs(st);
++st->cur->count;
}
static void
stats_updateptrs(struct stats *st)
{
int i;
struct bucket *p;
/* XXX if now - lasttime is big enough we should zero everything */
stats_now();
i = stats_bucket(st);
p = st->buckets + i;
while (p != st->cur) {
++st->cur;
if (st->cur >= st->buckets + st->len)
st->cur = st->buckets;
st->cur->count = 0;
st->cur->hiwater = 0;
}
st->lasttime = now;
}