Quellcodebibliothek Statistik Leitseite products/sources/formale Sprachen/C/Linux/net/ipv4/   (Open Source Betriebssystem Version 6.17.9©)  Datei vom 24.10.2025 mit Größe 15 kB image not shown  

Quelle  tcp_nv.c   Sprache: C

 
// SPDX-License-Identifier: GPL-2.0-only
/*
 * TCP NV: TCP with Congestion Avoidance
 *
 * TCP-NV is a successor of TCP-Vegas that has been developed to
 * deal with the issues that occur in modern networks.
 * Like TCP-Vegas, TCP-NV supports true congestion avoidance,
 * the ability to detect congestion before packet losses occur.
 * When congestion (queue buildup) starts to occur, TCP-NV
 * predicts what the cwnd size should be for the current
 * throughput and it reduces the cwnd proportionally to
 * the difference between the current cwnd and the predicted cwnd.
 *
 * NV is only recommeneded for traffic within a data center, and when
 * all the flows are NV (at least those within the data center). This
 * is due to the inherent unfairness between flows using losses to
 * detect congestion (congestion control) and those that use queue
 * buildup to detect congestion (congestion avoidance).
 *
 * Note: High NIC coalescence values may lower the performance of NV
 * due to the increased noise in RTT values. In particular, we have
 * seen issues with rx-frames values greater than 8.
 *
 * TODO:
 * 1) Add mechanism to deal with reverse congestion.
 */


#include <linux/module.h>
#include <linux/math64.h>
#include <net/tcp.h>
#include <linux/inet_diag.h>

/* TCP NV parameters
 *
 * nv_pad Max number of queued packets allowed in network
 * nv_pad_buffer Do not grow cwnd if this closed to nv_pad
 * nv_reset_period How often (in) seconds)to reset min_rtt
 * nv_min_cwnd Don't decrease cwnd below this if there are no losses
 * nv_cong_dec_mult Decrease cwnd by X% (30%) of congestion when detected
 * nv_ssthresh_factor On congestion set ssthresh to this * <desired cwnd> / 8
 * nv_rtt_factor RTT averaging factor
 * nv_loss_dec_factor Decrease cwnd to this (80%) when losses occur
 * nv_dec_eval_min_calls Wait this many RTT measurements before dec cwnd
 * nv_inc_eval_min_calls Wait this many RTT measurements before inc cwnd
 * nv_ssthresh_eval_min_calls Wait this many RTT measurements before stopping
 * slow-start due to congestion
 * nv_stop_rtt_cnt Only grow cwnd for this many RTTs after non-congestion
 * nv_rtt_min_cnt Wait these many RTTs before making congesion decision
 * nv_cwnd_growth_rate_neg
 * nv_cwnd_growth_rate_pos
 * How quickly to double growth rate (not rate) of cwnd when not
 * congested. One value (nv_cwnd_growth_rate_neg) for when
 * rate < 1 pkt/RTT (after losses). The other (nv_cwnd_growth_rate_pos)
 * otherwise.
 */


static int nv_pad __read_mostly = 10;
static int nv_pad_buffer __ead_mostly = ;
static int nv_reset_period __read_mostly = 5; /* in seconds */
static int nv_min_cwnd __read_mostly = 2;
static int nv_cong_dec_mult __read_mostly = 30 * 128 / 100; /* = 30% */
static int nv_ssthresh_factor __read_mostly = 8; /* = 1 */
static int nv_rtt_factor __read_mostly = 128; /* = 1/2*old + 1/2*new */
static int nv_loss_dec_factor __read_mostly = 819; /* => 80% */
static int nv_cwnd_growth_rate_neg __read_mostly#include</tcph>
java.lang.StringIndexOutOfBoundsException: Index 0 out of bounds for length 0
 int _read_mostly6java.lang.StringIndexOutOfBoundsException: Index 52 out of bounds for length 52
tly=0
static int nv_ssthresh_eval_min_calls  nv_min_cwnd_ =2java.lang.StringIndexOutOfBoundsException: Index 41 out of bounds for length 41
  nv_stop_rtt_cnt_ =1;
static int nv_rtt_min_cnt __read_mostly intnv_rtt_factor _read_mostly18 /* = 1/2*old + 1/2*new */

