Re: [Netem] [PATCH] (3/3) netem: allow random reordering
From: Stephen Hemminger <hidden>
Date: 2005-05-23 17:25:17
On Fri, 20 May 2005 20:28:40 +0000 Julio Kriger [off-list ref] wrote:
Hi! How do I use this feature? Shouldn't tc be modified to accept this new feature? Regards, Julio
Use this (it will be in the next version of iproute2). Also, you need to specify a delay because that is how netem does the reordering. diff -X dontdiff -urN iproute2-2.6.11-050330/include/linux/pkt_sched.h iproute2-netem/include/linux/pkt_sched.h
--- iproute2-2.6.11-050330/include/linux/pkt_sched.h 2005-04-01 11:58:11.000000000 -0800
+++ iproute2-netem/include/linux/pkt_sched.h 2005-05-04 11:31:14.000000000 -0700@@ -427,6 +427,7 @@ TCA_NETEM_UNSPEC, TCA_NETEM_CORR, TCA_NETEM_DELAY_DIST, + TCA_NETEM_REORDER, __TCA_NETEM_MAX, };
@@ -437,7 +438,7 @@ __u32 latency; /* added delay (us) */ __u32 limit; /* fifo limit (packets) */ __u32 loss; /* random packet loss (0=none ~0=100%) */ - __u32 gap; /* re-ordering gap (0 for delay all) */ + __u32 gap; /* re-ordering gap (0 for none) */ __u32 duplicate; /* random packet dup (0=none ~0=100%) */ __u32 jitter; /* random jitter in latency (us) */ };
@@ -449,6 +450,12 @@ __u32 dup_corr; /* duplicate correlation */ }; +struct tc_netem_reorder +{ + __u32 probability; + __u32 correlation; +}; + #define NETEM_DIST_SCALE 8192 #endif
diff -X dontdiff -urN iproute2-2.6.11-050330/tc/q_netem.c iproute2-netem/tc/q_netem.c
--- iproute2-2.6.11-050330/tc/q_netem.c 2005-04-01 11:58:11.000000000 -0800
+++ iproute2-netem/tc/q_netem.c 2005-05-04 13:31:25.000000000 -0700@@ -29,11 +29,11 @@ { fprintf(stderr, "Usage: ... netem [ limit PACKETS ] \n" \ -" [ delay TIME [ JITTER [CORRELATION]]]\n" \ +" [ delay TIME [ JITTER [CORRELATION]]]\n" \ +" [ distribution {uniform|normal|pareto|paretonormal} ]\n" \ " [ drop PERCENT [CORRELATION]] \n" \ " [ duplicate PERCENT [CORRELATION]]\n" \ -" [ distribution {uniform|normal|pareto|paretonormal} ]\n" \ -" [ gap PACKETS ]\n"); +" [ reorder PRECENT [CORRELATION] [ gap DISTANCE ]]\n"); } static void explain1(const char *arg)
@@ -127,11 +127,13 @@ struct rtattr *tail; struct tc_netem_qopt opt; struct tc_netem_corr cor; + struct tc_netem_reorder reorder; __s16 dist_data[MAXDIST]; memset(&opt, 0, sizeof(opt)); opt.limit = 1000; memset(&cor, 0, sizeof(cor)); + memset(&reorder, 0, sizeof(reorder)); while (argc > 0) { if (matches(*argv, "limit") == 0) {
@@ -178,6 +180,19 @@ return -1; } } + } else if (matches(*argv, "reorder") == 0) { + NEXT_ARG(); + if (get_percent(&reorder.probability, *argv)) { + explain1("reorder"); + return -1; + } + if (NEXT_IS_NUMBER()) { + NEXT_ARG(); + if (get_percent(&reorder.correlation, *argv)) { + explain1("reorder"); + return -1; + } + } } else if (matches(*argv, "gap") == 0) { NEXT_ARG(); if (get_u32(&opt.gap, *argv, 0)) {
@@ -215,8 +230,27 @@ tail = NLMSG_TAIL(n); + if (reorder.probability) { + if (opt.latency == 0) { + fprintf(stderr, "reordering not possible without specifying some delay\n"); + } + if (opt.gap == 0) + opt.gap = 1; + } else if (opt.gap > 0) { + fprintf(stderr, "gap specified without reorder probability\n"); + explain(); + return -1; + } + + if (dist_size > 0 && (opt.latency == 0 || opt.jitter == 0)) { + fprintf(stderr, "distribution specified but no latency and jitter values\n"); + explain(); + return -1; + } + addattr_l(n, 1024, TCA_OPTIONS, &opt, sizeof(opt)); addattr_l(n, 1024, TCA_NETEM_CORR, &cor, sizeof(cor)); + addattr_l(n, 1024, TCA_NETEM_REORDER, &reorder, sizeof(reorder)); if (dist_size > 0) { addattr_l(n, 32768, TCA_NETEM_DELAY_DIST,
@@ -229,6 +263,7 @@ static int netem_print_opt(struct qdisc_util *qu, FILE *f, struct rtattr *opt) { const struct tc_netem_corr *cor = NULL; + const struct tc_netem_reorder *reorder = NULL; struct tc_netem_qopt qopt; int len = RTA_PAYLOAD(opt) - sizeof(qopt); SPRINT_BUF(b1);
@@ -252,6 +287,11 @@ return -1; cor = RTA_DATA(tb[TCA_NETEM_CORR]); } + if (tb[TCA_NETEM_REORDER]) { + if (RTA_PAYLOAD(tb[TCA_NETEM_REORDER]) < sizeof(*reorder)) + return -1; + reorder = RTA_DATA(tb[TCA_NETEM_REORDER]); + } } fprintf(f, "limit %d", qopt.limit);
@@ -278,10 +318,19 @@ if (cor && cor->dup_corr) fprintf(f, " %s", sprint_percent(cor->dup_corr, b1)); } + + if (reorder && reorder->probability) { + fprintf(f, " reorder %s", + sprint_percent(reorder->probability, b1)); + if (reorder->correlation) + fprintf(f, " %s", + sprint_percent(reorder->correlation, b1)); + } if (qopt.gap) fprintf(f, " gap %lu", (unsigned long)qopt.gap); + return 0; }