intel-wired-lan.osuosl.org archive mirror
 help / color / mirror / Atom feed
From: Alexander Duyck <alexander.duyck@gmail.com>
To: intel-wired-lan@osuosl.org
Subject: [Intel-wired-lan] [next-queue v3 13/17] fm10k: Update adaptive ITR algorithm
Date: Thu, 15 Oct 2015 15:20:53 -0700	[thread overview]
Message-ID: <562026C5.4080002@gmail.com> (raw)
In-Reply-To: <1444944297-9733-13-git-send-email-jacob.e.keller@intel.com>

On 10/15/2015 02:24 PM, Jacob Keller wrote:
> The existing adaptive ITR algorithm is overly restrictive. It throttles
> incorrectly for various traffic rates, and does not produce good
> performance. The algorithm now allows for more interrupts per second,
> and does some calculation to help improve for smaller packet loads. In
> addition, take into account the new itr_scale from the hardware which
> indicates how much to scale due to PCIe link speed.
>
> Reported-by: Matthew Vick <matthew.vick@intel.com>
> Reported-by: Alex Duyck <alexander.duyck@gmail.com>
> Signed-off-by: Jacob Keller <jacob.e.keller@intel.com>
> ---
>   drivers/net/ethernet/intel/fm10k/fm10k.h      |  1 +
>   drivers/net/ethernet/intel/fm10k/fm10k_main.c | 52 ++++++++++++++++++++-------
>   drivers/net/ethernet/intel/fm10k/fm10k_pci.c  |  6 ++--
>   3 files changed, 45 insertions(+), 14 deletions(-)

One minor typo called out below.

