linux-can.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH v3 0/1] Allow drivers to modify dql.min_limit value
@ 2021-03-21 13:48 Vincent Mailhol
  2021-03-21 13:48 ` [PATCH v3 1/1] netdev: add netdev_queue_set_dql_min_limit() Vincent Mailhol
  2021-03-22 20:00 ` [PATCH v3 0/1] Allow drivers to modify dql.min_limit value patchwork-bot+netdevbpf
  0 siblings, 2 replies; 3+ messages in thread
From: Vincent Mailhol @ 2021-03-21 13:48 UTC (permalink / raw)
  To: Marc Kleine-Budde, linux-can, linux-kernel, netdev, Eric Dumazet,
	Dave Taht
  Cc: Peter Zijlstra, Randy Dunlap, David S . Miller, Jakub Kicinski,
	Vincent Mailhol

Abstract: would like to directly set dql.min_limit value inside a
driver to improve BQL performances of a CAN USB driver.

CAN packets have a small PDU: for classical CAN maximum size is
roughly 16 bytes (8 for payload and 8 for arbitration, CRC and
others).

I am writing an CAN driver for an USB interface. To compensate the
extra latency introduced by the USB, I want to group several CAN
frames and do one USB bulk send. To this purpose, I implemented BQL in
my driver.

However, the BQL algorithms can take time to adjust, especially if
there are small bursts.

The best way I found is to directly modify the dql.min_limit and set
it to some empirical values. This way, even during small burst events
I can have a good throughput. Slightly increasing the dql.min_limit
has no measurable impact on the latency as long as frames fit in the
same USB packet (i.e. BQL overheard is negligible compared to USB
overhead).

The BQL was not designed for USB nor was it designed for CAN's small
PDUs which probably explains why I am the first one to ever have
thought of using dql.min_limit within the driver.

The code I wrote looks like:

> #ifdef CONFIG_BQL
>	netdev_get_tx_queue(netdev, 0)->dql.min_limit = <some empirical value>;
> #endif

Using #ifdef to set up some variables is not a best practice. I am
sending this RFC to see if we can add a function to set this
dql.min_limit in a more pretty way.

For your reference, this RFQ is a follow-up of a discussion on the
linux-can mailing list:
https://lore.kernel.org/linux-can/20210309125708.ei75tr5vp2sanfh6@pengutronix.de/

Thank you for your comments.

Yours sincerely,
Vincent

** Changelog **

RFC v2 -> v3
  - More verbose commit description.
  - Fix kernel documentation.

RFC v1 -> RFC v2
  - Fix incorect #ifdef use.
Reference: https://lore.kernel.org/linux-can/20210309153547.q7zspf46k6terxqv@pengutronix.de/

Link to RFC v1:
https://lore.kernel.org/linux-can/20210309152354.95309-1-mailhol.vincent@wanadoo.fr/T/#t

Vincent Mailhol (1):
  netdev: add netdev_queue_set_dql_min_limit()

 include/linux/netdevice.h | 18 ++++++++++++++++++
 1 file changed, 18 insertions(+)

-- 
2.26.2


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

* [PATCH v3 1/1] netdev: add netdev_queue_set_dql_min_limit()
  2021-03-21 13:48 [PATCH v3 0/1] Allow drivers to modify dql.min_limit value Vincent Mailhol
@ 2021-03-21 13:48 ` Vincent Mailhol
  2021-03-22 20:00 ` [PATCH v3 0/1] Allow drivers to modify dql.min_limit value patchwork-bot+netdevbpf
  1 sibling, 0 replies; 3+ messages in thread
From: Vincent Mailhol @ 2021-03-21 13:48 UTC (permalink / raw)
  To: Marc Kleine-Budde, linux-can, linux-kernel, netdev, Eric Dumazet,
	Dave Taht
  Cc: Peter Zijlstra, Randy Dunlap, David S . Miller, Jakub Kicinski,
	Vincent Mailhol

Add a function to set the dynamic queue limit minimum value.

Some specific drivers might have legitimate reasons to configure
dql.min_limit to a given value. Typically, this is the case when the
PDU of the protocol is smaller than the packet size to used to
carry those frames to the device.

