All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH 1/4] pinctrl: gemini: Add missing functions
@ 2017-10-28 13:37 ` Linus Walleij
  0 siblings, 0 replies; 22+ messages in thread
From: Linus Walleij @ 2017-10-28 13:37 UTC (permalink / raw)
  To: linux-gpio, Hans Ulli Kroll, Florian Fainelli
  Cc: Janos Laube, Paulius Zaleckas, linux-arm-kernel, Linus Walleij

Some two functions were missing from the Gemini pin control
driver. Noticed when trying to use ethernet. Fix it up by
adding them.

Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
---
 drivers/pinctrl/pinctrl-gemini.c | 10 ++++++++++
 1 file changed, 10 insertions(+)

diff --git a/drivers/pinctrl/pinctrl-gemini.c b/drivers/pinctrl/pinctrl-gemini.c
index 39e6221e7100..7ffd768c0e02 100644
--- a/drivers/pinctrl/pinctrl-gemini.c
+++ b/drivers/pinctrl/pinctrl-gemini.c
@@ -2074,6 +2074,16 @@ static const struct gemini_pmx_func gemini_pmx_functions[] = {
 		.num_groups = ARRAY_SIZE(satagrps),
 	},
 	{
+		.name = "usb",
+		.groups = usbgrps,
+		.num_groups = ARRAY_SIZE(usbgrps),
+	},
+	{
+		.name = "gmii",
+		.groups = gmiigrps,
+		.num_groups = ARRAY_SIZE(gmiigrps),
+	},
+	{
 		.name = "pci",
 		.groups = pcigrps,
 		.num_groups = ARRAY_SIZE(pcigrps),
-- 
2.13.6


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 1/4] pinctrl: gemini: Add missing functions
@ 2017-10-28 13:37 ` Linus Walleij
  0 siblings, 0 replies; 22+ messages in thread
From: Linus Walleij @ 2017-10-28 13:37 UTC (permalink / raw)
  To: linux-arm-kernel

Some two functions were missing from the Gemini pin control
driver. Noticed when trying to use ethernet. Fix it up by
adding them.

Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
---
 drivers/pinctrl/pinctrl-gemini.c | 10 ++++++++++
 1 file changed, 10 insertions(+)

diff --git a/drivers/pinctrl/pinctrl-gemini.c b/drivers/pinctrl/pinctrl-gemini.c
index 39e6221e7100..7ffd768c0e02 100644
--- a/drivers/pinctrl/pinctrl-gemini.c
+++ b/drivers/pinctrl/pinctrl-gemini.c
@@ -2074,6 +2074,16 @@ static const struct gemini_pmx_func gemini_pmx_functions[] = {
 		.num_groups = ARRAY_SIZE(satagrps),
 	},
 	{
+		.name = "usb",
+		.groups = usbgrps,
+		.num_groups = ARRAY_SIZE(usbgrps),
+	},
+	{
+		.name = "gmii",
+		.groups = gmiigrps,
+		.num_groups = ARRAY_SIZE(gmiigrps),
+	},
+	{
 		.name = "pci",
 		.groups = pcigrps,
 		.num_groups = ARRAY_SIZE(pcigrps),
-- 
2.13.6

^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 2/4] pinctrl: Add skew-delay pin config and bindings
  2017-10-28 13:37 ` Linus Walleij
@ 2017-10-28 13:37   ` Linus Walleij
  -1 siblings, 0 replies; 22+ messages in thread
From: Linus Walleij @ 2017-10-28 13:37 UTC (permalink / raw)
  To: linux-gpio, Hans Ulli Kroll, Florian Fainelli
  Cc: Janos Laube, Paulius Zaleckas, linux-arm-kernel, Linus Walleij,
	devicetree

Some pin controllers (such as the Gemini) can control the
expected clock skew and output delay on certain pins with a
sub-nanosecond granularity. This is typically done by shunting
in a number of double inverters in front of or behind the pin.
Make it possible to configure this with a generic binding.

Cc: devicetree@vger.kernel.org
Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
---
 Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt | 4 ++++
 drivers/pinctrl/pinconf-generic.c                              | 2 ++
 include/linux/pinctrl/pinconf-generic.h                        | 5 +++++
 3 files changed, 11 insertions(+)

diff --git a/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt b/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
index 4483cc31e531..ad9bbbba36e9 100644
--- a/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
+++ b/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
@@ -271,6 +271,10 @@ output-high		- set the pin to output mode with high level
 sleep-hardware-state	- indicate this is sleep related state which will be programmed
 			  into the registers for the sleep state.
 slew-rate		- set the slew rate
+skew-delay		- this affects the expected clock skew on input pins
+			  and the delay before latching a value to an output
+			  pin. Typically indicates how many double-inverters are
+			  used to delay the signal.
 
 For example:
 
diff --git a/drivers/pinctrl/pinconf-generic.c b/drivers/pinctrl/pinconf-generic.c
index 8eaa25c3384f..b4f7f8a458ea 100644
--- a/drivers/pinctrl/pinconf-generic.c
+++ b/drivers/pinctrl/pinconf-generic.c
@@ -49,6 +49,7 @@ static const struct pin_config_item conf_items[] = {
 	PCONFDUMP(PIN_CONFIG_POWER_SOURCE, "pin power source", "selector", true),
 	PCONFDUMP(PIN_CONFIG_SLEEP_HARDWARE_STATE, "sleep hardware state", NULL, false),
 	PCONFDUMP(PIN_CONFIG_SLEW_RATE, "slew rate", NULL, true),
+	PCONFDUMP(PIN_CONFIG_SKEW_DELAY, "skew delay", NULL, true),
 };
 
 static void pinconf_generic_dump_one(struct pinctrl_dev *pctldev,
@@ -181,6 +182,7 @@ static const struct pinconf_generic_params dt_params[] = {
 	{ "power-source", PIN_CONFIG_POWER_SOURCE, 0 },
 	{ "sleep-hardware-state", PIN_CONFIG_SLEEP_HARDWARE_STATE, 0 },
 	{ "slew-rate", PIN_CONFIG_SLEW_RATE, 0 },
+	{ "skew-delay", PIN_CONFIG_SKEW_DELAY, 0 },
 };
 
 /**
diff --git a/include/linux/pinctrl/pinconf-generic.h b/include/linux/pinctrl/pinconf-generic.h
index 5d8bc7f21c2a..ec6dadcc1fde 100644
--- a/include/linux/pinctrl/pinconf-generic.h
+++ b/include/linux/pinctrl/pinconf-generic.h
@@ -90,6 +90,10 @@
  * @PIN_CONFIG_SLEW_RATE: if the pin can select slew rate, the argument to
  *	this parameter (on a custom format) tells the driver which alternative
  *	slew rate to use.
+ * @PIN_CONFIG_SKEW_DELAY: if the pin has programmable skew rate (on inputs)
+ *	or latch delay (on outputs) this parameter (in a custom format)
+ *	specifies the clock skew or latch delay. It typically controls how
+ *	many double inverters are put in front of the line.
  * @PIN_CONFIG_END: this is the last enumerator for pin configurations, if
  *	you need to pass in custom configurations to the pin controller, use
  *	PIN_CONFIG_END+1 as the base offset.
@@ -117,6 +121,7 @@ enum pin_config_param {
 	PIN_CONFIG_POWER_SOURCE,
 	PIN_CONFIG_SLEEP_HARDWARE_STATE,
 	PIN_CONFIG_SLEW_RATE,
+	PIN_CONFIG_SKEW_DELAY,
 	PIN_CONFIG_END = 0x7F,
 	PIN_CONFIG_MAX = 0xFF,
 };
-- 
2.13.6


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 2/4] pinctrl: Add skew-delay pin config and bindings
@ 2017-10-28 13:37   ` Linus Walleij
  0 siblings, 0 replies; 22+ messages in thread
From: Linus Walleij @ 2017-10-28 13:37 UTC (permalink / raw)
  To: linux-arm-kernel

Some pin controllers (such as the Gemini) can control the
expected clock skew and output delay on certain pins with a
sub-nanosecond granularity. This is typically done by shunting
in a number of double inverters in front of or behind the pin.
Make it possible to configure this with a generic binding.

Cc: devicetree at vger.kernel.org
Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
---
 Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt | 4 ++++
 drivers/pinctrl/pinconf-generic.c                              | 2 ++
 include/linux/pinctrl/pinconf-generic.h                        | 5 +++++
 3 files changed, 11 insertions(+)

diff --git a/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt b/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
index 4483cc31e531..ad9bbbba36e9 100644
--- a/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
+++ b/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
@@ -271,6 +271,10 @@ output-high		- set the pin to output mode with high level
 sleep-hardware-state	- indicate this is sleep related state which will be programmed
 			  into the registers for the sleep state.
 slew-rate		- set the slew rate
+skew-delay		- this affects the expected clock skew on input pins
+			  and the delay before latching a value to an output
+			  pin. Typically indicates how many double-inverters are
+			  used to delay the signal.
 
 For example:
 
diff --git a/drivers/pinctrl/pinconf-generic.c b/drivers/pinctrl/pinconf-generic.c
index 8eaa25c3384f..b4f7f8a458ea 100644
--- a/drivers/pinctrl/pinconf-generic.c
+++ b/drivers/pinctrl/pinconf-generic.c
@@ -49,6 +49,7 @@ static const struct pin_config_item conf_items[] = {
 	PCONFDUMP(PIN_CONFIG_POWER_SOURCE, "pin power source", "selector", true),
 	PCONFDUMP(PIN_CONFIG_SLEEP_HARDWARE_STATE, "sleep hardware state", NULL, false),
 	PCONFDUMP(PIN_CONFIG_SLEW_RATE, "slew rate", NULL, true),
+	PCONFDUMP(PIN_CONFIG_SKEW_DELAY, "skew delay", NULL, true),
 };
 
 static void pinconf_generic_dump_one(struct pinctrl_dev *pctldev,
@@ -181,6 +182,7 @@ static const struct pinconf_generic_params dt_params[] = {
 	{ "power-source", PIN_CONFIG_POWER_SOURCE, 0 },
 	{ "sleep-hardware-state", PIN_CONFIG_SLEEP_HARDWARE_STATE, 0 },
 	{ "slew-rate", PIN_CONFIG_SLEW_RATE, 0 },
+	{ "skew-delay", PIN_CONFIG_SKEW_DELAY, 0 },
 };
 
 /**
diff --git a/include/linux/pinctrl/pinconf-generic.h b/include/linux/pinctrl/pinconf-generic.h
index 5d8bc7f21c2a..ec6dadcc1fde 100644
--- a/include/linux/pinctrl/pinconf-generic.h
+++ b/include/linux/pinctrl/pinconf-generic.h
@@ -90,6 +90,10 @@
  * @PIN_CONFIG_SLEW_RATE: if the pin can select slew rate, the argument to
  *	this parameter (on a custom format) tells the driver which alternative
  *	slew rate to use.
+ * @PIN_CONFIG_SKEW_DELAY: if the pin has programmable skew rate (on inputs)
+ *	or latch delay (on outputs) this parameter (in a custom format)
+ *	specifies the clock skew or latch delay. It typically controls how
+ *	many double inverters are put in front of the line.
  * @PIN_CONFIG_END: this is the last enumerator for pin configurations, if
  *	you need to pass in custom configurations to the pin controller, use
  *	PIN_CONFIG_END+1 as the base offset.
@@ -117,6 +121,7 @@ enum pin_config_param {
 	PIN_CONFIG_POWER_SOURCE,
 	PIN_CONFIG_SLEEP_HARDWARE_STATE,
 	PIN_CONFIG_SLEW_RATE,
+	PIN_CONFIG_SKEW_DELAY,
 	PIN_CONFIG_END = 0x7F,
 	PIN_CONFIG_MAX = 0xFF,
 };
-- 
2.13.6

^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 3/4] pinctrl: gemini: Use generic DT parser
  2017-10-28 13:37 ` Linus Walleij
@ 2017-10-28 13:37   ` Linus Walleij
  -1 siblings, 0 replies; 22+ messages in thread
From: Linus Walleij @ 2017-10-28 13:37 UTC (permalink / raw)
  To: linux-gpio, Hans Ulli Kroll, Florian Fainelli
  Cc: Janos Laube, Paulius Zaleckas, linux-arm-kernel, Linus Walleij

We can just use the generic Device Tree parser code
in this driver and save some code.

Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
---
 drivers/pinctrl/Kconfig          |  1 +
 drivers/pinctrl/pinctrl-gemini.c | 66 +++-------------------------------------
 2 files changed, 5 insertions(+), 62 deletions(-)

diff --git a/drivers/pinctrl/Kconfig b/drivers/pinctrl/Kconfig
index 1778cf4f81c7..98b2d5dcbda7 100644
--- a/drivers/pinctrl/Kconfig
+++ b/drivers/pinctrl/Kconfig
@@ -151,6 +151,7 @@ config PINCTRL_GEMINI
 	depends on ARCH_GEMINI
 	default ARCH_GEMINI
 	select PINMUX
+	select GENERIC_PINCONF
 	select MFD_SYSCON
 
 config PINCTRL_MCP23S08
diff --git a/drivers/pinctrl/pinctrl-gemini.c b/drivers/pinctrl/pinctrl-gemini.c
index 7ffd768c0e02..18fb5ff8a442 100644
--- a/drivers/pinctrl/pinctrl-gemini.c
+++ b/drivers/pinctrl/pinctrl-gemini.c
@@ -13,6 +13,8 @@
 #include <linux/pinctrl/machine.h>
 #include <linux/pinctrl/pinctrl.h>
 #include <linux/pinctrl/pinmux.h>
+#include <linux/pinctrl/pinconf.h>
+#include <linux/pinctrl/pinconf-generic.h>
 #include <linux/platform_device.h>
 #include <linux/slab.h>
 #include <linux/regmap.h>
@@ -1918,73 +1920,13 @@ static void gemini_pin_dbg_show(struct pinctrl_dev *pctldev, struct seq_file *s,
 	seq_printf(s, " " DRIVER_NAME);
 }
 
-static int gemini_pinctrl_dt_subnode_to_map(struct pinctrl_dev *pctldev,
-					    struct device_node *np,
-					    struct pinctrl_map **map,
-					    unsigned int *reserved_maps,
-					    unsigned int *num_maps)
-{
-	int ret;
-	const char *function = NULL;
-	const char *group;
-	struct property *prop;
-
-	ret = of_property_read_string(np, "function", &function);
-	if (ret < 0)
-		return ret;
-
-	ret = of_property_count_strings(np, "groups");
-	if (ret < 0)
-		return ret;
-
-	ret = pinctrl_utils_reserve_map(pctldev, map, reserved_maps,
-					num_maps, ret);
-	if (ret < 0)
-		return ret;
-
-	of_property_for_each_string(np, "groups", prop, group) {
-		ret = pinctrl_utils_add_map_mux(pctldev, map, reserved_maps,
-						num_maps, group, function);
-		if (ret < 0)
-			return ret;
-		pr_debug("ADDED FUNCTION %s <-> GROUP %s\n",
-			 function, group);
-	}
-
-	return 0;
-}
-
-static int gemini_pinctrl_dt_node_to_map(struct pinctrl_dev *pctldev,
-				struct device_node *np_config,
-				struct pinctrl_map **map,
-				unsigned int *num_maps)
-{
-	unsigned int reserved_maps = 0;
-	struct device_node *np;
-	int ret;
-
-	*map = NULL;
-	*num_maps = 0;
-
-	for_each_child_of_node(np_config, np) {
-		ret = gemini_pinctrl_dt_subnode_to_map(pctldev, np, map,
-					&reserved_maps, num_maps);
-		if (ret < 0) {
-			pinctrl_utils_free_map(pctldev, *map, *num_maps);
-			return ret;
-		}
-	}
-
-	return 0;
-};
-
 static const struct pinctrl_ops gemini_pctrl_ops = {
 	.get_groups_count = gemini_get_groups_count,
 	.get_group_name = gemini_get_group_name,
 	.get_group_pins = gemini_get_group_pins,
 	.pin_dbg_show = gemini_pin_dbg_show,
-	.dt_node_to_map = gemini_pinctrl_dt_node_to_map,
-	.dt_free_map = pinctrl_utils_free_map,
+	.dt_node_to_map = pinconf_generic_dt_node_to_map_group,
+	.dt_free_map = pinconf_generic_dt_free_map,
 };
 
 /**
-- 
2.13.6


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 3/4] pinctrl: gemini: Use generic DT parser
@ 2017-10-28 13:37   ` Linus Walleij
  0 siblings, 0 replies; 22+ messages in thread
From: Linus Walleij @ 2017-10-28 13:37 UTC (permalink / raw)
  To: linux-arm-kernel

We can just use the generic Device Tree parser code
in this driver and save some code.

Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
---
 drivers/pinctrl/Kconfig          |  1 +
 drivers/pinctrl/pinctrl-gemini.c | 66 +++-------------------------------------
 2 files changed, 5 insertions(+), 62 deletions(-)

diff --git a/drivers/pinctrl/Kconfig b/drivers/pinctrl/Kconfig
index 1778cf4f81c7..98b2d5dcbda7 100644
--- a/drivers/pinctrl/Kconfig
+++ b/drivers/pinctrl/Kconfig
@@ -151,6 +151,7 @@ config PINCTRL_GEMINI
 	depends on ARCH_GEMINI
 	default ARCH_GEMINI
 	select PINMUX
+	select GENERIC_PINCONF
 	select MFD_SYSCON
 
 config PINCTRL_MCP23S08
diff --git a/drivers/pinctrl/pinctrl-gemini.c b/drivers/pinctrl/pinctrl-gemini.c
index 7ffd768c0e02..18fb5ff8a442 100644
--- a/drivers/pinctrl/pinctrl-gemini.c
+++ b/drivers/pinctrl/pinctrl-gemini.c
@@ -13,6 +13,8 @@
 #include <linux/pinctrl/machine.h>
 #include <linux/pinctrl/pinctrl.h>
 #include <linux/pinctrl/pinmux.h>
+#include <linux/pinctrl/pinconf.h>
+#include <linux/pinctrl/pinconf-generic.h>
 #include <linux/platform_device.h>
 #include <linux/slab.h>
 #include <linux/regmap.h>
@@ -1918,73 +1920,13 @@ static void gemini_pin_dbg_show(struct pinctrl_dev *pctldev, struct seq_file *s,
 	seq_printf(s, " " DRIVER_NAME);
 }
 
-static int gemini_pinctrl_dt_subnode_to_map(struct pinctrl_dev *pctldev,
-					    struct device_node *np,
-					    struct pinctrl_map **map,
-					    unsigned int *reserved_maps,
-					    unsigned int *num_maps)
-{
-	int ret;
-	const char *function = NULL;
-	const char *group;
-	struct property *prop;
-
-	ret = of_property_read_string(np, "function", &function);
-	if (ret < 0)
-		return ret;
-
-	ret = of_property_count_strings(np, "groups");
-	if (ret < 0)
-		return ret;
-
-	ret = pinctrl_utils_reserve_map(pctldev, map, reserved_maps,
-					num_maps, ret);
-	if (ret < 0)
-		return ret;
-
-	of_property_for_each_string(np, "groups", prop, group) {
-		ret = pinctrl_utils_add_map_mux(pctldev, map, reserved_maps,
-						num_maps, group, function);
-		if (ret < 0)
-			return ret;
-		pr_debug("ADDED FUNCTION %s <-> GROUP %s\n",
-			 function, group);
-	}
-
-	return 0;
-}
-
-static int gemini_pinctrl_dt_node_to_map(struct pinctrl_dev *pctldev,
-				struct device_node *np_config,
-				struct pinctrl_map **map,
-				unsigned int *num_maps)
-{
-	unsigned int reserved_maps = 0;
-	struct device_node *np;
-	int ret;
-
-	*map = NULL;
-	*num_maps = 0;
-
-	for_each_child_of_node(np_config, np) {
-		ret = gemini_pinctrl_dt_subnode_to_map(pctldev, np, map,
-					&reserved_maps, num_maps);
-		if (ret < 0) {
-			pinctrl_utils_free_map(pctldev, *map, *num_maps);
-			return ret;
-		}
-	}
-
-	return 0;
-};
-
 static const struct pinctrl_ops gemini_pctrl_ops = {
 	.get_groups_count = gemini_get_groups_count,
 	.get_group_name = gemini_get_group_name,
 	.get_group_pins = gemini_get_group_pins,
 	.pin_dbg_show = gemini_pin_dbg_show,
-	.dt_node_to_map = gemini_pinctrl_dt_node_to_map,
-	.dt_free_map = pinctrl_utils_free_map,
+	.dt_node_to_map = pinconf_generic_dt_node_to_map_group,
+	.dt_free_map = pinconf_generic_dt_free_map,
 };
 
 /**
-- 
2.13.6

^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 4/4] pinctrl: gemini: Implement clock skew/delay config
  2017-10-28 13:37 ` Linus Walleij
@ 2017-10-28 13:37   ` Linus Walleij
  -1 siblings, 0 replies; 22+ messages in thread
From: Linus Walleij @ 2017-10-28 13:37 UTC (permalink / raw)
  To: linux-gpio, Hans Ulli Kroll, Florian Fainelli
  Cc: Janos Laube, Paulius Zaleckas, linux-arm-kernel, Linus Walleij

This enabled pin config on the Gemini driver and implements
pin skew/delay so that the ethernet pins clocking can be
properly configured.

Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
---
 .../bindings/pinctrl/cortina,gemini-pinctrl.txt    |  10 +-
 drivers/pinctrl/pinctrl-gemini.c                   | 178 ++++++++++++++++++++-
 2 files changed, 182 insertions(+), 6 deletions(-)

diff --git a/Documentation/devicetree/bindings/pinctrl/cortina,gemini-pinctrl.txt b/Documentation/devicetree/bindings/pinctrl/cortina,gemini-pinctrl.txt
index 61466c58faae..d857b67fab72 100644
--- a/Documentation/devicetree/bindings/pinctrl/cortina,gemini-pinctrl.txt
+++ b/Documentation/devicetree/bindings/pinctrl/cortina,gemini-pinctrl.txt
@@ -9,8 +9,14 @@ The pin controller node must be a subnode of the system controller node.
 Required properties:
 - compatible: "cortina,gemini-pinctrl"
 
-Subnodes of the pin controller contain pin control multiplexing set-up.
-Please refer to pinctrl-bindings.txt for generic pin multiplexing nodes.
+Subnodes of the pin controller contain pin control multiplexing set-up
+and pin configuration of individual pins.
+
+Please refer to pinctrl-bindings.txt for generic pin multiplexing nodes
+and generic pin config nodes.
+
+Supported configurations:
+- skew-delay is supported on the Ethernet pins
 
 Example:
 
diff --git a/drivers/pinctrl/pinctrl-gemini.c b/drivers/pinctrl/pinctrl-gemini.c
index 18fb5ff8a442..bd6133f06759 100644
--- a/drivers/pinctrl/pinctrl-gemini.c
+++ b/drivers/pinctrl/pinctrl-gemini.c
@@ -24,6 +24,19 @@
 #define DRIVER_NAME "pinctrl-gemini"
 
 /**
+ * struct gemini_pin_conf - information about configuring a pin
+ * @pin: the pin number
+ * @reg: config register
+ * @mask: the bits affecting the configuration of the pin
+ */
+struct gemini_pin_conf {
+	unsigned int pin;
+	u32 reg;
+	u32 mask;
+};
+
+/**
+ * struct gemini_pmx - state holder for the gemini pin controller
  * @dev: a pointer back to containing device
  * @virtbase: the offset to the controller in virtual memory
  * @map: regmap to access registers
@@ -31,6 +44,8 @@
  * @is_3516: whether the SoC/package is the 3516 variant
  * @flash_pin: whether the flash pin (extended pins for parallel
  * flash) is set
+ * @confs: pin config information
+ * @nconfs: number of pin config information items
  */
 struct gemini_pmx {
 	struct device *dev;
@@ -39,6 +54,8 @@ struct gemini_pmx {
 	bool is_3512;
 	bool is_3516;
 	bool flash_pin;
+	const struct gemini_pin_conf *confs;
+	unsigned int nconfs;
 };
 
 /**
@@ -59,6 +76,13 @@ struct gemini_pin_group {
 	u32 value;
 };
 
+/* Some straight-forward control registers */
+#define GLOBAL_WORD_ID		0x00
+#define GLOBAL_STATUS		0x04
+#define GLOBAL_STATUS_FLPIN	BIT(20)
+#define GLOBAL_GMAC_CTRL_SKEW	0x1c
+#define GLOBAL_GMAC0_DATA_SKEW	0x20
+#define GLOBAL_GMAC1_DATA_SKEW	0x24
 /*
  * Global Miscellaneous Control Register
  * This register controls all Gemini pad/pin multiplexing
@@ -71,9 +95,6 @@ struct gemini_pin_group {
  *   DISABLED again. So you select a flash configuration once, and then
  *   you are stuck with it.
  */
-#define GLOBAL_WORD_ID		0x00
-#define GLOBAL_STATUS		0x04
-#define GLOBAL_STATUS_FLPIN	BIT(20)
 #define GLOBAL_MISC_CTRL	0x30
 #define TVC_CLK_PAD_ENABLE	BIT(20)
 #define PCI_CLK_PAD_ENABLE	BIT(17)
@@ -1925,7 +1946,7 @@ static const struct pinctrl_ops gemini_pctrl_ops = {
 	.get_group_name = gemini_get_group_name,
 	.get_group_pins = gemini_get_group_pins,
 	.pin_dbg_show = gemini_pin_dbg_show,
-	.dt_node_to_map = pinconf_generic_dt_node_to_map_group,
+	.dt_node_to_map = pinconf_generic_dt_node_to_map_all,
 	.dt_free_map = pinconf_generic_dt_free_map,
 };
 
@@ -2203,10 +2224,155 @@ static const struct pinmux_ops gemini_pmx_ops = {
 	.set_mux = gemini_pmx_set_mux,
 };
 
+#define GEMINI_CFGPIN(_n, _r, _lb, _hb) {	\
+	.pin = _n,				\
+	.reg = _r,				\
+	.mask = GENMASK(_hb, _lb)		\
+}
+
+static const struct gemini_pin_conf gemini_confs_3512[] = {
+	GEMINI_CFGPIN(259, GLOBAL_GMAC_CTRL_SKEW, 0, 3), /* GMAC0 RXDV */
+	GEMINI_CFGPIN(277, GLOBAL_GMAC_CTRL_SKEW, 4, 7), /* GMAC0 RXC */
+	GEMINI_CFGPIN(241, GLOBAL_GMAC_CTRL_SKEW, 8, 11), /* GMAC0 TXEN */
+	GEMINI_CFGPIN(312, GLOBAL_GMAC_CTRL_SKEW, 12, 15), /* GMAC0 TXC */
+	GEMINI_CFGPIN(298, GLOBAL_GMAC_CTRL_SKEW, 16, 19), /* GMAC1 RXDV */
+	GEMINI_CFGPIN(280, GLOBAL_GMAC_CTRL_SKEW, 20, 23), /* GMAC1 RXC */
+	GEMINI_CFGPIN(316, GLOBAL_GMAC_CTRL_SKEW, 24, 27), /* GMAC1 TXEN */
+	GEMINI_CFGPIN(243, GLOBAL_GMAC_CTRL_SKEW, 28, 31), /* GMAC1 TXC */
+	GEMINI_CFGPIN(295, GLOBAL_GMAC0_DATA_SKEW, 0, 3), /* GMAC0 RXD0 */
+	GEMINI_CFGPIN(313, GLOBAL_GMAC0_DATA_SKEW, 4, 7), /* GMAC0 RXD1 */
+	GEMINI_CFGPIN(242, GLOBAL_GMAC0_DATA_SKEW, 8, 11), /* GMAC0 RXD2 */
+	GEMINI_CFGPIN(260, GLOBAL_GMAC0_DATA_SKEW, 12, 15), /* GMAC0 RXD3 */
+	GEMINI_CFGPIN(294, GLOBAL_GMAC0_DATA_SKEW, 16, 19), /* GMAC0 TXD0 */
+	GEMINI_CFGPIN(276, GLOBAL_GMAC0_DATA_SKEW, 20, 23), /* GMAC0 TXD1 */
+	GEMINI_CFGPIN(258, GLOBAL_GMAC0_DATA_SKEW, 24, 27), /* GMAC0 TXD2 */
+	GEMINI_CFGPIN(240, GLOBAL_GMAC0_DATA_SKEW, 28, 31), /* GMAC0 TXD3 */
+	GEMINI_CFGPIN(262, GLOBAL_GMAC1_DATA_SKEW, 0, 3), /* GMAC1 RXD0 */
+	GEMINI_CFGPIN(244, GLOBAL_GMAC1_DATA_SKEW, 4, 7), /* GMAC1 RXD1 */
+	GEMINI_CFGPIN(317, GLOBAL_GMAC1_DATA_SKEW, 8, 11), /* GMAC1 RXD2 */
+	GEMINI_CFGPIN(299, GLOBAL_GMAC1_DATA_SKEW, 12, 15), /* GMAC1 RXD3 */
+	GEMINI_CFGPIN(261, GLOBAL_GMAC1_DATA_SKEW, 16, 19), /* GMAC1 TXD0 */
+	GEMINI_CFGPIN(279, GLOBAL_GMAC1_DATA_SKEW, 20, 23), /* GMAC1 TXD1 */
+	GEMINI_CFGPIN(297, GLOBAL_GMAC1_DATA_SKEW, 24, 27), /* GMAC1 TXD2 */
+	GEMINI_CFGPIN(315, GLOBAL_GMAC1_DATA_SKEW, 28, 31), /* GMAC1 TXD3 */
+};
+
+static const struct gemini_pin_conf gemini_confs_3516[] = {
+	GEMINI_CFGPIN(347, GLOBAL_GMAC_CTRL_SKEW, 0, 3), /* GMAC0 RXDV */
+	GEMINI_CFGPIN(386, GLOBAL_GMAC_CTRL_SKEW, 4, 7), /* GMAC0 RXC */
+	GEMINI_CFGPIN(307, GLOBAL_GMAC_CTRL_SKEW, 8, 11), /* GMAC0 TXEN */
+	GEMINI_CFGPIN(327, GLOBAL_GMAC_CTRL_SKEW, 12, 15), /* GMAC0 TXC */
+	GEMINI_CFGPIN(309, GLOBAL_GMAC_CTRL_SKEW, 16, 19), /* GMAC1 RXDV */
+	GEMINI_CFGPIN(390, GLOBAL_GMAC_CTRL_SKEW, 20, 23), /* GMAC1 RXC */
+	GEMINI_CFGPIN(370, GLOBAL_GMAC_CTRL_SKEW, 24, 27), /* GMAC1 TXEN */
+	GEMINI_CFGPIN(350, GLOBAL_GMAC_CTRL_SKEW, 28, 31), /* GMAC1 TXC */
+	GEMINI_CFGPIN(367, GLOBAL_GMAC0_DATA_SKEW, 0, 3), /* GMAC0 RXD0 */
+	GEMINI_CFGPIN(348, GLOBAL_GMAC0_DATA_SKEW, 4, 7), /* GMAC0 RXD1 */
+	GEMINI_CFGPIN(387, GLOBAL_GMAC0_DATA_SKEW, 8, 11), /* GMAC0 RXD2 */
+	GEMINI_CFGPIN(328, GLOBAL_GMAC0_DATA_SKEW, 12, 15), /* GMAC0 RXD3 */
+	GEMINI_CFGPIN(306, GLOBAL_GMAC0_DATA_SKEW, 16, 19), /* GMAC0 TXD0 */
+	GEMINI_CFGPIN(325, GLOBAL_GMAC0_DATA_SKEW, 20, 23), /* GMAC0 TXD1 */
+	GEMINI_CFGPIN(346, GLOBAL_GMAC0_DATA_SKEW, 24, 27), /* GMAC0 TXD2 */
+	GEMINI_CFGPIN(326, GLOBAL_GMAC0_DATA_SKEW, 28, 31), /* GMAC0 TXD3 */
+	GEMINI_CFGPIN(391, GLOBAL_GMAC1_DATA_SKEW, 0, 3), /* GMAC1 RXD0 */
+	GEMINI_CFGPIN(351, GLOBAL_GMAC1_DATA_SKEW, 4, 7), /* GMAC1 RXD1 */
+	GEMINI_CFGPIN(310, GLOBAL_GMAC1_DATA_SKEW, 8, 11), /* GMAC1 RXD2 */
+	GEMINI_CFGPIN(371, GLOBAL_GMAC1_DATA_SKEW, 12, 15), /* GMAC1 RXD3 */
+	GEMINI_CFGPIN(329, GLOBAL_GMAC1_DATA_SKEW, 16, 19), /* GMAC1 TXD0 */
+	GEMINI_CFGPIN(389, GLOBAL_GMAC1_DATA_SKEW, 20, 23), /* GMAC1 TXD1 */
+	GEMINI_CFGPIN(369, GLOBAL_GMAC1_DATA_SKEW, 24, 27), /* GMAC1 TXD2 */
+	GEMINI_CFGPIN(308, GLOBAL_GMAC1_DATA_SKEW, 28, 31), /* GMAC1 TXD3 */
+};
+
+static const struct gemini_pin_conf *gemini_get_pin_conf(struct gemini_pmx *pmx,
+							 unsigned int pin)
+{
+	const struct gemini_pin_conf *retconf;
+	int i;
+
+	for (i = 0; i < pmx->nconfs; i++) {
+		retconf = &gemini_confs_3516[i];
+		if (retconf->pin == pin)
+			return retconf;
+	}
+	return NULL;
+}
+
+static int gemini_pinconf_get(struct pinctrl_dev *pctldev, unsigned int pin,
+			      unsigned long *config)
+{
+	struct gemini_pmx *pmx = pinctrl_dev_get_drvdata(pctldev);
+	enum pin_config_param param = pinconf_to_config_param(*config);
+	const struct gemini_pin_conf *conf;
+	u32 val;
+
+	switch (param) {
+	case PIN_CONFIG_SKEW_DELAY:
+		conf = gemini_get_pin_conf(pmx, pin);
+		if (!conf)
+			return -ENOTSUPP;
+		regmap_read(pmx->map, conf->reg, &val);
+		val &= conf->mask;
+		val >>= (ffs(conf->mask) - 1);
+		*config = pinconf_to_config_packed(PIN_CONFIG_SKEW_DELAY, val);
+		break;
+	default:
+		return -ENOTSUPP;
+	}
+
+	return 0;
+}
+
+static int gemini_pinconf_set(struct pinctrl_dev *pctldev, unsigned int pin,
+			      unsigned long *configs, unsigned int num_configs)
+{
+	struct gemini_pmx *pmx = pinctrl_dev_get_drvdata(pctldev);
+	const struct gemini_pin_conf *conf;
+	enum pin_config_param param;
+	u32 arg;
+	int ret = 0;
+	int i;
+
+	for (i = 0; i < num_configs; i++) {
+		param = pinconf_to_config_param(configs[i]);
+		arg = pinconf_to_config_argument(configs[i]);
+
+		switch (param) {
+		case PIN_CONFIG_SKEW_DELAY:
+			if (arg > 0xf)
+				return -EINVAL;
+			conf = gemini_get_pin_conf(pmx, pin);
+			if (!conf) {
+				dev_err(pmx->dev,
+					"invalid pin for skew delay %d\n", pin);
+				return -ENOTSUPP;
+			}
+			arg <<= (ffs(conf->mask) - 1);
+			dev_dbg(pmx->dev,
+				"set pin %d to skew delay mask %08x, val %08x\n",
+				pin, conf->mask, arg);
+			regmap_update_bits(pmx->map, conf->reg, conf->mask, arg);
+			break;
+		default:
+			dev_err(pmx->dev, "Invalid config param %04x\n", param);
+			return -ENOTSUPP;
+		}
+	}
+
+	return ret;
+}
+
+static const struct pinconf_ops gemini_pinconf_ops = {
+	.pin_config_get = gemini_pinconf_get,
+	.pin_config_set = gemini_pinconf_set,
+	.is_generic = true,
+};
+
 static struct pinctrl_desc gemini_pmx_desc = {
 	.name = DRIVER_NAME,
 	.pctlops = &gemini_pctrl_ops,
 	.pmxops = &gemini_pmx_ops,
+	.confops = &gemini_pinconf_ops,
 	.owner = THIS_MODULE,
 };
 
@@ -2249,11 +2415,15 @@ static int gemini_pmx_probe(struct platform_device *pdev)
 	val &= 0xffff;
 	if (val == 0x3512) {
 		pmx->is_3512 = true;
+		pmx->confs = gemini_confs_3512;
+		pmx->nconfs = ARRAY_SIZE(gemini_confs_3512);
 		gemini_pmx_desc.pins = gemini_3512_pins;
 		gemini_pmx_desc.npins = ARRAY_SIZE(gemini_3512_pins);
 		dev_info(dev, "detected 3512 chip variant\n");
 	} else if (val == 0x3516) {
 		pmx->is_3516 = true;
+		pmx->confs = gemini_confs_3516;
+		pmx->nconfs = ARRAY_SIZE(gemini_confs_3516);
 		gemini_pmx_desc.pins = gemini_3516_pins;
 		gemini_pmx_desc.npins = ARRAY_SIZE(gemini_3516_pins);
 		dev_info(dev, "detected 3516 chip variant\n");
-- 
2.13.6


^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [PATCH 4/4] pinctrl: gemini: Implement clock skew/delay config
@ 2017-10-28 13:37   ` Linus Walleij
  0 siblings, 0 replies; 22+ messages in thread
From: Linus Walleij @ 2017-10-28 13:37 UTC (permalink / raw)
  To: linux-arm-kernel

This enabled pin config on the Gemini driver and implements
pin skew/delay so that the ethernet pins clocking can be
properly configured.

Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
---
 .../bindings/pinctrl/cortina,gemini-pinctrl.txt    |  10 +-
 drivers/pinctrl/pinctrl-gemini.c                   | 178 ++++++++++++++++++++-
 2 files changed, 182 insertions(+), 6 deletions(-)

diff --git a/Documentation/devicetree/bindings/pinctrl/cortina,gemini-pinctrl.txt b/Documentation/devicetree/bindings/pinctrl/cortina,gemini-pinctrl.txt
index 61466c58faae..d857b67fab72 100644
--- a/Documentation/devicetree/bindings/pinctrl/cortina,gemini-pinctrl.txt
+++ b/Documentation/devicetree/bindings/pinctrl/cortina,gemini-pinctrl.txt
@@ -9,8 +9,14 @@ The pin controller node must be a subnode of the system controller node.
 Required properties:
 - compatible: "cortina,gemini-pinctrl"
 
-Subnodes of the pin controller contain pin control multiplexing set-up.
-Please refer to pinctrl-bindings.txt for generic pin multiplexing nodes.
+Subnodes of the pin controller contain pin control multiplexing set-up
+and pin configuration of individual pins.
+
+Please refer to pinctrl-bindings.txt for generic pin multiplexing nodes
+and generic pin config nodes.
+
+Supported configurations:
+- skew-delay is supported on the Ethernet pins
 
 Example:
 
diff --git a/drivers/pinctrl/pinctrl-gemini.c b/drivers/pinctrl/pinctrl-gemini.c
index 18fb5ff8a442..bd6133f06759 100644
--- a/drivers/pinctrl/pinctrl-gemini.c
+++ b/drivers/pinctrl/pinctrl-gemini.c
@@ -24,6 +24,19 @@
 #define DRIVER_NAME "pinctrl-gemini"
 
 /**
+ * struct gemini_pin_conf - information about configuring a pin
+ * @pin: the pin number
+ * @reg: config register
+ * @mask: the bits affecting the configuration of the pin
+ */
+struct gemini_pin_conf {
+	unsigned int pin;
+	u32 reg;
+	u32 mask;
+};
+
+/**
+ * struct gemini_pmx - state holder for the gemini pin controller
  * @dev: a pointer back to containing device
  * @virtbase: the offset to the controller in virtual memory
  * @map: regmap to access registers
@@ -31,6 +44,8 @@
  * @is_3516: whether the SoC/package is the 3516 variant
  * @flash_pin: whether the flash pin (extended pins for parallel
  * flash) is set
+ * @confs: pin config information
+ * @nconfs: number of pin config information items
  */
 struct gemini_pmx {
 	struct device *dev;
@@ -39,6 +54,8 @@ struct gemini_pmx {
 	bool is_3512;
 	bool is_3516;
 	bool flash_pin;
+	const struct gemini_pin_conf *confs;
+	unsigned int nconfs;
 };
 
 /**
@@ -59,6 +76,13 @@ struct gemini_pin_group {
 	u32 value;
 };
 
+/* Some straight-forward control registers */
+#define GLOBAL_WORD_ID		0x00
+#define GLOBAL_STATUS		0x04
+#define GLOBAL_STATUS_FLPIN	BIT(20)
+#define GLOBAL_GMAC_CTRL_SKEW	0x1c
+#define GLOBAL_GMAC0_DATA_SKEW	0x20
+#define GLOBAL_GMAC1_DATA_SKEW	0x24
 /*
  * Global Miscellaneous Control Register
  * This register controls all Gemini pad/pin multiplexing
@@ -71,9 +95,6 @@ struct gemini_pin_group {
  *   DISABLED again. So you select a flash configuration once, and then
  *   you are stuck with it.
  */
-#define GLOBAL_WORD_ID		0x00
-#define GLOBAL_STATUS		0x04
-#define GLOBAL_STATUS_FLPIN	BIT(20)
 #define GLOBAL_MISC_CTRL	0x30
 #define TVC_CLK_PAD_ENABLE	BIT(20)
 #define PCI_CLK_PAD_ENABLE	BIT(17)
@@ -1925,7 +1946,7 @@ static const struct pinctrl_ops gemini_pctrl_ops = {
 	.get_group_name = gemini_get_group_name,
 	.get_group_pins = gemini_get_group_pins,
 	.pin_dbg_show = gemini_pin_dbg_show,
-	.dt_node_to_map = pinconf_generic_dt_node_to_map_group,
+	.dt_node_to_map = pinconf_generic_dt_node_to_map_all,
 	.dt_free_map = pinconf_generic_dt_free_map,
 };
 
@@ -2203,10 +2224,155 @@ static const struct pinmux_ops gemini_pmx_ops = {
 	.set_mux = gemini_pmx_set_mux,
 };
 
+#define GEMINI_CFGPIN(_n, _r, _lb, _hb) {	\
+	.pin = _n,				\
+	.reg = _r,				\
+	.mask = GENMASK(_hb, _lb)		\
+}
+
+static const struct gemini_pin_conf gemini_confs_3512[] = {
+	GEMINI_CFGPIN(259, GLOBAL_GMAC_CTRL_SKEW, 0, 3), /* GMAC0 RXDV */
+	GEMINI_CFGPIN(277, GLOBAL_GMAC_CTRL_SKEW, 4, 7), /* GMAC0 RXC */
+	GEMINI_CFGPIN(241, GLOBAL_GMAC_CTRL_SKEW, 8, 11), /* GMAC0 TXEN */
+	GEMINI_CFGPIN(312, GLOBAL_GMAC_CTRL_SKEW, 12, 15), /* GMAC0 TXC */
+	GEMINI_CFGPIN(298, GLOBAL_GMAC_CTRL_SKEW, 16, 19), /* GMAC1 RXDV */
+	GEMINI_CFGPIN(280, GLOBAL_GMAC_CTRL_SKEW, 20, 23), /* GMAC1 RXC */
+	GEMINI_CFGPIN(316, GLOBAL_GMAC_CTRL_SKEW, 24, 27), /* GMAC1 TXEN */
+	GEMINI_CFGPIN(243, GLOBAL_GMAC_CTRL_SKEW, 28, 31), /* GMAC1 TXC */
+	GEMINI_CFGPIN(295, GLOBAL_GMAC0_DATA_SKEW, 0, 3), /* GMAC0 RXD0 */
+	GEMINI_CFGPIN(313, GLOBAL_GMAC0_DATA_SKEW, 4, 7), /* GMAC0 RXD1 */
+	GEMINI_CFGPIN(242, GLOBAL_GMAC0_DATA_SKEW, 8, 11), /* GMAC0 RXD2 */
+	GEMINI_CFGPIN(260, GLOBAL_GMAC0_DATA_SKEW, 12, 15), /* GMAC0 RXD3 */
+	GEMINI_CFGPIN(294, GLOBAL_GMAC0_DATA_SKEW, 16, 19), /* GMAC0 TXD0 */
+	GEMINI_CFGPIN(276, GLOBAL_GMAC0_DATA_SKEW, 20, 23), /* GMAC0 TXD1 */
+	GEMINI_CFGPIN(258, GLOBAL_GMAC0_DATA_SKEW, 24, 27), /* GMAC0 TXD2 */
+	GEMINI_CFGPIN(240, GLOBAL_GMAC0_DATA_SKEW, 28, 31), /* GMAC0 TXD3 */
+	GEMINI_CFGPIN(262, GLOBAL_GMAC1_DATA_SKEW, 0, 3), /* GMAC1 RXD0 */
+	GEMINI_CFGPIN(244, GLOBAL_GMAC1_DATA_SKEW, 4, 7), /* GMAC1 RXD1 */
+	GEMINI_CFGPIN(317, GLOBAL_GMAC1_DATA_SKEW, 8, 11), /* GMAC1 RXD2 */
+	GEMINI_CFGPIN(299, GLOBAL_GMAC1_DATA_SKEW, 12, 15), /* GMAC1 RXD3 */
+	GEMINI_CFGPIN(261, GLOBAL_GMAC1_DATA_SKEW, 16, 19), /* GMAC1 TXD0 */
+	GEMINI_CFGPIN(279, GLOBAL_GMAC1_DATA_SKEW, 20, 23), /* GMAC1 TXD1 */
+	GEMINI_CFGPIN(297, GLOBAL_GMAC1_DATA_SKEW, 24, 27), /* GMAC1 TXD2 */
+	GEMINI_CFGPIN(315, GLOBAL_GMAC1_DATA_SKEW, 28, 31), /* GMAC1 TXD3 */
+};
+
+static const struct gemini_pin_conf gemini_confs_3516[] = {
+	GEMINI_CFGPIN(347, GLOBAL_GMAC_CTRL_SKEW, 0, 3), /* GMAC0 RXDV */
+	GEMINI_CFGPIN(386, GLOBAL_GMAC_CTRL_SKEW, 4, 7), /* GMAC0 RXC */
+	GEMINI_CFGPIN(307, GLOBAL_GMAC_CTRL_SKEW, 8, 11), /* GMAC0 TXEN */
+	GEMINI_CFGPIN(327, GLOBAL_GMAC_CTRL_SKEW, 12, 15), /* GMAC0 TXC */
+	GEMINI_CFGPIN(309, GLOBAL_GMAC_CTRL_SKEW, 16, 19), /* GMAC1 RXDV */
+	GEMINI_CFGPIN(390, GLOBAL_GMAC_CTRL_SKEW, 20, 23), /* GMAC1 RXC */
+	GEMINI_CFGPIN(370, GLOBAL_GMAC_CTRL_SKEW, 24, 27), /* GMAC1 TXEN */
+	GEMINI_CFGPIN(350, GLOBAL_GMAC_CTRL_SKEW, 28, 31), /* GMAC1 TXC */
+	GEMINI_CFGPIN(367, GLOBAL_GMAC0_DATA_SKEW, 0, 3), /* GMAC0 RXD0 */
+	GEMINI_CFGPIN(348, GLOBAL_GMAC0_DATA_SKEW, 4, 7), /* GMAC0 RXD1 */
+	GEMINI_CFGPIN(387, GLOBAL_GMAC0_DATA_SKEW, 8, 11), /* GMAC0 RXD2 */
+	GEMINI_CFGPIN(328, GLOBAL_GMAC0_DATA_SKEW, 12, 15), /* GMAC0 RXD3 */
+	GEMINI_CFGPIN(306, GLOBAL_GMAC0_DATA_SKEW, 16, 19), /* GMAC0 TXD0 */
+	GEMINI_CFGPIN(325, GLOBAL_GMAC0_DATA_SKEW, 20, 23), /* GMAC0 TXD1 */
+	GEMINI_CFGPIN(346, GLOBAL_GMAC0_DATA_SKEW, 24, 27), /* GMAC0 TXD2 */
+	GEMINI_CFGPIN(326, GLOBAL_GMAC0_DATA_SKEW, 28, 31), /* GMAC0 TXD3 */
+	GEMINI_CFGPIN(391, GLOBAL_GMAC1_DATA_SKEW, 0, 3), /* GMAC1 RXD0 */
+	GEMINI_CFGPIN(351, GLOBAL_GMAC1_DATA_SKEW, 4, 7), /* GMAC1 RXD1 */
+	GEMINI_CFGPIN(310, GLOBAL_GMAC1_DATA_SKEW, 8, 11), /* GMAC1 RXD2 */
+	GEMINI_CFGPIN(371, GLOBAL_GMAC1_DATA_SKEW, 12, 15), /* GMAC1 RXD3 */
+	GEMINI_CFGPIN(329, GLOBAL_GMAC1_DATA_SKEW, 16, 19), /* GMAC1 TXD0 */
+	GEMINI_CFGPIN(389, GLOBAL_GMAC1_DATA_SKEW, 20, 23), /* GMAC1 TXD1 */
+	GEMINI_CFGPIN(369, GLOBAL_GMAC1_DATA_SKEW, 24, 27), /* GMAC1 TXD2 */
+	GEMINI_CFGPIN(308, GLOBAL_GMAC1_DATA_SKEW, 28, 31), /* GMAC1 TXD3 */
+};
+
+static const struct gemini_pin_conf *gemini_get_pin_conf(struct gemini_pmx *pmx,
+							 unsigned int pin)
+{
+	const struct gemini_pin_conf *retconf;
+	int i;
+
+	for (i = 0; i < pmx->nconfs; i++) {
+		retconf = &gemini_confs_3516[i];
+		if (retconf->pin == pin)
+			return retconf;
+	}
+	return NULL;
+}
+
+static int gemini_pinconf_get(struct pinctrl_dev *pctldev, unsigned int pin,
+			      unsigned long *config)
+{
+	struct gemini_pmx *pmx = pinctrl_dev_get_drvdata(pctldev);
+	enum pin_config_param param = pinconf_to_config_param(*config);
+	const struct gemini_pin_conf *conf;
+	u32 val;
+
+	switch (param) {
+	case PIN_CONFIG_SKEW_DELAY:
+		conf = gemini_get_pin_conf(pmx, pin);
+		if (!conf)
+			return -ENOTSUPP;
+		regmap_read(pmx->map, conf->reg, &val);
+		val &= conf->mask;
+		val >>= (ffs(conf->mask) - 1);
+		*config = pinconf_to_config_packed(PIN_CONFIG_SKEW_DELAY, val);
+		break;
+	default:
+		return -ENOTSUPP;
+	}
+
+	return 0;
+}
+
+static int gemini_pinconf_set(struct pinctrl_dev *pctldev, unsigned int pin,
+			      unsigned long *configs, unsigned int num_configs)
+{
+	struct gemini_pmx *pmx = pinctrl_dev_get_drvdata(pctldev);
+	const struct gemini_pin_conf *conf;
+	enum pin_config_param param;
+	u32 arg;
+	int ret = 0;
+	int i;
+
+	for (i = 0; i < num_configs; i++) {
+		param = pinconf_to_config_param(configs[i]);
+		arg = pinconf_to_config_argument(configs[i]);
+
+		switch (param) {
+		case PIN_CONFIG_SKEW_DELAY:
+			if (arg > 0xf)
+				return -EINVAL;
+			conf = gemini_get_pin_conf(pmx, pin);
+			if (!conf) {
+				dev_err(pmx->dev,
+					"invalid pin for skew delay %d\n", pin);
+				return -ENOTSUPP;
+			}
+			arg <<= (ffs(conf->mask) - 1);
+			dev_dbg(pmx->dev,
+				"set pin %d to skew delay mask %08x, val %08x\n",
+				pin, conf->mask, arg);
+			regmap_update_bits(pmx->map, conf->reg, conf->mask, arg);
+			break;
+		default:
+			dev_err(pmx->dev, "Invalid config param %04x\n", param);
+			return -ENOTSUPP;
+		}
+	}
+
+	return ret;
+}
+
+static const struct pinconf_ops gemini_pinconf_ops = {
+	.pin_config_get = gemini_pinconf_get,
+	.pin_config_set = gemini_pinconf_set,
+	.is_generic = true,
+};
+
 static struct pinctrl_desc gemini_pmx_desc = {
 	.name = DRIVER_NAME,
 	.pctlops = &gemini_pctrl_ops,
 	.pmxops = &gemini_pmx_ops,
+	.confops = &gemini_pinconf_ops,
 	.owner = THIS_MODULE,
 };
 
@@ -2249,11 +2415,15 @@ static int gemini_pmx_probe(struct platform_device *pdev)
 	val &= 0xffff;
 	if (val == 0x3512) {
 		pmx->is_3512 = true;
+		pmx->confs = gemini_confs_3512;
+		pmx->nconfs = ARRAY_SIZE(gemini_confs_3512);
 		gemini_pmx_desc.pins = gemini_3512_pins;
 		gemini_pmx_desc.npins = ARRAY_SIZE(gemini_3512_pins);
 		dev_info(dev, "detected 3512 chip variant\n");
 	} else if (val == 0x3516) {
 		pmx->is_3516 = true;
+		pmx->confs = gemini_confs_3516;
+		pmx->nconfs = ARRAY_SIZE(gemini_confs_3516);
 		gemini_pmx_desc.pins = gemini_3516_pins;
 		gemini_pmx_desc.npins = ARRAY_SIZE(gemini_3516_pins);
 		dev_info(dev, "detected 3516 chip variant\n");
-- 
2.13.6

^ permalink raw reply related	[flat|nested] 22+ messages in thread

* Re: [PATCH 1/4] pinctrl: gemini: Add missing functions
  2017-10-28 13:37 ` Linus Walleij
@ 2017-11-01  5:55   ` Hans Ulli Kroll
  -1 siblings, 0 replies; 22+ messages in thread
From: Hans Ulli Kroll @ 2017-11-01  5:55 UTC (permalink / raw)
  To: Linus Walleij
  Cc: linux-gpio, Hans Ulli Kroll, Florian Fainelli, Janos Laube,
	Paulius Zaleckas, linux-arm-kernel

Hi Linus

On Sat, 28 Oct 2017, Linus Walleij wrote:

> Some two functions were missing from the Gemini pin control
> driver. Noticed when trying to use ethernet. Fix it up by
> adding them.
> 
> Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
> ---

Acked-by: Hans Ulli Kroll <ulli.kroll@googlemail.com>


^ permalink raw reply	[flat|nested] 22+ messages in thread

* [PATCH 1/4] pinctrl: gemini: Add missing functions
@ 2017-11-01  5:55   ` Hans Ulli Kroll
  0 siblings, 0 replies; 22+ messages in thread
From: Hans Ulli Kroll @ 2017-11-01  5:55 UTC (permalink / raw)
  To: linux-arm-kernel

Hi Linus

On Sat, 28 Oct 2017, Linus Walleij wrote:

> Some two functions were missing from the Gemini pin control
> driver. Noticed when trying to use ethernet. Fix it up by
> adding them.
> 
> Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
> ---

Acked-by: Hans Ulli Kroll <ulli.kroll@googlemail.com>

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH 2/4] pinctrl: Add skew-delay pin config and bindings
  2017-10-28 13:37   ` Linus Walleij
@ 2017-11-01  5:56       ` Hans Ulli Kroll
  -1 siblings, 0 replies; 22+ messages in thread
From: Hans Ulli Kroll @ 2017-11-01  5:56 UTC (permalink / raw)
  To: Linus Walleij
  Cc: linux-gpio-u79uwXL29TY76Z2rM5mHXA, Hans Ulli Kroll,
	Florian Fainelli, Janos Laube, Paulius Zaleckas,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	devicetree-u79uwXL29TY76Z2rM5mHXA

Hi Linus,

On Sat, 28 Oct 2017, Linus Walleij wrote:

> Some pin controllers (such as the Gemini) can control the
> expected clock skew and output delay on certain pins with a
> sub-nanosecond granularity. This is typically done by shunting
> in a number of double inverters in front of or behind the pin.
> Make it possible to configure this with a generic binding.
> 
> Cc: devicetree-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
> Signed-off-by: Linus Walleij <linus.walleij-QSEj5FYQhm4dnm+yROfE0A@public.gmane.org>
> ---

Acked-by: Hans Ulli Kroll <ulli.kroll-gM/Ye1E23mwN+BqQ9rBEUg@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	[flat|nested] 22+ messages in thread

* [PATCH 2/4] pinctrl: Add skew-delay pin config and bindings
@ 2017-11-01  5:56       ` Hans Ulli Kroll
  0 siblings, 0 replies; 22+ messages in thread
From: Hans Ulli Kroll @ 2017-11-01  5:56 UTC (permalink / raw)
  To: linux-arm-kernel

Hi Linus,

On Sat, 28 Oct 2017, Linus Walleij wrote:

> Some pin controllers (such as the Gemini) can control the
> expected clock skew and output delay on certain pins with a
> sub-nanosecond granularity. This is typically done by shunting
> in a number of double inverters in front of or behind the pin.
> Make it possible to configure this with a generic binding.
> 
> Cc: devicetree at vger.kernel.org
> Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
> ---

Acked-by: Hans Ulli Kroll <ulli.kroll@googlemail.com>

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH 3/4] pinctrl: gemini: Use generic DT parser
  2017-10-28 13:37   ` Linus Walleij
@ 2017-11-01  5:56     ` Hans Ulli Kroll
  -1 siblings, 0 replies; 22+ messages in thread
From: Hans Ulli Kroll @ 2017-11-01  5:56 UTC (permalink / raw)
  To: Linus Walleij
  Cc: linux-gpio, Hans Ulli Kroll, Florian Fainelli, Janos Laube,
	Paulius Zaleckas, linux-arm-kernel

Hi Linus

On Sat, 28 Oct 2017, Linus Walleij wrote:

> We can just use the generic Device Tree parser code
> in this driver and save some code.
> 
> Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
> ---
>  drivers/pinctrl/Kconfig          |  1 +
>  drivers/pinctrl/pinctrl-gemini.c | 66 +++-------------------------------------
>  2 files changed, 5 insertions(+), 62 deletions(-)
> 

Acked-by: Hans Ulli Kroll <ulli.kroll@googlemail.com>


^ permalink raw reply	[flat|nested] 22+ messages in thread

* [PATCH 3/4] pinctrl: gemini: Use generic DT parser
@ 2017-11-01  5:56     ` Hans Ulli Kroll
  0 siblings, 0 replies; 22+ messages in thread
From: Hans Ulli Kroll @ 2017-11-01  5:56 UTC (permalink / raw)
  To: linux-arm-kernel

Hi Linus

On Sat, 28 Oct 2017, Linus Walleij wrote:

> We can just use the generic Device Tree parser code
> in this driver and save some code.
> 
> Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
> ---
>  drivers/pinctrl/Kconfig          |  1 +
>  drivers/pinctrl/pinctrl-gemini.c | 66 +++-------------------------------------
>  2 files changed, 5 insertions(+), 62 deletions(-)
> 

Acked-by: Hans Ulli Kroll <ulli.kroll@googlemail.com>

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH 4/4] pinctrl: gemini: Implement clock skew/delay config
  2017-10-28 13:37   ` Linus Walleij
@ 2017-11-01  5:57     ` Hans Ulli Kroll
  -1 siblings, 0 replies; 22+ messages in thread