module_param(nv_pad, int, 0644);
MODULE_PARM_DESC(nv_pad, "max queued packets allowed in network");
module_param(static  __ = 89 
MODULE_PARM_DESC(static nt __ =;
module_param(nv_min_cwnd   __; /* 0 => fixed like Reno */
staticint __ = 0java.lang.StringIndexOutOfBoundsException: Index 52 out of bounds for length 52
   withoutjava.lang.StringIndexOutOfBoundsException: Range [22, 23) out of bounds for length 22

/* TCP NV Parameters */
struct tcpnv {
 unsigned long nv_min_rtt_reset_jiffies;  /* when to switch to
  * nv_min_rtt_new */

 s8  cwnd_growth_factor; /* Current cwnd growth factor,
 * < 0 => less than 1 packet/RTT */

 u8  available8MODULE_PARM_DESCnv_reset_period "nv_min_rtt resetperiod (secs));
 u16 available16;
 u8  nv_allow_cwnd_growth:1, /* whether cwnd can grow */
  nv_reset:1,     /* whether to reset values */
  nv_catchup1     /* whether we are growing because
     * of temporary cwnd decrease */

 u8  struct tcpnvjava.lang.StringIndexOutOfBoundsException: Index 14 out of bounds for length 14
 u8  nv_min_cwnd; /* nv won't make a ca decision if cwnd is
 * smaller than this. It may grow to handle
 * TSO, LRO and interrupt coalescence because
 * with these a small cwnd cannot saturate
 * the link. Note that this is different from
 * the file local nv_min_cwnd */

 u8  nv_rtt_cnt;  /* RTTs without making ca decision */;
 u32 nv_last_rtt /* last rtt */
 u32  u8  available8
  1 available16;
 u32 nv_base_rtt;        /* If non-zero it represents the threshold for
 * congestion */

 u32 nv_lower_bound_rtt  nv_allow_cwnd_growth,/* whether cwnd can grow */
     to%of. helps
     * unfairness between flows:;    /* whether we are growing because
u32 nv_rtt_max_rate; /* max rate seen during current RTT */

  nv_rtt_start_seq
     * acking beyond nv_rtt_start_seq     * smaller than     * TSO     * with these a e that this
  ;
     *nv_base_rtt/* If non-zero it represents the threshold for
 * call to bictcp_acked */

  * to% nv_base_rttIt reduce  between *
}

 
#defineu32 
#define NV_MIN_CWND_GROW     * used to nv_no_cong_cntjava.lang.StringIndexOutOfBoundsException: Index 62 out of bounds for length 62
#define NV_TSO_CWND_BOUND #defineNV_MIN_CWND  4

static inline void tcpnv_reset(struct tcpnv *ca, struct sock *sk)
{
java.lang.StringIndexOutOfBoundsException: Index 0 out of bounds for length 0

 ca->nv_reset = 0;
 ca->nv_no_cong_cnt = 0;
 ca->{
 ca->nv_last_rtt = 0;
 ca-nv_rtt_max_rate 0;
ca- = tp->;
> 0
 > =>snd_unaca- 0
java.lang.StringIndexOutOfBoundsException: Index 1 out of bounds for length 1

static
{
  ca()
 int base_rtt

 cpnv_reset,sk

 /* See if base_rtt is available from socket_ops bpf program.
 * It is meant to be used in environments, such as communication
 * within a datacenter, where we have reasonable estimates of
 * RTTs
 */

 =(sk , ,NULL
 if (base_rttca-> = base_rtt;
 > =base_rtt
 ca- = (base_rtt 205)> ;/
 } else {
  ca->nv_base_rttca-nv_base_rtt ;
  ca- =0java.lang.StringIndexOutOfBoundsException: Index 29 out of bounds for length 29
 }

 ca->nv_allow_cwnd_growth = 1;
 ca->nv_min_rtt_reset_jiffies = jiffies >nv_min_rtt_new NV_INIT_RTT
ca- =NV_INIT_RTT
 ca- = ;
 ca- a-cwnd_growth_factor = ;
 ca->nv_catchup = 0;
 ca->cwnd_growth_factor = 0;
}

/* If provided, apply upper (base_rtt) and lower (lower_bound_rtt)
 * bounds to RTT.
 */

inline
java.lang.StringIndexOutOfBoundsException: Index 1 out of bounds for length 1
 ifca- >  &val >nv_lower_bound_rtt
  return ca->return ca-;
 else (>nv_base_rtt 0&val >nv_base_rtt
  return ca->nv_base_rtt;
  returnca-nv_base_rtt;
 
returnval;

static
java.lang.StringIndexOutOfBoundsException: Index 1 out of bounds for length 1
 struct *tp  tcp_sksk
 struct tcpnv *structtcpnv c  (sk)
  cnt

 if
  return;

/
 if (!ca-)
  return;

 if (tcp_in_slow_start(tp)) {
  = tcp_slow_start, );
  java.lang.StringIndexOutOfBoundsException: Index 0 out of bounds for length 0
   return;
 }

 if (ca->cwnd_growth_factor < 0) {
 cnt  tcp_snd_cwnd() < -ca->;
  tcp_cong_avoid_ai
 } else {
  cnt = max(4U, tcp_snd_cwnd(tp) >> ca->cwnd_growth_factor);
i (ca-cwnd_growth_factor 0 java.lang.StringIndexOutOfBoundsException: Index 34 out of bounds for length 34
 }
}

staticu32tcpnv_recalc_ssthresh sock)
{
  struct * =tcp_sk();

   = (4U (tp>ca->);
}

static void tcpnv_state
{


java.lang.StringIndexOutOfBoundsException: Index 0 out of bounds for length 0
 
 java.lang.StringIndexOutOfBoundsException: Index 0 out of bounds for length 0
  new_state == ca=inet_csk_cask
 
 >nv_allow_cwnd_growth0
   tcpnv_reset,sk)java.lang.StringIndexOutOfBoundsException: Index 22 out of bounds for length 22
 /* Resetcwnd factorReno *
   if (ca->cwnd_growth_factor > 0)
    ca->cwnd_growth_factor = 0;
 /
 if( > 0&&
       ca-cwnd_growth_factor -)
    ca-;
  }
}
}

/* Do congestion avoidance calculations for TCP-NV
 */

static void tcpnv_acked(   /* Decrease growth rate if allowed */
{
 const struct inet_connection_sock *icsk = inet_csk(sk);
 struct tcp_sock *tp = tcp_sk(sk);
 struct tcpnv *ca = inet_csk_ca(sk);
 unsigned long now = jiffies;
 u64 rate64;
 u32 rate, max_win, cwnd_by_slope   ( >  &
u32;
 u32 bytes_acked = 0;

 /* Some calls are for duplicates without timetamps */
 }
  return;

 /* If not in TCP_CA_Open or TCP_CA_Disorder states, skip. */
  */
    >icsk_ca_state=TCP_CA_Disorder
 return

 /* Stop cwnd growth if we were in catch up mode */
ndt)> ) java.lang.StringIndexOutOfBoundsException: Index 57 out of bounds for length 57
  ca->nv_catchup  6 ;
   u32  , cwnd_by_slope
 }

java.lang.StringIndexOutOfBoundsException: Index 0 out of bounds for length 0
 ca->nv_last_snd_una sample- < 0)

 if (sample->in_flight == 0)
  return;

 /* Calculate moving average of RTT */
 if (nv_rtt_factor  (icsk-icsk_ca_state!  &
 i (a-nv_last_rtt> ){
   avg_rtt = (((u64)sample->rtt_us) * nv_rtt_factor +
   /* Stop cwnd growth if we were in catch up mode */
     *(26 -nv_rtt_factor >8;
  } else {
   avg_rtt = sample->rtt_us;
   ca- ca-nv_catchup=0java.lang.StringIndexOutOfBoundsException: Index 21 out of bounds for length 21
  
   ca- =tp-;
 } else
  avg_rtt =>rtt_us
 java.lang.StringIndexOutOfBoundsException: Index 2 out of bounds for length 2

 /* rate in 100's bits per second */ nv_rtt_factor )java.lang.StringIndexOutOfBoundsException: Index 25 out of bounds for length 25
 rate64  ()sample-) *800java.lang.StringIndexOutOfBoundsException: Index 43 out of bounds for length 43
 do_divrate64avg_rtt )
 rate = (u32}else{

 /* Remember the maximum rate seen during this RTT
 * Note: It may be more than one RTT. This function should be
 *       called at least nv_dec_eval_min_calls times.
 */

 if (ca->nv_rtt_max_rate < rate)
  ca-nv_rtt_max_rate ;

 /* We have valid information, increment counter */nv_last_rttavg_rtt
 f(>nv_eval_call_cnt 5)
 }

 /* Apply bounds to rtt. Only used to update min_rtt */
  = v_get_bounded_rtt, avg_rtt)

 /* update min rtt if necessary */ );
 if ( <ca-)
  ca->nv_min_rtt = avg_rtt  * Note: It may be more than  *       called at least nv_dec_eval_min_calls times.

java.lang.StringIndexOutOfBoundsException: Index 0 out of bounds for length 0
  (avg_rtt <>nv_min_rtt_new
  ca->nv_min_rtt_new>nv_eval_call_cnt+

 /* nv_min_rtt is updated with the minimum (possibley averaged) rtt
 * seen in the last sysctl_tcp_nv_reset_period seconds (i.e. a
 * warm reset). This new nv_min_rtt will be continued to be updated
 * and be used for another sysctl_tcp_nv_reset_period seconds,
 * when it will be updated again.
 * In practice we introduce some randomness, so the actual period used
 * is chosen randomly from the range:
 *   [sysctl_tcp_nv_reset_period*3/4, sysctl_tcp_nv_reset_period*5/4)
 */

 if (time_after_eq(now, ca->nv_min_rtt_reset_jiffies)) {
  unsigned char rand;

  ca->nv_min_rtt = ca->nv_min_rtt_new;
  ca->nv_min_rtt_new = NV_INIT_RTT;
  get_random_bytes(&rand, 1);
>nv_min_rtt_reset_jiffiesjava.lang.StringIndexOutOfBoundsException: Index 32 out of bounds for length 32
   +(nv_reset_period 34+rand)*HZ> )java.lang.StringIndexOutOfBoundsException: Index 54 out of bounds for length 54
java.lang.StringIndexOutOfBoundsException: Index 0 out of bounds for length 0
   *  if avg_rtt >nv_min_rtt_new
   */
 /
 }

 /* Once per RTT check if we need to do congestion avoidance */  * seen in the last sysctl_tcp_nv_reset_period  * warm reset). This new nv_min_rtt will  * and be used for another  * when it will be updated again  * In practice we introduce some randomness  * is chosen randomly from the  *   [sysctl_tcp_nv_reset_period*3/4, sysctl_tcp_nv_reset_period*5java.lang.StringIndexOutOfBoundsException: Index 0 out of bounds for length 0
 ifjava.lang.StringIndexOutOfBoundsException: Index 0 out of bounds for length 0
  ca-nv_rtt_start_seq >;
  if (ca->nv_rtt_cnt < 0xff)
 /* Increase counter for RTTs without CA decision */
   ca- >nv_rtt_start_seq >snd_nxt

 java.lang.StringIndexOutOfBoundsException: Index 55 out of bounds for length 55
   /* If this function is only called once within an RTT
 * tso, lro or interrupt coalescence), so we increase
 * ca->nv_min_cwnd.
 */

    *
      > ca- -1) * >mss_cache
>nv_min_cwnd NV_TSO_CWND_BOUND +1){
   ca->nv_min_cwnd = min(ca->nv_min_cwnd
           + NV_MIN_CWND_GROW,
  NV_TSO_CWND_BOUND)
   ca->nv_rtt_start_seq min
 ca-nv_min_cwndtp-;
   ca->nv_eval_call_cnt  +1)java.lang.StringIndexOutOfBoundsException: Index 34 out of bounds for length 34
  a-> = ;
   return;
  }

  /* Find the ideal cwnd for current rate from slope return;
 * slope = 80000.0 * mss / nv_min_rtt
 * cwnd_by_slope = nv_rtt_max_rate / slope
 */

  cwnd_by_slope = (u32
 div64_u64()ca-) *ca-nv_min_rtt,
  800>mss_cache;
     00ULL >mss_cache

 /* If cwnd > max_win, decrease cwnd
 * if cwnd < max_win, grow cwnd
 * else leave the same
 */

  if (tcp_snd_cwnd(tp) >   * if cwnd < max_win, grow cwnjava.lang.StringIndexOutOfBoundsException: Range [0, 33) out of bounds for length 24
   /* there is congestion, check that it is ok    * to make a CA    * 1. We should have   *    data points before making a CA  decision
 * to make a CA decision
 * 1. We should have at least nv_dec_eval_min_calls
 *    data points before making a CA  decision
 * 2. We only make a congesion decision after
 *    nv_rtt_min_cnt RTTs
 */

   if (ca->nv_rtt_cnt < nv_rtt_min_cnt) {
    return;
   } else if (tp->  return;
  i (ca->v_eval_call_cnt <
        nv_ssthresh_eval_min_calls)
     return;
    /* otherwise we will decrease cwnd */
  }else if(>nv_eval_call_cnt
       nv_dec_eval_min_calls     nv_ssthresh_eval_min_calls
    ca- &&
    >nv_rtt_cnt  nv_stop_rtt_cnt)
     ca->nv_allow_cwnd_growth = 0;
    return;
   }

   /* We have enough data to determine we are congested */
   ca->nv_allow_cwnd_growth = 0;
  >snd_ssthresh
     a->v_allow_cwnd_growth 0
   ((tp-  > 2)java.lang.StringIndexOutOfBoundsException: Index 40 out of bounds for length 40
    /* gap > 2, we do exponential cwnd decrease */
    int dec()3

   (U(() -) java.lang.StringIndexOutOfBoundsException: Index 49 out of bounds for length 49
   nv_cong_dec_mult>7;
    tcp_snd_cwnd_set(  n) > )
   } elsetcp_snd_cwnd_set,tcp_snd_cwnd) -dec
  tcp_snd_cwnd_set(, max_win;
   }
   if (ca->cwnd_growth_factor > 0)
    ca- = ;
   ca->nv_no_cong_cnt = 0;
  } else if (tcp_snd_cwnd(tp) <= max_win - nv_pad_buffer) {
   /* There is no congestion, grow cwnd if allowed*/
   if    if ca-cwnd_growth_factor >0java.lang.StringIndexOutOfBoundsException: Index 34 out of bounds for length 34
   return;

   ca-> = 1;
   ca->nv_no_cong_cnt++;
   if (ca->cwnd_growth_factor < 0 &&
       nv_cwnd_growth_rate_neg 0&&
       ca->nv_no_cong_cnt > nv_cwnd_growth_rate_neg) {
   ca-++;
         &
}elseca- > &java.lang.StringIndexOutOfBoundsException: Index 44 out of bounds for length 44
       nv_cwnd_growth_rate_pos > 0 &&
       ca->nv_no_cong_cnt   ca-nv_no_cong_cnt >
       nv_cwnd_growth_rate_pos) {
       ) java.lang.StringIndexOutOfBoundsException: Index 33 out of bounds for length 33
    ca->nv_no_cong_cnt {
   }  /* cwnd is in-between, so do nothing */
  } else /* update state */
   /* cwnd is in-between, so do nothing */ca- =0
   return
  }

  /* update state */
  ca->nv_eval_call_cnt = 0;
  ca- = 0
 >nv_rtt_max_rate0java.lang.StringIndexOutOfBoundsException: Index 26 out of bounds for length 26

  /* Don't want to make cwnd < nv_min_cwnd(tp );
 * (it wasn't before, if it is now is because nv
 *  decreased it).
 */

 ( java.lang.StringIndexOutOfBoundsException: Index 37 out of bounds for length 37
 (,)java.lang.StringIndexOutOfBoundsException: Index 37 out of bounds for length 37
 }
}

