All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH 2/8] power: add power sequence library
From: Peter Chen @ 2017-01-03  6:33 UTC (permalink / raw)
  To: gregkh, stern, ulf.hansson, broonie, sre, robh+dt, shawnguo, rjw,
	dbaryshkov
  Cc: heiko, linux-arm-kernel, p.zabel, devicetree, pawel.moll,
	mark.rutland, linux-usb, arnd, s.hauer, mail, troy.kisky,
	festevam, oscar, stephen.boyd, linux-pm, stillcompiling,
	linux-kernel, mka, vaibhav.hiremath, gary.bisson, hverkuil, krzk,
	Peter Chen
In-Reply-To: <1483425211-14473-1-git-send-email-peter.chen@nxp.com>

We have an well-known problem that the device needs to do some power
sequence before it can be recognized by related host, the typical
example like hard-wired mmc devices and usb devices.

This power sequence is hard to be described at device tree and handled by
related host driver, so we have created a common power sequence
library to cover this requirement. The core code has supplied
some common helpers for host driver, and individual power sequence
libraries handle kinds of power sequence for devices. The pwrseq
librares always need to allocate extra instance for compatible
string match.

pwrseq_generic is intended for general purpose of power sequence, which
handles gpios and clocks currently, and can cover other controls in
future. The host driver just needs to call of_pwrseq_on/of_pwrseq_off
if only one power sequence is needed, else call of_pwrseq_on_list
/of_pwrseq_off_list instead (eg, USB hub driver).

For new power sequence library, it can add its compatible string
to pwrseq_of_match_table, then the pwrseq core will match it with
DT's, and choose this library at runtime.

Signed-off-by: Peter Chen <peter.chen@nxp.com>
Tested-by: Maciej S. Szmigiero <mail@maciej.szmigiero.name>
Tested-by Joshua Clayton <stillcompiling@gmail.com>
Reviewed-by: Matthias Kaehlcke <mka@chromium.org>
Tested-by: Matthias Kaehlcke <mka@chromium.org>
---
 MAINTAINERS                           |   9 +
 drivers/power/Kconfig                 |   1 +
 drivers/power/Makefile                |   1 +
 drivers/power/pwrseq/Kconfig          |  20 ++
 drivers/power/pwrseq/Makefile         |   2 +
 drivers/power/pwrseq/core.c           | 335 ++++++++++++++++++++++++++++++++++
 drivers/power/pwrseq/pwrseq_generic.c | 224 +++++++++++++++++++++++
 include/linux/power/pwrseq.h          |  81 ++++++++
 8 files changed, 673 insertions(+)
 create mode 100644 drivers/power/pwrseq/Kconfig
 create mode 100644 drivers/power/pwrseq/Makefile
 create mode 100644 drivers/power/pwrseq/core.c
 create mode 100644 drivers/power/pwrseq/pwrseq_generic.c
 create mode 100644 include/linux/power/pwrseq.h

diff --git a/MAINTAINERS b/MAINTAINERS
index cfff2c9..ae2aa25 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -9828,6 +9828,15 @@ F:	include/linux/pm_*
 F:	include/linux/powercap.h
 F:	drivers/powercap/
 
+POWER SEQUENCE LIBRARY
+M:	Peter Chen <Peter.Chen@nxp.com>
+T:	git git://git.kernel.org/pub/scm/linux/kernel/git/peter.chen/usb.git
+L:	linux-pm@vger.kernel.org
+S:	Maintained
+F:	Documentation/devicetree/bindings/power/pwrseq/
+F:	drivers/power/pwrseq/
+F:	include/linux/power/pwrseq.h
+
 POWER SUPPLY CLASS/SUBSYSTEM and DRIVERS
 M:	Sebastian Reichel <sre@kernel.org>
 L:	linux-pm@vger.kernel.org
diff --git a/drivers/power/Kconfig b/drivers/power/Kconfig
index 63454b5..c1bb046 100644
--- a/drivers/power/Kconfig
+++ b/drivers/power/Kconfig
@@ -1,3 +1,4 @@
 source "drivers/power/avs/Kconfig"
 source "drivers/power/reset/Kconfig"
 source "drivers/power/supply/Kconfig"
+source "drivers/power/pwrseq/Kconfig"
diff --git a/drivers/power/Makefile b/drivers/power/Makefile
index ff35c71..7db8035 100644
--- a/drivers/power/Makefile
+++ b/drivers/power/Makefile
@@ -1,3 +1,4 @@
 obj-$(CONFIG_POWER_AVS)		+= avs/
 obj-$(CONFIG_POWER_RESET)	+= reset/
 obj-$(CONFIG_POWER_SUPPLY)	+= supply/
+obj-$(CONFIG_POWER_SEQUENCE)	+= pwrseq/
diff --git a/drivers/power/pwrseq/Kconfig b/drivers/power/pwrseq/Kconfig
new file mode 100644
index 0000000..c6b3569
--- /dev/null
+++ b/drivers/power/pwrseq/Kconfig
@@ -0,0 +1,20 @@
+#
+# Power Sequence library
+#
+
+menuconfig POWER_SEQUENCE
+	bool "Power sequence control"
+	help
+	   It is used for drivers which needs to do power sequence
+	   (eg, turn on clock, toggle reset gpio) before the related
+	   devices can be found by hardware, eg, USB bus.
+
+if POWER_SEQUENCE
+
+config PWRSEQ_GENERIC
+	bool "Generic power sequence control"
+	depends on OF
+	help
+	   This is the generic power sequence control library, and is
+	   supposed to support common power sequence usage.
+endif
diff --git a/drivers/power/pwrseq/Makefile b/drivers/power/pwrseq/Makefile
new file mode 100644
index 0000000..ad82389
--- /dev/null
+++ b/drivers/power/pwrseq/Makefile
@@ -0,0 +1,2 @@
+obj-$(CONFIG_POWER_SEQUENCE) += core.o
+obj-$(CONFIG_PWRSEQ_GENERIC) += pwrseq_generic.o
diff --git a/drivers/power/pwrseq/core.c b/drivers/power/pwrseq/core.c
new file mode 100644
index 0000000..3d19e62
--- /dev/null
+++ b/drivers/power/pwrseq/core.c
@@ -0,0 +1,335 @@
+/*
+ * core.c	power sequence core file
+ *
+ * Copyright (C) 2016 Freescale Semiconductor, Inc.
+ * Author: Peter Chen <peter.chen@nxp.com>
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2  of
+ * the License 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.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program.
+ */
+
+#include <linux/list.h>
+#include <linux/mutex.h>
+#include <linux/of.h>
+#include <linux/slab.h>
+#include <linux/power/pwrseq.h>
+
+static DEFINE_MUTEX(pwrseq_list_mutex);
+static LIST_HEAD(pwrseq_list);
+
+static int pwrseq_get(struct device_node *np, struct pwrseq *p)
+{
+	if (p && p->get)
+		return p->get(np, p);
+
+	return -ENOTSUPP;
+}
+
+static int pwrseq_on(struct pwrseq *p)
+{
+	if (p && p->on)
+		return p->on(p);
+
+	return -ENOTSUPP;
+}
+
+static void pwrseq_off(struct pwrseq *p)
+{
+	if (p && p->off)
+		p->off(p);
+}
+
+static void pwrseq_put(struct pwrseq *p)
+{
+	if (p && p->put)
+		p->put(p);
+}
+
+/**
+ * pwrseq_register - Add pwrseq instance to global pwrseq list
+ *
+ * @pwrseq: the pwrseq instance
+ */
+void pwrseq_register(struct pwrseq *pwrseq)
+{
+	mutex_lock(&pwrseq_list_mutex);
+	list_add(&pwrseq->node, &pwrseq_list);
+	mutex_unlock(&pwrseq_list_mutex);
+}
+EXPORT_SYMBOL_GPL(pwrseq_register);
+
+/**
+ * pwrseq_unregister - Remove pwrseq instance from global pwrseq list
+ *
+ * @pwrseq: the pwrseq instance
+ */
+void pwrseq_unregister(struct pwrseq *pwrseq)
+{
+	mutex_lock(&pwrseq_list_mutex);
+	list_del(&pwrseq->node);
+	mutex_unlock(&pwrseq_list_mutex);
+}
+EXPORT_SYMBOL_GPL(pwrseq_unregister);
+
+static struct pwrseq *pwrseq_find_available_instance(struct device_node *np)
+{
+	struct pwrseq *pwrseq;
+
+	mutex_lock(&pwrseq_list_mutex);
+	list_for_each_entry(pwrseq, &pwrseq_list, node) {
+		if (pwrseq->used)
+			continue;
+
+		/* compare compatible string for pwrseq node */
+		if (of_match_node(pwrseq->pwrseq_of_match_table, np)) {
+			pwrseq->used = true;
+			mutex_unlock(&pwrseq_list_mutex);
+			return pwrseq;
+		}
+
+		/* return generic pwrseq instance */
+		if (!strcmp(pwrseq->pwrseq_of_match_table->compatible,
+				"generic")) {
+			pr_debug("using generic pwrseq instance for %s\n",
+				np->full_name);
+			pwrseq->used = true;
+			mutex_unlock(&pwrseq_list_mutex);
+			return pwrseq;
+		}
+	}
+	mutex_unlock(&pwrseq_list_mutex);
+	pr_debug("Can't find any pwrseq instances for %s\n", np->full_name);
+
+	return NULL;
+}
+
+/**
+ * of_pwrseq_on - Carry out power sequence on for device node
+ *
+ * @np: the device node would like to power on
+ *
+ * Carry out a single device power on.  If multiple devices
+ * need to be handled, use of_pwrseq_on_list() instead.
+ *
+ * Return a pointer to the power sequence instance on success,
+ * or an error code otherwise.
+ */
+struct pwrseq *of_pwrseq_on(struct device_node *np)
+{
+	struct pwrseq *pwrseq;
+	int ret;
+
+	pwrseq = pwrseq_find_available_instance(np);
+	if (!pwrseq)
+		return ERR_PTR(-ENOENT);
+
+	ret = pwrseq_get(np, pwrseq);
+	if (ret) {
+		/* Mark current pwrseq as unused */
+		pwrseq->used = false;
+		return ERR_PTR(ret);
+	}
+
+	ret = pwrseq_on(pwrseq);
+	if (ret)
+		goto pwr_put;
+
+	return pwrseq;
+
+pwr_put:
+	pwrseq_put(pwrseq);
+	return ERR_PTR(ret);
+}
+EXPORT_SYMBOL_GPL(of_pwrseq_on);
+
+/**
+ * of_pwrseq_off - Carry out power sequence off for this pwrseq instance
+ *
+ * @pwrseq: the pwrseq instance which related device would like to be off
+ *
+ * This API is used to power off single device, it is the opposite
+ * operation for of_pwrseq_on.
+ */
+void of_pwrseq_off(struct pwrseq *pwrseq)
+{
+	pwrseq_off(pwrseq);
+	pwrseq_put(pwrseq);
+}
+EXPORT_SYMBOL_GPL(of_pwrseq_off);
+
+/**
+ * of_pwrseq_on_list - Carry out power sequence on for list
+ *
+ * @np: the device node would like to power on
+ * @head: the list head for pwrseq list on this bus
+ *
+ * This API is used to power on multiple devices at single bus.
+ * If there are several devices on bus (eg, USB bus), uses this
+ * this API. Otherwise, use of_pwrseq_on instead. After the device
+ * is powered on successfully, it will be added to pwrseq list for
+ * this bus. The caller needs to use mutex_lock for concurrent.
+ *
+ * Return 0 on success, or an error value otherwise.
+ */
+int of_pwrseq_on_list(struct device_node *np, struct list_head *head)
+{
+	struct pwrseq *pwrseq;
+	struct pwrseq_list_per_dev *pwrseq_list_node;
+
+	pwrseq_list_node = kzalloc(sizeof(*pwrseq_list_node), GFP_KERNEL);
+	if (!pwrseq_list_node)
+		return -ENOMEM;
+
+	pwrseq = of_pwrseq_on(np);
+	if (IS_ERR(pwrseq)) {
+		kfree(pwrseq_list_node);
+		return PTR_ERR(pwrseq);
+	}
+
+	pwrseq_list_node->pwrseq = pwrseq;
+	list_add(&pwrseq_list_node->list, head);
+
+	return 0;
+}
+EXPORT_SYMBOL_GPL(of_pwrseq_on_list);
+
+/**
+ * of_pwrseq_off_list - Carry out power sequence off for the list
+ *
+ * @head: the list head for pwrseq instance list on this bus
+ *
+ * This API is used to power off all devices on this bus, it is
+ * the opposite operation for of_pwrseq_on_list.
+ * The caller needs to use mutex_lock for concurrent.
+ */
+void of_pwrseq_off_list(struct list_head *head)
+{
+	struct pwrseq *pwrseq;
+	struct pwrseq_list_per_dev *pwrseq_list_node, *tmp_node;
+
+	list_for_each_entry_safe(pwrseq_list_node, tmp_node, head, list) {
+		pwrseq = pwrseq_list_node->pwrseq;
+		of_pwrseq_off(pwrseq);
+		list_del(&pwrseq_list_node->list);
+		kfree(pwrseq_list_node);
+	}
+}
+EXPORT_SYMBOL_GPL(of_pwrseq_off_list);
+
+/**
+ * pwrseq_suspend - Carry out power sequence suspend for this pwrseq instance
+ *
+ * @pwrseq: the pwrseq instance
+ *
+ * This API is used to do suspend operation on pwrseq instance.
+ *
+ * Return 0 on success, or an error value otherwise.
+ */
+int pwrseq_suspend(struct pwrseq *p)
+{
+	int ret = 0;
+
+	if (p && p->suspend)
+		ret = p->suspend(p);
+	else
+		return ret;
+
+	if (!ret)
+		p->suspended = true;
+	else
+		pr_err("%s failed\n", __func__);
+
+	return ret;
+}
+EXPORT_SYMBOL_GPL(pwrseq_suspend);
+
+/**
+ * pwrseq_resume - Carry out power sequence resume for this pwrseq instance
+ *
+ * @pwrseq: the pwrseq instance
+ *
+ * This API is used to do resume operation on pwrseq instance.
+ *
+ * Return 0 on success, or an error value otherwise.
+ */
+int pwrseq_resume(struct pwrseq *p)
+{
+	int ret = 0;
+
+	if (p && p->resume)
+		ret = p->resume(p);
+	else
+		return ret;
+
+	if (!ret)
+		p->suspended = false;
+	else
+		pr_err("%s failed\n", __func__);
+
+	return ret;
+}
+EXPORT_SYMBOL_GPL(pwrseq_resume);
+
+/**
+ * pwrseq_suspend_list - Carry out power sequence suspend for list
+ *
+ * @head: the list head for pwrseq instance list on this bus
+ *
+ * This API is used to do suspend on all power sequence instances on this bus.
+ * The caller needs to use mutex_lock for concurrent.
+ */
+int pwrseq_suspend_list(struct list_head *head)
+{
+	struct pwrseq *pwrseq;
+	struct pwrseq_list_per_dev *pwrseq_list_node;
+	int ret = 0;
+
+	list_for_each_entry(pwrseq_list_node, head, list) {
+		ret = pwrseq_suspend(pwrseq_list_node->pwrseq);
+		if (ret)
+			break;
+	}
+
+	if (ret) {
+		list_for_each_entry(pwrseq_list_node, head, list) {
+			pwrseq = pwrseq_list_node->pwrseq;
+			if (pwrseq->suspended)
+				pwrseq_resume(pwrseq);
+		}
+	}
+
+	return ret;
+}
+EXPORT_SYMBOL_GPL(pwrseq_suspend_list);
+
+/**
+ * pwrseq_resume_list - Carry out power sequence resume for the list
+ *
+ * @head: the list head for pwrseq instance list on this bus
+ *
+ * This API is used to do resume on all power sequence instances on this bus.
+ * The caller needs to use mutex_lock for concurrent.
+ */
+int pwrseq_resume_list(struct list_head *head)
+{
+	struct pwrseq_list_per_dev *pwrseq_list_node;
+	int ret = 0;
+
+	list_for_each_entry(pwrseq_list_node, head, list) {
+		ret = pwrseq_resume(pwrseq_list_node->pwrseq);
+		if (ret)
+			break;
+	}
+
+	return ret;
+}
+EXPORT_SYMBOL_GPL(pwrseq_resume_list);
diff --git a/drivers/power/pwrseq/pwrseq_generic.c b/drivers/power/pwrseq/pwrseq_generic.c
new file mode 100644
index 0000000..0e70a38
--- /dev/null
+++ b/drivers/power/pwrseq/pwrseq_generic.c
@@ -0,0 +1,224 @@
+/*
+ * pwrseq_generic.c	Generic power sequence handling
+ *
+ * Copyright (C) 2016 Freescale Semiconductor, Inc.
+ * Author: Peter Chen <peter.chen@nxp.com>
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2  of
+ * the License 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.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program.
+ */
+
+#include <linux/clk.h>
+#include <linux/delay.h>
+#include <linux/gpio.h>
+#include <linux/gpio/consumer.h>
+#include <linux/of.h>
+#include <linux/of_gpio.h>
+#include <linux/slab.h>
+
+#include <linux/power/pwrseq.h>
+
+struct pwrseq_generic {
+	struct pwrseq pwrseq;
+	struct gpio_desc *gpiod_reset;
+	struct clk *clks[PWRSEQ_MAX_CLKS];
+	u32 duration_us;
+	bool suspended;
+};
+
+#define to_generic_pwrseq(p) container_of(p, struct pwrseq_generic, pwrseq)
+
+static int pwrseq_generic_alloc_instance(void);
+static const struct of_device_id generic_id_table[] = {
+	{ .compatible = "generic",},
+	{ /* sentinel */ }
+};
+
+static int pwrseq_generic_suspend(struct pwrseq *pwrseq)
+{
+	struct pwrseq_generic *pwrseq_gen = to_generic_pwrseq(pwrseq);
+	int clk;
+
+	for (clk = PWRSEQ_MAX_CLKS - 1; clk >= 0; clk--)
+		clk_disable_unprepare(pwrseq_gen->clks[clk]);
+
+	pwrseq_gen->suspended = true;
+	return 0;
+}
+
+static int pwrseq_generic_resume(struct pwrseq *pwrseq)
+{
+	struct pwrseq_generic *pwrseq_gen = to_generic_pwrseq(pwrseq);
+	int clk, ret = 0;
+
+	for (clk = 0; clk < PWRSEQ_MAX_CLKS && pwrseq_gen->clks[clk]; clk++) {
+		ret = clk_prepare_enable(pwrseq_gen->clks[clk]);
+		if (ret) {
+			pr_err("Can't enable clock, ret=%d\n", ret);
+			goto err_disable_clks;
+		}
+	}
+
+	pwrseq_gen->suspended = false;
+	return ret;
+
+err_disable_clks:
+	while (--clk >= 0)
+		clk_disable_unprepare(pwrseq_gen->clks[clk]);
+
+	return ret;
+}
+
+static void pwrseq_generic_put(struct pwrseq *pwrseq)
+{
+	struct pwrseq_generic *pwrseq_gen = to_generic_pwrseq(pwrseq);
+	int clk;
+
+	if (pwrseq_gen->gpiod_reset)
+		gpiod_put(pwrseq_gen->gpiod_reset);
+
+	for (clk = 0; clk < PWRSEQ_MAX_CLKS; clk++)
+		clk_put(pwrseq_gen->clks[clk]);
+
+	pwrseq_unregister(&pwrseq_gen->pwrseq);
+	kfree(pwrseq_gen);
+}
+
+static void pwrseq_generic_off(struct pwrseq *pwrseq)
+{
+	struct pwrseq_generic *pwrseq_gen = to_generic_pwrseq(pwrseq);
+	int clk;
+
+	if (pwrseq_gen->suspended)
+		return;
+
+	for (clk = PWRSEQ_MAX_CLKS - 1; clk >= 0; clk--)
+		clk_disable_unprepare(pwrseq_gen->clks[clk]);
+}
+
+static int pwrseq_generic_on(struct pwrseq *pwrseq)
+{
+	struct pwrseq_generic *pwrseq_gen = to_generic_pwrseq(pwrseq);
+	int clk, ret = 0;
+	struct gpio_desc *gpiod_reset = pwrseq_gen->gpiod_reset;
+
+	for (clk = 0; clk < PWRSEQ_MAX_CLKS && pwrseq_gen->clks[clk]; clk++) {
+		ret = clk_prepare_enable(pwrseq_gen->clks[clk]);
+		if (ret) {
+			pr_err("Can't enable clock, ret=%d\n", ret);
+			goto err_disable_clks;
+		}
+	}
+
+	if (gpiod_reset) {
+		u32 duration_us = pwrseq_gen->duration_us;
+
+		if (duration_us <= 10)
+			udelay(10);
+		else
+			usleep_range(duration_us, duration_us + 100);
+		gpiod_set_value(gpiod_reset, 0);
+	}
+
+	return ret;
+
+err_disable_clks:
+	while (--clk >= 0)
+		clk_disable_unprepare(pwrseq_gen->clks[clk]);
+
+	return ret;
+}
+
+static int pwrseq_generic_get(struct device_node *np, struct pwrseq *pwrseq)
+{
+	struct pwrseq_generic *pwrseq_gen = to_generic_pwrseq(pwrseq);
+	enum of_gpio_flags flags;
+	int reset_gpio, clk, ret = 0;
+
+	for (clk = 0; clk < PWRSEQ_MAX_CLKS; clk++) {
+		pwrseq_gen->clks[clk] = of_clk_get(np, clk);
+		if (IS_ERR(pwrseq_gen->clks[clk])) {
+			ret = PTR_ERR(pwrseq_gen->clks[clk]);
+			if (ret != -ENOENT)
+				goto err_put_clks;
+			pwrseq_gen->clks[clk] = NULL;
+			break;
+		}
+	}
+
+	reset_gpio = of_get_named_gpio_flags(np, "reset-gpios", 0, &flags);
+	if (gpio_is_valid(reset_gpio)) {
+		unsigned long gpio_flags;
+
+		if (flags & OF_GPIO_ACTIVE_LOW)
+			gpio_flags = GPIOF_ACTIVE_LOW | GPIOF_OUT_INIT_LOW;
+		else
+			gpio_flags = GPIOF_OUT_INIT_HIGH;
+
+		ret = gpio_request_one(reset_gpio, gpio_flags,
+				"pwrseq-reset-gpios");
+		if (ret)
+			goto err_put_clks;
+
+		pwrseq_gen->gpiod_reset = gpio_to_desc(reset_gpio);
+		of_property_read_u32(np, "reset-duration-us",
+				&pwrseq_gen->duration_us);
+	} else if (reset_gpio == -ENOENT) {
+		; /* no such gpio */
+	} else {
+		ret = reset_gpio;
+		pr_err("Failed to get reset gpio on %s, err = %d\n",
+				np->full_name, reset_gpio);
+		goto err_put_clks;
+	}
+
+	/* allocate new one for later pwrseq instance request */
+	ret = pwrseq_generic_alloc_instance();
+	if (ret)
+		goto err_put_gpio;
+
+	return 0;
+
+err_put_gpio:
+	if (pwrseq_gen->gpiod_reset)
+		gpiod_put(pwrseq_gen->gpiod_reset);
+err_put_clks:
+	while (--clk >= 0)
+		clk_put(pwrseq_gen->clks[clk]);
+	return ret;
+}
+
+static int pwrseq_generic_alloc_instance(void)
+{
+	struct pwrseq_generic *pwrseq_gen;
+
+	pwrseq_gen = kzalloc(sizeof(*pwrseq_gen), GFP_KERNEL);
+	if (!pwrseq_gen)
+		return -ENOMEM;
+
+	pwrseq_gen->pwrseq.pwrseq_of_match_table = generic_id_table;
+	pwrseq_gen->pwrseq.get = pwrseq_generic_get;
+	pwrseq_gen->pwrseq.on = pwrseq_generic_on;
+	pwrseq_gen->pwrseq.off = pwrseq_generic_off;
+	pwrseq_gen->pwrseq.put = pwrseq_generic_put;
+	pwrseq_gen->pwrseq.suspend = pwrseq_generic_suspend;
+	pwrseq_gen->pwrseq.resume = pwrseq_generic_resume;
+
+	pwrseq_register(&pwrseq_gen->pwrseq);
+	return 0;
+}
+
+static int __init pwrseq_generic_register(void)
+{
+	return pwrseq_generic_alloc_instance();
+}
+postcore_initcall(pwrseq_generic_register)
diff --git a/include/linux/power/pwrseq.h b/include/linux/power/pwrseq.h
new file mode 100644
index 0000000..cbc344c
--- /dev/null
+++ b/include/linux/power/pwrseq.h
@@ -0,0 +1,81 @@
+#ifndef __LINUX_PWRSEQ_H
+#define __LINUX_PWRSEQ_H
+
+#include <linux/of.h>
+
+#define PWRSEQ_MAX_CLKS		3
+
+/**
+ * struct pwrseq - the power sequence structure
+ * @pwrseq_of_match_table: the OF device id table this pwrseq library supports
+ * @node: the list pointer to be added to pwrseq list
+ * @get: the API is used to get pwrseq instance from the device node
+ * @on: do power on for this pwrseq instance
+ * @off: do power off for this pwrseq instance
+ * @put: release the resources on this pwrseq instance
+ * @suspend: do suspend operation on this pwrseq instance
+ * @resume: do resume operation on this pwrseq instance
+ * @used: this pwrseq instance is used by device
+ */
+struct pwrseq {
+	const struct of_device_id *pwrseq_of_match_table;
+	struct list_head node;
+	int (*get)(struct device_node *np, struct pwrseq *p);
+	int (*on)(struct pwrseq *p);
+	void (*off)(struct pwrseq *p);
+	void (*put)(struct pwrseq *p);
+	int (*suspend)(struct pwrseq *p);
+	int (*resume)(struct pwrseq *p);
+	bool used;
+	bool suspended;
+};
+
+/* used for power sequence instance list in one driver */
+struct pwrseq_list_per_dev {
+	struct pwrseq *pwrseq;
+	struct list_head list;
+};
+
+#if IS_ENABLED(CONFIG_POWER_SEQUENCE)
+void pwrseq_register(struct pwrseq *pwrseq);
+void pwrseq_unregister(struct pwrseq *pwrseq);
+struct pwrseq *of_pwrseq_on(struct device_node *np);
+void of_pwrseq_off(struct pwrseq *pwrseq);
+int of_pwrseq_on_list(struct device_node *np, struct list_head *head);
+void of_pwrseq_off_list(struct list_head *head);
+int pwrseq_suspend(struct pwrseq *p);
+int pwrseq_resume(struct pwrseq *p);
+int pwrseq_suspend_list(struct list_head *head);
+int pwrseq_resume_list(struct list_head *head);
+#else
+static inline void pwrseq_register(struct pwrseq *pwrseq) {}
+static inline void pwrseq_unregister(struct pwrseq *pwrseq) {}
+static inline struct pwrseq *of_pwrseq_on(struct device_node *np)
+{
+	return NULL;
+}
+static void of_pwrseq_off(struct pwrseq *pwrseq) {}
+static int of_pwrseq_on_list(struct device_node *np, struct list_head *head)
+{
+	return 0;
+}
+static void of_pwrseq_off_list(struct list_head *head) {}
+static int pwrseq_suspend(struct pwrseq *p)
+{
+	return 0;
+}
+static int pwrseq_resume(struct pwrseq *p)
+{
+	return 0;
+}
+static int pwrseq_suspend_list(struct list_head *head)
+{
+	return 0;
+}
+static int pwrseq_resume_list(struct list_head *head)
+{
+	return 0;
+}
+#endif /* CONFIG_POWER_SEQUENCE */
+
+#endif  /* __LINUX_PWRSEQ_H */
-- 
2.7.4


