linux-wireless.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: Max Filippov <jcmvbkbc@gmail.com>
To: linux-wireless@vger.kernel.org
Cc: Christian Lamparter <chunkeey@web.de>, Max Filippov <jcmvbkbc@gmail.com>
Subject: [PATCH 5/5] p54spi: use firmware/DMA bug workaround that work under hight load in p54spi_rx
Date: Mon, 18 May 2009 03:02:35 +0400	[thread overview]
Message-ID: <1242601355-3178-6-git-send-email-jcmvbkbc@gmail.com> (raw)
In-Reply-To: <1242601355-3178-5-git-send-email-jcmvbkbc@gmail.com>

Under high load first data word, read after available data size
is sometimes lost in p54spi_rx. It seems to depend on frequency
of interrupts and latency of data read request relatively to
'data available' interrupt. The worst consequence of this bug
is loss of packet transmission acknowledgement, which in turn
causes overflow of tx queues and permanent link loss.

Read data size and first data word in one SPI transaction.
No packets from LMAC should have length less than 1 word,
so this shouldn't interfere with the next read transaction.

Also call p54spi_sleep if p54spi_wake succeeded.

Signed-off-by: Max Filippov <jcmvbkbc@gmail.com>
---
 drivers/net/wireless/p54/p54spi.c |   28 ++++++++++++++++++++--------
 1 files changed, 20 insertions(+), 8 deletions(-)

diff --git a/drivers/net/wireless/p54/p54spi.c b/drivers/net/wireless/p54/p54spi.c
index 9e0c1a2..fe90f88 100644
--- a/drivers/net/wireless/p54/p54spi.c
+++ b/drivers/net/wireless/p54/p54spi.c
@@ -357,32 +357,44 @@ static int p54spi_rx(struct p54s_priv *priv)
 {
 	struct sk_buff *skb;
 	u16 len;
+	u16 rx_head[2];
+#define READAHEAD_SZ (sizeof(rx_head)-sizeof(u16))
 
 	if (p54spi_wakeup(priv) < 0)
 		return -EBUSY;
 
-	/* dummy read to flush SPI DMA controller bug */
-	p54spi_read16(priv, SPI_ADRS_GEN_PURP_1);
-
-	len = p54spi_read16(priv, SPI_ADRS_DMA_DATA);
+	/* Read data size and first data word in one SPI transaction
+	 * This is workaround for firmware/DMA bug,
+	 * when first data word gets lost under high load.
+	 */
+	p54spi_spi_read(priv, SPI_ADRS_DMA_DATA, rx_head, sizeof(rx_head));
+	len = rx_head[0];
 
 	if (len == 0) {
-		dev_err(&priv->spi->dev, "rx request of zero bytes");
+		p54spi_sleep(priv);
+		dev_err(&priv->spi->dev, "rx request of zero bytes\n");
 		return 0;
 	}
 
-
 	/* Firmware may insert up to 4 padding bytes after the lmac header,
 	 * but it does not amend the size of SPI data transfer.
 	 * Such packets has correct data size in header, thus referencing
 	 * past the end of allocated skb. Reserve extra 4 bytes for this case */
 	skb = dev_alloc_skb(len + 4);
 	if (!skb) {
+		p54spi_sleep(priv);
 		dev_err(&priv->spi->dev, "could not alloc skb");
-		return 0;
+		return -ENOMEM;
 	}
 
-	p54spi_spi_read(priv, SPI_ADRS_DMA_DATA, skb_put(skb, len), len);
+	if (len <= READAHEAD_SZ) {
+		memcpy(skb_put(skb, len), rx_head + 1, len);
+	} else {
+		memcpy(skb_put(skb, READAHEAD_SZ), rx_head + 1, READAHEAD_SZ);
+		p54spi_spi_read(priv, SPI_ADRS_DMA_DATA,
+				skb_put(skb, len - READAHEAD_SZ),
+				len - READAHEAD_SZ);
+	}
 	p54spi_sleep(priv);
 	/* Put additional bytes to compensate for the possible
 	 * alignment-caused truncation */
-- 
1.6.0.6


  reply	other threads:[~2009-05-17 23:02 UTC|newest]

Thread overview: 8+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
     [not found] <0001-p54spi-fix-incorrect-access-sequence-to-DMA_WRITE_C.patch>
2009-05-17 23:02 ` [PATCH 0/5] p54spi: fixes to achieve link stability Max Filippov
2009-05-17 23:02   ` [PATCH 1/5] p54spi: fix incorrect access sequence to DMA_WRITE_CTRL in p54spi_spi_write_dma Max Filippov
2009-05-17 23:02     ` [PATCH 2/5] p54spi: cosmetic fixes: use even byte count in SPI write; drop unused interrupt status read Max Filippov
2009-05-17 23:02       ` [PATCH 3/5] p54spi: return status of p54spi_wakeup Max Filippov
2009-05-17 23:02         ` [PATCH 4/5] p54spi: always call p54spi_sleep in p54spi_tx_frame if p54spi_wakeup succeeded Max Filippov
2009-05-17 23:02           ` Max Filippov [this message]
2009-05-18 18:53             ` [PATCH 5/5] p54spi: use firmware/DMA bug workaround that work under hight load in p54spi_rx Kalle Valo
2009-05-18 21:21               ` Max Filippov

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=1242601355-3178-6-git-send-email-jcmvbkbc@gmail.com \
    --to=jcmvbkbc@gmail.com \
    --cc=chunkeey@web.de \
    --cc=linux-wireless@vger.kernel.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).