From patchwork Sun Sep 20 11:28:45 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Serge Semin X-Patchwork-Id: 258213 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-9.8 required=3.0 tests=BAYES_00, HEADER_FROM_DIFFERENT_DOMAINS, INCLUDES_PATCH, MAILING_LIST_MULTI, SIGNED_OFF_BY, SPF_HELO_NONE, SPF_PASS autolearn=ham autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id EC6C8C43465 for ; Sun, 20 Sep 2020 11:29:25 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id BE28A21D43 for ; Sun, 20 Sep 2020 11:29:25 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726327AbgITL3Z (ORCPT ); Sun, 20 Sep 2020 07:29:25 -0400 Received: from mail.baikalelectronics.com ([87.245.175.226]:53540 "EHLO mail.baikalelectronics.ru" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726267AbgITL3Z (ORCPT ); Sun, 20 Sep 2020 07:29:25 -0400 X-Greylist: delayed 357 seconds by postgrey-1.27 at vger.kernel.org; Sun, 20 Sep 2020 07:29:24 EDT Received: from localhost (unknown [127.0.0.1]) by mail.baikalelectronics.ru (Postfix) with ESMTP id 09325803202C; Sun, 20 Sep 2020 11:29:23 +0000 (UTC) X-Virus-Scanned: amavisd-new at baikalelectronics.ru Received: from mail.baikalelectronics.ru ([127.0.0.1]) by localhost (mail.baikalelectronics.ru [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id s3Ix_-mqKapR; Sun, 20 Sep 2020 14:29:22 +0300 (MSK) From: Serge Semin To: Mark Brown CC: Serge Semin , Serge Semin , Alexey Malahov , Ramil Zaripov , Pavel Parkhomenko , Andy Shevchenko , Andy Shevchenko , Lars Povlsen , "wuxu . wu" , Feng Tang , Rob Herring , , , Subject: [PATCH 01/30] spi: dw: Discard IRQ threshold macro Date: Sun, 20 Sep 2020 14:28:45 +0300 Message-ID: <20200920112914.26501-2-Sergey.Semin@baikalelectronics.ru> In-Reply-To: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> References: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> MIME-Version: 1.0 X-ClientProxiedBy: MAIL.baikal.int (192.168.51.25) To mail (192.168.51.25) Precedence: bulk List-ID: X-Mailing-List: linux-spi@vger.kernel.org The macro has been unused since a half of FIFO length was defined to be a marker of the IRQ. Let's remove it definition. Signed-off-by: Serge Semin --- drivers/spi/spi-dw.h | 3 --- 1 file changed, 3 deletions(-) diff --git a/drivers/spi/spi-dw.h b/drivers/spi/spi-dw.h index 90dfd21622d6..51bab30b9f85 100644 --- a/drivers/spi/spi-dw.h +++ b/drivers/spi/spi-dw.h @@ -92,9 +92,6 @@ #define SPI_DMA_RDMAE (1 << 0) #define SPI_DMA_TDMAE (1 << 1) -/* TX RX interrupt level threshold, max can be 256 */ -#define SPI_INT_THRESHOLD 32 - enum dw_ssi_type { SSI_MOTO_SPI = 0, SSI_TI_SSP, From patchwork Sun Sep 20 11:28:47 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Serge Semin X-Patchwork-Id: 258212 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-9.8 required=3.0 tests=BAYES_00, HEADER_FROM_DIFFERENT_DOMAINS, INCLUDES_PATCH, MAILING_LIST_MULTI, SIGNED_OFF_BY, SPF_HELO_NONE, SPF_PASS, URIBL_BLOCKED autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 5EC3EC43468 for ; Sun, 20 Sep 2020 11:29:38 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 3493C221EC for ; Sun, 20 Sep 2020 11:29:38 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726435AbgITL32 (ORCPT ); Sun, 20 Sep 2020 07:29:28 -0400 Received: from mail.baikalelectronics.com ([87.245.175.226]:53604 "EHLO mail.baikalelectronics.ru" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726326AbgITL30 (ORCPT ); Sun, 20 Sep 2020 07:29:26 -0400 Received: from localhost (unknown [127.0.0.1]) by mail.baikalelectronics.ru (Postfix) with ESMTP id 59B46803202B; Sun, 20 Sep 2020 11:29:24 +0000 (UTC) X-Virus-Scanned: amavisd-new at baikalelectronics.ru Received: from mail.baikalelectronics.ru ([127.0.0.1]) by localhost (mail.baikalelectronics.ru [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id FsL6JByAIE36; Sun, 20 Sep 2020 14:29:23 +0300 (MSK) From: Serge Semin To: Mark Brown CC: Serge Semin , Serge Semin , Alexey Malahov , Ramil Zaripov , Pavel Parkhomenko , Andy Shevchenko , Andy Shevchenko , Lars Povlsen , "wuxu . wu" , Feng Tang , Rob Herring , , , Subject: [PATCH 03/30] spi: dw: Initialize n_bytes before the memory barrier Date: Sun, 20 Sep 2020 14:28:47 +0300 Message-ID: <20200920112914.26501-4-Sergey.Semin@baikalelectronics.ru> In-Reply-To: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> References: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> MIME-Version: 1.0 X-ClientProxiedBy: MAIL.baikal.int (192.168.51.25) To mail (192.168.51.25) Precedence: bulk List-ID: X-Mailing-List: linux-spi@vger.kernel.org Since n_bytes field of the DW SPI private data is also utilized by the IRQ handler, we need to make sure it' initialization is done before the memory barrier. Signed-off-by: Serge Semin --- drivers/spi/spi-dw-core.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/spi/spi-dw-core.c b/drivers/spi/spi-dw-core.c index 8b3ce5a0378a..1af74362461d 100644 --- a/drivers/spi/spi-dw-core.c +++ b/drivers/spi/spi-dw-core.c @@ -299,6 +299,7 @@ static int dw_spi_transfer_one(struct spi_controller *master, dws->dma_mapped = 0; spin_lock_irqsave(&dws->buf_lock, flags); + dws->n_bytes = DIV_ROUND_UP(transfer->bits_per_word, BITS_PER_BYTE); dws->tx = (void *)transfer->tx_buf; dws->tx_end = dws->tx + transfer->len; dws->rx = transfer->rx_buf; @@ -323,7 +324,6 @@ static int dw_spi_transfer_one(struct spi_controller *master, } transfer->effective_speed_hz = dws->max_freq / chip->clk_div; - dws->n_bytes = DIV_ROUND_UP(transfer->bits_per_word, BITS_PER_BYTE); cr0 = dws->update_cr0(master, spi, transfer); dw_writel(dws, DW_SPI_CTRLR0, cr0); From patchwork Sun Sep 20 11:28:49 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Serge Semin X-Patchwork-Id: 258201 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-9.8 required=3.0 tests=BAYES_00, HEADER_FROM_DIFFERENT_DOMAINS, INCLUDES_PATCH, MAILING_LIST_MULTI, SIGNED_OFF_BY, SPF_HELO_NONE, SPF_PASS, URIBL_BLOCKED autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 90DEBC43465 for ; Sun, 20 Sep 2020 11:31:17 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 5B5B3216C4 for ; Sun, 20 Sep 2020 11:31:17 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726532AbgITL3n (ORCPT ); Sun, 20 Sep 2020 07:29:43 -0400 Received: from mail.baikalelectronics.com ([87.245.175.226]:53640 "EHLO mail.baikalelectronics.ru" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726390AbgITL33 (ORCPT ); Sun, 20 Sep 2020 07:29:29 -0400 Received: from localhost (unknown [127.0.0.1]) by mail.baikalelectronics.ru (Postfix) with ESMTP id B2D418001383; Sun, 20 Sep 2020 11:29:25 +0000 (UTC) X-Virus-Scanned: amavisd-new at baikalelectronics.ru Received: from mail.baikalelectronics.ru ([127.0.0.1]) by localhost (mail.baikalelectronics.ru [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id DDfvsA9FBVD7; Sun, 20 Sep 2020 14:29:25 +0300 (MSK) From: Serge Semin To: Mark Brown CC: Serge Semin , Serge Semin , Alexey Malahov , Ramil Zaripov , Pavel Parkhomenko , Andy Shevchenko , Andy Shevchenko , Lars Povlsen , "wuxu . wu" , Feng Tang , Rob Herring , , , Subject: [PATCH 05/30] spi: dw: Clear IRQ status on DW SPI controller reset Date: Sun, 20 Sep 2020 14:28:49 +0300 Message-ID: <20200920112914.26501-6-Sergey.Semin@baikalelectronics.ru> In-Reply-To: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> References: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> MIME-Version: 1.0 X-ClientProxiedBy: MAIL.baikal.int (192.168.51.25) To mail (192.168.51.25) Precedence: bulk List-ID: X-Mailing-List: linux-spi@vger.kernel.org It turns out the IRQ status isn't cleared after switching the controller off and getting it back on, which may cause raising false error interrupts if controller has been unsuccessfully used by, for instance, a bootloader before the driver is loaded. Let's explicitly clear the interrupts status in the dedicated controller reset method. Signed-off-by: Serge Semin --- drivers/spi/spi-dw.h | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/drivers/spi/spi-dw.h b/drivers/spi/spi-dw.h index 1ab704d1ebd8..ff77f39047ce 100644 --- a/drivers/spi/spi-dw.h +++ b/drivers/spi/spi-dw.h @@ -229,14 +229,15 @@ static inline void spi_umask_intr(struct dw_spi *dws, u32 mask) } /* - * This does disable the SPI controller, interrupts, and re-enable the - * controller back. Transmit and receive FIFO buffers are cleared when the - * device is disabled. + * This disables the SPI controller, interrupts, clears the interrupts status, + * and re-enable the controller back. Transmit and receive FIFO buffers are + * cleared when the device is disabled. */ static inline void spi_reset_chip(struct dw_spi *dws) { spi_enable_chip(dws, 0); spi_mask_intr(dws, 0xff); + dw_readl(dws, DW_SPI_ICR); spi_enable_chip(dws, 1); } From patchwork Sun Sep 20 11:28:50 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Serge Semin X-Patchwork-Id: 258199 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-9.8 required=3.0 tests=BAYES_00, HEADER_FROM_DIFFERENT_DOMAINS, INCLUDES_PATCH, MAILING_LIST_MULTI, SIGNED_OFF_BY, SPF_HELO_NONE, SPF_PASS, URIBL_BLOCKED autolearn=ham autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 17AA1C43463 for ; Sun, 20 Sep 2020 11:31:20 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id E17CF206E5 for ; Sun, 20 Sep 2020 11:31:19 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726311AbgITLbT (ORCPT ); Sun, 20 Sep 2020 07:31:19 -0400 Received: from mail.baikalelectronics.com ([87.245.175.226]:53648 "EHLO mail.baikalelectronics.ru" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726316AbgITL33 (ORCPT ); Sun, 20 Sep 2020 07:29:29 -0400 Received: from localhost (unknown [127.0.0.1]) by mail.baikalelectronics.ru (Postfix) with ESMTP id 791FF8001384; Sun, 20 Sep 2020 11:29:26 +0000 (UTC) X-Virus-Scanned: amavisd-new at baikalelectronics.ru Received: from mail.baikalelectronics.ru ([127.0.0.1]) by localhost (mail.baikalelectronics.ru [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id MXQmI7nk4Ji1; Sun, 20 Sep 2020 14:29:25 +0300 (MSK) From: Serge Semin To: Mark Brown CC: Serge Semin , Serge Semin , Alexey Malahov , Ramil Zaripov , Pavel Parkhomenko , Andy Shevchenko , Andy Shevchenko , Lars Povlsen , "wuxu . wu" , Feng Tang , Rob Herring , , , Subject: [PATCH 06/30] spi: dw: Disable all IRQs when controller is unused Date: Sun, 20 Sep 2020 14:28:50 +0300 Message-ID: <20200920112914.26501-7-Sergey.Semin@baikalelectronics.ru> In-Reply-To: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> References: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> MIME-Version: 1.0 X-ClientProxiedBy: MAIL.baikal.int (192.168.51.25) To mail (192.168.51.25) Precedence: bulk List-ID: X-Mailing-List: linux-spi@vger.kernel.org It's a good practice to disable all IRQs if a device is fully unused. In our case it is supposed to be done before requesting the IRQ and after the last byte of an SPI transfer is received. In the former case it's required to prevent the IRQ handler invocation before the driver data is fully initialized (which may happen if the IRQs status has been left uncleared before the device is probed). So we just moved the spi_hw_init() method invocation to the earlier stage before requesting the IRQ. In the later case there is just no point in having any of the IRQs enabled between SPI transfers and when there is no SPI message currently being processed. Signed-off-by: Serge Semin --- drivers/spi/spi-dw-core.c | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/drivers/spi/spi-dw-core.c b/drivers/spi/spi-dw-core.c index 18411f5b9954..be94ed5bb896 100644 --- a/drivers/spi/spi-dw-core.c +++ b/drivers/spi/spi-dw-core.c @@ -198,7 +198,7 @@ static irqreturn_t interrupt_transfer(struct dw_spi *dws) dw_reader(dws); if (dws->rx_end == dws->rx) { - spi_mask_intr(dws, SPI_INT_TXEI); + spi_mask_intr(dws, 0xff); spi_finalize_current_transfer(dws->master); return IRQ_HANDLED; } @@ -222,7 +222,7 @@ static irqreturn_t dw_spi_irq(int irq, void *dev_id) return IRQ_NONE; if (!master->cur_msg) { - spi_mask_intr(dws, SPI_INT_TXEI); + spi_mask_intr(dws, 0xff); return IRQ_HANDLED; } @@ -458,6 +458,9 @@ int dw_spi_add_host(struct device *dev, struct dw_spi *dws) spi_controller_set_devdata(master, dws); + /* Basic HW init */ + spi_hw_init(dev, dws); + ret = request_irq(dws->irq, dw_spi_irq, IRQF_SHARED, dev_name(dev), master); if (ret < 0) { @@ -485,9 +488,6 @@ int dw_spi_add_host(struct device *dev, struct dw_spi *dws) device_property_read_u32(dev, "rx-sample-delay-ns", &dws->def_rx_sample_dly_ns); - /* Basic HW init */ - spi_hw_init(dev, dws); - if (dws->dma_ops && dws->dma_ops->dma_init) { ret = dws->dma_ops->dma_init(dev, dws); if (ret) { From patchwork Sun Sep 20 11:28:55 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Serge Semin X-Patchwork-Id: 258211 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-9.8 required=3.0 tests=BAYES_00, HEADER_FROM_DIFFERENT_DOMAINS, INCLUDES_PATCH, MAILING_LIST_MULTI, SIGNED_OFF_BY, SPF_HELO_NONE, SPF_PASS, URIBL_BLOCKED autolearn=ham autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 7C6B4C43463 for ; Sun, 20 Sep 2020 11:29:42 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 4AB70221EC for ; Sun, 20 Sep 2020 11:29:42 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726471AbgITL3l (ORCPT ); Sun, 20 Sep 2020 07:29:41 -0400 Received: from mail.baikalelectronics.com ([87.245.175.226]:53710 "EHLO mail.baikalelectronics.ru" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726458AbgITL3l (ORCPT ); Sun, 20 Sep 2020 07:29:41 -0400 Received: from localhost (unknown [127.0.0.1]) by mail.baikalelectronics.ru (Postfix) with ESMTP id F24AD800163F; Sun, 20 Sep 2020 11:29:30 +0000 (UTC) X-Virus-Scanned: amavisd-new at baikalelectronics.ru Received: from mail.baikalelectronics.ru ([127.0.0.1]) by localhost (mail.baikalelectronics.ru [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id NPqE-OD8yIc0; Sun, 20 Sep 2020 14:29:30 +0300 (MSK) From: Serge Semin To: Mark Brown CC: Serge Semin , Serge Semin , Alexey Malahov , Ramil Zaripov , Pavel Parkhomenko , Andy Shevchenko , Andy Shevchenko , Lars Povlsen , "wuxu . wu" , Feng Tang , Rob Herring , , , Subject: [PATCH 11/30] spi: dw: Add DWC SSI capability Date: Sun, 20 Sep 2020 14:28:55 +0300 Message-ID: <20200920112914.26501-12-Sergey.Semin@baikalelectronics.ru> In-Reply-To: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> References: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> MIME-Version: 1.0 X-ClientProxiedBy: MAIL.baikal.int (192.168.51.25) To mail (192.168.51.25) Precedence: bulk List-ID: X-Mailing-List: linux-spi@vger.kernel.org Currently DWC SSI core is supported by means of setting up the core-specific update_cr0() callback. It isn't suitable for multiple reasons. First of all having exported several methods doing the same thing but for different chips makes the code harder to maintain. Secondly the spi-dw-core driver exports the methods, then the spi-dw-mmio driver sets the private data callback with one of them so to be called by the core driver again. That makes the code logic too complicated. Thirdly using callbacks for just updating the CR0 register is problematic, since in case if the register needed to be updated from different parts of the code, we'd have to create another callback (for instance the SPI device-specific parameters don't need to be calculated each time the SPI transfer is submitted, so it's better to pre-calculate the CR0 data at the SPI-device setup stage). So keeping all the above in mind let's discard the update_cr0() callbacks, define a generic and static dw_spi_update_cr0() method and create the DW_SPI_CAP_DWC_SSI capability, which when enabled would activate the alternative CR0 register layout. Signed-off-by: Serge Semin --- drivers/spi/spi-dw-core.c | 69 ++++++++++++--------------------------- drivers/spi/spi-dw-mmio.c | 20 ++---------- drivers/spi/spi-dw.h | 9 +---- 3 files changed, 23 insertions(+), 75 deletions(-) diff --git a/drivers/spi/spi-dw-core.c b/drivers/spi/spi-dw-core.c index 8f9737640ec1..c21641a485ce 100644 --- a/drivers/spi/spi-dw-core.c +++ b/drivers/spi/spi-dw-core.c @@ -228,60 +228,33 @@ static irqreturn_t dw_spi_irq(int irq, void *dev_id) return dws->transfer_handler(dws); } -/* Configure CTRLR0 for DW_apb_ssi */ -u32 dw_spi_update_cr0(struct spi_controller *master, struct spi_device *spi, - struct spi_transfer *transfer) +static void dw_spi_update_cr0(struct dw_spi *dws, struct spi_device *spi, + struct spi_transfer *transfer) { struct chip_data *chip = spi_get_ctldata(spi); u32 cr0; - /* Default SPI mode is SCPOL = 0, SCPH = 0 */ - cr0 = (transfer->bits_per_word - 1) - | (SSI_MOTO_SPI << SPI_FRF_OFFSET) - | ((((spi->mode & SPI_CPOL) ? 1 : 0) << SPI_SCOL_OFFSET) | - (((spi->mode & SPI_CPHA) ? 1 : 0) << SPI_SCPH_OFFSET) | - (((spi->mode & SPI_LOOP) ? 1 : 0) << SPI_SRL_OFFSET)) - | (chip->tmode << SPI_TMOD_OFFSET); - - return cr0; -} -EXPORT_SYMBOL_GPL(dw_spi_update_cr0); - -/* Configure CTRLR0 for DWC_ssi */ -u32 dw_spi_update_cr0_v1_01a(struct spi_controller *master, - struct spi_device *spi, - struct spi_transfer *transfer) -{ - struct dw_spi *dws = spi_controller_get_devdata(master); - struct chip_data *chip = spi_get_ctldata(spi); - u32 cr0; - - /* CTRLR0[ 4: 0] Data Frame Size */ cr0 = (transfer->bits_per_word - 1); - /* CTRLR0[ 7: 6] Frame Format */ - cr0 |= SSI_MOTO_SPI << DWC_SSI_CTRLR0_FRF_OFFSET; - - /* - * SPI mode (SCPOL|SCPH) - * CTRLR0[ 8] Serial Clock Phase - * CTRLR0[ 9] Serial Clock Polarity - */ - cr0 |= ((spi->mode & SPI_CPOL) ? 1 : 0) << DWC_SSI_CTRLR0_SCPOL_OFFSET; - cr0 |= ((spi->mode & SPI_CPHA) ? 1 : 0) << DWC_SSI_CTRLR0_SCPH_OFFSET; - - /* CTRLR0[11:10] Transfer Mode */ - cr0 |= chip->tmode << DWC_SSI_CTRLR0_TMOD_OFFSET; - - /* CTRLR0[13] Shift Register Loop */ - cr0 |= ((spi->mode & SPI_LOOP) ? 1 : 0) << DWC_SSI_CTRLR0_SRL_OFFSET; - - if (dws->caps & DW_SPI_CAP_KEEMBAY_MST) - cr0 |= DWC_SSI_CTRLR0_KEEMBAY_MST; + if (!(dws->caps & DW_SPI_CAP_DWC_SSI)) { + cr0 |= SSI_MOTO_SPI << SPI_FRF_OFFSET; + cr0 |= ((spi->mode & SPI_CPOL) ? 1 : 0) << SPI_SCOL_OFFSET; + cr0 |= ((spi->mode & SPI_CPHA) ? 1 : 0) << SPI_SCPH_OFFSET; + cr0 |= ((spi->mode & SPI_LOOP) ? 1 : 0) << SPI_SRL_OFFSET; + cr0 |= chip->tmode << SPI_TMOD_OFFSET; + } else { + cr0 |= SSI_MOTO_SPI << DWC_SSI_CTRLR0_FRF_OFFSET; + cr0 |= ((spi->mode & SPI_CPOL) ? 1 : 0) << DWC_SSI_CTRLR0_SCPOL_OFFSET; + cr0 |= ((spi->mode & SPI_CPHA) ? 1 : 0) << DWC_SSI_CTRLR0_SCPH_OFFSET; + cr0 |= ((spi->mode & SPI_LOOP) ? 1 : 0) << DWC_SSI_CTRLR0_SRL_OFFSET; + cr0 |= chip->tmode << DWC_SSI_CTRLR0_TMOD_OFFSET; + + if (dws->caps & DW_SPI_CAP_KEEMBAY_MST) + cr0 |= DWC_SSI_CTRLR0_KEEMBAY_MST; + } - return cr0; + dw_writel(dws, DW_SPI_CTRLR0, cr0); } -EXPORT_SYMBOL_GPL(dw_spi_update_cr0_v1_01a); static int dw_spi_transfer_one(struct spi_controller *master, struct spi_device *spi, struct spi_transfer *transfer) @@ -290,7 +263,6 @@ static int dw_spi_transfer_one(struct spi_controller *master, struct chip_data *chip = spi_get_ctldata(spi); u8 imask = 0; u16 txlevel = 0; - u32 cr0; int ret; dws->dma_mapped = 0; @@ -319,8 +291,7 @@ static int dw_spi_transfer_one(struct spi_controller *master, transfer->effective_speed_hz = dws->max_freq / chip->clk_div; - cr0 = dws->update_cr0(master, spi, transfer); - dw_writel(dws, DW_SPI_CTRLR0, cr0); + dw_spi_update_cr0(dws, spi, transfer); /* Check if current transfer is a DMA transaction */ if (master->can_dma && master->can_dma(master, spi, transfer)) diff --git a/drivers/spi/spi-dw-mmio.c b/drivers/spi/spi-dw-mmio.c index c0d351fde782..d0cc5bf4fa4e 100644 --- a/drivers/spi/spi-dw-mmio.c +++ b/drivers/spi/spi-dw-mmio.c @@ -110,9 +110,6 @@ static int dw_spi_mscc_init(struct platform_device *pdev, dwsmmio->dws.set_cs = dw_spi_mscc_set_cs; dwsmmio->priv = dwsmscc; - /* Register hook to configure CTRLR0 */ - dwsmmio->dws.update_cr0 = dw_spi_update_cr0; - return 0; } @@ -188,9 +185,6 @@ static int dw_spi_mscc_sparx5_init(struct platform_device *pdev, dwsmmio->dws.set_cs = dw_spi_sparx5_set_cs; dwsmmio->priv = dwsmscc; - /* Register hook to configure CTRLR0 */ - dwsmmio->dws.update_cr0 = dw_spi_update_cr0; - return 0; } @@ -199,18 +193,12 @@ static int dw_spi_alpine_init(struct platform_device *pdev, { dwsmmio->dws.caps = DW_SPI_CAP_CS_OVERRIDE; - /* Register hook to configure CTRLR0 */ - dwsmmio->dws.update_cr0 = dw_spi_update_cr0; - return 0; } static int dw_spi_dw_apb_init(struct platform_device *pdev, struct dw_spi_mmio *dwsmmio) { - /* Register hook to configure CTRLR0 */ - dwsmmio->dws.update_cr0 = dw_spi_update_cr0; - dw_spi_dma_setup_generic(&dwsmmio->dws); return 0; @@ -219,8 +207,7 @@ static int dw_spi_dw_apb_init(struct platform_device *pdev, static int dw_spi_dwc_ssi_init(struct platform_device *pdev, struct dw_spi_mmio *dwsmmio) { - /* Register hook to configure CTRLR0 */ - dwsmmio->dws.update_cr0 = dw_spi_update_cr0_v1_01a; + dwsmmio->dws.caps = DW_SPI_CAP_DWC_SSI; dw_spi_dma_setup_generic(&dwsmmio->dws); @@ -230,10 +217,7 @@ static int dw_spi_dwc_ssi_init(struct platform_device *pdev, static int dw_spi_keembay_init(struct platform_device *pdev, struct dw_spi_mmio *dwsmmio) { - dwsmmio->dws.caps = DW_SPI_CAP_KEEMBAY_MST; - - /* Register hook to configure CTRLR0 */ - dwsmmio->dws.update_cr0 = dw_spi_update_cr0_v1_01a; + dwsmmio->dws.caps = DW_SPI_CAP_KEEMBAY_MST | DW_SPI_CAP_DWC_SSI; return 0; } diff --git a/drivers/spi/spi-dw.h b/drivers/spi/spi-dw.h index da9b543322c9..c02351cf2f99 100644 --- a/drivers/spi/spi-dw.h +++ b/drivers/spi/spi-dw.h @@ -109,6 +109,7 @@ enum dw_ssi_type { /* DW SPI capabilities */ #define DW_SPI_CAP_CS_OVERRIDE BIT(0) #define DW_SPI_CAP_KEEMBAY_MST BIT(1) +#define DW_SPI_CAP_DWC_SSI BIT(2) struct dw_spi; struct dw_spi_dma_ops { @@ -136,8 +137,6 @@ struct dw_spi { u16 bus_num; u16 num_cs; /* supported slave numbers */ void (*set_cs)(struct spi_device *spi, bool enable); - u32 (*update_cr0)(struct spi_controller *master, struct spi_device *spi, - struct spi_transfer *transfer); /* Current message transfer state info */ size_t len; @@ -254,12 +253,6 @@ extern int dw_spi_add_host(struct device *dev, struct dw_spi *dws); extern void dw_spi_remove_host(struct dw_spi *dws); extern int dw_spi_suspend_host(struct dw_spi *dws); extern int dw_spi_resume_host(struct dw_spi *dws); -extern u32 dw_spi_update_cr0(struct spi_controller *master, - struct spi_device *spi, - struct spi_transfer *transfer); -extern u32 dw_spi_update_cr0_v1_01a(struct spi_controller *master, - struct spi_device *spi, - struct spi_transfer *transfer); #ifdef CONFIG_SPI_DW_DMA From patchwork Sun Sep 20 11:28:56 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Serge Semin X-Patchwork-Id: 258200 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-9.8 required=3.0 tests=BAYES_00, HEADER_FROM_DIFFERENT_DOMAINS, INCLUDES_PATCH, MAILING_LIST_MULTI, SIGNED_OFF_BY, SPF_HELO_NONE, SPF_PASS, URIBL_BLOCKED autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id E14CBC43469 for ; Sun, 20 Sep 2020 11:31:18 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id B6364206E5 for ; Sun, 20 Sep 2020 11:31:18 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726508AbgITL3m (ORCPT ); Sun, 20 Sep 2020 07:29:42 -0400 Received: from mail.baikalelectronics.com ([87.245.175.226]:53718 "EHLO mail.baikalelectronics.ru" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726462AbgITL3j (ORCPT ); Sun, 20 Sep 2020 07:29:39 -0400 Received: from localhost (unknown [127.0.0.1]) by mail.baikalelectronics.ru (Postfix) with ESMTP id 6F4578002549; Sun, 20 Sep 2020 11:29:31 +0000 (UTC) X-Virus-Scanned: amavisd-new at baikalelectronics.ru Received: from mail.baikalelectronics.ru ([127.0.0.1]) by localhost (mail.baikalelectronics.ru [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id 2kO6ijVyJ1qQ; Sun, 20 Sep 2020 14:29:30 +0300 (MSK) From: Serge Semin To: Mark Brown CC: Serge Semin , Serge Semin , Alexey Malahov , Ramil Zaripov , Pavel Parkhomenko , Andy Shevchenko , Andy Shevchenko , Lars Povlsen , "wuxu . wu" , Feng Tang , Rob Herring , , , Subject: [PATCH 12/30] spi: dw: Detach SPI device specific CR0 config method Date: Sun, 20 Sep 2020 14:28:56 +0300 Message-ID: <20200920112914.26501-13-Sergey.Semin@baikalelectronics.ru> In-Reply-To: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> References: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> MIME-Version: 1.0 X-ClientProxiedBy: MAIL.baikal.int (192.168.51.25) To mail (192.168.51.25) Precedence: bulk List-ID: X-Mailing-List: linux-spi@vger.kernel.org Indeed there is no point in detecting the SPI peripheral device parameters and initializing the CR0 register fields each time an SPI transfer is executed. Instead let's define a dedicated CR0 chip-data member, which will be initialized in accordance with the SPI device settings at the moment of setting it up. By doing so we'll finally make the SPI device chip_data serving as it's supposed to - to preserve the SPI device specific DW SPI configuration. See spi-fsl-dspi.c, spi-pl022.c, spi-pxa2xx.c drivers for example of the way the chip data is utilized. Signed-off-by: Serge Semin --- drivers/spi/spi-dw-core.c | 35 +++++++++++++++++++++++++++-------- 1 file changed, 27 insertions(+), 8 deletions(-) diff --git a/drivers/spi/spi-dw-core.c b/drivers/spi/spi-dw-core.c index c21641a485ce..a9644351d75f 100644 --- a/drivers/spi/spi-dw-core.c +++ b/drivers/spi/spi-dw-core.c @@ -27,6 +27,7 @@ struct chip_data { u16 clk_div; /* baud rate divider */ u32 speed_hz; /* baud rate */ + u32 cr0; u32 rx_sample_dly; /* RX sample delay */ }; @@ -228,31 +229,41 @@ static irqreturn_t dw_spi_irq(int irq, void *dev_id) return dws->transfer_handler(dws); } -static void dw_spi_update_cr0(struct dw_spi *dws, struct spi_device *spi, - struct spi_transfer *transfer) +static u32 dw_spi_get_cr0(struct dw_spi *dws, struct spi_device *spi) { - struct chip_data *chip = spi_get_ctldata(spi); - u32 cr0; - - cr0 = (transfer->bits_per_word - 1); + u32 cr0 = 0; if (!(dws->caps & DW_SPI_CAP_DWC_SSI)) { cr0 |= SSI_MOTO_SPI << SPI_FRF_OFFSET; cr0 |= ((spi->mode & SPI_CPOL) ? 1 : 0) << SPI_SCOL_OFFSET; cr0 |= ((spi->mode & SPI_CPHA) ? 1 : 0) << SPI_SCPH_OFFSET; cr0 |= ((spi->mode & SPI_LOOP) ? 1 : 0) << SPI_SRL_OFFSET; - cr0 |= chip->tmode << SPI_TMOD_OFFSET; } else { cr0 |= SSI_MOTO_SPI << DWC_SSI_CTRLR0_FRF_OFFSET; cr0 |= ((spi->mode & SPI_CPOL) ? 1 : 0) << DWC_SSI_CTRLR0_SCPOL_OFFSET; cr0 |= ((spi->mode & SPI_CPHA) ? 1 : 0) << DWC_SSI_CTRLR0_SCPH_OFFSET; cr0 |= ((spi->mode & SPI_LOOP) ? 1 : 0) << DWC_SSI_CTRLR0_SRL_OFFSET; - cr0 |= chip->tmode << DWC_SSI_CTRLR0_TMOD_OFFSET; if (dws->caps & DW_SPI_CAP_KEEMBAY_MST) cr0 |= DWC_SSI_CTRLR0_KEEMBAY_MST; } + return cr0; +} + +static void dw_spi_update_cr0(struct dw_spi *dws, struct spi_device *spi, + struct spi_transfer *transfer) +{ + struct chip_data *chip = spi_get_ctldata(spi); + u32 cr0 = chip->cr0; + + cr0 |= (transfer->bits_per_word - 1); + + if (!(dws->caps & DW_SPI_CAP_DWC_SSI)) + cr0 |= chip->tmode << SPI_TMOD_OFFSET; + else + cr0 |= chip->tmode << DWC_SSI_CTRLR0_TMOD_OFFSET; + dw_writel(dws, DW_SPI_CTRLR0, cr0); } @@ -350,6 +361,7 @@ static void dw_spi_handle_err(struct spi_controller *master, /* This may be called twice for each spi dev */ static int dw_spi_setup(struct spi_device *spi) { + struct dw_spi *dws = spi_controller_get_devdata(spi->controller); struct chip_data *chip; /* Only alloc on first setup */ @@ -373,6 +385,13 @@ static int dw_spi_setup(struct spi_device *spi) dws->max_freq); } + /* + * Update CR0 data each time the setup callback is invoked since + * the device parameters could have been changed, for instance, by + * the MMC SPI driver or something else. + */ + chip->cr0 = dw_spi_get_cr0(dws, spi); + chip->tmode = SPI_TMOD_TR; return 0; From patchwork Sun Sep 20 11:28:57 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Serge Semin X-Patchwork-Id: 258207 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-9.8 required=3.0 tests=BAYES_00, HEADER_FROM_DIFFERENT_DOMAINS, INCLUDES_PATCH, MAILING_LIST_MULTI, SIGNED_OFF_BY, SPF_HELO_NONE, SPF_PASS, URIBL_BLOCKED autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id CEA02C43465 for ; Sun, 20 Sep 2020 11:30:40 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 9EC9B20EDD for ; Sun, 20 Sep 2020 11:30:40 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726688AbgITLa1 (ORCPT ); Sun, 20 Sep 2020 07:30:27 -0400 Received: from mail.baikalelectronics.com ([87.245.175.226]:53930 "EHLO mail.baikalelectronics.ru" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726489AbgITL3w (ORCPT ); Sun, 20 Sep 2020 07:29:52 -0400 Received: from localhost (unknown [127.0.0.1]) by mail.baikalelectronics.ru (Postfix) with ESMTP id 1DF46800254A; Sun, 20 Sep 2020 11:29:32 +0000 (UTC) X-Virus-Scanned: amavisd-new at baikalelectronics.ru Received: from mail.baikalelectronics.ru ([127.0.0.1]) by localhost (mail.baikalelectronics.ru [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id 6t2WLHDTUFsV; Sun, 20 Sep 2020 14:29:31 +0300 (MSK) From: Serge Semin To: Mark Brown CC: Serge Semin , Serge Semin , Alexey Malahov , Ramil Zaripov , Pavel Parkhomenko , Andy Shevchenko , Andy Shevchenko , Lars Povlsen , "wuxu . wu" , Feng Tang , Rob Herring , , , Subject: [PATCH 13/30] spi: dw: Update SPI bus speed in a config function Date: Sun, 20 Sep 2020 14:28:57 +0300 Message-ID: <20200920112914.26501-14-Sergey.Semin@baikalelectronics.ru> In-Reply-To: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> References: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> MIME-Version: 1.0 X-ClientProxiedBy: MAIL.baikal.int (192.168.51.25) To mail (192.168.51.25) Precedence: bulk List-ID: X-Mailing-List: linux-spi@vger.kernel.org The SPI bus speed update functionality will be useful in another parts of the driver too (like to implement the SPI memory operations and from the DW SPI glue layers). Let's move it to the update_cr0() method then and since the later is now updating not only the CTRLR0 register alter its prototype to have a generic function name not related to CR0. Leave the too long line with the chip->clk_div setting as is for now, since it's going to be changed later anyway. Signed-off-by: Serge Semin --- drivers/spi/spi-dw-core.c | 28 ++++++++++++++-------------- 1 file changed, 14 insertions(+), 14 deletions(-) diff --git a/drivers/spi/spi-dw-core.c b/drivers/spi/spi-dw-core.c index a9644351d75f..0b80a16d9872 100644 --- a/drivers/spi/spi-dw-core.c +++ b/drivers/spi/spi-dw-core.c @@ -251,8 +251,8 @@ static u32 dw_spi_get_cr0(struct dw_spi *dws, struct spi_device *spi) return cr0; } -static void dw_spi_update_cr0(struct dw_spi *dws, struct spi_device *spi, - struct spi_transfer *transfer) +static void dw_spi_update_config(struct dw_spi *dws, struct spi_device *spi, + struct spi_transfer *transfer) { struct chip_data *chip = spi_get_ctldata(spi); u32 cr0 = chip->cr0; @@ -265,6 +265,17 @@ static void dw_spi_update_cr0(struct dw_spi *dws, struct spi_device *spi, cr0 |= chip->tmode << DWC_SSI_CTRLR0_TMOD_OFFSET; dw_writel(dws, DW_SPI_CTRLR0, cr0); + + /* Handle per transfer options for bpw and speed */ + if (transfer->speed_hz != dws->current_freq) { + if (transfer->speed_hz != chip->speed_hz) { + /* clk_div doesn't support odd number */ + chip->clk_div = (DIV_ROUND_UP(dws->max_freq, transfer->speed_hz) + 1) & 0xfffe; + chip->speed_hz = transfer->speed_hz; + } + dws->current_freq = transfer->speed_hz; + spi_set_clk(dws, chip->clk_div); + } } static int dw_spi_transfer_one(struct spi_controller *master, @@ -289,21 +300,10 @@ static int dw_spi_transfer_one(struct spi_controller *master, spi_enable_chip(dws, 0); - /* Handle per transfer options for bpw and speed */ - if (transfer->speed_hz != dws->current_freq) { - if (transfer->speed_hz != chip->speed_hz) { - /* clk_div doesn't support odd number */ - chip->clk_div = (DIV_ROUND_UP(dws->max_freq, transfer->speed_hz) + 1) & 0xfffe; - chip->speed_hz = transfer->speed_hz; - } - dws->current_freq = transfer->speed_hz; - spi_set_clk(dws, chip->clk_div); - } + dw_spi_update_config(dws, spi, transfer); transfer->effective_speed_hz = dws->max_freq / chip->clk_div; - dw_spi_update_cr0(dws, spi, transfer); - /* Check if current transfer is a DMA transaction */ if (master->can_dma && master->can_dma(master, spi, transfer)) dws->dma_mapped = master->cur_msg_mapped; From patchwork Sun Sep 20 11:28:58 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Serge Semin X-Patchwork-Id: 258210 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-9.8 required=3.0 tests=BAYES_00, HEADER_FROM_DIFFERENT_DOMAINS, INCLUDES_PATCH, MAILING_LIST_MULTI, SIGNED_OFF_BY, SPF_HELO_NONE, SPF_PASS autolearn=ham autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 37DDCC43463 for ; Sun, 20 Sep 2020 11:30:07 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 07A2420EDD for ; Sun, 20 Sep 2020 11:30:07 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726390AbgITLaF (ORCPT ); Sun, 20 Sep 2020 07:30:05 -0400 Received: from mail.baikalelectronics.com ([87.245.175.226]:53710 "EHLO mail.baikalelectronics.ru" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726472AbgITL3r (ORCPT ); Sun, 20 Sep 2020 07:29:47 -0400 Received: from localhost (unknown [127.0.0.1]) by mail.baikalelectronics.ru (Postfix) with ESMTP id C588B800254B; Sun, 20 Sep 2020 11:29:32 +0000 (UTC) X-Virus-Scanned: amavisd-new at baikalelectronics.ru Received: from mail.baikalelectronics.ru ([127.0.0.1]) by localhost (mail.baikalelectronics.ru [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id AJ5YZNwkhzYN; Sun, 20 Sep 2020 14:29:32 +0300 (MSK) From: Serge Semin To: Mark Brown CC: Serge Semin , Serge Semin , Alexey Malahov , Ramil Zaripov , Pavel Parkhomenko , Andy Shevchenko , Andy Shevchenko , Lars Povlsen , "wuxu . wu" , Feng Tang , Rob Herring , , , Subject: [PATCH 14/30] spi: dw: Simplify the SPI bus speed config procedure Date: Sun, 20 Sep 2020 14:28:58 +0300 Message-ID: <20200920112914.26501-15-Sergey.Semin@baikalelectronics.ru> In-Reply-To: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> References: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> MIME-Version: 1.0 X-ClientProxiedBy: MAIL.baikal.int (192.168.51.25) To mail (192.168.51.25) Precedence: bulk List-ID: X-Mailing-List: linux-spi@vger.kernel.org The code currently responsible for the SPI communication speed setting up is a bit messy. Most likely for some historical reason the bus frequency is saved in the peripheral chip private data. It's pointless now since the custom communication speed is a SPI-transfer-specific thing and only if there is no SPI transfer data specified (like during the SPI memory operations) it can be taken from the SPI device structure. But even in the later case there is no point in having the clock divider and the SPI bus frequency saved in the chip data, because the controller can be used for both SPI-transfer-based and SPI-transfer-less communications. From software point of view keeping the current clock divider in an SPI-device specific storage may give a small performance gain (to avoid sometimes a round-up division), but in comparison to the total SPI transfer time it just doesn't worth saving a few CPU cycles in comparison to the total SPI transfer time while having the harder to read code. The only optimization, which could worth preserving in the code is to avoid unnecessary DW SPI controller registers update if it's possible. So to speak let's simplify the SPI communication speed update procedure by removing the clock-related fields from the peripheral chip data and update the DW SPI clock divider only if it's really changed. The later change is reached by keeping the effective SPI bus speed in the internal DW SPI private data. Signed-off-by: Serge Semin --- drivers/spi/spi-dw-core.c | 23 ++++++++++------------- 1 file changed, 10 insertions(+), 13 deletions(-) diff --git a/drivers/spi/spi-dw-core.c b/drivers/spi/spi-dw-core.c index 0b80a16d9872..92138a6ada12 100644 --- a/drivers/spi/spi-dw-core.c +++ b/drivers/spi/spi-dw-core.c @@ -24,9 +24,6 @@ struct chip_data { u8 tmode; /* TR/TO/RO/EEPROM */ - u16 clk_div; /* baud rate divider */ - u32 speed_hz; /* baud rate */ - u32 cr0; u32 rx_sample_dly; /* RX sample delay */ }; @@ -256,6 +253,8 @@ static void dw_spi_update_config(struct dw_spi *dws, struct spi_device *spi, { struct chip_data *chip = spi_get_ctldata(spi); u32 cr0 = chip->cr0; + u32 speed_hz; + u16 clk_div; cr0 |= (transfer->bits_per_word - 1); @@ -266,15 +265,13 @@ static void dw_spi_update_config(struct dw_spi *dws, struct spi_device *spi, dw_writel(dws, DW_SPI_CTRLR0, cr0); - /* Handle per transfer options for bpw and speed */ - if (transfer->speed_hz != dws->current_freq) { - if (transfer->speed_hz != chip->speed_hz) { - /* clk_div doesn't support odd number */ - chip->clk_div = (DIV_ROUND_UP(dws->max_freq, transfer->speed_hz) + 1) & 0xfffe; - chip->speed_hz = transfer->speed_hz; - } - dws->current_freq = transfer->speed_hz; - spi_set_clk(dws, chip->clk_div); + /* Note DW APB SSI clock divider doesn't support odd numbers */ + clk_div = (DIV_ROUND_UP(dws->max_freq, transfer->speed_hz) + 1) & 0xfffe; + speed_hz = dws->max_freq / clk_div; + + if (dws->current_freq != speed_hz) { + spi_set_clk(dws, clk_div); + dws->current_freq = speed_hz; } } @@ -302,7 +299,7 @@ static int dw_spi_transfer_one(struct spi_controller *master, dw_spi_update_config(dws, spi, transfer); - transfer->effective_speed_hz = dws->max_freq / chip->clk_div; + transfer->effective_speed_hz = dws->current_freq; /* Check if current transfer is a DMA transaction */ if (master->can_dma && master->can_dma(master, spi, transfer)) From patchwork Sun Sep 20 11:29:00 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Serge Semin X-Patchwork-Id: 258205 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-9.8 required=3.0 tests=BAYES_00, HEADER_FROM_DIFFERENT_DOMAINS, INCLUDES_PATCH, MAILING_LIST_MULTI, SIGNED_OFF_BY, SPF_HELO_NONE, SPF_PASS, URIBL_BLOCKED autolearn=ham autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id CD097C43469 for ; Sun, 20 Sep 2020 11:30:42 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 9B75420672 for ; Sun, 20 Sep 2020 11:30:42 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726731AbgITLal (ORCPT ); Sun, 20 Sep 2020 07:30:41 -0400 Received: from mail.baikalelectronics.com ([87.245.175.226]:53682 "EHLO mail.baikalelectronics.ru" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726484AbgITL3v (ORCPT ); Sun, 20 Sep 2020 07:29:51 -0400 Received: from localhost (unknown [127.0.0.1]) by mail.baikalelectronics.ru (Postfix) with ESMTP id 87EB98002548; Sun, 20 Sep 2020 11:29:34 +0000 (UTC) X-Virus-Scanned: amavisd-new at baikalelectronics.ru Received: from mail.baikalelectronics.ru ([127.0.0.1]) by localhost (mail.baikalelectronics.ru [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id SAVTBsy5yY5c; Sun, 20 Sep 2020 14:29:33 +0300 (MSK) From: Serge Semin To: Mark Brown CC: Serge Semin , Serge Semin , Alexey Malahov , Ramil Zaripov , Pavel Parkhomenko , Andy Shevchenko , Andy Shevchenko , Lars Povlsen , "wuxu . wu" , Feng Tang , Rob Herring , , , Subject: [PATCH 16/30] spi: dw: Add DW SPI controller config structure Date: Sun, 20 Sep 2020 14:29:00 +0300 Message-ID: <20200920112914.26501-17-Sergey.Semin@baikalelectronics.ru> In-Reply-To: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> References: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> MIME-Version: 1.0 X-ClientProxiedBy: MAIL.baikal.int (192.168.51.25) To mail (192.168.51.25) Precedence: bulk List-ID: X-Mailing-List: linux-spi@vger.kernel.org DW APB SSI controller can be used by the two SPI core interfaces: traditional SPI transfers and SPI memory operations. The controller needs to be accordingly configured at runtime when the corresponding operations are executed. In order to do that for the both interfaces from a single function we introduce a new data wrapper for the transfer mode, data width, number of data frames (for the automatic data transfer) and the bus frequency. It will be used by the update_config() method to tune the DW APB SSI up. The update_config() method is made exported to be used not only by the DW SPI core driver, but by the glue layer drivers too. This will be required in a coming further commit. Signed-off-by: Serge Semin --- drivers/spi/spi-dw-core.c | 29 +++++++++++++++++------------ drivers/spi/spi-dw.h | 10 ++++++++++ 2 files changed, 27 insertions(+), 12 deletions(-) diff --git a/drivers/spi/spi-dw-core.c b/drivers/spi/spi-dw-core.c index f00fc4828480..9102685c1523 100644 --- a/drivers/spi/spi-dw-core.c +++ b/drivers/spi/spi-dw-core.c @@ -20,10 +20,8 @@ #include #endif -/* Slave spi_dev related */ +/* Slave spi_device related */ struct chip_data { - u8 tmode; /* TR/TO/RO/EEPROM */ - u32 cr0; u32 rx_sample_dly; /* RX sample delay */ }; @@ -248,25 +246,28 @@ static u32 dw_spi_get_cr0(struct dw_spi *dws, struct spi_device *spi) return cr0; } -static void dw_spi_update_config(struct dw_spi *dws, struct spi_device *spi, - struct spi_transfer *transfer) +void dw_spi_update_config(struct dw_spi *dws, struct spi_device *spi, + struct dw_spi_cfg *cfg) { struct chip_data *chip = spi_get_ctldata(spi); u32 cr0 = chip->cr0; u32 speed_hz; u16 clk_div; - cr0 |= (transfer->bits_per_word - 1); + cr0 |= (cfg->dfs - 1); if (!(dws->caps & DW_SPI_CAP_DWC_SSI)) - cr0 |= chip->tmode << SPI_TMOD_OFFSET; + cr0 |= cfg->tmode << SPI_TMOD_OFFSET; else - cr0 |= chip->tmode << DWC_SSI_CTRLR0_TMOD_OFFSET; + cr0 |= cfg->tmode << DWC_SSI_CTRLR0_TMOD_OFFSET; dw_writel(dws, DW_SPI_CTRLR0, cr0); + if (cfg->tmode == SPI_TMOD_EPROMREAD || cfg->tmode == SPI_TMOD_RO) + dw_writel(dws, DW_SPI_CTRLR1, cfg->ndf ? cfg->ndf - 1 : 0); + /* Note DW APB SSI clock divider doesn't support odd numbers */ - clk_div = (DIV_ROUND_UP(dws->max_freq, transfer->speed_hz) + 1) & 0xfffe; + clk_div = (DIV_ROUND_UP(dws->max_freq, cfg->freq) + 1) & 0xfffe; speed_hz = dws->max_freq / clk_div; if (dws->current_freq != speed_hz) { @@ -280,11 +281,17 @@ static void dw_spi_update_config(struct dw_spi *dws, struct spi_device *spi, dws->cur_rx_sample_dly = chip->rx_sample_dly; } } +EXPORT_SYMBOL_GPL(dw_spi_update_config); static int dw_spi_transfer_one(struct spi_controller *master, struct spi_device *spi, struct spi_transfer *transfer) { struct dw_spi *dws = spi_controller_get_devdata(master); + struct dw_spi_cfg cfg = { + .tmode = SPI_TMOD_TR, + .dfs = transfer->bits_per_word, + .freq = transfer->speed_hz, + }; u8 imask = 0; u16 txlevel = 0; int ret; @@ -302,7 +309,7 @@ static int dw_spi_transfer_one(struct spi_controller *master, spi_enable_chip(dws, 0); - dw_spi_update_config(dws, spi, transfer); + dw_spi_update_config(dws, spi, &cfg); transfer->effective_speed_hz = dws->current_freq; @@ -388,8 +395,6 @@ static int dw_spi_setup(struct spi_device *spi) */ chip->cr0 = dw_spi_get_cr0(dws, spi); - chip->tmode = SPI_TMOD_TR; - return 0; } diff --git a/drivers/spi/spi-dw.h b/drivers/spi/spi-dw.h index c02351cf2f99..2a2346438564 100644 --- a/drivers/spi/spi-dw.h +++ b/drivers/spi/spi-dw.h @@ -111,6 +111,14 @@ enum dw_ssi_type { #define DW_SPI_CAP_KEEMBAY_MST BIT(1) #define DW_SPI_CAP_DWC_SSI BIT(2) +/* Slave spi_transfer/spi_mem_op related */ +struct dw_spi_cfg { + u8 tmode; + u8 dfs; + u32 ndf; + u32 freq; +}; + struct dw_spi; struct dw_spi_dma_ops { int (*dma_init)(struct device *dev, struct dw_spi *dws); @@ -249,6 +257,8 @@ static inline void spi_shutdown_chip(struct dw_spi *dws) } extern void dw_spi_set_cs(struct spi_device *spi, bool enable); +extern void dw_spi_update_config(struct dw_spi *dws, struct spi_device *spi, + struct dw_spi_cfg *cfg); extern int dw_spi_add_host(struct device *dev, struct dw_spi *dws); extern void dw_spi_remove_host(struct dw_spi *dws); extern int dw_spi_suspend_host(struct dw_spi *dws); From patchwork Sun Sep 20 11:29:01 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Serge Semin X-Patchwork-Id: 258204 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-9.8 required=3.0 tests=BAYES_00, HEADER_FROM_DIFFERENT_DOMAINS, INCLUDES_PATCH, MAILING_LIST_MULTI, SIGNED_OFF_BY, SPF_HELO_NONE, SPF_PASS, URIBL_BLOCKED autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 0F1BEC43463 for ; Sun, 20 Sep 2020 11:31:00 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id C9D6720672 for ; Sun, 20 Sep 2020 11:30:59 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726739AbgITLam (ORCPT ); Sun, 20 Sep 2020 07:30:42 -0400 Received: from mail.baikalelectronics.com ([87.245.175.226]:53640 "EHLO mail.baikalelectronics.ru" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726475AbgITL3u (ORCPT ); Sun, 20 Sep 2020 07:29:50 -0400 Received: from localhost (unknown [127.0.0.1]) by mail.baikalelectronics.ru (Postfix) with ESMTP id 548008002562; Sun, 20 Sep 2020 11:29:35 +0000 (UTC) X-Virus-Scanned: amavisd-new at baikalelectronics.ru Received: from mail.baikalelectronics.ru ([127.0.0.1]) by localhost (mail.baikalelectronics.ru [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id cdPCdQANdvMQ; Sun, 20 Sep 2020 14:29:34 +0300 (MSK) From: Serge Semin To: Mark Brown CC: Serge Semin , Serge Semin , Alexey Malahov , Ramil Zaripov , Pavel Parkhomenko , Andy Shevchenko , Andy Shevchenko , Lars Povlsen , "wuxu . wu" , Feng Tang , Rob Herring , , , Subject: [PATCH 17/30] spi: dw: Refactor data IO procedure Date: Sun, 20 Sep 2020 14:29:01 +0300 Message-ID: <20200920112914.26501-18-Sergey.Semin@baikalelectronics.ru> In-Reply-To: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> References: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> MIME-Version: 1.0 X-ClientProxiedBy: MAIL.baikal.int (192.168.51.25) To mail (192.168.51.25) Precedence: bulk List-ID: X-Mailing-List: linux-spi@vger.kernel.org The Tx and Rx data write/read procedure can be significantly simplified by using Tx/Rx transfer lengths instead of the end pointers. By having the Tx/Rx data leftover lengths (in the number of transfer words) we can get rid of all subtraction and division operations utilized here and there in the tx_max(), rx_max(), dw_writer() and dw_reader() methods. Such modification will not only give us the more optimized IO procedures, but will make the data IO methods much more readable than before. Signed-off-by: Serge Semin --- drivers/spi/spi-dw-core.c | 37 +++++++++++++++++-------------------- drivers/spi/spi-dw.h | 5 ++--- 2 files changed, 19 insertions(+), 23 deletions(-) diff --git a/drivers/spi/spi-dw-core.c b/drivers/spi/spi-dw-core.c index 9102685c1523..84c1fdfd6e52 100644 --- a/drivers/spi/spi-dw-core.c +++ b/drivers/spi/spi-dw-core.c @@ -108,9 +108,8 @@ EXPORT_SYMBOL_GPL(dw_spi_set_cs); /* Return the max entries we can fill into tx fifo */ static inline u32 tx_max(struct dw_spi *dws) { - u32 tx_left, tx_room, rxtx_gap; + u32 tx_room, rxtx_gap; - tx_left = (dws->tx_end - dws->tx) / dws->n_bytes; tx_room = dws->fifo_len - dw_readl(dws, DW_SPI_TXFLR); /* @@ -121,18 +120,15 @@ static inline u32 tx_max(struct dw_spi *dws) * shift registers. So a control from sw point of * view is taken. */ - rxtx_gap = ((dws->rx_end - dws->rx) - (dws->tx_end - dws->tx)) - / dws->n_bytes; + rxtx_gap = dws->fifo_len - (dws->rx_len - dws->tx_len); - return min3(tx_left, tx_room, (u32) (dws->fifo_len - rxtx_gap)); + return min3((u32)dws->tx_len, tx_room, rxtx_gap); } /* Return the max entries we should read out of rx fifo */ static inline u32 rx_max(struct dw_spi *dws) { - u32 rx_left = (dws->rx_end - dws->rx) / dws->n_bytes; - - return min_t(u32, rx_left, dw_readl(dws, DW_SPI_RXFLR)); + return min_t(u32, dws->rx_len, dw_readl(dws, DW_SPI_RXFLR)); } static void dw_writer(struct dw_spi *dws) @@ -141,15 +137,16 @@ static void dw_writer(struct dw_spi *dws) u16 txw = 0; while (max--) { - /* Set the tx word if the transfer's original "tx" is not null */ - if (dws->tx_end - dws->len) { + if (dws->tx) { if (dws->n_bytes == 1) txw = *(u8 *)(dws->tx); else txw = *(u16 *)(dws->tx); + + dws->tx += dws->n_bytes; } dw_write_io_reg(dws, DW_SPI_DR, txw); - dws->tx += dws->n_bytes; + --dws->tx_len; } } @@ -160,14 +157,15 @@ static void dw_reader(struct dw_spi *dws) while (max--) { rxw = dw_read_io_reg(dws, DW_SPI_DR); - /* Care rx only if the transfer's original "rx" is not null */ - if (dws->rx_end - dws->len) { + if (dws->rx) { if (dws->n_bytes == 1) *(u8 *)(dws->rx) = rxw; else *(u16 *)(dws->rx) = rxw; + + dws->rx += dws->n_bytes; } - dws->rx += dws->n_bytes; + --dws->rx_len; } } @@ -192,7 +190,7 @@ static irqreturn_t interrupt_transfer(struct dw_spi *dws) } dw_reader(dws); - if (dws->rx_end == dws->rx) { + if (!dws->rx_len) { spi_mask_intr(dws, 0xff); spi_finalize_current_transfer(dws->master); return IRQ_HANDLED; @@ -299,12 +297,11 @@ static int dw_spi_transfer_one(struct spi_controller *master, dws->dma_mapped = 0; dws->n_bytes = DIV_ROUND_UP(transfer->bits_per_word, BITS_PER_BYTE); dws->tx = (void *)transfer->tx_buf; - dws->tx_end = dws->tx + transfer->len; + dws->tx_len = transfer->len / dws->n_bytes; dws->rx = transfer->rx_buf; - dws->rx_end = dws->rx + transfer->len; - dws->len = transfer->len; + dws->rx_len = dws->tx_len; - /* Ensure dw->rx and dw->rx_end are visible */ + /* Ensure the data above is visible for all CPUs */ smp_mb(); spi_enable_chip(dws, 0); @@ -331,7 +328,7 @@ static int dw_spi_transfer_one(struct spi_controller *master, return ret; } } else { - txlevel = min_t(u16, dws->fifo_len / 2, dws->len / dws->n_bytes); + txlevel = min_t(u16, dws->fifo_len / 2, dws->tx_len); dw_writel(dws, DW_SPI_TXFTLR, txlevel); /* Set the interrupt mask */ diff --git a/drivers/spi/spi-dw.h b/drivers/spi/spi-dw.h index 2a2346438564..cfc9f63acde4 100644 --- a/drivers/spi/spi-dw.h +++ b/drivers/spi/spi-dw.h @@ -147,11 +147,10 @@ struct dw_spi { void (*set_cs)(struct spi_device *spi, bool enable); /* Current message transfer state info */ - size_t len; void *tx; - void *tx_end; + unsigned int tx_len; void *rx; - void *rx_end; + unsigned int rx_len; int dma_mapped; u8 n_bytes; /* current is a 1/2 bytes op */ irqreturn_t (*transfer_handler)(struct dw_spi *dws); From patchwork Sun Sep 20 11:29:04 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Serge Semin X-Patchwork-Id: 258203 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-9.8 required=3.0 tests=BAYES_00, HEADER_FROM_DIFFERENT_DOMAINS, INCLUDES_PATCH, MAILING_LIST_MULTI, SIGNED_OFF_BY, SPF_HELO_NONE, SPF_PASS, URIBL_BLOCKED autolearn=ham autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id B742EC43463 for ; Sun, 20 Sep 2020 11:31:02 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 926FF23600 for ; Sun, 20 Sep 2020 11:31:02 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726789AbgITLbB (ORCPT ); Sun, 20 Sep 2020 07:31:01 -0400 Received: from mail.baikalelectronics.com ([87.245.175.226]:53690 "EHLO mail.baikalelectronics.ru" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726473AbgITL3t (ORCPT ); Sun, 20 Sep 2020 07:29:49 -0400 Received: from localhost (unknown [127.0.0.1]) by mail.baikalelectronics.ru (Postfix) with ESMTP id 1E791803202E; Sun, 20 Sep 2020 11:29:37 +0000 (UTC) X-Virus-Scanned: amavisd-new at baikalelectronics.ru Received: from mail.baikalelectronics.ru ([127.0.0.1]) by localhost (mail.baikalelectronics.ru [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id MPRx6JeoOrAO; Sun, 20 Sep 2020 14:29:36 +0300 (MSK) From: Serge Semin To: Mark Brown CC: Serge Semin , Serge Semin , Alexey Malahov , Ramil Zaripov , Pavel Parkhomenko , Andy Shevchenko , Andy Shevchenko , Lars Povlsen , "wuxu . wu" , Feng Tang , Rob Herring , , , Subject: [PATCH 20/30] spi: dw: Unmask IRQs after enabling the chip Date: Sun, 20 Sep 2020 14:29:04 +0300 Message-ID: <20200920112914.26501-21-Sergey.Semin@baikalelectronics.ru> In-Reply-To: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> References: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> MIME-Version: 1.0 X-ClientProxiedBy: MAIL.baikal.int (192.168.51.25) To mail (192.168.51.25) Precedence: bulk List-ID: X-Mailing-List: linux-spi@vger.kernel.org It's theoretically erroneous to enable IRQ before the chip is turned on. If IRQ handler gets executed before the chip is enabled, then any data written to the Tx FIFO will be just ignored. I say "theoretically" because we haven't noticed any problem with that, but let's fix it anyway just in case... Signed-off-by: Serge Semin --- drivers/spi/spi-dw-core.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/spi/spi-dw-core.c b/drivers/spi/spi-dw-core.c index 08bc53b9de88..8dbe11c1821c 100644 --- a/drivers/spi/spi-dw-core.c +++ b/drivers/spi/spi-dw-core.c @@ -355,8 +355,6 @@ static int dw_spi_transfer_one(struct spi_controller *master, spi_enable_chip(dws, 1); return ret; } - } else { - dw_spi_irq_setup(dws); } spi_enable_chip(dws, 1); @@ -364,6 +362,8 @@ static int dw_spi_transfer_one(struct spi_controller *master, if (dws->dma_mapped) return dws->dma_ops->dma_transfer(dws, transfer); + dw_spi_irq_setup(dws); + return 1; } From patchwork Sun Sep 20 11:29:05 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Serge Semin X-Patchwork-Id: 258202 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-9.8 required=3.0 tests=BAYES_00, HEADER_FROM_DIFFERENT_DOMAINS, INCLUDES_PATCH, MAILING_LIST_MULTI, SIGNED_OFF_BY, SPF_HELO_NONE, SPF_PASS, URIBL_BLOCKED autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id C32C1C43463 for ; Sun, 20 Sep 2020 11:31:14 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 955AA206E5 for ; Sun, 20 Sep 2020 11:31:14 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726483AbgITLbB (ORCPT ); Sun, 20 Sep 2020 07:31:01 -0400 Received: from mail.baikalelectronics.com ([87.245.175.226]:53698 "EHLO mail.baikalelectronics.ru" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726474AbgITL3u (ORCPT ); Sun, 20 Sep 2020 07:29:50 -0400 Received: from localhost (unknown [127.0.0.1]) by mail.baikalelectronics.ru (Postfix) with ESMTP id C618A80057AA; Sun, 20 Sep 2020 11:29:37 +0000 (UTC) X-Virus-Scanned: amavisd-new at baikalelectronics.ru Received: from mail.baikalelectronics.ru ([127.0.0.1]) by localhost (mail.baikalelectronics.ru [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id 3RU1y5s3P7f4; Sun, 20 Sep 2020 14:29:37 +0300 (MSK) From: Serge Semin To: Mark Brown CC: Serge Semin , Serge Semin , Alexey Malahov , Ramil Zaripov , Pavel Parkhomenko , Andy Shevchenko , Andy Shevchenko , Lars Povlsen , "wuxu . wu" , Feng Tang , Rob Herring , , , Subject: [PATCH 21/30] spi: dw: Discard chip enabling on DMA setup error Date: Sun, 20 Sep 2020 14:29:05 +0300 Message-ID: <20200920112914.26501-22-Sergey.Semin@baikalelectronics.ru> In-Reply-To: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> References: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> MIME-Version: 1.0 X-ClientProxiedBy: MAIL.baikal.int (192.168.51.25) To mail (192.168.51.25) Precedence: bulk List-ID: X-Mailing-List: linux-spi@vger.kernel.org It's pointless to enable the chip back if the DMA setup procedure fails, since we'll disable it on the next transfer anyway. For the same reason We don't do that in case of a failure detected in any other methods called from the transfer_one() method. While at it consider any non-zero value returned from the dma_setup callback to be erroneous as it's supposed to be in the kernel. Signed-off-by: Serge Semin --- drivers/spi/spi-dw-core.c | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/drivers/spi/spi-dw-core.c b/drivers/spi/spi-dw-core.c index 8dbe11c1821c..65db4dd3ea8a 100644 --- a/drivers/spi/spi-dw-core.c +++ b/drivers/spi/spi-dw-core.c @@ -351,10 +351,8 @@ static int dw_spi_transfer_one(struct spi_controller *master, if (dws->dma_mapped) { ret = dws->dma_ops->dma_setup(dws, transfer); - if (ret < 0) { - spi_enable_chip(dws, 1); + if (ret) return ret; - } } spi_enable_chip(dws, 1); From patchwork Sun Sep 20 11:29:06 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Serge Semin X-Patchwork-Id: 258208 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-9.8 required=3.0 tests=BAYES_00, HEADER_FROM_DIFFERENT_DOMAINS, INCLUDES_PATCH, MAILING_LIST_MULTI, SIGNED_OFF_BY, SPF_HELO_NONE, SPF_PASS, URIBL_BLOCKED autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 120BBC43463 for ; Sun, 20 Sep 2020 11:30:26 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id CECA820EDD for ; Sun, 20 Sep 2020 11:30:25 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726645AbgITLaN (ORCPT ); Sun, 20 Sep 2020 07:30:13 -0400 Received: from mail.baikalelectronics.com ([87.245.175.226]:53934 "EHLO mail.baikalelectronics.ru" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726501AbgITL3x (ORCPT ); Sun, 20 Sep 2020 07:29:53 -0400 Received: from localhost (unknown [127.0.0.1]) by mail.baikalelectronics.ru (Postfix) with ESMTP id 9071280057A8; Sun, 20 Sep 2020 11:29:38 +0000 (UTC) X-Virus-Scanned: amavisd-new at baikalelectronics.ru Received: from mail.baikalelectronics.ru ([127.0.0.1]) by localhost (mail.baikalelectronics.ru [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id 2f_I8YyWNmS2; Sun, 20 Sep 2020 14:29:38 +0300 (MSK) From: Serge Semin To: Mark Brown CC: Serge Semin , Serge Semin , Alexey Malahov , Ramil Zaripov , Pavel Parkhomenko , Andy Shevchenko , Andy Shevchenko , Lars Povlsen , "wuxu . wu" , Feng Tang , Rob Herring , , , Subject: [PATCH 22/30] spi: dw: De-assert chip-select on reset Date: Sun, 20 Sep 2020 14:29:06 +0300 Message-ID: <20200920112914.26501-23-Sergey.Semin@baikalelectronics.ru> In-Reply-To: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> References: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> MIME-Version: 1.0 X-ClientProxiedBy: MAIL.baikal.int (192.168.51.25) To mail (192.168.51.25) Precedence: bulk List-ID: X-Mailing-List: linux-spi@vger.kernel.org SPI memory operations implementation will require to have the CS register cleared before executing the operation in order not to have the transmission automatically started prior the Tx FIFO is pre-initialized. Let's clear the register then on explicit controller reset to fulfil the requirements in case of an error or having the CS left set by a bootloader or another software. Signed-off-by: Serge Semin --- drivers/spi/spi-dw.h | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/drivers/spi/spi-dw.h b/drivers/spi/spi-dw.h index cfc9f63acde4..eb1d46983319 100644 --- a/drivers/spi/spi-dw.h +++ b/drivers/spi/spi-dw.h @@ -237,15 +237,16 @@ static inline void spi_umask_intr(struct dw_spi *dws, u32 mask) } /* - * This disables the SPI controller, interrupts, clears the interrupts status, - * and re-enable the controller back. Transmit and receive FIFO buffers are - * cleared when the device is disabled. + * This disables the SPI controller, interrupts, clears the interrupts status + * and CS, then re-enables the controller back. Transmit and receive FIFO + * buffers are cleared when the device is disabled. */ static inline void spi_reset_chip(struct dw_spi *dws) { spi_enable_chip(dws, 0); spi_mask_intr(dws, 0xff); dw_readl(dws, DW_SPI_ICR); + dw_writel(dws, DW_SPI_SER, 0); spi_enable_chip(dws, 1); } From patchwork Sun Sep 20 11:29:08 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Serge Semin X-Patchwork-Id: 258209 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-9.8 required=3.0 tests=BAYES_00, HEADER_FROM_DIFFERENT_DOMAINS, INCLUDES_PATCH, MAILING_LIST_MULTI, SIGNED_OFF_BY, SPF_HELO_NONE, SPF_PASS, URIBL_BLOCKED autolearn=ham autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id D3ED4C43465 for ; Sun, 20 Sep 2020 11:30:13 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 9DFBD216C4 for ; Sun, 20 Sep 2020 11:30:13 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726472AbgITLaN (ORCPT ); Sun, 20 Sep 2020 07:30:13 -0400 Received: from mail.baikalelectronics.com ([87.245.175.226]:53938 "EHLO mail.baikalelectronics.ru" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726495AbgITL3w (ORCPT ); Sun, 20 Sep 2020 07:29:52 -0400 Received: from localhost (unknown [127.0.0.1]) by mail.baikalelectronics.ru (Postfix) with ESMTP id EBCEC80060AB; Sun, 20 Sep 2020 11:29:39 +0000 (UTC) X-Virus-Scanned: amavisd-new at baikalelectronics.ru Received: from mail.baikalelectronics.ru ([127.0.0.1]) by localhost (mail.baikalelectronics.ru [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id Dh3AEuqhIo0G; Sun, 20 Sep 2020 14:29:39 +0300 (MSK) From: Serge Semin To: Mark Brown CC: Serge Semin , Serge Semin , Alexey Malahov , Ramil Zaripov , Pavel Parkhomenko , Andy Shevchenko , Andy Shevchenko , Lars Povlsen , "wuxu . wu" , Feng Tang , Rob Herring , , , Subject: [PATCH 24/30] spi: dw: Move num-of retries parameter to the header file Date: Sun, 20 Sep 2020 14:29:08 +0300 Message-ID: <20200920112914.26501-25-Sergey.Semin@baikalelectronics.ru> In-Reply-To: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> References: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> MIME-Version: 1.0 X-ClientProxiedBy: MAIL.baikal.int (192.168.51.25) To mail (192.168.51.25) Precedence: bulk List-ID: X-Mailing-List: linux-spi@vger.kernel.org The parameter will be needed for another wait-done method being added in the framework of the SPI memory operation modification in a further commit. Signed-off-by: Serge Semin --- drivers/spi/spi-dw-dma.c | 5 ++--- drivers/spi/spi-dw.h | 2 ++ 2 files changed, 4 insertions(+), 3 deletions(-) diff --git a/drivers/spi/spi-dw-dma.c b/drivers/spi/spi-dw-dma.c index bb390ff67d1d..9db119dc5554 100644 --- a/drivers/spi/spi-dw-dma.c +++ b/drivers/spi/spi-dw-dma.c @@ -17,7 +17,6 @@ #include "spi-dw.h" -#define WAIT_RETRIES 5 #define RX_BUSY 0 #define RX_BURST_LEVEL 16 #define TX_BUSY 1 @@ -208,7 +207,7 @@ static inline bool dw_spi_dma_tx_busy(struct dw_spi *dws) static int dw_spi_dma_wait_tx_done(struct dw_spi *dws, struct spi_transfer *xfer) { - int retry = WAIT_RETRIES; + int retry = SPI_WAIT_RETRIES; struct spi_delay delay; u32 nents; @@ -283,7 +282,7 @@ static inline bool dw_spi_dma_rx_busy(struct dw_spi *dws) static int dw_spi_dma_wait_rx_done(struct dw_spi *dws) { - int retry = WAIT_RETRIES; + int retry = SPI_WAIT_RETRIES; struct spi_delay delay; unsigned long ns, us; u32 nents; diff --git a/drivers/spi/spi-dw.h b/drivers/spi/spi-dw.h index eb1d46983319..946065201c9c 100644 --- a/drivers/spi/spi-dw.h +++ b/drivers/spi/spi-dw.h @@ -100,6 +100,8 @@ #define SPI_DMA_RDMAE (1 << 0) #define SPI_DMA_TDMAE (1 << 1) +#define SPI_WAIT_RETRIES 5 + enum dw_ssi_type { SSI_MOTO_SPI = 0, SSI_TI_SSP, From patchwork Sun Sep 20 11:29:13 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Serge Semin X-Patchwork-Id: 258206 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-9.8 required=3.0 tests=BAYES_00, HEADER_FROM_DIFFERENT_DOMAINS, INCLUDES_PATCH, MAILING_LIST_MULTI, SIGNED_OFF_BY, SPF_HELO_NONE, SPF_PASS, URIBL_BLOCKED autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 545B4C43468 for ; Sun, 20 Sep 2020 11:30:41 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 2813F20672 for ; Sun, 20 Sep 2020 11:30:41 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726684AbgITLa0 (ORCPT ); Sun, 20 Sep 2020 07:30:26 -0400 Received: from mail.baikalelectronics.com ([87.245.175.226]:53996 "EHLO mail.baikalelectronics.ru" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726551AbgITL3z (ORCPT ); Sun, 20 Sep 2020 07:29:55 -0400 Received: from localhost (unknown [127.0.0.1]) by mail.baikalelectronics.ru (Postfix) with ESMTP id 0979780060B9; Sun, 20 Sep 2020 11:29:44 +0000 (UTC) X-Virus-Scanned: amavisd-new at baikalelectronics.ru Received: from mail.baikalelectronics.ru ([127.0.0.1]) by localhost (mail.baikalelectronics.ru [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id G4IjOgbZ2q5Y; Sun, 20 Sep 2020 14:29:43 +0300 (MSK) From: Serge Semin To: Mark Brown , Rob Herring CC: Serge Semin , Serge Semin , Alexey Malahov , Ramil Zaripov , Pavel Parkhomenko , Andy Shevchenko , Andy Shevchenko , Lars Povlsen , "wuxu . wu" , Feng Tang , , , Subject: [PATCH 29/30] dt-bindings: spi: dw: Add Baikal-T1 SPI Controllers Date: Sun, 20 Sep 2020 14:29:13 +0300 Message-ID: <20200920112914.26501-30-Sergey.Semin@baikalelectronics.ru> In-Reply-To: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> References: <20200920112914.26501-1-Sergey.Semin@baikalelectronics.ru> MIME-Version: 1.0 X-ClientProxiedBy: MAIL.baikal.int (192.168.51.25) To mail (192.168.51.25) Precedence: bulk List-ID: X-Mailing-List: linux-spi@vger.kernel.org These controllers are based on the DW APB SSI IP-core and embedded into the SoC, so two of them are equipped with IRQ, DMA, 64 words FIFOs and 4 native CS, while another one as being utilized by the Baikal-T1 System Boot Controller has got a very limited resources: no IRQ, no DMA, only a single native chip-select and just 8 bytes Tx/Rx FIFOs available. That's why we have to mark the IRQ to be optional for the later interface. The SPI controller embedded into the Baikal-T1 System Boot Controller can be also used to directly access an external SPI flash by means of a dedicated FSM. The corresponding MMIO region availability is switchable by the embedded multiplexor, which phandle can be specified in the dts node. * We added a new example to test out the non-standard Baikal-T1 System Boot SPI Controller DT binding. Co-developed-by: Ramil Zaripov Signed-off-by: Ramil Zaripov Signed-off-by: Serge Semin Reviewed-by: Rob Herring --- .../bindings/spi/snps,dw-apb-ssi.yaml | 33 +++++++++++++++++-- 1 file changed, 31 insertions(+), 2 deletions(-) diff --git a/Documentation/devicetree/bindings/spi/snps,dw-apb-ssi.yaml b/Documentation/devicetree/bindings/spi/snps,dw-apb-ssi.yaml index c62cbe79f00d..d6ae35777dac 100644 --- a/Documentation/devicetree/bindings/spi/snps,dw-apb-ssi.yaml +++ b/Documentation/devicetree/bindings/spi/snps,dw-apb-ssi.yaml @@ -22,6 +22,21 @@ allOf: properties: reg: minItems: 2 + - if: + properties: + compatible: + contains: + enum: + - baikal,bt1-sys-ssi + then: + properties: + mux-controls: + maxItems: 1 + required: + - mux-controls + else: + required: + - interrupts properties: compatible: @@ -44,12 +59,16 @@ properties: - const: snps,dw-apb-ssi - description: Intel Keem Bay SPI Controller const: intel,keembay-ssi + - description: Baikal-T1 SPI Controller + const: baikal,bt1-ssi + - description: Baikal-T1 System Boot SPI Controller + const: baikal,bt1-sys-ssi reg: minItems: 1 items: - description: DW APB SSI controller memory mapped registers - - description: SPI MST region map + - description: SPI MST region map or directly mapped SPI ROM interrupts: maxItems: 1 @@ -114,7 +133,6 @@ required: - reg - "#address-cells" - "#size-cells" - - interrupts - clocks examples: @@ -130,4 +148,15 @@ examples: cs-gpios = <&gpio0 13 0>, <&gpio0 14 0>; }; + - | + spi@1f040100 { + compatible = "baikal,bt1-sys-ssi"; + reg = <0x1f040100 0x900>, + <0x1c000000 0x1000000>; + #address-cells = <1>; + #size-cells = <0>; + mux-controls = <&boot_mux>; + clocks = <&ccu_sys>; + clock-names = "ssi_clk"; + }; ...