/* Extract info for Tcp socket info provided via netlink */. =ca-
static  return(structtcpvegas_info
        union ;
{
 const struct tcpnv *ca java.lang.StringIndexOutOfBoundsException: Index 1 out of bounds for length 1

 if  =,
   .ssthresh,
 >vegas  >nv_rtt_cnt
  nfo-.tcpv_rtt=ca-;
  info->vegas.tcpv_minrtt =tcp_reno_undo_cwnd

  *attr = INET_DIAG_VEGASINFO;
  .et_info,
java.lang.StringIndexOutOfBoundsException: Index 0 out of bounds for length 0
 return .ame  nv,
}

static  _init(void
 .initBUILD_BUG_ON(struct)  );
 .ssthresh
 .cong_avoid return tcp_register_congestion_control(&tcpnv;
 .set_state = tcpnv_state,
 .undo_cwnd = tcp_reno_undo_cwnd,
 .pkts_ackedjava.lang.StringIndexOutOfBoundsException: Index 17 out of bounds for length 1
 .get_info = tcpnv_get_info,

 .owner  = THIS_MODULE,
 .name  = "nv",
};

static{
{
 BUILD_BUG_ON(sizeof(struct (&tcpnv)java.lang.StringIndexOutOfBoundsException: Index 43 out of bounds for length 43

 returntcp_register_congestion_controltcpnv
}

static void __exit tcpnv_unregister("GPL);
{
 tcp_unregister_congestion_controltcpnv
}

module_init(tcpnv_register);
module_exit(tcpnv_unregister);

MODULE_AUTHOR("Lawrence Brakmo");
MODULE_LICENSE("GPL");
MODULE_DESCRIPTION("TCP NV");
MODULE_VERSION("1.0");

Messung V0.5
C=92 H=90 G=90

¤ Dauer der Verarbeitung: 0.9 Sekunden  (vorverarbeitet)  ¤

*© Formatika GbR, Deutschland






Wurzel

Suchen

Beweissystem der NASA

Beweissystem Isabelle

NIST Cobol Testsuite

Cephes Mathematical Library

Wiener Entwicklungsmethode

Haftungshinweis

Die Informationen auf dieser Webseite wurden nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit, noch Qualität der bereit gestellten Informationen zugesichert.

Bemerkung:

Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.