netdev.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* Re: [PATCH] netem/iproute2 solving correlated loss issues [2/5]
       [not found] <4B2B5A26.8050400@uniroma2.it>
@ 2009-12-18 11:24 ` Fabio Ludovici
  2009-12-18 17:36   ` Stephen Hemminger
  2009-12-18 11:27 ` [PATCH] netem/iproute2 solving correlated loss issues [3/5] Fabio Ludovici
                   ` (2 subsequent siblings)
  3 siblings, 1 reply; 8+ messages in thread
From: Fabio Ludovici @ 2009-12-18 11:24 UTC (permalink / raw)
  To: netdev

[-- Attachment #1: Type: text/plain, Size: 47 bytes --]

patch 2/5 : linux-2.6.32/net/sched/sch_netem.c

[-- Attachment #2: netem_patch_2_of_5 --]
[-- Type: text/plain, Size: 8136 bytes --]

diff -uNr linux-2.6.32/net/sched/sch_netem.c linux-2.6.32-netem/net/sched/sch_netem.c
--- linux-2.6.32/net/sched/sch_netem.c	2009-12-03 04:51:21.000000000 +0100
+++ linux-2.6.32-netem/net/sched/sch_netem.c	2009-12-11 13:06:11.477439585 +0100
@@ -24,6 +24,11 @@
 #include <net/pkt_sched.h>
 
 #define VERSION "1.2"
+static int num_of_drops = 0;	     //GI model-number of dropped packets
+static int num_of_transmissions = 0; //GI model-numberof transmitted packets
+static int chain_state;	     	     //GI Model-Markov chain state
+static int pattern_counter=0;	     //deterministic pattern counter
+static int repetitions_done=0;	     //deterministc pattern repetitions counter
 
 /*	Network Emulation Queuing algorithm.
 	====================================
@@ -62,6 +67,21 @@
 	u32 duplicate;
 	u32 reorder;
 	u32 corrupt;
+	u32 p13;	
+	u32 p31;	
+	u32 p23;	
+	u32 p32;	
+	u32 p14;
+	u32 gilb_p;
+	u32 gilb_r;		
+	u32 gilb_h;		
+	u32 gilb_k;	
+	u32 algorithm;
+	u32 logging; 
+	u32 query; 
+	u16 pattern_length;
+	u32 pattern_repetitions;
+	u32 *kernel_pattern;
 
 	struct crndstate {
 		u32 last;
@@ -151,6 +171,7 @@
  * 	NET_XMIT_DROP: queue length didn't change.
  *      NET_XMIT_SUCCESS: one skb was queued.
  */
+
 static int netem_enqueue(struct sk_buff *skb, struct Qdisc *sch)
 {
 	struct netem_sched_data *q = qdisc_priv(sch);
@@ -160,6 +181,9 @@
 	int ret;
 	int count = 1;
 
+	u32 GI_random; 		     //GI loss model random number
+	u32 gilbell_random; 	     //Gilbert-Elliot loss model random number
+	
 	pr_debug("netem_enqueue skb=%p\n", skb);
 
 	/* Random duplication */
@@ -170,6 +194,157 @@
 	if (q->loss && q->loss >= get_crandom(&q->loss_cor))
 		--count;
 
+	/* General and Intuitive loss generator, Gilbert-Elliot generator, deterministic pattern
+	====================================
+        
+	Sources: [1] S. Salsano, F. Ludovici, A. Ordine: "Definition of a general and
+	intuitive loss model for packet networks and its implementation in the Netem
+	module in the Linux kernel", July 2009 available at 
+	http://netgroup.uniroma2.it/twiki/bin/view.cgi/Main/NetEm2#TechnicalReports
+
+	 ----------------------------------------------------------------
+
+	 This is an algorithm for loss generation based on the 4-state Markov chain adopted
+         in the GI (General and Intuitive) loss model. A random number (GI_random) is extracted
+         and compared to the transition probabilities to decide if a packet will be lost or not.
+         State 1 is related to successfully transmitted packets within a gap period,  State 4 to 
+         isolated losses within a gap period, State 3 to lost packets withing a burst, State 2 to 
+	 successfully transmitted packets within a burst. 
+        */
+
+    	if (q->algorithm==0) {
+
+	GI_random=net_random(); 
+    	
+    	switch (chain_state) {	
+   	    case 1:
+		num_of_transmissions++;
+		if((0<GI_random)&&(GI_random<q->p13))	{
+			chain_state=3;
+			break;
+		}
+		else if((q->p13<GI_random)&&(GI_random<(4294967295u-q->p14)))	{
+			chain_state=1;					
+			break;
+		}
+		else if(((4294967295u-q->p14)<GI_random) && (GI_random<4294967295u))	{
+			chain_state=4;
+			break;
+		}				
+ 	    case 2:  			
+   	    	num_of_transmissions++;
+   	    	if(GI_random<q->p23)	{
+			chain_state=3;
+			break;
+		}	
+		else  	{			
+			chain_state=2;
+			break;
+		}							
+   	    case 3:
+   	    	--count;
+		num_of_drops++; 
+		if (q->logging==1) 
+			printk("netem loss event GI burst %d RFPLE %d\n", 
+				num_of_drops, num_of_transmissions);
+		num_of_transmissions=0; 
+    		if((0<GI_random)&&(GI_random<q->p32)){
+			chain_state=2;
+			break;
+		}	
+		else if((q->p32<GI_random) && (GI_random<(q->p31+q->p32))){
+		chain_state=1;
+		break;
+		}
+		else if(((q->p31+q->p32)<GI_random) && (GI_random<4294967295u)){ 
+		chain_state=3;
+		break;
+		}
+	    case 4:
+	    	--count;
+	     	num_of_drops++;
+	     	chain_state=1;
+	     	if (q->logging==1) 
+			printk("netem loss event GI isolated %d RFPLE %d\n", 
+			num_of_drops, num_of_transmissions);
+		break;
+	}		
+	}
+	
+	/* Gilbert-Elliot loss generator algorithm 
+	This is an algorithm for loss generation based on the Gilbert-Elliot loss model and its 
+	special cases. 
+	*/
+        
+	if (q->algorithm==1) {
+
+	switch(chain_state) {
+	    case 1:		
+		gilbell_random=net_random();
+		if(gilbell_random<4294967295u-q->gilb_k){
+		--count;
+		num_of_drops++;
+		if (q->logging==1) 
+			printk("netem loss event gilbell %d RFPLE %d\n", 
+			num_of_drops, num_of_transmissions);
+		num_of_transmissions=0;
+		} 
+		else	{
+		num_of_transmissions++;
+		}
+	  	gilbell_random=net_random();
+		if(gilbell_random<q->gilb_p){
+		chain_state=2;			  			  	    
+		}
+		break;
+						
+	case 2:			
+		gilbell_random=net_random();								
+		if(gilbell_random<4294967295u-q->gilb_h){
+		--count;
+		num_of_drops++;
+		if (q->logging==1)
+			printk("netem loss event gilbell %d RFPLE %d\n", 
+				num_of_drops, num_of_transmissions);
+			num_of_transmissions=0;											
+		}
+		else	{
+		num_of_transmissions++;
+		}
+		gilbell_random=net_random();	
+		if(gilbell_random<q->gilb_r)	{
+			chain_state=1;
+		}
+		break;		
+	}
+	}
+
+	/* Deterministic loss pattern algorithm 
+	This options reads a loss sequence of 0 and 1 from a file where 0 represents a
+	transmitted packet and 1 represents a loss event. The pattern can be repeated 
+	for a fixed number of times or indefinitely (if pattern_repetitions=0).
+	*/     
+	
+	if ((0<q->pattern_length) & ((q->pattern_repetitions==0)||
+		(repetitions_done<q->pattern_repetitions)) & 
+		(pattern_counter<q->pattern_length)){  
+	
+		if (0<q->kernel_pattern[pattern_counter-1]){
+		--count;
+		num_of_drops++; 
+    		if (q->logging==1) 
+			printk("netem loss event deterministic %d RFPLE %d\n", 
+				num_of_drops, num_of_transmissions);
+		num_of_transmissions=0;
+				}
+		else num_of_transmissions++;
+		pattern_counter++;
+		if (pattern_counter==q->pattern_length-1){
+		repetitions_done++;
+		pattern_counter=1;
+		}	
+		}	
+				
 	if (count == 0) {
 		sch->qstats.drops++;
 		kfree_skb(skb);
@@ -396,6 +571,7 @@
 	struct nlattr *tb[TCA_NETEM_MAX + 1];
 	struct tc_netem_qopt *qopt;
 	int ret;
+	int pattern_element;
 
 	if (opt == NULL)
 		return -EINVAL;
@@ -418,6 +594,31 @@
 	q->counter = 0;
 	q->loss = qopt->loss;
 	q->duplicate = qopt->duplicate;
+	q->p13 = qopt->p13;		
+	q->p31 = qopt->p31;		
+	q->p32 = qopt->p32;		
+	q->p23 = qopt->p23;		
+	q->p14 = qopt->p14;
+	q->gilb_p = qopt->gilb_p;		
+	q->gilb_r = qopt->gilb_r;		
+	q->gilb_h = qopt->gilb_h;		
+	q->gilb_k = qopt->gilb_k;		
+	q->logging = qopt->logging; 
+	q->query = qopt->query; 
+	q->algorithm = qopt->algorithm; 
+ 	q->pattern_length = qopt->pattern_length; 
+ 	q->pattern_repetitions = qopt->pattern_repetitions; 	
+ 	q->kernel_pattern=kmalloc(q->pattern_length*sizeof(size_t), 
+		GFP_KERNEL);
+	
+		for (pattern_element=1; pattern_element<q->pattern_length; 
+			pattern_element++)	{
+			q->kernel_pattern[pattern_element-1] = 
+			qopt->user_pattern[pattern_element-1]; 
+							}								
+	pattern_counter=1;
+	repetitions_done=0;	 	
+	chain_state=1;
 
 	/* for compatibility with earlier versions.
 	 * if gap is set, need to assume 100% probability
@@ -571,7 +772,32 @@
 	struct tc_netem_corr cor;
 	struct tc_netem_reorder reorder;
 	struct tc_netem_corrupt corrupt;
-
+	int pattern_element;
+	qopt.p13=q->p13;
+	qopt.p31=q->p31;
+	qopt.p23=q->p23;
+	qopt.p32=q->p32;
+	qopt.p14=q->p14;
+	
+	qopt.gilb_p=q->gilb_p;
+	qopt.gilb_r=q->gilb_r;
+	qopt.gilb_h=q->gilb_h;
+	qopt.gilb_k=q->gilb_k;
+			 		
+	qopt.logging = q->logging;  
+	qopt.query = q->query;
+	qopt.algorithm = q->algorithm;
+	qopt.pattern_length = q->pattern_length; 
+	qopt.pattern_repetitions = q->pattern_repetitions;  
+	qopt.user_pattern=kmalloc(qopt.pattern_length*sizeof(size_t), 
+		GFP_KERNEL);
+	if(q->pattern_length)	{
+		for (pattern_element=1; pattern_element<q->pattern_length; 
+			pattern_element++) 	{
+		qopt.user_pattern[pattern_element-1] = 
+		q->kernel_pattern[pattern_element-1]; 	
+					} 
+					}
 	qopt.latency = q->latency;
 	qopt.jitter = q->jitter;
 	qopt.limit = q->limit;

^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: [PATCH] netem/iproute2 solving correlated loss issues [3/5]
       [not found] <4B2B5A26.8050400@uniroma2.it>
  2009-12-18 11:24 ` [PATCH] netem/iproute2 solving correlated loss issues [2/5] Fabio Ludovici
@ 2009-12-18 11:27 ` Fabio Ludovici
  2009-12-18 11:30 ` [PATCH] netem/iproute2 solving correlated loss issues [4/5] Fabio Ludovici
       [not found] ` <4B2B5A65.1060300@uniroma2.it>
  3 siblings, 0 replies; 8+ messages in thread
From: Fabio Ludovici @ 2009-12-18 11:27 UTC (permalink / raw)
  To: netdev

[-- Attachment #1: Type: text/plain, Size: 56 bytes --]

patch 3/5 : iproute2-2.6.29-1/include/linux/pkt_sched.h

[-- Attachment #2: tc_patch_3_of_5 --]
[-- Type: text/plain, Size: 1533 bytes --]

diff -uNr iproute2-2.6.29-1/include/linux/pkt_sched.h iproute2-2.6.29-1-netem/include/linux/pkt_sched.h
--- iproute2-2.6.29-1/include/linux/pkt_sched.h	2009-03-24 23:40:54.000000000 +0100
+++ iproute2-2.6.29-1-netem/include/linux/pkt_sched.h	2009-12-11 16:41:06.594482411 +0100
@@ -479,6 +479,21 @@
 	__u32	gap;		/* re-ordering gap (0 for none) */
 	__u32   duplicate;	/* random packet dup  (0=none ~0=100%) */
 	__u32	jitter;		/* random jitter in latency (us) */
+	__u32	p13;		/* GI loss model-state 1 to 3 transition probability */
+	__u32	p31;		/* GI loss model-state 3 to 1 transition probability */
+	__u32	p32;		/* GI loss model-state 3 to 2 transition probability */
+	__u32	p23;		/* GI loss model-state 2 to 3 transition probability */
+	__u32   p14;		/* GI loss model-state 1 to 4 transition probability */
+	__u32	gilb_p;		/* Gilbert-Elliot model-state good-bad transition probability */
+	__u32	gilb_r;		/* Gilbert-Elliot model-state bad-good transition probability */
+	__u32	gilb_h;		/* Gilbert-Elliot-loss model loss probability in bad state */
+	__u32	gilb_k;		/* Gilbert-Elliot-loss model loss probability in good state */
+	__u32   algorithm;	/* loss model algorithm selection */
+	__u32 	logging;  	/* loss logging mode selector */
+	__u32   query;		/* loss query mode selector */
+	__u16   pattern_length; /* deterministic loss pattern length */
+	__u32   pattern_repetitions; /* deterministc loss pattern repetitions */
+	__u16   *user_pattern; /* determinist loss pattern elements */
 };
 
 struct tc_netem_corr

^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: [PATCH] netem/iproute2 solving correlated loss issues [4/5]
       [not found] <4B2B5A26.8050400@uniroma2.it>
  2009-12-18 11:24 ` [PATCH] netem/iproute2 solving correlated loss issues [2/5] Fabio Ludovici
  2009-12-18 11:27 ` [PATCH] netem/iproute2 solving correlated loss issues [3/5] Fabio Ludovici
@ 2009-12-18 11:30 ` Fabio Ludovici
       [not found] ` <4B2B5A65.1060300@uniroma2.it>
  3 siblings, 0 replies; 8+ messages in thread
From: Fabio Ludovici @ 2009-12-18 11:30 UTC (permalink / raw)
  To: netdev

[-- Attachment #1: Type: text/plain, Size: 50 bytes --]

patch 4/5 : iproute2-2.6.29-1/man/man8/tc-netem.8

[-- Attachment #2: tc_patch_4_of_5 --]
[-- Type: text/plain, Size: 10791 bytes --]

diff -uNr iproute2-2.6.29-1/man/man8/tc-netem.8 iproute2-2.6.29-1-netem/man/man8/tc-netem.8
--- iproute2-2.6.29-1/man/man8/tc-netem.8	1970-01-01 01:00:00.000000000 +0100
+++ iproute2-2.6.29-1-netem/man/man8/tc-netem.8	2009-12-11 16:41:25.184219339 +0100
@@ -0,0 +1,258 @@
+.TH NETEM 8 "11 December 2009" "iproute2" "Linux"
+.SH NAME
+NetEm \- Network Emulator
+.SH SYNOPSIS
+.B tc qdisc ... dev
+dev
+.B ] add netem  [ limit 
+packets
+.B ] 
+
+.B tc qdisc ... dev
+dev
+.B ] add netem [ logging 
+LEVEL ]
+.B ] 
+
+.B tc qdisc ... dev
+dev
+.B ] add netem [ delay 
+TIME [ JITTER [CORRELATION]]]
+.B ] 
+
+.B tc qdisc ... dev
+dev
+.B ] add netem [ distribution 
+{uniform|normal|pareto|paretonormal} ]
+.B ] 
+
+.B tc qdisc ... dev
+dev
+.B ] add netem [ drop 
+PERCENT [CORRELATION]]
+.B ] 
+
+.B tc qdisc ... dev
+dev
+.B ] add netem [ loss
+PERCENT [CORRELATION]]
+.B ] 
+
+.B tc qdisc ... dev
+dev
+.B ] add netem  [ query 
+] 
+
+.B tc qdisc ... dev
+dev
+.B ] add netem [ loss_GI 
+ploss [burst_length [density [pisol [good_burst_length]]]]
+.B ] 
+
+.B tc qdisc ... dev
+dev
+.B ] add netem [ loss_GI_tran
+p13 p31 [p32 p23 [p14]]
+.B ] 
+
+.B tc qdisc ... dev
+dev
+.B ] add netem  [ loss_bern 
+p 
+.B ] 
+
+.B tc qdisc ... dev
+dev
+.B ] add netem  [ loss_gilb 
+p r [1-h]]
+.B ]
+
+.B tc qdisc ... dev
+dev
+.B ] add netem  [ loss_gilbell 
+p r [1-h [1-k]]
+.B ]
+
+.B tc qdisc ... dev
+dev
+.B ] add netem  [ loss_gilb_4s 
+p r [1-h]]
+
+
+.B tc qdisc ... dev
+dev
+.B ] add netem  [ loss_gilbell_4s 
+p r [1-h [1-k]]
+.B ]
+
+.B tc qdisc ... dev
+dev
+.B ] add netem [ loss_pattern 
+FILENAME [REPETITIONS]]
+.B ] 
+
+.B tc qdisc ... dev
+dev
+.B ] add netem  [ corrupt 
+PERCENT [CORRELATION]]
+.B ] 
+
+.B tc qdisc ... dev
+dev
+.B ] add netem  [ duplicate 
+PERCENT [CORRELATION]]
+.B ] 
+
+.B tc qdisc ... dev
+dev
+.B ] add netem  [ reorder 
+PRECENT [CORRELATION] [ gap DISTANCE ]]
+.B ] 
+
+.SH DESCRIPTION
+NetEm is an enhancment of the Linux traffic control facilities 
+that allow to add delay, packet loss, duplication and more other
+characteristics to packets outgoing from a selected network
+interface. NetEm is build using the existing Quality Of Service (QOS)
+and Differentiated Services (diffserv) facilities in the Linux
+kernel. 
+
+.SH netem OPTIONS
+netem has the following options:
+
+.B limit 
+packets
+
+limits the effect of selected options to the indicated number of next packets. 
+
+.B logging
+LEVEL
+
+sets a logging level. Actually it works for loss_GI, loss_GI_tran, loss_bern, loss_gilb, loss_gilbell, loss_gilb_4s, loss_gilbell_4s, loss_pattern options. If not specified, level 0 will be used which means that no data will be logged. If logging level is 1 for each loss events the kernel logs will include a line like "netem loss event algorithm [type] x RFPLE y" where RFPLE stands for "Received From Previous Loss Event" and it counts the number y of good packets received between two loss events while x is the number of all lost packets and algorithm refers to the selected loss generation algorithm (
+.B GI
+, 
+.B gilbell 
+or 
+.B deterministic). 
+The type label applies only to the GI algorithm and can be 
+.B burst 
+or 
+.B isolated.
+
+.B delay 
+TIME [ JITTER [CORRELATION]]]
+
+adds the chosen delay to the packets outgoing to chosen network interface. The optional parameters allows to introduce a delay variation and a correlation. Delay and jitter values are expressed in ms while correlation is percentage. 
+
+.B distribution 
+{uniform|normal|pareto|paretonormal} 
+ 
+allow the choose the delay distribution. If not specified, the default distribution is normal. Additional parameters allow to consider situations in which network has variable delays depending on traffic flows concurring on the same path, that causes severeal delay peaks and a tail. 
+
+.B drop 
+PERCENT [CORRELATION]
+
+OR
+
+.B loss
+PERCENT [CORRELATION]
+
+using drop or loss is the same. It adds the chosen independent loss probability to packets outgoing from the chosen network interface. It is also possibile to add a correlation, through the proper parameter. However this option is now deprecated due to the noticed bad behaviour. To have introduce independent packet losses, which corresponds to the Bernoulli loss model, please use the loss_bern option.
+
+.B query
+
+enables the query mode. Actually it works for loss_GI, loss_GI_tran\, loss_bern, loss_gilb, loss_gilbell. When the query mode is enabled and one of the supported options are selected, the correspondent transition probabilities and GI parameters are calculated and printed to screen without passing the parameters to the qdisc. So this option works like a parameter converter. If the option is not specified the query mode is disabled so the parameters will be regularly passed to the netem qdisc. 
+
+.B loss_GI 
+ploss [burst_length [density [pisol [good_burst_length]]]]
+
+implements the GI (General and Intuitive) loss model, with the underlying 4-state Markov. The parameter ploss  is mandatory and if used alone corresponds to the Bernoulli model while the optional parameters allows to extend the model to 2-state (burst_length), 3-state (density), and 4-state (pisol). Without specifing good_burst_length the hyphotesis of statistical independence for the losses within the burst will be used.
+
+.B loss_GI_tran
+p13 p31 [p32 p23 [p14]]
+
+implements the GI (General and Intuitive) model using the 4-state Markov transition probabilities as input parameters. The first two parameters p13 and p31 are mandatory and if used alone corresponds to a 2-state model while the optional parameters allows to extend the model to 3-state (p23 and p32) and 4-state (p14). State 1 corresponds to good reception, State 4 to independent losses, State 3 to burst losses and State 2 to good reception within a burst. 
+
+.B loss_bern 
+p
+
+implements the Bernoulli loss model. Allows to introduce, through the p parameter, an independent loss probability to packets outgoing from chosen network interface. This option is equivalent to the old and now deprecated drop / loss
+option used without the correlation parameter. 
+
+.B loss_gilb 
+p r [1-h]
+
+implements the Gilbert loss model through the two mandatory parameters p and r and the optional 1-h. This model has two states: "good" and "bad". If only the mandatory parameters are specified, the Simple Gilbert model will be used, while to use the full Gilbert model it is needed to specify the whole set of three parameters.
+
+.B loss_gilbell 
+p r [1-h [1-k]]
+
+implements the Gilbert-Elliot loss model through the two mandatory parameters p and r and the optional 1-h and 1-k where  1-k is an independent loss probability in the "good" state while 1-h is the loss density within the "bad" state. This model is an enhanced version of the Gilbert model.
+
+.B loss_gilb_4s
+p r [1-h]
+
+implements the Gilbert-4s loss model that is particular version of the GI model which behaviour is very similar to the Gilbert's. The input parameters are the same of the real Gilbert model. The transition probabilities and GI parameters that corresponds to the Gilbert input parameters are calculated and printed to screen. This option is included to study the correspondence between GI model and the models available in the literature, it has no practical use at the moment.
+
+.B loss_gilbell_4s 
+p r [1-h [1-k]]
+
+implements the Gilbert-Elliot-4s loss model that is particular version of the GI model which behaviour is very similar to the Gilbert-Elliot's. The input parameters are the same of the real Gilbert model. The transition probabilities and GI parameters that corresponds to the Gilbert-Elliot input parameters are calculated and printed to screen. This option is included to study the correspondence between GI model and the models available in the literature, it has no practical use at the moment.
+
+.B loss_pattern 
+FILENAME [REPETITIONS]
+
+generates a deterministic loss pattern. It reads from the text file FILENAME a sequence of "1" and "0" where "1" are the loss events and "0" are the regular transmission of packets . The parameter repetitions is optional and is the number of "replicas" of the loss pattern file. It is optional and by default is 0 which means infinite repetition of the loss pattern.
+
+.B corrupt 
+PERCENT [CORRELATION]]
+
+allows the emulate the random noise introducing an error in a random position for a chosen percent of packets. It is also possible to add a correlation through the proper parameter.
+
+.B duplicate 
+PERCENT [CORRELATION]]
+
+using this option the chosen percent of packets is duplicated before queueing them. It is also possible to add a correlation through the proper parameter.
+
+.B reorder 
+PRECENT [CORRELATION] [ gap DISTANCE ]]
+
+there are two ways to use this option:
+
+.B reorder 
+gap 5 10 ms 
+
+in this first example every 5th (10th, 15th) packet is sent immediately while other packets are delayed by 10 ms 
+
+.B reorder 
+25% 50%
+
+in this second example 25% of packets are sent immediately (with correlation of 50%) while the other are delayed by 10 ms.
+
+.SH LIMITATIONS
+The main known limitation of Netem are related to timer granularity, since Linux is not a real-time operating system; to the choice of Pseudo-Random Number Generator (PRNG) and the original loss model. To have a better behavior in emulating losses, the new loss_GI_tran, loss_GI, loss_bern, loss_gilb, loss_gilbell, loss_gilb_4s, loss_gilbell_4s options were added.
+
+
+.SH SOURCES
+.TP
+o
+Hemminger S. , "Network Emulation with NetEm", Open Source Development Lab, April 2005 (http://devresources.linux-foundation.org/shemminger/netem/LCA2005_paper.pdf)
+
+.TP
+o
+Netem page from Linux foundation, (http://www.linuxfoundation.org/en/Net:Netem)
+
+.TP
+o
+Salsano S., Ludovici F., Ordine A., "Definition of a general and intuitive loss model for packet
+networks and its implementation in the Netem module in the Linux kernel", 
+August 2009 (http://netgroup.uniroma2.it/twiki/pub/Main/netem2/TR-loss-netem.pdf)
+
+
+.SH SEE ALSO
+.BR tc (8)
+
+.SH AUTHOR
+Netem was written by Stephen Hemminger at OSDL and is based on NISTnet. This version includes the new GI (General and Intuitive) loss generator, the Gilbert-Elliot loss generator, the deterministic pattern mode. This options were developed by Networking Group, University of Rome "Tor Vergata" involving Stefano Salsano, Fabio Ludovici, Alessandro Ordine. This manpage was created by Fabio Ludovici <fabio.ludovici AT yahoo DOT it>.
+
+

^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: [PATCH] netem/iproute2 solving correlated loss issues [5/5]
       [not found] ` <4B2B5A65.1060300@uniroma2.it>
@ 2009-12-18 11:30   ` Fabio Ludovici
  0 siblings, 0 replies; 8+ messages in thread
From: Fabio Ludovici @ 2009-12-18 11:30 UTC (permalink / raw)
  To: netdev

[-- Attachment #1: Type: text/plain, Size: 44 bytes --]

patch 5/5 : iproute2-2.6.29-1/tc/q_netem.c


[-- Attachment #2: tc_patch_5_of_5 --]
[-- Type: text/plain, Size: 16662 bytes --]

diff -uNr iproute2-2.6.29-1/tc/q_netem.c iproute2-2.6.29-1-netem/tc/q_netem.c
--- iproute2-2.6.29-1/tc/q_netem.c	2009-03-24 23:40:54.000000000 +0100
+++ iproute2-2.6.29-1-netem/tc/q_netem.c	2009-12-11 16:41:14.766468716 +0100
@@ -7,7 +7,6 @@
  *		2 of the License, or (at your option) any later version.
  *
  * Authors:	Stephen Hemminger <shemminger@osdl.org>
- *
  */
 
 #include <stdio.h>
@@ -29,9 +28,19 @@
 {
 	fprintf(stderr,
 "Usage: ... netem [ limit PACKETS ] \n" \
+"                 [ logging LEVEL ] \n" \
+"		  [ query ] \n" \
 "                 [ delay TIME [ JITTER [CORRELATION]]]\n" \
 "                 [ distribution {uniform|normal|pareto|paretonormal} ]\n" \
 "                 [ drop PERCENT [CORRELATION]] \n" \
+"		  [ loss_GI ploss [burst_length [density [pisol [good_burst_length]]]]] \n" \
+"		  [ loss_GI_tran p13 p31 [p32 p23 [p14]]]  \n" \
+"		  [ loss_bern p ] \n" \
+"		  [ loss_gilb_4s p r [1-h]] \n" \
+"		  [ loss_gilbell_4s p r [1-h [1-k]]] \n" \
+"		  [ loss_gilb p r [1-h]] \n" \
+"		  [ loss_gilbell p r [1-h [1-k]]] \n" \
+"                 [ loss_pattern [filename [repetitions]]] \n" \
 "                 [ corrupt PERCENT [CORRELATION]] \n" \
 "                 [ duplicate PERCENT [CORRELATION]]\n" \
 "                 [ reorder PRECENT [CORRELATION] [ gap DISTANCE ]]\n");
@@ -138,6 +147,10 @@
 
 	memset(&opt, 0, sizeof(opt));
 	opt.limit = 1000;
+	opt.query = 0; 
+	opt.logging = 0; 
+	opt.pattern_length = 0;
+	opt.pattern_repetitions = 0; 
 	memset(&cor, 0, sizeof(cor));
 	memset(&reorder, 0, sizeof(reorder));
 	memset(&corrupt, 0, sizeof(corrupt));
@@ -150,6 +163,14 @@
 				explain1("limit");
 				return -1;
 			}
+		} else if (matches(*argv, "logging") == 0) {		
+			NEXT_ARG();
+			if (get_size(&opt.logging, *argv)) {
+				explain1("logging");
+				return -1;
+			}
+		} else if (matches(*argv, "query") == 0) {		
+			opt.query=1;			
 		} else if (matches(*argv, "latency") == 0 ||
 			   matches(*argv, "delay") == 0) {
 			NEXT_ARG();
@@ -189,6 +210,506 @@
 					return -1;
 				}
 			}
+		} else if (matches(*argv, "loss_GI") == 0)  {		
+			NEXT_ARG();
+
+			double p13=0;
+			double p31=1;
+			double p32=0;
+			double p23=1;
+			double p14=0;
+			double ploss=0;
+			double burst_length=1;
+			double rho=1;
+			double pisol=0;
+			double good_burst_length=0;
+
+			opt.algorithm=0;	//algorithm 0 is GI, 1 is gilbell
+			
+			ploss=strtod(*argv,(char **)NULL)/100;
+
+			if (NEXT_IS_NUMBER()) {			
+			NEXT_ARG();
+			burst_length=strtod(*argv,(char **)NULL);
+			
+			if (NEXT_IS_NUMBER()) {
+			NEXT_ARG();			
+			rho=strtod(*argv,(char **)NULL)/100;
+			
+			if (ploss>rho) {
+			printf("\nError: ploss>density \n");
+			break;
+			}
+			
+			if (NEXT_IS_NUMBER())	{
+			NEXT_ARG();
+			pisol=strtod(*argv,(char **)NULL)/100;
+			
+			if (pisol>ploss) {
+			printf("\nError: pisol>ploss \n");
+			break;
+			}
+
+			if (ploss>(rho-pisol*(rho-1))) {
+			printf("\nError: ploss>density-pisol(density-1) \n");
+			break;
+			}
+			
+			if (NEXT_IS_NUMBER())	{
+			NEXT_ARG();
+			good_burst_length=strtod(*argv,(char **)NULL);
+			if (good_burst_length>burst_length) {printf("\nError: good burst length>burst length \n ");
+			break;
+							}
+						}		
+					}
+				}
+			}
+					
+			if(burst_length==0) {
+			p13=ploss;
+			p31=1-ploss;
+			}
+			
+			else if((burst_length!=0) & (rho==1) & (pisol==0)) {
+			p13=ploss/(burst_length*(1-ploss));
+			p31=1/burst_length;
+			} 
+			
+			else if ((burst_length!=0) & (rho!=1) & (pisol==0)) {
+			p13=(-ploss)/(burst_length*ploss-burst_length*rho);
+			p31=1/(burst_length*rho);
+			}
+			
+			else if ((burst_length!=0) & (rho!=1) & (pisol!=0)) {
+			p13=(pisol-ploss)/(burst_length*(pisol-1)*(rho-ploss));
+			p31=1/(burst_length*rho);
+			p14=pisol/(1-pisol);
+			}
+				
+			if((burst_length!=0) & (rho!=1))	{
+			
+				if(good_burst_length==0)	{
+				p23=(burst_length*rho-1) / (burst_length-1);
+				p32=(1+rho*rho*burst_length-rho-burst_length*rho) / (rho-rho*burst_length);
+							        					}				
+				else	{
+				p23=1/good_burst_length;
+				p32=(1-rho) / (rho*good_burst_length);				
+					}	
+					
+								}
+					
+			if (burst_length==0) burst_length=1/p31;						
+						
+			printf("\nTransition probabilities are:\n ");
+			printf("--------------------------------");
+			printf("\np13 is %.3f%% ", 100*p13);
+			printf("\np31 is %.3f%% ", 100*p31);
+			printf("\np32 is %.3f%% ", 100*p32);
+			printf("\np23 is %.3f%% ", 100*p23);
+			printf("\np14 is %.3f%%\n ", 100*p14);
+			
+			printf("\nGI (General and Intuitive) parameters will be: \n");
+			printf("--------------------------------");
+			printf("\nploss is %.3f%% ", 100*ploss);
+			printf("\nburst length is %.3f", burst_length);
+			printf("\nburst density is %.3f%% ", 100*rho);
+			printf("\nisolated ploss is %.3f%% ", 100*pisol);
+			printf("\ngood burst length is %.3f\n ", good_burst_length);
+
+			if(opt.query==0)	{
+			opt.p13=4294967295u*p13;
+			opt.p31=4294967295u*p31;
+			opt.p32=4294967295u*p32;
+			opt.p23=4294967295u*p23;
+			opt.p14=4294967295u*p14;			
+			}
+			
+			if(opt.query==1) return -1;	
+
+		} else if (matches(*argv, "loss_GI_tran") == 0)  {
+
+			double p13=0;
+			double p31=1;
+			double p32=0;
+			double p23=1;
+			double p14=0;
+			double ploss;
+			double burst_length;
+			double rho;
+			double pisol;
+			double good_burst_length;
+
+			opt.algorithm=0; 	//algorithm 0 is 4-state, 1 is gilbell
+
+			NEXT_ARG();
+			p13=strtod(*argv,(char **)NULL)/100;
+
+			if (NEXT_IS_NUMBER()) {			
+			NEXT_ARG();
+			p31=strtod(*argv,(char **)NULL)/100;
+			if (NEXT_IS_NUMBER()) {
+			NEXT_ARG();
+			p32=strtod(*argv,(char **)NULL)/100;
+			if (NEXT_IS_NUMBER()) {
+			NEXT_ARG();
+			p23=strtod(*argv,(char **)NULL)/100;
+			if (NEXT_IS_NUMBER()) {
+			NEXT_ARG();
+			p14=strtod(*argv,(char **)NULL)/100;
+			}
+			}
+			}
+			}
+
+			else p31=1-p13;
+			
+			printf("\nTransition probabilities are:\n ");
+			printf("--------------------------------");
+			printf("\np13 is %.3f%% ", 100*p13);
+			printf("\np31 is %.3f%% ", 100*p31);
+			printf("\np32 is %.3f%% ", 100*p32);
+			printf("\np23 is %.3f%% ", 100*p23);
+			printf("\np14 is %.3f%%\n ", 100*p14);
+
+			ploss=(p13*p23+p14*p23*p31) / (p13*p23+p23*p31+p14*p23*p31+p13*p32);
+			burst_length=(p32+p23) / (p23*p31);
+			rho=(p13*p23) / (p13*p23+p13*p32);
+			pisol=(p14*p23*p31) / (p14*p23*p31+p23*p31);
+			good_burst_length=1/p23;
+
+			printf("\nGI (General and Intuitive) parameters will be: \n");
+			printf("--------------------------------");
+			printf("\nploss is %.3f%%", 100*ploss);
+			printf("\nburst length is %.3f", burst_length);
+			printf("\nburst density is %.3f%% ", 100*rho);
+			printf("\nisolated ploss is %.3f%% ", 100*pisol);
+			printf("\ngood burst length is %.3f\n ", good_burst_length);
+
+			if(opt.query==0)	{
+			opt.p13=4294967295u*p13;
+			opt.p31=4294967295u*p31;
+			opt.p32=4294967295u*p32;
+			opt.p23=4294967295u*p23;
+			opt.p14=4294967295u*p14;			
+			}
+			
+			if(opt.query==1) return -1;
+			
+		} else if (matches(*argv, "loss_gilb") == 0)  {
+			
+			double p=0;
+			double r=0;
+			double h=0;
+									
+			opt.algorithm=1;	//algorithm 1 is gilbell
+					
+			NEXT_ARG();
+			p=strtod(*argv,(char **)NULL)/100;
+			
+			NEXT_ARG();
+			r=strtod(*argv,(char **)NULL)/100;
+						
+			if (NEXT_IS_NUMBER())	{
+			NEXT_ARG();
+			h=(100-strtod(*argv,(char **)NULL))/100;						
+			}
+
+			printf("\nGilbert parameters will be: \n");
+			printf("--------------------------------");
+			printf("\np is %.3f%% ", 100*p);
+			printf("\nr is %.3f%%", 100*r);
+			printf("\n1-h is %.3f%%\n", 100*(1-h));	
+			
+			opt.gilb_p=4294967295u*p;
+			opt.gilb_r=4294967295u*r;
+			opt.gilb_h=4294967295u*h;
+														
+		} else if (matches(*argv, "loss_gilbell") == 0)  {
+			
+			double p=0;
+			double r=0;
+			double h=0;
+			double k=1;
+			
+			opt.algorithm=1;	//algorithm 1 is gilbell
+					
+			NEXT_ARG();
+			p=strtod(*argv,(char **)NULL)/100;
+			
+			NEXT_ARG();
+			r=strtod(*argv,(char **)NULL)/100;
+						
+			if (NEXT_IS_NUMBER())	{
+			NEXT_ARG();
+			h=(100-strtod(*argv,(char **)NULL))/100;
+						
+			if (NEXT_IS_NUMBER())	{
+			NEXT_ARG();
+			k=(100-strtod(*argv,(char **)NULL))/100;			
+						}
+						}
+
+			printf("\nGilbert-Elliot parameters will be: \n");
+			printf("--------------------------------");
+			printf("\np is %.3f%% ", 100*p);
+			printf("\nr is %.3f%%", 100*r);
+			printf("\n1-h is %.3f%% ", 100*(1-h));
+			printf("\n1-k is %.3f%%\n", 100*(1-k));		
+			
+			opt.gilb_p=4294967295u*p;
+			opt.gilb_r=4294967295u*r;
+			opt.gilb_h=4294967295u*h;
+			opt.gilb_k=4294967295u*k;		
+
+		} else if (matches(*argv, "loss_bern") == 0)  {		
+			
+			double p=0;
+			double r=0;
+			double ploss=0;
+			double burst_length=1;
+			double p13=0;
+			double p31=0;
+			
+			opt.algorithm=0;	//algorithm 0 is 4-state, 1 is gilbell
+					
+			NEXT_ARG();
+			p=strtod(*argv,(char **)NULL)/100;
+			r=1-p;
+			
+			ploss=p/(p+r);
+			burst_length=1/r;
+			
+			p13=p;
+			p31=r;
+
+			printf("\nTransition probabilities are:\n ");
+			printf("--------------------------------");
+			printf("\np13 is %.3f%% ", 100*p13);
+			printf("\np31 is %.3f%% ", 100*p31);
+			printf("\np32 is 0.000%% ");
+			printf("\np23 is 100.000%% ");
+			printf("\np14 is 0.000%%\n ");
+			
+			printf("\nGI (General and Intuitive) parameters will be: \n");
+			printf("--------------------------------");
+			printf("\nploss is %.3f%% ", 100*ploss);
+			printf("\nburst length is %.3f", burst_length);
+			printf("\nburst density is 100.000%% ");
+			printf("\nisolated ploss is 0.000%% ");
+			printf("\ngood burst length is 1.000%%\n "); 
+
+			if(opt.query==0)	{
+			opt.p13=4294967295u*p13;
+			opt.p31=4294967295u*p31;
+			opt.p32=0;
+			opt.p23=4294967295u;
+			opt.p14=0;			
+			}
+			
+			if(opt.query==1) return -1;			
+
+		} else if (matches(*argv, "loss_gilb_4s") == 0)  {
+			double p=0;
+			double r=0;
+			double h=0;
+			double ploss=0;
+			double burst_length=1;
+			double rho=1;
+			double p13=0;
+			double p31=1;
+			double p23=1;
+			double p32=0;
+			
+			opt.algorithm=0;	//algorithm 0 is 4-state, 1 is gilbell
+					
+			NEXT_ARG();
+			p=strtod(*argv,(char **)NULL)/100;
+			
+			NEXT_ARG();
+			r=strtod(*argv,(char **)NULL)/100;						
+			
+			if (NEXT_IS_NUMBER())	{
+			NEXT_ARG();
+			h=(100-strtod(*argv,(char **)NULL))/100;
+						
+						}
+
+			ploss=(r-+p-h*p)/(p+r);
+			burst_length=(1/(r-r*h))*((h*h*(1-h+2*r*h*h-6*r*h+2*r))+(2*h*(1-h)*(1-h+r*h*h-3*h*r+r))+((1-h)*(1-h)*(1-h)));
+			
+			if(h!=0) rho=(1-h)/(r*burst_length);
+			else rho=1;
+	
+			p13=(-ploss)/(burst_length*(-rho+ploss));
+			p31=1/(burst_length*rho);
+
+			if (rho<1)	{	
+        		p32=(1+rho*rho*burst_length-rho-burst_length*rho) / (rho-rho*burst_length);
+			p23=(burst_length*rho-1) / (burst_length-1);			
+			}
+
+			else 	{
+			p32=0;
+			p23=1;
+			}
+
+			printf("\nTransition probabilities are:\n ");
+			printf("--------------------------------");
+			printf("\np13 is %.3f%% ", 100*p13);
+			printf("\np31 is %.3f%% ", 100*p31);
+			printf("\np32 is %.3f%% ", 100*p32);
+			printf("\np23 is %.3f%% ", 100*p23);
+			printf("\np14 is 0.000%%\n");
+			
+			printf("\nGI (General and Intuitive) parameters will be: \n");
+			printf("--------------------------------");
+			printf("\nploss is %.3f%% ", 100*ploss);
+			printf("\nburst length is %.3f", burst_length);
+			printf("\nburst density is %.3f%% ", 100*rho);
+			printf("\nisolated ploss is 0.000%% ");
+			printf("\ngood burst length is %.3f\n ", 1/p23); 
+
+			if(opt.query==0)	{
+			opt.p13=4294967295u*p13;
+			opt.p31=4294967295u*p31;
+			if(rho!=1) {
+			opt.p32=4294967295u*p32;
+			opt.p23=4294967295u*p23;
+			}
+			else {
+			opt.p32=0;
+			opt.p23=4294967295u;
+			}
+						}	
+			
+			if(opt.query==1) return -1;	
+
+		} else if (matches(*argv, "loss_gilbell_4s") == 0)  {
+			
+			double p=0;
+			double r=0;
+			double h=0;
+			double k=1;
+			double ploss=0;
+			double burst_length=1;
+			double rho=1;
+			double pisol=0;	
+			double p13=0;
+			double p31=1;
+			double p23=1;
+			double p32=0;
+			double p14=0;
+
+			opt.algorithm=0;	//algoritnm 1 is gilbell
+					
+			NEXT_ARG();
+			p=strtod(*argv,(char **)NULL)/100;
+			
+			NEXT_ARG();
+			r=strtod(*argv,(char **)NULL)/100;
+						
+			
+			if (NEXT_IS_NUMBER())	{
+			NEXT_ARG();
+			h=(100-strtod(*argv,(char **)NULL))/100;
+						
+			if (NEXT_IS_NUMBER())	{
+			NEXT_ARG();
+			k=(100-strtod(*argv,(char **)NULL))/100;
+			
+						}
+						}
+
+			ploss=(r-k*r+p-h*p)/(p+r);
+			burst_length=(1/(r-r*h))*((h*h*(1-h+2*r*h*h-6*r*h+2*r))+(2*h*(1-h)*(1-h+r*h*h-3*h*r+r))+((1-h)*(1-h)*(1-h)));
+			
+			if(h!=0) rho=(1-h)/(r*burst_length);
+			else rho=1;
+	
+			if(k!=1) pisol=1-k;
+			else pisol=0;
+	
+			p13=(pisol-ploss)/(burst_length*(pisol*(rho-1)-rho+ploss));
+			p31=1/(burst_length*rho);
+
+			if (rho<1)	{	
+        		p32=(1+rho*rho*burst_length-rho-burst_length*rho) / (rho-rho*burst_length);
+			p23=(burst_length*rho-1) / (burst_length-1);			
+			}
+
+			else 	{
+			p32=0;
+			p23=1;
+			}
+
+			if (pisol!=0) p14=(pisol) / (1-pisol);
+			else p14=0;			
+			
+			printf("\nTransition probabilities are:\n ");
+			printf("--------------------------------");
+			printf("\np13 is %.3f%% ", 100*p13);
+			printf("\np31 is %.3f%% ", 100*p31);
+			printf("\np32 is %.3f%% ", 100*p32);
+			printf("\np23 is %.3f%% ", 100*p23);
+			printf("\np14 is %.3f%%\n ", 100*p14);
+			
+			printf("\nGI (General and Intuitive) parameters will be: \n");
+			printf("--------------------------------");
+			printf("\nploss is %.3f%% ", 100*ploss);
+			printf("\nburst length is %.3f", burst_length);
+			printf("\nburst density is %.3f%% ", 100*rho);
+			printf("\nisolated ploss is %.3f%% ", 100*pisol);
+			printf("\ngood burst length is %.3f\n ", 1/p23); 
+
+			if(opt.query==0)	{
+			opt.p13=4294967295u*p13;
+			opt.p31=4294967295u*p31;
+			if(rho!=1) {
+			opt.p32=4294967295u*p32;
+			opt.p23=4294967295u*p23;
+			}
+			else {
+			opt.p32=0;
+			opt.p23=4294967295u;
+			}
+			if(pisol>0) opt.p14=4294967295u*p14;
+			else opt.p14=0;		
+						}
+						
+			if(opt.query==1) return -1;				
+					
+		} else if (matches(*argv, "loss_pattern") == 0)  {	//LOSS PATTERN		
+			NEXT_ARG();
+						
+			int i; 
+					
+			FILE *sequence;
+			
+			sequence=fopen(*argv, "r");
+			
+			if (sequence == NULL) {
+				printf("Could not open the file %s \n", *argv);
+				exit(1);  } 				
+
+			fseek(sequence, 0, SEEK_END);
+			fgetpos(sequence, &opt.pattern_length);
+			rewind(sequence);
+
+			opt.user_pattern=malloc(opt.pattern_length*sizeof(int));
+			opt.pattern_repetitions=0;  			
+
+			for(i=1; i<opt.pattern_length; i++) {
+			if(fgetc(sequence)=='1') opt.user_pattern[i-1]=1;			
+			else opt.user_pattern[i-1]=0; }
+
+  			fclose(sequence);
+   			
+   			if (NEXT_IS_NUMBER()) {			
+			NEXT_ARG();
+			opt.pattern_repetitions=strtod(*argv,(char **)NULL);
+						}
 		} else if (matches(*argv, "reorder") == 0) {
 			NEXT_ARG();
 			present[TCA_NETEM_REORDER] = 1;
@@ -344,6 +865,46 @@
 	}
 
 	fprintf(f, "limit %d", qopt.limit);
+	if(qopt.logging!=0) fprintf(f, " logging %d", qopt.logging); 
+	if(qopt.pattern_length!=0) fprintf(f, " pattern_length %d", qopt.pattern_length);
+	if(qopt.pattern_repetitions!=0) fprintf(f, " pattern_repetitions %d", qopt.pattern_repetitions);
+	int j;
+	for (j=1; j<qopt.pattern_length; j++) {
+	fprintf(f, " pattern element %d is %d\n", j-1, qopt.user_pattern[j-1]);
+						}
+	
+	if (qopt.latency) {
+		fprintf(f, " delay %s", sprint_ticks(qopt.latency, b1));
+
+		if (qopt.jitter) {
+			fprintf(f, "  %s", sprint_ticks(qopt.jitter, b1));
+			if (cor && cor->delay_corr)
+				fprintf(f, " %s", sprint_percent(cor->delay_corr, b1));
+		}
+	}
+
+	if (qopt.loss) {
+		fprintf(f, " loss %s", sprint_percent(qopt.loss, b1));
+		if (cor && cor->loss_corr)
+			fprintf(f, " %s", sprint_percent(cor->loss_corr, b1));
+	}
+	
+	if (qopt.p13) {								
+		fprintf(f, " p13 %s", sprint_percent(qopt.p13, b1));
+		fprintf(f, " p31 %s", sprint_percent(qopt.p31, b1));
+		fprintf(f, " p32 %s", sprint_percent(qopt.p32, b1));
+		fprintf(f, " p23 %s", sprint_percent(qopt.p23, b1));
+		fprintf(f, " p14 %s", sprint_percent(qopt.p14, b1));
+			}	
+			
+	if (qopt.gilb_p) {								
+		fprintf(f, " p %s", sprint_percent(qopt.gilb_p, b1));
+		fprintf(f, " r %s", sprint_percent(qopt.gilb_r, b1));
+		fprintf(f, " h %s", sprint_percent(qopt.gilb_h, b1));
+		if (qopt.gilb_k) fprintf(f, " k %s", sprint_percent(qopt.gilb_k, b1));
+			}		
+
+	fprintf(f, "limit %d", qopt.limit);
 
 	if (qopt.latency) {
 		fprintf(f, " delay %s", sprint_ticks(qopt.latency, b1));

^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: [PATCH] netem/iproute2 solving correlated loss issues [2/5]
  2009-12-18 11:24 ` [PATCH] netem/iproute2 solving correlated loss issues [2/5] Fabio Ludovici
@ 2009-12-18 17:36   ` Stephen Hemminger
  2009-12-18 23:49     ` Stefano Salsano
  2009-12-19  4:01     ` David Miller
  0 siblings, 2 replies; 8+ messages in thread
From: Stephen Hemminger @ 2009-12-18 17:36 UTC (permalink / raw)
  To: Fabio Ludovici; +Cc: netdev

On Fri, 18 Dec 2009 12:24:38 +0100
Fabio Ludovici <fabio.ludovici@yahoo.it> wrote:

> patch 2/5 : linux-2.6.32/net/sched/sch_netem.c

Could you send with official signed-off-by line please?

Need some style work to match kernel coding style (not a big issue).
And it would be helpful to put in more descriptive variable names
or documentation. But I will try and address these and resubmit,
keeping you as original author.


^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: [PATCH] netem/iproute2 solving correlated loss issues [2/5]
  2009-12-18 17:36   ` Stephen Hemminger
@ 2009-12-18 23:49     ` Stefano Salsano
  2009-12-19  4:01     ` David Miller
  1 sibling, 0 replies; 8+ messages in thread
From: Stefano Salsano @ 2009-12-18 23:49 UTC (permalink / raw)
  To: Stephen Hemminger; +Cc: Fabio Ludovici, netdev

Stephen Hemminger wrote:
> On Fri, 18 Dec 2009 12:24:38 +0100
> Fabio Ludovici <fabio.ludovici@yahoo.it> wrote:
>> patch 2/5 : linux-2.6.32/net/sched/sch_netem.c
> 
> Could you send with official signed-off-by line please?

we will resend this (and the other related patches) with the 
signed-off-by line, sorry !

> Need some style work to match kernel coding style (not a big issue).
> And it would be helpful to put in more descriptive variable names
> or documentation. But I will try and address these and resubmit,
> keeping you as original author.

we'll try to address some of the issues in the resubmission of the patch

you are very welcome to add yourself as author if you wish, in case you 
will help us with styling/renaming/documentation !

thank you
Stefano & Fabio
-- 
*******************************************************************
Stefano Salsano
Dipartimento Ingegneria Elettronica
Universita' di Roma "Tor Vergata"
Via del Politecnico, 1 - 00133 Roma - ITALY

http://netgroup.uniroma2.it/Stefano_Salsano/

E-mail  : stefano.salsano@uniroma2.it
Cell.   : +39 320 4307310
Office  : (Tel.) +39 06 72597770  (Fax.) +39 06 72597435
*******************************************************************

^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: [PATCH] netem/iproute2 solving correlated loss issues [2/5]
  2009-12-18 17:36   ` Stephen Hemminger
  2009-12-18 23:49     ` Stefano Salsano
@ 2009-12-19  4:01     ` David Miller
  2009-12-19  9:48       ` Stefano Salsano
  1 sibling, 1 reply; 8+ messages in thread
From: David Miller @ 2009-12-19  4:01 UTC (permalink / raw)
  To: shemminger; +Cc: fabio.ludovici, netdev

From: Stephen Hemminger <shemminger@vyatta.com>
Date: Fri, 18 Dec 2009 09:36:05 -0800

> On Fri, 18 Dec 2009 12:24:38 +0100
> Fabio Ludovici <fabio.ludovici@yahoo.it> wrote:
> 
>> patch 2/5 : linux-2.6.32/net/sched/sch_netem.c
> 
> Could you send with official signed-off-by line please?
> 
> Need some style work to match kernel coding style (not a big issue).
> And it would be helpful to put in more descriptive variable names
> or documentation. But I will try and address these and resubmit,
> keeping you as original author.

I would like some kind of commit message which at least
explains what in the world this stuff is, how it works,
why we want it etc.

Furthermore it is fundamentally flawed in it's implementation
in that the user exported data structures cannot be changed,
you cannot change the layout and you absolutely cannot
change the size of these things or else various tool and
kernel combinations stop working.

^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: [PATCH] netem/iproute2 solving correlated loss issues [2/5]
  2009-12-19  4:01     ` David Miller
@ 2009-12-19  9:48       ` Stefano Salsano
  0 siblings, 0 replies; 8+ messages in thread
From: Stefano Salsano @ 2009-12-19  9:48 UTC (permalink / raw)
  To: David Miller; +Cc: shemminger, fabio.ludovici, netdev

David Miller wrote:
> I would like some kind of commit message which at least
> explains what in the world this stuff is, how it works,
> why we want it etc.
> 

you're right we will put this information in the commit messages, some 
hints hereafter:

starting from the consideration that the model for generating correlated 
loss is broken in current netem (as for example described in
https://lists.linux-foundation.org/pipermail/netem/2007-September/001156.html)
we have implemented a more general loss model

the patch allows to generate loss patterns according to a determinist 
pattern that can be given as input:

tc qdisc add/change dev eth0 root netem loss_pattern filename

or according to different loss models including the ones commonly used 
in the literature (bernoulli, gilbert, gilbert-elliot...)

tc qdisc add/change dev eth0 root netem loss_bern       p
tc qdisc add/change dev eth0 root netem loss_gilb       p r [1-h]
tc qdisc add/change dev eth0 root netem loss_gilbell    p r [1-h [1-k]]
tc qdisc add/change dev eth0 root netem loss_GI         ploss 
[burst_length [density [pisol [good_burst_length]]]]
tc qdisc add/change dev eth0 root netem loss_GI_tran    p13 p31 [p32 p23 
[p14]]
tc qdisc add/change dev eth0 root netem loss_gilb_4s    p r [1-h]
tc qdisc add/change dev eth0 root netem loss_gilbell_4s p r [1-h [1-k]]

(full explanation is reported in 
http://netgroup.uniroma2.it/twiki/bin/view.cgi/Main/NetEm2)


-- 
*******************************************************************
Stefano Salsano
Dipartimento Ingegneria Elettronica
Universita' di Roma "Tor Vergata"
Via del Politecnico, 1 - 00133 Roma - ITALY

http://netgroup.uniroma2.it/Stefano_Salsano/

E-mail  : stefano.salsano@uniroma2.it
Cell.   : +39 320 4307310
Office  : (Tel.) +39 06 72597770  (Fax.) +39 06 72597435
*******************************************************************

^ permalink raw reply	[flat|nested] 8+ messages in thread

end of thread, other threads:[~2009-12-19  9:48 UTC | newest]

Thread overview: 8+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
     [not found] <4B2B5A26.8050400@uniroma2.it>
2009-12-18 11:24 ` [PATCH] netem/iproute2 solving correlated loss issues [2/5] Fabio Ludovici
2009-12-18 17:36   ` Stephen Hemminger
2009-12-18 23:49     ` Stefano Salsano
2009-12-19  4:01     ` David Miller
2009-12-19  9:48       ` Stefano Salsano
2009-12-18 11:27 ` [PATCH] netem/iproute2 solving correlated loss issues [3/5] Fabio Ludovici
2009-12-18 11:30 ` [PATCH] netem/iproute2 solving correlated loss issues [4/5] Fabio Ludovici
     [not found] ` <4B2B5A65.1060300@uniroma2.it>
2009-12-18 11:30   ` [PATCH] netem/iproute2 solving correlated loss issues [5/5] Fabio Ludovici

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).