^ permalink raw reply related

* [PATCH 0/8] power: add power sequence library
From: Peter Chen @ 2017-01-03  6:33 UTC (permalink / raw)
  To: gregkh, stern, ulf.hansson, broonie, sre, robh+dt, shawnguo, rjw,
	dbaryshkov
  Cc: heiko, linux-arm-kernel, p.zabel, devicetree, pawel.moll,
	mark.rutland, linux-usb, arnd, s.hauer, mail, troy.kisky,
	festevam, oscar, stephen.boyd, linux-pm, stillcompiling,
	linux-kernel, mka, vaibhav.hiremath, gary.bisson, hverkuil, krzk,
	Peter Chen

Hi all,

This is a follow-up for my last power sequence framework patch set [1].
According to Rob Herring and Ulf Hansson's comments[2]. The kinds of
power sequence instances will be added at postcore_initcall, the match
criteria is compatible string first, if the compatible string is not
matched between dts and library, it will try to use generic power sequence.
	 
The host driver just needs to call of_pwrseq_on/of_pwrseq_off
if only one power sequence instance is needed, for more power sequences
are used, using of_pwrseq_on_list/of_pwrseq_off_list instead (eg, USB hub driver).

In future, if there are special power sequence requirements, the special
power sequence library can be created.

This patch set is tested on i.mx6 sabresx evk using a dts change, I use
two hot-plug devices to simulate this use case, the related binding
change is updated at patch [1/6], The udoo board changes were tested
using my last power sequence patch set.[3]

Except for hard-wired MMC and USB devices, I find the USB ULPI PHY also
need to power on itself before it can be found by ULPI bus.

[1] http://www.spinics.net/lists/linux-usb/msg142755.html
[2] http://www.spinics.net/lists/linux-usb/msg143106.html
[3] http://www.spinics.net/lists/linux-usb/msg142815.html

Changes for v11:
- Fix warning: (USB) selects POWER_SEQUENCE which has unmet direct dependencies (OF)
- Delete redundant copyright statement.
- Change pr_warn to pr_debug at wrseq_find_available_instance
- Refine kerneldoc
- %s/ENONET/ENOENT 
- Allocate pwrseq list node before than carry out power sequence on 
- Add mutex_lock/mutex_lock for pwrseq node browse at pwrseq_find_available_instance
- Add pwrseq_suspend/resume for API both single instance and list 
- Add .pwrseq_suspend/resume for pwrseq_generic.c
- Add pwrseq_suspend_list and pwrseq_resume_list for USB hub suspend
  and resume routine

Changes for v10:
- Improve the kernel-doc for power sequence core, including exported APIs and
  main structure. [Patch 2/8]
- Change Kconfig, and let the user choose power sequence. [Patch 2/8]
- Delete EXPORT_SYMBOL and change related APIs as local, these APIs do not
  be intended to export currently. [Patch 2/8]
- Selete POWER_SEQUENCE at USB core's Kconfig. [Patch 4/8]

Changes for v9:
- Add Vaibhav Hiremath's reviewed-by [Patch 4/8]
- Rebase to v4.9-rc1

Changes for v8:
- Allocate one extra pwrseq instance if pwrseq_get has succeed, it can avoid
  preallocate instances problem which the number of instance is decided at
  compile time, thanks for Heiko Stuebner's suggestion [Patch 2/8]
- Delete pwrseq_compatible_sample.c which is the demo purpose to show compatible
  match method. [Patch 2/8]
- Add Maciej S. Szmigiero's tested-by. [Patch 7/8]

Changes for v7:
- Create kinds of power sequence instance at postcore_initcall, and match
  the instance with node using compatible string, the beneit of this is
  the host driver doesn't need to consider which pwrseq instance needs
  to be used, and pwrseq core will match it, however, it eats some memories
  if less power sequence instances are used. [Patch 2/8]
- Add pwrseq_compatible_sample.c to test match pwrseq using device_id. [Patch 2/8]
- Fix the comments Vaibhav Hiremath adds for error path for clock and do not
  use device_node for parameters at pwrseq_on. [Patch 2/8]
- Simplify the caller to use power sequence, follows Alan's commnets [Patch 4/8]
- Tested three pwrseq instances together using both specific compatible string and
  generic libraries.

Changes for v6:
- Add Matthias Kaehlcke's Reviewed-by and Tested-by. (patch [2/6])
- Change chipidea core of_node assignment for coming user. (patch [5/6])
- Applies Joshua Clayton's three dts changes for two boards,
  the USB device's reg has only #address-cells, but without #size-cells.

Changes for v5:
- Delete pwrseq_register/pwrseq_unregister, which is useless currently
- Fix the linker error when the pwrseq user is compiled as module

Changes for v4:
- Create the patch on next-20160722 
- Fix the of_node is not NULL after chipidea driver is unbinded [Patch 5/6]
- Using more friendly wait method for reset gpio [Patch 2/6]
- Support multiple input clocks [Patch 2/6]
- Add Rob Herring's ack for DT changes
- Add Joshua Clayton's Tested-by

Changes for v3:
- Delete "power-sequence" property at binding-doc, and change related code
  at both library and user code.
- Change binding-doc example node name with Rob's comments
- of_get_named_gpio_flags only gets the gpio, but without setting gpio flags,
  add additional code request gpio with proper gpio flags
- Add Philipp Zabel's Ack and MAINTAINER's entry

Changes for v2:
- Delete "pwrseq" prefix and clock-names for properties at dt binding
- Should use structure not but its pointer for kzalloc
- Since chipidea core has no of_node, let core's of_node equals glue
  layer's at core's probe

Joshua Clayton (2):
  ARM: dts: imx6qdl: Enable usb node children with <reg>
  ARM: dts: imx6q-evi: Fix onboard hub reset line

Peter Chen (6):
  binding-doc: power: pwrseq-generic: add binding doc for generic power
    sequence library
  power: add power sequence library
  binding-doc: usb: usb-device: add optional properties for power
    sequence
  usb: core: add power sequence handling for USB devices
  usb: chipidea: let chipidea core device of_node equal's glue layer
    device of_node
  ARM: dts: imx6qdl-udoo.dtsi: fix onboard USB HUB property

 .../bindings/power/pwrseq/pwrseq-generic.txt       |  48 +++
 .../devicetree/bindings/usb/usb-device.txt         |  10 +-
 MAINTAINERS                                        |   9 +
 arch/arm/boot/dts/imx6q-evi.dts                    |  25 +-
 arch/arm/boot/dts/imx6qdl-udoo.dtsi                |  26 +-
 arch/arm/boot/dts/imx6qdl.dtsi                     |   6 +
 drivers/power/Kconfig                              |   1 +
 drivers/power/Makefile                             |   1 +
 drivers/power/pwrseq/Kconfig                       |  20 ++
 drivers/power/pwrseq/Makefile                      |   2 +
 drivers/power/pwrseq/core.c                        | 335 +++++++++++++++++++++
 drivers/power/pwrseq/pwrseq_generic.c              | 224 ++++++++++++++
 drivers/usb/Kconfig                                |   1 +
 drivers/usb/chipidea/core.c                        |  27 +-
 drivers/usb/core/hub.c                             |  48 ++-
 drivers/usb/core/hub.h                             |   1 +
 include/linux/power/pwrseq.h                       |  81 +++++
 17 files changed, 823 insertions(+), 42 deletions(-)
 create mode 100644 Documentation/devicetree/bindings/power/pwrseq/pwrseq-generic.txt
 create mode 100644 drivers/power/pwrseq/Kconfig
 create mode 100644 drivers/power/pwrseq/Makefile
 create mode 100644 drivers/power/pwrseq/core.c
 create mode 100644 drivers/power/pwrseq/pwrseq_generic.c
 create mode 100644 include/linux/power/pwrseq.h

-- 
2.7.4

^ permalink raw reply

* RE:FW : Aluminum gravity die casting
From: Bob @ 2017-01-03  6:36 UTC (permalink / raw)
  To: linux-kernel

Hello, 

We are the specialized manufacturer of aluminum casting in China with advantages as follows: 
1. All kinds of casting processes: die casting, sand casting, gravity premanent mold casting to meet your different demand. 
2. 17 years experience only dedicated in aluminum castings with precision machining, More profession, more competitive. 
3. All molds made by ourself to reduce your cost. Advanced machining equipments and testing equipments. 

40% of our shipment are for your market, proved our competitive in pricing and quality. Shall you have any interest, pls contact for possible deal.
 
b.rgds 
Bob Hu 
Ningbo Yinzhou Xusheng Machinery Factory
Cell: 0086-1395832 7774 
Skype: bobhu1 
Tel: 0086-574-88128603 
bob@xs-aluminumcasting.com 
www.xs-aluminumcasting.com

^ permalink raw reply

* [PATCH v2] drm/mediatek: Support UYVY and YUYV format for overlay
From: Daniel Kurtz @ 2017-01-03  6:27 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1483079183-38637-1-git-send-email-bibby.hsieh@mediatek.com>

On Fri, Dec 30, 2016 at 2:26 PM, Bibby Hsieh <bibby.hsieh@mediatek.com> wrote:
>
> MT8173 overlay can support UYVY and YUYV format,
> we add the format in DRM driver.
>
> Signed-off-by: Bibby Hsieh <bibby.hsieh@mediatek.com>
> Reviewed-by: Daniel Kurtz <djkurtz@chromium.org>
> ---
>  drivers/gpu/drm/mediatek/mtk_disp_ovl.c  | 21 +++++++++++++++++++++
>  drivers/gpu/drm/mediatek/mtk_drm_plane.c |  2 ++
>  2 files changed, 23 insertions(+)
>
> diff --git a/drivers/gpu/drm/mediatek/mtk_disp_ovl.c b/drivers/gpu/drm/mediatek/mtk_disp_ovl.c
> index c703102..de05845 100644
> --- a/drivers/gpu/drm/mediatek/mtk_disp_ovl.c
> +++ b/drivers/gpu/drm/mediatek/mtk_disp_ovl.c
> @@ -40,10 +40,13 @@
>  #define        OVL_RDMA_MEM_GMC        0x40402020
>
>  #define OVL_CON_BYTE_SWAP      BIT(24)
> +#define OVL_CON_MTX_YUV_TO_RGB (6 << 16)
>  #define OVL_CON_CLRFMT_RGB565  (0 << 12)
>  #define OVL_CON_CLRFMT_RGB888  (1 << 12)
>  #define OVL_CON_CLRFMT_RGBA8888        (2 << 12)
>  #define OVL_CON_CLRFMT_ARGB8888        (3 << 12)
> +#define OVL_CON_CLRFMT_UYVY    (4 << 12)
> +#define OVL_CON_CLRFMT_YUYV    (5 << 12)

Why not just add " | OVL_CON_MTX_YUV_TO_RGB" here in the definition of
these two constants, instead of adding a helper function?

>  #define        OVL_CON_AEN             BIT(8)
>  #define        OVL_CON_ALPHA           0xff
>
> @@ -162,6 +165,21 @@ static unsigned int ovl_fmt_convert(unsigned int fmt)
>         case DRM_FORMAT_XBGR8888:
>         case DRM_FORMAT_ABGR8888:
>                 return OVL_CON_CLRFMT_RGBA8888 | OVL_CON_BYTE_SWAP;
> +       case DRM_FORMAT_UYVY:
> +               return OVL_CON_CLRFMT_UYVY;
> +       case DRM_FORMAT_YUYV:
> +               return OVL_CON_CLRFMT_YUYV;
> +       }
> +}
> +
> +static bool ovl_yuv_space(unsigned int fmt)
> +{
> +       switch (fmt) {
> +       case DRM_FORMAT_UYVY:
> +       case DRM_FORMAT_YUYV:
> +               return true;
> +       default:
> +               return false;
>         }
>  }
>
> @@ -183,6 +201,9 @@ static void mtk_ovl_layer_config(struct mtk_ddp_comp *comp, unsigned int idx,
>         if (idx != 0)
>                 con |= OVL_CON_AEN | OVL_CON_ALPHA;
>
> +       if (ovl_yuv_space(fmt))
> +               con |= OVL_CON_MTX_YUV_TO_RGB;
> +
>         writel_relaxed(con, comp->regs + DISP_REG_OVL_CON(idx));
>         writel_relaxed(pitch, comp->regs + DISP_REG_OVL_PITCH(idx));
>         writel_relaxed(src_size, comp->regs + DISP_REG_OVL_SRC_SIZE(idx));
> diff --git a/drivers/gpu/drm/mediatek/mtk_drm_plane.c b/drivers/gpu/drm/mediatek/mtk_drm_plane.c
> index c461a23..8c02d1d 100644
> --- a/drivers/gpu/drm/mediatek/mtk_drm_plane.c
> +++ b/drivers/gpu/drm/mediatek/mtk_drm_plane.c
> @@ -28,6 +28,8 @@
>         DRM_FORMAT_XRGB8888,
>         DRM_FORMAT_ARGB8888,
>         DRM_FORMAT_RGB565,
> +       DRM_FORMAT_UYVY,
> +       DRM_FORMAT_YUYV,
>  };
>
>  static void mtk_plane_reset(struct drm_plane *plane)
> --
> 1.9.1
>

^ permalink raw reply

* Re: [PATCH v2] drm/mediatek: Support UYVY and YUYV format for overlay
From: Daniel Kurtz @ 2017-01-03  6:27 UTC (permalink / raw)
  To: Bibby Hsieh
  Cc: David Airlie, Matthias Brugger, Daniel Vetter, dri-devel,
	moderated list:ARM/Mediatek SoC support, Yingjoe Chen, Cawa Cheng,
	Philipp Zabel, YT Shen, Thierry Reding, CK Hu, Mao Huang,
	linux-arm-kernel@lists.infradead.org,
	linux-kernel@vger.kernel.org, Sascha Hauer
In-Reply-To: <1483079183-38637-1-git-send-email-bibby.hsieh@mediatek.com>

On Fri, Dec 30, 2016 at 2:26 PM, Bibby Hsieh <bibby.hsieh@mediatek.com> wrote:
>
> MT8173 overlay can support UYVY and YUYV format,
> we add the format in DRM driver.
>
> Signed-off-by: Bibby Hsieh <bibby.hsieh@mediatek.com>
> Reviewed-by: Daniel Kurtz <djkurtz@chromium.org>
> ---
>  drivers/gpu/drm/mediatek/mtk_disp_ovl.c  | 21 +++++++++++++++++++++
>  drivers/gpu/drm/mediatek/mtk_drm_plane.c |  2 ++
>  2 files changed, 23 insertions(+)
>
> diff --git a/drivers/gpu/drm/mediatek/mtk_disp_ovl.c b/drivers/gpu/drm/mediatek/mtk_disp_ovl.c
> index c703102..de05845 100644
> --- a/drivers/gpu/drm/mediatek/mtk_disp_ovl.c
> +++ b/drivers/gpu/drm/mediatek/mtk_disp_ovl.c
> @@ -40,10 +40,13 @@
>  #define        OVL_RDMA_MEM_GMC        0x40402020
>
>  #define OVL_CON_BYTE_SWAP      BIT(24)
> +#define OVL_CON_MTX_YUV_TO_RGB (6 << 16)
>  #define OVL_CON_CLRFMT_RGB565  (0 << 12)
>  #define OVL_CON_CLRFMT_RGB888  (1 << 12)
>  #define OVL_CON_CLRFMT_RGBA8888        (2 << 12)
>  #define OVL_CON_CLRFMT_ARGB8888        (3 << 12)
> +#define OVL_CON_CLRFMT_UYVY    (4 << 12)
> +#define OVL_CON_CLRFMT_YUYV    (5 << 12)

Why not just add " | OVL_CON_MTX_YUV_TO_RGB" here in the definition of
these two constants, instead of adding a helper function?

>  #define        OVL_CON_AEN             BIT(8)
>  #define        OVL_CON_ALPHA           0xff
>
> @@ -162,6 +165,21 @@ static unsigned int ovl_fmt_convert(unsigned int fmt)
>         case DRM_FORMAT_XBGR8888:
>         case DRM_FORMAT_ABGR8888:
>                 return OVL_CON_CLRFMT_RGBA8888 | OVL_CON_BYTE_SWAP;
> +       case DRM_FORMAT_UYVY:
> +               return OVL_CON_CLRFMT_UYVY;
> +       case DRM_FORMAT_YUYV:
> +               return OVL_CON_CLRFMT_YUYV;
> +       }
> +}
> +
> +static bool ovl_yuv_space(unsigned int fmt)
> +{
> +       switch (fmt) {
> +       case DRM_FORMAT_UYVY:
> +       case DRM_FORMAT_YUYV:
> +               return true;
> +       default:
> +               return false;
>         }
>  }
>
> @@ -183,6 +201,9 @@ static void mtk_ovl_layer_config(struct mtk_ddp_comp *comp, unsigned int idx,
>         if (idx != 0)
>                 con |= OVL_CON_AEN | OVL_CON_ALPHA;
>
> +       if (ovl_yuv_space(fmt))
> +               con |= OVL_CON_MTX_YUV_TO_RGB;
> +
>         writel_relaxed(con, comp->regs + DISP_REG_OVL_CON(idx));
>         writel_relaxed(pitch, comp->regs + DISP_REG_OVL_PITCH(idx));
>         writel_relaxed(src_size, comp->regs + DISP_REG_OVL_SRC_SIZE(idx));
> diff --git a/drivers/gpu/drm/mediatek/mtk_drm_plane.c b/drivers/gpu/drm/mediatek/mtk_drm_plane.c
> index c461a23..8c02d1d 100644
> --- a/drivers/gpu/drm/mediatek/mtk_drm_plane.c
> +++ b/drivers/gpu/drm/mediatek/mtk_drm_plane.c
> @@ -28,6 +28,8 @@
>         DRM_FORMAT_XRGB8888,
>         DRM_FORMAT_ARGB8888,
>         DRM_FORMAT_RGB565,
> +       DRM_FORMAT_UYVY,
> +       DRM_FORMAT_YUYV,
>  };
>
>  static void mtk_plane_reset(struct drm_plane *plane)
> --
> 1.9.1
>