From: Hans Ulli Kroll @ 2017-11-01  5:57 UTC (permalink / raw)
  To: Linus Walleij
  Cc: linux-gpio, Hans Ulli Kroll, Florian Fainelli, Janos Laube,
	Paulius Zaleckas, linux-arm-kernel

Hi Linus,

On Sat, 28 Oct 2017, Linus Walleij wrote:

> This enabled pin config on the Gemini driver and implements
> pin skew/delay so that the ethernet pins clocking can be
> properly configured.
> 
> Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
> ---
>  .../bindings/pinctrl/cortina,gemini-pinctrl.txt    |  10 +-
>  drivers/pinctrl/pinctrl-gemini.c                   | 178 ++++++++++++++++++++-
>  2 files changed, 182 insertions(+), 6 deletions(-)
> 

Acked-by: Hans Ulli Kroll <ulli.kroll@googlemail.com>


^ permalink raw reply	[flat|nested] 22+ messages in thread

* [PATCH 4/4] pinctrl: gemini: Implement clock skew/delay config
@ 2017-11-01  5:57     ` Hans Ulli Kroll
  0 siblings, 0 replies; 22+ messages in thread
From: Hans Ulli Kroll @ 2017-11-01  5:57 UTC (permalink / raw)
  To: linux-arm-kernel

Hi Linus,

On Sat, 28 Oct 2017, Linus Walleij wrote:

> This enabled pin config on the Gemini driver and implements
> pin skew/delay so that the ethernet pins clocking can be
> properly configured.
> 
> Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
> ---
>  .../bindings/pinctrl/cortina,gemini-pinctrl.txt    |  10 +-
>  drivers/pinctrl/pinctrl-gemini.c                   | 178 ++++++++++++++++++++-
>  2 files changed, 182 insertions(+), 6 deletions(-)
> 

Acked-by: Hans Ulli Kroll <ulli.kroll@googlemail.com>

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH 2/4] pinctrl: Add skew-delay pin config and bindings
  2017-10-28 13:37   ` Linus Walleij
