Implement an upper limit for packets per second sent by node.

This commit is contained in:
Gleb Smirnoff 2005-12-23 19:14:38 +00:00
parent cd34c8b6a2
commit 7223585771
Notes: svn2git 2020-12-20 02:59:44 +00:00
svn path=/head/; revision=153690
3 changed files with 53 additions and 5 deletions

View File

@ -32,7 +32,7 @@
.\" Author: Dave Chapeskie <dchapeskie@sandvine.com>
.\" $FreeBSD$
.\"
.Dd April 5, 2005
.Dd December 5, 2005
.Dt NG_SOURCE 4
.Os
.Sh NAME
@ -175,6 +175,11 @@ hook.
.It Dv NGM_SOURCE_SETIFACE Pq Ic setiface
This message requires the name of the interface
to be configured as an argument.
.It Dv NGM_SOURCE_SETPPS Pq Ic setpps
This message requires a single
.Vt uint32_t
parameter which puts upper limit on the amount of packets
sent per second.
.El
.Sh SHUTDOWN
This node shuts down upon receipt of a

View File

@ -181,6 +181,13 @@ static const struct ng_cmdlist ng_source_cmds[] = {
&ng_parse_string_type,
NULL
},
{
NGM_SOURCE_COOKIE,
NGM_SOURCE_SETPPS,
"setpps",
&ng_parse_uint32_type,
NULL
},
{ 0 }
};
@ -350,6 +357,21 @@ ng_source_rcvmsg(node_p node, item_p item, hook_p lasthook)
}
ng_source_store_output_ifp(sc, ifname);
break;
}
case NGM_SOURCE_SETPPS:
{
uint32_t pps;
if (msg->header.arglen != sizeof(uint32_t)) {
error = EINVAL;
break;
}
pps = *(uint32_t *)msg->data;
sc->stats.maxPps = pps;
break;
}
default:
@ -548,6 +570,7 @@ ng_source_start(sc_p sc, uint64_t packets)
timevalclear(&sc->stats.elapsedTime);
timevalclear(&sc->stats.endTime);
getmicrotime(&sc->stats.startTime);
getmicrotime(&sc->stats.lastTime);
ng_callout(&sc->intr_ch, sc->node, NULL, 0,
ng_source_intr, sc, 0);
@ -593,6 +616,21 @@ ng_source_intr(node_p node, hook_p hook, void *arg1, int arg2)
} else
packets = sc->snd_queue.ifq_len;
if (sc->stats.maxPps != 0) {
struct timeval now, elapsed;
uint64_t usec;
int maxpkt;
getmicrotime(&now);
elapsed = now;
timevalsub(&elapsed, &sc->stats.lastTime);
usec = elapsed.tv_sec * 1000000 + elapsed.tv_usec;
maxpkt = (uint64_t)sc->stats.maxPps * usec / 1000000;
sc->stats.lastTime = now;
if (packets > maxpkt)
packets = maxpkt;
}
ng_source_send(sc, packets, NULL);
if (sc->packets == 0)
ng_source_stop(sc);

View File

@ -52,13 +52,15 @@
/* Statistics structure returned by NGM_SOURCE_GET_STATS */
struct ng_source_stats {
u_int64_t outOctets;
u_int64_t outFrames;
u_int32_t queueOctets;
u_int32_t queueFrames;
uint64_t outOctets;
uint64_t outFrames;
uint32_t queueOctets;
uint32_t queueFrames;
uint32_t maxPps;
struct timeval startTime;
struct timeval endTime;
struct timeval elapsedTime;
struct timeval lastTime;
};
extern const struct ng_parse_type ng_source_timeval_type;
@ -68,9 +70,11 @@ extern const struct ng_parse_type ng_source_timeval_type;
{ "outFrames", &ng_parse_uint64_type }, \
{ "queueOctets", &ng_parse_uint32_type }, \
{ "queueFrames", &ng_parse_uint32_type }, \
{ "maxPps", &ng_parse_uint32_type }, \
{ "startTime", &ng_source_timeval_type }, \
{ "endTime", &ng_source_timeval_type }, \
{ "elapsedTime", &ng_source_timeval_type }, \
{ "lastTime", &ng_source_timeval_type }, \
{ NULL } \
}
@ -83,6 +87,7 @@ enum {
NGM_SOURCE_STOP, /* stop sending queued data */
NGM_SOURCE_CLR_DATA, /* clear the queued data */
NGM_SOURCE_SETIFACE, /* configure downstream iface */
NGM_SOURCE_SETPPS, /* rate-limiting packets per second */
};
#endif /* _NETGRAPH_NG_SOURCE_H_ */