^ permalink raw reply

* Re: [PATCH 1/2] arm64:dt:ls1046a: Add TMU device tree support for LS1046A
From: Shawn Guo @ 2017-01-03  6:26 UTC (permalink / raw)
  To: Troy Jia
  Cc: devicetree@vger.kernel.org, linux-kernel@vger.kernel.org,
	Scott Wood, edubezval@gmail.com, Y.T. Tang, robh+dt@kernel.org,
	rui.zhang@intel.com, linux-arm-kernel@lists.infradead.org
In-Reply-To: <AM4PR0401MB1843C415E2CF7D58BD5A1064EB6E0@AM4PR0401MB1843.eurprd04.prod.outlook.com>

On Tue, Jan 03, 2017 at 03:49:33AM +0000, Troy Jia wrote:
> > > @@ -279,6 +282,82 @@
> > >  			clocks = <&sysclk>;
> > >  		};
> > >
> > > +		tmu: tmu@1f00000 {
> > > +			compatible = "fsl,qoriq-tmu";
> > > +			reg = <0x0 0x1f00000 0x0 0x10000>;
> > > +			interrupts = <0 33 0x4>;
> > > +			fsl,tmu-range = <0xb0000 0x9002a 0x6004c 0x30062>;
> > > +			fsl,tmu-calibration = <0x00000000 0x00000026
> > > +					       0x00000001 0x0000002d
> > > +					       0x00000002 0x00000032
> > > +					       0x00000003 0x00000039
> > > +					       0x00000004 0x0000003f
> > > +					       0x00000005 0x00000046
> > > +					       0x00000006 0x0000004d
> > > +					       0x00000007 0x00000054
> > > +					       0x00000008 0x0000005a
> > > +					       0x00000009 0x00000061
> > > +					       0x0000000a 0x0000006a
> > > +					       0x0000000b 0x00000071
> > > +
> > 
> > Instead of a newline, can we have a single line comment here to tell how these
> > calibration data is grouped?
> 
> Each group represent one temperature range. It's a good idea to add comment here.
> Could I just add one comment like below to clarify all four groups?
> /* Each calibration data group represent one temperature range. There are four ranges in total */

Probably the following form?

	/* Calibration data group 1 */
	...
	/* Calibration data group 2 */
	...
	/* Calibration data group 3 */
	...
	/* Calibration data group 4 */
	...


> 
> > 
> > > +					       0x00010000 0x00000025
> > > +					       0x00010001 0x0000002c
> > > +					       0x00010002 0x00000035
> > > +					       0x00010003 0x0000003d
> > > +					       0x00010004 0x00000045
> > > +					       0x00010005 0x0000004e
> > > +					       0x00010006 0x00000057
> > > +					       0x00010007 0x00000061
> > > +					       0x00010008 0x0000006b
> > > +					       0x00010009 0x00000076
> > > +
> > > +					       0x00020000 0x00000029
> > > +					       0x00020001 0x00000033
> > > +					       0x00020002 0x0000003d
> > > +					       0x00020003 0x00000049
> > > +					       0x00020004 0x00000056
> > > +					       0x00020005 0x00000061
> > > +					       0x00020006 0x0000006d
> > > +
> > > +					       0x00030000 0x00000021
> > > +					       0x00030001 0x0000002a
> > > +					       0x00030002 0x0000003c
> > > +					       0x00030003 0x0000004e>;
> > > +			big-endian;
> > > +			#thermal-sensor-cells = <1>;
> > > +		};
> > > +
> > > +		thermal-zones {
> > > +			cpu_thermal: cpu-thermal {
> > > +				polling-delay-passive = <1000>;
> > > +				polling-delay = <5000>;
> > > +
> > 
> > We usually do not have newline between properties but nodes, or between
> > property list and child node.
> 
> I just follow the style of thermal binding of
> Documentation/devicetree/bindings/thermal/thermal.txt.

Different subsystem or binding examples use different style, but when we
put things together in the platform dts, we would like to have them in a
unified style.

Shawn

^ permalink raw reply

* Re: [PATCH 1/2] arm64:dt:ls1046a: Add TMU device tree support for LS1046A
From: Shawn Guo @ 2017-01-03  6:26 UTC (permalink / raw)
  To: Troy Jia
  Cc: devicetree-u79uwXL29TY76Z2rM5mHXA@public.gmane.org,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA@public.gmane.org, Scott Wood,
	edubezval-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org, Y.T. Tang,
	robh+dt-DgEjT+Ai2ygdnm+yROfE0A@public.gmane.org,
	rui.zhang-ral2JQCrhuEAvxtiuMwx3w@public.gmane.org,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r@public.gmane.org
In-Reply-To: <AM4PR0401MB1843C415E2CF7D58BD5A1064EB6E0-4rsfagO7TJwDKNMzkuERCo3W/0Ik+aLCnBOFsp37pqbUKgpGm//BTAC/G2K4zDHf@public.gmane.org>

On Tue, Jan 03, 2017 at 03:49:33AM +0000, Troy Jia wrote:
> > > @@ -279,6 +282,82 @@
> > >  			clocks = <&sysclk>;
> > >  		};
> > >
> > > +		tmu: tmu@1f00000 {
> > > +			compatible = "fsl,qoriq-tmu";
> > > +			reg = <0x0 0x1f00000 0x0 0x10000>;
> > > +			interrupts = <0 33 0x4>;
> > > +			fsl,tmu-range = <0xb0000 0x9002a 0x6004c 0x30062>;
> > > +			fsl,tmu-calibration = <0x00000000 0x00000026
> > > +					       0x00000001 0x0000002d
> > > +					       0x00000002 0x00000032
> > > +					       0x00000003 0x00000039
> > > +					       0x00000004 0x0000003f
> > > +					       0x00000005 0x00000046
> > > +					       0x00000006 0x0000004d
> > > +					       0x00000007 0x00000054
> > > +					       0x00000008 0x0000005a
> > > +					       0x00000009 0x00000061
> > > +					       0x0000000a 0x0000006a
> > > +					       0x0000000b 0x00000071
> > > +
> > 
> > Instead of a newline, can we have a single line comment here to tell how these
> > calibration data is grouped?
> 
> Each group represent one temperature range. It's a good idea to add comment here.
> Could I just add one comment like below to clarify all four groups?
> /* Each calibration data group represent one temperature range. There are four ranges in total */

Probably the following form?

	/* Calibration data group 1 */
	...
	/* Calibration data group 2 */
	...
	/* Calibration data group 3 */
	...
	/* Calibration data group 4 */
	...


> 
> > 
> > > +					       0x00010000 0x00000025
> > > +					       0x00010001 0x0000002c
> > > +					       0x00010002 0x00000035
> > > +					       0x00010003 0x0000003d
> > > +					       0x00010004 0x00000045
> > > +					       0x00010005 0x0000004e
> > > +					       0x00010006 0x00000057
> > > +					       0x00010007 0x00000061
> > > +					       0x00010008 0x0000006b
> > > +					       0x00010009 0x00000076
> > > +
> > > +					       0x00020000 0x00000029
> > > +					       0x00020001 0x00000033
> > > +					       0x00020002 0x0000003d
> > > +					       0x00020003 0x00000049
> > > +					       0x00020004 0x00000056
> > > +					       0x00020005 0x00000061
> > > +					       0x00020006 0x0000006d
> > > +
> > > +					       0x00030000 0x00000021
> > > +					       0x00030001 0x0000002a
> > > +					       0x00030002 0x0000003c
> > > +					       0x00030003 0x0000004e>;
> > > +			big-endian;
> > > +			#thermal-sensor-cells = <1>;
> > > +		};
> > > +
> > > +		thermal-zones {
> > > +			cpu_thermal: cpu-thermal {
> > > +				polling-delay-passive = <1000>;
> > > +				polling-delay = <5000>;
> > > +
> > 
> > We usually do not have newline between properties but nodes, or between
> > property list and child node.
> 
> I just follow the style of thermal binding of
> Documentation/devicetree/bindings/thermal/thermal.txt.

Different subsystem or binding examples use different style, but when we
put things together in the platform dts, we would like to have them in a
unified style.

Shawn
--
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 1/2] arm64:dt:ls1046a: Add TMU device tree support for LS1046A
From: Shawn Guo @ 2017-01-03  6:26 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <AM4PR0401MB1843C415E2CF7D58BD5A1064EB6E0@AM4PR0401MB1843.eurprd04.prod.outlook.com>

On Tue, Jan 03, 2017 at 03:49:33AM +0000, Troy Jia wrote:
> > > @@ -279,6 +282,82 @@
> > >  			clocks = <&sysclk>;
> > >  		};
> > >
> > > +		tmu: tmu at 1f00000 {
> > > +			compatible = "fsl,qoriq-tmu";
> > > +			reg = <0x0 0x1f00000 0x0 0x10000>;
> > > +			interrupts = <0 33 0x4>;
> > > +			fsl,tmu-range = <0xb0000 0x9002a 0x6004c 0x30062>;
> > > +			fsl,tmu-calibration = <0x00000000 0x00000026
> > > +					       0x00000001 0x0000002d
> > > +					       0x00000002 0x00000032
> > > +					       0x00000003 0x00000039
> > > +					       0x00000004 0x0000003f
> > > +					       0x00000005 0x00000046
> > > +					       0x00000006 0x0000004d
> > > +					       0x00000007 0x00000054
> > > +					       0x00000008 0x0000005a
> > > +					       0x00000009 0x00000061
> > > +					       0x0000000a 0x0000006a
> > > +					       0x0000000b 0x00000071
> > > +
> > 
> > Instead of a newline, can we have a single line comment here to tell how these
> > calibration data is grouped?
> 
> Each group represent one temperature range. It's a good idea to add comment here.
> Could I just add one comment like below to clarify all four groups?
> /* Each calibration data group represent one temperature range. There are four ranges in total */

Probably the following form?

	/* Calibration data group 1 */
	...
	/* Calibration data group 2 */
	...
	/* Calibration data group 3 */
	...
	/* Calibration data group 4 */
	...


> 
> > 
> > > +					       0x00010000 0x00000025
> > > +					       0x00010001 0x0000002c
> > > +					       0x00010002 0x00000035
> > > +					       0x00010003 0x0000003d
> > > +					       0x00010004 0x00000045
> > > +					       0x00010005 0x0000004e
> > > +					       0x00010006 0x00000057
> > > +					       0x00010007 0x00000061
> > > +					       0x00010008 0x0000006b
> > > +					       0x00010009 0x00000076
> > > +
> > > +					       0x00020000 0x00000029
> > > +					       0x00020001 0x00000033
> > > +					       0x00020002 0x0000003d
> > > +					       0x00020003 0x00000049
> > > +					       0x00020004 0x00000056
> > > +					       0x00020005 0x00000061
> > > +					       0x00020006 0x0000006d
> > > +
> > > +					       0x00030000 0x00000021
> > > +					       0x00030001 0x0000002a
> > > +					       0x00030002 0x0000003c
> > > +					       0x00030003 0x0000004e>;
> > > +			big-endian;
> > > +			#thermal-sensor-cells = <1>;
> > > +		};
> > > +
> > > +		thermal-zones {
> > > +			cpu_thermal: cpu-thermal {
> > > +				polling-delay-passive = <1000>;
> > > +				polling-delay = <5000>;
> > > +
> > 
> > We usually do not have newline between properties but nodes, or between
> > property list and child node.
> 
> I just follow the style of thermal binding of
> Documentation/devicetree/bindings/thermal/thermal.txt.

Different subsystem or binding examples use different style, but when we
put things together in the platform dts, we would like to have them in a
unified style.

Shawn

^ permalink raw reply

* Re: [PATCH 2/2] usb: host: xhci: Handle the right timeout command
From: Baolin Wang @ 2017-01-03  6:20 UTC (permalink / raw)
  To: Mathias Nyman
  Cc: Lu Baolu, Mathias Nyman, Greg KH, USB, LKML, Mark Brown,
	Lu, Baolu
In-Reply-To: <586A6A61.8040902@linux.intel.com>

On 2 January 2017 at 22:57, Mathias Nyman <mathias.nyman@linux.intel.com> wrote:
> On 27.12.2016 05:07, Baolin Wang wrote:
>>
>> Hi,
>>
>> On 21 December 2016 at 21:00, Mathias Nyman
>> <mathias.nyman@linux.intel.com> wrote:
>>>
>>> On 21.12.2016 04:22, Baolin Wang wrote:
>>>>
>>>>
>>>> Hi Mathias,
>>>>
>>>> On 20 December 2016 at 23:13, Mathias Nyman
>>>> <mathias.nyman@linux.intel.com> wrote:
>>>>>
>>>>>
>>>>> On 20.12.2016 09:30, Baolin Wang wrote:
>>>>> ...
>>>>>
>>>>> Alright, I gathered all current work related to xhci races and timeouts
>>>>> and put them into a branch:
>>>>>
>>>>> git://git.kernel.org/pub/scm/linux/kernel/git/mnyman/xhci.git
>>>>> timeout_race_fixes
>>>>>
>>>>> Its based on 4.9
>>>>> It includes a few other patches just to avoid conflicts and  make my
>>>>> life
>>>>> easier
>>>>>
>>>>> Interesting patches are:
>>>>>
>>>>> ee4eb91 xhci: remove unnecessary check for pending timer
>>>>> 0cba67d xhci: detect stop endpoint race using pending timer instead of
>>>>> counter.
>>>>> 4f2535f xhci: Handle command completion and timeout race
>>>>> b9d00d7 usb: host: xhci: Fix possible wild pointer when handling abort
>>>>> command
>>>>> 529a5a0 usb: xhci: fix possible wild pointer
>>>>> 4766555 xhci: Fix race related to abort operation
>>>>> de834a3 xhci: Use delayed_work instead of timer for command timeout
>>>>> 69973b8 Linux 4.9
>>>>>
>>>>> The fixes for command queue races will go to usb-linus and stable, the
>>>>> reworks for stop ep watchdog timer will go to usb-next.
>>>>
>>>>
>>>>
>>>> How about applying below patch in your 'timeout_race_fixes' branch?
>>>> [PATCH] usb: host: xhci: Clean up commands when stop endpoint command is
>>>> timeout
>>>> https://lkml.org/lkml/2016/12/13/94
>>>>
>>>
>>> usb_hc_died() should eventyally end up calling xhci_mem_cleanup()
>>> which will cleanup the command queue. But I need to look into that
>>
>>
>> usb_hc_died() did not call xhci_mem_cleanup() to clean up command
>> queue, it just disconnects all children devices attached on the dying
>> hub. I did not find where it will clean up the command queue when
>> issuing usb_hc_died(). Also before issuing usb_hc_died() in
>> xhci_handle_command_timeout(), we will call
>> xhci_cleanup_command_queue(). I think it should same as in
>> xhci_stop_endpoint_command_watchdog().
>>
>
> You're right, it doesn't call xhci_mem_cleanup.
> Need to look at this after getting first series of fixes to usb-linus

Thanks.

-- 
Baolin.wang
Best Regards

^ permalink raw reply

* Re: [PATCH] diff: add interhunk context config option
From: Pranit Bauva @ 2017-01-03  6:19 UTC (permalink / raw)
  To: Vegard Nossum; +Cc: Junio C Hamano, Git List, René Scharfe
In-Reply-To: <20170102233114.20778-1-vegard.nossum@oracle.com>

Hey Vegard,

On Tue, Jan 3, 2017 at 5:01 AM, Vegard Nossum <vegard.nossum@oracle.com> wrote:
> The --inter-hunk-context= option was added in commit 6d0e674a5754
> ("diff: add option to show context between close hunks"). This patch
> allows configuring a default for this option.
>
> Cc: René Scharfe <l.s.r@web.de>
> Signed-off-by: Vegard Nossum <vegard.nossum@oracle.com>
> ---
>  Documentation/diff-options.txt | 2 ++
>  diff.c                         | 8 ++++++++
>  2 files changed, 10 insertions(+)
>
> diff --git a/Documentation/diff-options.txt b/Documentation/diff-options.txt
> index e6215c372..163b65444 100644
> --- a/Documentation/diff-options.txt
> +++ b/Documentation/diff-options.txt
> @@ -511,6 +511,8 @@ endif::git-format-patch[]
>  --inter-hunk-context=<lines>::
>         Show the context between diff hunks, up to the specified number
>         of lines, thereby fusing hunks that are close to each other.
> +       Defaults to `diff.interhunkcontext` or 0 if the config option
> +       is unset.

Seems good. But I think you have missed adding the documentation of
this to Documentation/diff-config.txt . Generally whatever config
variable one adds, is added to Documentation/config.txt but in this
case, there exists a separate Documentation/diff-config.txt for all
"diff" related things which is included in Documentation/config.txt .
Also, you need to link the link both the parts of this documentation.
Please refer to commit id aaab84203 so as to know what I am talking
about.

>  -W::
>  --function-context::
> diff --git a/diff.c b/diff.c
> index 84dba60c4..40b4e6afe 100644
> --- a/diff.c
> +++ b/diff.c
> @@ -33,6 +33,7 @@ static int diff_rename_limit_default = 400;
>  static int diff_suppress_blank_empty;
>  static int diff_use_color_default = -1;
>  static int diff_context_default = 3;
> +static int diff_interhunk_context_default = 0;
>  static const char *diff_word_regex_cfg;
>  static const char *external_diff_cmd_cfg;
>  static const char *diff_order_file_cfg;
> @@ -248,6 +249,12 @@ int git_diff_ui_config(const char *var, const char *value, void *cb)
>                         return -1;
>                 return 0;
>         }
> +       if (!strcmp(var, "diff.interhunkcontext")) {
> +               diff_interhunk_context_default = git_config_int(var, value);
> +               if (diff_interhunk_context_default < 0)
> +                       return -1;
> +               return 0;
> +       }
>         if (!strcmp(var, "diff.renames")) {
>                 diff_detect_rename_default = git_config_rename(var, value);
>                 return 0;
> @@ -3371,6 +3378,7 @@ void diff_setup(struct diff_options *options)
>         options->rename_limit = -1;
>         options->dirstat_permille = diff_dirstat_permille_default;
>         options->context = diff_context_default;
> +       options->interhunkcontext = diff_interhunk_context_default;
>         options->ws_error_highlight = ws_error_highlight_default;
>         DIFF_OPT_SET(options, RENAME_EMPTY);

On a first look, it seems that we can overwrite the default config
values by using a different command line argument which is good.

Also, tests are missing. It seems that t/t4032 might be a good place
to add those tests.

Rest all is quite good! :)

Regards,
Pranit Bauva

^ permalink raw reply

* Re: [PATCH net 9/9] virtio-net: XDP support for small buffers
From: Jason Wang @ 2017-01-03  6:16 UTC (permalink / raw)
  To: John Fastabend, mst, virtualization, netdev, linux-kernel
  Cc: john.r.fastabend
In-Reply-To: <586AD79B.2070203@gmail.com>



On 2017年01月03日 06:43, John Fastabend wrote:
> On 16-12-23 06:37 AM, Jason Wang wrote:
>> Commit f600b6905015 ("virtio_net: Add XDP support") leaves the case of
>> small receive buffer untouched. This will confuse the user who want to
>> set XDP but use small buffers. Other than forbid XDP in small buffer
>> mode, let's make it work. XDP then can only work at skb->data since
>> virtio-net create skbs during refill, this is sub optimal which could
>> be optimized in the future.
>>
>> Cc: John Fastabend <john.r.fastabend@intel.com>
>> Signed-off-by: Jason Wang <jasowang@redhat.com>
>> ---
>>   drivers/net/virtio_net.c | 112 ++++++++++++++++++++++++++++++++++++-----------
>>   1 file changed, 87 insertions(+), 25 deletions(-)
>>
> Hi Jason,
>
> I was doing some more testing on this what do you think about doing this
> so that free_unused_bufs() handles the buffer free with dev_kfree_skb()
> instead of put_page in small receive mode. Seems more correct to me.
>
>
> diff --git a/drivers/net/virtio_net.c b/drivers/net/virtio_net.c
> index 783e842..27ff76c 100644
> --- a/drivers/net/virtio_net.c
> +++ b/drivers/net/virtio_net.c
> @@ -1898,6 +1898,10 @@ static void free_receive_page_frags(struct virtnet_info *vi)
>
>   static bool is_xdp_queue(struct virtnet_info *vi, int q)
>   {
> +       /* For small receive mode always use kfree_skb variants */
> +       if (!vi->mergeable_rx_bufs)
> +               return false;
> +
>          if (q < (vi->curr_queue_pairs - vi->xdp_queue_pairs))
>                  return false;
>          else if (q < vi->curr_queue_pairs)
>
>
> patch is untested just spotted doing code review.
>
> Thanks,
> John

We probably need a better name for this function.

Acked-by: Jason Wang <jasowang@redhat.com>

^ permalink raw reply

* Re: [PATCH net 9/9] virtio-net: XDP support for small buffers
From: Jason Wang @ 2017-01-03  6:16 UTC (permalink / raw)
  To: John Fastabend, mst, virtualization, netdev, linux-kernel
  Cc: john.r.fastabend
In-Reply-To: <586AD79B.2070203@gmail.com>



On 2017年01月03日 06:43, John Fastabend wrote:
> On 16-12-23 06:37 AM, Jason Wang wrote:
>> Commit f600b6905015 ("virtio_net: Add XDP support") leaves the case of
>> small receive buffer untouched. This will confuse the user who want to
>> set XDP but use small buffers. Other than forbid XDP in small buffer
>> mode, let's make it work. XDP then can only work at skb->data since
>> virtio-net create skbs during refill, this is sub optimal which could
>> be optimized in the future.
>>
>> Cc: John Fastabend <john.r.fastabend@intel.com>
>> Signed-off-by: Jason Wang <jasowang@redhat.com>
>> ---
>>   drivers/net/virtio_net.c | 112 ++++++++++++++++++++++++++++++++++++-----------
>>   1 file changed, 87 insertions(+), 25 deletions(-)
>>
> Hi Jason,
>
> I was doing some more testing on this what do you think about doing this
> so that free_unused_bufs() handles the buffer free with dev_kfree_skb()
> instead of put_page in small receive mode. Seems more correct to me.
>
>
> diff --git a/drivers/net/virtio_net.c b/drivers/net/virtio_net.c
> index 783e842..27ff76c 100644
> --- a/drivers/net/virtio_net.c
> +++ b/drivers/net/virtio_net.c
> @@ -1898,6 +1898,10 @@ static void free_receive_page_frags(struct virtnet_info *vi)
>
>   static bool is_xdp_queue(struct virtnet_info *vi, int q)
>   {
> +       /* For small receive mode always use kfree_skb variants */
> +       if (!vi->mergeable_rx_bufs)
> +               return false;
> +
>          if (q < (vi->curr_queue_pairs - vi->xdp_queue_pairs))
>                  return false;
>          else if (q < vi->curr_queue_pairs)
>
>
> patch is untested just spotted doing code review.
>
> Thanks,
> John

We probably need a better name for this function.

Acked-by: Jason Wang <jasowang@redhat.com>

_______________________________________________
Virtualization mailing list
Virtualization@lists.linux-foundation.org
https://lists.linuxfoundation.org/mailman/listinfo/virtualization

^ permalink raw reply

* Re: [Qemu-devel] [PATCH v10 16/26] intel_iommu: add support for split irqchip
From: Peter Xu @ 2017-01-03  6:15 UTC (permalink / raw)
  To: Jan Kiszka, Paolo Bonzini
  Cc: qemu-devel, imammedo, rth, ehabkost, jasowang, marcel, mst,
	rkrcmar, alex.williamson, wexu, davidkiarie4, Valentine Sinitsyn
In-Reply-To: <576FD856.1020806@web.de>

On Sun, Jun 26, 2016 at 03:27:50PM +0200, Jan Kiszka wrote:
> On 2016-06-26 03:48, Peter Xu wrote:
> > On Sat, Jun 25, 2016 at 05:18:40PM +0200, Jan Kiszka wrote:
> >> On 2016-06-25 15:18, Peter Xu wrote:
> >>> On Sat, Jun 25, 2016 at 10:08:10AM +0200, Jan Kiszka wrote:
> > 
> > [...]
> > 
> >>> I have a thought on how to implement the "sink" you have mentioned:
> >>>
> >>> First of all, in KVM, we provide a new KVM_IRQ_ROUTING_* type, maybe
> >>> called:
> >>>
> >>>   KVM_IRQ_ROUTING_EVENTFD
> >>
> >> Not really, because all sources are either using eventfds, which you can
> >> also terminate in user space (already done for vhost and vfio in certain
> >> scenarios - IIRC) or originate there anyway (IOAPIC).
> > 
> > But how should we handle the cases when the interrupt path are all in
> > kernel?
> 
> There are none which we can't redirect (only full in-kernel irqchip
> would have, but that's unsupported anyway).
> 
> > 
> > For vhost, data should be transfered all inside kernel when split
> > irqchip and irqfd are used: when vhost got data, it triggers irqfd to
> > deliver the interrupt to KVM. Along the way, we should all in kernel.
> > 
> > For vfio, we have vfio_msihandler() who handles the hardware IRQ and
> > then triggers irqfd as well to KVM. Again, it seems all in kernel
> > space, no chance to stop that as well.
> > 
> > Please correct me if I was wrong.
> 
> Look at what vhost is doing e.g.: when a virtqueue is masked, it
> installs an event notifier that records incoming events in a pending
> state field. When it's unmasked, the corresponding KVM irqfd is installed.

Hmm I think it's time I pick up this topic up again... :)

Since it's been half a year from the last post of this thread (I
believe this thread is the so-called "cold data" and should be stored
on tapes already... and sorry fot the long delay), I'd like to do a
quick summary on this: interrupt remap still cannot work well when we
install fault interrupts - when that happens, we should inject VT-d
fault, rather than keeping silence.

The suggestion from Jan above should be a good solution that only need
to touch qemu part - that's the most benefit AFAIU. However, OTOH IMO
we need to modify all the kvm irqfd users with this fix (pci-assign,
ioapic, ivshmem, vfio-pci, virtio) - we need to have all these devices
init with an "fault sink" eventfd, then when we detected specific
irqfd install error, we install the "fault sink". What's worse, if we
add new devices with irqfd support, we need to implement the same
error handling logic as well. Am I understanding it correctly? If so,
isn't that awkward?

Now I am re-thinking about my KVM_IRQ_ROUTING_EVENTFD proposal to do
it - in that case, we should not need to worry about the users of kvm
irqfd, and the error handling is done automatically even with new
irqfd users coming in. The disadvantage is of course we need to touch
both qemu and kvm, also we need to touch KVM API for it (though I
think it'll only need very small change in KVM). And not sure whether
that would worth it.

Or, any better way to do it?

Hope I didn't miss anything. Comments are welcomed!

Regards,

-- peterx

^ permalink raw reply

* Re: [PATCH v4 0/7] Add MACsec offload support for ixgbe
From: Lu, Wenzhuo @ 2017-01-03  6:15 UTC (permalink / raw)
  To: Bie, Tiwei, dev@dpdk.org
  Cc: adrien.mazarguil@6wind.com, Mcnamara, John,
	olivier.matz@6wind.com, thomas.monjalon@6wind.com,
	Ananyev, Konstantin, Zhang, Helin, Dai, Wei, Wang, Xiao W
In-Reply-To: <1482939691-34855-1-git-send-email-tiwei.bie@intel.com>

Hi,


> -----Original Message-----
> From: Bie, Tiwei
> Sent: Wednesday, December 28, 2016 11:41 PM
> To: dev@dpdk.org
> Cc: adrien.mazarguil@6wind.com; Lu, Wenzhuo; Mcnamara, John;
> olivier.matz@6wind.com; thomas.monjalon@6wind.com; Ananyev, Konstantin;
> Zhang, Helin; Dai, Wei; Wang, Xiao W
> Subject: [PATCH v4 0/7] Add MACsec offload support for ixgbe
> 
> This patch set adds the MACsec offload support for ixgbe.
> The testpmd is also updated to support MACsec cmds.
> 
> v2:
> - Update the documents for testpmd;
> - Update the release notes;
> - Reuse the functions provided by base code;
> 
> v3:
> - Add the missing parts of MACsec mbuf flag and reorganize the patch set;
> - Add an ethdev event type for MACsec;
> - Advertise the MACsec offload capabilities based on the mac type;
> - Minor fixes and improvements;
> 
> v4:
> - Reserve bits in mbuf and ethdev for PMD specific API;
> - Use the reserved bits in PMD specific API;
> 
> Tiwei Bie (7):
>   mbuf: reserve a Tx offload flag for PMD-specific API
>   ethdev: reserve an event type for PMD-specific API
>   ethdev: reserve capability flags for PMD-specific API
>   net/ixgbe: add MACsec offload support
>   app/testpmd: add MACsec offload commands
>   doc: add ixgbe specific APIs
>   doc: update the release notes for the reserved flags
> 
>  app/test-pmd/cmdline.c                      | 389 ++++++++++++++++++++++
>  app/test-pmd/macfwd.c                       |   7 +
>  app/test-pmd/macswap.c                      |   7 +
>  app/test-pmd/testpmd.h                      |   2 +
>  app/test-pmd/txonly.c                       |   7 +
>  doc/guides/rel_notes/release_17_02.rst      |  18 ++
>  doc/guides/testpmd_app_ug/testpmd_funcs.rst |  32 ++
>  drivers/net/ixgbe/ixgbe_ethdev.c            | 481 +++++++++++++++++++++++++++-
>  drivers/net/ixgbe/ixgbe_ethdev.h            |  45 +++
>  drivers/net/ixgbe/ixgbe_rxtx.c              |   5 +
>  drivers/net/ixgbe/rte_pmd_ixgbe.h           | 122 +++++++
>  drivers/net/ixgbe/rte_pmd_ixgbe_version.map |  11 +
>  lib/librte_ether/rte_ethdev.h               |   4 +
>  lib/librte_mbuf/rte_mbuf.c                  |   2 +
>  lib/librte_mbuf/rte_mbuf.h                  |   5 +
>  15 files changed, 1132 insertions(+), 5 deletions(-)
> 
> --
> 2.7.4
Series Acked-by: Wenzhuo Lu <wenzhuo.lu@intel.com>

^ permalink raw reply

* Re: [net PATCH] net: virtio: cap mtu when XDP programs are running
From: Jason Wang @ 2017-01-03  6:14 UTC (permalink / raw)
  To: John Fastabend, mst; +Cc: john.r.fastabend, netdev, alexei.starovoitov, daniel
In-Reply-To: <20170102223031.11541.28717.stgit@john-Precision-Tower-5810>



On 2017年01月03日 06:30, John Fastabend wrote:
> XDP programs can not consume multiple pages so we cap the MTU to
> avoid this case. Virtio-net however only checks the MTU at XDP
> program load and does not block MTU changes after the program
> has loaded.
>
> This patch sets/clears the max_mtu value at XDP load/unload time.
>
> Signed-off-by: John Fastabend <john.r.fastabend@intel.com>
> ---
>   drivers/net/virtio_net.c |    9 ++++++---
>   1 file changed, 6 insertions(+), 3 deletions(-)
>
> diff --git a/drivers/net/virtio_net.c b/drivers/net/virtio_net.c
> index 5deeda6..783e842 100644
> --- a/drivers/net/virtio_net.c
> +++ b/drivers/net/virtio_net.c
> @@ -1699,6 +1699,9 @@ static void virtnet_init_settings(struct net_device *dev)
>   	.set_settings = virtnet_set_settings,
>   };
>   
> +#define MIN_MTU ETH_MIN_MTU
> +#define MAX_MTU ETH_MAX_MTU
> +
>   static int virtnet_xdp_set(struct net_device *dev, struct bpf_prog *prog)
>   {
>   	unsigned long int max_sz = PAGE_SIZE - sizeof(struct padded_vnet_hdr);
> @@ -1748,6 +1751,9 @@ static int virtnet_xdp_set(struct net_device *dev, struct bpf_prog *prog)
>   			virtnet_set_queues(vi, curr_qp);
>   			return PTR_ERR(prog);
>   		}
> +		dev->max_mtu = max_sz;
> +	} else {
> +		dev->max_mtu = ETH_MAX_MTU;

Or use ETH_DATA_LEN here consider we only allocate a size of 
GOOD_PACKET_LEN for each small buffer?

Thanks

>   	}
>   
>   	vi->xdp_queue_pairs = xdp_qp;
> @@ -2133,9 +2139,6 @@ static bool virtnet_validate_features(struct virtio_device *vdev)
>   	return true;
>   }
>   
> -#define MIN_MTU ETH_MIN_MTU
> -#define MAX_MTU ETH_MAX_MTU
> -
>   static int virtnet_probe(struct virtio_device *vdev)
>   {
>   	int i, err;
>

^ permalink raw reply

* Re: How to recover a filesystem without formatting nor using the btrfs check command.
From: Qu Wenruo @ 2017-01-03  6:11 UTC (permalink / raw)
  To: none; +Cc: linux-btrfs
In-Reply-To: <866efefad9d62f7f00c117edc4715651@mx.sdfeu.org>

At 01/02/2017 07:29 AM, none wrote:
> Le 2016-10-27 03:11, Qu Wenruo a écrit :
>> At 10/26/2016 07:52 PM, none wrote:
>>> Le 2016-10-26 03:43, Qu Wenruo a écrit :
>>>> Unfortunately, low memory mode is right here.
>>>>
>>>> If btrfs-image dump the image correctly, your extent tree is really
>>>> screwed up.
>>>>
>>>> And how badly it is screwed up?
>>>> It only contains the basic block group info.
>>>> Almost empty, without any really useful EXTENT_ITEM/METADATA_ITEM.
>>>> You can check it by btrfs-debug-tree -t extent.
>>>> Normally, one EXTENT_DATA or tree block should have corresponding
>>>> EXTENT_ITEM or METADATA_ITEM in extent tree.
>>>>
>>>> But in your dump, I only find EXTENT_ITEM less than a dozen, which is
>>>> totally abnormal for the used size of your fs.
>>> Please note df -h report 55Gb used due to a very high compression ratio.
>>> Basically most of the theoretical used space is done by less than 100
>>> files. I want to delete them
>>>> That's why lowmem mode is reporting so many backref lost.
>>> Whithout the lowmem mode, only 3 lines are reported :
>>>
>>> Failed to find [75191291904, 168, 4096]
>>> btrfs unable to find ref byte nr 75191291904 parent 0 root 1  owner 1
>>> offset 0
>>> Failed to find [75191316480, 168, 4096]
>>> btrfs unable to find ref byte nr 75191316480 parent 0 root 1  owner 0
>>> offset 1
>>> parent transid verify failed on 75191349248 wanted 3555361 found 3555362
>>> Ignoring transid failure
>>>
>>> and then it’s cpu locked.
>>
>> It's the dead loop make btrfsck only able to check the first several
>> extents, no method to continue.
>>
>> If we solve the dead loop, then there won't be less error report from
>> original btrfsck.
>> (lowmem mode just avoid the possibility to dead loop by its design)
>>
>>>
>>>> It's almost a miracle that you can still write data into the fs.
>>>> And I heavily doubt the correctness of your existing files.
>>> They are definitely correct. I have several root filesystem and I can
>>> chroot to all of them (though I’m mounting the partition readonly in
>>> order to avoid dangerous writes in that case). In each case I tried
>>> python and ruby cgi scripts.
>>
>> You should check more, normally scrub will help, but considering the
>> state of btrfs, scrub may not work at all or make things worse.
>>
>>>> As extent tree is screwed up, it's completely possible new write are
>>>> overwriting existing data.
>>> Though I only attempted to write to 3 files. But yes, this was something
>>> I suspected : that writing damage things.
>>>> The only chance seems to be --init-extent-tree, but that's very
>>>> dangerous and I highly suspect the screwed up extent tree is caused by
>>>> interrupted extent tree rebuild.
>>> The problem is --init-extent-tree implies --repair which discard
>>> --mode=lowmem and cause the dead lock :
>>> https://bugzilla.kernel.org/show_bug.cgi?id=178781
>>
>> Yes, that's the problem, and current situation may be caused by
>> interrupted extent tree rebuild.
>>
>>>> Thanks,
>>>> Qu
>>>>
>>> And finally, I found several corrupt directories yesterday.
>>>
>>> Do you mean it’s impossible to rescue anything by repairing ? (this is
>>> something I doubt since most files are valid)
>>
>> Not completely, I'm digging into the dead loop problem, and after that
>> you may still recover the fs(or part of it) using --init-extent-tree.
>>
>> Thanks,
>> Qu
>>
>>>
>>> Thank you.
>
> Hello, what’s the status of my report since last October ?
>
> thanks,
>
>
Sorry for the late reply.

I tried your image but...
It's so slow, no matter the mode I'm using.

So I'm not sure if it's a deadlock since lowmem mode still takes several 
minuts and just output the same output.

The fs contains SOOOOOOOOO many reflinks and I can hardly determine if 
it's normal or deadlock.


Considering btrfs check original mode is using list to iteration 
backrefs, it can be very very slow, maybe O(n^3)~O(n^4).

And considering the number of reflinks, it can be longer than your 
assumption (maybe longer than 48 hours).

Just try xfstests generic/175, and see how slow btrfs check is.


And since your fs tree is super big, normal btrfs-debug-tree output will 
be over several GBs for debugging, this also makes things quite nasty to 
debug manually.

IMHO we only have 2 remaining methods to fix your fs:
1) Rework current backref structure.
    Use rb-tree other than list to iteration.
2) Introduce --init-extent-tree in lowmem mode.