Concrete example: a CAN (Control Area Network) device with an USB 2.0
interface.  The PDU of classical CAN protocol are roughly 16 bytes but
the USB packet size (which is used to carry the CAN frames to the
device) might be up to 512 bytes.  Wen small traffic burst occurs, BQL
algorithm is not able to immediately adjust and this would result in
having to send many small USB packets (i.e packet of 16 bytes for each
CAN frame). Filling up the USB packet with CAN frames is relatively
fast (small latency issue) but the gain of not having to send several
small USB packets is huge (big throughput increase). In this case,
forcing dql.min_limit to a given value that would allow to stuff the
USB packet is always a win.

This function is to be used by network drivers which are able to prove
through a rationale and through empirical tests on several environment
(with other applications, heavy context switching, virtualization...),
that they constantly reach better performances with a specific
predefined dql.min_limit value with no noticeable latency impact.

Signed-off-by: Vincent Mailhol <mailhol.vincent@wanadoo.fr>
---
 include/linux/netdevice.h | 18 ++++++++++++++++++
 1 file changed, 18 insertions(+)

diff --git a/include/linux/netdevice.h b/include/linux/netdevice.h
index ddf4cfc12615..c3511263b15a 100644
--- a/include/linux/netdevice.h
+++ b/include/linux/netdevice.h
@@ -3389,6 +3389,24 @@ netif_xmit_frozen_or_drv_stopped(const struct netdev_queue *dev_queue)
 	return dev_queue->state & QUEUE_STATE_DRV_XOFF_OR_FROZEN;
 }
 
+/**
+ *	netdev_queue_set_dql_min_limit - set dql minimum limit
+ *	@dev_queue: pointer to transmit queue
+ *	@min_limit: dql minimum limit
+ *
+ * Forces xmit_more() to return true until the minimum threshold
+ * defined by @min_limit is reached (or until the tx queue is
+ * empty). Warning: to be use with care, misuse will impact the
+ * latency.
+ */
+static inline void netdev_queue_set_dql_min_limit(struct netdev_queue *dev_queue,
+						  unsigned int min_limit)
+{
+#ifdef CONFIG_BQL
+	dev_queue->dql.min_limit = min_limit;
+#endif
+}
+
 /**
  *	netdev_txq_bql_enqueue_prefetchw - prefetch bql data for write
  *	@dev_queue: pointer to transmit queue
-- 
2.26.2


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

* Re: [PATCH v3 0/1] Allow drivers to modify dql.min_limit value
  2021-03-21 13:48 [PATCH v3 0/1] Allow drivers to modify dql.min_limit value Vincent Mailhol
  2021-03-21 13:48 ` [PATCH v3 1/1] netdev: add netdev_queue_set_dql_min_limit() Vincent Mailhol
@ 2021-03-22 20:00 ` patchwork-bot+netdevbpf
  1 sibling, 0 replies; 3+ messages in thread
From: patchwork-bot+netdevbpf @ 2021-03-22 20:00 UTC (permalink / raw)
  To: Vincent Mailhol
  Cc: mkl, linux-can, linux-kernel, netdev, eric.dumazet, dave.taht,
	peterz, rdunlap, davem, kuba

Hello:

This patch was applied to netdev/net-next.git (refs/heads/master):

On Sun, 21 Mar 2021 22:48:48 +0900 you wrote:
> Abstract: would like to directly set dql.min_limit value inside a
> driver to improve BQL performances of a CAN USB driver.
> 
> CAN packets have a small PDU: for classical CAN maximum size is
> roughly 16 bytes (8 for payload and 8 for arbitration, CRC and
> others).
> 
> [...]

Here is the summary with links:
  - [v3,1/1] netdev: add netdev_queue_set_dql_min_limit()
    https://git.kernel.org/netdev/net-next/c/f57bac3c33e7

You are awesome, thank you!
--
Deet-doot-dot, I am a bot.
https://korg.docs.kernel.org/patchwork/pwbot.html



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

end of thread, other threads:[~2021-03-22 20:01 UTC | newest]

Thread overview: 3+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2021-03-21 13:48 [PATCH v3 0/1] Allow drivers to modify dql.min_limit value Vincent Mailhol
2021-03-21 13:48 ` [PATCH v3 1/1] netdev: add netdev_queue_set_dql_min_limit() Vincent Mailhol
2021-03-22 20:00 ` [PATCH v3 0/1] Allow drivers to modify dql.min_limit value patchwork-bot+netdevbpf

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).