[Sumover-dev] [svn commit] r4273 - vic/branches/cc/cc
sumover-dev at cs.ucl.ac.uk
sumover-dev at cs.ucl.ac.uk
Fri Aug 15 14:03:07 BST 2008
Author: soohyunc
Date: Fri Aug 15 14:03:07 2008
New Revision: 4273
Modified:
vic/branches/cc/cc/tfwc_rcvr.cpp
vic/branches/cc/cc/tfwc_rcvr.h
vic/branches/cc/cc/tfwc_sndr.cpp
vic/branches/cc/cc/tfwc_sndr.h
Log:
o added in (TfwcSndr)
(1) loss history calculation
(2) generate weight for history calculation
(3) interpret received ackvec to real packet sequence numbers
(4) generate margin vector (emulating TCP's 3dupacks)
o To be added in (TfwcSndr)
(1) loss interval
(2) new RTO
(3) detect the very first packet loss
(i.e., until the very first packet loss, it just goes to AIMD process)
Modified: vic/branches/cc/cc/tfwc_rcvr.cpp
==============================================================================
--- vic/branches/cc/cc/tfwc_rcvr.cpp (original)
+++ vic/branches/cc/cc/tfwc_rcvr.cpp Fri Aug 15 14:03:07 2008
@@ -75,11 +75,13 @@
}
}
+ // trim ackvec
+ int offset = currseq_ - ackofack_;
+ if (ackofack_)
+ trimvec(tfwcAV, offset);
+
// set this seqno to the prevseq before exit
prevseq_ = currseq_;
-
- // trim ackvec
- trimvec(tfwcAV);
}
// parse timestamp
else if (type == XR_BT_3) {
Modified: vic/branches/cc/cc/tfwc_rcvr.h
==============================================================================
--- vic/branches/cc/cc/tfwc_rcvr.h (original)
+++ vic/branches/cc/cc/tfwc_rcvr.h Fri Aug 15 14:03:07 2008
@@ -53,12 +53,8 @@
u_int16_t ackofack_; // ackofack
private:
// trim ackvec
- inline void trimvec(u_int32_t ackvec) {
- int n = ackofack_ - 1;
- if (currseq_ > ackofack_)
- tfwcAV = ackvec >> n << n;
- else
- tfwcAV = ackvec << n >> n;
+ inline void trimvec(u_int32_t vec, int offset) {
+ tfwcAV = vec >> offset;
}
u_int32_t ts_echo_; // for time stamp echoing
Modified: vic/branches/cc/cc/tfwc_sndr.cpp
==============================================================================
--- vic/branches/cc/cc/tfwc_sndr.cpp (original)
+++ vic/branches/cc/cc/tfwc_sndr.cpp Fri Aug 15 14:03:07 2008
@@ -49,15 +49,26 @@
seqno_(0),
cwnd_(1),
aoa_(0),
- now_(0),
+ t_now_(0),
ts_(0),
ts_echo_(0),
- last_ack_(0),
+ now_(0),
+ lastest_ack_(0),
ndtp_(0),
nakp_(0),
ntep_(0),
+ nsve_(0),
epoch_(1)
{
+ // allocate tsvec_ in memory
+ tsvec_ = (double *)malloc(sizeof(double)* TSZ);
+ // allocate seqvec in memory
+ seqvec_ = (u_int32_t *)malloc(sizeof(u_int32_t)* SSZ );
+
+ // for simulating TCP's 3 dupack rule
+ u_int32_t mvec_ = 0x00;
+ UNUSED(mvec_); // to shut up gcc-4.x
+
minrto_ = 0.0;
maxrto_ = 100000.0;
srtt_ = -1.0;
@@ -69,10 +80,6 @@
beta_ = 0.25;
g_ = 0.01;
k_ = 4;
-
- // for simulating TCP's 3 dupack rule
- u_int32_t mvec_ = 0x00;
- UNUSED(mvec_); // to shut up gcc-4.x
}
void TfwcSndr::tfwc_sndr_send(pktbuf* pb) {
@@ -82,10 +89,11 @@
// get seqno and mark timestamp for this data packet
seqno_ = ntohs(rh->rh_seqno);
- now_ = tfwc_sndr_now();
+ now_ = tfwc_sndr_now(); // double type (reference time)
+ t_now_ = tfwc_sndr_t_now(); // u_int32_t type (reference time)
// timestamp vector for loss history update
- //tsvec_[seqno_%TSZ - 1] = now_;
+ tsvec_[seqno_%TSZ - 1] = now_;
// sequence number must be greater than zero
assert (seqno_ > 0);
@@ -98,36 +106,63 @@
{
// retrieve ackvec
if (type == XR_BT_1) {
+ UNUSED(ts_echo);
nakp_++; // number of ackvec packet received
- ackv_ = ackv; // store ackvec
+ //ackv_ = ackv; // store ackvec
+
+ // lastest ack (head of ackvec)
+ lastest_ack_ = get_head_pos(ackv) + aoa_;
- // store head of ackvec as last ack (real number)
- last_ack_ = get_head_pos(ackv_) * epoch_;
+ // generate seqno vec
+ gen_seqno_vec(ackv);
// generate margin vector
- marginvec(ackv_);
- ackv_ |= mvec_; // masking ackvec
+ marginvec(ackv);
// detect loss
+ is_loss_ = detect_loss(seqvec_, mvec_[DUPACKS-1] - 1, aoa_);
// congestion window control
+ control(seqvec_);
// set ackofack (real number)
- aoa_ = ackofack(mvec_) * epoch_;
+ aoa_ = ackofack();
+
+ // update RTT with the sampled RTT
+ tao_ = tfwc_sndr_now() - tsvec_[seqno_%TSZ];
+ update_rtt(tao_);
}
// retrieve ts echo
else if (type == XR_BT_3) {
ntep_++; // number of ts echo packet received
- ts_echo_ = ts_echo;
- debug_msg(" ts echo: %d\n", ts_echo_);
+ /*
+ ts_echo_ = ts_echo;
+ debug_msg(" ts echo: %d\n", ts_echo_);
+
+ tao_ = 1e-6 * (double)(tfwc_sndr_now() - ts_echo_);
- tao_ = (double)(tfwc_sndr_now() - ts_echo_)/1000000;
-
// update RTT
update_rtt(tao_);
+ */
}
}
+bool TfwcSndr::detect_loss(u_int32_t* vec, u_int16_t end, u_int16_t begin) {
+ bool ret; // 'true' when there is a loss
+ int lc = 0; // counter
+
+ // number of tempvec element
+ int numvec = (end - begin < 0) ? 0 : end - begin;
+ int tempvec[numvec];
+ bool is_there;
+
+ for (int i = 0; i < numvec; i++) {
+ tempvec[i] = (begin + 1) + i;
+ // is there stuff
+ }
+ return ret = (lc > 0) ? true : false;
+}
+
void TfwcSndr::update_rtt(double rtt_sample) {
// calculate smoothed RTT
@@ -152,3 +187,69 @@
if (rto_ > maxrto_)
rto_ = maxrto_;
}
+
+void TfwcSndr::control(u_int32_t* seqvec) {
+ loss_history(seqvec);
+
+}
+
+void TfwcSndr::gen_weight() {
+#ifdef SHORT_HISTORY
+ // this is just weighted moving average (WMA)
+ for(int i = 0; i <= HSZ; i++){
+ if(i < HSZ/2)
+ weight_[i] = 1.0;
+ else
+ weight_[i] = 1.0 - (i-(HSZ/2 - 1.0)) / (HSZ/2 + 1.0);
+ }
+#else
+ // this is exponentially weighted moving average (EWMA)
+ for (int i=0; i <= HSZ; i++) {
+ if (i < HSZ/4)
+ weight_[i] = 1.0;
+ else
+ weight_[i] = 2.0 / (i - 1.0);
+ }
+#endif
+}
+
+void TfwcSndr::loss_history(u_int32_t* seqvec) {
+ pseudo_interval_ = 1 / p_;
+
+ /* bzero for all history information */
+ for(int i = 0; i <= HSZ+1; i++)
+ history_[i] = 0;
+
+ /* (let) most recent history information be 0 */
+ history_[0] = 0;
+
+ /* (let) the pseudo interval be the first history information */
+ history_[1] = (int) pseudo_interval_;
+}
+
+void TfwcSndr::pseudo_p() {
+ for (pseudo_p_ = 0.00001; pseudo_p_ < 1.0; pseudo_p_ += 0.00001) {
+ f_p_ = sqrt((2.0/3.0) * pseudo_p_) + 12.0 * pseudo_p_ *
+ (1.0 + 32.0 * pow(pseudo_p_, 2.0)) * sqrt((3.0/8.0) * pseudo_p_);
+
+ t_win_ = 1 / f_p_;
+
+ if(t_win_ < tmp_cwnd_)
+ break;
+ }
+ p_ = pseudo_p_;
+}
+
+void TfwcSndr::pseudo_history() {
+ pseudo_interval_ = 1 / p_;
+
+ /* bzero for all history information */
+ for(int i = 0; i <= HSZ+1; i++)
+ history_[i] = 0;
+
+ /* (let) most recent history information be 0 */
+ history_[0] = 0;
+
+ /* (let) the pseudo interval be the first history information */
+ history_[1] = (int) pseudo_interval_;
+}
Modified: vic/branches/cc/cc/tfwc_sndr.h
==============================================================================
--- vic/branches/cc/cc/tfwc_sndr.h (original)
+++ vic/branches/cc/cc/tfwc_sndr.h Fri Aug 15 14:03:07 2008
@@ -39,7 +39,14 @@
#define DUPACKS 3 // simulating TCP's 3 dupacks
#define CHB 0x80000000 // ackvec check bit (head search)
#define CTB 0x01 // ackvec check bit (tail search)
-#define TSZ 1000 // tsvec_ size
+#define TSZ 1000 // tsvec_ size
+#define SSZ 1000 // seqvec_ size
+
+#ifdef SHORT_HISTORY
+#define HSZ 8 // history size for avg loss history
+#else
+#define HSZ 16 // history size for avg loss history
+#endif
// set AckVec bitmap from LSB
#define SET_BIT_VEC(ackvec_, bit) (ackvec_ = ((ackvec_ << 1) | bit))
@@ -53,25 +60,40 @@
// AckVec tail search
#define GET_TAIL_VEC(ackvec_, i) ( ackvec_ & (CTB << i) )
+// check bit at i-th location
+#define CHECK_BIT_AT(vec, i) ( vec & (1 << (i-1)) )
+
class TfwcSndr {
public:
TfwcSndr();
// parse RTP data packet from Transmitter module
void tfwc_sndr_send(pktbuf*);
+
+ // main reception path (XR packet)
void tfwc_sndr_recv(u_int16_t type, u_int32_t ackv, u_int32_t ts_echo);
// return current data packet's seqno
inline u_int16_t tfwc_sndr_get_seqno() { return seqno_; }
+
// return ackofack
inline u_int16_t tfwc_sndr_get_aoa() { return aoa_; }
- // set timestamp (TfwcSndr)
- inline u_int32_t tfwc_sndr_now() {
+
+ // set timestamp in u_int32_t type (TfwcSndr)
+ inline u_int32_t tfwc_sndr_t_now() {
+ timeval tv;
+ ::gettimeofday(&tv, 0);
+ return (tv.tv_sec + tv.tv_usec);
+ }
+
+ // set timestamp in double type (TfwcSndr)
+ inline double tfwc_sndr_now() {
timeval tv;
::gettimeofday(&tv, 0);
- return (u_int32_t) (tv.tv_sec + tv.tv_usec);
+ return ((double) tv.tv_sec + 1e-6 * (double) tv.tv_usec);
}
- // return timestamp
- inline u_int32_t tfwc_sndr_get_ts() { return now_; }
+
+ // return timestamp in u_int32_t type
+ inline u_int32_t tfwc_sndr_get_ts() { return t_now_; }
// variables
u_int16_t seqno_; // packet sequence number
@@ -97,35 +119,81 @@
return (l + 1);
}
// generate margin vector
- inline void marginvec(u_int32_t ackvec) {
- int head = get_head_pos(ackvec);
+ inline void marginvec(u_int32_t vec) {
+ int hseq = get_head_pos(vec) + aoa_; // ackvec head seqno
+
+ for (int i = 0; i < DUPACKS; i++) {
+ mvec_[i] = hseq - i;
- for (int i = 0; i < DUPACKS; i++)
- mvec_ |= 1 << ((head-1) - i);
+ // round up if it is less than zero
+ mvec_[i] = (mvec_[i] <= 0) ? 0 : mvec_[i];
+ }
+ }
+ // generate seqno vector (interpret ackvec to real sequence numbers)
+ inline void gen_seqno_vec(u_int32_t vec) {
+ int hseq = get_head_pos(vec) + aoa_; // ackvec head seqno
+ int cnt = hseq - aoa_;
+
+ for (int i = 0; i < cnt; i++) {
+ seqvec_[i%SSZ] = hseq - i;
+ }
}
// ackofack
- inline u_int16_t ackofack (u_int32_t ackvec) {
- return (get_tail_pos(ackvec) - 1);
+ inline u_int16_t ackofack () {
+ return (mvec_[DUPACKS - 1] - 1);
}
- u_int32_t mvec_; // margin vec (simulatinmg TCP 3 dupacks)
+ u_int32_t mvec_[DUPACKS]; // margin vec (simulatinmg TCP 3 dupacks)
u_int32_t ackv_; // received AckVec (from TfwcRcvr)
u_int32_t pvec_; // sent packet list
u_int16_t aoa_; // ack of ack
- u_int32_t now_; // the time when the data packet sent
+ u_int32_t t_now_; // the time when the data packet sent
u_int32_t ts_; // time stamp
u_int32_t ts_echo_; // echo time stamp from the receiver
- u_int32_t *tsvec_; // timestamp vector
+ double now_; // real-time now
double tao_; // sampled RTT
private:
// update RTT
- void update_rtt(double tao); // update RTT
+ void update_rtt(double tao);
+
+ // detect packet loss
+ bool detect_loss(u_int32_t*, u_int16_t, u_int16_t);
+
+ // control congestion window
+ void control(u_int32_t* seqvec);
+
+ // calculate loss history
+ void loss_history(u_int32_t* seqvec);
+
+ // estimate loss history and loss probability
+ void pseudo_p();
+ void pseudo_history();
+
+ void gen_weight();
- u_int16_t last_ack_; // last packet seqno from ackvec
+ u_int16_t lastest_ack_; // lastest seqno from ackvec
+ u_int32_t *seqvec_; // generated seqno vec
+ double *tsvec_; // timestamp vector
int ndtp_; // number of data packet sent
int nakp_; // number of ackvec packet received
int ntep_; // number of ts echo packet received
+ int nsve_; // number of seqvec element
int epoch_; // communication epoch
+ bool is_loss_;
+ double f_p_; // f(p) = sqrt(2/3)*p + 12*p*(1+32*p^2)*sqrt(3/8)*p
+ double p_; // packet loss probability
+ double t_win_; // temporal cwin size to get p_ value
+ int tmp_cwnd_; // temporary cwnd value
+ double pseudo_p_; // faked packet loss probability
+ double pseudo_interval_;// faked loss interval
+ double avg_interval_; // average loss interval
+ double history_[HSZ+1]; // loss interval history
+ double weight_[HSZ+1]; // weight for calculating avg loss interval
+ double I_tot_; // total sum
+ double I_tot0_; // from 0 to n-1
+ double I_tot1_; // form 1 to n
+ double tot_weight_; // total weight
+ int hsz_; // current history size
// RTT related variables
double srtt_; // smoothed RTT
@@ -135,10 +203,10 @@
double maxrto_; // max RTO
double alpha_; // smoothing factor for RTT/RTO calculation
double beta_; // smoothing factor for RTT/RTO calculation
- double g_; // timer granularity
- int k_; // k value
- double t0_; // t0 value at TCP throughput equation
- double df_; // decay factor
+ double g_; // timer granularity
+ int k_; // k value
+ double t0_; // t0 value at TCP throughput equation
+ double df_; // decay factor
double sqrtrtt_; // the mean of the sqrt of RTT
};
More information about the Sumover-dev
mailing list