]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/commitdiff
fixes for 4.19
authorSasha Levin <sashal@kernel.org>
Wed, 12 Feb 2020 13:37:20 +0000 (08:37 -0500)
committerSasha Levin <sashal@kernel.org>
Wed, 12 Feb 2020 13:37:20 +0000 (08:37 -0500)
Signed-off-by: Sasha Levin <sashal@kernel.org>
queue-4.19/gpio-zynq-report-gpio-direction-at-boot.patch [new file with mode: 0644]
queue-4.19/serial-uartps-add-a-timeout-to-the-tx-empty-wait.patch [new file with mode: 0644]
queue-4.19/series
queue-4.19/spi-spi-mem-add-extra-sanity-checks-on-the-op-param.patch [new file with mode: 0644]
queue-4.19/spi-spi-mem-fix-inverted-logic-in-op-sanity-check.patch [new file with mode: 0644]

diff --git a/queue-4.19/gpio-zynq-report-gpio-direction-at-boot.patch b/queue-4.19/gpio-zynq-report-gpio-direction-at-boot.patch
new file mode 100644 (file)
index 0000000..e2636be
--- /dev/null
@@ -0,0 +1,67 @@
+From 48e2526aeced20483b3eab27adb8f30b5bcdaf64 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Mon, 10 Feb 2020 10:18:26 -0700
+Subject: gpio: zynq: Report gpio direction at boot
+
+From: Brandon Maier <Brandon.Maier@collins.com>
+
+commit 6169005ceb8c715582eca70df3912cd2b351ede2 upstream
+
+The Zynq's gpios can be configured by the bootloader. But Linux will
+erroneously report all gpios as inputs unless we implement
+get_direction().
+
+Signed-off-by: Brandon Maier <Brandon.Maier@collins.com>
+Tested-by: Michal Simek <michal.simek@xilinx.com>
+Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
+Cc: stable <stable@vger.kernel.org> # 4.19
+Signed-off-by: Mathieu Poirier <mathieu.poirier@linaro.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ drivers/gpio/gpio-zynq.c | 23 +++++++++++++++++++++++
+ 1 file changed, 23 insertions(+)
+
+diff --git a/drivers/gpio/gpio-zynq.c b/drivers/gpio/gpio-zynq.c
+index a9238fb150131..5dec96155814b 100644
+--- a/drivers/gpio/gpio-zynq.c
++++ b/drivers/gpio/gpio-zynq.c
+@@ -357,6 +357,28 @@ static int zynq_gpio_dir_out(struct gpio_chip *chip, unsigned int pin,
+       return 0;
+ }
++/**
++ * zynq_gpio_get_direction - Read the direction of the specified GPIO pin
++ * @chip:     gpio_chip instance to be worked on
++ * @pin:      gpio pin number within the device
++ *
++ * This function returns the direction of the specified GPIO.
++ *
++ * Return: 0 for output, 1 for input
++ */
++static int zynq_gpio_get_direction(struct gpio_chip *chip, unsigned int pin)
++{
++      u32 reg;
++      unsigned int bank_num, bank_pin_num;
++      struct zynq_gpio *gpio = gpiochip_get_data(chip);
++
++      zynq_gpio_get_bank_pin(pin, &bank_num, &bank_pin_num, gpio);
++
++      reg = readl_relaxed(gpio->base_addr + ZYNQ_GPIO_DIRM_OFFSET(bank_num));
++
++      return !(reg & BIT(bank_pin_num));
++}
++
+ /**
+  * zynq_gpio_irq_mask - Disable the interrupts for a gpio pin
+  * @irq_data: per irq and chip data passed down to chip functions
+@@ -829,6 +851,7 @@ static int zynq_gpio_probe(struct platform_device *pdev)
+       chip->free = zynq_gpio_free;
+       chip->direction_input = zynq_gpio_dir_in;
+       chip->direction_output = zynq_gpio_dir_out;
++      chip->get_direction = zynq_gpio_get_direction;
+       chip->base = of_alias_get_id(pdev->dev.of_node, "gpio");
+       chip->ngpio = gpio->p_data->ngpio;
+-- 
+2.20.1
+
diff --git a/queue-4.19/serial-uartps-add-a-timeout-to-the-tx-empty-wait.patch b/queue-4.19/serial-uartps-add-a-timeout-to-the-tx-empty-wait.patch
new file mode 100644 (file)
index 0000000..af5dcea
--- /dev/null
@@ -0,0 +1,71 @@
+From 9935038f90cf05f3c2e235fcded8a139af908c79 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Mon, 10 Feb 2020 10:18:25 -0700
+Subject: serial: uartps: Add a timeout to the tx empty wait
+
+From: Shubhrajyoti Datta <shubhrajyoti.datta@xilinx.com>
+
+commit 277375b864e8147975b064b513f491e2a910e66a upstream
+
+In case the cable is not connected then the target gets into
+an infinite wait for tx empty.
+Add a timeout to the tx empty wait.
+
+Reported-by: Jean-Francois Dagenais <jeff.dagenais@gmail.com>
+Signed-off-by: Shubhrajyoti Datta <shubhrajyoti.datta@xilinx.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+Cc: stable <stable@vger.kernel.org> # 4.19
+Signed-off-by: Mathieu Poirier <mathieu.poirier@linaro.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ drivers/tty/serial/xilinx_uartps.c | 14 ++++++++++----
+ 1 file changed, 10 insertions(+), 4 deletions(-)
+
+diff --git a/drivers/tty/serial/xilinx_uartps.c b/drivers/tty/serial/xilinx_uartps.c
+index 66d49d5118853..7cbee19ea93d5 100644
+--- a/drivers/tty/serial/xilinx_uartps.c
++++ b/drivers/tty/serial/xilinx_uartps.c
+@@ -26,6 +26,7 @@
+ #include <linux/of.h>
+ #include <linux/module.h>
+ #include <linux/pm_runtime.h>
++#include <linux/iopoll.h>
+ #define CDNS_UART_TTY_NAME    "ttyPS"
+ #define CDNS_UART_NAME                "xuartps"
+@@ -34,6 +35,7 @@
+ #define CDNS_UART_NR_PORTS    2
+ #define CDNS_UART_FIFO_SIZE   64      /* FIFO size */
+ #define CDNS_UART_REGISTER_SPACE      0x1000
++#define TX_TIMEOUT            500000
+ /* Rx Trigger level */
+ static int rx_trigger_level = 56;
+@@ -681,16 +683,20 @@ static void cdns_uart_set_termios(struct uart_port *port,
+       unsigned int cval = 0;
+       unsigned int baud, minbaud, maxbaud;
+       unsigned long flags;
+-      unsigned int ctrl_reg, mode_reg;
++      unsigned int ctrl_reg, mode_reg, val;
++      int err;
+       spin_lock_irqsave(&port->lock, flags);
+       /* Wait for the transmit FIFO to empty before making changes */
+       if (!(readl(port->membase + CDNS_UART_CR) &
+                               CDNS_UART_CR_TX_DIS)) {
+-              while (!(readl(port->membase + CDNS_UART_SR) &
+-                              CDNS_UART_SR_TXEMPTY)) {
+-                      cpu_relax();
++              err = readl_poll_timeout(port->membase + CDNS_UART_SR,
++                                       val, (val & CDNS_UART_SR_TXEMPTY),
++                                       1000, TX_TIMEOUT);
++              if (err) {
++                      dev_err(port->dev, "timed out waiting for tx empty");
++                      return;
+               }
+       }
+-- 
+2.20.1
+
index d9af5a4c81c6d32c39213a87fa27e8bb1d56a256..5ebd33fb334a9127069a2e7963154329d89bc2a9 100644 (file)
@@ -1,2 +1,6 @@
 asoc-pcm-update-fe-be-trigger-order-based-on-the-com.patch
 hv_sock-remove-the-accept-port-restriction.patch
+serial-uartps-add-a-timeout-to-the-tx-empty-wait.patch
+gpio-zynq-report-gpio-direction-at-boot.patch
+spi-spi-mem-add-extra-sanity-checks-on-the-op-param.patch
+spi-spi-mem-fix-inverted-logic-in-op-sanity-check.patch
diff --git a/queue-4.19/spi-spi-mem-add-extra-sanity-checks-on-the-op-param.patch b/queue-4.19/spi-spi-mem-add-extra-sanity-checks-on-the-op-param.patch
new file mode 100644 (file)
index 0000000..ad17cd7
--- /dev/null
@@ -0,0 +1,114 @@
+From 40beb98f7c94280f3ee69e80c4925bc946a3fb63 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Mon, 10 Feb 2020 10:18:27 -0700
+Subject: spi: spi-mem: Add extra sanity checks on the op param
+
+From: Boris Brezillon <boris.brezillon@bootlin.com>
+
+commit 380583227c0c7f52383b0cd5c0e2de93ed31d553 upstream
+
+Some combinations are simply not valid and should be rejected before
+the op is passed to the SPI controller driver.
+
+Add an spi_mem_check_op() helper and use it in spi_mem_exec_op() and
+spi_mem_supports_op() to make sure the spi-mem operation is valid.
+
+Signed-off-by: Boris Brezillon <boris.brezillon@bootlin.com>
+Signed-off-by: Mark Brown <broonie@kernel.org>
+Cc: stable <stable@vger.kernel.org> # 4.19
+Signed-off-by: Mathieu Poirier <mathieu.poirier@linaro.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ drivers/spi/spi-mem.c | 54 ++++++++++++++++++++++++++++++++++++++-----
+ 1 file changed, 48 insertions(+), 6 deletions(-)
+
+diff --git a/drivers/spi/spi-mem.c b/drivers/spi/spi-mem.c
+index eb72dba71d832..cc3d425aae56c 100644
+--- a/drivers/spi/spi-mem.c
++++ b/drivers/spi/spi-mem.c
+@@ -12,6 +12,8 @@
+ #include "internals.h"
++#define SPI_MEM_MAX_BUSWIDTH          4
++
+ /**
+  * spi_controller_dma_map_mem_op_data() - DMA-map the buffer attached to a
+  *                                      memory operation
+@@ -149,6 +151,44 @@ static bool spi_mem_default_supports_op(struct spi_mem *mem,
+ }
+ EXPORT_SYMBOL_GPL(spi_mem_default_supports_op);
++static bool spi_mem_buswidth_is_valid(u8 buswidth)
++{
++      if (hweight8(buswidth) > 1 || buswidth > SPI_MEM_MAX_BUSWIDTH)
++              return false;
++
++      return true;
++}
++
++static int spi_mem_check_op(const struct spi_mem_op *op)
++{
++      if (!op->cmd.buswidth)
++              return -EINVAL;
++
++      if ((op->addr.nbytes && !op->addr.buswidth) ||
++          (op->dummy.nbytes && !op->dummy.buswidth) ||
++          (op->data.nbytes && !op->data.buswidth))
++              return -EINVAL;
++
++      if (spi_mem_buswidth_is_valid(op->cmd.buswidth) ||
++          spi_mem_buswidth_is_valid(op->addr.buswidth) ||
++          spi_mem_buswidth_is_valid(op->dummy.buswidth) ||
++          spi_mem_buswidth_is_valid(op->data.buswidth))
++              return -EINVAL;
++
++      return 0;
++}
++
++static bool spi_mem_internal_supports_op(struct spi_mem *mem,
++                                       const struct spi_mem_op *op)
++{
++      struct spi_controller *ctlr = mem->spi->controller;
++
++      if (ctlr->mem_ops && ctlr->mem_ops->supports_op)
++              return ctlr->mem_ops->supports_op(mem, op);
++
++      return spi_mem_default_supports_op(mem, op);
++}
++
+ /**
+  * spi_mem_supports_op() - Check if a memory device and the controller it is
+  *                       connected to support a specific memory operation
+@@ -166,12 +206,10 @@ EXPORT_SYMBOL_GPL(spi_mem_default_supports_op);
+  */
+ bool spi_mem_supports_op(struct spi_mem *mem, const struct spi_mem_op *op)
+ {
+-      struct spi_controller *ctlr = mem->spi->controller;
+-
+-      if (ctlr->mem_ops && ctlr->mem_ops->supports_op)
+-              return ctlr->mem_ops->supports_op(mem, op);
++      if (spi_mem_check_op(op))
++              return false;
+-      return spi_mem_default_supports_op(mem, op);
++      return spi_mem_internal_supports_op(mem, op);
+ }
+ EXPORT_SYMBOL_GPL(spi_mem_supports_op);
+@@ -196,7 +234,11 @@ int spi_mem_exec_op(struct spi_mem *mem, const struct spi_mem_op *op)
+       u8 *tmpbuf;
+       int ret;
+-      if (!spi_mem_supports_op(mem, op))
++      ret = spi_mem_check_op(op);
++      if (ret)
++              return ret;
++
++      if (!spi_mem_internal_supports_op(mem, op))
+               return -ENOTSUPP;
+       if (ctlr->mem_ops) {
+-- 
+2.20.1
+
diff --git a/queue-4.19/spi-spi-mem-fix-inverted-logic-in-op-sanity-check.patch b/queue-4.19/spi-spi-mem-fix-inverted-logic-in-op-sanity-check.patch
new file mode 100644 (file)
index 0000000..28455d5
--- /dev/null
@@ -0,0 +1,48 @@
+From b55cdc35ff19b386de955f81867f761a9175e64e Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Tue, 25 Sep 2018 11:46:55 +0200
+Subject: spi: spi-mem: Fix inverted logic in op sanity check
+
+From: Geert Uytterhoeven <geert+renesas@glider.be>
+
+[ Upstream commit aea3877e24f3acc6145094848dbb85f9ce85674a ]
+
+On r8a7791/koelsch:
+
+    m25p80 spi0.0: error -22 reading 9f
+    m25p80: probe of spi0.0 failed with error -22
+
+Apparently the logic in spi_mem_check_op() is wrong, rejecting the
+spi-mem operation if any buswidth is valid, instead of invalid.
+
+Fixes: 380583227c0c7f52 ("spi: spi-mem: Add extra sanity checks on the op param")
+Signed-off-by: Geert Uytterhoeven <geert+renesas@glider.be>
+Reviewed-by: Boris Brezillon <boris.brezillon@bootlin.com>
+Signed-off-by: Mark Brown <broonie@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ drivers/spi/spi-mem.c | 8 ++++----
+ 1 file changed, 4 insertions(+), 4 deletions(-)
+
+diff --git a/drivers/spi/spi-mem.c b/drivers/spi/spi-mem.c
+index cc3d425aae56c..62a7b80801d22 100644
+--- a/drivers/spi/spi-mem.c
++++ b/drivers/spi/spi-mem.c
+@@ -169,10 +169,10 @@ static int spi_mem_check_op(const struct spi_mem_op *op)
+           (op->data.nbytes && !op->data.buswidth))
+               return -EINVAL;
+-      if (spi_mem_buswidth_is_valid(op->cmd.buswidth) ||
+-          spi_mem_buswidth_is_valid(op->addr.buswidth) ||
+-          spi_mem_buswidth_is_valid(op->dummy.buswidth) ||
+-          spi_mem_buswidth_is_valid(op->data.buswidth))
++      if (!spi_mem_buswidth_is_valid(op->cmd.buswidth) ||
++          !spi_mem_buswidth_is_valid(op->addr.buswidth) ||
++          !spi_mem_buswidth_is_valid(op->dummy.buswidth) ||
++          !spi_mem_buswidth_is_valid(op->data.buswidth))
+               return -EINVAL;
+       return 0;
+-- 
+2.20.1
+