Neither way it's a quick fix.
And I'm trying to implement the 2nd method first, but it may takes a lot 
of time.
(I still have a lot of other btrfs development to do, sorry)

I'd suggest you to rebuild the fs, considering the time we need to fix it.

Thanks,
Qu



^ permalink raw reply

* Re: [RFC, PATCHv2 29/29] mm, x86: introduce RLIMIT_VADDR
From: Andy Lutomirski @ 2017-01-03  6:08 UTC (permalink / raw)
  To: Arnd Bergmann
  Cc: Kirill A. Shutemov, Linus Torvalds, Andrew Morton, X86 ML,
	Thomas Gleixner, Ingo Molnar, H. Peter Anvin, Andi Kleen,
	Dave Hansen, linux-arch, linux-mm@kvack.org,
	linux-kernel@vger.kernel.org, Linux API,
	linux-arm-kernel@lists.infradead.org, Catalin Marinas,
	Will Deacon
In-Reply-To: <2736959.3MfCab47fD@wuerfel>

On Mon, Jan 2, 2017 at 12:44 AM, Arnd Bergmann <arnd@arndb.de> wrote:
> On Tuesday, December 27, 2016 4:54:13 AM CET Kirill A. Shutemov wrote:
>> As with other resources you can set the limit lower than current usage.
>> It would affect only future virtual address space allocations.

I still don't buy all these use cases:

>>
>> Use-cases for new rlimit:
>>
>>   - Bumping the soft limit to RLIM_INFINITY, allows current process all
>>     its children to use addresses above 47-bits.

OK, I get this, but only as a workaround for programs that make
assumptions about the address space and don't use some mechanism (to
be designed?) to work correctly in spite of a larger address space.

>>
>>   - Bumping the soft limit to RLIM_INFINITY after fork(2), but before
>>     exec(2) allows the child to use addresses above 47-bits.

Ditto.

>>
>>   - Lowering the hard limit to 47-bits would prevent current process all
>>     its children to use addresses above 47-bits, unless a process has
>>     CAP_SYS_RESOURCES.

I've tried and I can't imagine any reason to do this.

>>
>>   - It’s also can be handy to lower hard or soft limit to arbitrary
>>     address. User-mode emulation in QEMU may lower the limit to 32-bit
>>     to emulate 32-bit machine on 64-bit host.

I don't understand.  QEMU user-mode emulation intercepts all syscalls.
What QEMU would *actually* want is a way to say "allocate me some
memory with the high N bits clear".  mmap-via-int80 on x86 should be
fixed to do this, but a new syscall with an explicit parameter would
work, as would a prctl changing the current limit.

>>
>> TODO:
>>   - port to non-x86;
>>
>> Not-yet-signed-off-by: Kirill A. Shutemov <kirill.shutemov@linux.intel.com>
>> Cc: linux-api@vger.kernel.org
>
> This seems to nicely address the same problem on arm64, which has
> run into the same issue due to the various page table formats
> that can currently be chosen at compile time.

On further reflection, I think this has very little to do with paging
formats except insofar as paging formats make us notice the problem.
The issue is that user code wants to be able to assume an upper limit
on an address, and it gets an upper limit right now that depends on
architecture due to paging formats.  But someone really might want to
write a *portable* 64-bit program that allocates memory with the high
16 bits clear.  So let's add such a mechanism directly.

As a thought experiment, what if x86_64 simply never allocated "high"
(above 2^47-1) addresses unless a new mmap-with-explicit-limit syscall
were used?  Old glibc would continue working.  Old VMs would work.
New programs that want to use ginormous mappings would have to use the
new syscall.  This would be totally stateless and would have no issues
with CRIU.

If necessary, we could also have a prctl that changes a
"personality-like" limit that is in effect when the old mmap was used.
I say "personality-like" because it would reset under exactly the same
conditions that personality resets itself.

Thoughts?

^ permalink raw reply

* [RFC, PATCHv2 29/29] mm, x86: introduce RLIMIT_VADDR
From: Andy Lutomirski @ 2017-01-03  6:08 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <2736959.3MfCab47fD@wuerfel>

On Mon, Jan 2, 2017 at 12:44 AM, Arnd Bergmann <arnd@arndb.de> wrote:
> On Tuesday, December 27, 2016 4:54:13 AM CET Kirill A. Shutemov wrote:
>> As with other resources you can set the limit lower than current usage.
>> It would affect only future virtual address space allocations.

I still don't buy all these use cases:

>>
>> Use-cases for new rlimit:
>>
>>   - Bumping the soft limit to RLIM_INFINITY, allows current process all
>>     its children to use addresses above 47-bits.

OK, I get this, but only as a workaround for programs that make
assumptions about the address space and don't use some mechanism (to
be designed?) to work correctly in spite of a larger address space.

>>
>>   - Bumping the soft limit to RLIM_INFINITY after fork(2), but before
>>     exec(2) allows the child to use addresses above 47-bits.

Ditto.

>>
>>   - Lowering the hard limit to 47-bits would prevent current process all
>>     its children to use addresses above 47-bits, unless a process has
>>     CAP_SYS_RESOURCES.

I've tried and I can't imagine any reason to do this.

>>
>>   - It?s also can be handy to lower hard or soft limit to arbitrary
>>     address. User-mode emulation in QEMU may lower the limit to 32-bit
>>     to emulate 32-bit machine on 64-bit host.

I don't understand.  QEMU user-mode emulation intercepts all syscalls.
What QEMU would *actually* want is a way to say "allocate me some
memory with the high N bits clear".  mmap-via-int80 on x86 should be
fixed to do this, but a new syscall with an explicit parameter would
work, as would a prctl changing the current limit.

>>
>> TODO:
>>   - port to non-x86;
>>
>> Not-yet-signed-off-by: Kirill A. Shutemov <kirill.shutemov@linux.intel.com>
>> Cc: linux-api at vger.kernel.org
>
> This seems to nicely address the same problem on arm64, which has
> run into the same issue due to the various page table formats
> that can currently be chosen at compile time.

On further reflection, I think this has very little to do with paging
formats except insofar as paging formats make us notice the problem.
The issue is that user code wants to be able to assume an upper limit
on an address, and it gets an upper limit right now that depends on
architecture due to paging formats.  But someone really might want to
write a *portable* 64-bit program that allocates memory with the high
16 bits clear.  So let's add such a mechanism directly.

As a thought experiment, what if x86_64 simply never allocated "high"
(above 2^47-1) addresses unless a new mmap-with-explicit-limit syscall
were used?  Old glibc would continue working.  Old VMs would work.
New programs that want to use ginormous mappings would have to use the
new syscall.  This would be totally stateless and would have no issues
with CRIU.

If necessary, we could also have a prctl that changes a
"personality-like" limit that is in effect when the old mmap was used.
I say "personality-like" because it would reset under exactly the same
conditions that personality resets itself.

Thoughts?

^ permalink raw reply

* Re: [RFC, PATCHv2 29/29] mm, x86: introduce RLIMIT_VADDR
From: Andy Lutomirski @ 2017-01-03  6:08 UTC (permalink / raw)
  To: Arnd Bergmann
  Cc: Kirill A. Shutemov, Linus Torvalds, Andrew Morton, X86 ML,
	Thomas Gleixner, Ingo Molnar, H. Peter Anvin, Andi Kleen,
	Dave Hansen, linux-arch, linux-mm@kvack.org,
	linux-kernel@vger.kernel.org, Linux API,
	linux-arm-kernel@lists.infradead.org, Catalin Marinas,
	Will Deacon
