From patchwork Mon Nov 21 05:54:03 2016 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Sanchayan X-Patchwork-Id: 9438789 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id 12697600BA for ; Mon, 21 Nov 2016 06:03:51 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 0330E28984 for ; Mon, 21 Nov 2016 06:03:51 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id E9DD92898B; Mon, 21 Nov 2016 06:03:50 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-6.8 required=2.0 tests=BAYES_00, DKIM_ADSP_CUSTOM_MED, DKIM_SIGNED,FREEMAIL_FROM,RCVD_IN_DNSWL_HI,T_DKIM_INVALID autolearn=unavailable version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 87C4F28984 for ; Mon, 21 Nov 2016 06:03:50 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1753357AbcKUGDZ (ORCPT ); Mon, 21 Nov 2016 01:03:25 -0500 Received: from mail-pf0-f194.google.com ([209.85.192.194]:33565 "EHLO mail-pf0-f194.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1751214AbcKUGDX (ORCPT ); Mon, 21 Nov 2016 01:03:23 -0500 Received: by mail-pf0-f194.google.com with SMTP id 144so17620363pfv.0; Sun, 20 Nov 2016 22:03:23 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=from:to:cc:subject:date:message-id:in-reply-to:references :in-reply-to:references; bh=9SQk27RpW7Cj74vIOA2rpNIea7NT7CtHy08xHwmr+/0=; b=SAH1q3OSeRg5cA9gxUd4h0RM7fGVXYV2SKeLCGX2pVXj7H8Xf6zHhnuoHA6y1O5QO8 P/lc0ixyRIJaTgABtFpa6e8JRTuNIqvj82loZ+NfTw1ggf6BcMO/VYaZ4oEkz0Pt+D54 idvAQp8FtNXOGnXsOCWhgaTrnReLdDLyw1y+zpos5+E66on03d+vmWVqWOg6kTtFPOmN bCcReChDVaG+0JvPydQ0MLR5VOeJFDLSh8U11FsdEcPdIInKyTOdr5p/8JS7jxkBe+wx fjPGQzQc7vfGQTWe1VZLafRZtUsD2DBl2aK1PQPMKh8OEiRe5ue9Jv7MfHTV56ZzK9d9 3pmg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20130820; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:in-reply-to:references; bh=9SQk27RpW7Cj74vIOA2rpNIea7NT7CtHy08xHwmr+/0=; b=S6FHBUVxX3vQJFx3v0LLoax9pzWQnVm1ckF5Hpnl1+dcmS9Z6AVJA2uG91hb6xZQu0 XQ9usb/oaX+dQR9R242XWVxKpx+MAlhrIh2PK5/aNuwqetIBFziIoQyIElhDNweBfQKu xiRuqHfNYiPvjZBVHON0+Vo5Y0qkkV2+rx/qfT7fgX07Nkw6FB8/oKTnUpQWC29ovpLA 9NwiLbdil8bUkul2hTxAeExj9wi8ZvfXPCIHSJPmcaz2DOtT8c6wt0u3ZSyPaRgCLOyW eUxweMhHV4qEJf8x8YJGqcGOGBb1T7pvezXMs6HGng0pCuIAllNPyue0tfpNsdnuFdKE 1qiQ== X-Gm-Message-State: AKaTC03olZfrZc3uoBekM0axdMFpwhd1JcFMeuLf1vfBhmdv2WCKpTdlT0ZrvHELJvAvqg== X-Received: by 10.99.111.78 with SMTP id k75mr28895865pgc.114.1479708198008; Sun, 20 Nov 2016 22:03:18 -0800 (PST) Received: from localhost ([115.115.243.34]) by smtp.gmail.com with ESMTPSA id q2sm16002359pga.8.2016.11.20.22.03.17 (version=TLS1_2 cipher=ECDHE-RSA-CHACHA20-POLY1305 bits=256/256); Sun, 20 Nov 2016 22:03:17 -0800 (PST) From: Sanchayan Maity To: broonie@kernel.org Cc: stefan@agner.ch, linux-arm-kernel@lists.infradead.org, linux-kernel@vger.kernel.org, linux-spi@vger.kernel.org, Sanchayan Maity Subject: [PATCH v2 3/4] spi: spi-fsl-dspi: Fix incorrect DMA setup Date: Mon, 21 Nov 2016 11:24:03 +0530 Message-Id: X-Mailer: git-send-email 2.10.2 In-Reply-To: References: In-Reply-To: References: Sender: linux-spi-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-spi@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Currently dmaengine_prep_slave_single was being called with length set to the complete DMA buffer size. This resulted in unwanted bytes being transferred to the SPI register leading to clock and MOSI lines having unwanted data even after chip select got deasserted and the required bytes having been transferred. While at it also clean up the use of curr_xfer_len which is central to the DMA setup, from bytes to DMA transfers for every use. Signed-off-by: Sanchayan Maity Reviewed-by: Stefan Agner --- drivers/spi/spi-fsl-dspi.c | 35 ++++++++++++++++++----------------- 1 file changed, 18 insertions(+), 17 deletions(-) diff --git a/drivers/spi/spi-fsl-dspi.c b/drivers/spi/spi-fsl-dspi.c index 41422cd..08882f7 100644 --- a/drivers/spi/spi-fsl-dspi.c +++ b/drivers/spi/spi-fsl-dspi.c @@ -151,6 +151,7 @@ static const struct fsl_dspi_devtype_data ls2085a_data = { }; struct fsl_dspi_dma { + /* Length of transfer in words of DSPI_FIFO_SIZE */ u32 curr_xfer_len; u32 *tx_dma_buf; @@ -217,15 +218,13 @@ static void dspi_rx_dma_callback(void *arg) struct fsl_dspi *dspi = arg; struct fsl_dspi_dma *dma = dspi->dma; int rx_word; - int i, len; + int i; u16 d; rx_word = is_double_byte_mode(dspi); - len = rx_word ? (dma->curr_xfer_len / 2) : dma->curr_xfer_len; - if (!(dspi->dataflags & TRAN_STATE_RX_VOID)) { - for (i = 0; i < len; i++) { + for (i = 0; i < dma->curr_xfer_len; i++) { d = dspi->dma->rx_dma_buf[i]; rx_word ? (*(u16 *)dspi->rx = d) : (*(u8 *)dspi->rx = d); @@ -242,14 +241,12 @@ static int dspi_next_xfer_dma_submit(struct fsl_dspi *dspi) struct device *dev = &dspi->pdev->dev; int time_left; int tx_word; - int i, len; + int i; u16 val; tx_word = is_double_byte_mode(dspi); - len = tx_word ? (dma->curr_xfer_len / 2) : dma->curr_xfer_len; - - for (i = 0; i < len - 1; i++) { + for (i = 0; i < dma->curr_xfer_len - 1; i++) { val = tx_word ? *(u16 *) dspi->tx : *(u8 *) dspi->tx; dspi->dma->tx_dma_buf[i] = SPI_PUSHR_TXDATA(val) | SPI_PUSHR_PCS(dspi->cs) | @@ -267,7 +264,9 @@ static int dspi_next_xfer_dma_submit(struct fsl_dspi *dspi) dma->tx_desc = dmaengine_prep_slave_single(dma->chan_tx, dma->tx_dma_phys, - DSPI_DMA_BUFSIZE, DMA_MEM_TO_DEV, + dma->curr_xfer_len * + DMA_SLAVE_BUSWIDTH_4_BYTES, + DMA_MEM_TO_DEV, DMA_PREP_INTERRUPT | DMA_CTRL_ACK); if (!dma->tx_desc) { dev_err(dev, "Not able to get desc for DMA xfer\n"); @@ -283,7 +282,9 @@ static int dspi_next_xfer_dma_submit(struct fsl_dspi *dspi) dma->rx_desc = dmaengine_prep_slave_single(dma->chan_rx, dma->rx_dma_phys, - DSPI_DMA_BUFSIZE, DMA_DEV_TO_MEM, + dma->curr_xfer_len * + DMA_SLAVE_BUSWIDTH_4_BYTES, + DMA_DEV_TO_MEM, DMA_PREP_INTERRUPT | DMA_CTRL_ACK); if (!dma->rx_desc) { dev_err(dev, "Not able to get desc for DMA xfer\n"); @@ -330,17 +331,17 @@ static int dspi_dma_xfer(struct fsl_dspi *dspi) struct device *dev = &dspi->pdev->dev; int curr_remaining_bytes; int bytes_per_buffer; - int tx_word; + int word = 1; int ret = 0; - tx_word = is_double_byte_mode(dspi); + if (is_double_byte_mode(dspi)) + word = 2; curr_remaining_bytes = dspi->len; + bytes_per_buffer = DSPI_DMA_BUFSIZE / DSPI_FIFO_SIZE; while (curr_remaining_bytes) { /* Check if current transfer fits the DMA buffer */ - dma->curr_xfer_len = curr_remaining_bytes; - bytes_per_buffer = DSPI_DMA_BUFSIZE / - (DSPI_FIFO_SIZE / (tx_word ? 2 : 1)); - if (curr_remaining_bytes > bytes_per_buffer) + dma->curr_xfer_len = curr_remaining_bytes / word; + if (dma->curr_xfer_len > bytes_per_buffer) dma->curr_xfer_len = bytes_per_buffer; ret = dspi_next_xfer_dma_submit(dspi); @@ -349,7 +350,7 @@ static int dspi_dma_xfer(struct fsl_dspi *dspi) goto exit; } else { - curr_remaining_bytes -= dma->curr_xfer_len; + curr_remaining_bytes -= dma->curr_xfer_len * word; if (curr_remaining_bytes < 0) curr_remaining_bytes = 0; dspi->len = curr_remaining_bytes;