> diff --git a/drivers/net/ethernet/intel/fm10k/fm10k.h b/drivers/net/ethernet/intel/fm10k/fm10k.h
> index a2484cb88d86..bdbb804a594f 100644
> --- a/drivers/net/ethernet/intel/fm10k/fm10k.h
> +++ b/drivers/net/ethernet/intel/fm10k/fm10k.h
> @@ -164,6 +164,7 @@ struct fm10k_ring_container {
>   	unsigned int total_packets;	/* total packets processed this int */
>   	u16 work_limit;			/* total work allowed per interrupt */
>   	u16 itr;			/* interrupt throttle rate value */
> +	u8 itr_scale;			/* ITR adjustment scaler based on PCI speed */
>   	u8 count;			/* total number of rings in vector */
>   };
>
> diff --git a/drivers/net/ethernet/intel/fm10k/fm10k_main.c b/drivers/net/ethernet/intel/fm10k/fm10k_main.c
> index 8207ee189600..2ee02e51afe9 100644
> --- a/drivers/net/ethernet/intel/fm10k/fm10k_main.c
> +++ b/drivers/net/ethernet/intel/fm10k/fm10k_main.c
> @@ -1367,7 +1367,7 @@ static bool fm10k_clean_tx_irq(struct fm10k_q_vector *q_vector,
>    **/
>   static void fm10k_update_itr(struct fm10k_ring_container *ring_container)
>   {
> -	unsigned int avg_wire_size, packets;
> +	unsigned int avg_wire_size, packets, itr_round;
>
>   	/* Only update ITR if we are using adaptive setting */
>   	if (!ITR_IS_ADAPTIVE(ring_container->itr))
> @@ -1379,18 +1379,44 @@ static void fm10k_update_itr(struct fm10k_ring_container *ring_container)
>
>   	avg_wire_size = ring_container->total_bytes / packets;
>
> -	/* Add 24 bytes to size to account for CRC, preamble, and gap */
> -	avg_wire_size += 24;
> +	/* The following is a crude approximation of:
> +	 *  wmem_default / (size + overhead) = desired_pkts_per_int
> +	 *  rate / bits_per_byte / (size + ethernet overhead) = pkt_rate
> +	 *  (desired_pkt_rate / pkt_rate) * usecs_per_sec = ITR value
> +	 *
> +	 * Assuming wmem_default is 212992 and overhead is 640 bytes per
> +	 * packet, (256 skb, 64 headroom, 320 shared info), we can reduce the
> +	 * formula down to
> +	 *
> +	 *  (34 * (size + 24)) / (size + 640) = ITR
> +	 *
> +	 * We first do some math on the packet size and then finally bitshift
> +	 * by 8 after rounding up. We also have to account for PCIe link speed
> +	 * difference as ITR scales based on this.
> +	 */
> +	if (avg_wire_size <= 360) {
> +		/* Start at 333K ints/sec and gradually drop to 77K ints/sec */
> +		avg_wire_size *= 8;
> +		avg_wire_size += 376;
> +	} else if (avg_wire_size <= 1152) {
> +		/* 77K ints/sec to 45K ints/sec */
> +		avg_wire_size *= 3;
> +		avg_wire_size += 2176;
> +	} else if (avg_wire_size <= 1920) {
> +		/* 45K ints/ec to 38K ints/sec */

Typo here.  Should be "ints/sec", not "ints/ec".

> +		avg_wire_size += 4480;
> +	} else {
> +		/* plateau at a limit of 38K ints/sec */
> +		avg_wire_size = 6656;
> +	}
>
> -	/* Don't starve jumbo frames */
> -	if (avg_wire_size > 3000)
> -		avg_wire_size = 3000;
> -
> -	/* Give a little boost to mid-size frames */
> -	if ((avg_wire_size > 300) && (avg_wire_size < 1200))
> -		avg_wire_size /= 3;
> -	else
> -		avg_wire_size /= 2;
> +	/* Perform final bitshift for division after rounding up to ensure
> +	 * that the calculation will never get below a 1. The bit shift
> +	 * accounts for changes in the ITR due to PCIe link speed.
> +	 */
> +	itr_round = ACCESS_ONCE(ring_container->itr_scale) + 8;
> +	avg_wire_size += (1 << itr_round) - 1;
> +	avg_wire_size >>= itr_round;
>
>   	/* write back value and retain adaptive flag */
>   	ring_container->itr = avg_wire_size | FM10K_ITR_ADAPTIVE;
> @@ -1608,6 +1634,7 @@ static int fm10k_alloc_q_vector(struct fm10k_intfc *interface,
>   	q_vector->tx.ring = ring;
>   	q_vector->tx.work_limit = FM10K_DEFAULT_TX_WORK;
>   	q_vector->tx.itr = interface->tx_itr;
> +	q_vector->tx.itr_scale = interface->hw.mac.itr_scale;
>   	q_vector->tx.count = txr_count;
>
>   	while (txr_count) {
> @@ -1636,6 +1663,7 @@ static int fm10k_alloc_q_vector(struct fm10k_intfc *interface,
>   	/* save Rx ring container info */
>   	q_vector->rx.ring = ring;
>   	q_vector->rx.itr = interface->rx_itr;
> +	q_vector->rx.itr_scale = interface->hw.mac.itr_scale;
>   	q_vector->rx.count = rxr_count;
>
>   	while (rxr_count) {
> diff --git a/drivers/net/ethernet/intel/fm10k/fm10k_pci.c b/drivers/net/ethernet/intel/fm10k/fm10k_pci.c
> index 9ad9f9164d91..cbf38da0ada7 100644
> --- a/drivers/net/ethernet/intel/fm10k/fm10k_pci.c
> +++ b/drivers/net/ethernet/intel/fm10k/fm10k_pci.c
> @@ -880,7 +880,8 @@ static irqreturn_t fm10k_msix_mbx_vf(int __always_unused irq, void *data)
>
>   	/* re-enable mailbox interrupt and indicate 20us delay */
>   	fm10k_write_reg(hw, FM10K_VFITR(FM10K_MBX_VECTOR),
> -			FM10K_ITR_ENABLE | FM10K_MBX_INT_DELAY);
> +			FM10K_ITR_ENABLE | (FM10K_MBX_INT_DELAY >>
> +					    hw->mac.itr_scale));
>
>   	/* service upstream mailbox */
>   	if (fm10k_mbx_trylock(interface)) {
> @@ -1111,7 +1112,8 @@ static irqreturn_t fm10k_msix_mbx_pf(int __always_unused irq, void *data)
>
>   	/* re-enable mailbox interrupt and indicate 20us delay */
>   	fm10k_write_reg(hw, FM10K_ITR(FM10K_MBX_VECTOR),
> -			FM10K_ITR_ENABLE | FM10K_MBX_INT_DELAY);
> +			FM10K_ITR_ENABLE | (FM10K_MBX_INT_DELAY >>
> +					    hw->mac.itr_scale));
>
>   	return IRQ_HANDLED;
>   }
>


  reply	other threads:[~2015-10-15 22:20 UTC|newest]

Thread overview: 19+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2015-10-15 21:24 [Intel-wired-lan] [next-queue v3 01/17] fm10k: conditionally compile DCB and DebugFS support Jacob Keller
2015-10-15 21:24 ` [Intel-wired-lan] [next-queue v3 02/17] fm10k: set netdev features in one location Jacob Keller
2015-10-15 21:24 ` [Intel-wired-lan] [next-queue v3 03/17] fm10k: reset max_queues on init_hw_vf failure Jacob Keller
2015-10-15 21:24 ` [Intel-wired-lan] [next-queue v3 04/17] fm10k: always check init_hw for errors Jacob Keller
2015-10-15 21:24 ` [Intel-wired-lan] [next-queue v3 05/17] fm10k: reinitialize queuing scheme after calling init_hw Jacob Keller
2015-10-15 21:24 ` [Intel-wired-lan] [next-queue v3 06/17] fm10k: Correct typecast in fm10k_update_xc_addr_pf Jacob Keller
2015-10-15 21:24 ` [Intel-wired-lan] [next-queue v3 07/17] fm10k: explicitly typecast vlan values to u16 Jacob Keller
2015-10-15 21:24 ` [Intel-wired-lan] [next-queue v3 08/17] fm10k: add statistics for actual DWORD count of mbmem mailbox Jacob Keller
2015-10-15 21:24 ` [Intel-wired-lan] [next-queue v3 09/17] fm10k: rename mbx_tx_oversized statistic to mbx_tx_dropped Jacob Keller
2015-10-15 21:24 ` [Intel-wired-lan] [next-queue v3 10/17] fm10k: add TEB check to fm10k_gre_is_nvgre Jacob Keller
2015-10-15 21:24 ` [Intel-wired-lan] [next-queue v3 11/17] fm10k: Add support for ITR scaling based on PCIe link speed Jacob Keller
2015-10-15 21:24 ` [Intel-wired-lan] [next-queue v3 12/17] fm10k: introduce ITR_IS_ADAPTIVE macro Jacob Keller
2015-10-15 21:24 ` [Intel-wired-lan] [next-queue v3 13/17] fm10k: Update adaptive ITR algorithm Jacob Keller
2015-10-15 22:20   ` Alexander Duyck [this message]
2015-10-15 21:24 ` [Intel-wired-lan] [next-queue v3 14/17] fm10k: use macro for default Tx and Rx ITR values Jacob Keller
2015-10-15 21:24 ` [Intel-wired-lan] [next-queue v3 15/17] fm10k: change default Tx ITR to 25usec Jacob Keller
2015-10-15 21:24 ` [Intel-wired-lan] [next-queue v3 16/17] fm10k: TRIVIAL fix typo of hardware Jacob Keller
2015-10-15 21:24 ` [Intel-wired-lan] [next-queue v3 17/17] fm10k: TRIVIAL cleanup order at top of fm10k_xmit_frame Jacob Keller
2015-11-03 20:51 ` [Intel-wired-lan] [next-queue v3 01/17] fm10k: conditionally compile DCB and DebugFS support Singh, Krishneil K

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=562026C5.4080002@gmail.com \
    --to=alexander.duyck@gmail.com \
    --cc=intel-wired-lan@osuosl.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
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).