In-Reply-To: <2736959.3MfCab47fD@wuerfel>

On Mon, Jan 2, 2017 at 12:44 AM, Arnd Bergmann <arnd@arndb.de> wrote:
> On Tuesday, December 27, 2016 4:54:13 AM CET Kirill A. Shutemov wrote:
>> As with other resources you can set the limit lower than current usage.
>> It would affect only future virtual address space allocations.

I still don't buy all these use cases:

>>
>> Use-cases for new rlimit:
>>
>>   - Bumping the soft limit to RLIM_INFINITY, allows current process all
>>     its children to use addresses above 47-bits.

OK, I get this, but only as a workaround for programs that make
assumptions about the address space and don't use some mechanism (to
be designed?) to work correctly in spite of a larger address space.

>>
>>   - Bumping the soft limit to RLIM_INFINITY after fork(2), but before
>>     exec(2) allows the child to use addresses above 47-bits.

Ditto.

>>
>>   - Lowering the hard limit to 47-bits would prevent current process all
>>     its children to use addresses above 47-bits, unless a process has
>>     CAP_SYS_RESOURCES.

I've tried and I can't imagine any reason to do this.

>>
>>   - It’s also can be handy to lower hard or soft limit to arbitrary
>>     address. User-mode emulation in QEMU may lower the limit to 32-bit
>>     to emulate 32-bit machine on 64-bit host.

I don't understand.  QEMU user-mode emulation intercepts all syscalls.
What QEMU would *actually* want is a way to say "allocate me some
memory with the high N bits clear".  mmap-via-int80 on x86 should be
fixed to do this, but a new syscall with an explicit parameter would
work, as would a prctl changing the current limit.

>>
>> TODO:
>>   - port to non-x86;
>>
>> Not-yet-signed-off-by: Kirill A. Shutemov <kirill.shutemov@linux.intel.com>
>> Cc: linux-api@vger.kernel.org
>
> This seems to nicely address the same problem on arm64, which has
> run into the same issue due to the various page table formats
> that can currently be chosen at compile time.

On further reflection, I think this has very little to do with paging
formats except insofar as paging formats make us notice the problem.
The issue is that user code wants to be able to assume an upper limit
on an address, and it gets an upper limit right now that depends on
architecture due to paging formats.  But someone really might want to
write a *portable* 64-bit program that allocates memory with the high
16 bits clear.  So let's add such a mechanism directly.

As a thought experiment, what if x86_64 simply never allocated "high"
(above 2^47-1) addresses unless a new mmap-with-explicit-limit syscall
were used?  Old glibc would continue working.  Old VMs would work.
New programs that want to use ginormous mappings would have to use the
new syscall.  This would be totally stateless and would have no issues
with CRIU.

If necessary, we could also have a prctl that changes a
"personality-like" limit that is in effect when the old mmap was used.
I say "personality-like" because it would reset under exactly the same
conditions that personality resets itself.

Thoughts?

--
To unsubscribe, send a message with 'unsubscribe linux-mm' in
the body to majordomo@kvack.org.  For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"dont@kvack.org"> email@kvack.org </a>

^ permalink raw reply

* [RFC PATCH] ucm: Add support for device positions
From: mengdong.lin @ 2017-01-03  6:09 UTC (permalink / raw)
  To: alsa-devel, broonie
  Cc: Mengdong Lin, tiwai, mengdong.lin, liam.r.girdwood, vinod.koul,
	pierre-louis.bossart

From: Mengdong Lin <mengdong.lin@linux.intel.com>

Users can provide prosition info of audio devices as a device value. This
will help the sound server to choose an audio devices from some candidates
based on the their locations and the status of the machine.

The value name is the "Postion", and its value should be a composition of
"Top", "Bottom", "Left", "Right", "Front" and "Back". For example, a
speaker may have a position like "Front Top".

The postion value can be got by either of the two APIs:
- snd_use_case_get(), via identifier 'Postion/device', to get the original
  position string defined by the user.
- snd_use_case_geti(), via identifier '_devpos/device', to get the integer
  value of the position. If the user has not define a position, 0 will be
  returned that means an unknown position.

Signed-off-by: Mengdong Lin <mengdong.lin@linux.intel.com>