@ 2017-11-01 21:26     ` Rob Herring
  -1 siblings, 0 replies; 22+ messages in thread
From: Rob Herring @ 2017-11-01 21:26 UTC (permalink / raw)
  To: Linus Walleij
  Cc: linux-gpio, Hans Ulli Kroll, Florian Fainelli, Janos Laube,
	Paulius Zaleckas, linux-arm-kernel, devicetree

On Sat, Oct 28, 2017 at 03:37:17PM +0200, Linus Walleij wrote:
> Some pin controllers (such as the Gemini) can control the
> expected clock skew and output delay on certain pins with a
> sub-nanosecond granularity. This is typically done by shunting
> in a number of double inverters in front of or behind the pin.
> Make it possible to configure this with a generic binding.
> 
> Cc: devicetree@vger.kernel.org
> Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
> ---
>  Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt | 4 ++++
>  drivers/pinctrl/pinconf-generic.c                              | 2 ++
>  include/linux/pinctrl/pinconf-generic.h                        | 5 +++++
>  3 files changed, 11 insertions(+)
> 
> diff --git a/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt b/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
> index 4483cc31e531..ad9bbbba36e9 100644
> --- a/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
> +++ b/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
> @@ -271,6 +271,10 @@ output-high		- set the pin to output mode with high level
>  sleep-hardware-state	- indicate this is sleep related state which will be programmed
>  			  into the registers for the sleep state.
>  slew-rate		- set the slew rate
> +skew-delay		- this affects the expected clock skew on input pins
> +			  and the delay before latching a value to an output
> +			  pin. Typically indicates how many double-inverters are
> +			  used to delay the signal.

Units?

>  
>  For example:
>  

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [PATCH 2/4] pinctrl: Add skew-delay pin config and bindings
@ 2017-11-01 21:26     ` Rob Herring
  0 siblings, 0 replies; 22+ messages in thread
