Linux Serial subsystem development
 help / color / mirror / Atom feed
* [PATCH v5 09/11] platform: Accept const properties
From: Jan Kiszka @ 2017-06-02  7:28 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Linus Walleij, Alexandre Courbot
  Cc: Linux Kernel Mailing List, linux-serial, linux-gpio,
	Sudip Mukherjee, Andy Shevchenko, Sascha Weisenberger
In-Reply-To: <cover.1496388533.git.jan.kiszka@siemens.com>

Aligns us with device_add_properties, the function we call.

Signed-off-by: Jan Kiszka <jan.kiszka@siemens.com>
---
 drivers/base/platform.c         | 2 +-
 include/linux/platform_device.h | 2 +-
 2 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/base/platform.c b/drivers/base/platform.c
index a102152301c8..71ea6f4d33c2 100644
--- a/drivers/base/platform.c
+++ b/drivers/base/platform.c
@@ -344,7 +344,7 @@ EXPORT_SYMBOL_GPL(platform_device_add_data);
  * platform device is released.
  */
 int platform_device_add_properties(struct platform_device *pdev,
-				   struct property_entry *properties)
+				   const struct property_entry *properties)
 {
 	return device_add_properties(&pdev->dev, properties);
 }
diff --git a/include/linux/platform_device.h b/include/linux/platform_device.h
index 98c2a7c7108e..49f634d96118 100644
--- a/include/linux/platform_device.h
+++ b/include/linux/platform_device.h
@@ -172,7 +172,7 @@ extern int platform_device_add_resources(struct platform_device *pdev,
 extern int platform_device_add_data(struct platform_device *pdev,
 				    const void *data, size_t size);
 extern int platform_device_add_properties(struct platform_device *pdev,
-					  struct property_entry *properties);
+				const struct property_entry *properties);
 extern int platform_device_add(struct platform_device *pdev);
 extern void platform_device_del(struct platform_device *pdev);
 extern void platform_device_put(struct platform_device *pdev);
-- 
2.12.3

^ permalink raw reply related

* [PATCH v5 08/11] serial: exar: Factor out platform hooks
From: Jan Kiszka @ 2017-06-02  7:28 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Linus Walleij, Alexandre Courbot
  Cc: Linux Kernel Mailing List, linux-serial, linux-gpio,
	Sudip Mukherjee, Andy Shevchenko, Sascha Weisenberger
In-Reply-To: <cover.1496388533.git.jan.kiszka@siemens.com>

This prepares the addition of IOT2040 platform support by preparing the
needed setup and rs485_config hooks.

Signed-off-by: Jan Kiszka <jan.kiszka@siemens.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
---
 drivers/tty/serial/8250/8250_exar.c | 32 +++++++++++++++++++++++++++-----
 1 file changed, 27 insertions(+), 5 deletions(-)

diff --git a/drivers/tty/serial/8250/8250_exar.c b/drivers/tty/serial/8250/8250_exar.c
index ee4b142f3ed0..1106f1f58c77 100644
--- a/drivers/tty/serial/8250/8250_exar.c
+++ b/drivers/tty/serial/8250/8250_exar.c
@@ -63,6 +63,11 @@
 
 struct exar8250;
 
+struct exar8250_platform {
+	int (*rs485_config)(struct uart_port *, struct serial_rs485 *);
+	int (*register_gpio)(struct pci_dev *, struct uart_8250_port *);
+};
+
 /**
  * struct exar8250_board - board information
  * @num_ports: number of serial ports
@@ -196,7 +201,7 @@ static void setup_gpio(struct pci_dev *pcidev, u8 __iomem *p)
 }
 
 static void *
-xr17v35x_register_gpio(struct pci_dev *pcidev)
+__xr17v35x_register_gpio(struct pci_dev *pcidev)
 {
 	struct platform_device *pdev;
 
@@ -215,17 +220,36 @@ xr17v35x_register_gpio(struct pci_dev *pcidev)
 	return pdev;
 }
 
+static int xr17v35x_register_gpio(struct pci_dev *pcidev,
+				  struct uart_8250_port *port)
+{
+	if (pcidev->vendor == PCI_VENDOR_ID_EXAR)
+		port->port.private_data =
+			__xr17v35x_register_gpio(pcidev);
+
+	return 0;
+}
+
+static const struct exar8250_platform exar8250_default_platform = {
+	.register_gpio = xr17v35x_register_gpio,
+};
+
 static int
 pci_xr17v35x_setup(struct exar8250 *priv, struct pci_dev *pcidev,
 		   struct uart_8250_port *port, int idx)
 {
 	const struct exar8250_board *board = priv->board;
+	const struct exar8250_platform *platform;
 	unsigned int offset = idx * 0x400;
 	unsigned int baud = 7812500;
 	u8 __iomem *p;
 	int ret;
 
+	platform = &exar8250_default_platform;
+
 	port->port.uartclk = baud * 16;
+	port->port.rs485_config = platform->rs485_config;
+
 	/*
 	 * Setup the uart clock for the devices on expansion slot to
 	 * half the clock speed of the main chip (which is 125MHz)
@@ -248,12 +272,10 @@ pci_xr17v35x_setup(struct exar8250 *priv, struct pci_dev *pcidev,
 		/* Setup Multipurpose Input/Output pins. */
 		setup_gpio(pcidev, p);
 
-		if (pcidev->vendor == PCI_VENDOR_ID_EXAR)
-			port->port.private_data =
-				xr17v35x_register_gpio(pcidev);
+		ret = platform->register_gpio(pcidev, port);
 	}
 
-	return 0;
+	return ret;
 }
 
 static void pci_xr17v35x_exit(struct pci_dev *pcidev)
-- 
2.12.3

^ permalink raw reply related

* [PATCH v5 07/11] gpio-exar/8250-exar: Rearrange gpiochip parenthood
From: Jan Kiszka @ 2017-06-02  7:28 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Linus Walleij, Alexandre Courbot
  Cc: Linux Kernel Mailing List, linux-serial, linux-gpio,
	Sudip Mukherjee, Andy Shevchenko, Sascha Weisenberger
In-Reply-To: <cover.1496388533.git.jan.kiszka@siemens.com>

Set the parent of the exar gpiochip to its platform device, like other
gpiochips are doing it. In order to keep the relationship discoverable
for ACPI systems, set the platform device companion to the PCI device.

Signed-off-by: Jan Kiszka <jan.kiszka@siemens.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
Acked-by: Linus Walleij <linus.walleij@linaro.org>
---
 drivers/gpio/gpio-exar.c            | 2 +-
 drivers/tty/serial/8250/8250_exar.c | 2 ++
 2 files changed, 3 insertions(+), 1 deletion(-)

diff --git a/drivers/gpio/gpio-exar.c b/drivers/gpio/gpio-exar.c
index f3585a184f39..1a629831d45b 100644
--- a/drivers/gpio/gpio-exar.c
+++ b/drivers/gpio/gpio-exar.c
@@ -142,7 +142,7 @@ static int gpio_exar_probe(struct platform_device *pdev)
 
 	sprintf(exar_gpio->name, "exar_gpio%d", index);
 	exar_gpio->gpio_chip.label = exar_gpio->name;
-	exar_gpio->gpio_chip.parent = &pcidev->dev;
+	exar_gpio->gpio_chip.parent = &pdev->dev;
 	exar_gpio->gpio_chip.direction_output = exar_direction_output;
 	exar_gpio->gpio_chip.direction_input = exar_direction_input;
 	exar_gpio->gpio_chip.get_direction = exar_get_direction;
diff --git a/drivers/tty/serial/8250/8250_exar.c b/drivers/tty/serial/8250/8250_exar.c
index 0f4b236d7e68..ee4b142f3ed0 100644
--- a/drivers/tty/serial/8250/8250_exar.c
+++ b/drivers/tty/serial/8250/8250_exar.c
@@ -9,6 +9,7 @@
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License.
  */
+#include <linux/acpi.h>
 #include <linux/io.h>
 #include <linux/kernel.h>
 #include <linux/module.h>
@@ -204,6 +205,7 @@ xr17v35x_register_gpio(struct pci_dev *pcidev)
 		return NULL;
 
 	pdev->dev.parent = &pcidev->dev;
+	ACPI_COMPANION_SET(&pdev->dev, ACPI_COMPANION(&pcidev->dev));
 
 	if (platform_device_add(pdev) < 0) {
 		platform_device_put(pdev);
-- 
2.12.3

^ permalink raw reply related

* [PATCH v5 06/11] gpio: exar: Fix reading of directions and values
From: Jan Kiszka @ 2017-06-02  7:28 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Linus Walleij, Alexandre Courbot
  Cc: Linux Kernel Mailing List, linux-serial, linux-gpio,
	Sudip Mukherjee, Andy Shevchenko, Sascha Weisenberger
In-Reply-To: <cover.1496388533.git.jan.kiszka@siemens.com>

First, the logic for translating a register bit to the return code of
exar_get_direction and exar_get_value were wrong. And second, there was
a flip regarding the register bank in exar_get_direction.

Signed-off-by: Jan Kiszka <jan.kiszka@siemens.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
Acked-by: Linus Walleij <linus.walleij@linaro.org>
---
 drivers/gpio/gpio-exar.c | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/drivers/gpio/gpio-exar.c b/drivers/gpio/gpio-exar.c
index b29890b143ce..f3585a184f39 100644
--- a/drivers/gpio/gpio-exar.c
+++ b/drivers/gpio/gpio-exar.c
@@ -68,7 +68,7 @@ static int exar_get(struct gpio_chip *chip, unsigned int reg)
 	value = readb(exar_gpio->regs + reg);
 	mutex_unlock(&exar_gpio->lock);
 
-	return !!value;
+	return value;
 }
 
 static int exar_get_direction(struct gpio_chip *chip, unsigned int offset)
@@ -78,7 +78,7 @@ static int exar_get_direction(struct gpio_chip *chip, unsigned int offset)
 	int val;
 
 	addr = bank ? EXAR_OFFSET_MPIOSEL_HI : EXAR_OFFSET_MPIOSEL_LO;
-	val = exar_get(chip, addr) >> (offset % 8);
+	val = exar_get(chip, addr) & BIT(offset % 8);
 
 	return !!val;
 }
@@ -89,8 +89,8 @@ static int exar_get_value(struct gpio_chip *chip, unsigned int offset)
 	unsigned int addr;
 	int val;
 
-	addr = bank ? EXAR_OFFSET_MPIOLVL_LO : EXAR_OFFSET_MPIOLVL_HI;
-	val = exar_get(chip, addr) >> (offset % 8);
+	addr = bank ? EXAR_OFFSET_MPIOLVL_HI : EXAR_OFFSET_MPIOLVL_LO;
+	val = exar_get(chip, addr) & BIT(offset % 8);
 
 	return !!val;
 }
-- 
2.12.3

^ permalink raw reply related

* [PATCH v5 05/11] gpio: exar: Fix iomap request
From: Jan Kiszka @ 2017-06-02  7:28 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Linus Walleij, Alexandre Courbot
  Cc: Linux Kernel Mailing List, linux-serial, linux-gpio,
	Sudip Mukherjee, Andy Shevchenko, Sascha Weisenberger
In-Reply-To: <cover.1496388533.git.jan.kiszka@siemens.com>

The UART driver already maps the resource for us. Trying to do this here
only fails and leaves us with a non-working device.

Signed-off-by: Jan Kiszka <jan.kiszka@siemens.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
Acked-by: Linus Walleij <linus.walleij@linaro.org>
---
 drivers/gpio/gpio-exar.c | 10 +++-------
 1 file changed, 3 insertions(+), 7 deletions(-)

diff --git a/drivers/gpio/gpio-exar.c b/drivers/gpio/gpio-exar.c
index 65126fa1e512..b29890b143ce 100644
--- a/drivers/gpio/gpio-exar.c
+++ b/drivers/gpio/gpio-exar.c
@@ -125,14 +125,10 @@ static int gpio_exar_probe(struct platform_device *pdev)
 	int index, ret;
 
 	/*
-	 * Map the pci device to get the register addresses.
-	 * We will need to read and write those registers to control
-	 * the GPIO pins.
-	 * Using managed functions will save us from unmaping on exit.
-	 * As the device is enabled using managed functions by the
-	 * UART driver we can also use managed functions here.
+	 * The UART driver must have mapped region 0 prior to registering this
+	 * device - use it.
 	 */
-	p = pcim_iomap(pcidev, 0, 0);
+	p = pcim_iomap_table(pcidev)[0];
 	if (!p)
 		return -ENOMEM;
 
-- 
2.12.3

^ permalink raw reply related

* [PATCH v5 04/11] gpio: exar: Allocate resources on behalf of the platform device
From: Jan Kiszka @ 2017-06-02  7:28 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Linus Walleij, Alexandre Courbot
  Cc: Linux Kernel Mailing List, linux-serial, linux-gpio,
	Sudip Mukherjee, Andy Shevchenko, Sascha Weisenberger
In-Reply-To: <cover.1496388533.git.jan.kiszka@siemens.com>

Do not allocate resources on behalf of the parent device but on our own.
Otherwise, cleanup does not properly work if gpio-exar is removed but
not the parent device.

Signed-off-by: Jan Kiszka <jan.kiszka@siemens.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
Acked-by: Linus Walleij <linus.walleij@linaro.org>
---
 drivers/gpio/gpio-exar.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/gpio/gpio-exar.c b/drivers/gpio/gpio-exar.c
index da4550bb9939..65126fa1e512 100644
--- a/drivers/gpio/gpio-exar.c
+++ b/drivers/gpio/gpio-exar.c
@@ -136,7 +136,7 @@ static int gpio_exar_probe(struct platform_device *pdev)
 	if (!p)
 		return -ENOMEM;
 