diff --git a/include/use-case.h b/include/use-case.h
index 8911645..b3b451b 100644
--- a/include/use-case.h
+++ b/include/use-case.h
@@ -165,6 +165,28 @@ extern "C" {
 #define SND_USE_CASE_TQ_VOICE		"Voice"		/**< Voice Tone Quality */
 #define SND_USE_CASE_TQ_TONES		"Tones"		/**< Tones Tone Quality */
 
+
+/**
+ * Device Position bits
+ *
+ * 0 is reserved for unknown position in each dimesion. Users can get the
+ * integer value of the device postion by API snd_use_case_geti() via
+ * identifier '_devpos/device', and the returned value is a compostion of
+ * three dimesions.
+ *
+ * NOTE: Users can also get the position string like "Top Left" by API
+ * snd_use_case_get() via identifier 'Position/device".
+ */
+#define SND_USE_CASE_POS_LEFT           (1<<0)
+#define SND_USE_CASE_POS_RIGHT          (2<<0)
+#define SND_USE_CASE_POS_HORIZON_MASK   (0xffff<<0)
+#define SND_USE_CASE_POS_TOP            (1<<4)
+#define SND_USE_CASE_POS_BOTTOM         (2<<4)
+#define SND_USE_CASE_POS_VERTICAL_MASK  (0xffff<<4)
+#define SND_USE_CASE_POS_FRONT          (1<<8)
+#define SND_USE_CASE_POS_BACK           (2<<8)
+#define SND_USE_CASE_DEPTH_MASK         (0xffff<<8)
+
 /** use case container */
 typedef struct snd_use_case_mgr snd_use_case_mgr_t;
 
@@ -319,6 +341,10 @@ int snd_use_case_get_list(snd_use_case_mgr_t *uc_mgr,
  *        trick upper software layers to e.g. automatically mute speakers when
  *        headphones are plugged in, but that's application policy
  *        configuration that doesn't belong to UCM configuration files.
+ *  - Position
+ *       Position of the device, a composition of "Left", "Right", "Top",
+ *       "Bottom", "Front" and "Back". For example, a device speaker may
+ *        have a position like "Front Top".
  */
 int snd_use_case_get(snd_use_case_mgr_t *uc_mgr,
                      const char *identifier,
diff --git a/src/ucm/main.c b/src/ucm/main.c
index 2d33886..d196a57 100644
--- a/src/ucm/main.c
+++ b/src/ucm/main.c
@@ -801,6 +801,26 @@ long device_status(snd_use_case_mgr_t *uc_mgr,
         return 0;
 }
 
+/* get the device postion */
+long device_position(snd_use_case_mgr_t *uc_mgr, const char *device_name)
+{
+	struct use_case_device *dev;
+	struct list_head *pos, *base;
+
+	if (uc_mgr->active_verb == NULL)
+		return -EINVAL;
+
+	base = &uc_mgr->active_verb->device_list;
+	list_for_each(pos, base) {
+		dev = list_entry(pos, struct use_case_device, list);
+		if (strcmp(dev->name, device_name) == 0)
+			return dev->position;
+	}
+
+	/* cannot find the device */
+	return -1;
+}
+
 long modifier_status(snd_use_case_mgr_t *uc_mgr,
                      const char *modifier_name)
 {
@@ -1645,6 +1665,19 @@ int snd_use_case_geti(snd_use_case_mgr_t *uc_mgr,
 		} else if (identifier[0] == '_')
 			err = -ENOENT;
 #endif
+		} else if (check_identifier(identifier, "_devpos")) {
+			if (!str) {
+				err = -EINVAL;
+				goto __end;
+			}
+
+			err = device_position(uc_mgr, str);
+			if (err >= 0) {
+				*value = err;
+				err = 0;
+			} else {
+				err = -EINVAL;
+			}
 		} else
                         err = -ENOENT;
                 if (str)
diff --git a/src/ucm/parser.c b/src/ucm/parser.c
index 4dc35c3..fc035c3 100644
--- a/src/ucm/parser.c
+++ b/src/ucm/parser.c
@@ -55,6 +55,22 @@ static const char * const component_dir[] = {
 	NULL,		/* terminator */
 };
 
+struct position {
+	int val;
+	const char *id;
+};
+
+/* device positions */
+static struct position positions[] = {
+	{ SND_USE_CASE_POS_LEFT, "Left" },
+	{ SND_USE_CASE_POS_RIGHT, "Right" },
+	{ SND_USE_CASE_POS_TOP, "Top" },
+	{ SND_USE_CASE_POS_BOTTOM, "Bottom" },
+	{ SND_USE_CASE_POS_FRONT, "Front" },
+	{ SND_USE_CASE_POS_BACK, "Back" },
+	{ 0, NULL },	/* terminator */
+};
+
 static int filename_filter(const struct dirent *dirent);
 static int is_component_directory(const char *dir);
 
@@ -62,6 +78,30 @@ static int parse_sequence(snd_use_case_mgr_t *uc_mgr,
 			  struct list_head *base,
 			  snd_config_t *cfg);
 
+static unsigned int parse_position(struct list_head *value_list)
+{
+	struct list_head *pos;
+	struct ucm_value *val;
+	int i, position = 0;
+
+	list_for_each(pos, value_list) {
+		val = list_entry(pos, struct ucm_value, list);
+		if (strncmp("Position", val->name, MAX_IDENTIFIER) == 0) {
+			i = 0;
+			while (positions[i].id) {
+				if (strstr(val->data, positions[i].id))
+					position |= positions[i].val;
+				i++;
+			}
+
+			return position;
+		}
+	}
+
+	/* unknown position */
+	return 0;
+}
+
 /*
  * Parse string
  */
@@ -870,6 +910,7 @@ static int parse_device(snd_use_case_mgr_t *uc_mgr,
 				uc_error("error: failed to parse Value");
 				return err;
 			}
+			device->position = parse_position(&device->value_list);
 			continue;
 		}
 	}
diff --git a/src/ucm/ucm_local.h b/src/ucm/ucm_local.h
index 299a5b9..2537a1d 100644
--- a/src/ucm/ucm_local.h
+++ b/src/ucm/ucm_local.h
@@ -42,6 +42,7 @@
 
 #define MAX_FILE		256
 #define MAX_CARD_LONG_NAME	80
+#define MAX_IDENTIFIER		32	/* Max length of identifier string */
 #define ALSA_USE_CASE_DIR	ALSA_CONFIG_DIR "/ucm"
 
 #define SEQUENCE_ELEMENT_TYPE_CDEV	1
@@ -139,6 +140,7 @@ struct use_case_device {
 
 	char *name;
 	char *comment;
+	int position; /* bits of SND_USE_CASE_POS_, 0 for unknown position */
 
 	/* device enable and disable sequences */
 	struct list_head enable_list;
-- 
2.7.4

^ permalink raw reply related

* [PATCH v2 2/2] iio: Add gravity sensor support
From: Song Hongyan @ 2017-01-03 14:27 UTC (permalink / raw)
  To: linux-input, linux-iio; +Cc: jikos, jic23, srinivas.pandruvada, Song Hongyan
In-Reply-To: <1483453678-6015-1-git-send-email-hongyan.song@intel.com>

Gravity sensor is a soft sensor, which derives value from
standard accelerometer device by filtering out the acceleration
which is not caused by gravity.

Gravity sensor provides a three dimensional vector indicating
the direction and magnitude of gravity. Typically, this sensor
is used to determine the device's relative orientation in space.
The units and the coordinate system is the same as the one used by
the acceleration sensor.
When a device is at rest, the output of the gravity sensor should
be identical to that of the accelerometer.

More information can be found in:
http://www.usb.org/developers/hidpage/HUTRR59_-_Usages_for_Wearables.pdf

Gravity sensor and accelerometer have similar channels and
share channel usage ids. So the most of the code for accel_3d
can be reused.

Signed-off-by: Song Hongyan <hongyan.song@intel.com>
Acked-by: Srinivas Pandruvada <srinivas.pandruvada@linux.intel.com>
---
changes: add more explaination about gravity sensor.

 drivers/iio/accel/hid-sensor-accel-3d.c | 74 +++++++++++++++++++++++++++------
 include/linux/hid-sensor-ids.h          |  3 ++
 2 files changed, 64 insertions(+), 13 deletions(-)

diff --git a/drivers/iio/accel/hid-sensor-accel-3d.c b/drivers/iio/accel/hid-sensor-accel-3d.c
index ab1e238..9edd574 100644
--- a/drivers/iio/accel/hid-sensor-accel-3d.c
+++ b/drivers/iio/accel/hid-sensor-accel-3d.c
@@ -90,6 +90,41 @@ struct accel_3d_state {
 	}
 };
 
+/* Channel definitions */
+static const struct iio_chan_spec gravity_channels[] = {
+	{
+		.type = IIO_GRAVITY,
+		.modified = 1,
+		.channel2 = IIO_MOD_X,
+		.info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
+		.info_mask_shared_by_type = BIT(IIO_CHAN_INFO_OFFSET) |
+		BIT(IIO_CHAN_INFO_SCALE) |
+		BIT(IIO_CHAN_INFO_SAMP_FREQ) |
+		BIT(IIO_CHAN_INFO_HYSTERESIS),
+		.scan_index = CHANNEL_SCAN_INDEX_X,
+	}, {
+		.type = IIO_GRAVITY,
+		.modified = 1,
+		.channel2 = IIO_MOD_Y,
+		.info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
+		.info_mask_shared_by_type = BIT(IIO_CHAN_INFO_OFFSET) |
+		BIT(IIO_CHAN_INFO_SCALE) |
+		BIT(IIO_CHAN_INFO_SAMP_FREQ) |
+		BIT(IIO_CHAN_INFO_HYSTERESIS),
+		.scan_index = CHANNEL_SCAN_INDEX_Y,
+	}, {
+		.type = IIO_GRAVITY,
+		.modified = 1,
+		.channel2 = IIO_MOD_Z,
+		.info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
+		.info_mask_shared_by_type = BIT(IIO_CHAN_INFO_OFFSET) |
+		BIT(IIO_CHAN_INFO_SCALE) |
+		BIT(IIO_CHAN_INFO_SAMP_FREQ) |
+		BIT(IIO_CHAN_INFO_HYSTERESIS),
+		.scan_index = CHANNEL_SCAN_INDEX_Z,
+	}
+};
+
 /* Adjust channel real bits based on report descriptor */
 static void accel_3d_adjust_channel_bit_mask(struct iio_chan_spec *channels,
 						int channel, int size)
@@ -111,6 +146,8 @@ static int accel_3d_read_raw(struct iio_dev *indio_dev,
 	int report_id = -1;
 	u32 address;
 	int ret_type;
+	struct hid_sensor_hub_device *hsdev =
+					accel_state->common_attributes.hsdev;
 
 	*val = 0;
 	*val2 = 0;
@@ -122,8 +159,7 @@ static int accel_3d_read_raw(struct iio_dev *indio_dev,
 		if (report_id >= 0)
 			*val = sensor_hub_input_attr_get_raw_value(
 					accel_state->common_attributes.hsdev,
-					HID_USAGE_SENSOR_ACCEL_3D, address,
-					report_id,
+					hsdev->usage, address, report_id,
 					SENSOR_HUB_SYNC);
 		else {
 			*val = 0;
@@ -272,7 +308,7 @@ static int accel_3d_parse_report(struct platform_device *pdev,
 			st->accel[2].index, st->accel[2].report_id);
 
 	st->scale_precision = hid_sensor_format_scale(
-				HID_USAGE_SENSOR_ACCEL_3D,
+				hsdev->usage,
 				&st->accel[CHANNEL_SCAN_INDEX_X],
 				&st->scale_pre_decml, &st->scale_post_decml);
 
@@ -295,9 +331,12 @@ static int accel_3d_parse_report(struct platform_device *pdev,
 static int hid_accel_3d_probe(struct platform_device *pdev)
 {
 	int ret = 0;
-	static const char *name = "accel_3d";
+	static const char *name;
 	struct iio_dev *indio_dev;
 	struct accel_3d_state *accel_state;
+	const struct iio_chan_spec *channel_spec;
+	int channel_size;
+
 	struct hid_sensor_hub_device *hsdev = pdev->dev.platform_data;
 
 	indio_dev = devm_iio_device_alloc(&pdev->dev,
@@ -311,24 +350,30 @@ static int hid_accel_3d_probe(struct platform_device *pdev)
 	accel_state->common_attributes.hsdev = hsdev;
 	accel_state->common_attributes.pdev = pdev;
 
-	ret = hid_sensor_parse_common_attributes(hsdev,
-					HID_USAGE_SENSOR_ACCEL_3D,
+	if (hsdev->usage == HID_USAGE_SENSOR_ACCEL_3D) {
+		name = "accel_3d";
+		channel_spec = accel_3d_channels;
+		channel_size = sizeof(accel_3d_channels);
+	} else {
+		name = "gravity";
+		channel_spec = gravity_channels;
+		channel_size = sizeof(gravity_channels);
+	}
+	ret = hid_sensor_parse_common_attributes(hsdev, hsdev->usage,
 					&accel_state->common_attributes);
 	if (ret) {
 		dev_err(&pdev->dev, "failed to setup common attributes\n");
 		return ret;
 	}
+	indio_dev->channels = kmemdup(channel_spec, channel_size, GFP_KERNEL);
 
-	indio_dev->channels = kmemdup(accel_3d_channels,
-				      sizeof(accel_3d_channels), GFP_KERNEL);
 	if (!indio_dev->channels) {
 		dev_err(&pdev->dev, "failed to duplicate channels\n");
 		return -ENOMEM;
 	}
-
 	ret = accel_3d_parse_report(pdev, hsdev,
-				    (struct iio_chan_spec *)indio_dev->channels,
-				    HID_USAGE_SENSOR_ACCEL_3D, accel_state);
+				(struct iio_chan_spec *)indio_dev->channels,
+				hsdev->usage, accel_state);
 	if (ret) {
 		dev_err(&pdev->dev, "failed to setup attributes\n");
 		goto error_free_dev_mem;
@@ -363,7 +408,7 @@ static int hid_accel_3d_probe(struct platform_device *pdev)
 	accel_state->callbacks.send_event = accel_3d_proc_event;
 	accel_state->callbacks.capture_sample = accel_3d_capture_sample;
 	accel_state->callbacks.pdev = pdev;
-	ret = sensor_hub_register_callback(hsdev, HID_USAGE_SENSOR_ACCEL_3D,
+	ret = sensor_hub_register_callback(hsdev, hsdev->usage,
 					&accel_state->callbacks);
 	if (ret < 0) {
 		dev_err(&pdev->dev, "callback reg failed\n");
@@ -390,7 +435,7 @@ static int hid_accel_3d_remove(struct platform_device *pdev)
 	struct iio_dev *indio_dev = platform_get_drvdata(pdev);
 	struct accel_3d_state *accel_state = iio_priv(indio_dev);
 
-	sensor_hub_remove_callback(hsdev, HID_USAGE_SENSOR_ACCEL_3D);
+	sensor_hub_remove_callback(hsdev, hsdev->usage);
 	iio_device_unregister(indio_dev);
 	hid_sensor_remove_trigger(&accel_state->common_attributes);
 	iio_triggered_buffer_cleanup(indio_dev);
@@ -404,6 +449,9 @@ static int hid_accel_3d_remove(struct platform_device *pdev)
 		/* Format: HID-SENSOR-usage_id_in_hex_lowercase */
 		.name = "HID-SENSOR-200073",
 	},
+	{	/* gravity sensor */
+		.name = "HID-SENSOR-20007b",
+	},
 	{ /* sentinel */ }
 };
 MODULE_DEVICE_TABLE(platform, hid_accel_3d_ids);
diff --git a/include/linux/hid-sensor-ids.h b/include/linux/hid-sensor-ids.h
index f2ee90a..b6778fd2 100644
--- a/include/linux/hid-sensor-ids.h
+++ b/include/linux/hid-sensor-ids.h
@@ -52,6 +52,9 @@
 #define HID_USAGE_SENSOR_ANGL_VELOCITY_Y_AXIS			0x200458
 #define HID_USAGE_SENSOR_ANGL_VELOCITY_Z_AXIS			0x200459
 
+/* Gravity vector */
+#define HID_USAGE_SENSOR_GRAVITY_VECTOR				0x20007B
+
 /* ORIENTATION: Compass 3D: (200083) */
 #define HID_USAGE_SENSOR_COMPASS_3D				0x200083
 #define HID_USAGE_SENSOR_DATA_ORIENTATION			0x200470
-- 
1.9.1


^ permalink raw reply related

* [PATCH v2 1/2] iio: Add channel for Gravity
From: Song Hongyan @ 2017-01-03 14:27 UTC (permalink / raw)
  To: linux-input, linux-iio; +Cc: jikos, jic23, srinivas.pandruvada, Song Hongyan

Add new channel types support for gravity sensor.

Gravity sensor provides an application-level or physical collection that
identifies a device that measures exclusively the force of Earth's
gravity along any number of axes.

More information can be found in:
http://www.usb.org/developers/hidpage/HUTRR59_-_Usages_for_Wearables.pdf

Signed-off-by: Song Hongyan <hongyan.song@intel.com>
---
 Documentation/ABI/testing/sysfs-bus-iio | 11 +++++++++++
 drivers/iio/industrialio-core.c         |  1 +
 include/uapi/linux/iio/types.h          |  1 +
 tools/iio/iio_event_monitor.c           |  2 ++
 4 files changed, 15 insertions(+)

diff --git a/Documentation/ABI/testing/sysfs-bus-iio b/Documentation/ABI/testing/sysfs-bus-iio
index fee35c0..60b7406 100644
--- a/Documentation/ABI/testing/sysfs-bus-iio
+++ b/Documentation/ABI/testing/sysfs-bus-iio
@@ -170,6 +170,17 @@ Description:
 		Has all of the equivalent parameters as per voltageY. Units
 		after application of scale and offset are m/s^2.
 
+
+What:		/sys/bus/iio/devices/iio:deviceX/in_gravity_x_raw
+What:		/sys/bus/iio/devices/iio:deviceX/in_gravity_y_raw
+What:		/sys/bus/iio/devices/iio:deviceX/in_gravity_z_raw
+KernelVersion:	4.11
+Contact:	linux-iio@vger.kernel.org
+Description:
+		Gravity in direction x, y or z (may be arbitrarily assigned
+		but should match other such assignments on device).
+		Units after application of scale and offset are m/s^2.
+
 What:		/sys/bus/iio/devices/iio:deviceX/in_anglvel_x_raw
 What:		/sys/bus/iio/devices/iio:deviceX/in_anglvel_y_raw
 What:		/sys/bus/iio/devices/iio:deviceX/in_anglvel_z_raw
diff --git a/drivers/iio/industrialio-core.c b/drivers/iio/industrialio-core.c
index fc340ed..72fc96a 100644
--- a/drivers/iio/industrialio-core.c
+++ b/drivers/iio/industrialio-core.c
@@ -81,6 +81,7 @@ struct bus_type iio_bus_type = {
 	[IIO_PH] = "ph",
 	[IIO_UVINDEX] = "uvindex",
 	[IIO_ELECTRICALCONDUCTIVITY] = "electricalconductivity",
+	[IIO_GRAVITY]  = "gravity",
 };
 
 static const char * const iio_modifier_names[] = {
diff --git a/include/uapi/linux/iio/types.h b/include/uapi/linux/iio/types.h
index 22e5e58..d3f7ba7 100644
--- a/include/uapi/linux/iio/types.h
+++ b/include/uapi/linux/iio/types.h
@@ -40,6 +40,7 @@ enum iio_chan_type {
 	IIO_PH,
 	IIO_UVINDEX,
 	IIO_ELECTRICALCONDUCTIVITY,
+	IIO_GRAVITY,
 };
 
 enum iio_modifier {
diff --git a/tools/iio/iio_event_monitor.c b/tools/iio/iio_event_monitor.c
index d9b7e0f..b61245e 100644
--- a/tools/iio/iio_event_monitor.c
+++ b/tools/iio/iio_event_monitor.c
@@ -57,6 +57,7 @@
 	[IIO_RESISTANCE] = "resistance",
 	[IIO_PH] = "ph",
 	[IIO_UVINDEX] = "uvindex",
+	[IIO_GRAVITY] = "gravity",
 };
 
 static const char * const iio_ev_type_text[] = {
@@ -149,6 +150,7 @@ static bool event_is_known(struct iio_event_data *event)
 	case IIO_RESISTANCE:
 	case IIO_PH:
 	case IIO_UVINDEX:
+	case IIO_GRAVITY:
 		break;
 	default:
 		return false;
-- 
1.9.1


^ permalink raw reply related

* Re: [PATCH v2 2/2] ARM: dts: imx6q: Add mccmon6 board support
From: Lukasz Majewski @ 2017-01-03  6:02 UTC (permalink / raw)
  To: Shawn Guo
  Cc: Rob Herring, Mark Rutland, Russell King, Fabio Estevam,
	linux-kernel, devicetree, linux-arm-kernel, Vladimir Zapolskiy,
	Sascha Hauer, Zerlauth Karl (LWN), Lukasz Majewski
In-Reply-To: <20170103020650.GM20956@dragon>

Hi Shawn,

Thank you for your comments.

> On Tue, Jan 03, 2017 at 12:43:38AM +0100, Lukasz Majewski wrote:
> > From: Lukasz Majewski <l.majewski@majess.pl>
> > 
> > This patch provides support for Liebherr's Monitor 6 board
> > (abverrated as mccmon6) to Linux kernel.
> > 
> > Signed-off-by: Lukasz Majewski <lukma@denx.de>
> > ---
> > Changes for v2:
> > - Reorganize the dts file according to Valdimir Zapolskiy's comments
> > 
> > ---
> > MCCMON6 board support depends on following patches:
> > 
> > 1. "video: backlight: pwm_bl: Initialize fb_bl_on[x] and use_count
> > during pwm_backlight_probe()"
> > http://patchwork.ozlabs.org/patch/708844/
> > 
> > 2. "pwm: imx: Provide atomic operation for IMX PWM driver"
> > 	http://patchwork.ozlabs.org/patch/708847/ -
> > http://patchwork.ozlabs.org/patch/708843/ ---
> >  arch/arm/boot/dts/Makefile          |   1 +
> >  arch/arm/boot/dts/imx6q-mccmon6.dts | 477
> > ++++++++++++++++++++++++++++++++++++ 2 files changed, 478
> > insertions(+) create mode 100644 arch/arm/boot/dts/imx6q-mccmon6.dts
> > 
> > diff --git a/arch/arm/boot/dts/Makefile b/arch/arm/boot/dts/Makefile
> > index c558ba7..0aa8e89 100644
> > --- a/arch/arm/boot/dts/Makefile
> > +++ b/arch/arm/boot/dts/Makefile
> > @@ -383,6 +383,7 @@ dtb-$(CONFIG_SOC_IMX6Q) += \
> >  	imx6q-hummingboard.dtb \
> >  	imx6q-icore-rqs.dtb \
> >  	imx6q-marsboard.dtb \
> > +	imx6q-mccmon6.dtb \
> >  	imx6q-nitrogen6x.dtb \
> >  	imx6q-nitrogen6_max.dtb \
> >  	imx6q-novena.dtb \
> > diff --git a/arch/arm/boot/dts/imx6q-mccmon6.dts
> > b/arch/arm/boot/dts/imx6q-mccmon6.dts new file mode 100644
> > index 0000000..7128dc2
> > --- /dev/null
> > +++ b/arch/arm/boot/dts/imx6q-mccmon6.dts
> > @@ -0,0 +1,477 @@
> > +/*
> > + * Copyright 2016-2017
> > + * Lukasz Majewski, DENX Software Engineering, lukma@denx.de
> > + *
> > + * 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.
> > + *
> > + */
> 
> You might want to GPL/X11 dual licence for non-Linux device tree
> users. There are a plenty of examples in arch/arm/boot/dts.  But note
> the following correction.
> 
> https://patchwork.kernel.org/patch/9475057/

For this board GPLv2 is enough. Is the above description correct or do
I need to add something?

> 
> > +
> > +/dts-v1/;
> > +
> > +#include "imx6q.dtsi"
> > +
> > +#include <dt-bindings/gpio/gpio.h>
> > +#include <dt-bindings/pwm/pwm.h>
> > +
> > +/ {
> > +	model = "Liebherr (LWN) monitor6 i.MX6 Quad Board";
> > +	compatible = "lwn,mccmon6", "fsl,imx6q";
> > +
> > +	memory {
> > +		reg = <0x10000000 0x80000000>;
> > +	};
> > +
> > +	backlight_lvds: backlight {
> > +		compatible = "pwm-backlight";
> > +		pinctrl-names = "default";
> > +		pinctrl-0 = <&pinctrl_backlight>;
> > +		pwms = <&pwm2 0 5000000 PWM_POLARITY_INVERTED>;
> > +		brightness-levels = <  0   1   2   3   4   5   6
> > 7   8   9
> > +				      10  11  12  13  14  15  16
> > 17  18  19
> > +				      20  21  22  23  24  25  26
> > 27  28  29
> > +				      30  31  32  33  34  35  36
> > 37  38  39
> > +				      40  41  42  43  44  45  46
> > 47  48  49
> > +				      50  51  52  53  54  55  56
> > 57  58  59
> > +				      60  61  62  63  64  65  66
> > 67  68  69
> > +				      70  71  72  73  74  75  76
> > 77  78  79
> > +				      80  81  82  83  84  85  86
> > 87  88  89
> > +				      90  91  92  93  94  95  96
> > 97  98  99
> > +				     100 101 102 103 104 105 106
> > 107 108 109
> > +				     110 111 112 113 114 115 116
> > 117 118 119
> > +				     120 121 122 123 124 125 126
> > 127 128 129
> > +				     130 131 132 133 134 135 136
> > 137 138 139
> > +				     140 141 142 143 144 145 146
> > 147 148 149
> > +				     150 151 152 153 154 155 156
> > 157 158 159
> > +				     160 161 162 163 164 165 166
> > 167 168 169
> > +				     170 171 172 173 174 175 176
> > 177 178 179
> > +				     180 181 182 183 184 185 186
> > 187 188 189
> > +				     190 191 192 193 194 195 196
> > 197 198 199
> > +				     200 201 202 203 204 205 206
> > 207 208 209
> > +				     210 211 212 213 214 215 216
> > 217 218 219
> > +				     220 221 222 223 224 225 226
> > 227 228 229
> > +				     230 231 232 233 234 235 236
> > 237 238 239
> > +				     240 241 242 243 244 245 246
> > 247 248 249
> > +				     250 251 252 253 254 255>;
> > +		default-brightness-level = <50>;
> > +		enable-gpios = <&gpio1 2 GPIO_ACTIVE_LOW>;
> > +	};
> > +
> > +	reg_lvds: regulator-lvds {
> > +		compatible = "regulator-fixed";
> > +		regulator-name = "lvds_ppen";
> > +		regulator-min-microvolt = <3300000>;
> > +		regulator-max-microvolt = <3300000>;
> > +		regulator-boot-on;
> > +		pinctrl-names = "default";
> > +		pinctrl-0 = <&pinctrl_reg_lvds>;
> > +		gpio = <&gpio1 19 GPIO_ACTIVE_HIGH>;
> > +		enable-active-high;
> > +	};
> > +
> > +	panel-lvds0 {
> > +		compatible = "innolux,g121x1-l03";
> > +		backlight = <&backlight_lvds>;
> > +		power-supply = <&reg_lvds>;
> > +
> > +		port {
> > +			panel_in_lvds0: endpoint {
> > +				remote-endpoint = <&lvds0_out>;
> > +			};
> > +		};
> > +	};
> > +};
> > +
> > +&iomuxc {
> 
> Considering the data amount of this node, we generally put it at the
> bottom of the file to improve the readability of the rest.

But then it will not be alphabetically ordered :-).

I can put it on the end - no problem.

> 
> > +	pinctrl-names = "default";
> > +
> > +	imx6q-mccmon6 {
> 
> This container node can now be dropped completely to save one level of
> indentation.

Ok, I will remove imx6q-mccmon6 container node completely.

> 
> > +		pinctrl_backlight: dispgrp {
> > +			fsl,pins = <
> > +				/* BLEN_OUT */
> > +				MX6QDL_PAD_GPIO_2__GPIO1_IO02
> > 0x1b0b0
> > +			>;
> > +		};
> > +
> > +		pinctrl_ecspi3: ecspi3grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_DISP0_DAT2__ECSPI3_MISO	0x100b1
> > +
> > MX6QDL_PAD_DISP0_DAT1__ECSPI3_MOSI	0x100b1
> > +
> > MX6QDL_PAD_DISP0_DAT0__ECSPI3_SCLK	0x100b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_ecspi3_cs: ecspi3cs {
> 
> ecspi3csgrp, if we follow the naming scheme used in other nodes.
> 
> > +			fsl,pins = <
> > +				MX6QDL_PAD_DISP0_DAT3__GPIO4_IO24
> > 0x80000000
> > +			>;
> > +		};
> > +
> > +		pinctrl_ecspi3_flwp: ecspi3flwp {
> 
> Ditto
> 
> > +			fsl,pins = <
> > +				MX6QDL_PAD_DISP0_DAT6__GPIO4_IO27
> > 0x80000000
> > +			>;
> > +		};
> > +
> > +		pinctrl_enet: enetgrp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_ENET_MDIO__ENET_MDIO		0x1b0b0
> > +
> > MX6QDL_PAD_ENET_MDC__ENET_MDC		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_TXC__RGMII_TXC		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_TD0__RGMII_TD0		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_TD1__RGMII_TD1		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_TD2__RGMII_TD2		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_TD3__RGMII_TD3		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_TX_CTL__RGMII_TX_CTL	0x1b0b0
> > +
> > MX6QDL_PAD_ENET_REF_CLK__ENET_TX_CLK	0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_RXC__RGMII_RXC		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_RD0__RGMII_RD0		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_RD1__RGMII_RD1		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_RD2__RGMII_RD2		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_RD3__RGMII_RD3		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_RX_CTL__RGMII_RX_CTL	0x1b0b0
> > +				MX6QDL_PAD_GPIO_16__ENET_REF_CLK
> > 0x4001b0a8
> > +
> > MX6QDL_PAD_GPIO_6__ENET_IRQ		0x000b1
> > +
> > MX6QDL_PAD_ENET_RXD0__GPIO1_IO27        0x1b0b0
> > +			>;
> > +		};
> > +
> > +		pinctrl_i2c1: i2c1grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_CSI0_DAT9__I2C1_SCL	0x4001b8b1
> > +
> > MX6QDL_PAD_CSI0_DAT8__I2C1_SDA	0x4001b8b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_i2c2: i2c2grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_KEY_COL3__I2C2_SCL	0x4001b8b1
> > +
> > MX6QDL_PAD_KEY_ROW3__I2C2_SDA	0x4001b8b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_pwm2: pwm2grp {
> > +			fsl,pins = <
> > +				MX6QDL_PAD_GPIO_1__PWM2_OUT
> > 0x1b0b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_reg_lvds: req_lvds_grp {
> 
> reglvdsgrp
> 
> > +			fsl,pins = <
> > +				/* LVDS_PPEN_OUT */
> > +
> > MX6QDL_PAD_SD1_DAT2__GPIO1_IO19         0x1b0b0
> > +			>;
> > +		};
> > +
> > +		pinctrl_uart1: uart1grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_CSI0_DAT10__UART1_TX_DATA	0x1b0b1
> > +
> > MX6QDL_PAD_CSI0_DAT11__UART1_RX_DATA	0x1b0b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_uart4: uart4grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_KEY_COL0__UART4_TX_DATA	0x1b0b1
> > +
> > MX6QDL_PAD_KEY_ROW0__UART4_RX_DATA	0x1b0b1
> > +
> > MX6QDL_PAD_CSI0_DAT16__UART4_RTS_B	0x1b0b1
> > +
> > MX6QDL_PAD_CSI0_DAT17__UART4_CTS_B	0x1b0b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_usdhc2: usdhc2grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_SD2_CMD__SD2_CMD		0x17059
> > +
> > MX6QDL_PAD_SD2_CLK__SD2_CLK		0x10059
> > +
> > MX6QDL_PAD_SD2_DAT0__SD2_DATA0		0x17059
> > +
> > MX6QDL_PAD_SD2_DAT1__SD2_DATA1		0x17059
> > +
> > MX6QDL_PAD_SD2_DAT2__SD2_DATA2		0x17059
> > +
> > MX6QDL_PAD_SD2_DAT3__SD2_DATA3		0x17059
> > +
> > MX6QDL_PAD_GPIO_4__GPIO1_IO04           0x1b0b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_usdhc3: usdhc3grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_SD3_CMD__SD3_CMD		0x17059
> > +
> > MX6QDL_PAD_SD3_CLK__SD3_CLK		0x10059
> > +
> > MX6QDL_PAD_SD3_DAT0__SD3_DATA0		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT1__SD3_DATA1		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT2__SD3_DATA2		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT3__SD3_DATA3		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT4__SD3_DATA4		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT5__SD3_DATA5		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT6__SD3_DATA6		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT7__SD3_DATA7		0x17059
> > +
> > MX6QDL_PAD_SD3_RST__SD3_RESET		0x17059
> > +			>;
> > +		};
> > +
> > +		pinctrl_weim_cs0: weimcs0grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_EIM_CS0__EIM_CS0_B		0xb0b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_weim_nor: weimnorgrp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_EIM_OE__EIM_OE_B		0xb0b1
> > +
> > MX6QDL_PAD_EIM_RW__EIM_RW		0xb0b1
> > +
> > MX6QDL_PAD_EIM_WAIT__EIM_WAIT_B	0xb060
> > +
> > MX6QDL_PAD_EIM_D16__EIM_DATA16		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D17__EIM_DATA17		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D18__EIM_DATA18		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D19__EIM_DATA19		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D20__EIM_DATA20		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D21__EIM_DATA21		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D22__EIM_DATA22		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D23__EIM_DATA23		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D24__EIM_DATA24		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D25__EIM_DATA25		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D26__EIM_DATA26		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D27__EIM_DATA27		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D28__EIM_DATA28		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D29__EIM_DATA29		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D30__EIM_DATA30		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D31__EIM_DATA31		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_A23__EIM_ADDR23		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A22__EIM_ADDR22		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A21__EIM_ADDR21		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A20__EIM_ADDR20		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A19__EIM_ADDR19		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A18__EIM_ADDR18		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A17__EIM_ADDR17		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A16__EIM_ADDR16		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA15__EIM_AD15		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA14__EIM_AD14		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA13__EIM_AD13		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA12__EIM_AD12		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA11__EIM_AD11		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA10__EIM_AD10		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA9__EIM_AD09		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA8__EIM_AD08		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA7__EIM_AD07		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA6__EIM_AD06		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA5__EIM_AD05		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA4__EIM_AD04		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA3__EIM_AD03		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA2__EIM_AD02		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA1__EIM_AD01		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA0__EIM_AD00		0xb0b1
> > +			>;
> > +		};
> > +	};
> > +};
> > +
> > +&ecspi3 {
> > +	cs-gpios = <&gpio4 24 0>;
> 
> GPIO_ACTIVE_HIGH?

No, on our HW it is GPIO_ACTIVE_LOW

> 
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_ecspi3 &pinctrl_ecspi3_cs
> > &pinctrl_ecspi3_flwp>;
> > +	status = "okay";
> > +
> > +	flash: s25sl032p@0 {
> 
> Node name should be as generic as possible, while label name can be
> specific.  That said, 's25sl032p: flash@0' should be better.

OK.

> 
> > +		#address-cells = <1>;
> > +		#size-cells = <1>;
> > +		compatible = "spansion,s25sl032p", "jedec,spi-nor";
> 
> "spansion,s25sl032p" doesn't seem to be documented.  Can it be
> dropped?

This memory is jedec compatible and uses "jedec,spi-nor", so
"spansion,s25sl032p" can be dropped

> 
> > +		spi-max-frequency = <40000000>;
> > +		reg = <0>;
> > +	};
> > +};
> > +
> > +&fec {
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_enet>;
> > +	phy-mode = "rgmii";
> > +	phy-reset-gpios = <&gpio1 27 0>;
> 
> GPIO_ACTIVE_xxx?  But you probably need GPIO_ACTIVE_LOW.

Yes.

> 
> > +	interrupts-extended = <&gpio1 6 IRQ_TYPE_LEVEL_HIGH>,
> > +			      <&intc 0 119 IRQ_TYPE_LEVEL_HIGH>;
> > +	status = "okay";
> > +};
> > +
> > +&i2c1 {
> > +	clock-frequency = <100000>;
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_i2c1>;
> > +	status = "okay";
> > +};
> > +
> > +&i2c2 {
> > +	clock-frequency = <100000>;
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_i2c2>;
> > +	status = "okay";
> > +
> > +	pmic: pfuze100@08 {
> 
> pfuze100: pmic@08
> 
> > +		compatible = "fsl,pfuze100";
> > +		reg = <0x08>;
> > +
> > +		regulators {
> > +			sw1a_reg: sw1ab {
> > +				regulator-min-microvolt = <300000>;
> > +				regulator-max-microvolt =
> > <1875000>;
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +				regulator-ramp-delay = <6250>;
> > +			};
> > +
> > +			sw1c_reg: sw1c {
> > +				regulator-min-microvolt = <300000>;
> > +				regulator-max-microvolt =
> > <1875000>;
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +				regulator-ramp-delay = <6250>;
> > +			};
> > +
> > +			sw2_reg: sw2 {
> > +				regulator-min-microvolt = <800000>;
> > +				regulator-max-microvolt =
> > <3950000>;
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +			};
> > +
> > +			sw3a_reg: sw3a {
> > +				regulator-min-microvolt = <400000>;
> > +				regulator-max-microvolt =
> > <1975000>;
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +			};
> > +
> > +			sw3b_reg: sw3b {
> > +				regulator-min-microvolt = <400000>;
> > +				regulator-max-microvolt =
> > <1975000>;
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +			};
> > +
> > +			sw4_reg: sw4 {
> > +				regulator-min-microvolt = <800000>;
> > +				regulator-max-microvolt =
> > <3300000>;
> > +			};
> > +
> > +			swbst_reg: swbst {
> > +				regulator-min-microvolt =
> > <5000000>;
> > +				regulator-max-microvolt =
> > <5150000>;
> > +			};
> > +
> > +			snvs_reg: vsnvs {
> > +				regulator-min-microvolt =
> > <1000000>;
> > +				regulator-max-microvolt =
> > <3000000>;
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +			};
> > +
> > +			vref_reg: vrefddr {
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +			};
> > +
> > +			vgen1_reg: vgen1 {
> > +				regulator-min-microvolt = <800000>;
> > +				regulator-max-microvolt =
> > <1550000>;
> > +			};
> > +
> > +			vgen2_reg: vgen2 {
> > +				regulator-min-microvolt = <800000>;
> > +				regulator-max-microvolt =
> > <1550000>;
> > +			};
> > +
> > +			vgen3_reg: vgen3 {
> > +				regulator-min-microvolt =
> > <1800000>;
> > +				regulator-max-microvolt =
> > <3300000>;
> > +			};
> > +
> > +			vgen4_reg: vgen4 {
> > +				regulator-min-microvolt =
> > <1800000>;
> > +				regulator-max-microvolt =
> > <3300000>;
> > +				regulator-always-on;
> > +			};
> > +
> > +			vgen5_reg: vgen5 {
> > +				regulator-min-microvolt =
> > <1800000>;
> > +				regulator-max-microvolt =
> > <3300000>;
> > +				regulator-always-on;
> > +			};
> > +
> > +			vgen6_reg: vgen6 {
> > +				regulator-min-microvolt =
> > <1800000>;
> > +				regulator-max-microvolt =
> > <3300000>;
> > +				regulator-always-on;
> > +			};
> > +		};
> > +	};
> > +};
> > +
> > +&ldb {
> > +	status = "okay";
> > +
> > +	lvds0: lvds-channel@0 {
> > +		fsl,data-mapping = "spwg";
> > +		fsl,data-width = <24>;
> > +		status = "okay";
> > +
> > +		port@4 {
> > +			reg = <4>;
> > +
> > +			lvds0_out: endpoint {
> > +				remote-endpoint =
> > <&panel_in_lvds0>;
> > +			};
> > +		};
> > +	};
> > +};
> > +
> > +&pwm2 {
> > +	#pwm-cells = <3>;
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_pwm2>;
> > +	status = "okay";
> > +};
> > +
> > +&uart1 {
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_uart1>;
> > +	status = "okay";
> > +};
> > +
> > +&uart4 {
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_uart4>;
> > +	uart-has-rtscts;
> > +	status = "okay";
> > +};
> > +
> > +&usdhc2 {
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_usdhc2>;
> > +	cd-gpios = <&gpio1 4 GPIO_ACTIVE_LOW>;
> > +	bus-width = <4>;
> > +	status = "okay";
> > +};
> > +
> > +&usdhc3 {
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_usdhc3>;
> > +	bus-width = <8>;
> > +	non-removable;
> > +	status = "okay";
> > +};
> > +
> > +&weim {
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_weim_nor &pinctrl_weim_cs0>;
> > +	#address-cells = <2>;
> > +	#size-cells = <1>;
> 
> These two properties can be saved from board dts since commit
> 1be81ea58607 ("ARM: dts: imx6: Add imx-weim parameters to dtsi's").

Ok, I will remove them.

> 
> Shawn
> 
> > +	ranges = <0 0 0x08000000 0x08000000>;
> > +	status = "okay";
> > +
> > +	nor@0,0 {
> > +		compatible = "cfi-flash";
> > +		reg = <0 0 0x02000000>;
> > +		#address-cells = <1>;
> > +		#size-cells = <1>;
> > +		bank-width = <2>;
> > +		use-advanced-sector-protection;
> > +		fsl,weim-cs-timing = <0x00620081 0x00000001
> > 0x1c022000
> > +				0x0000c000 0x1404a38e 0x00000000>;
> > +	};
> > +};
> > -- 
> > 2.1.4
> > 


Best regards,

Lukasz Majewski

--

DENX Software Engineering GmbH,      Managing Director: Wolfgang Denk
HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany
Phone: (+49)-8142-66989-10 Fax: (+49)-8142-66989-80 Email: wd@denx.de

^ permalink raw reply

* Re: [PATCH v2 2/2] ARM: dts: imx6q: Add mccmon6 board support
From: Lukasz Majewski @ 2017-01-03  6:02 UTC (permalink / raw)
  To: Shawn Guo
  Cc: Rob Herring, Mark Rutland, Russell King, Fabio Estevam,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	devicetree-u79uwXL29TY76Z2rM5mHXA,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	Vladimir Zapolskiy, Sascha Hauer, Zerlauth Karl (LWN),
	Lukasz Majewski
In-Reply-To: <20170103020650.GM20956@dragon>

Hi Shawn,

Thank you for your comments.

> On Tue, Jan 03, 2017 at 12:43:38AM +0100, Lukasz Majewski wrote:
> > From: Lukasz Majewski <l.majewski-AM3owJQeAb5mR6Xm/wNWPw@public.gmane.org>
> > 
> > This patch provides support for Liebherr's Monitor 6 board
> > (abverrated as mccmon6) to Linux kernel.
> > 
> > Signed-off-by: Lukasz Majewski <lukma-ynQEQJNshbs@public.gmane.org>
> > ---
> > Changes for v2:
> > - Reorganize the dts file according to Valdimir Zapolskiy's comments
> > 
> > ---
> > MCCMON6 board support depends on following patches:
> > 
> > 1. "video: backlight: pwm_bl: Initialize fb_bl_on[x] and use_count
> > during pwm_backlight_probe()"
> > http://patchwork.ozlabs.org/patch/708844/
> > 
> > 2. "pwm: imx: Provide atomic operation for IMX PWM driver"
> > 	http://patchwork.ozlabs.org/patch/708847/ -
> > http://patchwork.ozlabs.org/patch/708843/ ---
> >  arch/arm/boot/dts/Makefile          |   1 +
> >  arch/arm/boot/dts/imx6q-mccmon6.dts | 477
> > ++++++++++++++++++++++++++++++++++++ 2 files changed, 478
> > insertions(+) create mode 100644 arch/arm/boot/dts/imx6q-mccmon6.dts
> > 
> > diff --git a/arch/arm/boot/dts/Makefile b/arch/arm/boot/dts/Makefile
> > index c558ba7..0aa8e89 100644
> > --- a/arch/arm/boot/dts/Makefile
> > +++ b/arch/arm/boot/dts/Makefile
> > @@ -383,6 +383,7 @@ dtb-$(CONFIG_SOC_IMX6Q) += \
> >  	imx6q-hummingboard.dtb \
> >  	imx6q-icore-rqs.dtb \
> >  	imx6q-marsboard.dtb \
> > +	imx6q-mccmon6.dtb \
> >  	imx6q-nitrogen6x.dtb \
> >  	imx6q-nitrogen6_max.dtb \
> >  	imx6q-novena.dtb \
> > diff --git a/arch/arm/boot/dts/imx6q-mccmon6.dts
> > b/arch/arm/boot/dts/imx6q-mccmon6.dts new file mode 100644
> > index 0000000..7128dc2
> > --- /dev/null
> > +++ b/arch/arm/boot/dts/imx6q-mccmon6.dts
> > @@ -0,0 +1,477 @@
> > +/*
> > + * Copyright 2016-2017
> > + * Lukasz Majewski, DENX Software Engineering, lukma-ynQEQJNshbs@public.gmane.org
> > + *
> > + * 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.
> > + *
> > + */
> 
> You might want to GPL/X11 dual licence for non-Linux device tree
> users. There are a plenty of examples in arch/arm/boot/dts.  But note
> the following correction.
> 
> https://patchwork.kernel.org/patch/9475057/

For this board GPLv2 is enough. Is the above description correct or do
I need to add something?

> 
> > +
> > +/dts-v1/;
> > +
> > +#include "imx6q.dtsi"
> > +
> > +#include <dt-bindings/gpio/gpio.h>
> > +#include <dt-bindings/pwm/pwm.h>
> > +
> > +/ {
> > +	model = "Liebherr (LWN) monitor6 i.MX6 Quad Board";
> > +	compatible = "lwn,mccmon6", "fsl,imx6q";
> > +
> > +	memory {
> > +		reg = <0x10000000 0x80000000>;
> > +	};
> > +
> > +	backlight_lvds: backlight {
> > +		compatible = "pwm-backlight";
> > +		pinctrl-names = "default";
> > +		pinctrl-0 = <&pinctrl_backlight>;
> > +		pwms = <&pwm2 0 5000000 PWM_POLARITY_INVERTED>;
> > +		brightness-levels = <  0   1   2   3   4   5   6
> > 7   8   9
> > +				      10  11  12  13  14  15  16
> > 17  18  19
> > +				      20  21  22  23  24  25  26
> > 27  28  29
> > +				      30  31  32  33  34  35  36
> > 37  38  39
> > +				      40  41  42  43  44  45  46
> > 47  48  49
> > +				      50  51  52  53  54  55  56
> > 57  58  59
> > +				      60  61  62  63  64  65  66
> > 67  68  69
> > +				      70  71  72  73  74  75  76
> > 77  78  79
> > +				      80  81  82  83  84  85  86
> > 87  88  89
> > +				      90  91  92  93  94  95  96
> > 97  98  99
> > +				     100 101 102 103 104 105 106
> > 107 108 109
> > +				     110 111 112 113 114 115 116
> > 117 118 119
> > +				     120 121 122 123 124 125 126
> > 127 128 129
> > +				     130 131 132 133 134 135 136
> > 137 138 139
> > +				     140 141 142 143 144 145 146
> > 147 148 149
> > +				     150 151 152 153 154 155 156
> > 157 158 159
> > +				     160 161 162 163 164 165 166
> > 167 168 169
> > +				     170 171 172 173 174 175 176
> > 177 178 179
> > +				     180 181 182 183 184 185 186
> > 187 188 189
> > +				     190 191 192 193 194 195 196
> > 197 198 199
> > +				     200 201 202 203 204 205 206
> > 207 208 209
> > +				     210 211 212 213 214 215 216
> > 217 218 219
> > +				     220 221 222 223 224 225 226
> > 227 228 229
> > +				     230 231 232 233 234 235 236
> > 237 238 239
> > +				     240 241 242 243 244 245 246
> > 247 248 249
> > +				     250 251 252 253 254 255>;
> > +		default-brightness-level = <50>;
> > +		enable-gpios = <&gpio1 2 GPIO_ACTIVE_LOW>;
> > +	};
> > +
> > +	reg_lvds: regulator-lvds {
> > +		compatible = "regulator-fixed";
> > +		regulator-name = "lvds_ppen";
> > +		regulator-min-microvolt = <3300000>;
> > +		regulator-max-microvolt = <3300000>;
> > +		regulator-boot-on;
> > +		pinctrl-names = "default";
> > +		pinctrl-0 = <&pinctrl_reg_lvds>;
> > +		gpio = <&gpio1 19 GPIO_ACTIVE_HIGH>;
> > +		enable-active-high;
> > +	};
> > +
> > +	panel-lvds0 {
> > +		compatible = "innolux,g121x1-l03";
> > +		backlight = <&backlight_lvds>;
> > +		power-supply = <&reg_lvds>;
> > +
> > +		port {
> > +			panel_in_lvds0: endpoint {
> > +				remote-endpoint = <&lvds0_out>;
> > +			};
> > +		};
> > +	};
> > +};
> > +
> > +&iomuxc {
> 
> Considering the data amount of this node, we generally put it at the
> bottom of the file to improve the readability of the rest.

But then it will not be alphabetically ordered :-).

I can put it on the end - no problem.

> 
> > +	pinctrl-names = "default";
> > +
> > +	imx6q-mccmon6 {
> 
> This container node can now be dropped completely to save one level of
> indentation.

Ok, I will remove imx6q-mccmon6 container node completely.

> 
> > +		pinctrl_backlight: dispgrp {
> > +			fsl,pins = <
> > +				/* BLEN_OUT */
> > +				MX6QDL_PAD_GPIO_2__GPIO1_IO02
> > 0x1b0b0
> > +			>;
> > +		};
> > +
> > +		pinctrl_ecspi3: ecspi3grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_DISP0_DAT2__ECSPI3_MISO	0x100b1
> > +
> > MX6QDL_PAD_DISP0_DAT1__ECSPI3_MOSI	0x100b1
> > +
> > MX6QDL_PAD_DISP0_DAT0__ECSPI3_SCLK	0x100b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_ecspi3_cs: ecspi3cs {
> 
> ecspi3csgrp, if we follow the naming scheme used in other nodes.
> 
> > +			fsl,pins = <
> > +				MX6QDL_PAD_DISP0_DAT3__GPIO4_IO24
> > 0x80000000
> > +			>;
> > +		};
> > +
> > +		pinctrl_ecspi3_flwp: ecspi3flwp {
> 
> Ditto
> 
> > +			fsl,pins = <
> > +				MX6QDL_PAD_DISP0_DAT6__GPIO4_IO27
> > 0x80000000
> > +			>;
> > +		};
> > +
> > +		pinctrl_enet: enetgrp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_ENET_MDIO__ENET_MDIO		0x1b0b0
> > +
> > MX6QDL_PAD_ENET_MDC__ENET_MDC		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_TXC__RGMII_TXC		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_TD0__RGMII_TD0		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_TD1__RGMII_TD1		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_TD2__RGMII_TD2		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_TD3__RGMII_TD3		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_TX_CTL__RGMII_TX_CTL	0x1b0b0
> > +
> > MX6QDL_PAD_ENET_REF_CLK__ENET_TX_CLK	0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_RXC__RGMII_RXC		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_RD0__RGMII_RD0		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_RD1__RGMII_RD1		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_RD2__RGMII_RD2		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_RD3__RGMII_RD3		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_RX_CTL__RGMII_RX_CTL	0x1b0b0
> > +				MX6QDL_PAD_GPIO_16__ENET_REF_CLK
> > 0x4001b0a8
> > +
> > MX6QDL_PAD_GPIO_6__ENET_IRQ		0x000b1
> > +
> > MX6QDL_PAD_ENET_RXD0__GPIO1_IO27        0x1b0b0
> > +			>;
> > +		};
> > +
> > +		pinctrl_i2c1: i2c1grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_CSI0_DAT9__I2C1_SCL	0x4001b8b1
> > +
> > MX6QDL_PAD_CSI0_DAT8__I2C1_SDA	0x4001b8b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_i2c2: i2c2grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_KEY_COL3__I2C2_SCL	0x4001b8b1
> > +
> > MX6QDL_PAD_KEY_ROW3__I2C2_SDA	0x4001b8b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_pwm2: pwm2grp {
> > +			fsl,pins = <
> > +				MX6QDL_PAD_GPIO_1__PWM2_OUT
> > 0x1b0b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_reg_lvds: req_lvds_grp {
> 
> reglvdsgrp
> 
> > +			fsl,pins = <
> > +				/* LVDS_PPEN_OUT */
> > +
> > MX6QDL_PAD_SD1_DAT2__GPIO1_IO19         0x1b0b0
> > +			>;
> > +		};
> > +
> > +		pinctrl_uart1: uart1grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_CSI0_DAT10__UART1_TX_DATA	0x1b0b1
> > +
> > MX6QDL_PAD_CSI0_DAT11__UART1_RX_DATA	0x1b0b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_uart4: uart4grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_KEY_COL0__UART4_TX_DATA	0x1b0b1
> > +
> > MX6QDL_PAD_KEY_ROW0__UART4_RX_DATA	0x1b0b1
> > +
> > MX6QDL_PAD_CSI0_DAT16__UART4_RTS_B	0x1b0b1
> > +
> > MX6QDL_PAD_CSI0_DAT17__UART4_CTS_B	0x1b0b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_usdhc2: usdhc2grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_SD2_CMD__SD2_CMD		0x17059
> > +
> > MX6QDL_PAD_SD2_CLK__SD2_CLK		0x10059
> > +
> > MX6QDL_PAD_SD2_DAT0__SD2_DATA0		0x17059
> > +
> > MX6QDL_PAD_SD2_DAT1__SD2_DATA1		0x17059
> > +
> > MX6QDL_PAD_SD2_DAT2__SD2_DATA2		0x17059
> > +
> > MX6QDL_PAD_SD2_DAT3__SD2_DATA3		0x17059
> > +
> > MX6QDL_PAD_GPIO_4__GPIO1_IO04           0x1b0b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_usdhc3: usdhc3grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_SD3_CMD__SD3_CMD		0x17059
> > +
> > MX6QDL_PAD_SD3_CLK__SD3_CLK		0x10059
> > +
> > MX6QDL_PAD_SD3_DAT0__SD3_DATA0		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT1__SD3_DATA1		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT2__SD3_DATA2		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT3__SD3_DATA3		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT4__SD3_DATA4		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT5__SD3_DATA5		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT6__SD3_DATA6		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT7__SD3_DATA7		0x17059
> > +
> > MX6QDL_PAD_SD3_RST__SD3_RESET		0x17059
> > +			>;
> > +		};
> > +
> > +		pinctrl_weim_cs0: weimcs0grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_EIM_CS0__EIM_CS0_B		0xb0b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_weim_nor: weimnorgrp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_EIM_OE__EIM_OE_B		0xb0b1
> > +
> > MX6QDL_PAD_EIM_RW__EIM_RW		0xb0b1
> > +
> > MX6QDL_PAD_EIM_WAIT__EIM_WAIT_B	0xb060
> > +
> > MX6QDL_PAD_EIM_D16__EIM_DATA16		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D17__EIM_DATA17		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D18__EIM_DATA18		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D19__EIM_DATA19		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D20__EIM_DATA20		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D21__EIM_DATA21		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D22__EIM_DATA22		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D23__EIM_DATA23		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D24__EIM_DATA24		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D25__EIM_DATA25		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D26__EIM_DATA26		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D27__EIM_DATA27		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D28__EIM_DATA28		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D29__EIM_DATA29		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D30__EIM_DATA30		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D31__EIM_DATA31		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_A23__EIM_ADDR23		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A22__EIM_ADDR22		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A21__EIM_ADDR21		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A20__EIM_ADDR20		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A19__EIM_ADDR19		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A18__EIM_ADDR18		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A17__EIM_ADDR17		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A16__EIM_ADDR16		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA15__EIM_AD15		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA14__EIM_AD14		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA13__EIM_AD13		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA12__EIM_AD12		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA11__EIM_AD11		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA10__EIM_AD10		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA9__EIM_AD09		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA8__EIM_AD08		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA7__EIM_AD07		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA6__EIM_AD06		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA5__EIM_AD05		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA4__EIM_AD04		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA3__EIM_AD03		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA2__EIM_AD02		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA1__EIM_AD01		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA0__EIM_AD00		0xb0b1
> > +			>;
> > +		};
> > +	};
> > +};
> > +
> > +&ecspi3 {
> > +	cs-gpios = <&gpio4 24 0>;
> 
> GPIO_ACTIVE_HIGH?

No, on our HW it is GPIO_ACTIVE_LOW

> 
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_ecspi3 &pinctrl_ecspi3_cs
> > &pinctrl_ecspi3_flwp>;
> > +	status = "okay";
> > +
> > +	flash: s25sl032p@0 {
> 
> Node name should be as generic as possible, while label name can be
> specific.  That said, 's25sl032p: flash@0' should be better.

OK.

> 
> > +		#address-cells = <1>;
> > +		#size-cells = <1>;
> > +		compatible = "spansion,s25sl032p", "jedec,spi-nor";
> 
> "spansion,s25sl032p" doesn't seem to be documented.  Can it be
> dropped?

This memory is jedec compatible and uses "jedec,spi-nor", so
"spansion,s25sl032p" can be dropped

> 
> > +		spi-max-frequency = <40000000>;
> > +		reg = <0>;
> > +	};
> > +};
> > +
> > +&fec {
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_enet>;
> > +	phy-mode = "rgmii";
> > +	phy-reset-gpios = <&gpio1 27 0>;
> 
> GPIO_ACTIVE_xxx?  But you probably need GPIO_ACTIVE_LOW.

Yes.

> 
> > +	interrupts-extended = <&gpio1 6 IRQ_TYPE_LEVEL_HIGH>,
> > +			      <&intc 0 119 IRQ_TYPE_LEVEL_HIGH>;
> > +	status = "okay";
> > +};
> > +
> > +&i2c1 {
> > +	clock-frequency = <100000>;
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_i2c1>;
> > +	status = "okay";
> > +};
> > +
> > +&i2c2 {
> > +	clock-frequency = <100000>;
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_i2c2>;
> > +	status = "okay";
> > +
> > +	pmic: pfuze100@08 {
> 
> pfuze100: pmic@08
> 
> > +		compatible = "fsl,pfuze100";
> > +		reg = <0x08>;
> > +
> > +		regulators {
> > +			sw1a_reg: sw1ab {
> > +				regulator-min-microvolt = <300000>;
> > +				regulator-max-microvolt =
> > <1875000>;
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +				regulator-ramp-delay = <6250>;
> > +			};
> > +
> > +			sw1c_reg: sw1c {
> > +				regulator-min-microvolt = <300000>;
> > +				regulator-max-microvolt =
> > <1875000>;
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +				regulator-ramp-delay = <6250>;
> > +			};
> > +
> > +			sw2_reg: sw2 {
> > +				regulator-min-microvolt = <800000>;
> > +				regulator-max-microvolt =
> > <3950000>;
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +			};
> > +
> > +			sw3a_reg: sw3a {
> > +				regulator-min-microvolt = <400000>;
> > +				regulator-max-microvolt =
> > <1975000>;
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +			};
> > +
> > +			sw3b_reg: sw3b {
> > +				regulator-min-microvolt = <400000>;
> > +				regulator-max-microvolt =
> > <1975000>;
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +			};
> > +
> > +			sw4_reg: sw4 {
> > +				regulator-min-microvolt = <800000>;
> > +				regulator-max-microvolt =
> > <3300000>;
> > +			};
> > +
> > +			swbst_reg: swbst {
> > +				regulator-min-microvolt =
> > <5000000>;
> > +				regulator-max-microvolt =
> > <5150000>;
> > +			};
> > +
> > +			snvs_reg: vsnvs {
> > +				regulator-min-microvolt =
> > <1000000>;
> > +				regulator-max-microvolt =
> > <3000000>;
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +			};
> > +
> > +			vref_reg: vrefddr {
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +			};
> > +
> > +			vgen1_reg: vgen1 {
> > +				regulator-min-microvolt = <800000>;
> > +				regulator-max-microvolt =
> > <1550000>;
> > +			};
> > +
> > +			vgen2_reg: vgen2 {
> > +				regulator-min-microvolt = <800000>;
> > +				regulator-max-microvolt =
> > <1550000>;
> > +			};
> > +
> > +			vgen3_reg: vgen3 {
> > +				regulator-min-microvolt =
> > <1800000>;
> > +				regulator-max-microvolt =
> > <3300000>;
> > +			};
> > +
> > +			vgen4_reg: vgen4 {
> > +				regulator-min-microvolt =
> > <1800000>;
> > +				regulator-max-microvolt =
> > <3300000>;
> > +				regulator-always-on;
> > +			};
> > +
> > +			vgen5_reg: vgen5 {
> > +				regulator-min-microvolt =
> > <1800000>;
> > +				regulator-max-microvolt =
> > <3300000>;
> > +				regulator-always-on;
> > +			};
> > +
> > +			vgen6_reg: vgen6 {
> > +				regulator-min-microvolt =
> > <1800000>;
> > +				regulator-max-microvolt =
> > <3300000>;
> > +				regulator-always-on;
> > +			};
> > +		};
> > +	};
> > +};
> > +
> > +&ldb {
> > +	status = "okay";
> > +
> > +	lvds0: lvds-channel@0 {
> > +		fsl,data-mapping = "spwg";
> > +		fsl,data-width = <24>;
> > +		status = "okay";
> > +
> > +		port@4 {
> > +			reg = <4>;
> > +
> > +			lvds0_out: endpoint {
> > +				remote-endpoint =
> > <&panel_in_lvds0>;
> > +			};
> > +		};
> > +	};
> > +};
> > +
> > +&pwm2 {
> > +	#pwm-cells = <3>;
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_pwm2>;
> > +	status = "okay";
> > +};
> > +
> > +&uart1 {
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_uart1>;
> > +	status = "okay";
> > +};
> > +
> > +&uart4 {
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_uart4>;
> > +	uart-has-rtscts;
> > +	status = "okay";
> > +};
> > +
> > +&usdhc2 {
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_usdhc2>;
> > +	cd-gpios = <&gpio1 4 GPIO_ACTIVE_LOW>;
> > +	bus-width = <4>;
> > +	status = "okay";
> > +};
> > +
> > +&usdhc3 {
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_usdhc3>;
> > +	bus-width = <8>;
> > +	non-removable;
> > +	status = "okay";
> > +};
> > +
> > +&weim {
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_weim_nor &pinctrl_weim_cs0>;
> > +	#address-cells = <2>;
> > +	#size-cells = <1>;
> 
> These two properties can be saved from board dts since commit
> 1be81ea58607 ("ARM: dts: imx6: Add imx-weim parameters to dtsi's").

Ok, I will remove them.

> 
> Shawn
> 
> > +	ranges = <0 0 0x08000000 0x08000000>;
> > +	status = "okay";
> > +
> > +	nor@0,0 {
> > +		compatible = "cfi-flash";
> > +		reg = <0 0 0x02000000>;
> > +		#address-cells = <1>;
> > +		#size-cells = <1>;
> > +		bank-width = <2>;
> > +		use-advanced-sector-protection;
> > +		fsl,weim-cs-timing = <0x00620081 0x00000001
> > 0x1c022000
> > +				0x0000c000 0x1404a38e 0x00000000>;
> > +	};
> > +};
> > -- 
> > 2.1.4
> > 


Best regards,

Lukasz Majewski

--

DENX Software Engineering GmbH,      Managing Director: Wolfgang Denk
HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany
Phone: (+49)-8142-66989-10 Fax: (+49)-8142-66989-80 Email: wd-ynQEQJNshbs@public.gmane.org
--
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] ARM: dts: imx6q: Add mccmon6 board support
From: Lukasz Majewski @ 2017-01-03  6:02 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <20170103020650.GM20956@dragon>

Hi Shawn,

Thank you for your comments.

> On Tue, Jan 03, 2017 at 12:43:38AM +0100, Lukasz Majewski wrote:
> > From: Lukasz Majewski <l.majewski@majess.pl>
> > 
> > This patch provides support for Liebherr's Monitor 6 board
> > (abverrated as mccmon6) to Linux kernel.
> > 
> > Signed-off-by: Lukasz Majewski <lukma@denx.de>
> > ---
> > Changes for v2:
> > - Reorganize the dts file according to Valdimir Zapolskiy's comments
> > 
> > ---
> > MCCMON6 board support depends on following patches:
> > 
> > 1. "video: backlight: pwm_bl: Initialize fb_bl_on[x] and use_count
> > during pwm_backlight_probe()"
> > http://patchwork.ozlabs.org/patch/708844/
> > 
> > 2. "pwm: imx: Provide atomic operation for IMX PWM driver"
> > 	http://patchwork.ozlabs.org/patch/708847/ -
> > http://patchwork.ozlabs.org/patch/708843/ ---
> >  arch/arm/boot/dts/Makefile          |   1 +
> >  arch/arm/boot/dts/imx6q-mccmon6.dts | 477
> > ++++++++++++++++++++++++++++++++++++ 2 files changed, 478
> > insertions(+) create mode 100644 arch/arm/boot/dts/imx6q-mccmon6.dts
> > 
> > diff --git a/arch/arm/boot/dts/Makefile b/arch/arm/boot/dts/Makefile
> > index c558ba7..0aa8e89 100644
> > --- a/arch/arm/boot/dts/Makefile
> > +++ b/arch/arm/boot/dts/Makefile
> > @@ -383,6 +383,7 @@ dtb-$(CONFIG_SOC_IMX6Q) += \
> >  	imx6q-hummingboard.dtb \
> >  	imx6q-icore-rqs.dtb \
> >  	imx6q-marsboard.dtb \
> > +	imx6q-mccmon6.dtb \
> >  	imx6q-nitrogen6x.dtb \
> >  	imx6q-nitrogen6_max.dtb \
> >  	imx6q-novena.dtb \
> > diff --git a/arch/arm/boot/dts/imx6q-mccmon6.dts
> > b/arch/arm/boot/dts/imx6q-mccmon6.dts new file mode 100644
> > index 0000000..7128dc2
> > --- /dev/null
> > +++ b/arch/arm/boot/dts/imx6q-mccmon6.dts
> > @@ -0,0 +1,477 @@
> > +/*
> > + * Copyright 2016-2017
> > + * Lukasz Majewski, DENX Software Engineering, lukma at denx.de
> > + *
> > + * 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.
> > + *
> > + */
> 
> You might want to GPL/X11 dual licence for non-Linux device tree
> users. There are a plenty of examples in arch/arm/boot/dts.  But note
> the following correction.
> 
> https://patchwork.kernel.org/patch/9475057/

For this board GPLv2 is enough. Is the above description correct or do
I need to add something?

> 
> > +
> > +/dts-v1/;
> > +
> > +#include "imx6q.dtsi"
> > +
> > +#include <dt-bindings/gpio/gpio.h>
> > +#include <dt-bindings/pwm/pwm.h>
> > +
> > +/ {
> > +	model = "Liebherr (LWN) monitor6 i.MX6 Quad Board";
> > +	compatible = "lwn,mccmon6", "fsl,imx6q";
> > +
> > +	memory {
> > +		reg = <0x10000000 0x80000000>;
> > +	};
> > +
> > +	backlight_lvds: backlight {
> > +		compatible = "pwm-backlight";
> > +		pinctrl-names = "default";
> > +		pinctrl-0 = <&pinctrl_backlight>;
> > +		pwms = <&pwm2 0 5000000 PWM_POLARITY_INVERTED>;
> > +		brightness-levels = <  0   1   2   3   4   5   6
> > 7   8   9
> > +				      10  11  12  13  14  15  16
> > 17  18  19
> > +				      20  21  22  23  24  25  26
> > 27  28  29
> > +				      30  31  32  33  34  35  36
> > 37  38  39
> > +				      40  41  42  43  44  45  46
> > 47  48  49
> > +				      50  51  52  53  54  55  56
> > 57  58  59
> > +				      60  61  62  63  64  65  66
> > 67  68  69
> > +				      70  71  72  73  74  75  76
> > 77  78  79
> > +				      80  81  82  83  84  85  86
> > 87  88  89
> > +				      90  91  92  93  94  95  96
> > 97  98  99
> > +				     100 101 102 103 104 105 106
> > 107 108 109
> > +				     110 111 112 113 114 115 116
> > 117 118 119
> > +				     120 121 122 123 124 125 126
> > 127 128 129
> > +				     130 131 132 133 134 135 136
> > 137 138 139
> > +				     140 141 142 143 144 145 146
> > 147 148 149
> > +				     150 151 152 153 154 155 156
> > 157 158 159
> > +				     160 161 162 163 164 165 166
> > 167 168 169
> > +				     170 171 172 173 174 175 176
> > 177 178 179
> > +				     180 181 182 183 184 185 186
> > 187 188 189
> > +				     190 191 192 193 194 195 196
> > 197 198 199
> > +				     200 201 202 203 204 205 206
> > 207 208 209
> > +				     210 211 212 213 214 215 216
> > 217 218 219
> > +				     220 221 222 223 224 225 226
> > 227 228 229
> > +				     230 231 232 233 234 235 236
> > 237 238 239
> > +				     240 241 242 243 244 245 246
> > 247 248 249
> > +				     250 251 252 253 254 255>;
> > +		default-brightness-level = <50>;
> > +		enable-gpios = <&gpio1 2 GPIO_ACTIVE_LOW>;
> > +	};
> > +
> > +	reg_lvds: regulator-lvds {
> > +		compatible = "regulator-fixed";
> > +		regulator-name = "lvds_ppen";
> > +		regulator-min-microvolt = <3300000>;
> > +		regulator-max-microvolt = <3300000>;
> > +		regulator-boot-on;
> > +		pinctrl-names = "default";
> > +		pinctrl-0 = <&pinctrl_reg_lvds>;
> > +		gpio = <&gpio1 19 GPIO_ACTIVE_HIGH>;
> > +		enable-active-high;
> > +	};
> > +
> > +	panel-lvds0 {
> > +		compatible = "innolux,g121x1-l03";
> > +		backlight = <&backlight_lvds>;
> > +		power-supply = <&reg_lvds>;
> > +
> > +		port {
> > +			panel_in_lvds0: endpoint {
> > +				remote-endpoint = <&lvds0_out>;
> > +			};
> > +		};
> > +	};
> > +};
> > +
> > +&iomuxc {
> 
> Considering the data amount of this node, we generally put it at the
> bottom of the file to improve the readability of the rest.

But then it will not be alphabetically ordered :-).

I can put it on the end - no problem.

> 
> > +	pinctrl-names = "default";
> > +
> > +	imx6q-mccmon6 {
> 
> This container node can now be dropped completely to save one level of
> indentation.

Ok, I will remove imx6q-mccmon6 container node completely.

> 
> > +		pinctrl_backlight: dispgrp {
> > +			fsl,pins = <
> > +				/* BLEN_OUT */
> > +				MX6QDL_PAD_GPIO_2__GPIO1_IO02
> > 0x1b0b0
> > +			>;
> > +		};
> > +
> > +		pinctrl_ecspi3: ecspi3grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_DISP0_DAT2__ECSPI3_MISO	0x100b1
> > +
> > MX6QDL_PAD_DISP0_DAT1__ECSPI3_MOSI	0x100b1
> > +
> > MX6QDL_PAD_DISP0_DAT0__ECSPI3_SCLK	0x100b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_ecspi3_cs: ecspi3cs {
> 
> ecspi3csgrp, if we follow the naming scheme used in other nodes.
> 
> > +			fsl,pins = <
> > +				MX6QDL_PAD_DISP0_DAT3__GPIO4_IO24
> > 0x80000000
> > +			>;
> > +		};
> > +
> > +		pinctrl_ecspi3_flwp: ecspi3flwp {
> 
> Ditto
> 
> > +			fsl,pins = <
> > +				MX6QDL_PAD_DISP0_DAT6__GPIO4_IO27
> > 0x80000000
> > +			>;
> > +		};
> > +
> > +		pinctrl_enet: enetgrp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_ENET_MDIO__ENET_MDIO		0x1b0b0
> > +
> > MX6QDL_PAD_ENET_MDC__ENET_MDC		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_TXC__RGMII_TXC		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_TD0__RGMII_TD0		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_TD1__RGMII_TD1		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_TD2__RGMII_TD2		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_TD3__RGMII_TD3		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_TX_CTL__RGMII_TX_CTL	0x1b0b0
> > +
> > MX6QDL_PAD_ENET_REF_CLK__ENET_TX_CLK	0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_RXC__RGMII_RXC		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_RD0__RGMII_RD0		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_RD1__RGMII_RD1		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_RD2__RGMII_RD2		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_RD3__RGMII_RD3		0x1b0b0
> > +
> > MX6QDL_PAD_RGMII_RX_CTL__RGMII_RX_CTL	0x1b0b0
> > +				MX6QDL_PAD_GPIO_16__ENET_REF_CLK
> > 0x4001b0a8
> > +
> > MX6QDL_PAD_GPIO_6__ENET_IRQ		0x000b1
> > +
> > MX6QDL_PAD_ENET_RXD0__GPIO1_IO27        0x1b0b0
> > +			>;
> > +		};
> > +
> > +		pinctrl_i2c1: i2c1grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_CSI0_DAT9__I2C1_SCL	0x4001b8b1
> > +
> > MX6QDL_PAD_CSI0_DAT8__I2C1_SDA	0x4001b8b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_i2c2: i2c2grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_KEY_COL3__I2C2_SCL	0x4001b8b1
> > +
> > MX6QDL_PAD_KEY_ROW3__I2C2_SDA	0x4001b8b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_pwm2: pwm2grp {
> > +			fsl,pins = <
> > +				MX6QDL_PAD_GPIO_1__PWM2_OUT
> > 0x1b0b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_reg_lvds: req_lvds_grp {
> 
> reglvdsgrp
> 
> > +			fsl,pins = <
> > +				/* LVDS_PPEN_OUT */
> > +
> > MX6QDL_PAD_SD1_DAT2__GPIO1_IO19         0x1b0b0
> > +			>;
> > +		};
> > +
> > +		pinctrl_uart1: uart1grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_CSI0_DAT10__UART1_TX_DATA	0x1b0b1
> > +
> > MX6QDL_PAD_CSI0_DAT11__UART1_RX_DATA	0x1b0b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_uart4: uart4grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_KEY_COL0__UART4_TX_DATA	0x1b0b1
> > +
> > MX6QDL_PAD_KEY_ROW0__UART4_RX_DATA	0x1b0b1
> > +
> > MX6QDL_PAD_CSI0_DAT16__UART4_RTS_B	0x1b0b1
> > +
> > MX6QDL_PAD_CSI0_DAT17__UART4_CTS_B	0x1b0b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_usdhc2: usdhc2grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_SD2_CMD__SD2_CMD		0x17059
> > +
> > MX6QDL_PAD_SD2_CLK__SD2_CLK		0x10059
> > +
> > MX6QDL_PAD_SD2_DAT0__SD2_DATA0		0x17059
> > +
> > MX6QDL_PAD_SD2_DAT1__SD2_DATA1		0x17059
> > +
> > MX6QDL_PAD_SD2_DAT2__SD2_DATA2		0x17059
> > +
> > MX6QDL_PAD_SD2_DAT3__SD2_DATA3		0x17059
> > +
> > MX6QDL_PAD_GPIO_4__GPIO1_IO04           0x1b0b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_usdhc3: usdhc3grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_SD3_CMD__SD3_CMD		0x17059
> > +
> > MX6QDL_PAD_SD3_CLK__SD3_CLK		0x10059
> > +
> > MX6QDL_PAD_SD3_DAT0__SD3_DATA0		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT1__SD3_DATA1		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT2__SD3_DATA2		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT3__SD3_DATA3		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT4__SD3_DATA4		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT5__SD3_DATA5		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT6__SD3_DATA6		0x17059
> > +
> > MX6QDL_PAD_SD3_DAT7__SD3_DATA7		0x17059
> > +
> > MX6QDL_PAD_SD3_RST__SD3_RESET		0x17059
> > +			>;
> > +		};
> > +
> > +		pinctrl_weim_cs0: weimcs0grp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_EIM_CS0__EIM_CS0_B		0xb0b1
> > +			>;
> > +		};
> > +
> > +		pinctrl_weim_nor: weimnorgrp {
> > +			fsl,pins = <
> > +
> > MX6QDL_PAD_EIM_OE__EIM_OE_B		0xb0b1
> > +
> > MX6QDL_PAD_EIM_RW__EIM_RW		0xb0b1
> > +
> > MX6QDL_PAD_EIM_WAIT__EIM_WAIT_B	0xb060
> > +
> > MX6QDL_PAD_EIM_D16__EIM_DATA16		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D17__EIM_DATA17		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D18__EIM_DATA18		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D19__EIM_DATA19		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D20__EIM_DATA20		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D21__EIM_DATA21		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D22__EIM_DATA22		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D23__EIM_DATA23		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D24__EIM_DATA24		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D25__EIM_DATA25		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D26__EIM_DATA26		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D27__EIM_DATA27		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D28__EIM_DATA28		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D29__EIM_DATA29		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D30__EIM_DATA30		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_D31__EIM_DATA31		0x1b0b0
> > +
> > MX6QDL_PAD_EIM_A23__EIM_ADDR23		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A22__EIM_ADDR22		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A21__EIM_ADDR21		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A20__EIM_ADDR20		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A19__EIM_ADDR19		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A18__EIM_ADDR18		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A17__EIM_ADDR17		0xb0b1
> > +
> > MX6QDL_PAD_EIM_A16__EIM_ADDR16		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA15__EIM_AD15		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA14__EIM_AD14		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA13__EIM_AD13		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA12__EIM_AD12		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA11__EIM_AD11		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA10__EIM_AD10		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA9__EIM_AD09		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA8__EIM_AD08		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA7__EIM_AD07		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA6__EIM_AD06		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA5__EIM_AD05		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA4__EIM_AD04		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA3__EIM_AD03		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA2__EIM_AD02		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA1__EIM_AD01		0xb0b1
> > +
> > MX6QDL_PAD_EIM_DA0__EIM_AD00		0xb0b1
> > +			>;
> > +		};
> > +	};
> > +};
> > +
> > +&ecspi3 {
> > +	cs-gpios = <&gpio4 24 0>;
> 
> GPIO_ACTIVE_HIGH?

No, on our HW it is GPIO_ACTIVE_LOW

> 
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_ecspi3 &pinctrl_ecspi3_cs
> > &pinctrl_ecspi3_flwp>;
> > +	status = "okay";
> > +
> > +	flash: s25sl032p at 0 {
> 
> Node name should be as generic as possible, while label name can be
> specific.  That said, 's25sl032p: flash at 0' should be better.

OK.

> 
> > +		#address-cells = <1>;
> > +		#size-cells = <1>;
> > +		compatible = "spansion,s25sl032p", "jedec,spi-nor";
> 
> "spansion,s25sl032p" doesn't seem to be documented.  Can it be
> dropped?

This memory is jedec compatible and uses "jedec,spi-nor", so
"spansion,s25sl032p" can be dropped

> 
> > +		spi-max-frequency = <40000000>;
> > +		reg = <0>;
> > +	};
> > +};
> > +
> > +&fec {
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_enet>;
> > +	phy-mode = "rgmii";
> > +	phy-reset-gpios = <&gpio1 27 0>;
> 
> GPIO_ACTIVE_xxx?  But you probably need GPIO_ACTIVE_LOW.

Yes.

> 
> > +	interrupts-extended = <&gpio1 6 IRQ_TYPE_LEVEL_HIGH>,
> > +			      <&intc 0 119 IRQ_TYPE_LEVEL_HIGH>;
> > +	status = "okay";
> > +};
> > +
> > +&i2c1 {
> > +	clock-frequency = <100000>;
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_i2c1>;
> > +	status = "okay";
> > +};
> > +
> > +&i2c2 {
> > +	clock-frequency = <100000>;
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_i2c2>;
> > +	status = "okay";
> > +
> > +	pmic: pfuze100 at 08 {
> 
> pfuze100: pmic at 08
> 
> > +		compatible = "fsl,pfuze100";
> > +		reg = <0x08>;
> > +
> > +		regulators {
> > +			sw1a_reg: sw1ab {
> > +				regulator-min-microvolt = <300000>;
> > +				regulator-max-microvolt =
> > <1875000>;
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +				regulator-ramp-delay = <6250>;
> > +			};
> > +
> > +			sw1c_reg: sw1c {
> > +				regulator-min-microvolt = <300000>;
> > +				regulator-max-microvolt =
> > <1875000>;
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +				regulator-ramp-delay = <6250>;
> > +			};
> > +
> > +			sw2_reg: sw2 {
> > +				regulator-min-microvolt = <800000>;
> > +				regulator-max-microvolt =
> > <3950000>;
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +			};
> > +
> > +			sw3a_reg: sw3a {
> > +				regulator-min-microvolt = <400000>;
> > +				regulator-max-microvolt =
> > <1975000>;
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +			};
> > +
> > +			sw3b_reg: sw3b {
> > +				regulator-min-microvolt = <400000>;
> > +				regulator-max-microvolt =
> > <1975000>;
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +			};
> > +
> > +			sw4_reg: sw4 {
> > +				regulator-min-microvolt = <800000>;
> > +				regulator-max-microvolt =
> > <3300000>;
> > +			};
> > +
> > +			swbst_reg: swbst {
> > +				regulator-min-microvolt =
> > <5000000>;
> > +				regulator-max-microvolt =
> > <5150000>;
> > +			};
> > +
> > +			snvs_reg: vsnvs {
> > +				regulator-min-microvolt =
> > <1000000>;
> > +				regulator-max-microvolt =
> > <3000000>;
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +			};
> > +
> > +			vref_reg: vrefddr {
> > +				regulator-boot-on;
> > +				regulator-always-on;
> > +			};
> > +
> > +			vgen1_reg: vgen1 {
> > +				regulator-min-microvolt = <800000>;
> > +				regulator-max-microvolt =
> > <1550000>;
> > +			};
> > +
> > +			vgen2_reg: vgen2 {
> > +				regulator-min-microvolt = <800000>;
> > +				regulator-max-microvolt =
> > <1550000>;
> > +			};
> > +
> > +			vgen3_reg: vgen3 {
> > +				regulator-min-microvolt =
> > <1800000>;
> > +				regulator-max-microvolt =
> > <3300000>;
> > +			};
> > +
> > +			vgen4_reg: vgen4 {
> > +				regulator-min-microvolt =
> > <1800000>;
> > +				regulator-max-microvolt =
> > <3300000>;
> > +				regulator-always-on;
> > +			};
> > +
> > +			vgen5_reg: vgen5 {
> > +				regulator-min-microvolt =
> > <1800000>;
> > +				regulator-max-microvolt =
> > <3300000>;
> > +				regulator-always-on;
> > +			};
> > +
> > +			vgen6_reg: vgen6 {
> > +				regulator-min-microvolt =
> > <1800000>;
> > +				regulator-max-microvolt =
> > <3300000>;
> > +				regulator-always-on;
> > +			};
> > +		};
> > +	};
> > +};
> > +
> > +&ldb {
> > +	status = "okay";
> > +
> > +	lvds0: lvds-channel at 0 {
> > +		fsl,data-mapping = "spwg";
> > +		fsl,data-width = <24>;
> > +		status = "okay";
> > +
> > +		port at 4 {
> > +			reg = <4>;
> > +
> > +			lvds0_out: endpoint {
> > +				remote-endpoint =
> > <&panel_in_lvds0>;
> > +			};
> > +		};
> > +	};
> > +};
> > +
> > +&pwm2 {
> > +	#pwm-cells = <3>;
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_pwm2>;
> > +	status = "okay";
> > +};
> > +
> > +&uart1 {
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_uart1>;
> > +	status = "okay";
> > +};
> > +
> > +&uart4 {
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_uart4>;
> > +	uart-has-rtscts;
> > +	status = "okay";
> > +};
> > +
> > +&usdhc2 {
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_usdhc2>;
> > +	cd-gpios = <&gpio1 4 GPIO_ACTIVE_LOW>;
> > +	bus-width = <4>;
> > +	status = "okay";
> > +};
> > +
> > +&usdhc3 {
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_usdhc3>;
> > +	bus-width = <8>;
> > +	non-removable;
> > +	status = "okay";
> > +};
> > +
> > +&weim {
> > +	pinctrl-names = "default";
> > +	pinctrl-0 = <&pinctrl_weim_nor &pinctrl_weim_cs0>;
> > +	#address-cells = <2>;
> > +	#size-cells = <1>;
> 
> These two properties can be saved from board dts since commit
> 1be81ea58607 ("ARM: dts: imx6: Add imx-weim parameters to dtsi's").

Ok, I will remove them.

> 
> Shawn
> 
> > +	ranges = <0 0 0x08000000 0x08000000>;
> > +	status = "okay";
> > +
> > +	nor at 0,0 {
> > +		compatible = "cfi-flash";
> > +		reg = <0 0 0x02000000>;
> > +		#address-cells = <1>;
> > +		#size-cells = <1>;
> > +		bank-width = <2>;
> > +		use-advanced-sector-protection;
> > +		fsl,weim-cs-timing = <0x00620081 0x00000001
> > 0x1c022000
> > +				0x0000c000 0x1404a38e 0x00000000>;
> > +	};
> > +};
> > -- 
> > 2.1.4
> > 


Best regards,

Lukasz Majewski

--

DENX Software Engineering GmbH,      Managing Director: Wolfgang Denk
HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany
Phone: (+49)-8142-66989-10 Fax: (+49)-8142-66989-80 Email: wd at denx.de

^ permalink raw reply


This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.