From: Rob Herring @ 2017-11-01 21:26 UTC (permalink / raw)
  To: linux-arm-kernel

On Sat, Oct 28, 2017 at 03:37:17PM +0200, Linus Walleij wrote:
> Some pin controllers (such as the Gemini) can control the
> expected clock skew and output delay on certain pins with a
> sub-nanosecond granularity. This is typically done by shunting
> in a number of double inverters in front of or behind the pin.
> Make it possible to configure this with a generic binding.
> 
> Cc: devicetree at vger.kernel.org
> Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
> ---
>  Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt | 4 ++++
>  drivers/pinctrl/pinconf-generic.c                              | 2 ++
>  include/linux/pinctrl/pinconf-generic.h                        | 5 +++++
>  3 files changed, 11 insertions(+)
> 
> diff --git a/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt b/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
> index 4483cc31e531..ad9bbbba36e9 100644
> --- a/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
> +++ b/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
> @@ -271,6 +271,10 @@ output-high		- set the pin to output mode with high level
>  sleep-hardware-state	- indicate this is sleep related state which will be programmed
>  			  into the registers for the sleep state.
>  slew-rate		- set the slew rate
> +skew-delay		- this affects the expected clock skew on input pins
> +			  and the delay before latching a value to an output
> +			  pin. Typically indicates how many double-inverters are
> +			  used to delay the signal.

Units?

>  
>  For example:
>  

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH 2/4] pinctrl: Add skew-delay pin config and bindings
  2017-11-01 21:26     ` Rob Herring
@ 2017-11-02 14:32       ` Linus Walleij
  -1 siblings, 0 replies; 22+ messages in thread
From: Linus Walleij @ 2017-11-02 14:32 UTC (permalink / raw)
  To: Rob Herring
  Cc: linux-gpio-u79uwXL29TY76Z2rM5mHXA, Hans Ulli Kroll,
	Florian Fainelli, Janos Laube, Paulius Zaleckas,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	devicetree-u79uwXL29TY76Z2rM5mHXA

On Wed, Nov 1, 2017 at 10:26 PM, Rob Herring <robh-DgEjT+Ai2ygdnm+yROfE0A@public.gmane.org> wrote:
> On Sat, Oct 28, 2017 at 03:37:17PM +0200, Linus Walleij wrote:
>> Some pin controllers (such as the Gemini) can control the
>> expected clock skew and output delay on certain pins with a
>> sub-nanosecond granularity. This is typically done by shunting
>> in a number of double inverters in front of or behind the pin.
>> Make it possible to configure this with a generic binding.
>>
>> Cc: devicetree-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
>> Signed-off-by: Linus Walleij <linus.walleij-QSEj5FYQhm4dnm+yROfE0A@public.gmane.org>
>> ---
>>  Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt | 4 ++++
>>  drivers/pinctrl/pinconf-generic.c                              | 2 ++
>>  include/linux/pinctrl/pinconf-generic.h                        | 5 +++++
>>  3 files changed, 11 insertions(+)
>>
>> diff --git a/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt b/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
>> index 4483cc31e531..ad9bbbba36e9 100644
>> --- a/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
>> +++ b/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
>> @@ -271,6 +271,10 @@ output-high              - set the pin to output mode with high level
>>  sleep-hardware-state - indicate this is sleep related state which will be programmed
>>                         into the registers for the sleep state.
>>  slew-rate            - set the slew rate
>> +skew-delay           - this affects the expected clock skew on input pins
>> +                       and the delay before latching a value to an output
>> +                       pin. Typically indicates how many double-inverters are
>> +                       used to delay the signal.
>
> Units?

Number of double-inverters I guess, just as it says.

skew-delay = <1>; // number of inverter pairs

Like with other bindings of this type they are custom.

The Gemini datasheet says "every unit represents about 0.2 ns".

So if you set it to 1, that means (as far as I can guess) this
is shunted in:

   |\    |\
--+ >o--+ >o---
   |/    |/

The signal will take ~0.2 ns to propagate through this.
For 2, there will be four inverters etc.

It is dependent of production technology, and I do not know
if everyone is using something like double-inverters.

We could try to define a value in picoseconds instead so I
would need to set this to 200 in that case if you think that is better:

skew-delay = <200>; // picoseconds

I think it would be kludgy since with increasing clock speeds
maybe picoseconds would be too big even. Nanoseconds is
apparently already a to coarse unit.

Yours,
Linus Walleij
--
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	[flat|nested] 22+ messages in thread

* [PATCH 2/4] pinctrl: Add skew-delay pin config and bindings
@ 2017-11-02 14:32       ` Linus Walleij
  0 siblings, 0 replies; 22+ messages in thread
From: Linus Walleij @ 2017-11-02 14:32 UTC (permalink / raw)
  To: linux-arm-kernel

On Wed, Nov 1, 2017 at 10:26 PM, Rob Herring <robh@kernel.org> wrote:
> On Sat, Oct 28, 2017 at 03:37:17PM +0200, Linus Walleij wrote:
>> Some pin controllers (such as the Gemini) can control the
>> expected clock skew and output delay on certain pins with a
>> sub-nanosecond granularity. This is typically done by shunting
>> in a number of double inverters in front of or behind the pin.
>> Make it possible to configure this with a generic binding.
>>
>> Cc: devicetree at vger.kernel.org
>> Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
>> ---
>>  Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt | 4 ++++
>>  drivers/pinctrl/pinconf-generic.c                              | 2 ++
>>  include/linux/pinctrl/pinconf-generic.h                        | 5 +++++
>>  3 files changed, 11 insertions(+)
>>
>> diff --git a/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt b/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
>> index 4483cc31e531..ad9bbbba36e9 100644
>> --- a/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
>> +++ b/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
>> @@ -271,6 +271,10 @@ output-high              - set the pin to output mode with high level
>>  sleep-hardware-state - indicate this is sleep related state which will be programmed
>>                         into the registers for the sleep state.
>>  slew-rate            - set the slew rate
>> +skew-delay           - this affects the expected clock skew on input pins
>> +                       and the delay before latching a value to an output
>> +                       pin. Typically indicates how many double-inverters are
>> +                       used to delay the signal.
>
> Units?

Number of double-inverters I guess, just as it says.

skew-delay = <1>; // number of inverter pairs

Like with other bindings of this type they are custom.

The Gemini datasheet says "every unit represents about 0.2 ns".

So if you set it to 1, that means (as far as I can guess) this
is shunted in:

   |\    |\
--+ >o--+ >o---
   |/    |/

The signal will take ~0.2 ns to propagate through this.
For 2, there will be four inverters etc.

It is dependent of production technology, and I do not know
if everyone is using something like double-inverters.

We could try to define a value in picoseconds instead so I
would need to set this to 200 in that case if you think that is better:

skew-delay = <200>; // picoseconds

I think it would be kludgy since with increasing clock speeds
maybe picoseconds would be too big even. Nanoseconds is
apparently already a to coarse unit.

Yours,
Linus Walleij

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH 2/4] pinctrl: Add skew-delay pin config and bindings
  2017-11-02 14:32       ` Linus Walleij
@ 2017-11-08  0:38         ` Rob Herring
  -1 siblings, 0 replies; 22+ messages in thread
From: Rob Herring @ 2017-11-08  0:38 UTC (permalink / raw)
  To: Linus Walleij
  Cc: linux-gpio, Hans Ulli Kroll, Florian Fainelli, Janos Laube,
	Paulius Zaleckas, linux-arm-kernel, devicetree

On Thu, Nov 2, 2017 at 9:32 AM, Linus Walleij <linus.walleij@linaro.org> wrote:
> On Wed, Nov 1, 2017 at 10:26 PM, Rob Herring <robh@kernel.org> wrote:
>> On Sat, Oct 28, 2017 at 03:37:17PM +0200, Linus Walleij wrote:
>>> Some pin controllers (such as the Gemini) can control the
>>> expected clock skew and output delay on certain pins with a
>>> sub-nanosecond granularity. This is typically done by shunting
>>> in a number of double inverters in front of or behind the pin.
>>> Make it possible to configure this with a generic binding.
>>>
>>> Cc: devicetree@vger.kernel.org
>>> Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
>>> ---
>>>  Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt | 4 ++++
>>>  drivers/pinctrl/pinconf-generic.c                              | 2 ++
>>>  include/linux/pinctrl/pinconf-generic.h                        | 5 +++++
>>>  3 files changed, 11 insertions(+)
>>>
>>> diff --git a/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt b/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
>>> index 4483cc31e531..ad9bbbba36e9 100644
>>> --- a/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
>>> +++ b/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
>>> @@ -271,6 +271,10 @@ output-high              - set the pin to output mode with high level
>>>  sleep-hardware-state - indicate this is sleep related state which will be programmed
>>>                         into the registers for the sleep state.
>>>  slew-rate            - set the slew rate
>>> +skew-delay           - this affects the expected clock skew on input pins
>>> +                       and the delay before latching a value to an output
>>> +                       pin. Typically indicates how many double-inverters are
>>> +                       used to delay the signal.
>>
>> Units?
>
> Number of double-inverters I guess, just as it says.
>
> skew-delay = <1>; // number of inverter pairs
>
> Like with other bindings of this type they are custom.
>
> The Gemini datasheet says "every unit represents about 0.2 ns".
>
> So if you set it to 1, that means (as far as I can guess) this
> is shunted in:
>
>    |\    |\
> --+ >o--+ >o---
>    |/    |/
>
> The signal will take ~0.2 ns to propagate through this.
> For 2, there will be four inverters etc.
>
> It is dependent of production technology, and I do not know
> if everyone is using something like double-inverters.
>
> We could try to define a value in picoseconds instead so I
> would need to set this to 200 in that case if you think that is better:
>
> skew-delay = <200>; // picoseconds
>
> I think it would be kludgy since with increasing clock speeds
> maybe picoseconds would be too big even. Nanoseconds is
> apparently already a to coarse unit.

Okay, it is fine.

Acked-by: Rob Herring <robh@kernel.org>

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [PATCH 2/4] pinctrl: Add skew-delay pin config and bindings
@ 2017-11-08  0:38         ` Rob Herring
  0 siblings, 0 replies; 22+ messages in thread
From: Rob Herring @ 2017-11-08  0:38 UTC (permalink / raw)
  To: linux-arm-kernel

On Thu, Nov 2, 2017 at 9:32 AM, Linus Walleij <linus.walleij@linaro.org> wrote:
> On Wed, Nov 1, 2017 at 10:26 PM, Rob Herring <robh@kernel.org> wrote:
>> On Sat, Oct 28, 2017 at 03:37:17PM +0200, Linus Walleij wrote:
>>> Some pin controllers (such as the Gemini) can control the
>>> expected clock skew and output delay on certain pins with a
>>> sub-nanosecond granularity. This is typically done by shunting
>>> in a number of double inverters in front of or behind the pin.
>>> Make it possible to configure this with a generic binding.
>>>
>>> Cc: devicetree at vger.kernel.org
>>> Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
>>> ---
>>>  Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt | 4 ++++
>>>  drivers/pinctrl/pinconf-generic.c                              | 2 ++
>>>  include/linux/pinctrl/pinconf-generic.h                        | 5 +++++
>>>  3 files changed, 11 insertions(+)
>>>
>>> diff --git a/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt b/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
>>> index 4483cc31e531..ad9bbbba36e9 100644
>>> --- a/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
>>> +++ b/Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt
>>> @@ -271,6 +271,10 @@ output-high              - set the pin to output mode with high level
>>>  sleep-hardware-state - indicate this is sleep related state which will be programmed
>>>                         into the registers for the sleep state.
>>>  slew-rate            - set the slew rate
>>> +skew-delay           - this affects the expected clock skew on input pins
>>> +                       and the delay before latching a value to an output
>>> +                       pin. Typically indicates how many double-inverters are
>>> +                       used to delay the signal.
>>
>> Units?
>
> Number of double-inverters I guess, just as it says.
>
> skew-delay = <1>; // number of inverter pairs
>
> Like with other bindings of this type they are custom.
>
> The Gemini datasheet says "every unit represents about 0.2 ns".
>
> So if you set it to 1, that means (as far as I can guess) this
> is shunted in:
>
>    |\    |\
> --+ >o--+ >o---
>    |/    |/
>
> The signal will take ~0.2 ns to propagate through this.
> For 2, there will be four inverters etc.
>
> It is dependent of production technology, and I do not know
> if everyone is using something like double-inverters.
>
> We could try to define a value in picoseconds instead so I
> would need to set this to 200 in that case if you think that is better:
>
> skew-delay = <200>; // picoseconds
>
> I think it would be kludgy since with increasing clock speeds
> maybe picoseconds would be too big even. Nanoseconds is
> apparently already a to coarse unit.

Okay, it is fine.

Acked-by: Rob Herring <robh@kernel.org>

^ permalink raw reply	[flat|nested] 22+ messages in thread

end of thread, other threads:[~2017-11-08  0:39 UTC | newest]

Thread overview: 22+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2017-10-28 13:37 [PATCH 1/4] pinctrl: gemini: Add missing functions Linus Walleij
2017-10-28 13:37 ` Linus Walleij
2017-10-28 13:37 ` [PATCH 2/4] pinctrl: Add skew-delay pin config and bindings Linus Walleij
2017-10-28 13:37   ` Linus Walleij
     [not found]   ` <20171028133719.27528-2-linus.walleij-QSEj5FYQhm4dnm+yROfE0A@public.gmane.org>
2017-11-01  5:56     ` Hans Ulli Kroll
2017-11-01  5:56       ` Hans Ulli Kroll
2017-11-01 21:26   ` Rob Herring
2017-11-01 21:26     ` Rob Herring
2017-11-02 14:32     ` Linus Walleij
2017-11-02 14:32       ` Linus Walleij
2017-11-08  0:38       ` Rob Herring
2017-11-08  0:38         ` Rob Herring
2017-10-28 13:37 ` [PATCH 3/4] pinctrl: gemini: Use generic DT parser Linus Walleij
2017-10-28 13:37   ` Linus Walleij
2017-11-01  5:56   ` Hans Ulli Kroll
2017-11-01  5:56     ` Hans Ulli Kroll
2017-10-28 13:37 ` [PATCH 4/4] pinctrl: gemini: Implement clock skew/delay config Linus Walleij
2017-10-28 13:37   ` Linus Walleij
2017-11-01  5:57   ` Hans Ulli Kroll
2017-11-01  5:57     ` Hans Ulli Kroll
2017-11-01  5:55 ` [PATCH 1/4] pinctrl: gemini: Add missing functions Hans Ulli Kroll
2017-11-01  5:55   ` Hans Ulli Kroll

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.