-	exar_gpio = devm_kzalloc(&pcidev->dev, sizeof(*exar_gpio), GFP_KERNEL);
+	exar_gpio = devm_kzalloc(&pdev->dev, sizeof(*exar_gpio), GFP_KERNEL);
 	if (!exar_gpio)
 		return -ENOMEM;
 
@@ -157,7 +157,7 @@ static int gpio_exar_probe(struct platform_device *pdev)
 	exar_gpio->regs = p;
 	exar_gpio->index = index;
 
-	ret = devm_gpiochip_add_data(&pcidev->dev,
+	ret = devm_gpiochip_add_data(&pdev->dev,
 				     &exar_gpio->gpio_chip, exar_gpio);
 	if (ret)
 		goto err_destroy;
-- 
2.12.3

^ permalink raw reply related

* [PATCH v5 03/11] gpio-exar/8250-exar: Fix passing in of parent PCI device
From: Jan Kiszka @ 2017-06-02  7:28 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Linus Walleij, Alexandre Courbot
  Cc: Linux Kernel Mailing List, linux-serial, linux-gpio,
	Sudip Mukherjee, Andy Shevchenko, Sascha Weisenberger
In-Reply-To: <cover.1496388533.git.jan.kiszka@siemens.com>

This fixes reloading of the GPIO driver for the same platform device
instance as created by the exar UART driver: First of all, the driver
sets drvdata to its own value during probing and does not restore the
original value on exit. But this won't help anyway as the core clears
drvdata after the driver left.

Set the platform device parent instead.

Signed-off-by: Jan Kiszka <jan.kiszka@siemens.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
Acked-by: Linus Walleij <linus.walleij@linaro.org>
---
 drivers/gpio/gpio-exar.c            | 2 +-
 drivers/tty/serial/8250/8250_exar.c | 3 ++-
 2 files changed, 3 insertions(+), 2 deletions(-)

diff --git a/drivers/gpio/gpio-exar.c b/drivers/gpio/gpio-exar.c
index 006a9a67c2a4..da4550bb9939 100644
--- a/drivers/gpio/gpio-exar.c
+++ b/drivers/gpio/gpio-exar.c
@@ -119,7 +119,7 @@ static int exar_direction_input(struct gpio_chip *chip, unsigned int offset)
 
 static int gpio_exar_probe(struct platform_device *pdev)
 {
-	struct pci_dev *pcidev = platform_get_drvdata(pdev);
+	struct pci_dev *pcidev = to_pci_dev(pdev->dev.parent);
 	struct exar_gpio_chip *exar_gpio;
 	void __iomem *p;
 	int index, ret;
diff --git a/drivers/tty/serial/8250/8250_exar.c b/drivers/tty/serial/8250/8250_exar.c
index c29c7e675890..0f4b236d7e68 100644
--- a/drivers/tty/serial/8250/8250_exar.c
+++ b/drivers/tty/serial/8250/8250_exar.c
@@ -203,7 +203,8 @@ xr17v35x_register_gpio(struct pci_dev *pcidev)
 	if (!pdev)
 		return NULL;
 
-	platform_set_drvdata(pdev, pcidev);
+	pdev->dev.parent = &pcidev->dev;
+
 	if (platform_device_add(pdev) < 0) {
 		platform_device_put(pdev);
 		return NULL;
-- 
2.12.3

^ permalink raw reply related

* [PATCH v5 02/11] gpio-exar/8250-exar: Do not even instantiate a GPIO device for Commtech cards
From: Jan Kiszka @ 2017-06-02  7:28 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Linus Walleij, Alexandre Courbot
  Cc: Linux Kernel Mailing List, linux-serial, linux-gpio,
	Sudip Mukherjee, Andy Shevchenko, Sascha Weisenberger
In-Reply-To: <cover.1496388533.git.jan.kiszka@siemens.com>

Commtech adapters need the MPIOs for internal purposes, and the
gpio-exar driver already refused to pick them up. But there is actually
no point in even creating the underlying platform device.

Signed-off-by: Jan Kiszka <jan.kiszka@siemens.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
Acked-by: Linus Walleij <linus.walleij@linaro.org>
---
 drivers/gpio/gpio-exar.c            | 3 ---
 drivers/tty/serial/8250/8250_exar.c | 4 +++-
 2 files changed, 3 insertions(+), 4 deletions(-)

diff --git a/drivers/gpio/gpio-exar.c b/drivers/gpio/gpio-exar.c
index 081076771217..006a9a67c2a4 100644
--- a/drivers/gpio/gpio-exar.c
+++ b/drivers/gpio/gpio-exar.c
@@ -124,9 +124,6 @@ static int gpio_exar_probe(struct platform_device *pdev)
 	void __iomem *p;
 	int index, ret;
 
-	if (pcidev->vendor != PCI_VENDOR_ID_EXAR)
-		return -ENODEV;
-
 	/*
 	 * Map the pci device to get the register addresses.
 	 * We will need to read and write those registers to control
diff --git a/drivers/tty/serial/8250/8250_exar.c b/drivers/tty/serial/8250/8250_exar.c
index 8984e8b2d524..c29c7e675890 100644
--- a/drivers/tty/serial/8250/8250_exar.c
+++ b/drivers/tty/serial/8250/8250_exar.c
@@ -245,7 +245,9 @@ pci_xr17v35x_setup(struct exar8250 *priv, struct pci_dev *pcidev,
 		/* Setup Multipurpose Input/Output pins. */
 		setup_gpio(pcidev, p);
 
-		port->port.private_data = xr17v35x_register_gpio(pcidev);
+		if (pcidev->vendor == PCI_VENDOR_ID_EXAR)
+			port->port.private_data =
+				xr17v35x_register_gpio(pcidev);
 	}
 
 	return 0;
-- 
2.12.3

^ permalink raw reply related

* [PATCH v5 01/11] serial: exar: Leave MPIOs as output for Commtech adapters
From: Jan Kiszka @ 2017-06-02  7:28 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Linus Walleij, Alexandre Courbot
  Cc: Linux Kernel Mailing List, linux-serial, linux-gpio,
	Sudip Mukherjee, Andy Shevchenko, Sascha Weisenberger
In-Reply-To: <cover.1496388533.git.jan.kiszka@siemens.com>

Commtech adapters apparently need the original setting as outputs, see
https://marc.info/?l=linux-gpio&m=149557425201323&w=2. Account for that.

Fixes: 7dea8165f1d6 ("serial: exar: Preconfigure xr17v35x MPIOs as output")
Signed-off-by: Jan Kiszka <jan.kiszka@siemens.com>
Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
---
 drivers/tty/serial/8250/8250_exar.c | 15 +++++++++++----
 1 file changed, 11 insertions(+), 4 deletions(-)

diff --git a/drivers/tty/serial/8250/8250_exar.c b/drivers/tty/serial/8250/8250_exar.c
index b4fa585156c7..8984e8b2d524 100644
--- a/drivers/tty/serial/8250/8250_exar.c
+++ b/drivers/tty/serial/8250/8250_exar.c
@@ -171,19 +171,26 @@ pci_xr17c154_setup(struct exar8250 *priv, struct pci_dev *pcidev,
 	return default_setup(priv, pcidev, idx, offset, port);
 }
 
-static void setup_gpio(u8 __iomem *p)
+static void setup_gpio(struct pci_dev *pcidev, u8 __iomem *p)
 {
+	/*
+	 * The Commtech adapters required the MPIOs to be driven low. The Exar
+	 * devices will export them as GPIOs, so we pre-configure them safely
+	 * as inputs.
+	 */
+	u8 dir = pcidev->vendor == PCI_VENDOR_ID_EXAR ? 0xff : 0x00;
+
 	writeb(0x00, p + UART_EXAR_MPIOINT_7_0);
 	writeb(0x00, p + UART_EXAR_MPIOLVL_7_0);
 	writeb(0x00, p + UART_EXAR_MPIO3T_7_0);
 	writeb(0x00, p + UART_EXAR_MPIOINV_7_0);
-	writeb(0xff, p + UART_EXAR_MPIOSEL_7_0);
+	writeb(dir,  p + UART_EXAR_MPIOSEL_7_0);
 	writeb(0x00, p + UART_EXAR_MPIOOD_7_0);
 	writeb(0x00, p + UART_EXAR_MPIOINT_15_8);
 	writeb(0x00, p + UART_EXAR_MPIOLVL_15_8);
 	writeb(0x00, p + UART_EXAR_MPIO3T_15_8);
 	writeb(0x00, p + UART_EXAR_MPIOINV_15_8);
-	writeb(0xff, p + UART_EXAR_MPIOSEL_15_8);
+	writeb(dir,  p + UART_EXAR_MPIOSEL_15_8);
 	writeb(0x00, p + UART_EXAR_MPIOOD_15_8);
 }
 
@@ -236,7 +243,7 @@ pci_xr17v35x_setup(struct exar8250 *priv, struct pci_dev *pcidev,
 
 	if (idx == 0) {
 		/* Setup Multipurpose Input/Output pins. */
-		setup_gpio(p);
+		setup_gpio(pcidev, p);
 
 		port->port.private_data = xr17v35x_register_gpio(pcidev);
 	}
-- 
2.12.3

^ permalink raw reply related

* [PATCH v5 00/11] serial/gpio: exar: Fixes and support for IOT2000
From: Jan Kiszka @ 2017-06-02  7:28 UTC (permalink / raw)
  To: Greg Kroah-Hartman, Linus Walleij, Alexandre Courbot
  Cc: Linux Kernel Mailing List, linux-serial, linux-gpio,
	Sudip Mukherjee, Andy Shevchenko, Sascha Weisenberger

This makes the gpio-exar driver usable, which was prevented by a number
of fatal bugs, and adds support for the SIMATIC IOT2040 to the 8250-exar
driver and, indirectly, to gpio-exar as well. It's a cross-subsystem
series, so I'm also cross-posting to the serial and gpio lists.

Changes in v5:
 - factor out exar8250_platform hook setup as separate patch
 - pass properties to __xr17v35x_register_gpio
 - constant property support for platform_device_add_properties

Jan

Jan Kiszka (11):
  serial: exar: Leave MPIOs as output for Commtech adapters
  gpio-exar/8250-exar: Do not even instantiate a GPIO device for
    Commtech cards
  gpio-exar/8250-exar: Fix passing in of parent PCI device
  gpio: exar: Allocate resources on behalf of the platform device
  gpio: exar: Fix iomap request
  gpio: exar: Fix reading of directions and values
  gpio-exar/8250-exar: Rearrange gpiochip parenthood
  serial: exar: Factor out platform hooks
  platform: Accept const properties
  gpio-exar/8250-exar: Make set of exported GPIOs configurable
  serial: exar: Add support for IOT2040 device

 drivers/base/platform.c             |   2 +-
 drivers/gpio/gpio-exar.c            |  75 +++++++-------
 drivers/tty/serial/8250/8250_exar.c | 188 ++++++++++++++++++++++++++++++++++--
 include/linux/platform_device.h     |   2 +-
 4 files changed, 218 insertions(+), 49 deletions(-)

-- 
2.12.3

^ permalink raw reply

* Re: [GIT PULL] TTY/Serial driver fixes for 4.11-rc4
From: Greg KH @ 2017-06-02  0:06 UTC (permalink / raw)
  To: Dmitry Vyukov
  Cc: Alan Cox, Vegard Nossum, Linus Torvalds, Jiri Slaby,
	Andrew Morton, LKML, linux-serial
In-Reply-To: <CACT4Y+YSOD26=AAMgw2D-A_Nvk5On71qLY40LhXXUiZpp2-h+Q@mail.gmail.com>

On Thu, Jun 01, 2017 at 02:06:08PM +0200, Dmitry Vyukov wrote:
> On Wed, May 31, 2017 at 5:04 PM, Alan Cox <gnomes@lxorguk.ukuu.org.uk> wrote:
> > On Wed, 31 May 2017 20:16:12 +0900
> > Greg KH <gregkh@linuxfoundation.org> wrote:
> >
> >> On Wed, May 31, 2017 at 10:39:23AM +0200, Dmitry Vyukov wrote:
> >> > On Tue, May 30, 2017 at 2:09 PM, Alan Cox <gnomes@lxorguk.ukuu.org.uk> wrote:
> >> > >> >> I'll think about possible solutions, but I have no prior experience
> >> > >> >> with the tty code. In the meantime syzkaller also hit a couple of
> >> > >> >> other fun tty/pty bugs including a write/ioctl race that results in
> >> > >> >> buffer overflow :-/
> >> > >
> >> > > There are several of those, including some of that have been documented
> >> > > for years but nobody ever volunteered to fix - in particular all the
> >> > > interfaces that push characters to the tty other than via the normal
> >> > > interrupt receive path are dodgy (console selection in particular)
> >> > >
> >> > > The original tty model btw was that setting the ldisc to n_tty cannot
> >> > > fail, and the structure allocated was smaller than a page size so was
> >> > > safe.
> >> > >
> >> > > The simple way to fix it is to restore that behaviour by adding a 'null'
> >> > > ldisc that we can fail to instead of N_TTY since the N_TTY failback path
> >> > > is long broken.
> >> >
> >> > Greg, what do you think about this patch? Are you ready to accept
> >> > something like this?
> >> > Definitely shorter than changing all drivers.
> >>
> >> Yes, it looks reasonable to me.
> >
> >
> >
> > Ok try this
> 
> 
> I've applied the patch and run syzkaller with it. I don't see kernel
> panics in tty_ldisc_restore any more. Also don't see any new
> tty-related crashes.
> 
> Greg, will you take it from here?

I can if Alan sends it to me in a form I can apply it in (i.e. it has a
siged-off-by line...)

thanks,

greg k-h

^ permalink raw reply

* Re: [GIT PULL] TTY/Serial driver fixes for 4.11-rc4
From: Dmitry Vyukov @ 2017-06-01 12:06 UTC (permalink / raw)
  To: Alan Cox
  Cc: Greg KH, Vegard Nossum, Linus Torvalds, Jiri Slaby, Andrew Morton,
	LKML, linux-serial
In-Reply-To: <20170531160420.3b173a4a@alans-desktop>

On Wed, May 31, 2017 at 5:04 PM, Alan Cox <gnomes@lxorguk.ukuu.org.uk> wrote:
> On Wed, 31 May 2017 20:16:12 +0900
> Greg KH <gregkh@linuxfoundation.org> wrote:
>
>> On Wed, May 31, 2017 at 10:39:23AM +0200, Dmitry Vyukov wrote:
>> > On Tue, May 30, 2017 at 2:09 PM, Alan Cox <gnomes@lxorguk.ukuu.org.uk> wrote:
>> > >> >> I'll think about possible solutions, but I have no prior experience
>> > >> >> with the tty code. In the meantime syzkaller also hit a couple of
>> > >> >> other fun tty/pty bugs including a write/ioctl race that results in
>> > >> >> buffer overflow :-/
>> > >
>> > > There are several of those, including some of that have been documented
>> > > for years but nobody ever volunteered to fix - in particular all the
>> > > interfaces that push characters to the tty other than via the normal
>> > > interrupt receive path are dodgy (console selection in particular)
>> > >
>> > > The original tty model btw was that setting the ldisc to n_tty cannot
>> > > fail, and the structure allocated was smaller than a page size so was
>> > > safe.
>> > >
>> > > The simple way to fix it is to restore that behaviour by adding a 'null'
>> > > ldisc that we can fail to instead of N_TTY since the N_TTY failback path
>> > > is long broken.
>> >
>> > Greg, what do you think about this patch? Are you ready to accept
>> > something like this?
>> > Definitely shorter than changing all drivers.
>>
>> Yes, it looks reasonable to me.
>
>
>
> Ok try this


I've applied the patch and run syzkaller with it. I don't see kernel
panics in tty_ldisc_restore any more. Also don't see any new
tty-related crashes.

Greg, will you take it from here?


> commit f6db8de7eca11cfeafa92f2ec866fa75425c5f38
> Author: Alan Cox <alan@llwyncelyn.cymru>
> Date:   Tue May 30 12:59:45 2017 +0100
>
>     tty: handle the case where we cannot restore a line discipline
>
>     Historically the N_TTY driver could never fail but this has become broken over
>     time. Rather than trying to rewrite half the ldisc layer to fix the breakage
>     introduce a second level of fallback with an N_NULL ldisc which cannot fail,
>     and thus restore the guarantees required by the ldisc layer.
>
>     We still try and fail to N_TTY first. It's much more useful to find yourself
>     back in your old ldisc (first attempt) or in N_TTY (second attempt), and while
>     I'm not aware of any code out there that makes those assumptions it's good to
>     drive(r) defensively.
>
> diff --git a/drivers/tty/Makefile b/drivers/tty/Makefile
> index f02becd..8689279 100644
> --- a/drivers/tty/Makefile
> +++ b/drivers/tty/Makefile
> @@ -1,6 +1,7 @@
>  obj-$(CONFIG_TTY)              += tty_io.o n_tty.o tty_ioctl.o tty_ldisc.o \
>                                    tty_buffer.o tty_port.o tty_mutex.o \
> -                                  tty_ldsem.o tty_baudrate.o tty_jobctrl.o
> +                                  tty_ldsem.o tty_baudrate.o tty_jobctrl.o \
> +                                  n_null.o
>  obj-$(CONFIG_LEGACY_PTYS)      += pty.o
>  obj-$(CONFIG_UNIX98_PTYS)      += pty.o
>  obj-$(CONFIG_AUDIT)            += tty_audit.o
> diff --git a/drivers/tty/n_null.c b/drivers/tty/n_null.c
> new file mode 100644
> index 0000000..d63261c
> --- /dev/null
> +++ b/drivers/tty/n_null.c
> @@ -0,0 +1,80 @@
> +#include <linux/types.h>
> +#include <linux/errno.h>
> +#include <linux/tty.h>
> +#include <linux/module.h>
> +
> +/*
> + *  n_null.c - Null line discipline used in the failure path
> + *
> + *  Copyright (C) Intel 2017
> + *
> + * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
> + *
> + *  This program is free software; you can redistribute it and/or modify
> + *  it under the terms of the GNU General Public License version 2
> + *  as published by the Free Software Foundation.
> + *
> + *  This program is distributed in the hope that it will be useful,
> + *  but WITHOUT ANY WARRANTY; without even the implied warranty of
> + *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
> + *  GNU General Public License for more details.
> + *
> + * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
> + */
> +
> +static int n_null_open(struct tty_struct *tty)
> +{
> +       return 0;
> +}
> +
> +static void n_null_close(struct tty_struct *tty)
> +{
> +}
> +
> +static ssize_t n_null_read(struct tty_struct *tty, struct file *file,
> +                          unsigned char __user * buf, size_t nr)
> +{
> +       return -EOPNOTSUPP;
> +}
> +
> +static ssize_t n_null_write(struct tty_struct *tty, struct file *file,
> +                           const unsigned char *buf, size_t nr)
> +{
> +       return -EOPNOTSUPP;
> +}
> +
> +static void n_null_receivebuf(struct tty_struct *tty,
> +                                const unsigned char *cp, char *fp,
> +                                int cnt)
> +{
> +}
> +
> +static struct tty_ldisc_ops null_ldisc = {
> +       .owner          =       THIS_MODULE,
> +       .magic          =       TTY_LDISC_MAGIC,
> +       .name           =       "n_null",
> +       .open           =       n_null_open,
> +       .close          =       n_null_close,
> +       .read           =       n_null_read,
> +       .write          =       n_null_write,
> +       .receive_buf    =       n_null_receivebuf
> +};
> +
> +static int __init n_null_init(void)
> +{
> +       BUG_ON(tty_register_ldisc(N_NULL, &null_ldisc));
> +       return 0;
> +}
> +
> +static void __exit n_null_exit(void)
> +{
> +       tty_unregister_ldisc(N_NULL);
> +}
> +
> +module_init(n_null_init);
> +module_exit(n_null_exit);
> +
> +MODULE_LICENSE("GPL");
> +MODULE_AUTHOR("Alan Cox");
> +MODULE_ALIAS_LDISC(N_NULL);
> +MODULE_DESCRIPTION("Null ldisc driver");
> diff --git a/drivers/tty/tty_ldisc.c b/drivers/tty/tty_ldisc.c
> index f6ffe28..2fe216b 100644
> --- a/drivers/tty/tty_ldisc.c
> +++ b/drivers/tty/tty_ldisc.c
> @@ -492,6 +492,29 @@ static void tty_ldisc_close(struct tty_struct *tty, struct tty_ldisc *ld)
>  }
>
>  /**
> + *     tty_ldisc_failto        -       helper for ldisc failback
> + *     @tty: tty to open the ldisc on
> + *     @ld: ldisc we are trying to fail back to
> + *
> + *     Helper to try and recover a tty when switching back to the old
> + *     ldisc fails and we need something attached.
> + */
> +
> +static int tty_ldisc_failto(struct tty_struct *tty, int ld)
> +{
> +       struct tty_ldisc *disc = tty_ldisc_get(tty, ld);
> +       int r;
> +
> +       if (IS_ERR(disc))
> +               return PTR_ERR(disc);
> +       tty->ldisc = disc;
> +       tty_set_termios_ldisc(tty, ld);
> +       if ((r = tty_ldisc_open(tty, disc)) < 0)
> +               tty_ldisc_put(disc);
> +       return r;
> +}
> +
> +/**
>   *     tty_ldisc_restore       -       helper for tty ldisc change
>   *     @tty: tty to recover
>   *     @old: previous ldisc
> @@ -502,9 +525,6 @@ static void tty_ldisc_close(struct tty_struct *tty, struct tty_ldisc *ld)
>
>  static void tty_ldisc_restore(struct tty_struct *tty, struct tty_ldisc *old)
>  {
> -       struct tty_ldisc *new_ldisc;
> -       int r;
> -
>         /* There is an outstanding reference here so this is safe */
>         old = tty_ldisc_get(tty, old->ops->num);
>         WARN_ON(IS_ERR(old));
> @@ -512,17 +532,13 @@ static void tty_ldisc_restore(struct tty_struct *tty, struct tty_ldisc *old)
>         tty_set_termios_ldisc(tty, old->ops->num);
>         if (tty_ldisc_open(tty, old) < 0) {
>                 tty_ldisc_put(old);
> -               /* This driver is always present */
> -               new_ldisc = tty_ldisc_get(tty, N_TTY);
> -               if (IS_ERR(new_ldisc))
> -                       panic("n_tty: get");
> -               tty->ldisc = new_ldisc;
> -               tty_set_termios_ldisc(tty, N_TTY);
> -               r = tty_ldisc_open(tty, new_ldisc);
> -               if (r < 0)
> -                       panic("Couldn't open N_TTY ldisc for "
> -                             "%s --- error %d.",
> -                             tty_name(tty), r);
> +               /* The traditional behaviour is to fall back to N_TTY, we
> +                  want to avoid falling back to N_NULL unless we have no
> +                  choice to avoid the risk of breaking anything */
> +               if (tty_ldisc_failto(tty, N_TTY) < 0 &&
> +                   tty_ldisc_failto(tty, N_NULL) < 0)
> +                       panic("Couldn't open N_NULL ldisc for %s.",
> +                             tty_name(tty));
>         }
>  }
>
> diff --git a/include/uapi/linux/tty.h b/include/uapi/linux/tty.h
> index e7855df..cf14553 100644
> --- a/include/uapi/linux/tty.h
> +++ b/include/uapi/linux/tty.h
> @@ -36,5 +36,6 @@
>  #define N_TRACEROUTER  24      /* Trace data routing for MIPI P1149.7 */
>  #define N_NCI          25      /* NFC NCI UART */
>  #define N_SPEAKUP      26      /* Speakup communication with synths */
> +#define N_NULL         27      /* Null ldisc used for error handling */
>
>  #endif /* _UAPI_LINUX_TTY_H */

^ permalink raw reply

* Re: [PATCH v9 3/3] printk: fix double printing with earlycon
From: Petr Mladek @ 2017-06-01 12:03 UTC (permalink / raw)
  To: Aleksey Makarov
  Cc: Sergey Senozhatsky, Sabrina Dubroca, linux-serial, linux-kernel,
	Sudeep Holla, Greg Kroah-Hartman, Peter Hurley, Jiri Slaby,
	Robin Murphy, Steven Rostedt, Nair, Jayachandran,
	Sergey Senozhatsky
In-Reply-To: <4e679bec-4804-9791-fc2b-0e96ad67d511@linaro.org>

On Fri 2017-05-26 12:37:12, Aleksey Makarov wrote:
> 
> 
> On 05/18/2017 06:49 PM, Petr Mladek wrote:
> >On Sun 2017-05-14 23:37:50, Aleksey Makarov wrote:
> >>
> >>
> >>On 05/12/2017 03:57 PM, Petr Mladek wrote:
> >>>On Thu 2017-05-11 17:41:58, Sergey Senozhatsky wrote:
> I meant that it is difficult to fix the bug that only one line
> (first matched) of registered console device receives kernel logs.
> That is because of 'index' field of struct console can refer to only one
> tty line.

I think that bigger problem is that con->match() functions have
side effects and we could not try matching all consoles
mentioned in console_cmdline. Otherwise, we would be able
to enable all mentioned ttyS* drivers that are listed.


> - The reason why logs appear twice is that earlycon is not
> deregistered after non-early consoles are available.

OK

> - Earlycon is not deregistered because in some cases
> flag CON_CONSDEV is not set for any of the new non-early
> consoles.

This is one explanation. Another reason might be that
an early console is added into console_cmdline by mistake.
By other words, if early consoles are not mentioned in
console_cmdline we could not mismatch them with the normal
console. See below for more on this idea.


> - That flag is not set when two entries of console_cmdline
> array refer to the same console.  We match the first entry,
> it is not preferred and the flag CON_CONSDEV is set only
> for preferred console.
> 
> - So I changed the order of array walk so that if there
> are two entries referring to the same console, last one is matched.
> If we specify a console as prefered (last entry in command line)
> that means that we expect a driver will eventually register
> its console and for that driver we will match the last
> entry and the earlycon will be deregistered.

This still handles the problem only for the preferred (last entry
in command line) console. In theory, there might be more consoles
listed twice.


> - The subtle question is why we deregister earlycon only
> when CON_CONSDEV is set (i. e. only for preferred console).
> That check for CON_CONSDEV was initially introduced in
> 
> d37bf60de0b4 console: console handover to preferred console
> 
> and then refactored in
> 
> 4d09161196c9 printk: Enable the use of more than one CON_BOOT (early console)
> 8259cf434202 printk: Ensure that "console enabled" messages are printed on the console
> 
> The reason is that some consoles can be registered later or earlier
> and if we deregister earlycon when the first non-early console
> is registered, we can lose some lines of log.  To prevent that
> we specify the console *which is being watched* as preferred
> (the last console in the console_cmdline array) and
> deregister earlycon only when kernel registers its driver.

Good to know. Thanks a lot for the archaeology.


> >BTW: I wonder if we really need to add consoles defined by ACPI SPCR
> >table into the console_cmdline array.
> 
> The console_cmdline array is the place where we add descriptions
> of consoles that should receive log output. ACPI SPCR specifies exactly
> that information, and I believe it should go to that array.

Are consoles defined by earlycon= command line parameter
added to console_cmdline? I do not see this anywhere in
the following functions:

  + param_setup_earlycon()
  + setup_earlycon()
  + register_earlycon()
  + early_init_dt_scan_chosen_stdout()
  + of_setup_earlycon()

IMHO, the main question is whether the console defined by
ACPI SPCR is early or normal one. IMHO, it is early console
and it should be handled the same way as the other early
consoles.


> >I am even more curious when
> >seeing the following code in drivers/acpi/spcr.c:
> >
> >int __init parse_spcr(bool earlycon) { [...] if (earlycon)
> >setup_earlycon(opts);

setup_early() calls register_earlycon() when the console is
found in __earlycon_table. Then it calls register_console().

I guess that the console is enabled here because we do not
have preferred cosole when this is called. Therefore it is
enabled by the following code:

	/*
	 *	See if we want to use this console driver. If we
	 *	didn't select a console we take the first one
	 *	that registers here.
	 */
	if (!has_preferred) {
		if (newcon->index < 0)
			newcon->index = 0;
		if (newcon->setup == NULL ||
		    newcon->setup(newcon, NULL) == 0) {
			newcon->flags |= CON_ENABLED;
			if (newcon->device) {
				newcon->flags |= CON_CONSDEV;
				has_preferred = true;
			}

Note that it gets enabled without being listed in console_cmdline.

> >err = add_preferred_console(uart, 0, opts + strlen(uart) + 1); }

Then it is added to the console_cmdline after being enabled.
Let's discuss why below.

> >Do we really need to call add_preferred_console() for
> these early consoles?
> 
> Yes we need.

Why exactly?

> When we setup an earlycon, we enable output
> to that console immediately.  Drivers can register its real
> non-early consoles much later so we just add description
> of that consoles to the console_cmdline arraly so that
> when the driver registers a matching driver, earlycon is replaced
> by a regular device.

console_cmdline is used to match the newly registered consoles.
If it matches and newcon->setup() succeeds, the console is enabled.
Why do we need to match the new consoles with the already
registered and enabled one?

Please, note that the early consoles are disabled using
the "console_drivers" list. They do not need to be listed in
"console_cmdline" to be disabled.

Do I miss something?

Best Regards,
Petr

^ permalink raw reply

* [PATCH] Fix serial console on SNI RM400 machines
From: Thomas Bogendoerfer @ 2017-05-31 20:21 UTC (permalink / raw)
  To: gregkh, jslaby, linux-serial, linux-kernel; +Cc: linux

sccnxp driver doesn't get the correct uart clock rate, if CONFIG_HAVE_CLOCK
is disabled. Correct usage of clk API to make it work with/without it.

Fixes: 90efa75f7ab0 (serial: sccnxp: Using CLK API for getting UART clock)

Suggested-by: Russell King - ARM Linux <linux@armlinux.org.uk>
Signed-off-by: Thomas Bogendoerfer <tsbogend@alpha.franken.de>
---
 drivers/tty/serial/sccnxp.c | 15 ++++++++++-----
 1 file changed, 10 insertions(+), 5 deletions(-)

diff --git a/drivers/tty/serial/sccnxp.c b/drivers/tty/serial/sccnxp.c
index fcf803f..cdd2f94 100644
--- a/drivers/tty/serial/sccnxp.c
+++ b/drivers/tty/serial/sccnxp.c
@@ -884,14 +884,19 @@ static int sccnxp_probe(struct platform_device *pdev)
 
 	clk = devm_clk_get(&pdev->dev, NULL);
 	if (IS_ERR(clk)) {
-		if (PTR_ERR(clk) == -EPROBE_DEFER) {
-			ret = -EPROBE_DEFER;
+		ret = PTR_ERR(clk);
+		if (ret == -EPROBE_DEFER)
 			goto err_out;
-		}
+		uartclk = 0;
+	} else {
+		clk_prepare_enable(clk);
+		uartclk = clk_get_rate(clk);
+	}
+
+	if (!uartclk) {
 		dev_notice(&pdev->dev, "Using default clock frequency\n");
 		uartclk = s->chip->freq_std;
-	} else
-		uartclk = clk_get_rate(clk);
+	}
 
 	/* Check input frequency */
 	if ((uartclk < s->chip->freq_min) || (uartclk > s->chip->freq_max)) {
-- 
2.1.4

^ permalink raw reply related

* Re: [PATCH v4 2/9] gpio-exar/8250-exar: Do not even instantiate a GPIO device for Commtech cards
From: Andy Shevchenko @ 2017-05-31 18:02 UTC (permalink / raw)
  To: Jan Kiszka
  Cc: Greg Kroah-Hartman, Linus Walleij, Alexandre Courbot,
	Linux Kernel Mailing List, linux-serial@vger.kernel.org,
	linux-gpio@vger.kernel.org, Sudip Mukherjee, Sascha Weisenberger
In-Reply-To: <6ded8dab-caec-70e3-daf0-16622f89970a@siemens.com>

On Wed, May 31, 2017 at 7:34 PM, Jan Kiszka <jan.kiszka@siemens.com> wrote:
> On 2017-05-30 20:33, Andy Shevchenko wrote:
>> On Tue, May 30, 2017 at 10:01 AM, Jan Kiszka <jan.kiszka@siemens.com> wrote:
>>> Commtech adapters need the MPIOs for internal purposes, and the
>>> gpio-exar driver already refused to pick them up. But there is actually
>>> no point in even creating the underlying platform device.
>>
>> It still feels that partially you may do stuff here, like
>> renaming to
>> __xr17v35x_register_gpio()
>> and creating
>> xr17v35x_register_gpio() wrapper.
>
> Sorry, that remains unrelated to the topic of this patch and would be
> unclean. If you want me to pull those refactorings out of patch 9, I
> need to write a separate patch - no problem.

Okay, I would go with separate patch, if maintainers are okay with
this approach.

-- 
With Best Regards,
Andy Shevchenko

^ permalink raw reply

* Re: [PATCH v4 2/9] gpio-exar/8250-exar: Do not even instantiate a GPIO device for Commtech cards
From: Jan Kiszka @ 2017-05-31 16:34 UTC (permalink / raw)
  To: Andy Shevchenko
  Cc: Greg Kroah-Hartman, Linus Walleij, Alexandre Courbot,
	Linux Kernel Mailing List, linux-serial@vger.kernel.org,
	linux-gpio@vger.kernel.org, Sudip Mukherjee, Sascha Weisenberger
In-Reply-To: <CAHp75Vc0t5t8O5cPaxX_oQJQKsN3OWNFfqnA_K3GW4qpfY+N5Q@mail.gmail.com>

On 2017-05-30 20:33, Andy Shevchenko wrote:
> On Tue, May 30, 2017 at 10:01 AM, Jan Kiszka <jan.kiszka@siemens.com> wrote:
>> Commtech adapters need the MPIOs for internal purposes, and the
>> gpio-exar driver already refused to pick them up. But there is actually
>> no point in even creating the underlying platform device.
> 
> It still feels that partially you may do stuff here, like
> renaming to
> __xr17v35x_register_gpio()
> and creating
> xr17v35x_register_gpio() wrapper.

Sorry, that remains unrelated to the topic of this patch and would be
unclean. If you want me to pull those refactorings out of patch 9, I
need to write a separate patch - no problem.

Jan

-- 
Siemens AG, Corporate Technology, CT RDA ITP SES-DE
Corporate Competence Center Embedded Linux

^ permalink raw reply

* Re: [GIT PULL] TTY/Serial driver fixes for 4.11-rc4
From: Alan Cox @ 2017-05-31 15:04 UTC (permalink / raw)
  To: Greg KH
  Cc: Dmitry Vyukov, Vegard Nossum, Linus Torvalds, Jiri Slaby,
	Andrew Morton, LKML, linux-serial
In-Reply-To: <20170531111612.GA6332@kroah.com>

On Wed, 31 May 2017 20:16:12 +0900
Greg KH <gregkh@linuxfoundation.org> wrote:

> On Wed, May 31, 2017 at 10:39:23AM +0200, Dmitry Vyukov wrote:
> > On Tue, May 30, 2017 at 2:09 PM, Alan Cox <gnomes@lxorguk.ukuu.org.uk> wrote:  
> > >> >> I'll think about possible solutions, but I have no prior experience
> > >> >> with the tty code. In the meantime syzkaller also hit a couple of
> > >> >> other fun tty/pty bugs including a write/ioctl race that results in
> > >> >> buffer overflow :-/  
> > >
> > > There are several of those, including some of that have been documented
> > > for years but nobody ever volunteered to fix - in particular all the
> > > interfaces that push characters to the tty other than via the normal
> > > interrupt receive path are dodgy (console selection in particular)
> > >
> > > The original tty model btw was that setting the ldisc to n_tty cannot
> > > fail, and the structure allocated was smaller than a page size so was
> > > safe.
> > >
> > > The simple way to fix it is to restore that behaviour by adding a 'null'
> > > ldisc that we can fail to instead of N_TTY since the N_TTY failback path
> > > is long broken.  
> > 
> > Greg, what do you think about this patch? Are you ready to accept
> > something like this?
> > Definitely shorter than changing all drivers.  
> 
> Yes, it looks reasonable to me.



Ok try this

commit f6db8de7eca11cfeafa92f2ec866fa75425c5f38
Author: Alan Cox <alan@llwyncelyn.cymru>
Date:   Tue May 30 12:59:45 2017 +0100

    tty: handle the case where we cannot restore a line discipline
    
    Historically the N_TTY driver could never fail but this has become broken over
    time. Rather than trying to rewrite half the ldisc layer to fix the breakage
    introduce a second level of fallback with an N_NULL ldisc which cannot fail,
    and thus restore the guarantees required by the ldisc layer.
    
    We still try and fail to N_TTY first. It's much more useful to find yourself
    back in your old ldisc (first attempt) or in N_TTY (second attempt), and while
    I'm not aware of any code out there that makes those assumptions it's good to
    drive(r) defensively.

diff --git a/drivers/tty/Makefile b/drivers/tty/Makefile
index f02becd..8689279 100644
--- a/drivers/tty/Makefile
+++ b/drivers/tty/Makefile
@@ -1,6 +1,7 @@
 obj-$(CONFIG_TTY)		+= tty_io.o n_tty.o tty_ioctl.o tty_ldisc.o \
 				   tty_buffer.o tty_port.o tty_mutex.o \
-				   tty_ldsem.o tty_baudrate.o tty_jobctrl.o
+				   tty_ldsem.o tty_baudrate.o tty_jobctrl.o \
+				   n_null.o
 obj-$(CONFIG_LEGACY_PTYS)	+= pty.o
 obj-$(CONFIG_UNIX98_PTYS)	+= pty.o
 obj-$(CONFIG_AUDIT)		+= tty_audit.o
diff --git a/drivers/tty/n_null.c b/drivers/tty/n_null.c
new file mode 100644
index 0000000..d63261c
--- /dev/null
+++ b/drivers/tty/n_null.c
@@ -0,0 +1,80 @@
+#include <linux/types.h>
+#include <linux/errno.h>
+#include <linux/tty.h>
+#include <linux/module.h>
+
+/*
+ *  n_null.c - Null line discipline used in the failure path
+ *
+ *  Copyright (C) Intel 2017
+ *
+ * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ *
+ *  This program is free software; you can redistribute it and/or modify
+ *  it under the terms of the GNU General Public License version 2
+ *  as published by the Free Software Foundation.
+ *
+ *  This program is distributed in the hope that it will be useful,
+ *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+ *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ *  GNU General Public License for more details.
+ *
+ * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ */
+
+static int n_null_open(struct tty_struct *tty)
+{
+	return 0;
+}
+
+static void n_null_close(struct tty_struct *tty)
+{
+}
+
+static ssize_t n_null_read(struct tty_struct *tty, struct file *file,
+			   unsigned char __user * buf, size_t nr)
+{
+	return -EOPNOTSUPP;
+}
+
+static ssize_t n_null_write(struct tty_struct *tty, struct file *file,
+			    const unsigned char *buf, size_t nr)
+{
+	return -EOPNOTSUPP;
+}
+
+static void n_null_receivebuf(struct tty_struct *tty,
+				 const unsigned char *cp, char *fp,
+				 int cnt)
+{
+}
+
+static struct tty_ldisc_ops null_ldisc = {
+	.owner		=	THIS_MODULE,
+	.magic		=	TTY_LDISC_MAGIC,
+	.name		=	"n_null",
+	.open		=	n_null_open,
+	.close		=	n_null_close,
+	.read		=	n_null_read,
+	.write		=	n_null_write,
+	.receive_buf	=	n_null_receivebuf
+};
+
+static int __init n_null_init(void)
+{
+	BUG_ON(tty_register_ldisc(N_NULL, &null_ldisc));
+	return 0;
+}
+
+static void __exit n_null_exit(void)
+{
+	tty_unregister_ldisc(N_NULL);
+}
+
+module_init(n_null_init);
+module_exit(n_null_exit);
+
+MODULE_LICENSE("GPL");
+MODULE_AUTHOR("Alan Cox");
+MODULE_ALIAS_LDISC(N_NULL);
+MODULE_DESCRIPTION("Null ldisc driver");
diff --git a/drivers/tty/tty_ldisc.c b/drivers/tty/tty_ldisc.c
index f6ffe28..2fe216b 100644
--- a/drivers/tty/tty_ldisc.c
+++ b/drivers/tty/tty_ldisc.c
@@ -492,6 +492,29 @@ static void tty_ldisc_close(struct tty_struct *tty, struct tty_ldisc *ld)
 }
 
 /**
+ *	tty_ldisc_failto	-	helper for ldisc failback
+ *	@tty: tty to open the ldisc on
+ *	@ld: ldisc we are trying to fail back to
+ *
+ *	Helper to try and recover a tty when switching back to the old
+ *	ldisc fails and we need something attached.
+ */
+
+static int tty_ldisc_failto(struct tty_struct *tty, int ld)
+{
+	struct tty_ldisc *disc = tty_ldisc_get(tty, ld);
+	int r;
+
+	if (IS_ERR(disc))
+		return PTR_ERR(disc);
+	tty->ldisc = disc;
+	tty_set_termios_ldisc(tty, ld);
+	if ((r = tty_ldisc_open(tty, disc)) < 0)
+		tty_ldisc_put(disc);
+	return r;
+}
+
+/**
  *	tty_ldisc_restore	-	helper for tty ldisc change
  *	@tty: tty to recover
  *	@old: previous ldisc
@@ -502,9 +525,6 @@ static void tty_ldisc_close(struct tty_struct *tty, struct tty_ldisc *ld)
 
 static void tty_ldisc_restore(struct tty_struct *tty, struct tty_ldisc *old)
 {
-	struct tty_ldisc *new_ldisc;
-	int r;
-
 	/* There is an outstanding reference here so this is safe */
 	old = tty_ldisc_get(tty, old->ops->num);
 	WARN_ON(IS_ERR(old));
@@ -512,17 +532,13 @@ static void tty_ldisc_restore(struct tty_struct *tty, struct tty_ldisc *old)
 	tty_set_termios_ldisc(tty, old->ops->num);
 	if (tty_ldisc_open(tty, old) < 0) {
 		tty_ldisc_put(old);
-		/* This driver is always present */
-		new_ldisc = tty_ldisc_get(tty, N_TTY);
-		if (IS_ERR(new_ldisc))
-			panic("n_tty: get");
-		tty->ldisc = new_ldisc;
-		tty_set_termios_ldisc(tty, N_TTY);
-		r = tty_ldisc_open(tty, new_ldisc);
-		if (r < 0)
-			panic("Couldn't open N_TTY ldisc for "
-			      "%s --- error %d.",
-			      tty_name(tty), r);
+		/* The traditional behaviour is to fall back to N_TTY, we
+		   want to avoid falling back to N_NULL unless we have no
+		   choice to avoid the risk of breaking anything */
+		if (tty_ldisc_failto(tty, N_TTY) < 0 &&
+		    tty_ldisc_failto(tty, N_NULL) < 0)
+			panic("Couldn't open N_NULL ldisc for %s.",
+			      tty_name(tty));
 	}
 }
 
diff --git a/include/uapi/linux/tty.h b/include/uapi/linux/tty.h
index e7855df..cf14553 100644
--- a/include/uapi/linux/tty.h
+++ b/include/uapi/linux/tty.h
@@ -36,5 +36,6 @@
 #define N_TRACEROUTER	24	/* Trace data routing for MIPI P1149.7 */
 #define N_NCI		25	/* NFC NCI UART */
 #define N_SPEAKUP	26	/* Speakup communication with synths */
+#define N_NULL		27	/* Null ldisc used for error handling */
 
 #endif /* _UAPI_LINUX_TTY_H */

^ permalink raw reply related

* RE: [PATCH 6/6] tty: serial: lpuart: add a more accurate baud rate calculation method
From: A.S. Dong @ 2017-05-31 14:18 UTC (permalink / raw)
  To: Andy Shevchenko
  Cc: linux-serial@vger.kernel.org, linux-kernel@vger.kernel.org,
	linux-arm Mailing List, Greg Kroah-Hartman, Jiri Slaby, Andy Duan,
	Stefan Agner, Mingkai Hu, Y.B. Lu
In-Reply-To: <CAHp75Vemc5qoD7gbc_sJBSasYTFYSYOuWZv4N-4X60arWX8aJg@mail.gmail.com>

Hi Andy,

> -----Original Message-----
> From: Andy Shevchenko [mailto:andy.shevchenko@gmail.com]
> Sent: Sunday, May 28, 2017 8:04 AM
> To: A.S. Dong
> Cc: linux-serial@vger.kernel.org; linux-kernel@vger.kernel.org; linux-arm
> Mailing List; Greg Kroah-Hartman; Jiri Slaby; Andy Duan; Stefan Agner;
> Mingkai Hu; Y.B. Lu
> Subject: Re: [PATCH 6/6] tty: serial: lpuart: add a more accurate baud
> rate calculation method
> 
> On Tue, May 9, 2017 at 10:50 AM, Dong Aisheng <aisheng.dong@nxp.com> wrote:
> > On new LPUART versions, the oversampling ratio for the receiver can be
> > changed from 4x (00011) to 32x (11111) which could help us get a more
> > accurate baud rate divider.
> >
> > The idea is to use the best OSR (over-sampling rate) possible.
> > Note, OSR is typically hard-set to 16 in other LPUART instantiations.
> > Loop to find the best OSR value possible, one that generates minimum
> > baud diff iterate through the rest of the supported values of OSR.
> 
> > +lpuart32_serial_setbrg(struct lpuart_port *sport, unsigned int
> > +baudrate) {
> > +       u32 sbr, osr, baud_diff, tmp_osr, tmp_sbr, tmp_diff, tmp;
> > +       u32 clk = sport->port.uartclk;
> > +
> > +       /*
> > +        * The idea is to use the best OSR (over-sampling rate) possible.
> > +        * Note, OSR is typically hard-set to 16 in other LPUART
> instantiations.
> > +        * Loop to find the best OSR value possible, one that generates
> minimum
> > +        * baud_diff iterate through the rest of the supported values of
> OSR.
> > +        *
> > +        * Calculation Formula:
> > +        *  Baud Rate = baud clock / ((OSR+1) × SBR)
> > +        */
> > +       baud_diff = baudrate;
> > +       osr = 0;
> > +       sbr = 0;
> > +
> 
> > +       for (tmp_osr = 4; tmp_osr <= 32; tmp_osr++) {
> 
> I _think_ you may simplify this and avoid for-loop if you reconsider
> approach.
> 

The algorithm is that we have to iterate all possible OSCs and find
the one with minimum baud_diff.

I'm not sure what alternative approach did you mean?

But there is indeed a optimization way, see below.

> > +               /* calculate the temporary sbr value  */
> > +               tmp_sbr = (clk / (baudrate * tmp_osr));
> > +               if (tmp_sbr == 0)
> > +                       tmp_sbr = 1;
> > +
> > +               /*
> > +                * calculate the baud rate difference based on the
> temporary
> > +                * osr and sbr values
> > +                */
> 
> > +               tmp_diff = clk / (tmp_osr * tmp_sbr) - baudrate;
> 
> (32 - 4 + 1) times division is called...
> 

Yes.

> > +
> > +               /* select best values between sbr and sbr+1 */
> > +               tmp = clk / (tmp_osr * (tmp_sbr + 1));
> > +               if (tmp_diff > (baudrate - tmp)) {
> > +                       tmp_diff = baudrate - tmp;
> > +                       tmp_sbr++;
> > +               }
> > +
> > +               if (tmp_diff <= baud_diff) {
> > +                       baud_diff = tmp_diff;
> > +                       osr = tmp_osr;
> > +                       sbr = tmp_sbr;

To optimize the looping, we probably could do:
If (!daud_diff)
	Break;

> > +               }
> > +       }
> 
> > +       /* handle buadrate outside acceptable rate */
> > +       if (baud_diff > ((baudrate / 100) * 3))
> > +               dev_warn(sport->port.dev,
> > +                        "unacceptable baud rate difference of more
> > + than 3%%\n");
> 
> Shouldn't you fall back to previous setting?
> 

Hmmm.. Is there defined semantic to do that or is there any other ones
doing that way?

I see most drivers not doing that.

> > +
> > +       tmp = lpuart32_read(sport->port.membase + UARTBAUD);
> > +
> 
> > +       if ((osr > 3) && (osr < 8))
> 
> Isn't it
> 
> if (osr ^ BIT(2) < BIT(2))
> 
> ?
> 

That is obvious hard to understand and I'd rather keep a more explicit way.

> > +               tmp |= UARTBAUD_BOTHEDGE;
> 
> > +}
> 
> > +       if (of_device_is_compatible(port->dev->of_node, "fsl,imx7ulp-
> lpuart")) {
> > +               lpuart32_serial_setbrg(sport, baud);
> 
> > +       } else {
> > +               sbr = sport->port.uartclk / (16 * baud);
> > +               bd &= ~UARTBAUD_SBR_MASK;
> > +               bd |= sbr & UARTBAUD_SBR_MASK;
> > +               bd |= UARTBAUD_BOTHEDGE;
> > +               bd &= ~(UARTBAUD_TDMAE | UARTBAUD_RDMAE);
> > +               lpuart32_write(bd, sport->port.membase + UARTBAUD);
> > +       }
> 
> Perhaps it makes sense to split this to a helper function as well (in a
> separate patch).
> 

That will be removed according to Stefan's suggestion to get LS platforms
Start to test.

Regards
Dong Aisheng

^ permalink raw reply

* Re: [PATCH v2 2/2] arm64: dts: Add Mediatek SoC MT2712 and evaluation board dts and Makefile
From: Matthias Brugger @ 2017-05-31 12:42 UTC (permalink / raw)
  To: YT Shen, Rob Herring
  Cc: Mark Rutland, Thomas Gleixner, Jason Cooper, Marc Zyngier,
	Greg Kroah-Hartman, Catalin Marinas, Will Deacon, Mars Cheng,
	devicetree-u79uwXL29TY76Z2rM5mHXA,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-serial-u79uwXL29TY76Z2rM5mHXA,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	linux-mediatek-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	srv_heupstream-NuS5LvNUpcJWk0Htik3J/w
In-Reply-To: <1496230773-22633-3-git-send-email-yt.shen-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>



On 31/05/17 13:39, YT Shen wrote:
> This adds basic chip support for Mediatek 2712
> 
> Signed-off-by: YT Shen <yt.shen-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>
> ---
>   arch/arm64/boot/dts/mediatek/Makefile       |   1 +
>   arch/arm64/boot/dts/mediatek/mt2712-evb.dts |  39 +++++++
>   arch/arm64/boot/dts/mediatek/mt2712e.dtsi   | 166 ++++++++++++++++++++++++++++
>   3 files changed, 206 insertions(+)
>   create mode 100644 arch/arm64/boot/dts/mediatek/mt2712-evb.dts
>   create mode 100644 arch/arm64/boot/dts/mediatek/mt2712e.dtsi
> 
> diff --git a/arch/arm64/boot/dts/mediatek/Makefile b/arch/arm64/boot/dts/mediatek/Makefile
> index 9fbfd32..fcc0604 100644
> --- a/arch/arm64/boot/dts/mediatek/Makefile
> +++ b/arch/arm64/boot/dts/mediatek/Makefile
> @@ -1,3 +1,4 @@
> +dtb-$(CONFIG_ARCH_MEDIATEK) += mt2712-evb.dtb
>   dtb-$(CONFIG_ARCH_MEDIATEK) += mt6755-evb.dtb
>   dtb-$(CONFIG_ARCH_MEDIATEK) += mt6795-evb.dtb
>   dtb-$(CONFIG_ARCH_MEDIATEK) += mt8173-evb.dtb
> diff --git a/arch/arm64/boot/dts/mediatek/mt2712-evb.dts b/arch/arm64/boot/dts/mediatek/mt2712-evb.dts
> new file mode 100644
> index 0000000..e526c0f
> --- /dev/null
> +++ b/arch/arm64/boot/dts/mediatek/mt2712-evb.dts
> @@ -0,0 +1,39 @@
> +/*
> + * Copyright (c) 2017 MediaTek Inc.
> + * Author: YT Shen <yt.shen-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>
> + *
> + * SPDX-License-Identifier: (GPL-2.0 OR MIT)
> + */
> +
> +/dts-v1/;
> +#include "mt2712e.dtsi"
> +
> +/ {
> +	model = "MediaTek MT2712 evaluation board";
> +	compatible = "mediatek,mt2712-evb", "mediatek,mt2712";
> +
> +	aliases {
> +		serial0 = &uart0;
> +		serial1 = &uart1;
> +		serial2 = &uart2;
> +		serial3 = &uart3;
> +		serial4 = &uart4;
> +		serial5 = &uart5;
> +	};

Just declare serial0 here, as you don't use the others.

> +
> +	memory@40000000 {
> +		device_type = "memory";
> +		reg = <0 0x40000000 0 0x80000000>;
> +	};
> +
> +	chosen {
> +		stdout-path = "serial0:921600n8";
> +		linux,initrd-start = <0x45000000>;
> +		linux,initrd-end   = <0x4a000000>;

initrd-start and end should be dynamically set by the bootloader and not 
via a chosen node. Is your bootloader not able to do that?

> +	};
> +};
> +
> +&uart0 {
> +	status = "okay";
> +};
> +
> diff --git a/arch/arm64/boot/dts/mediatek/mt2712e.dtsi b/arch/arm64/boot/dts/mediatek/mt2712e.dtsi
> new file mode 100644
> index 0000000..6df0da9
> --- /dev/null
> +++ b/arch/arm64/boot/dts/mediatek/mt2712e.dtsi
> @@ -0,0 +1,166 @@
> +/*
> + * Copyright (c) 2017 MediaTek Inc.
> + * Author: YT Shen <yt.shen-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>
> + *
> + * SPDX-License-Identifier: (GPL-2.0 OR MIT)
> + */
> +
> +#include <dt-bindings/interrupt-controller/irq.h>
> +#include <dt-bindings/interrupt-controller/arm-gic.h>
> +
> +/ {
> +	compatible = "mediatek,mt2712";
> +	interrupt-parent = <&sysirq>;
> +	#address-cells = <2>;
> +	#size-cells = <2>;
> +
> +	cpus {
> +		#address-cells = <1>;
> +		#size-cells = <0>;
> +
> +		cpu-map {
> +			cluster0 {
> +				core0 {
> +					cpu = <&cpu0>;
> +				};
> +				core1 {
> +					cpu = <&cpu1>;
> +				};
> +			};
> +
> +			cluster1 {
> +				core0 {
> +					cpu = <&cpu2>;
> +				};
> +			};
> +		};
> +
> +		cpu0: cpu@0 {
> +			device_type = "cpu";
> +			compatible = "arm,cortex-a35";

do you mean cortex-a53?

> +			reg = <0x000>;
> +		};
> +
> +		cpu1: cpu@1 {
> +			device_type = "cpu";
> +			compatible = "arm,cortex-a35";

same here.

Regards,
Matthias

> +			reg = <0x001>;
> +			enable-method = "psci";
> +		};
> +
> +		cpu2: cpu@200 {
> +			device_type = "cpu";
> +			compatible = "arm,cortex-a72";
> +			reg = <0x200>;
> +			enable-method = "psci";
> +		};
> +	};
> +
> +	psci {
> +		compatible = "arm,psci-0.2";
> +		method = "smc";
> +	};
> +
> +	uart_clk: dummy26m {
> +		compatible = "fixed-clock";
> +		clock-frequency = <26000000>;
> +		#clock-cells = <0>;
> +	};
> +
> +	timer {
> +		compatible = "arm,armv8-timer";
> +		interrupt-parent = <&gic>;
> +		interrupts = <GIC_PPI 13
> +			      (GIC_CPU_MASK_SIMPLE(6) | IRQ_TYPE_LEVEL_LOW)>,
> +			     <GIC_PPI 14
> +			      (GIC_CPU_MASK_SIMPLE(6) | IRQ_TYPE_LEVEL_LOW)>,
> +			     <GIC_PPI 11
> +			      (GIC_CPU_MASK_SIMPLE(6) | IRQ_TYPE_LEVEL_LOW)>,
> +			     <GIC_PPI 10
> +			      (GIC_CPU_MASK_SIMPLE(6) | IRQ_TYPE_LEVEL_LOW)>;
> +	};
> +
> +	soc {
> +		#address-cells = <2>;
> +		#size-cells = <2>;
> +		compatible = "simple-bus";
> +		ranges;
> +
> +		uart5: serial@1000f000 {
> +			compatible = "mediatek,mt2712-uart",
> +				     "mediatek,mt6577-uart";
> +			reg = <0 0x1000f000 0 0x400>;
> +			interrupts = <GIC_SPI 127 IRQ_TYPE_LEVEL_LOW>;
> +			clocks = <&uart_clk>;
> +			status = "disabled";
> +		};
> +
> +		sysirq: interrupt-controller@10220a80 {
> +			compatible = "mediatek,mt2712-sysirq",
> +				     "mediatek,mt6577-sysirq";
> +			interrupt-controller;
> +			#interrupt-cells = <3>;
> +			interrupt-parent = <&gic>;
> +			reg = <0 0x10220a80 0 0x40>;
> +		};
> +
> +		gic: interrupt-controller@10510000 {
> +			compatible = "arm,gic-400";
> +			#interrupt-cells = <3>;
> +			interrupt-parent = <&gic>;
> +			interrupt-controller;
> +			reg = <0 0x10510000 0 0x1000>,
> +			      <0 0x10520000 0 0x1000>,
> +			      <0 0x10540000 0 0x2000>,
> +			      <0 0x10560000 0 0x2000>;
> +			interrupts = <GIC_PPI 9
> +				(GIC_CPU_MASK_SIMPLE(6) | IRQ_TYPE_LEVEL_HIGH)>;
> +		};
> +
> +		uart0: serial@11002000 {
> +			compatible = "mediatek,mt2712-uart",
> +				     "mediatek,mt6577-uart";
> +			reg = <0 0x11002000 0 0x400>;
> +			interrupts = <GIC_SPI 91 IRQ_TYPE_LEVEL_LOW>;
> +			clocks = <&uart_clk>;
> +			status = "disabled";
> +		};
> +
> +		uart1: serial@11003000 {
> +			compatible = "mediatek,mt2712-uart",
> +				     "mediatek,mt6577-uart";
> +			reg = <0 0x11003000 0 0x400>;
> +			interrupts = <GIC_SPI 92 IRQ_TYPE_LEVEL_LOW>;
> +			clocks = <&uart_clk>;
> +			status = "disabled";
> +		};
> +
> +		uart2: serial@11004000 {
> +			compatible = "mediatek,mt2712-uart",
> +				     "mediatek,mt6577-uart";
> +			reg = <0 0x11004000 0 0x400>;
> +			interrupts = <GIC_SPI 93 IRQ_TYPE_LEVEL_LOW>;
> +			clocks = <&uart_clk>;
> +			status = "disabled";
> +		};
> +
> +		uart3: serial@11005000 {
> +			compatible = "mediatek,mt2712-uart",
> +				     "mediatek,mt6577-uart";
> +			reg = <0 0x11005000 0 0x400>;
> +			interrupts = <GIC_SPI 94 IRQ_TYPE_LEVEL_LOW>;
> +			clocks = <&uart_clk>;
> +			status = "disabled";
> +		};
> +
> +		uart4: serial@11019000 {
> +			compatible = "mediatek,mt2712-uart",
> +				     "mediatek,mt6577-uart";
> +			reg = <0 0x11019000 0 0x400>;
> +			interrupts = <GIC_SPI 126 IRQ_TYPE_LEVEL_LOW>;
> +			clocks = <&uart_clk>;
> +			status = "disabled";
> +		};
> +	};
> +};
> +
> 
--
To unsubscribe from this list: send the line "unsubscribe devicetree" in
the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply

* Re: [PATCH v2 2/2] arm64: dts: Add Mediatek SoC MT2712 and evaluation board dts and Makefile
From: Marc Zyngier @ 2017-05-31 12:38 UTC (permalink / raw)
  To: YT Shen, Rob Herring, Matthias Brugger
  Cc: Mark Rutland, Thomas Gleixner, Jason Cooper, Greg Kroah-Hartman,
	Catalin Marinas, Will Deacon, Mars Cheng,
	devicetree-u79uwXL29TY76Z2rM5mHXA,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-serial-u79uwXL29TY76Z2rM5mHXA,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	linux-mediatek-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	srv_heupstream-NuS5LvNUpcJWk0Htik3J/w
In-Reply-To: <1496230773-22633-3-git-send-email-yt.shen-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>

On 31/05/17 12:39, YT Shen wrote:
> This adds basic chip support for Mediatek 2712
> 
> Signed-off-by: YT Shen <yt.shen-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>
> ---
>  arch/arm64/boot/dts/mediatek/Makefile       |   1 +
>  arch/arm64/boot/dts/mediatek/mt2712-evb.dts |  39 +++++++
>  arch/arm64/boot/dts/mediatek/mt2712e.dtsi   | 166 ++++++++++++++++++++++++++++
>  3 files changed, 206 insertions(+)
>  create mode 100644 arch/arm64/boot/dts/mediatek/mt2712-evb.dts
>  create mode 100644 arch/arm64/boot/dts/mediatek/mt2712e.dtsi
> 
> diff --git a/arch/arm64/boot/dts/mediatek/Makefile b/arch/arm64/boot/dts/mediatek/Makefile
> index 9fbfd32..fcc0604 100644
> --- a/arch/arm64/boot/dts/mediatek/Makefile
> +++ b/arch/arm64/boot/dts/mediatek/Makefile
> @@ -1,3 +1,4 @@
> +dtb-$(CONFIG_ARCH_MEDIATEK) += mt2712-evb.dtb
>  dtb-$(CONFIG_ARCH_MEDIATEK) += mt6755-evb.dtb
>  dtb-$(CONFIG_ARCH_MEDIATEK) += mt6795-evb.dtb
>  dtb-$(CONFIG_ARCH_MEDIATEK) += mt8173-evb.dtb
> diff --git a/arch/arm64/boot/dts/mediatek/mt2712-evb.dts b/arch/arm64/boot/dts/mediatek/mt2712-evb.dts
> new file mode 100644
> index 0000000..e526c0f
> --- /dev/null
> +++ b/arch/arm64/boot/dts/mediatek/mt2712-evb.dts
> @@ -0,0 +1,39 @@
> +/*
> + * Copyright (c) 2017 MediaTek Inc.
> + * Author: YT Shen <yt.shen-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>
> + *
> + * SPDX-License-Identifier: (GPL-2.0 OR MIT)
> + */
> +
> +/dts-v1/;
> +#include "mt2712e.dtsi"
> +
> +/ {
> +	model = "MediaTek MT2712 evaluation board";
> +	compatible = "mediatek,mt2712-evb", "mediatek,mt2712";
> +
> +	aliases {
> +		serial0 = &uart0;
> +		serial1 = &uart1;
> +		serial2 = &uart2;
> +		serial3 = &uart3;
> +		serial4 = &uart4;
> +		serial5 = &uart5;
> +	};
> +
> +	memory@40000000 {
> +		device_type = "memory";
> +		reg = <0 0x40000000 0 0x80000000>;
> +	};
> +
> +	chosen {
> +		stdout-path = "serial0:921600n8";
> +		linux,initrd-start = <0x45000000>;
> +		linux,initrd-end   = <0x4a000000>;
> +	};
> +};
> +
> +&uart0 {
> +	status = "okay";
> +};
> +
> diff --git a/arch/arm64/boot/dts/mediatek/mt2712e.dtsi b/arch/arm64/boot/dts/mediatek/mt2712e.dtsi
> new file mode 100644
> index 0000000..6df0da9
> --- /dev/null
> +++ b/arch/arm64/boot/dts/mediatek/mt2712e.dtsi
> @@ -0,0 +1,166 @@
> +/*
> + * Copyright (c) 2017 MediaTek Inc.
> + * Author: YT Shen <yt.shen-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>
> + *
> + * SPDX-License-Identifier: (GPL-2.0 OR MIT)
> + */
> +
> +#include <dt-bindings/interrupt-controller/irq.h>
> +#include <dt-bindings/interrupt-controller/arm-gic.h>
> +
> +/ {
> +	compatible = "mediatek,mt2712";
> +	interrupt-parent = <&sysirq>;
> +	#address-cells = <2>;
> +	#size-cells = <2>;
> +
> +	cpus {
> +		#address-cells = <1>;
> +		#size-cells = <0>;
> +
> +		cpu-map {
> +			cluster0 {
> +				core0 {
> +					cpu = <&cpu0>;
> +				};
> +				core1 {
> +					cpu = <&cpu1>;
> +				};
> +			};
> +
> +			cluster1 {
> +				core0 {
> +					cpu = <&cpu2>;
> +				};
> +			};
> +		};
> +
> +		cpu0: cpu@0 {
> +			device_type = "cpu";
> +			compatible = "arm,cortex-a35";
> +			reg = <0x000>;
> +		};
> +
> +		cpu1: cpu@1 {
> +			device_type = "cpu";
> +			compatible = "arm,cortex-a35";
> +			reg = <0x001>;
> +			enable-method = "psci";
> +		};
> +
> +		cpu2: cpu@200 {
> +			device_type = "cpu";
> +			compatible = "arm,cortex-a72";
> +			reg = <0x200>;
> +			enable-method = "psci";
> +		};
> +	};
> +
> +	psci {
> +		compatible = "arm,psci-0.2";
> +		method = "smc";
> +	};
> +
> +	uart_clk: dummy26m {
> +		compatible = "fixed-clock";
> +		clock-frequency = <26000000>;
> +		#clock-cells = <0>;
> +	};
> +
> +	timer {
> +		compatible = "arm,armv8-timer";
> +		interrupt-parent = <&gic>;
> +		interrupts = <GIC_PPI 13
> +			      (GIC_CPU_MASK_SIMPLE(6) | IRQ_TYPE_LEVEL_LOW)>,

Why 6? I only count 3 cores...

> +			     <GIC_PPI 14
> +			      (GIC_CPU_MASK_SIMPLE(6) | IRQ_TYPE_LEVEL_LOW)>,
> +			     <GIC_PPI 11
> +			      (GIC_CPU_MASK_SIMPLE(6) | IRQ_TYPE_LEVEL_LOW)>,
> +			     <GIC_PPI 10
> +			      (GIC_CPU_MASK_SIMPLE(6) | IRQ_TYPE_LEVEL_LOW)>;
> +	};
> +
> +	soc {
> +		#address-cells = <2>;
> +		#size-cells = <2>;
> +		compatible = "simple-bus";
> +		ranges;
> +
> +		uart5: serial@1000f000 {
> +			compatible = "mediatek,mt2712-uart",
> +				     "mediatek,mt6577-uart";
> +			reg = <0 0x1000f000 0 0x400>;
> +			interrupts = <GIC_SPI 127 IRQ_TYPE_LEVEL_LOW>;
> +			clocks = <&uart_clk>;
> +			status = "disabled";
> +		};
> +
> +		sysirq: interrupt-controller@10220a80 {
> +			compatible = "mediatek,mt2712-sysirq",
> +				     "mediatek,mt6577-sysirq";
> +			interrupt-controller;
> +			#interrupt-cells = <3>;
> +			interrupt-parent = <&gic>;
> +			reg = <0 0x10220a80 0 0x40>;
> +		};
> +
> +		gic: interrupt-controller@10510000 {
> +			compatible = "arm,gic-400";
> +			#interrupt-cells = <3>;
> +			interrupt-parent = <&gic>;
> +			interrupt-controller;
> +			reg = <0 0x10510000 0 0x1000>,
> +			      <0 0x10520000 0 0x1000>,

If that's truly a GIC400, then the above is wrong (the CPU interface is
spread over 8kB).

I also suspect that the first 4kB are aliased over
0x10520000:0x1052f000, and the second over 0x10530000:0x1053f000 (in the
true SBSA tradition). If that's the case, then the size is actually 128kB.

> +			      <0 0x10540000 0 0x2000>,
> +			      <0 0x10560000 0 0x2000>;

Please check GICV as well, which probably behaves the same way.

> +			interrupts = <GIC_PPI 9
> +				(GIC_CPU_MASK_SIMPLE(6) | IRQ_TYPE_LEVEL_HIGH)>;

Same thing here with 6 CPUs.

> +		};
> +
> +		uart0: serial@11002000 {
> +			compatible = "mediatek,mt2712-uart",
> +				     "mediatek,mt6577-uart";
> +			reg = <0 0x11002000 0 0x400>;
> +			interrupts = <GIC_SPI 91 IRQ_TYPE_LEVEL_LOW>;
> +			clocks = <&uart_clk>;
> +			status = "disabled";
> +		};
> +
> +		uart1: serial@11003000 {
> +			compatible = "mediatek,mt2712-uart",
> +				     "mediatek,mt6577-uart";
> +			reg = <0 0x11003000 0 0x400>;
> +			interrupts = <GIC_SPI 92 IRQ_TYPE_LEVEL_LOW>;
> +			clocks = <&uart_clk>;
> +			status = "disabled";
> +		};
> +
> +		uart2: serial@11004000 {
> +			compatible = "mediatek,mt2712-uart",
> +				     "mediatek,mt6577-uart";
> +			reg = <0 0x11004000 0 0x400>;
> +			interrupts = <GIC_SPI 93 IRQ_TYPE_LEVEL_LOW>;
> +			clocks = <&uart_clk>;
> +			status = "disabled";
> +		};
> +
> +		uart3: serial@11005000 {
> +			compatible = "mediatek,mt2712-uart",
> +				     "mediatek,mt6577-uart";
> +			reg = <0 0x11005000 0 0x400>;
> +			interrupts = <GIC_SPI 94 IRQ_TYPE_LEVEL_LOW>;
> +			clocks = <&uart_clk>;
> +			status = "disabled";
> +		};
> +
> +		uart4: serial@11019000 {
> +			compatible = "mediatek,mt2712-uart",
> +				     "mediatek,mt6577-uart";
> +			reg = <0 0x11019000 0 0x400>;
> +			interrupts = <GIC_SPI 126 IRQ_TYPE_LEVEL_LOW>;
> +			clocks = <&uart_clk>;
> +			status = "disabled";
> +		};
> +	};
> +};
> +
> 

No PMU wired on this system?

Thanks,

	M.
-- 
Jazz is not dead. It just smells funny...
--
To unsubscribe from this list: send the line "unsubscribe devicetree" in
the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply

* [PATCH v2 2/2] arm64: dts: Add Mediatek SoC MT2712 and evaluation board dts and Makefile
From: YT Shen @ 2017-05-31 11:39 UTC (permalink / raw)
  To: Rob Herring, Matthias Brugger
  Cc: Mark Rutland, Thomas Gleixner, Jason Cooper, Marc Zyngier,
	Greg Kroah-Hartman, Catalin Marinas, Will Deacon, Mars Cheng,
	YT Shen, devicetree, linux-kernel, linux-serial, linux-arm-kernel,
	linux-mediatek, srv_heupstream
In-Reply-To: <1496230773-22633-1-git-send-email-yt.shen@mediatek.com>

This adds basic chip support for Mediatek 2712

Signed-off-by: YT Shen <yt.shen@mediatek.com>
---
 arch/arm64/boot/dts/mediatek/Makefile       |   1 +
 arch/arm64/boot/dts/mediatek/mt2712-evb.dts |  39 +++++++
 arch/arm64/boot/dts/mediatek/mt2712e.dtsi   | 166 ++++++++++++++++++++++++++++
 3 files changed, 206 insertions(+)
 create mode 100644 arch/arm64/boot/dts/mediatek/mt2712-evb.dts
 create mode 100644 arch/arm64/boot/dts/mediatek/mt2712e.dtsi

diff --git a/arch/arm64/boot/dts/mediatek/Makefile b/arch/arm64/boot/dts/mediatek/Makefile
index 9fbfd32..fcc0604 100644
--- a/arch/arm64/boot/dts/mediatek/Makefile
+++ b/arch/arm64/boot/dts/mediatek/Makefile
@@ -1,3 +1,4 @@
+dtb-$(CONFIG_ARCH_MEDIATEK) += mt2712-evb.dtb
 dtb-$(CONFIG_ARCH_MEDIATEK) += mt6755-evb.dtb
 dtb-$(CONFIG_ARCH_MEDIATEK) += mt6795-evb.dtb
 dtb-$(CONFIG_ARCH_MEDIATEK) += mt8173-evb.dtb
diff --git a/arch/arm64/boot/dts/mediatek/mt2712-evb.dts b/arch/arm64/boot/dts/mediatek/mt2712-evb.dts
new file mode 100644
index 0000000..e526c0f
--- /dev/null
+++ b/arch/arm64/boot/dts/mediatek/mt2712-evb.dts
@@ -0,0 +1,39 @@
+/*
+ * Copyright (c) 2017 MediaTek Inc.
+ * Author: YT Shen <yt.shen@mediatek.com>
+ *
+ * SPDX-License-Identifier: (GPL-2.0 OR MIT)
+ */
+
+/dts-v1/;
+#include "mt2712e.dtsi"
+
+/ {
+	model = "MediaTek MT2712 evaluation board";
+	compatible = "mediatek,mt2712-evb", "mediatek,mt2712";
+
+	aliases {
+		serial0 = &uart0;
+		serial1 = &uart1;
+		serial2 = &uart2;
+		serial3 = &uart3;
+		serial4 = &uart4;
+		serial5 = &uart5;
+	};
+
+	memory@40000000 {
+		device_type = "memory";
+		reg = <0 0x40000000 0 0x80000000>;
+	};
+
+	chosen {
+		stdout-path = "serial0:921600n8";
+		linux,initrd-start = <0x45000000>;
+		linux,initrd-end   = <0x4a000000>;
+	};
+};
+
+&uart0 {
+	status = "okay";
+};
+
diff --git a/arch/arm64/boot/dts/mediatek/mt2712e.dtsi b/arch/arm64/boot/dts/mediatek/mt2712e.dtsi
new file mode 100644
index 0000000..6df0da9
--- /dev/null
+++ b/arch/arm64/boot/dts/mediatek/mt2712e.dtsi
@@ -0,0 +1,166 @@
+/*
+ * Copyright (c) 2017 MediaTek Inc.
+ * Author: YT Shen <yt.shen@mediatek.com>
+ *
+ * SPDX-License-Identifier: (GPL-2.0 OR MIT)
+ */
+
+#include <dt-bindings/interrupt-controller/irq.h>
+#include <dt-bindings/interrupt-controller/arm-gic.h>
+
+/ {
+	compatible = "mediatek,mt2712";
+	interrupt-parent = <&sysirq>;
+	#address-cells = <2>;
+	#size-cells = <2>;
+
+	cpus {
+		#address-cells = <1>;
+		#size-cells = <0>;
+
+		cpu-map {
+			cluster0 {
+				core0 {
+					cpu = <&cpu0>;
+				};
+				core1 {
+					cpu = <&cpu1>;
+				};
+			};
+
+			cluster1 {
+				core0 {
+					cpu = <&cpu2>;
+				};
+			};
+		};
+
+		cpu0: cpu@0 {
+			device_type = "cpu";
+			compatible = "arm,cortex-a35";
+			reg = <0x000>;
+		};
+
+		cpu1: cpu@1 {
+			device_type = "cpu";
+			compatible = "arm,cortex-a35";
+			reg = <0x001>;
+			enable-method = "psci";
+		};
+
+		cpu2: cpu@200 {
+			device_type = "cpu";
+			compatible = "arm,cortex-a72";
+			reg = <0x200>;
+			enable-method = "psci";
+		};
+	};
+
+	psci {
+		compatible = "arm,psci-0.2";
+		method = "smc";
+	};
+
+	uart_clk: dummy26m {
+		compatible = "fixed-clock";
+		clock-frequency = <26000000>;
+		#clock-cells = <0>;
+	};
+
+	timer {
+		compatible = "arm,armv8-timer";
+		interrupt-parent = <&gic>;
+		interrupts = <GIC_PPI 13
+			      (GIC_CPU_MASK_SIMPLE(6) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 14
+			      (GIC_CPU_MASK_SIMPLE(6) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 11
+			      (GIC_CPU_MASK_SIMPLE(6) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 10
+			      (GIC_CPU_MASK_SIMPLE(6) | IRQ_TYPE_LEVEL_LOW)>;
+	};
+
+	soc {
+		#address-cells = <2>;
+		#size-cells = <2>;
+		compatible = "simple-bus";
+		ranges;
+
+		uart5: serial@1000f000 {
+			compatible = "mediatek,mt2712-uart",
+				     "mediatek,mt6577-uart";
+			reg = <0 0x1000f000 0 0x400>;
+			interrupts = <GIC_SPI 127 IRQ_TYPE_LEVEL_LOW>;
+			clocks = <&uart_clk>;
+			status = "disabled";
+		};
+
+		sysirq: interrupt-controller@10220a80 {
+			compatible = "mediatek,mt2712-sysirq",
+				     "mediatek,mt6577-sysirq";
+			interrupt-controller;
+			#interrupt-cells = <3>;
+			interrupt-parent = <&gic>;
+			reg = <0 0x10220a80 0 0x40>;
+		};
+
+		gic: interrupt-controller@10510000 {
+			compatible = "arm,gic-400";
+			#interrupt-cells = <3>;
+			interrupt-parent = <&gic>;
+			interrupt-controller;
+			reg = <0 0x10510000 0 0x1000>,
+			      <0 0x10520000 0 0x1000>,
+			      <0 0x10540000 0 0x2000>,
+			      <0 0x10560000 0 0x2000>;
+			interrupts = <GIC_PPI 9
+				(GIC_CPU_MASK_SIMPLE(6) | IRQ_TYPE_LEVEL_HIGH)>;
+		};
+
+		uart0: serial@11002000 {
+			compatible = "mediatek,mt2712-uart",
+				     "mediatek,mt6577-uart";
+			reg = <0 0x11002000 0 0x400>;
+			interrupts = <GIC_SPI 91 IRQ_TYPE_LEVEL_LOW>;
+			clocks = <&uart_clk>;
+			status = "disabled";
+		};
+
+		uart1: serial@11003000 {
+			compatible = "mediatek,mt2712-uart",
+				     "mediatek,mt6577-uart";
+			reg = <0 0x11003000 0 0x400>;
+			interrupts = <GIC_SPI 92 IRQ_TYPE_LEVEL_LOW>;
+			clocks = <&uart_clk>;
+			status = "disabled";
+		};
+
+		uart2: serial@11004000 {
+			compatible = "mediatek,mt2712-uart",
+				     "mediatek,mt6577-uart";
+			reg = <0 0x11004000 0 0x400>;
+			interrupts = <GIC_SPI 93 IRQ_TYPE_LEVEL_LOW>;
+			clocks = <&uart_clk>;
+			status = "disabled";
+		};
+
+		uart3: serial@11005000 {
+			compatible = "mediatek,mt2712-uart",
+				     "mediatek,mt6577-uart";
+			reg = <0 0x11005000 0 0x400>;
+			interrupts = <GIC_SPI 94 IRQ_TYPE_LEVEL_LOW>;
+			clocks = <&uart_clk>;
+			status = "disabled";
+		};
+
+		uart4: serial@11019000 {
+			compatible = "mediatek,mt2712-uart",
+				     "mediatek,mt6577-uart";
+			reg = <0 0x11019000 0 0x400>;
+			interrupts = <GIC_SPI 126 IRQ_TYPE_LEVEL_LOW>;
+			clocks = <&uart_clk>;
+			status = "disabled";
+		};
+	};
+};
+
-- 
1.9.1

^ permalink raw reply related

* [PATCH v2 1/2] dt-bindings: arm: Add bindings for Mediatek MT2712 SoC Platform
From: YT Shen @ 2017-05-31 11:39 UTC (permalink / raw)
  To: Rob Herring, Matthias Brugger
  Cc: Mark Rutland, devicetree, Jason Cooper, srv_heupstream,
	Marc Zyngier, Catalin Marinas, Will Deacon, linux-kernel,
	Mars Cheng, linux-serial, Greg Kroah-Hartman, YT Shen,
	linux-mediatek, Thomas Gleixner, linux-arm-kernel
In-Reply-To: <1496230773-22633-1-git-send-email-yt.shen@mediatek.com>

This adds dt-binding documentation for Mediatek MT2712.
Only include very basic items: cpu, gic and uart.

Signed-off-by: YT Shen <yt.shen@mediatek.com>
Acked-by: Rob Herring <robh@kernel.org>
---
 Documentation/devicetree/bindings/arm/mediatek.txt                    | 4 ++++
 .../devicetree/bindings/interrupt-controller/mediatek,sysirq.txt      | 1 +
 Documentation/devicetree/bindings/serial/mtk-uart.txt                 | 1 +
 3 files changed, 6 insertions(+)

diff --git a/Documentation/devicetree/bindings/arm/mediatek.txt b/Documentation/devicetree/bindings/arm/mediatek.txt
index c860b24..3161651 100644
--- a/Documentation/devicetree/bindings/arm/mediatek.txt
+++ b/Documentation/devicetree/bindings/arm/mediatek.txt
@@ -7,6 +7,7 @@ Required root node property:
 
 compatible: Must contain one of
    "mediatek,mt2701"
+   "mediatek,mt2712"
    "mediatek,mt6580"
    "mediatek,mt6589"
    "mediatek,mt6592"
@@ -23,6 +24,9 @@ Supported boards:
 - Evaluation board for MT2701:
     Required root node properties:
       - compatible = "mediatek,mt2701-evb", "mediatek,mt2701";
+- Evaluation board for MT2712:
+    Required root node properties:
+      - compatible = "mediatek,mt2712-evb", "mediatek,mt2712";
 - Evaluation board for MT6580:
     Required root node properties:
       - compatible = "mediatek,mt6580-evbp1", "mediatek,mt6580";
diff --git a/Documentation/devicetree/bindings/interrupt-controller/mediatek,sysirq.txt b/Documentation/devicetree/bindings/interrupt-controller/mediatek,sysirq.txt
index a89c03b..653adb5 100644
--- a/Documentation/devicetree/bindings/interrupt-controller/mediatek,sysirq.txt
+++ b/Documentation/devicetree/bindings/interrupt-controller/mediatek,sysirq.txt
@@ -16,6 +16,7 @@ Required properties:
 	"mediatek,mt6580-sysirq"
 	"mediatek,mt6577-sysirq"
 	"mediatek,mt2701-sysirq"
+	"mediatek,mt2712-sysirq"
 - interrupt-controller : Identifies the node as an interrupt controller
 - #interrupt-cells : Use the same format as specified by GIC in arm,gic.txt.
 - interrupt-parent: phandle of irq parent for sysirq. The parent must
diff --git a/Documentation/devicetree/bindings/serial/mtk-uart.txt b/Documentation/devicetree/bindings/serial/mtk-uart.txt
index 0015c72..5f88e0d 100644
--- a/Documentation/devicetree/bindings/serial/mtk-uart.txt
+++ b/Documentation/devicetree/bindings/serial/mtk-uart.txt
@@ -3,6 +3,7 @@
 Required properties:
 - compatible should contain:
   * "mediatek,mt2701-uart" for MT2701 compatible UARTS
+  * "mediatek,mt2712-uart" for MT2712 compatible UARTS
   * "mediatek,mt6580-uart" for MT6580 compatible UARTS
   * "mediatek,mt6582-uart" for MT6582 compatible UARTS
   * "mediatek,mt6589-uart" for MT6589 compatible UARTS
-- 
1.9.1

^ permalink raw reply related

* [PATCH v2 0/2] Add basic support for Mediatek MT2712 SoC
From: YT Shen @ 2017-05-31 11:39 UTC (permalink / raw)
  To: Rob Herring, Matthias Brugger
  Cc: Mark Rutland, Thomas Gleixner, Jason Cooper, Marc Zyngier,
	Greg Kroah-Hartman, Catalin Marinas, Will Deacon, Mars Cheng,
	YT Shen, devicetree-u79uwXL29TY76Z2rM5mHXA,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-serial-u79uwXL29TY76Z2rM5mHXA,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	linux-mediatek-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	srv_heupstream-NuS5LvNUpcJWk0Htik3J/w

MT2712 is a SoC based on 64bit ARMv8 architecture.
MT2712 share many HW IP with MT8173.  This patchset was tested on MT2712 evaluation board, and boot to shell ok.

This series contains document bindings, device tree including interrupt, uart.

Changes compared to v1:
- change subject prefix for bindings
- change device tree license to SPDX tag.
- change bootargs parameter to DT usage.
- change intpol-controller to interrupt-controller

YT Shen (2):
  dt-bindings: arm: Add bindings for Mediatek MT2712 SoC Platform
  arm64: dts: Add Mediatek SoC MT2712 and evaluation board dts and
    Makefile

 Documentation/devicetree/bindings/arm/mediatek.txt |   4 +
 .../interrupt-controller/mediatek,sysirq.txt       |   1 +
 .../devicetree/bindings/serial/mtk-uart.txt        |   1 +
 arch/arm64/boot/dts/mediatek/Makefile              |   1 +
 arch/arm64/boot/dts/mediatek/mt2712-evb.dts        |  39 +++++
 arch/arm64/boot/dts/mediatek/mt2712e.dtsi          | 166 +++++++++++++++++++++
 6 files changed, 212 insertions(+)
 create mode 100644 arch/arm64/boot/dts/mediatek/mt2712-evb.dts
 create mode 100644 arch/arm64/boot/dts/mediatek/mt2712e.dtsi

-- 
1.9.1

--
To unsubscribe from this list: send the line "unsubscribe devicetree" in
the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply

* Re: [GIT PULL] TTY/Serial driver fixes for 4.11-rc4
From: Greg KH @ 2017-05-31 11:16 UTC (permalink / raw)
  To: Dmitry Vyukov
  Cc: Alan Cox, Vegard Nossum, Linus Torvalds, Jiri Slaby,
	Andrew Morton, LKML, linux-serial
In-Reply-To: <CACT4Y+aoRRao41hGpVkO+qVk9TB5ZSPiRpQxp7H9EN+RqW-1-Q@mail.gmail.com>

On Wed, May 31, 2017 at 10:39:23AM +0200, Dmitry Vyukov wrote:
> On Tue, May 30, 2017 at 2:09 PM, Alan Cox <gnomes@lxorguk.ukuu.org.uk> wrote:
> >> >> I'll think about possible solutions, but I have no prior experience
> >> >> with the tty code. In the meantime syzkaller also hit a couple of
> >> >> other fun tty/pty bugs including a write/ioctl race that results in
> >> >> buffer overflow :-/
> >
> > There are several of those, including some of that have been documented
> > for years but nobody ever volunteered to fix - in particular all the
> > interfaces that push characters to the tty other than via the normal
> > interrupt receive path are dodgy (console selection in particular)
> >
> > The original tty model btw was that setting the ldisc to n_tty cannot
> > fail, and the structure allocated was smaller than a page size so was
> > safe.
> >
> > The simple way to fix it is to restore that behaviour by adding a 'null'
> > ldisc that we can fail to instead of N_TTY since the N_TTY failback path
> > is long broken.
> 
> Greg, what do you think about this patch? Are you ready to accept
> something like this?
> Definitely shorter than changing all drivers.

Yes, it looks reasonable to me.

^ permalink raw reply

* Re: [GIT PULL] TTY/Serial driver fixes for 4.11-rc4
From: Dmitry Vyukov @ 2017-05-31  8:39 UTC (permalink / raw)
  To: Alan Cox
  Cc: Greg KH, Vegard Nossum, Linus Torvalds, Jiri Slaby, Andrew Morton,
	LKML, linux-serial
In-Reply-To: <20170530130905.382487d5@alans-desktop>

On Tue, May 30, 2017 at 2:09 PM, Alan Cox <gnomes@lxorguk.ukuu.org.uk> wrote:
>> >> I'll think about possible solutions, but I have no prior experience
>> >> with the tty code. In the meantime syzkaller also hit a couple of
>> >> other fun tty/pty bugs including a write/ioctl race that results in
>> >> buffer overflow :-/
>
> There are several of those, including some of that have been documented
> for years but nobody ever volunteered to fix - in particular all the
> interfaces that push characters to the tty other than via the normal
> interrupt receive path are dodgy (console selection in particular)
>
> The original tty model btw was that setting the ldisc to n_tty cannot
> fail, and the structure allocated was smaller than a page size so was
> safe.
>
> The simple way to fix it is to restore that behaviour by adding a 'null'
> ldisc that we can fail to instead of N_TTY since the N_TTY failback path
> is long broken.

Greg, what do you think about this patch? Are you ready to accept
something like this?
Definitely shorter than changing all drivers.

> Something like this (untested)
>
> commit 797035eaf800889287b0b176a11c89c0f1fbba30
> Author: Alan Cox <alan@llwyncelyn.cymru>
> Date:   Tue May 30 12:59:45 2017 +0100
>
>     tty: handle the case where we cannot restore a line discipline
>
>     Historically the N_TTY driver could never fail but this has become broken over
>     time. Rather than trying to rewrite half the ldisc layer to fix the breakage
>     introduce a second level of fallback with an N_NULL ldisc which cannot fail,
>     and thus restore the guarantees required by the ldisc layer.
>
>     We still try and fail to N_TTY first. It's much more useful to find yourself
>     back in your old ldisc (first attempt) or in N_TTY (second attempt), and while
>     I'm not aware of any code out there that makes those assumptions it's good to
>     drive(r) defensively.
>
>     No signed off by: this is just a proposal!
>
> diff --git a/drivers/tty/n_null.c b/drivers/tty/n_null.c
> new file mode 100644
> index 0000000..c5812cd
> --- /dev/null
> +++ b/drivers/tty/n_null.c
> @@ -0,0 +1,67 @@
> +/*
> + *  n_null.c - Null line discipline used in the failure path
> + *
> + *  Copyright (C) Intel 2017
> + *
> + * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
> + *
> + *  This program is free software; you can redistribute it and/or modify
> + *  it under the terms of the GNU General Public License version 2
> + *  as published by the Free Software Foundation.
> + *
> + *  This program is distributed in the hope that it will be useful,
> + *  but WITHOUT ANY WARRANTY; without even the implied warranty of
> + *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
> + *  GNU General Public License for more details.
> + *
> + * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
> + */
> +
> +static int n_null_open(struct tty_struct *tty)
> +{
> +       return 0;
> +}
> +
> +static void n_null_close(struct tty_struct *tty)
> +{
> +}
> +
> +static ssize_t n_null_read(struct tty_struct *tty, struct file *file,
> +                          unsigned char __user * buf, size_t nr)
> +{
> +       return -EOPNOTSUPP;
> +}
> +
> +static ssize_t n_null_write(struct tty_struct *tty, struct file *file,
> +                           const unsigned char *buf, size_t nr)
> +{
> +       return -EOPNOTSUPP;
> +}
> +
> +static ssize_t n_null_receivebuf(struct tty_struct *tty,
> +                                const unsigned char *cp, char *fp,
> +                                int cnt)
> +{
> +}
> +
> +static struct tty_ldisc_ops null_ldisc {
> +       .owner          =       THIS_MODULE,
> +       .magic          =       TTY_LDISC_MAGIC,
> +       .name           =       "n_null",
> +       .open           =       n_null_open,
> +       .close          =       n_null_close,
> +       .read           =       n_null_read,
> +       .write          =       n_null_write,
> +       .receive_buf    =       n_null_receivebuf
> +};
> +
> +static int __init n_null_init(void)
> +{
> +       BUG_ON(tty_register_ldisc(N_NULL, &null_ldisc));
> +       return 0;
> +}
> +
> +static void __exit n_null_exit(void)
> +{
> +       tty_unregister_ldisc(N_NULL);
> +}
> diff --git a/drivers/tty/tty_ldisc.c b/drivers/tty/tty_ldisc.c
> index f6ffe28..e80e05f 100644
> --- a/drivers/tty/tty_ldisc.c
> +++ b/drivers/tty/tty_ldisc.c
> @@ -492,6 +492,29 @@ static void tty_ldisc_close(struct tty_struct *tty, struct tty_ldisc *ld)
>  }
>
>  /**
> + *     tty_ldisc_failto        -       helper for ldisc failback
> + *     @tty: tty to open the ldisc on
> + *     @ld: ldisc we are trying to fail back to
> + *
> + *     Helper to try and recover a tty when switching back to the old
> + *     ldisc fails and we need something attached.
> + */
> +
> +static int tty_ldisc_failto(struct tty_struct *tty, int ld)
> +{
> +       struct tty_ldisc *disc = tty_ldisc_get(tty, ld);
> +       int r;
> +
> +       if (IS_ERR(disc))
> +               return PTR_ERR(disc);
> +       tty->ldisc = disc;
> +       tty_set_termios_ldisc(tty, ld);
> +       if ((r = tty_ldisc_open(tty, disc)) < 0)
> +               tty_ldisc_put(ld);
> +       return r;
> +}
> +
> +/**
>   *     tty_ldisc_restore       -       helper for tty ldisc change
>   *     @tty: tty to recover
>   *     @old: previous ldisc
> @@ -512,15 +535,14 @@ static void tty_ldisc_restore(struct tty_struct *tty, struct tty_ldisc *old)
>         tty_set_termios_ldisc(tty, old->ops->num);
>         if (tty_ldisc_open(tty, old) < 0) {
>                 tty_ldisc_put(old);
> -               /* This driver is always present */
> -               new_ldisc = tty_ldisc_get(tty, N_TTY);
> -               if (IS_ERR(new_ldisc))
> -                       panic("n_tty: get");
> -               tty->ldisc = new_ldisc;
> -               tty_set_termios_ldisc(tty, N_TTY);
> -               r = tty_ldisc_open(tty, new_ldisc);
> +               /* The traditional behaviour is to fall back to N_TTY, we
> +                  want to avoid falling back to N_NULL unless we have no
> +                  choice to avoid the risk of breaking anything */
> +               if (tty_ldisc_failto(tty, N_TTY) < 0 &&
> +                   tty_ldisc_failto(tty, N_NULL) < 0)
> +               /* Fall back to null ldisc */
>                 if (r < 0)
> -                       panic("Couldn't open N_TTY ldisc for "
> +                       panic("Couldn't open N_NULL ldisc for "
>                               "%s --- error %d.",
>                               tty_name(tty), r);
>         }
> diff --git a/include/uapi/linux/tty.h b/include/uapi/linux/tty.h
> index e7855df..cf14553 100644
> --- a/include/uapi/linux/tty.h
> +++ b/include/uapi/linux/tty.h
> @@ -36,5 +36,6 @@
>  #define N_TRACEROUTER  24      /* Trace data routing for MIPI P1149.7 */
>  #define N_NCI          25      /* NFC NCI UART */
>  #define N_SPEAKUP      26      /* Speakup communication with synths */
> +#define N_NULL         27      /* Null ldisc used for error handling */
>
>  #endif /* _UAPI_LINUX_TTY_H */

^ permalink raw reply


This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox