Commit 623ad755 authored by Tal Gilboa's avatar Tal Gilboa Committed by David S. Miller

net/dim: Support adaptive TX moderation

Interrupt moderation for TX traffic requires different profiles than RX
interrupt moderation. The main goal here is to reduce interrupt rate and
allow better payload aggregation by keeping SKBs in the TX queue a bit
longer. Ping-pong behavior would get a profile with a short timer, so
latency wouldn't increase for these scenarios. There might be a slight
degradation in bandwidth for single stream with large message sizes, since
net.ipv4.tcp_limit_output_bytes is limiting the allowed TX traffic, but
with many streams performance is always improved.
Signed-off-by: default avatarTal Gilboa <talgi@mellanox.com>
Reviewed-by: default avatarTariq Toukan <tariqt@mellanox.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 026a807c
...@@ -103,11 +103,12 @@ enum { ...@@ -103,11 +103,12 @@ enum {
#define NET_DIM_PARAMS_NUM_PROFILES 5 #define NET_DIM_PARAMS_NUM_PROFILES 5
/* Adaptive moderation profiles */ /* Adaptive moderation profiles */
#define NET_DIM_DEFAULT_RX_CQ_MODERATION_PKTS_FROM_EQE 256 #define NET_DIM_DEFAULT_RX_CQ_MODERATION_PKTS_FROM_EQE 256
#define NET_DIM_DEFAULT_TX_CQ_MODERATION_PKTS_FROM_EQE 128
#define NET_DIM_DEF_PROFILE_CQE 1 #define NET_DIM_DEF_PROFILE_CQE 1
#define NET_DIM_DEF_PROFILE_EQE 1 #define NET_DIM_DEF_PROFILE_EQE 1
/* All profiles sizes must be NET_PARAMS_DIM_NUM_PROFILES */ /* All profiles sizes must be NET_PARAMS_DIM_NUM_PROFILES */
#define NET_DIM_EQE_PROFILES { \ #define NET_DIM_RX_EQE_PROFILES { \
{1, NET_DIM_DEFAULT_RX_CQ_MODERATION_PKTS_FROM_EQE}, \ {1, NET_DIM_DEFAULT_RX_CQ_MODERATION_PKTS_FROM_EQE}, \
{8, NET_DIM_DEFAULT_RX_CQ_MODERATION_PKTS_FROM_EQE}, \ {8, NET_DIM_DEFAULT_RX_CQ_MODERATION_PKTS_FROM_EQE}, \
{64, NET_DIM_DEFAULT_RX_CQ_MODERATION_PKTS_FROM_EQE}, \ {64, NET_DIM_DEFAULT_RX_CQ_MODERATION_PKTS_FROM_EQE}, \
...@@ -115,7 +116,7 @@ enum { ...@@ -115,7 +116,7 @@ enum {
{256, NET_DIM_DEFAULT_RX_CQ_MODERATION_PKTS_FROM_EQE}, \ {256, NET_DIM_DEFAULT_RX_CQ_MODERATION_PKTS_FROM_EQE}, \
} }
#define NET_DIM_CQE_PROFILES { \ #define NET_DIM_RX_CQE_PROFILES { \
{2, 256}, \ {2, 256}, \
{8, 128}, \ {8, 128}, \
{16, 64}, \ {16, 64}, \
...@@ -123,32 +124,68 @@ enum { ...@@ -123,32 +124,68 @@ enum {
{64, 64} \ {64, 64} \
} }
#define NET_DIM_TX_EQE_PROFILES { \
{1, NET_DIM_DEFAULT_TX_CQ_MODERATION_PKTS_FROM_EQE}, \
{8, NET_DIM_DEFAULT_TX_CQ_MODERATION_PKTS_FROM_EQE}, \
{32, NET_DIM_DEFAULT_TX_CQ_MODERATION_PKTS_FROM_EQE}, \
{64, NET_DIM_DEFAULT_TX_CQ_MODERATION_PKTS_FROM_EQE}, \
{128, NET_DIM_DEFAULT_TX_CQ_MODERATION_PKTS_FROM_EQE} \
}
#define NET_DIM_TX_CQE_PROFILES { \
{5, 128}, \
{8, 64}, \
{16, 32}, \
{32, 32}, \
{64, 32} \
}
static const struct net_dim_cq_moder static const struct net_dim_cq_moder
profile[NET_DIM_CQ_PERIOD_NUM_MODES][NET_DIM_PARAMS_NUM_PROFILES] = { rx_profile[NET_DIM_CQ_PERIOD_NUM_MODES][NET_DIM_PARAMS_NUM_PROFILES] = {
NET_DIM_EQE_PROFILES, NET_DIM_RX_EQE_PROFILES,
NET_DIM_CQE_PROFILES, NET_DIM_RX_CQE_PROFILES,
};
static const struct net_dim_cq_moder
tx_profile[NET_DIM_CQ_PERIOD_NUM_MODES][NET_DIM_PARAMS_NUM_PROFILES] = {
NET_DIM_TX_EQE_PROFILES,
NET_DIM_TX_CQE_PROFILES,
}; };
static inline struct net_dim_cq_moder static inline struct net_dim_cq_moder
net_dim_get_rx_moderation(u8 cq_period_mode, int ix) net_dim_get_rx_moderation(u8 cq_period_mode, int ix)
{ {
struct net_dim_cq_moder cq_moder = profile[cq_period_mode][ix]; struct net_dim_cq_moder cq_moder = rx_profile[cq_period_mode][ix];
cq_moder.cq_period_mode = cq_period_mode; cq_moder.cq_period_mode = cq_period_mode;
return cq_moder; return cq_moder;
} }
static inline struct net_dim_cq_moder static inline struct net_dim_cq_moder
net_dim_get_def_rx_moderation(u8 rx_cq_period_mode) net_dim_get_def_rx_moderation(u8 cq_period_mode)
{
u8 profile_ix = cq_period_mode == NET_DIM_CQ_PERIOD_MODE_START_FROM_CQE ?
NET_DIM_DEF_PROFILE_CQE : NET_DIM_DEF_PROFILE_EQE;
return net_dim_get_rx_moderation(cq_period_mode, profile_ix);
}
static inline struct net_dim_cq_moder
net_dim_get_tx_moderation(u8 cq_period_mode, int ix)
{ {
int default_profile_ix; struct net_dim_cq_moder cq_moder = tx_profile[cq_period_mode][ix];
if (rx_cq_period_mode == NET_DIM_CQ_PERIOD_MODE_START_FROM_CQE) cq_moder.cq_period_mode = cq_period_mode;
default_profile_ix = NET_DIM_DEF_PROFILE_CQE; return cq_moder;
else /* NET_DIM_CQ_PERIOD_MODE_START_FROM_EQE */ }
default_profile_ix = NET_DIM_DEF_PROFILE_EQE;
static inline struct net_dim_cq_moder
net_dim_get_def_tx_moderation(u8 cq_period_mode)
{
u8 profile_ix = cq_period_mode == NET_DIM_CQ_PERIOD_MODE_START_FROM_CQE ?
NET_DIM_DEF_PROFILE_CQE : NET_DIM_DEF_PROFILE_EQE;
return net_dim_get_rx_moderation(rx_cq_period_mode, default_profile_ix); return net_dim_get_tx_moderation(cq_period_mode, profile_ix);
} }
static inline bool net_dim_on_top(struct net_dim *dim) static inline bool net_dim_on_top(struct net_dim *dim)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment