linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling
@ 2018-08-10 18:08 Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 01/40] dt-bindings: Add Tegra PMC pad configuration bindings Aapo Vienamo
                   ` (42 more replies)
  0 siblings, 43 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Hi all,

This series implements support for faster signaling modes on Tegra
SDHCI controllers. This series consist of several parts: changes
requried for 1.8 V signaling and pad control, pad calibration, and
tuning. Following earlies patch sets have been merged into this
larger set: "Tegra PMC pinctrl pad configuration", "Tegra SDHCI enable
1.8 V signaling on Tegar210 and Tegra186", "Tegra SDHCI update the
padautocal procedure". Also the patches for enabling SDHCI tuning
are added.

Changelog:
v2:
	- Fix grammar in PMC device tree bindings docs
	- Remove a stray line from tegra sdhci bindings
	- Cosmetic changes to PMC pinctrl driver
	- Fix a typo in "soc/tegra: pmc: Implement
	  tegra_io_pad_is_powered()" commit message
	- Declare mask and value on the same line in
	  tegra_io_pad_is_powered()
	- Move the call to tegra_sdhci_is_pad_and_regulator_valid() to
	  inside the if condition in tegra_sdhci_reset()
	- Use usleep_range() in tegra_sdhci_configure_cal_pad()
	- Move sdhci_writel() out of the enable if-else body in
	  tegra_sdhci_configure_cal_pad()
	- Add a delay before starting polling in
	  tegra_sdhci_pad_autocalib()
	- Use usleep_range() in tegra_sdhci_set_tap()
	- Rename orig_enabled to status in
	  tegra_sdhci_configure_card_clk()
	- Fix if condition wrapping alignment in tegra_sdhci_set_tap()

v1:
	- Probe the regulator voltage capabilities to determine whether pinctrl
	  is needed in tegra_sdhci_r eset
	- Don't remove tegra_sdhci_voltage_switch()
	- Use dev_warn() in tegra_sdhci_init_pinctrl_info()
	- Don't change start_signal_voltage_switch callback if pinctrl info
	  invalid
	- Only call udelay(1) on enable in tegra_sdhci_configure_cal_pad()
	- Add nvidia, prefix to pad autocal offset dt props in the example

See the original patch sets for earlier changelogs.

Aapo Vienamo (40):
  dt-bindings: Add Tegra PMC pad configuration bindings
  dt-bindings: mmc: tegra: Add pad voltage control properties
  dt-bindings: Add Tegra SDHCI pad pdpu offset bindings
  dt-bindings: mmc: Add Tegra SDHCI sampling trimmer values
  soc/tegra: pmc: Fix pad voltage configuration for Tegra186
  soc/tegra: pmc: Factor out DPD register bit calculation
  soc/tegra: pmc: Implement tegra_io_pad_is_powered()
  soc/tegra: pmc: Use X macro to generate IO pad tables
  soc/tegra: pmc: Remove public pad voltage APIs
  soc/tegra: pmc: Implement pad configuration via pinctrl
  mmc: sdhci: Add a quirk to skip clearing the transfer mode register on
    tuning
  mmc: tegra: Reconfigure pad voltages during voltage switching
  mmc: tegra: Poll for calibration completion
  mmc: tegra: Set calibration pad voltage reference
  mmc: tegra: Power on the calibration pad
  mmc: tegra: Disable card clock during pad calibration
  mmc: tegra: Program pad autocal offsets from dt
  mmc: tegra: Perform pad calibration after voltage switch
  mmc: tegra: Enable pad calibration on Tegra210 and Tegra186
  mmc: tegra: Add a workaround for tap value change glitch
  mmc: tegra: Parse default trim and tap from dt
  mmc: tegra: Configure default tap values
  mmc: tegra: Configure default trim value on reset
  mmc: tegra: Use standard SDHCI tuning on Tegra210 and Tegra186
  mmc: sdhci: Add a quirk to disable card clock during tuning
  mmc: tegra: Enable workaround for tuning transfer mode bug
  mmc: tegra: Set SDHCI_QUIRK2_TUNE_DIS_CARD_CLK on Tegra210
  mmc: tegra: Enable UHS and HS200 modes for Tegra210
  mmc: tegra: Enable UHS and HS200 modes for Tegra186
  arm64: dts: Add Tegra210 sdmmc pinctrl voltage states
  arm64: dts: Add Tegra186 sdmmc pinctrl voltage states
  arm64: dts: tegra210-p2180: Allow ldo2 to go down to 1.8 V
  arm64: dts: tegra210-p2180: Correct sdmmc4 vqmmc-supply
  arm64: dts: tegra210-p2597: Remove no-1-8-v from sdmmc1
  arm64: dts: tegra186: Add sdmmc pad auto calibration offsets
  arm64: dts: tegra210: Add sdmmc pad auto calibration offsets
  arm64: dts: tegra210: Add SDHCI tap and trim values
  arm64: dts: tegra186: Add SDHCI tap and trim values
  arm64: dts: tegra186: Assign clocks for sdmmc1 and sdmmc4
  arm64: dts: tegra210: Assign clocks for sdmmc1 and sdmmc4

 .../bindings/arm/tegra/nvidia,tegra186-pmc.txt     |  93 ++++
 .../bindings/arm/tegra/nvidia,tegra20-pmc.txt      | 103 ++++
 .../bindings/mmc/nvidia,tegra20-sdhci.txt          |  68 +++
 arch/arm64/boot/dts/nvidia/tegra186.dtsi           |  74 +++
 arch/arm64/boot/dts/nvidia/tegra210-p2180.dtsi     |  12 +-
 arch/arm64/boot/dts/nvidia/tegra210-p2597.dtsi     |   1 -
 arch/arm64/boot/dts/nvidia/tegra210.dtsi           |  55 ++
 drivers/mmc/host/sdhci-tegra.c                     | 556 +++++++++++++++++++--
 drivers/mmc/host/sdhci.c                           |  21 +
 drivers/mmc/host/sdhci.h                           |   4 +
 drivers/soc/tegra/pmc.c                            | 511 ++++++++++++++-----
 include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h |  18 +
 include/soc/tegra/pmc.h                            |  20 +-
 13 files changed, 1324 insertions(+), 212 deletions(-)
 create mode 100644 include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h

-- 
2.7.4


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

* [PATCH v2 01/40] dt-bindings: Add Tegra PMC pad configuration bindings
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 02/40] dt-bindings: mmc: tegra: Add pad voltage control properties Aapo Vienamo
                   ` (41 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Document the PMC pinctrl bindings for pad power state and signaling
voltage configuration. Both nvidia,tegra186-pmc.txt and
nvidia,tegra20-pmc.txt are modified as they both cover SoC generations
for which these bindings apply.

Add a header defining Tegra PMC pad voltage configurations.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
Acked-by: Jon Hunter <jonathanh@nvidia.com>
Reviewed-by: Rob Herring <robh@kernel.org>
---
 .../bindings/arm/tegra/nvidia,tegra186-pmc.txt     |  93 +++++++++++++++++++
 .../bindings/arm/tegra/nvidia,tegra20-pmc.txt      | 103 +++++++++++++++++++++
 include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h |  18 ++++
 3 files changed, 214 insertions(+)
 create mode 100644 include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h

diff --git a/Documentation/devicetree/bindings/arm/tegra/nvidia,tegra186-pmc.txt b/Documentation/devicetree/bindings/arm/tegra/nvidia,tegra186-pmc.txt
index 5a3bf7c..c9fd6d1 100644
--- a/Documentation/devicetree/bindings/arm/tegra/nvidia,tegra186-pmc.txt
+++ b/Documentation/devicetree/bindings/arm/tegra/nvidia,tegra186-pmc.txt
@@ -34,3 +34,96 @@ Board DTS:
 	pmc@c360000 {
 		nvidia,invert-interrupt;
 	};
+
+== Pad Control ==
+
+On Tegra SoCs a pad is a set of pins which are configured as a group.
+The pin grouping is a fixed attribute of the hardware. The PMC can be
+used to set pad power state and signaling voltage. A pad can be either
+in active or power down mode. The support for power state and signaling
+voltage configuration varies depending on the pad in question. 3.3 V and
+1.8 V signaling voltages are supported on pins where software
+controllable signaling voltage switching is available.
+
+Pad configurations are described with pin configuration nodes which
+are placed under the pmc node and they are referred to by the pinctrl
+client properties. For more information see
+Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt.
+
+The following pads are present on Tegra186:
+csia		csib		dsi		mipi-bias
+pex-clk-bias	pex-clk3	pex-clk2	pex-clk1
+usb0		usb1		usb2		usb-bias
+uart		audio		hsic		dbg
+hdmi-dp0	hdmi-dp1	pex-cntrl	sdmmc2-hv
+sdmmc4		cam		dsib		dsic
+dsid		csic		csid		csie
+dsif		spi		ufs		dmic-hv
+edp		sdmmc1-hv	sdmmc3-hv	conn
+audio-hv	ao-hv
+
+Required pin configuration properties:
+  - pins: A list of strings, each of which contains the name of a pad
+	  to be configured.
+
+Optional pin configuration properties:
+  - low-power-enable: Configure the pad into power down mode
+  - low-power-disable: Configure the pad into active mode
+  - power-source: Must contain either TEGRA_IO_PAD_VOLTAGE_1V8 or
+    TEGRA_IO_PAD_VOLTAGE_3V3 to select between signaling voltages.
+    The values are defined in
+    include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h.
+
+Note: The power state can be configured on all of the above pads except
+      for ao-hv. Following pads have software configurable signaling
+      voltages: sdmmc2-hv, dmic-hv, sdmmc1-hv, sdmmc3-hv, audio-hv,
+      ao-hv.
+
+Pad configuration state example:
+	pmc: pmc@7000e400 {
+		compatible = "nvidia,tegra186-pmc";
+		reg = <0 0x0c360000 0 0x10000>,
+		      <0 0x0c370000 0 0x10000>,
+		      <0 0x0c380000 0 0x10000>,
+		      <0 0x0c390000 0 0x10000>;
+		reg-names = "pmc", "wake", "aotag", "scratch";
+
+		...
+
+		sdmmc1_3v3: sdmmc1-3v3 {
+			pins = "sdmmc1-hv";
+			power-source = <TEGRA_IO_PAD_VOLTAGE_3V3>;
+		};
+
+		sdmmc1_1v8: sdmmc1-1v8 {
+			pins = "sdmmc1-hv";
+			power-source = <TEGRA_IO_PAD_VOLTAGE_1V8>;
+		};
+
+		hdmi_off: hdmi-off {
+			pins = "hdmi";
+			low-power-enable;
+		}
+
+		hdmi_on: hdmi-on {
+			pins = "hdmi";
+			low-power-disable;
+		}
+	};
+
+Pinctrl client example:
+	sdmmc1: sdhci@3400000 {
+		...
+		pinctrl-names = "sdmmc-3v3", "sdmmc-1v8";
+		pinctrl-0 = <&sdmmc1_3v3>;
+		pinctrl-1 = <&sdmmc1_1v8>;
+	};
+
+	...
+
+	sor0: sor@15540000 {
+		...
+		pinctrl-0 = <&hdmi_off>;
+		pinctrl-1 = <&hdmi_on>;
+		pinctrl-names = "hdmi-on", "hdmi-off";
+	};
diff --git a/Documentation/devicetree/bindings/arm/tegra/nvidia,tegra20-pmc.txt b/Documentation/devicetree/bindings/arm/tegra/nvidia,tegra20-pmc.txt
index a74b37b..cb12f33 100644
--- a/Documentation/devicetree/bindings/arm/tegra/nvidia,tegra20-pmc.txt
+++ b/Documentation/devicetree/bindings/arm/tegra/nvidia,tegra20-pmc.txt
@@ -195,3 +195,106 @@ Example:
 		power-domains = <&pd_audio>;
 		...
 	};
+
+== Pad Control ==
+
+On Tegra SoCs a pad is a set of pins which are configured as a group.
+The pin grouping is a fixed attribute of the hardware. The PMC can be
+used to set pad power state and signaling voltage. A pad can be either
+in active or power down mode. The support for power state and signaling
+voltage configuration varies depending on the pad in question. 3.3 V and
+1.8 V signaling voltages are supported on pins where software
+controllable signaling voltage switching is available.
+
+The pad configuration state nodes are placed under the pmc node and they
+are referred to by the pinctrl client properties. For more information
+see Documentation/devicetree/bindings/pinctrl/pinctrl-bindings.txt.
+The pad name should be used as the value of the pins property in pin
+configuration nodes.
+
+The following pads are present on Tegra124 and Tegra132:
+audio		bb		cam		comp
+csia		csb		cse		dsi
+dsib		dsic		dsid		hdmi
+hsic		hv		lvds		mipi-bias
+nand		pex-bias	pex-clk1	pex-clk2
+pex-cntrl	sdmmc1		sdmmc3		sdmmc4
+sys_ddc		uart		usb0		usb1
+usb2		usb_bias
+
+The following pads are present on Tegra210:
+audio		audio-hv	cam		csia
+csib		csic		csid		csie
+csif		dbg		debug-nonao	dmic
+dp		dsi		dsib		dsic
+dsid		emmc		emmc2		gpio
+hdmi		hsic		lvds		mipi-bias
+pex-bias	pex-clk1	pex-clk2	pex-cntrl
+sdmmc1		sdmmc3		spi		spi-hv
+uart		usb0		usb1		usb2
+usb3		usb-bias
+
+Required pin configuration properties:
+  - pins: Must contain name of the pad(s) to be configured.
+
+Optional pin configuration properties:
+  - low-power-enable: Configure the pad into power down mode
+  - low-power-disable: Configure the pad into active mode
+  - power-source: Must contain either TEGRA_IO_PAD_VOLTAGE_1V8
+    or TEGRA_IO_PAD_VOLTAGE_3V3 to select between signaling voltages.
+    The values are defined in
+    include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h.
+
+Note: The power state can be configured on all of the Tegra124 and
+      Tegra132 pads. None of the Tegra124 or Tegra132 pads support
+      signaling voltage switching.
+
+Note: All of the listed Tegra210 pads except pex-cntrl support power
+      state configuration. Signaling voltage switching is supported on
+      following Tegra210 pads: audio, audio-hv, cam, dbg, dmic, gpio,
+      pex-cntrl, sdmmc1, sdmmc3, spi, spi-hv, and uart.
+
+Pad configuration state example:
+	pmc: pmc@7000e400 {
+		compatible = "nvidia,tegra210-pmc";
+		reg = <0x0 0x7000e400 0x0 0x400>;
+		clocks = <&tegra_car TEGRA210_CLK_PCLK>, <&clk32k_in>;
+		clock-names = "pclk", "clk32k_in";
+
+		...
+
+		sdmmc1_3v3: sdmmc1-3v3 {
+			pins = "sdmmc1";
+			power-source = <TEGRA_IO_PAD_VOLTAGE_3V3>;
+		};
+
+		sdmmc1_1v8: sdmmc1-1v8 {
+			pins = "sdmmc1";
+			power-source = <TEGRA_IO_PAD_VOLTAGE_1V8>;
+		};
+
+		hdmi_off: hdmi-off {
+			pins = "hdmi";
+			low-power-enable;
+		}
+
+		hdmi_on: hdmi-on {
+			pins = "hdmi";
+			low-power-disable;
+		}
+	};
+
+Pinctrl client example:
+	sdmmc1: sdhci@700b0000 {
+		...
+		pinctrl-names = "sdmmc-3v3", "sdmmc-1v8";
+		pinctrl-0 = <&sdmmc1_3v3>;
+		pinctrl-1 = <&sdmmc1_1v8>;
+	};
+	...
+	sor@54540000 {
+		...
+		pinctrl-0 = <&hdmi_off>;
+		pinctrl-1 = <&hdmi_on>;
+		pinctrl-names = "hdmi-on", "hdmi-off";
+	};
diff --git a/include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h b/include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h
new file mode 100644
index 0000000..20f4340
--- /dev/null
+++ b/include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h
@@ -0,0 +1,18 @@
+/* SPDX-License-Identifier: GPL-2.0 */
+/*
+ * pinctrl-tegra-io-pad.h: Tegra I/O pad source voltage configuration constants
+ * pinctrl bindings.
+ *
+ * Copyright (c) 2018, NVIDIA CORPORATION.  All rights reserved.
+ *
+ * Author: Aapo Vienamo <avienamo@nvidia.com>
+ */
+
+#ifndef _DT_BINDINGS_PINCTRL_TEGRA_IO_PAD_H
+#define _DT_BINDINGS_PINCTRL_TEGRA_IO_PAD_H
+
+/* Voltage levels of the I/O pad's source rail */
+#define TEGRA_IO_PAD_VOLTAGE_1V8	0
+#define TEGRA_IO_PAD_VOLTAGE_3V3	1
+
+#endif
-- 
2.7.4


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

* [PATCH v2 02/40] dt-bindings: mmc: tegra: Add pad voltage control properties
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 01/40] dt-bindings: Add Tegra PMC pad configuration bindings Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 03/40] dt-bindings: Add Tegra SDHCI pad pdpu offset bindings Aapo Vienamo
                   ` (40 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Document the pinctrl bindings used by the SDHCI driver to reconfigure
pad voltages on controllers supporting multiple voltage levels.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
Reviewed-by: Mikko Perttunen <mperttunen@nvidia.com>
Reviewed-by: Rob Herring <robh@kernel.org>
---
 .../bindings/mmc/nvidia,tegra20-sdhci.txt          | 22 ++++++++++++++++++++++
 1 file changed, 22 insertions(+)

diff --git a/Documentation/devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt b/Documentation/devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt
index 9bce578..90c214d 100644
--- a/Documentation/devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt
+++ b/Documentation/devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt
@@ -38,3 +38,25 @@ sdhci@c8000200 {
 	power-gpios = <&gpio 155 0>; /* gpio PT3 */
 	bus-width = <8>;
 };
+
+Optional properties for Tegra210 and Tegra186:
+- pinctrl-names, pinctrl-0, pinctrl-1 : Specify pad voltage
+  configurations. Valid pinctrl-names are "sdmmc-3v3" and "sdmmc-1v8"
+  for controllers supporting multiple voltage levels. The order of names
+  should correspond to the pin configuration states in pinctrl-0 and
+  pinctrl-1.
+
+Example:
+sdhci@700b0000 {
+	compatible = "nvidia,tegra210-sdhci", "nvidia,tegra124-sdhci";
+	reg = <0x0 0x700b0000 0x0 0x200>;
+	interrupts = <GIC_SPI 14 IRQ_TYPE_LEVEL_HIGH>;
+	clocks = <&tegra_car TEGRA210_CLK_SDMMC1>;
+	clock-names = "sdhci";
+	resets = <&tegra_car 14>;
+	reset-names = "sdhci";
+	pinctrl-names = "sdmmc-3v3", "sdmmc-1v8";
+	pinctrl-0 = <&sdmmc1_3v3>;
+	pinctrl-1 = <&sdmmc1_1v8>;
+	status = "disabled";
+};
-- 
2.7.4


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

* [PATCH v2 03/40] dt-bindings: Add Tegra SDHCI pad pdpu offset bindings
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 01/40] dt-bindings: Add Tegra PMC pad configuration bindings Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 02/40] dt-bindings: mmc: tegra: Add pad voltage control properties Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-13 19:24   ` Rob Herring
  2018-08-10 18:08 ` [PATCH v2 04/40] dt-bindings: mmc: Add Tegra SDHCI sampling trimmer values Aapo Vienamo
                   ` (39 subsequent siblings)
  42 siblings, 1 reply; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Add bindings documentation for pad pull up and pull down offset values to be
programmed before executing automatic pad drive strength calibration.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 .../bindings/mmc/nvidia,tegra20-sdhci.txt          | 35 ++++++++++++++++++++++
 1 file changed, 35 insertions(+)

diff --git a/Documentation/devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt b/Documentation/devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt
index 90c214d..9713e05 100644
--- a/Documentation/devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt
+++ b/Documentation/devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt
@@ -45,6 +45,37 @@ Optional properties for Tegra210 and Tegra186:
   for controllers supporting multiple voltage levels. The order of names
   should correspond to the pin configuration states in pinctrl-0 and
   pinctrl-1.
+- nvidia,only-1-8-v : The presence of this property indicates that the
+  controller operates at a 1.8 V fixed I/O voltage.
+- nvidia,pad-autocal-pull-up-offset-3v3,
+  nvidia,pad-autocal-pull-down-offset-3v3 : Specify drive strength
+  calibration offsets for 3.3 V signaling modes.
+- nvidia,pad-autocal-pull-up-offset-1v8,
+  nvidia,pad-autocal-pull-down-offset-1v8 : Specify drive strength
+  calibration offsets for 1.8 V signaling modes.
+- nvidia,pad-autocal-pull-up-offset-3v3-timeout,
+  nvidia,pad-autocal-pull-down-offset-3v3-timeout : Specify drive
+  strength used as a fallback in case the automatic calibration times
+  out on a 3.3 V signaling mode.
+- nvidia,pad-autocal-pull-up-offset-1v8-timeout,
+  nvidia,pad-autocal-pull-down-offset-1v8-timeout : Specify drive
+  strength used as a fallback in case the automatic calibration times
+  out on a 1.8 V signaling mode.
+- nvidia,pad-autocal-pull-up-offset-sdr104,
+  nvidia,pad-autocal-pull-down-offset-sdr104 : Specify drive strength
+  calibration offsets for SDR104 mode.
+- nvidia,pad-autocal-pull-up-offset-hs400,
+  nvidia,pad-autocal-pull-down-offset-hs400 : Specify drive strength
+  calibration offsets for HS400 mode.
+
+  Notes on the pad calibration pull up and pulldown offset values:
+    - The property values are drive codes which are programmed into the
+      PD_OFFSET and PU_OFFSET sections of the
+      SDHCI_TEGRA_AUTO_CAL_CONFIG register.
+    - A higher value corresponds to higher drive strength. Please refer
+      to the reference manual of the SoC for correct values.
+    - The SDR104 and HS400 timing specific values are used in
+      corresponding modes if specified.
 
 Example:
 sdhci@700b0000 {
@@ -58,5 +89,9 @@ sdhci@700b0000 {
 	pinctrl-names = "sdmmc-3v3", "sdmmc-1v8";
 	pinctrl-0 = <&sdmmc1_3v3>;
 	pinctrl-1 = <&sdmmc1_1v8>;
+	nvidia,pad-autocal-pull-up-offset-3v3 = <0x00>;
+	nvidia,pad-autocal-pull-down-offset-3v3 = <0x7d>;
+	nvidia,pad-autocal-pull-up-offset-1v8 = <0x7b>;
+	nvidia,pad-autocal-pull-down-offset-1v8 = <0x7b>;
 	status = "disabled";
 };
-- 
2.7.4


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

* [PATCH v2 04/40] dt-bindings: mmc: Add Tegra SDHCI sampling trimmer values
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (2 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 03/40] dt-bindings: Add Tegra SDHCI pad pdpu offset bindings Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-13 19:25   ` Rob Herring
  2018-08-10 18:08 ` [PATCH v2 05/40] soc/tegra: pmc: Fix pad voltage configuration for Tegra186 Aapo Vienamo
                   ` (38 subsequent siblings)
  42 siblings, 1 reply; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Document the Tegra SDHCI inbound and outbound sampling trimmer values.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 .../devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt          | 11 +++++++++++
 1 file changed, 11 insertions(+)

diff --git a/Documentation/devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt b/Documentation/devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt
index 9713e05..edecf97 100644
--- a/Documentation/devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt
+++ b/Documentation/devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt
@@ -67,6 +67,10 @@ Optional properties for Tegra210 and Tegra186:
 - nvidia,pad-autocal-pull-up-offset-hs400,
   nvidia,pad-autocal-pull-down-offset-hs400 : Specify drive strength
   calibration offsets for HS400 mode.
+- nvidia,default-tap : Specify the default inbound sampling clock
+  trimmer value for non-tunable modes.
+- nvidia,default-trim : Specify the default outbound clock trimmer
+  value.
 
   Notes on the pad calibration pull up and pulldown offset values:
     - The property values are drive codes which are programmed into the
@@ -77,6 +81,13 @@ Optional properties for Tegra210 and Tegra186:
     - The SDR104 and HS400 timing specific values are used in
       corresponding modes if specified.
 
+  Notes on tap and trim values:
+    - The values are used for compensating trace length differences
+      by adjusting the sampling point.
+    - The values are programmed to the Vendor Clock Control Register.
+      Please refer to the reference manual of the SoC for correct
+      values.
+
 Example:
 sdhci@700b0000 {
 	compatible = "nvidia,tegra210-sdhci", "nvidia,tegra124-sdhci";
-- 
2.7.4


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

* [PATCH v2 05/40] soc/tegra: pmc: Fix pad voltage configuration for Tegra186
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (3 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 04/40] dt-bindings: mmc: Add Tegra SDHCI sampling trimmer values Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 06/40] soc/tegra: pmc: Factor out DPD register bit calculation Aapo Vienamo
                   ` (37 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Implement support for the PMC_IMPL_E_33V_PWR register which replaces
PMC_PWR_DET register interface of the SoC generations preceding
Tegra186. Also add the voltage bit offsets to the tegra186_io_pads[]
table and the AO_HV pad.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
Acked-by: Jon Hunter <jonathanh@nvidia.com>
---
 drivers/soc/tegra/pmc.c | 55 +++++++++++++++++++++++++++++++++++--------------
 include/soc/tegra/pmc.h |  1 +
 2 files changed, 40 insertions(+), 16 deletions(-)

diff --git a/drivers/soc/tegra/pmc.c b/drivers/soc/tegra/pmc.c
index 2d6f3fc..d3ce6d1 100644
--- a/drivers/soc/tegra/pmc.c
+++ b/drivers/soc/tegra/pmc.c
@@ -65,6 +65,8 @@
 
 #define PWRGATE_STATUS			0x38
 
+#define PMC_IMPL_E_33V_PWR		0x40
+
 #define PMC_PWR_DET			0x48
 
 #define PMC_SCRATCH0_MODE_RECOVERY	BIT(31)
@@ -154,6 +156,7 @@ struct tegra_pmc_soc {
 	bool has_tsense_reset;
 	bool has_gpu_clamps;
 	bool needs_mbist_war;
+	bool has_impl_33v_pwr;
 
 	const struct tegra_io_pad_soc *io_pads;
 	unsigned int num_io_pads;
@@ -1073,20 +1076,31 @@ int tegra_io_pad_set_voltage(enum tegra_io_pad id,
 
 	mutex_lock(&pmc->powergates_lock);
 
-	/* write-enable PMC_PWR_DET_VALUE[pad->voltage] */
-	value = tegra_pmc_readl(PMC_PWR_DET);
-	value |= BIT(pad->voltage);
-	tegra_pmc_writel(value, PMC_PWR_DET);
+	if (pmc->soc->has_impl_33v_pwr) {
+		value = tegra_pmc_readl(PMC_IMPL_E_33V_PWR);
 
-	/* update I/O voltage */
-	value = tegra_pmc_readl(PMC_PWR_DET_VALUE);
+		if (voltage == TEGRA_IO_PAD_1800000UV)
+			value &= ~BIT(pad->voltage);
+		else
+			value |= BIT(pad->voltage);
 
-	if (voltage == TEGRA_IO_PAD_1800000UV)
-		value &= ~BIT(pad->voltage);
-	else
+		tegra_pmc_writel(value, PMC_IMPL_E_33V_PWR);
+	} else {
+		/* write-enable PMC_PWR_DET_VALUE[pad->voltage] */
+		value = tegra_pmc_readl(PMC_PWR_DET);
 		value |= BIT(pad->voltage);
+		tegra_pmc_writel(value, PMC_PWR_DET);
+
+		/* update I/O voltage */
+		value = tegra_pmc_readl(PMC_PWR_DET_VALUE);
 
-	tegra_pmc_writel(value, PMC_PWR_DET_VALUE);
+		if (voltage == TEGRA_IO_PAD_1800000UV)
+			value &= ~BIT(pad->voltage);
+		else
+			value |= BIT(pad->voltage);
+
+		tegra_pmc_writel(value, PMC_PWR_DET_VALUE);
+	}
 
 	mutex_unlock(&pmc->powergates_lock);
 
@@ -1108,7 +1122,10 @@ int tegra_io_pad_get_voltage(enum tegra_io_pad id)
 	if (pad->voltage == UINT_MAX)
 		return -ENOTSUPP;
 
-	value = tegra_pmc_readl(PMC_PWR_DET_VALUE);
+	if (pmc->soc->has_impl_33v_pwr)
+		value = tegra_pmc_readl(PMC_IMPL_E_33V_PWR);
+	else
+		value = tegra_pmc_readl(PMC_PWR_DET_VALUE);
 
 	if ((value & BIT(pad->voltage)) == 0)
 		return TEGRA_IO_PAD_1800000UV;
@@ -1567,6 +1584,7 @@ static const struct tegra_pmc_soc tegra30_pmc_soc = {
 	.cpu_powergates = tegra30_cpu_powergates,
 	.has_tsense_reset = true,
 	.has_gpu_clamps = false,
+	.has_impl_33v_pwr = false,
 	.num_io_pads = 0,
 	.io_pads = NULL,
 	.regs = &tegra20_pmc_regs,
@@ -1609,6 +1627,7 @@ static const struct tegra_pmc_soc tegra114_pmc_soc = {
 	.cpu_powergates = tegra114_cpu_powergates,
 	.has_tsense_reset = true,
 	.has_gpu_clamps = false,
+	.has_impl_33v_pwr = false,
 	.num_io_pads = 0,
 	.io_pads = NULL,
 	.regs = &tegra20_pmc_regs,
@@ -1689,6 +1708,7 @@ static const struct tegra_pmc_soc tegra124_pmc_soc = {
 	.cpu_powergates = tegra124_cpu_powergates,
 	.has_tsense_reset = true,
 	.has_gpu_clamps = true,
+	.has_impl_33v_pwr = false,
 	.num_io_pads = ARRAY_SIZE(tegra124_io_pads),
 	.io_pads = tegra124_io_pads,
 	.regs = &tegra20_pmc_regs,
@@ -1778,6 +1798,7 @@ static const struct tegra_pmc_soc tegra210_pmc_soc = {
 	.cpu_powergates = tegra210_cpu_powergates,
 	.has_tsense_reset = true,
 	.has_gpu_clamps = true,
+	.has_impl_33v_pwr = false,
 	.needs_mbist_war = true,
 	.num_io_pads = ARRAY_SIZE(tegra210_io_pads),
 	.io_pads = tegra210_io_pads,
@@ -1806,7 +1827,7 @@ static const struct tegra_io_pad_soc tegra186_io_pads[] = {
 	{ .id = TEGRA_IO_PAD_HDMI_DP0, .dpd = 28, .voltage = UINT_MAX },
 	{ .id = TEGRA_IO_PAD_HDMI_DP1, .dpd = 29, .voltage = UINT_MAX },
 	{ .id = TEGRA_IO_PAD_PEX_CNTRL, .dpd = 32, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_SDMMC2_HV, .dpd = 34, .voltage = UINT_MAX },
+	{ .id = TEGRA_IO_PAD_SDMMC2_HV, .dpd = 34, .voltage = 5 },
 	{ .id = TEGRA_IO_PAD_SDMMC4, .dpd = 36, .voltage = UINT_MAX },
 	{ .id = TEGRA_IO_PAD_CAM, .dpd = 38, .voltage = UINT_MAX },
 	{ .id = TEGRA_IO_PAD_DSIB, .dpd = 40, .voltage = UINT_MAX },
@@ -1818,12 +1839,13 @@ static const struct tegra_io_pad_soc tegra186_io_pads[] = {
 	{ .id = TEGRA_IO_PAD_CSIF, .dpd = 46, .voltage = UINT_MAX },
 	{ .id = TEGRA_IO_PAD_SPI, .dpd = 47, .voltage = UINT_MAX },
 	{ .id = TEGRA_IO_PAD_UFS, .dpd = 49, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_DMIC_HV, .dpd = 52, .voltage = UINT_MAX },
+	{ .id = TEGRA_IO_PAD_DMIC_HV, .dpd = 52, .voltage = 2 },
 	{ .id = TEGRA_IO_PAD_EDP, .dpd = 53, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_SDMMC1_HV, .dpd = 55, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_SDMMC3_HV, .dpd = 56, .voltage = UINT_MAX },
+	{ .id = TEGRA_IO_PAD_SDMMC1_HV, .dpd = 55, .voltage = 4 },
+	{ .id = TEGRA_IO_PAD_SDMMC3_HV, .dpd = 56, .voltage = 6 },
 	{ .id = TEGRA_IO_PAD_CONN, .dpd = 60, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_AUDIO_HV, .dpd = 61, .voltage = UINT_MAX },
+	{ .id = TEGRA_IO_PAD_AUDIO_HV, .dpd = 61, .voltage = 1 },
+	{ .id = TEGRA_IO_PAD_AO_HV, .dpd = UINT_MAX, .voltage = 0 },
 };
 
 static const struct tegra_pmc_regs tegra186_pmc_regs = {
@@ -1876,6 +1898,7 @@ static const struct tegra_pmc_soc tegra186_pmc_soc = {
 	.cpu_powergates = NULL,
 	.has_tsense_reset = false,
 	.has_gpu_clamps = false,
+	.has_impl_33v_pwr = true,
 	.num_io_pads = ARRAY_SIZE(tegra186_io_pads),
 	.io_pads = tegra186_io_pads,
 	.regs = &tegra186_pmc_regs,
diff --git a/include/soc/tegra/pmc.h b/include/soc/tegra/pmc.h
index c32bf91..445aa66 100644
--- a/include/soc/tegra/pmc.h
+++ b/include/soc/tegra/pmc.h
@@ -134,6 +134,7 @@ enum tegra_io_pad {
 	TEGRA_IO_PAD_USB2,
 	TEGRA_IO_PAD_USB3,
 	TEGRA_IO_PAD_USB_BIAS,
+	TEGRA_IO_PAD_AO_HV,
 };
 
 /* deprecated, use TEGRA_IO_PAD_{HDMI,LVDS} instead */
-- 
2.7.4


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

* [PATCH v2 06/40] soc/tegra: pmc: Factor out DPD register bit calculation
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (4 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 05/40] soc/tegra: pmc: Fix pad voltage configuration for Tegra186 Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 07/40] soc/tegra: pmc: Implement tegra_io_pad_is_powered() Aapo Vienamo
                   ` (36 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Factor out the the code to calculate the correct DPD register and bit
number for a given pad. This logic will be needed to query the status
register.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
Acked-by: Jon Hunter <jonathanh@nvidia.com>
---
 drivers/soc/tegra/pmc.c | 20 +++++++++++++++++---
 1 file changed, 17 insertions(+), 3 deletions(-)

diff --git a/drivers/soc/tegra/pmc.c b/drivers/soc/tegra/pmc.c
index d3ce6d1..f88bcb6 100644
--- a/drivers/soc/tegra/pmc.c
+++ b/drivers/soc/tegra/pmc.c
@@ -922,11 +922,12 @@ tegra_io_pad_find(struct tegra_pmc *pmc, enum tegra_io_pad id)
 	return NULL;
 }
 
-static int tegra_io_pad_prepare(enum tegra_io_pad id, unsigned long *request,
-				unsigned long *status, u32 *mask)
+static int tegra_io_pad_get_dpd_register_bit(enum tegra_io_pad id,
+					     unsigned long *request,
+					     unsigned long *status,
+					     u32 *mask)
 {
 	const struct tegra_io_pad_soc *pad;
-	unsigned long rate, value;
 
 	pad = tegra_io_pad_find(pmc, id);
 	if (!pad) {
@@ -947,6 +948,19 @@ static int tegra_io_pad_prepare(enum tegra_io_pad id, unsigned long *request,
 		*request = pmc->soc->regs->dpd2_req;
 	}
 
+	return 0;
+}
+
+static int tegra_io_pad_prepare(enum tegra_io_pad id, unsigned long *request,
+				unsigned long *status, u32 *mask)
+{
+	unsigned long rate, value;
+	int err;
+
+	err = tegra_io_pad_get_dpd_register_bit(id, request, status, mask);
+	if (err)
+		return err;
+
 	if (pmc->clk) {
 		rate = clk_get_rate(pmc->clk);
 		if (!rate) {
-- 
2.7.4


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

* [PATCH v2 07/40] soc/tegra: pmc: Implement tegra_io_pad_is_powered()
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (5 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 06/40] soc/tegra: pmc: Factor out DPD register bit calculation Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 08/40] soc/tegra: pmc: Use X macro to generate IO pad tables Aapo Vienamo
                   ` (35 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Implement a function to query whether a pad is in deep power down mode.
This is needed by the pinctrl callbacks.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
Acked-by: Jon Hunter <jonathanh@nvidia.com>
---
 drivers/soc/tegra/pmc.c | 15 +++++++++++++++
 1 file changed, 15 insertions(+)

diff --git a/drivers/soc/tegra/pmc.c b/drivers/soc/tegra/pmc.c
index f88bcb6..eb9385f 100644
--- a/drivers/soc/tegra/pmc.c
+++ b/drivers/soc/tegra/pmc.c
@@ -1075,6 +1075,21 @@ int tegra_io_pad_power_disable(enum tegra_io_pad id)
 }
 EXPORT_SYMBOL(tegra_io_pad_power_disable);
 
+static int tegra_io_pad_is_powered(enum tegra_io_pad id)
+{
+	unsigned long request, status;
+	u32 mask, value;
+	int err;
+
+	err = tegra_io_pad_get_dpd_register_bit(id, &request, &status, &mask);
+	if (err)
+		return err;
+
+	value = tegra_pmc_readl(status);
+
+	return !(value & mask);
+}
+
 int tegra_io_pad_set_voltage(enum tegra_io_pad id,
 			     enum tegra_io_pad_voltage voltage)
 {
-- 
2.7.4


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

* [PATCH v2 08/40] soc/tegra: pmc: Use X macro to generate IO pad tables
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (6 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 07/40] soc/tegra: pmc: Implement tegra_io_pad_is_powered() Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 09/40] soc/tegra: pmc: Remove public pad voltage APIs Aapo Vienamo
                   ` (34 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Refactor the IO pad tables into macro tables so that they can be reused
to generate pinctrl pin descriptors. Also add a name field which is
needed by pinctrl.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/soc/tegra/pmc.c | 233 ++++++++++++++++++++++++++----------------------
 1 file changed, 127 insertions(+), 106 deletions(-)

diff --git a/drivers/soc/tegra/pmc.c b/drivers/soc/tegra/pmc.c
index eb9385f..3b844b0 100644
--- a/drivers/soc/tegra/pmc.c
+++ b/drivers/soc/tegra/pmc.c
@@ -137,6 +137,7 @@ struct tegra_io_pad_soc {
 	enum tegra_io_pad id;
 	unsigned int dpd;
 	unsigned int voltage;
+	const char *name;
 };
 
 struct tegra_pmc_regs {
@@ -1697,37 +1698,49 @@ static const u8 tegra124_cpu_powergates[] = {
 	TEGRA_POWERGATE_CPU3,
 };
 
+#define TEGRA_IO_PAD(_id, _dpd, _voltage, _name)	\
+	((struct tegra_io_pad_soc) {			\
+		.id	= (_id),			\
+		.dpd	= (_dpd),			\
+		.voltage = (_voltage),			\
+		.name	= (_name),			\
+	})
+
+#define TEGRA124_IO_PAD_TABLE(_pad)					\
+	/* .id                          .dpd    .voltage  .name	*/	\
+	_pad(TEGRA_IO_PAD_AUDIO,	17,	UINT_MAX, "audio"),	\
+	_pad(TEGRA_IO_PAD_BB,		15,	UINT_MAX, "bb"),	\
+	_pad(TEGRA_IO_PAD_CAM,		36,	UINT_MAX, "cam"),	\
+	_pad(TEGRA_IO_PAD_COMP,		22,	UINT_MAX, "comp"),	\
+	_pad(TEGRA_IO_PAD_CSIA,		0,	UINT_MAX, "csia"),	\
+	_pad(TEGRA_IO_PAD_CSIB,		1,	UINT_MAX, "csb"),	\
+	_pad(TEGRA_IO_PAD_CSIE,		44,	UINT_MAX, "cse"),	\
+	_pad(TEGRA_IO_PAD_DSI,		2,	UINT_MAX, "dsi"),	\
+	_pad(TEGRA_IO_PAD_DSIB,		39,	UINT_MAX, "dsib"),	\
+	_pad(TEGRA_IO_PAD_DSIC,		40,	UINT_MAX, "dsic"),	\
+	_pad(TEGRA_IO_PAD_DSID,		41,	UINT_MAX, "dsid"),	\
+	_pad(TEGRA_IO_PAD_HDMI,		28,	UINT_MAX, "hdmi"),	\
+	_pad(TEGRA_IO_PAD_HSIC,		19,	UINT_MAX, "hsic"),	\
+	_pad(TEGRA_IO_PAD_HV,		38,	UINT_MAX, "hv"),	\
+	_pad(TEGRA_IO_PAD_LVDS,		57,	UINT_MAX, "lvds"),	\
+	_pad(TEGRA_IO_PAD_MIPI_BIAS,	3,	UINT_MAX, "mipi-bias"),	\
+	_pad(TEGRA_IO_PAD_NAND,		13,	UINT_MAX, "nand"),	\
+	_pad(TEGRA_IO_PAD_PEX_BIAS,	4,	UINT_MAX, "pex-bias"),	\
+	_pad(TEGRA_IO_PAD_PEX_CLK1,	5,	UINT_MAX, "pex-clk1"),	\
+	_pad(TEGRA_IO_PAD_PEX_CLK2,	6,	UINT_MAX, "pex-clk2"),	\
+	_pad(TEGRA_IO_PAD_PEX_CNTRL,	32,	UINT_MAX, "pex-cntrl"),	\
+	_pad(TEGRA_IO_PAD_SDMMC1,	33,	UINT_MAX, "sdmmc1"),	\
+	_pad(TEGRA_IO_PAD_SDMMC3,	34,	UINT_MAX, "sdmmc3"),	\
+	_pad(TEGRA_IO_PAD_SDMMC4,	35,	UINT_MAX, "sdmmc4"),	\
+	_pad(TEGRA_IO_PAD_SYS_DDC,	58,	UINT_MAX, "sys_ddc"),	\
+	_pad(TEGRA_IO_PAD_UART,		14,	UINT_MAX, "uart"),	\
+	_pad(TEGRA_IO_PAD_USB0,		9,	UINT_MAX, "usb0"),	\
+	_pad(TEGRA_IO_PAD_USB1,		10,	UINT_MAX, "usb1"),	\
+	_pad(TEGRA_IO_PAD_USB2,		11,	UINT_MAX, "usb2"),	\
+	_pad(TEGRA_IO_PAD_USB_BIAS,	12,	UINT_MAX, "usb_bias")
+
 static const struct tegra_io_pad_soc tegra124_io_pads[] = {
-	{ .id = TEGRA_IO_PAD_AUDIO, .dpd = 17, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_BB, .dpd = 15, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_CAM, .dpd = 36, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_COMP, .dpd = 22, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_CSIA, .dpd = 0, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_CSIB, .dpd = 1, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_CSIE, .dpd = 44, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_DSI, .dpd = 2, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_DSIB, .dpd = 39, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_DSIC, .dpd = 40, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_DSID, .dpd = 41, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_HDMI, .dpd = 28, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_HSIC, .dpd = 19, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_HV, .dpd = 38, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_LVDS, .dpd = 57, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_MIPI_BIAS, .dpd = 3, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_NAND, .dpd = 13, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_PEX_BIAS, .dpd = 4, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_PEX_CLK1, .dpd = 5, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_PEX_CLK2, .dpd = 6, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_PEX_CNTRL, .dpd = 32, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_SDMMC1, .dpd = 33, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_SDMMC3, .dpd = 34, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_SDMMC4, .dpd = 35, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_SYS_DDC, .dpd = 58, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_UART, .dpd = 14, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_USB0, .dpd = 9, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_USB1, .dpd = 10, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_USB2, .dpd = 11, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_USB_BIAS, .dpd = 12, .voltage = UINT_MAX },
+	TEGRA124_IO_PAD_TABLE(TEGRA_IO_PAD)
 };
 
 static const struct tegra_pmc_soc tegra124_pmc_soc = {
@@ -1779,45 +1792,49 @@ static const u8 tegra210_cpu_powergates[] = {
 	TEGRA_POWERGATE_CPU3,
 };
 
+#define TEGRA210_IO_PAD_TABLE(_pad)					   \
+	/*   .id                        .dpd     .voltage  .name */	   \
+	_pad(TEGRA_IO_PAD_AUDIO,       17,	 5,	   "audio"),	   \
+	_pad(TEGRA_IO_PAD_AUDIO_HV,    61,	 18,	   "audio-hv"),	   \
+	_pad(TEGRA_IO_PAD_CAM,	       36,	 10,	   "cam"),	   \
+	_pad(TEGRA_IO_PAD_CSIA,	       0,	 UINT_MAX, "csia"),	   \
+	_pad(TEGRA_IO_PAD_CSIB,	       1,	 UINT_MAX, "csib"),	   \
+	_pad(TEGRA_IO_PAD_CSIC,	       42,	 UINT_MAX, "csic"),	   \
+	_pad(TEGRA_IO_PAD_CSID,	       43,	 UINT_MAX, "csid"),	   \
+	_pad(TEGRA_IO_PAD_CSIE,	       44,	 UINT_MAX, "csie"),	   \
+	_pad(TEGRA_IO_PAD_CSIF,	       45,	 UINT_MAX, "csif"),	   \
+	_pad(TEGRA_IO_PAD_DBG,	       25,	 19,	   "dbg"),	   \
+	_pad(TEGRA_IO_PAD_DEBUG_NONAO, 26,	 UINT_MAX, "debug-nonao"), \
+	_pad(TEGRA_IO_PAD_DMIC,	       50,	 20,	   "dmic"),	   \
+	_pad(TEGRA_IO_PAD_DP,	       51,	 UINT_MAX, "dp"),	   \
+	_pad(TEGRA_IO_PAD_DSI,	       2,	 UINT_MAX, "dsi"),	   \
+	_pad(TEGRA_IO_PAD_DSIB,	       39,	 UINT_MAX, "dsib"),	   \
+	_pad(TEGRA_IO_PAD_DSIC,	       40,	 UINT_MAX, "dsic"),	   \
+	_pad(TEGRA_IO_PAD_DSID,	       41,	 UINT_MAX, "dsid"),	   \
+	_pad(TEGRA_IO_PAD_EMMC,	       35,	 UINT_MAX, "emmc"),	   \
+	_pad(TEGRA_IO_PAD_EMMC2,       37,	 UINT_MAX, "emmc2"),	   \
+	_pad(TEGRA_IO_PAD_GPIO,	       27,	 21,	   "gpio"),	   \
+	_pad(TEGRA_IO_PAD_HDMI,	       28,	 UINT_MAX, "hdmi"),	   \
+	_pad(TEGRA_IO_PAD_HSIC,	       19,	 UINT_MAX, "hsic"),	   \
+	_pad(TEGRA_IO_PAD_LVDS,	       57,	 UINT_MAX, "lvds"),	   \
+	_pad(TEGRA_IO_PAD_MIPI_BIAS,   3,	 UINT_MAX, "mipi-bias"),   \
+	_pad(TEGRA_IO_PAD_PEX_BIAS,    4,	 UINT_MAX, "pex-bias"),    \
+	_pad(TEGRA_IO_PAD_PEX_CLK1,    5,	 UINT_MAX, "pex-clk1"),    \
+	_pad(TEGRA_IO_PAD_PEX_CLK2,    6,	 UINT_MAX, "pex-clk2"),    \
+	_pad(TEGRA_IO_PAD_PEX_CNTRL,   UINT_MAX, 11,	   "pex-cntrl"),   \
+	_pad(TEGRA_IO_PAD_SDMMC1,      33,	 12,	   "sdmmc1"),	   \
+	_pad(TEGRA_IO_PAD_SDMMC3,      34,	 13,	   "sdmmc3"),	   \
+	_pad(TEGRA_IO_PAD_SPI,	       46,	 22,	   "spi"),	   \
+	_pad(TEGRA_IO_PAD_SPI_HV,      47,	 23,	   "spi-hv"),	   \
+	_pad(TEGRA_IO_PAD_UART,	       14,	 2,	   "uart"),	   \
+	_pad(TEGRA_IO_PAD_USB0,	       9,	 UINT_MAX, "usb0"),	   \
+	_pad(TEGRA_IO_PAD_USB1,	       10,	 UINT_MAX, "usb1"),	   \
+	_pad(TEGRA_IO_PAD_USB2,	       11,	 UINT_MAX, "usb2"),	   \
+	_pad(TEGRA_IO_PAD_USB3,	       18,	 UINT_MAX, "usb3"),	   \
+	_pad(TEGRA_IO_PAD_USB_BIAS,    12,	 UINT_MAX, "usb-bias")
+
 static const struct tegra_io_pad_soc tegra210_io_pads[] = {
-	{ .id = TEGRA_IO_PAD_AUDIO, .dpd = 17, .voltage = 5 },
-	{ .id = TEGRA_IO_PAD_AUDIO_HV, .dpd = 61, .voltage = 18 },
-	{ .id = TEGRA_IO_PAD_CAM, .dpd = 36, .voltage = 10 },
-	{ .id = TEGRA_IO_PAD_CSIA, .dpd = 0, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_CSIB, .dpd = 1, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_CSIC, .dpd = 42, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_CSID, .dpd = 43, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_CSIE, .dpd = 44, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_CSIF, .dpd = 45, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_DBG, .dpd = 25, .voltage = 19 },
-	{ .id = TEGRA_IO_PAD_DEBUG_NONAO, .dpd = 26, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_DMIC, .dpd = 50, .voltage = 20 },
-	{ .id = TEGRA_IO_PAD_DP, .dpd = 51, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_DSI, .dpd = 2, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_DSIB, .dpd = 39, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_DSIC, .dpd = 40, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_DSID, .dpd = 41, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_EMMC, .dpd = 35, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_EMMC2, .dpd = 37, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_GPIO, .dpd = 27, .voltage = 21 },
-	{ .id = TEGRA_IO_PAD_HDMI, .dpd = 28, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_HSIC, .dpd = 19, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_LVDS, .dpd = 57, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_MIPI_BIAS, .dpd = 3, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_PEX_BIAS, .dpd = 4, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_PEX_CLK1, .dpd = 5, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_PEX_CLK2, .dpd = 6, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_PEX_CNTRL, .dpd = UINT_MAX, .voltage = 11 },
-	{ .id = TEGRA_IO_PAD_SDMMC1, .dpd = 33, .voltage = 12 },
-	{ .id = TEGRA_IO_PAD_SDMMC3, .dpd = 34, .voltage = 13 },
-	{ .id = TEGRA_IO_PAD_SPI, .dpd = 46, .voltage = 22 },
-	{ .id = TEGRA_IO_PAD_SPI_HV, .dpd = 47, .voltage = 23 },
-	{ .id = TEGRA_IO_PAD_UART, .dpd = 14, .voltage = 2 },
-	{ .id = TEGRA_IO_PAD_USB0, .dpd = 9, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_USB1, .dpd = 10, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_USB2, .dpd = 11, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_USB3, .dpd = 18, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_USB_BIAS, .dpd = 12, .voltage = UINT_MAX },
+	TEGRA210_IO_PAD_TABLE(TEGRA_IO_PAD)
 };
 
 static const struct tegra_pmc_soc tegra210_pmc_soc = {
@@ -1836,45 +1853,49 @@ static const struct tegra_pmc_soc tegra210_pmc_soc = {
 	.setup_irq_polarity = tegra20_pmc_setup_irq_polarity,
 };
 
+#define TEGRA186_IO_PAD_TABLE(_pad)					     \
+	/*   .id                        .dpd      .voltage  .name */	     \
+	_pad(TEGRA_IO_PAD_CSIA,		0,	  UINT_MAX, "csia"),	     \
+	_pad(TEGRA_IO_PAD_CSIB,		1,	  UINT_MAX, "csib"),	     \
+	_pad(TEGRA_IO_PAD_DSI,		2,	  UINT_MAX, "dsi"),	     \
+	_pad(TEGRA_IO_PAD_MIPI_BIAS,	3,	  UINT_MAX, "mipi-bias"),    \
+	_pad(TEGRA_IO_PAD_PEX_CLK_BIAS,	4,	  UINT_MAX, "pex-clk-bias"), \
+	_pad(TEGRA_IO_PAD_PEX_CLK3,	5,	  UINT_MAX, "pex-clk3"),     \
+	_pad(TEGRA_IO_PAD_PEX_CLK2,	6,	  UINT_MAX, "pex-clk2"),     \
+	_pad(TEGRA_IO_PAD_PEX_CLK1,	7,	  UINT_MAX, "pex-clk1"),     \
+	_pad(TEGRA_IO_PAD_USB0,		9,	  UINT_MAX, "usb0"),	     \
+	_pad(TEGRA_IO_PAD_USB1,		10,	  UINT_MAX, "usb1"),	     \
+	_pad(TEGRA_IO_PAD_USB2,		11,	  UINT_MAX, "usb2"),	     \
+	_pad(TEGRA_IO_PAD_USB_BIAS,	12,	  UINT_MAX, "usb-bias"),     \
+	_pad(TEGRA_IO_PAD_UART,		14,	  UINT_MAX, "uart"),	     \
+	_pad(TEGRA_IO_PAD_AUDIO,	17,	  UINT_MAX, "audio"),	     \
+	_pad(TEGRA_IO_PAD_HSIC,		19,	  UINT_MAX, "hsic"),	     \
+	_pad(TEGRA_IO_PAD_DBG,		25,	  UINT_MAX, "dbg"),	     \
+	_pad(TEGRA_IO_PAD_HDMI_DP0,	28,	  UINT_MAX, "hdmi-dp0"),     \
+	_pad(TEGRA_IO_PAD_HDMI_DP1,	29,	  UINT_MAX, "hdmi-dp1"),     \
+	_pad(TEGRA_IO_PAD_PEX_CNTRL,	32,	  UINT_MAX, "pex-cntrl"),    \
+	_pad(TEGRA_IO_PAD_SDMMC2_HV,	34,	  5,	    "sdmmc2-hv"),    \
+	_pad(TEGRA_IO_PAD_SDMMC4,	36,	  UINT_MAX, "sdmmc4"),	     \
+	_pad(TEGRA_IO_PAD_CAM,		38,	  UINT_MAX, "cam"),	     \
+	_pad(TEGRA_IO_PAD_DSIB,		40,	  UINT_MAX, "dsib"),	     \
+	_pad(TEGRA_IO_PAD_DSIC,		41,	  UINT_MAX, "dsic"),	     \
+	_pad(TEGRA_IO_PAD_DSID,		42,	  UINT_MAX, "dsid"),	     \
+	_pad(TEGRA_IO_PAD_CSIC,		43,	  UINT_MAX, "csic"),	     \
+	_pad(TEGRA_IO_PAD_CSID,		44,	  UINT_MAX, "csid"),	     \
+	_pad(TEGRA_IO_PAD_CSIE,		45,	  UINT_MAX, "csie"),	     \
+	_pad(TEGRA_IO_PAD_CSIF,		46,	  UINT_MAX, "csif"),	     \
+	_pad(TEGRA_IO_PAD_SPI,		47,	  UINT_MAX, "spi"),	     \
+	_pad(TEGRA_IO_PAD_UFS,		49,	  UINT_MAX, "ufs"),	     \
+	_pad(TEGRA_IO_PAD_DMIC_HV,	52,	  2,	    "dmic-hv"),	     \
+	_pad(TEGRA_IO_PAD_EDP,		53,	  UINT_MAX, "edp"),	     \
+	_pad(TEGRA_IO_PAD_SDMMC1_HV,	55,	  4,	    "sdmmc1-hv"),    \
+	_pad(TEGRA_IO_PAD_SDMMC3_HV,	56,	  6,	    "sdmmc3-hv"),    \
+	_pad(TEGRA_IO_PAD_CONN,		60,	  UINT_MAX, "conn"),	     \
+	_pad(TEGRA_IO_PAD_AUDIO_HV,	61,	  1,	    "audio-hv"),     \
+	_pad(TEGRA_IO_PAD_AO_HV,	UINT_MAX, 0,	    "ao-hv")
+
 static const struct tegra_io_pad_soc tegra186_io_pads[] = {
-	{ .id = TEGRA_IO_PAD_CSIA, .dpd = 0, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_CSIB, .dpd = 1, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_DSI, .dpd = 2, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_MIPI_BIAS, .dpd = 3, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_PEX_CLK_BIAS, .dpd = 4, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_PEX_CLK3, .dpd = 5, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_PEX_CLK2, .dpd = 6, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_PEX_CLK1, .dpd = 7, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_USB0, .dpd = 9, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_USB1, .dpd = 10, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_USB2, .dpd = 11, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_USB_BIAS, .dpd = 12, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_UART, .dpd = 14, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_AUDIO, .dpd = 17, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_HSIC, .dpd = 19, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_DBG, .dpd = 25, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_HDMI_DP0, .dpd = 28, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_HDMI_DP1, .dpd = 29, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_PEX_CNTRL, .dpd = 32, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_SDMMC2_HV, .dpd = 34, .voltage = 5 },
-	{ .id = TEGRA_IO_PAD_SDMMC4, .dpd = 36, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_CAM, .dpd = 38, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_DSIB, .dpd = 40, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_DSIC, .dpd = 41, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_DSID, .dpd = 42, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_CSIC, .dpd = 43, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_CSID, .dpd = 44, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_CSIE, .dpd = 45, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_CSIF, .dpd = 46, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_SPI, .dpd = 47, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_UFS, .dpd = 49, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_DMIC_HV, .dpd = 52, .voltage = 2 },
-	{ .id = TEGRA_IO_PAD_EDP, .dpd = 53, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_SDMMC1_HV, .dpd = 55, .voltage = 4 },
-	{ .id = TEGRA_IO_PAD_SDMMC3_HV, .dpd = 56, .voltage = 6 },
-	{ .id = TEGRA_IO_PAD_CONN, .dpd = 60, .voltage = UINT_MAX },
-	{ .id = TEGRA_IO_PAD_AUDIO_HV, .dpd = 61, .voltage = 1 },
-	{ .id = TEGRA_IO_PAD_AO_HV, .dpd = UINT_MAX, .voltage = 0 },
+	TEGRA186_IO_PAD_TABLE(TEGRA_IO_PAD)
 };
 
 static const struct tegra_pmc_regs tegra186_pmc_regs = {
-- 
2.7.4


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

* [PATCH v2 09/40] soc/tegra: pmc: Remove public pad voltage APIs
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (7 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 08/40] soc/tegra: pmc: Use X macro to generate IO pad tables Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 10/40] soc/tegra: pmc: Implement pad configuration via pinctrl Aapo Vienamo
                   ` (33 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Make tegra_io_pad_set_voltage() and tegra_io_pad_get_voltage() static
and remove the prototypes from pmc.h. Remove enum tegra_io_pad_voltage
and use the defines from <dt-bindings/pinctrl/pinctrl-tegra-io-pad.h>
instead.

These functions aren't used outside of the pmc driver and new use cases
should use the pinctrl interface instead.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
Acked-by: Jon Hunter <jonathanh@nvidia.com>
---
 drivers/soc/tegra/pmc.c | 17 ++++++++---------
 include/soc/tegra/pmc.h | 19 -------------------
 2 files changed, 8 insertions(+), 28 deletions(-)

diff --git a/drivers/soc/tegra/pmc.c b/drivers/soc/tegra/pmc.c
index 3b844b0..de6832d 100644
--- a/drivers/soc/tegra/pmc.c
+++ b/drivers/soc/tegra/pmc.c
@@ -45,6 +45,8 @@
 #include <soc/tegra/fuse.h>
 #include <soc/tegra/pmc.h>
 
+#include <dt-bindings/pinctrl/pinctrl-tegra-io-pad.h>
+
 #define PMC_CNTRL			0x0
 #define  PMC_CNTRL_INTR_POLARITY	BIT(17) /* inverts INTR polarity */
 #define  PMC_CNTRL_CPU_PWRREQ_OE	BIT(16) /* CPU pwr req enable */
@@ -1091,8 +1093,7 @@ static int tegra_io_pad_is_powered(enum tegra_io_pad id)
 	return !(value & mask);
 }
 
-int tegra_io_pad_set_voltage(enum tegra_io_pad id,
-			     enum tegra_io_pad_voltage voltage)
+static int tegra_io_pad_set_voltage(enum tegra_io_pad id, int voltage)
 {
 	const struct tegra_io_pad_soc *pad;
 	u32 value;
@@ -1109,7 +1110,7 @@ int tegra_io_pad_set_voltage(enum tegra_io_pad id,
 	if (pmc->soc->has_impl_33v_pwr) {
 		value = tegra_pmc_readl(PMC_IMPL_E_33V_PWR);
 
-		if (voltage == TEGRA_IO_PAD_1800000UV)
+		if (voltage == TEGRA_IO_PAD_VOLTAGE_1V8)
 			value &= ~BIT(pad->voltage);
 		else
 			value |= BIT(pad->voltage);
@@ -1124,7 +1125,7 @@ int tegra_io_pad_set_voltage(enum tegra_io_pad id,
 		/* update I/O voltage */
 		value = tegra_pmc_readl(PMC_PWR_DET_VALUE);
 
-		if (voltage == TEGRA_IO_PAD_1800000UV)
+		if (voltage == TEGRA_IO_PAD_VOLTAGE_1V8)
 			value &= ~BIT(pad->voltage);
 		else
 			value |= BIT(pad->voltage);
@@ -1138,9 +1139,8 @@ int tegra_io_pad_set_voltage(enum tegra_io_pad id,
 
 	return 0;
 }
-EXPORT_SYMBOL(tegra_io_pad_set_voltage);
 
-int tegra_io_pad_get_voltage(enum tegra_io_pad id)
+static int tegra_io_pad_get_voltage(enum tegra_io_pad id)
 {
 	const struct tegra_io_pad_soc *pad;
 	u32 value;
@@ -1158,11 +1158,10 @@ int tegra_io_pad_get_voltage(enum tegra_io_pad id)
 		value = tegra_pmc_readl(PMC_PWR_DET_VALUE);
 
 	if ((value & BIT(pad->voltage)) == 0)
-		return TEGRA_IO_PAD_1800000UV;
+		return TEGRA_IO_PAD_VOLTAGE_1V8;
 
-	return TEGRA_IO_PAD_3300000UV;
+	return TEGRA_IO_PAD_VOLTAGE_3V3;
 }
-EXPORT_SYMBOL(tegra_io_pad_get_voltage);
 
 /**
  * tegra_io_rail_power_on() - enable power to I/O rail
diff --git a/include/soc/tegra/pmc.h b/include/soc/tegra/pmc.h
index 445aa66..5624268 100644
--- a/include/soc/tegra/pmc.h
+++ b/include/soc/tegra/pmc.h
@@ -141,16 +141,6 @@ enum tegra_io_pad {
 #define TEGRA_IO_RAIL_HDMI	TEGRA_IO_PAD_HDMI
 #define TEGRA_IO_RAIL_LVDS	TEGRA_IO_PAD_LVDS
 
-/**
- * enum tegra_io_pad_voltage - voltage level of the I/O pad's source rail
- * @TEGRA_IO_PAD_1800000UV: 1.8 V
- * @TEGRA_IO_PAD_3300000UV: 3.3 V
- */
-enum tegra_io_pad_voltage {
-	TEGRA_IO_PAD_1800000UV,
-	TEGRA_IO_PAD_3300000UV,
-};
-
 #ifdef CONFIG_SOC_TEGRA_PMC
 int tegra_powergate_is_powered(unsigned int id);
 int tegra_powergate_power_on(unsigned int id);
@@ -163,9 +153,6 @@ int tegra_powergate_sequence_power_up(unsigned int id, struct clk *clk,
 
 int tegra_io_pad_power_enable(enum tegra_io_pad id);
 int tegra_io_pad_power_disable(enum tegra_io_pad id);
-int tegra_io_pad_set_voltage(enum tegra_io_pad id,
-			     enum tegra_io_pad_voltage voltage);
-int tegra_io_pad_get_voltage(enum tegra_io_pad id);
 
 /* deprecated, use tegra_io_pad_power_{enable,disable}() instead */
 int tegra_io_rail_power_on(unsigned int id);
@@ -213,12 +200,6 @@ static inline int tegra_io_pad_power_disable(enum tegra_io_pad id)
 	return -ENOSYS;
 }
 
-static inline int tegra_io_pad_set_voltage(enum tegra_io_pad id,
-					   enum tegra_io_pad_voltage voltage)
-{
-	return -ENOSYS;
-}
-
 static inline int tegra_io_pad_get_voltage(enum tegra_io_pad id)
 {
 	return -ENOSYS;
-- 
2.7.4


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

* [PATCH v2 10/40] soc/tegra: pmc: Implement pad configuration via pinctrl
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (8 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 09/40] soc/tegra: pmc: Remove public pad voltage APIs Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 11/40] mmc: sdhci: Add a quirk to skip clearing the transfer mode register on tuning Aapo Vienamo
                   ` (32 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Register a pinctrl device and implement get and set functions for
PIN_CONFIG_LOW_POWER_MODE and PIN_CONFIG_POWER_SOURCE parameters.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
Acked-by: Jon Hunter <jonathanh@nvidia.com>
---
 drivers/soc/tegra/pmc.c | 187 +++++++++++++++++++++++++++++++++++++++++++++++-
 1 file changed, 185 insertions(+), 2 deletions(-)

diff --git a/drivers/soc/tegra/pmc.c b/drivers/soc/tegra/pmc.c
index de6832d..f666995 100644
--- a/drivers/soc/tegra/pmc.c
+++ b/drivers/soc/tegra/pmc.c
@@ -33,6 +33,9 @@
 #include <linux/of_address.h>
 #include <linux/of_clk.h>
 #include <linux/of_platform.h>
+#include <linux/pinctrl/pinctrl.h>
+#include <linux/pinctrl/pinconf.h>
+#include <linux/pinctrl/pinconf-generic.h>
 #include <linux/platform_device.h>
 #include <linux/pm_domain.h>
 #include <linux/reboot.h>
@@ -164,6 +167,9 @@ struct tegra_pmc_soc {
 	const struct tegra_io_pad_soc *io_pads;
 	unsigned int num_io_pads;
 
+	const struct pinctrl_pin_desc *pin_descs;
+	unsigned int num_pin_descs;
+
 	const struct tegra_pmc_regs *regs;
 	void (*init)(struct tegra_pmc *pmc);
 	void (*setup_irq_polarity)(struct tegra_pmc *pmc,
@@ -222,6 +228,8 @@ struct tegra_pmc {
 	DECLARE_BITMAP(powergates_available, TEGRA_POWERGATE_MAX);
 
 	struct mutex powergates_lock;
+
+	struct pinctrl_dev *pctl_dev;
 };
 
 static struct tegra_pmc *pmc = &(struct tegra_pmc) {
@@ -1399,6 +1407,142 @@ static void tegra_pmc_init_tsense_reset(struct tegra_pmc *pmc)
 	of_node_put(np);
 }
 
+static int tegra_io_pad_pinctrl_get_groups_count(struct pinctrl_dev *pctl_dev)
+{
+	return pmc->soc->num_io_pads;
+}
+
+static const char *tegra_io_pad_pinctrl_get_group_name(
+		struct pinctrl_dev *pctl, unsigned int group)
+{
+	return pmc->soc->io_pads[group].name;
+}
+
+static int tegra_io_pad_pinctrl_get_group_pins(struct pinctrl_dev *pctl_dev,
+					       unsigned int group,
+					       const unsigned int **pins,
+					       unsigned int *num_pins)
+{
+	*pins = &pmc->soc->io_pads[group].id;
+	*num_pins = 1;
+	return 0;
+}
+
+static const struct pinctrl_ops tegra_io_pad_pinctrl_ops = {
+	.get_groups_count = tegra_io_pad_pinctrl_get_groups_count,
+	.get_group_name = tegra_io_pad_pinctrl_get_group_name,
+	.get_group_pins = tegra_io_pad_pinctrl_get_group_pins,
+	.dt_node_to_map = pinconf_generic_dt_node_to_map_pin,
+	.dt_free_map = pinconf_generic_dt_free_map,
+};
+
+static int tegra_io_pad_pinconf_get(struct pinctrl_dev *pctl_dev,
+				    unsigned int pin, unsigned long *config)
+{
+	const struct tegra_io_pad_soc *pad = tegra_io_pad_find(pmc, pin);
+	enum pin_config_param param = pinconf_to_config_param(*config);
+	int ret;
+	u32 arg;
+
+	if (!pad)
+		return -EINVAL;
+
+	switch (param) {
+	case PIN_CONFIG_POWER_SOURCE:
+		ret = tegra_io_pad_get_voltage(pad->id);
+		if (ret < 0)
+			return ret;
+		arg = ret;
+		break;
+	case PIN_CONFIG_LOW_POWER_MODE:
+		ret = tegra_io_pad_is_powered(pad->id);
+		if (ret < 0)
+			return ret;
+		arg = !ret;
+		break;
+	default:
+		return -EINVAL;
+	}
+
+	*config = pinconf_to_config_packed(param, arg);
+
+	return 0;
+}
+
+static int tegra_io_pad_pinconf_set(struct pinctrl_dev *pctl_dev,
+				    unsigned int pin, unsigned long *configs,
+				    unsigned int num_configs)
+{
+	const struct tegra_io_pad_soc *pad = tegra_io_pad_find(pmc, pin);
+	enum pin_config_param param;
+	unsigned int i;
+	int err;
+	u32 arg;
+
+	if (!pad)
+		return -EINVAL;
+
+	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_LOW_POWER_MODE:
+			if (arg)
+				err = tegra_io_pad_power_disable(pad->id);
+			else
+				err = tegra_io_pad_power_enable(pad->id);
+			if (err)
+				return err;
+			break;
+		case PIN_CONFIG_POWER_SOURCE:
+			if (arg != TEGRA_IO_PAD_VOLTAGE_1V8 &&
+			    arg != TEGRA_IO_PAD_VOLTAGE_3V3)
+				return -EINVAL;
+			err = tegra_io_pad_set_voltage(pad->id, arg);
+			if (err)
+				return err;
+			break;
+		default:
+			return -EINVAL;
+		}
+	}
+
+	return 0;
+}
+
+static const struct pinconf_ops tegra_io_pad_pinconf_ops = {
+	.pin_config_get = tegra_io_pad_pinconf_get,
+	.pin_config_set = tegra_io_pad_pinconf_set,
+	.is_generic = true,
+};
+
+static struct pinctrl_desc tegra_pmc_pctl_desc = {
+	.pctlops = &tegra_io_pad_pinctrl_ops,
+	.confops = &tegra_io_pad_pinconf_ops,
+};
+
+static int tegra_pmc_pinctrl_init(struct tegra_pmc *pmc)
+{
+	int err = 0;
+
+	if (!pmc->soc->num_pin_descs)
+		return 0;
+
+	tegra_pmc_pctl_desc.name = dev_name(pmc->dev);
+	tegra_pmc_pctl_desc.pins = pmc->soc->pin_descs;
+	tegra_pmc_pctl_desc.npins = pmc->soc->num_pin_descs;
+
+	pmc->pctl_dev = devm_pinctrl_register(pmc->dev, &tegra_pmc_pctl_desc,
+					      pmc);
+	if (IS_ERR(pmc->pctl_dev)) {
+		err = PTR_ERR(pmc->pctl_dev);
+		dev_err(pmc->dev, "unable to register pinctrl, %d\n", err);
+	}
+
+	return err;
+}
+
 static int tegra_pmc_probe(struct platform_device *pdev)
 {
 	void __iomem *base;
@@ -1476,18 +1620,27 @@ static int tegra_pmc_probe(struct platform_device *pdev)
 
 	err = register_restart_handler(&tegra_pmc_restart_handler);
 	if (err) {
-		debugfs_remove(pmc->debugfs);
 		dev_err(&pdev->dev, "unable to register restart handler, %d\n",
 			err);
-		return err;
+		goto cleanup_debugfs;
 	}
 
+	err = tegra_pmc_pinctrl_init(pmc);
+	if (err)
+		goto cleanup_restart_handler;
+
 	mutex_lock(&pmc->powergates_lock);
 	iounmap(pmc->base);
 	pmc->base = base;
 	mutex_unlock(&pmc->powergates_lock);
 
 	return 0;
+
+cleanup_restart_handler:
+	unregister_restart_handler(&tegra_pmc_restart_handler);
+cleanup_debugfs:
+	debugfs_remove(pmc->debugfs);
+	return err;
 }
 
 #if defined(CONFIG_PM_SLEEP) && defined(CONFIG_ARM)
@@ -1577,6 +1730,8 @@ static const struct tegra_pmc_soc tegra20_pmc_soc = {
 	.has_gpu_clamps = false,
 	.num_io_pads = 0,
 	.io_pads = NULL,
+	.num_pin_descs = 0,
+	.pin_descs = NULL,
 	.regs = &tegra20_pmc_regs,
 	.init = tegra20_pmc_init,
 	.setup_irq_polarity = tegra20_pmc_setup_irq_polarity,
@@ -1616,6 +1771,8 @@ static const struct tegra_pmc_soc tegra30_pmc_soc = {
 	.has_impl_33v_pwr = false,
 	.num_io_pads = 0,
 	.io_pads = NULL,
+	.num_pin_descs = 0,
+	.pin_descs = NULL,
 	.regs = &tegra20_pmc_regs,
 	.init = tegra20_pmc_init,
 	.setup_irq_polarity = tegra20_pmc_setup_irq_polarity,
@@ -1659,6 +1816,8 @@ static const struct tegra_pmc_soc tegra114_pmc_soc = {
 	.has_impl_33v_pwr = false,
 	.num_io_pads = 0,
 	.io_pads = NULL,
+	.num_pin_descs = 0,
+	.pin_descs = NULL,
 	.regs = &tegra20_pmc_regs,
 	.init = tegra20_pmc_init,
 	.setup_irq_polarity = tegra20_pmc_setup_irq_polarity,
@@ -1705,6 +1864,12 @@ static const u8 tegra124_cpu_powergates[] = {
 		.name	= (_name),			\
 	})
 
+#define TEGRA_IO_PIN_DESC(_id, _dpd, _voltage, _name)	\
+	((struct pinctrl_pin_desc) {			\
+		.number = (_id),			\
+		.name	= (_name)			\
+	})
+
 #define TEGRA124_IO_PAD_TABLE(_pad)					\
 	/* .id                          .dpd    .voltage  .name	*/	\
 	_pad(TEGRA_IO_PAD_AUDIO,	17,	UINT_MAX, "audio"),	\
@@ -1742,6 +1907,10 @@ static const struct tegra_io_pad_soc tegra124_io_pads[] = {
 	TEGRA124_IO_PAD_TABLE(TEGRA_IO_PAD)
 };
 
+static const struct pinctrl_pin_desc tegra124_pin_descs[] = {
+	TEGRA124_IO_PAD_TABLE(TEGRA_IO_PIN_DESC)
+};
+
 static const struct tegra_pmc_soc tegra124_pmc_soc = {
 	.num_powergates = ARRAY_SIZE(tegra124_powergates),
 	.powergates = tegra124_powergates,
@@ -1752,6 +1921,8 @@ static const struct tegra_pmc_soc tegra124_pmc_soc = {
 	.has_impl_33v_pwr = false,
 	.num_io_pads = ARRAY_SIZE(tegra124_io_pads),
 	.io_pads = tegra124_io_pads,
+	.num_pin_descs = ARRAY_SIZE(tegra124_pin_descs),
+	.pin_descs = tegra124_pin_descs,
 	.regs = &tegra20_pmc_regs,
 	.init = tegra20_pmc_init,
 	.setup_irq_polarity = tegra20_pmc_setup_irq_polarity,
@@ -1836,6 +2007,10 @@ static const struct tegra_io_pad_soc tegra210_io_pads[] = {
 	TEGRA210_IO_PAD_TABLE(TEGRA_IO_PAD)
 };
 
+static const struct pinctrl_pin_desc tegra210_pin_descs[] = {
+	TEGRA210_IO_PAD_TABLE(TEGRA_IO_PIN_DESC)
+};
+
 static const struct tegra_pmc_soc tegra210_pmc_soc = {
 	.num_powergates = ARRAY_SIZE(tegra210_powergates),
 	.powergates = tegra210_powergates,
@@ -1847,6 +2022,8 @@ static const struct tegra_pmc_soc tegra210_pmc_soc = {
 	.needs_mbist_war = true,
 	.num_io_pads = ARRAY_SIZE(tegra210_io_pads),
 	.io_pads = tegra210_io_pads,
+	.num_pin_descs = ARRAY_SIZE(tegra210_pin_descs),
+	.pin_descs = tegra210_pin_descs,
 	.regs = &tegra20_pmc_regs,
 	.init = tegra20_pmc_init,
 	.setup_irq_polarity = tegra20_pmc_setup_irq_polarity,
@@ -1897,6 +2074,10 @@ static const struct tegra_io_pad_soc tegra186_io_pads[] = {
 	TEGRA186_IO_PAD_TABLE(TEGRA_IO_PAD)
 };
 
+static const struct pinctrl_pin_desc tegra186_pin_descs[] = {
+	TEGRA186_IO_PAD_TABLE(TEGRA_IO_PIN_DESC)
+};
+
 static const struct tegra_pmc_regs tegra186_pmc_regs = {
 	.scratch0 = 0x2000,
 	.dpd_req = 0x74,
@@ -1950,6 +2131,8 @@ static const struct tegra_pmc_soc tegra186_pmc_soc = {
 	.has_impl_33v_pwr = true,
 	.num_io_pads = ARRAY_SIZE(tegra186_io_pads),
 	.io_pads = tegra186_io_pads,
+	.num_pin_descs = ARRAY_SIZE(tegra186_pin_descs),
+	.pin_descs = tegra186_pin_descs,
 	.regs = &tegra186_pmc_regs,
 	.init = NULL,
 	.setup_irq_polarity = tegra186_pmc_setup_irq_polarity,
-- 
2.7.4


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

* [PATCH v2 11/40] mmc: sdhci: Add a quirk to skip clearing the transfer mode register on tuning
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (9 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 10/40] soc/tegra: pmc: Implement pad configuration via pinctrl Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-27 11:01   ` Adrian Hunter
  2018-08-10 18:08 ` [PATCH v2 12/40] mmc: tegra: Reconfigure pad voltages during voltage switching Aapo Vienamo
                   ` (31 subsequent siblings)
  42 siblings, 1 reply; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Add SDHCI_QUIRK2_TUNE_SKIP_XFERRMODE_REG_PROG to skip programming the
SDHCI_TRANSFER_MODE in sdhci_set_transfer_mode() if tuning command is
being sent.

On Tegra210 and Tegra186 the tuning sequence hangs if the SDHCI
transfer mode register is touched.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/mmc/host/sdhci.c | 6 ++++++
 drivers/mmc/host/sdhci.h | 2 ++
 2 files changed, 8 insertions(+)

diff --git a/drivers/mmc/host/sdhci.c b/drivers/mmc/host/sdhci.c
index a7b5602..04dc443 100644
--- a/drivers/mmc/host/sdhci.c
+++ b/drivers/mmc/host/sdhci.c
@@ -1028,6 +1028,12 @@ static void sdhci_set_transfer_mode(struct sdhci_host *host,
 
 	if (data == NULL) {
 		if (host->quirks2 &
+			SDHCI_QUIRK2_TUNE_SKIP_XFERMODE_REG_PROG &&
+				(cmd->opcode == MMC_SEND_TUNING_BLOCK ||
+				 cmd->opcode == MMC_SEND_TUNING_BLOCK_HS200)) {
+			return;
+		}
+		if (host->quirks2 &
 			SDHCI_QUIRK2_CLEAR_TRANSFERMODE_REG_BEFORE_CMD) {
 			sdhci_writew(host, 0x0, SDHCI_TRANSFER_MODE);
 		} else {
diff --git a/drivers/mmc/host/sdhci.h b/drivers/mmc/host/sdhci.h
index 23966f8..0a99008 100644
--- a/drivers/mmc/host/sdhci.h
+++ b/drivers/mmc/host/sdhci.h
@@ -450,6 +450,8 @@ struct sdhci_host {
  * obtainable timeout.
  */
 #define SDHCI_QUIRK2_DISABLE_HW_TIMEOUT			(1<<17)
+/* Don't clear the SDHCI_TRANSFER_MODE register on tuning commands */
+#define SDHCI_QUIRK2_TUNE_SKIP_XFERMODE_REG_PROG	(1<<18)
 
 	int irq;		/* Device IRQ */
 	void __iomem *ioaddr;	/* Mapped address */
-- 
2.7.4


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

* [PATCH v2 12/40] mmc: tegra: Reconfigure pad voltages during voltage switching
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (10 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 11/40] mmc: sdhci: Add a quirk to skip clearing the transfer mode register on tuning Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 13/40] mmc: tegra: Poll for calibration completion Aapo Vienamo
                   ` (30 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Parse the pinctrl state and nvidia,only-1-8-v properties from the device
tree. Validate the pinctrl and regulator configuration before unmasking
UHS modes. Implement pad voltage state reconfiguration in the mmc
start_signal_voltage_switch() callback. Add NVQUIRK_NEEDS_PAD_CONTROL
and add set it for Tegra210 and Tegra186.

The pad configuration is done in the mmc callback because the order of
pad reconfiguration and sdhci voltage switch depend on the voltage to
which the transition occurs.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/mmc/host/sdhci-tegra.c | 136 ++++++++++++++++++++++++++++++++++++++---
 1 file changed, 129 insertions(+), 7 deletions(-)

diff --git a/drivers/mmc/host/sdhci-tegra.c b/drivers/mmc/host/sdhci-tegra.c
index ddf00166..5e7f9ba 100644
--- a/drivers/mmc/host/sdhci-tegra.c
+++ b/drivers/mmc/host/sdhci-tegra.c
@@ -21,6 +21,8 @@
 #include <linux/io.h>
 #include <linux/of.h>
 #include <linux/of_device.h>
+#include <linux/pinctrl/consumer.h>
+#include <linux/regulator/consumer.h>
 #include <linux/reset.h>
 #include <linux/mmc/card.h>
 #include <linux/mmc/host.h>
@@ -55,6 +57,7 @@
 #define NVQUIRK_ENABLE_SDR104		BIT(4)
 #define NVQUIRK_ENABLE_DDR50		BIT(5)
 #define NVQUIRK_HAS_PADCALIB		BIT(6)
+#define NVQUIRK_NEEDS_PAD_CONTROL	BIT(7)
 
 struct sdhci_tegra_soc_data {
 	const struct sdhci_pltfm_data *pdata;
@@ -66,8 +69,12 @@ struct sdhci_tegra {
 	struct gpio_desc *power_gpio;
 	bool ddr_signaling;
 	bool pad_calib_required;
+	bool pad_control_available;
 
 	struct reset_control *rst;
+	struct pinctrl *pinctrl_sdmmc;
+	struct pinctrl_state *pinctrl_state_3v3;
+	struct pinctrl_state *pinctrl_state_1v8;
 };
 
 static u16 tegra_sdhci_readw(struct sdhci_host *host, int reg)
@@ -138,6 +145,39 @@ static unsigned int tegra_sdhci_get_ro(struct sdhci_host *host)
 	return mmc_gpio_get_ro(host->mmc);
 }
 
+static bool tegra_sdhci_is_pad_and_regulator_valid(struct sdhci_host *host)
+{
+	struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
+	struct sdhci_tegra *tegra_host = sdhci_pltfm_priv(pltfm_host);
+	int has_1v8, has_3v3;
+
+	/*
+	 * The SoCs which have NVQUIRK_NEEDS_PAD_CONTROL require software pad
+	 * voltage configuration in order to perform voltage switching. This
+	 * means that valid pinctrl info is required on SDHCI instances capable
+	 * of performing voltage switching. Whether or not an SDHCI instance is
+	 * capable of voltage switching is determined based on the regulator.
+	 */
+
+	if (!(tegra_host->soc_data->nvquirks & NVQUIRK_NEEDS_PAD_CONTROL))
+		return true;
+
+	if (IS_ERR(host->mmc->supply.vqmmc))
+		return false;
+
+	has_1v8 = regulator_is_supported_voltage(host->mmc->supply.vqmmc,
+						 1700000, 1950000);
+
+	has_3v3 = regulator_is_supported_voltage(host->mmc->supply.vqmmc,
+						 2700000, 3600000);
+
+	if (has_1v8 == 1 && has_3v3 == 1)
+		return tegra_host->pad_control_available;
+
+	/* Fixed voltage, no pad control required. */
+	return true;
+}
+
 static void tegra_sdhci_reset(struct sdhci_host *host, u8 mask)
 {
 	struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
@@ -160,13 +200,7 @@ static void tegra_sdhci_reset(struct sdhci_host *host, u8 mask)
 
 	clk_ctrl &= ~SDHCI_CLOCK_CTRL_SPI_MODE_CLKEN_OVERRIDE;
 
-	/*
-	 * If the board does not define a regulator for the SDHCI
-	 * IO voltage, then don't advertise support for UHS modes
-	 * even if the device supports it because the IO voltage
-	 * cannot be configured.
-	 */
-	if (!IS_ERR(host->mmc->supply.vqmmc)) {
+	if (tegra_sdhci_is_pad_and_regulator_valid(host)) {
 		/* Erratum: Enable SDHCI spec v3.00 support */
 		if (soc_data->nvquirks & NVQUIRK_ENABLE_SDHCI_SPEC_300)
 			misc_ctrl |= SDHCI_MISC_CTRL_ENABLE_SDHCI_SPEC_300;
@@ -286,6 +320,84 @@ static int tegra_sdhci_execute_tuning(struct sdhci_host *host, u32 opcode)
 	return mmc_send_tuning(host->mmc, opcode, NULL);
 }
 
+static int tegra_sdhci_set_padctrl(struct sdhci_host *host, int voltage)
+{
+	struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
+	struct sdhci_tegra *tegra_host = sdhci_pltfm_priv(pltfm_host);
+	int ret;
+
+	if (!tegra_host->pad_control_available)
+		return 0;
+
+	if (voltage == MMC_SIGNAL_VOLTAGE_180) {
+		ret = pinctrl_select_state(tegra_host->pinctrl_sdmmc,
+					   tegra_host->pinctrl_state_1v8);
+		if (ret < 0)
+			dev_err(mmc_dev(host->mmc),
+				"setting 1.8V failed, ret: %d\n", ret);
+	} else {
+		ret = pinctrl_select_state(tegra_host->pinctrl_sdmmc,
+					   tegra_host->pinctrl_state_3v3);
+		if (ret < 0)
+			dev_err(mmc_dev(host->mmc),
+				"setting 3.3V failed, ret: %d\n", ret);
+	}
+
+	return ret;
+}
+
+static int sdhci_tegra_start_signal_voltage_switch(struct mmc_host *mmc,
+						   struct mmc_ios *ios)
+{
+	struct sdhci_host *host = mmc_priv(mmc);
+	int ret = 0;
+
+	if (ios->signal_voltage == MMC_SIGNAL_VOLTAGE_330) {
+		ret = tegra_sdhci_set_padctrl(host, ios->signal_voltage);
+		if (ret < 0)
+			return ret;
+		ret = sdhci_start_signal_voltage_switch(mmc, ios);
+	} else if (ios->signal_voltage == MMC_SIGNAL_VOLTAGE_180) {
+		ret = sdhci_start_signal_voltage_switch(mmc, ios);
+		if (ret < 0)
+			return ret;
+		ret = tegra_sdhci_set_padctrl(host, ios->signal_voltage);
+	}
+
+	return ret;
+}
+
+static int tegra_sdhci_init_pinctrl_info(struct device *dev,
+					 struct sdhci_tegra *tegra_host)
+{
+	tegra_host->pinctrl_sdmmc = devm_pinctrl_get(dev);
+	if (IS_ERR(tegra_host->pinctrl_sdmmc)) {
+		dev_dbg(dev, "No pinctrl info, err: %ld\n",
+			PTR_ERR(tegra_host->pinctrl_sdmmc));
+		return -1;
+	}
+
+	tegra_host->pinctrl_state_3v3 =
+		pinctrl_lookup_state(tegra_host->pinctrl_sdmmc, "sdmmc-3v3");
+	if (IS_ERR(tegra_host->pinctrl_state_3v3)) {
+		dev_warn(dev, "Missing 3.3V pad state, err: %ld\n",
+			 PTR_ERR(tegra_host->pinctrl_state_3v3));
+		return -1;
+	}
+
+	tegra_host->pinctrl_state_1v8 =
+		pinctrl_lookup_state(tegra_host->pinctrl_sdmmc, "sdmmc-1v8");
+	if (IS_ERR(tegra_host->pinctrl_state_1v8)) {
+		dev_warn(dev, "Missing 1.8V pad state, err: %ld\n",
+			 PTR_ERR(tegra_host->pinctrl_state_3v3));
+		return -1;
+	}
+
+	tegra_host->pad_control_available = true;
+
+	return 0;
+}
+
 static void tegra_sdhci_voltage_switch(struct sdhci_host *host)
 {
 	struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
@@ -419,6 +531,7 @@ static const struct sdhci_pltfm_data sdhci_tegra210_pdata = {
 
 static const struct sdhci_tegra_soc_data soc_data_tegra210 = {
 	.pdata = &sdhci_tegra210_pdata,
+	.nvquirks = NVQUIRK_NEEDS_PAD_CONTROL,
 };
 
 static const struct sdhci_pltfm_data sdhci_tegra186_pdata = {
@@ -442,6 +555,7 @@ static const struct sdhci_pltfm_data sdhci_tegra186_pdata = {
 
 static const struct sdhci_tegra_soc_data soc_data_tegra186 = {
 	.pdata = &sdhci_tegra186_pdata,
+	.nvquirks = NVQUIRK_NEEDS_PAD_CONTROL,
 };
 
 static const struct of_device_id sdhci_tegra_dt_match[] = {
@@ -478,8 +592,16 @@ static int sdhci_tegra_probe(struct platform_device *pdev)
 	tegra_host = sdhci_pltfm_priv(pltfm_host);
 	tegra_host->ddr_signaling = false;
 	tegra_host->pad_calib_required = false;
+	tegra_host->pad_control_available = false;
 	tegra_host->soc_data = soc_data;
 
+	if (soc_data->nvquirks & NVQUIRK_NEEDS_PAD_CONTROL) {
+		rc = tegra_sdhci_init_pinctrl_info(&pdev->dev, tegra_host);
+		if (rc == 0)
+			host->mmc_host_ops.start_signal_voltage_switch =
+				sdhci_tegra_start_signal_voltage_switch;
+	}
+
 	rc = mmc_of_parse(host->mmc);
 	if (rc)
 		goto err_parse_dt;
-- 
2.7.4


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

* [PATCH v2 13/40] mmc: tegra: Poll for calibration completion
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (11 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 12/40] mmc: tegra: Reconfigure pad voltages during voltage switching Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 14/40] mmc: tegra: Set calibration pad voltage reference Aapo Vienamo
                   ` (29 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Implement polling with 10 ms timeout for automatic pad drive strength
calibration.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/mmc/host/sdhci-tegra.c | 22 +++++++++++++++++-----
 1 file changed, 17 insertions(+), 5 deletions(-)

diff --git a/drivers/mmc/host/sdhci-tegra.c b/drivers/mmc/host/sdhci-tegra.c
index 5e7f9ba..a62a3fc 100644
--- a/drivers/mmc/host/sdhci-tegra.c
+++ b/drivers/mmc/host/sdhci-tegra.c
@@ -16,6 +16,7 @@
 #include <linux/err.h>
 #include <linux/module.h>
 #include <linux/init.h>
+#include <linux/iopoll.h>
 #include <linux/platform_device.h>
 #include <linux/clk.h>
 #include <linux/io.h>
@@ -50,6 +51,9 @@
 #define SDHCI_AUTO_CAL_START			BIT(31)
 #define SDHCI_AUTO_CAL_ENABLE			BIT(29)
 
+#define SDHCI_TEGRA_AUTO_CAL_STATUS		0x1ec
+#define SDHCI_TEGRA_AUTO_CAL_ACTIVE		BIT(31)
+
 #define NVQUIRK_FORCE_SDHCI_SPEC_200	BIT(0)
 #define NVQUIRK_ENABLE_BLOCK_GAP_DET	BIT(1)
 #define NVQUIRK_ENABLE_SDHCI_SPEC_300	BIT(2)
@@ -226,13 +230,21 @@ static void tegra_sdhci_reset(struct sdhci_host *host, u8 mask)
 
 static void tegra_sdhci_pad_autocalib(struct sdhci_host *host)
 {
-	u32 val;
+	u32 reg;
+	int ret;
+
+	reg = sdhci_readl(host, SDHCI_TEGRA_AUTO_CAL_CONFIG);
+	reg |= SDHCI_AUTO_CAL_ENABLE | SDHCI_AUTO_CAL_START;
+	sdhci_writel(host, reg, SDHCI_TEGRA_AUTO_CAL_CONFIG);
 
-	mdelay(1);
+	usleep_range(1, 2);
+	/* 10 ms timeout */
+	ret = readl_poll_timeout(host->ioaddr + SDHCI_TEGRA_AUTO_CAL_STATUS,
+				 reg, !(reg & SDHCI_TEGRA_AUTO_CAL_ACTIVE),
+				 1000, 10000);
 
-	val = sdhci_readl(host, SDHCI_TEGRA_AUTO_CAL_CONFIG);
-	val |= SDHCI_AUTO_CAL_ENABLE | SDHCI_AUTO_CAL_START;
-	sdhci_writel(host,val, SDHCI_TEGRA_AUTO_CAL_CONFIG);
+	if (ret)
+		dev_err(mmc_dev(host->mmc), "Pad autocal timed out\n");
 }
 
 static void tegra_sdhci_set_clock(struct sdhci_host *host, unsigned int clock)
-- 
2.7.4


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

* [PATCH v2 14/40] mmc: tegra: Set calibration pad voltage reference
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (12 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 13/40] mmc: tegra: Poll for calibration completion Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 15/40] mmc: tegra: Power on the calibration pad Aapo Vienamo
                   ` (28 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Configure the voltage reference used by the automatic pad drive strength
calibration procedure. The value is a magic number from the TRM.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/mmc/host/sdhci-tegra.c | 56 +++++++++++++++++++++++++-----------------
 1 file changed, 33 insertions(+), 23 deletions(-)

diff --git a/drivers/mmc/host/sdhci-tegra.c b/drivers/mmc/host/sdhci-tegra.c
index a62a3fc..6ddc7c2 100644
--- a/drivers/mmc/host/sdhci-tegra.c
+++ b/drivers/mmc/host/sdhci-tegra.c
@@ -41,27 +41,31 @@
 #define SDHCI_CLOCK_CTRL_PADPIPE_CLKEN_OVERRIDE		BIT(3)
 #define SDHCI_CLOCK_CTRL_SPI_MODE_CLKEN_OVERRIDE	BIT(2)
 
-#define SDHCI_TEGRA_VENDOR_MISC_CTRL		0x120
-#define SDHCI_MISC_CTRL_ENABLE_SDR104		0x8
-#define SDHCI_MISC_CTRL_ENABLE_SDR50		0x10
-#define SDHCI_MISC_CTRL_ENABLE_SDHCI_SPEC_300	0x20
-#define SDHCI_MISC_CTRL_ENABLE_DDR50		0x200
-
-#define SDHCI_TEGRA_AUTO_CAL_CONFIG		0x1e4
-#define SDHCI_AUTO_CAL_START			BIT(31)
-#define SDHCI_AUTO_CAL_ENABLE			BIT(29)
-
-#define SDHCI_TEGRA_AUTO_CAL_STATUS		0x1ec
-#define SDHCI_TEGRA_AUTO_CAL_ACTIVE		BIT(31)
-
-#define NVQUIRK_FORCE_SDHCI_SPEC_200	BIT(0)
-#define NVQUIRK_ENABLE_BLOCK_GAP_DET	BIT(1)
-#define NVQUIRK_ENABLE_SDHCI_SPEC_300	BIT(2)
-#define NVQUIRK_ENABLE_SDR50		BIT(3)
-#define NVQUIRK_ENABLE_SDR104		BIT(4)
-#define NVQUIRK_ENABLE_DDR50		BIT(5)
-#define NVQUIRK_HAS_PADCALIB		BIT(6)
-#define NVQUIRK_NEEDS_PAD_CONTROL	BIT(7)
+#define SDHCI_TEGRA_VENDOR_MISC_CTRL			0x120
+#define SDHCI_MISC_CTRL_ENABLE_SDR104			0x8
+#define SDHCI_MISC_CTRL_ENABLE_SDR50			0x10
+#define SDHCI_MISC_CTRL_ENABLE_SDHCI_SPEC_300		0x20
+#define SDHCI_MISC_CTRL_ENABLE_DDR50			0x200
+
+#define SDHCI_TEGRA_AUTO_CAL_CONFIG			0x1e4
+#define SDHCI_AUTO_CAL_START				BIT(31)
+#define SDHCI_AUTO_CAL_ENABLE				BIT(29)
+
+#define SDHCI_TEGRA_SDMEM_COMP_PADCTRL			0x1e0
+#define SDHCI_TEGRA_SDMEM_COMP_PADCTRL_VREF_SEL_MASK	0x0000000f
+#define SDHCI_TEGRA_SDMEM_COMP_PADCTRL_VREF_SEL_VAL	0x7
+
+#define SDHCI_TEGRA_AUTO_CAL_STATUS			0x1ec
+#define SDHCI_TEGRA_AUTO_CAL_ACTIVE			BIT(31)
+
+#define NVQUIRK_FORCE_SDHCI_SPEC_200			BIT(0)
+#define NVQUIRK_ENABLE_BLOCK_GAP_DET			BIT(1)
+#define NVQUIRK_ENABLE_SDHCI_SPEC_300			BIT(2)
+#define NVQUIRK_ENABLE_SDR50				BIT(3)
+#define NVQUIRK_ENABLE_SDR104				BIT(4)
+#define NVQUIRK_ENABLE_DDR50				BIT(5)
+#define NVQUIRK_HAS_PADCALIB				BIT(6)
+#define NVQUIRK_NEEDS_PAD_CONTROL			BIT(7)
 
 struct sdhci_tegra_soc_data {
 	const struct sdhci_pltfm_data *pdata;
@@ -187,7 +191,7 @@ static void tegra_sdhci_reset(struct sdhci_host *host, u8 mask)
 	struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
 	struct sdhci_tegra *tegra_host = sdhci_pltfm_priv(pltfm_host);
 	const struct sdhci_tegra_soc_data *soc_data = tegra_host->soc_data;
-	u32 misc_ctrl, clk_ctrl;
+	u32 misc_ctrl, clk_ctrl, pad_ctrl;
 
 	sdhci_reset(host, mask);
 
@@ -222,8 +226,14 @@ static void tegra_sdhci_reset(struct sdhci_host *host, u8 mask)
 	sdhci_writel(host, misc_ctrl, SDHCI_TEGRA_VENDOR_MISC_CTRL);
 	sdhci_writel(host, clk_ctrl, SDHCI_TEGRA_VENDOR_CLOCK_CTRL);
 
-	if (soc_data->nvquirks & NVQUIRK_HAS_PADCALIB)
+	if (soc_data->nvquirks & NVQUIRK_HAS_PADCALIB) {
+		pad_ctrl = sdhci_readl(host, SDHCI_TEGRA_SDMEM_COMP_PADCTRL);
+		pad_ctrl &= ~SDHCI_TEGRA_SDMEM_COMP_PADCTRL_VREF_SEL_MASK;
+		pad_ctrl |= SDHCI_TEGRA_SDMEM_COMP_PADCTRL_VREF_SEL_VAL;
+		sdhci_writel(host, pad_ctrl, SDHCI_TEGRA_SDMEM_COMP_PADCTRL);
+
 		tegra_host->pad_calib_required = true;
+	}
 
 	tegra_host->ddr_signaling = false;
 }
-- 
2.7.4


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

* [PATCH v2 15/40] mmc: tegra: Power on the calibration pad
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (13 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 14/40] mmc: tegra: Set calibration pad voltage reference Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 16/40] mmc: tegra: Disable card clock during pad calibration Aapo Vienamo
                   ` (27 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Automatic pad drive strength calibration is performed on a separate pad
identical to the ones used for driving the actual bus. Power on the
calibration pad during the calibration procedure and power it off
afterwards to save power.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
Reviewed-by: Mikko Perttunen <mperttunen@nvidia.com>
---
 drivers/mmc/host/sdhci-tegra.c | 26 ++++++++++++++++++++++++++
 1 file changed, 26 insertions(+)

diff --git a/drivers/mmc/host/sdhci-tegra.c b/drivers/mmc/host/sdhci-tegra.c
index 6ddc7c2..a00e366 100644
--- a/drivers/mmc/host/sdhci-tegra.c
+++ b/drivers/mmc/host/sdhci-tegra.c
@@ -54,6 +54,7 @@
 #define SDHCI_TEGRA_SDMEM_COMP_PADCTRL			0x1e0
 #define SDHCI_TEGRA_SDMEM_COMP_PADCTRL_VREF_SEL_MASK	0x0000000f
 #define SDHCI_TEGRA_SDMEM_COMP_PADCTRL_VREF_SEL_VAL	0x7
+#define SDHCI_TEGRA_SDMEM_COMP_PADCTRL_E_INPUT_E_PWRD	BIT(31)
 
 #define SDHCI_TEGRA_AUTO_CAL_STATUS			0x1ec
 #define SDHCI_TEGRA_AUTO_CAL_ACTIVE			BIT(31)
@@ -238,11 +239,34 @@ static void tegra_sdhci_reset(struct sdhci_host *host, u8 mask)
 	tegra_host->ddr_signaling = false;
 }
 
+static void tegra_sdhci_configure_cal_pad(struct sdhci_host *host, bool enable)
+{
+	u32 val;
+
+	/*
+	 * Enable or disable the additional I/O pad used by the drive strength
+	 * calibration process.
+	 */
+	val = sdhci_readl(host, SDHCI_TEGRA_SDMEM_COMP_PADCTRL);
+
+	if (enable)
+		val |= SDHCI_TEGRA_SDMEM_COMP_PADCTRL_E_INPUT_E_PWRD;
+	else
+		val &= ~SDHCI_TEGRA_SDMEM_COMP_PADCTRL_E_INPUT_E_PWRD;
+
+	sdhci_writel(host, val, SDHCI_TEGRA_SDMEM_COMP_PADCTRL);
+
+	if (enable)
+		usleep_range(1, 2);
+}
+
 static void tegra_sdhci_pad_autocalib(struct sdhci_host *host)
 {
 	u32 reg;
 	int ret;
 
+	tegra_sdhci_configure_cal_pad(host, true);
+
 	reg = sdhci_readl(host, SDHCI_TEGRA_AUTO_CAL_CONFIG);
 	reg |= SDHCI_AUTO_CAL_ENABLE | SDHCI_AUTO_CAL_START;
 	sdhci_writel(host, reg, SDHCI_TEGRA_AUTO_CAL_CONFIG);
@@ -253,6 +277,8 @@ static void tegra_sdhci_pad_autocalib(struct sdhci_host *host)
 				 reg, !(reg & SDHCI_TEGRA_AUTO_CAL_ACTIVE),
 				 1000, 10000);
 
+	tegra_sdhci_configure_cal_pad(host, false);
+
 	if (ret)
 		dev_err(mmc_dev(host->mmc), "Pad autocal timed out\n");
 }
-- 
2.7.4


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

* [PATCH v2 16/40] mmc: tegra: Disable card clock during pad calibration
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (14 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 15/40] mmc: tegra: Power on the calibration pad Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 17/40] mmc: tegra: Program pad autocal offsets from dt Aapo Vienamo
                   ` (26 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Disable the card clock during automatic pad drive strength calibration
and re-enable it afterwards.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/mmc/host/sdhci-tegra.c | 26 ++++++++++++++++++++++++++
 1 file changed, 26 insertions(+)

diff --git a/drivers/mmc/host/sdhci-tegra.c b/drivers/mmc/host/sdhci-tegra.c
index a00e366..f1eda0c 100644
--- a/drivers/mmc/host/sdhci-tegra.c
+++ b/drivers/mmc/host/sdhci-tegra.c
@@ -260,11 +260,35 @@ static void tegra_sdhci_configure_cal_pad(struct sdhci_host *host, bool enable)
 		usleep_range(1, 2);
 }
 
+static bool tegra_sdhci_configure_card_clk(struct sdhci_host *host, bool enable)
+{
+	bool status;
+	u32 reg;
+
+	reg = sdhci_readw(host, SDHCI_CLOCK_CONTROL);
+	status = !!(reg & SDHCI_CLOCK_CARD_EN);
+
+	if (status == enable)
+		return status;
+
+	if (enable)
+		reg |= SDHCI_CLOCK_CARD_EN;
+	else
+		reg &= ~SDHCI_CLOCK_CARD_EN;
+
+	sdhci_writew(host, reg, SDHCI_CLOCK_CONTROL);
+
+	return status;
+}
+
 static void tegra_sdhci_pad_autocalib(struct sdhci_host *host)
 {
+	bool card_clk_enabled;
 	u32 reg;
 	int ret;
 
+	card_clk_enabled = tegra_sdhci_configure_card_clk(host, false);
+
 	tegra_sdhci_configure_cal_pad(host, true);
 
 	reg = sdhci_readl(host, SDHCI_TEGRA_AUTO_CAL_CONFIG);
@@ -279,6 +303,8 @@ static void tegra_sdhci_pad_autocalib(struct sdhci_host *host)
 
 	tegra_sdhci_configure_cal_pad(host, false);
 
+	tegra_sdhci_configure_card_clk(host, card_clk_enabled);
+
 	if (ret)
 		dev_err(mmc_dev(host->mmc), "Pad autocal timed out\n");
 }
-- 
2.7.4


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

* [PATCH v2 17/40] mmc: tegra: Program pad autocal offsets from dt
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (15 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 16/40] mmc: tegra: Disable card clock during pad calibration Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 18/40] mmc: tegra: Perform pad calibration after voltage switch Aapo Vienamo
                   ` (25 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Parse the pad drive strength calibration offsets from the device tree.
Program the calibration offsets in accordance with the current signaling
mode.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/mmc/host/sdhci-tegra.c | 152 ++++++++++++++++++++++++++++++++++++++++-
 1 file changed, 151 insertions(+), 1 deletion(-)

diff --git a/drivers/mmc/host/sdhci-tegra.c b/drivers/mmc/host/sdhci-tegra.c
index f1eda0c..eff1c82 100644
--- a/drivers/mmc/host/sdhci-tegra.c
+++ b/drivers/mmc/host/sdhci-tegra.c
@@ -50,6 +50,7 @@
 #define SDHCI_TEGRA_AUTO_CAL_CONFIG			0x1e4
 #define SDHCI_AUTO_CAL_START				BIT(31)
 #define SDHCI_AUTO_CAL_ENABLE				BIT(29)
+#define SDHCI_AUTO_CAL_PDPU_OFFSET_MASK			0x0000ffff
 
 #define SDHCI_TEGRA_SDMEM_COMP_PADCTRL			0x1e0
 #define SDHCI_TEGRA_SDMEM_COMP_PADCTRL_VREF_SEL_MASK	0x0000000f
@@ -73,6 +74,22 @@ struct sdhci_tegra_soc_data {
 	u32 nvquirks;
 };
 
+/* Magic pull up and pull down pad calibration offsets */
+struct sdhci_tegra_autocal_offsets {
+	u32 pull_up_3v3;
+	u32 pull_down_3v3;
+	u32 pull_up_3v3_timeout;
+	u32 pull_down_3v3_timeout;
+	u32 pull_up_1v8;
+	u32 pull_down_1v8;
+	u32 pull_up_1v8_timeout;
+	u32 pull_down_1v8_timeout;
+	u32 pull_up_sdr104;
+	u32 pull_down_sdr104;
+	u32 pull_up_hs400;
+	u32 pull_down_hs400;
+};
+
 struct sdhci_tegra {
 	const struct sdhci_tegra_soc_data *soc_data;
 	struct gpio_desc *power_gpio;
@@ -84,6 +101,8 @@ struct sdhci_tegra {
 	struct pinctrl *pinctrl_sdmmc;
 	struct pinctrl_state *pinctrl_state_3v3;
 	struct pinctrl_state *pinctrl_state_1v8;
+
+	struct sdhci_tegra_autocal_offsets autocal_offsets;
 };
 
 static u16 tegra_sdhci_readw(struct sdhci_host *host, int reg)
@@ -281,12 +300,45 @@ static bool tegra_sdhci_configure_card_clk(struct sdhci_host *host, bool enable)
 	return status;
 }
 
+static void tegra_sdhci_set_pad_autocal_offset(struct sdhci_host *host,
+					       u16 pdpu)
+{
+	u32 reg;
+
+	reg = sdhci_readl(host, SDHCI_TEGRA_AUTO_CAL_CONFIG);
+	reg &= ~SDHCI_AUTO_CAL_PDPU_OFFSET_MASK;
+	reg |= pdpu;
+	sdhci_writel(host, reg, SDHCI_TEGRA_AUTO_CAL_CONFIG);
+}
+
 static void tegra_sdhci_pad_autocalib(struct sdhci_host *host)
 {
+	struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
+	struct sdhci_tegra *tegra_host = sdhci_pltfm_priv(pltfm_host);
+	struct sdhci_tegra_autocal_offsets offsets =
+			tegra_host->autocal_offsets;
+	struct mmc_ios *ios = &host->mmc->ios;
 	bool card_clk_enabled;
+	u16 pdpu;
 	u32 reg;
 	int ret;
 
+	switch (ios->timing) {
+	case MMC_TIMING_UHS_SDR104:
+		pdpu = offsets.pull_down_sdr104 << 8 | offsets.pull_up_sdr104;
+		break;
+	case MMC_TIMING_MMC_HS400:
+		pdpu = offsets.pull_down_hs400 << 8 | offsets.pull_up_hs400;
+		break;
+	default:
+		if (ios->signal_voltage == MMC_SIGNAL_VOLTAGE_180)
+			pdpu = offsets.pull_down_1v8 << 8 | offsets.pull_up_1v8;
+		else
+			pdpu = offsets.pull_down_3v3 << 8 | offsets.pull_up_3v3;
+	}
+
+	tegra_sdhci_set_pad_autocal_offset(host, pdpu);
+
 	card_clk_enabled = tegra_sdhci_configure_card_clk(host, false);
 
 	tegra_sdhci_configure_cal_pad(host, true);
@@ -305,8 +357,104 @@ static void tegra_sdhci_pad_autocalib(struct sdhci_host *host)
 
 	tegra_sdhci_configure_card_clk(host, card_clk_enabled);
 
-	if (ret)
+	if (ret) {
 		dev_err(mmc_dev(host->mmc), "Pad autocal timed out\n");
+
+		if (ios->signal_voltage == MMC_SIGNAL_VOLTAGE_180)
+			pdpu = offsets.pull_down_1v8_timeout << 8 |
+			       offsets.pull_up_1v8_timeout;
+		else
+			pdpu = offsets.pull_down_3v3_timeout << 8 |
+			       offsets.pull_up_3v3_timeout;
+
+		/* Disable automatic calibration and use fixed offsets */
+		reg = sdhci_readl(host, SDHCI_TEGRA_AUTO_CAL_CONFIG);
+		reg &= ~SDHCI_AUTO_CAL_ENABLE;
+		sdhci_writel(host, reg, SDHCI_TEGRA_AUTO_CAL_CONFIG);
+
+		tegra_sdhci_set_pad_autocal_offset(host, pdpu);
+	}
+}
+
+static void tegra_sdhci_parse_pad_autocal_dt(struct sdhci_host *host)
+{
+	struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
+	struct sdhci_tegra *tegra_host = sdhci_pltfm_priv(pltfm_host);
+	struct sdhci_tegra_autocal_offsets *autocal =
+			&tegra_host->autocal_offsets;
+	int err;
+
+	err = device_property_read_u32(host->mmc->parent,
+			"nvidia,pad-autocal-pull-up-offset-3v3",
+			&autocal->pull_up_3v3);
+	if (err)
+		autocal->pull_up_3v3 = 0;
+
+	err = device_property_read_u32(host->mmc->parent,
+			"nvidia,pad-autocal-pull-down-offset-3v3",
+			&autocal->pull_down_3v3);
+	if (err)
+		autocal->pull_down_3v3 = 0;
+
+	err = device_property_read_u32(host->mmc->parent,
+			"nvidia,pad-autocal-pull-up-offset-1v8",
+			&autocal->pull_up_1v8);
+	if (err)
+		autocal->pull_up_1v8 = 0;
+
+	err = device_property_read_u32(host->mmc->parent,
+			"nvidia,pad-autocal-pull-down-offset-1v8",
+			&autocal->pull_down_1v8);
+	if (err)
+		autocal->pull_down_1v8 = 0;
+
+	err = device_property_read_u32(host->mmc->parent,
+			"nvidia,pad-autocal-pull-up-offset-3v3-timeout",
+			&autocal->pull_up_3v3);
+	if (err)
+		autocal->pull_up_3v3_timeout = 0;
+
+	err = device_property_read_u32(host->mmc->parent,
+			"nvidia,pad-autocal-pull-down-offset-3v3-timeout",
+			&autocal->pull_down_3v3);
+	if (err)
+		autocal->pull_down_3v3_timeout = 0;
+
+	err = device_property_read_u32(host->mmc->parent,
+			"nvidia,pad-autocal-pull-up-offset-1v8-timeout",
+			&autocal->pull_up_1v8);
+	if (err)
+		autocal->pull_up_1v8_timeout = 0;
+
+	err = device_property_read_u32(host->mmc->parent,
+			"nvidia,pad-autocal-pull-down-offset-1v8-timeout",
+			&autocal->pull_down_1v8);
+	if (err)
+		autocal->pull_down_1v8_timeout = 0;
+
+	err = device_property_read_u32(host->mmc->parent,
+			"nvidia,pad-autocal-pull-up-offset-sdr104",
+			&autocal->pull_up_sdr104);
+	if (err)
+		autocal->pull_up_sdr104 = autocal->pull_up_1v8;
+
+	err = device_property_read_u32(host->mmc->parent,
+			"nvidia,pad-autocal-pull-down-offset-sdr104",
+			&autocal->pull_down_sdr104);
+	if (err)
+		autocal->pull_down_sdr104 = autocal->pull_down_1v8;
+
+	err = device_property_read_u32(host->mmc->parent,
+			"nvidia,pad-autocal-pull-up-offset-hs400",
+			&autocal->pull_up_hs400);
+	if (err)
+		autocal->pull_up_hs400 = autocal->pull_up_1v8;
+
+	err = device_property_read_u32(host->mmc->parent,
+			"nvidia,pad-autocal-pull-down-offset-hs400",
+			&autocal->pull_down_hs400);
+	if (err)
+		autocal->pull_down_hs400 = autocal->pull_down_1v8;
 }
 
 static void tegra_sdhci_set_clock(struct sdhci_host *host, unsigned int clock)
@@ -683,6 +831,8 @@ static int sdhci_tegra_probe(struct platform_device *pdev)
 	if (tegra_host->soc_data->nvquirks & NVQUIRK_ENABLE_DDR50)
 		host->mmc->caps |= MMC_CAP_1_8V_DDR;
 
+	tegra_sdhci_parse_pad_autocal_dt(host);
+
 	tegra_host->power_gpio = devm_gpiod_get_optional(&pdev->dev, "power",
 							 GPIOD_OUT_HIGH);
 	if (IS_ERR(tegra_host->power_gpio)) {
-- 
2.7.4


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

* [PATCH v2 18/40] mmc: tegra: Perform pad calibration after voltage switch
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (16 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 17/40] mmc: tegra: Program pad autocal offsets from dt Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 19/40] mmc: tegra: Enable pad calibration on Tegra210 and Tegra186 Aapo Vienamo
                   ` (24 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Run the automatic pad calibration after voltage switching if
tegra_host->pad_calib_required is set.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/mmc/host/sdhci-tegra.c | 5 +++++
 1 file changed, 5 insertions(+)

diff --git a/drivers/mmc/host/sdhci-tegra.c b/drivers/mmc/host/sdhci-tegra.c
index eff1c82..d7f3480 100644
--- a/drivers/mmc/host/sdhci-tegra.c
+++ b/drivers/mmc/host/sdhci-tegra.c
@@ -572,6 +572,8 @@ static int sdhci_tegra_start_signal_voltage_switch(struct mmc_host *mmc,
 						   struct mmc_ios *ios)
 {
 	struct sdhci_host *host = mmc_priv(mmc);
+	struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
+	struct sdhci_tegra *tegra_host = sdhci_pltfm_priv(pltfm_host);
 	int ret = 0;
 
 	if (ios->signal_voltage == MMC_SIGNAL_VOLTAGE_330) {
@@ -586,6 +588,9 @@ static int sdhci_tegra_start_signal_voltage_switch(struct mmc_host *mmc,
 		ret = tegra_sdhci_set_padctrl(host, ios->signal_voltage);
 	}
 
+	if (tegra_host->pad_calib_required)
+		tegra_sdhci_pad_autocalib(host);
+
 	return ret;
 }
 
-- 
2.7.4


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

* [PATCH v2 19/40] mmc: tegra: Enable pad calibration on Tegra210 and Tegra186
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (17 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 18/40] mmc: tegra: Perform pad calibration after voltage switch Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 20/40] mmc: tegra: Add a workaround for tap value change glitch Aapo Vienamo
                   ` (23 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Set NVQUIRK_HAS_PADCALIB on Tegra210 and Tegra186 to enable automatic
pad drive strength calibration.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/mmc/host/sdhci-tegra.c | 6 ++++--
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/drivers/mmc/host/sdhci-tegra.c b/drivers/mmc/host/sdhci-tegra.c
index d7f3480..955c317 100644
--- a/drivers/mmc/host/sdhci-tegra.c
+++ b/drivers/mmc/host/sdhci-tegra.c
@@ -758,7 +758,8 @@ static const struct sdhci_pltfm_data sdhci_tegra210_pdata = {
 
 static const struct sdhci_tegra_soc_data soc_data_tegra210 = {
 	.pdata = &sdhci_tegra210_pdata,
-	.nvquirks = NVQUIRK_NEEDS_PAD_CONTROL,
+	.nvquirks = NVQUIRK_NEEDS_PAD_CONTROL |
+		    NVQUIRK_HAS_PADCALIB,
 };
 
 static const struct sdhci_pltfm_data sdhci_tegra186_pdata = {
@@ -782,7 +783,8 @@ static const struct sdhci_pltfm_data sdhci_tegra186_pdata = {
 
 static const struct sdhci_tegra_soc_data soc_data_tegra186 = {
 	.pdata = &sdhci_tegra186_pdata,
-	.nvquirks = NVQUIRK_NEEDS_PAD_CONTROL,
+	.nvquirks = NVQUIRK_NEEDS_PAD_CONTROL |
+		    NVQUIRK_HAS_PADCALIB,
 };
 
 static const struct of_device_id sdhci_tegra_dt_match[] = {
-- 
2.7.4


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

* [PATCH v2 20/40] mmc: tegra: Add a workaround for tap value change glitch
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (18 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 19/40] mmc: tegra: Enable pad calibration on Tegra210 and Tegra186 Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 21/40] mmc: tegra: Parse default trim and tap from dt Aapo Vienamo
                   ` (22 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Add quirk to disable the card clock during configuration of the tap
value in tegra_sdhci_set_tap() and issue sdhci_reset() after value
change. This is a workaround to avoid propagation of a potential
glitch caused by setting the tap value.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/mmc/host/sdhci-tegra.c | 30 ++++++++++++++++++++++++++++--
 1 file changed, 28 insertions(+), 2 deletions(-)

diff --git a/drivers/mmc/host/sdhci-tegra.c b/drivers/mmc/host/sdhci-tegra.c
index 955c317..e82fb92 100644
--- a/drivers/mmc/host/sdhci-tegra.c
+++ b/drivers/mmc/host/sdhci-tegra.c
@@ -47,6 +47,9 @@
 #define SDHCI_MISC_CTRL_ENABLE_SDHCI_SPEC_300		0x20
 #define SDHCI_MISC_CTRL_ENABLE_DDR50			0x200
 
+#define SDHCI_VNDR_TUN_CTRL0_0				0x1c0
+#define SDHCI_VNDR_TUN_CTRL0_TUN_HW_TAP			0x20000
+
 #define SDHCI_TEGRA_AUTO_CAL_CONFIG			0x1e4
 #define SDHCI_AUTO_CAL_START				BIT(31)
 #define SDHCI_AUTO_CAL_ENABLE				BIT(29)
@@ -68,6 +71,7 @@
 #define NVQUIRK_ENABLE_DDR50				BIT(5)
 #define NVQUIRK_HAS_PADCALIB				BIT(6)
 #define NVQUIRK_NEEDS_PAD_CONTROL			BIT(7)
+#define NVQUIRK_DIS_CARD_CLK_CONFIG_TAP			BIT(8)
 
 struct sdhci_tegra_soc_data {
 	const struct sdhci_pltfm_data *pdata;
@@ -500,12 +504,32 @@ static unsigned int tegra_sdhci_get_max_clock(struct sdhci_host *host)
 
 static void tegra_sdhci_set_tap(struct sdhci_host *host, unsigned int tap)
 {
+	struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
+	struct sdhci_tegra *tegra_host = sdhci_pltfm_priv(pltfm_host);
+	const struct sdhci_tegra_soc_data *soc_data = tegra_host->soc_data;
+	bool card_clk_enabled = false;
 	u32 reg;
 
+	/*
+	 * Touching the tap values is a bit tricky on some SoC generations.
+	 * The quirk enables a workaround for a glitch that sometimes occurs if
+	 * the tap values are changed.
+	 */
+
+	if (soc_data->nvquirks & NVQUIRK_DIS_CARD_CLK_CONFIG_TAP)
+		card_clk_enabled = tegra_sdhci_configure_card_clk(host, false);
+
 	reg = sdhci_readl(host, SDHCI_TEGRA_VENDOR_CLOCK_CTRL);
 	reg &= ~SDHCI_CLOCK_CTRL_TAP_MASK;
 	reg |= tap << SDHCI_CLOCK_CTRL_TAP_SHIFT;
 	sdhci_writel(host, reg, SDHCI_TEGRA_VENDOR_CLOCK_CTRL);
+
+	if (soc_data->nvquirks & NVQUIRK_DIS_CARD_CLK_CONFIG_TAP &&
+	    card_clk_enabled) {
+		usleep_range(1, 2);
+		sdhci_reset(host, SDHCI_RESET_CMD | SDHCI_RESET_DATA);
+		tegra_sdhci_configure_card_clk(host, card_clk_enabled);
+	}
 }
 
 static int tegra_sdhci_execute_tuning(struct sdhci_host *host, u32 opcode)
@@ -759,7 +783,8 @@ static const struct sdhci_pltfm_data sdhci_tegra210_pdata = {
 static const struct sdhci_tegra_soc_data soc_data_tegra210 = {
 	.pdata = &sdhci_tegra210_pdata,
 	.nvquirks = NVQUIRK_NEEDS_PAD_CONTROL |
-		    NVQUIRK_HAS_PADCALIB,
+		    NVQUIRK_HAS_PADCALIB |
+		    NVQUIRK_DIS_CARD_CLK_CONFIG_TAP,
 };
 
 static const struct sdhci_pltfm_data sdhci_tegra186_pdata = {
@@ -784,7 +809,8 @@ static const struct sdhci_pltfm_data sdhci_tegra186_pdata = {
 static const struct sdhci_tegra_soc_data soc_data_tegra186 = {
 	.pdata = &sdhci_tegra186_pdata,
 	.nvquirks = NVQUIRK_NEEDS_PAD_CONTROL |
-		    NVQUIRK_HAS_PADCALIB,
+		    NVQUIRK_HAS_PADCALIB |
+		    NVQUIRK_DIS_CARD_CLK_CONFIG_TAP,
 };
 
 static const struct of_device_id sdhci_tegra_dt_match[] = {
-- 
2.7.4


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

* [PATCH v2 21/40] mmc: tegra: Parse default trim and tap from dt
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (19 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 20/40] mmc: tegra: Add a workaround for tap value change glitch Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 22/40] mmc: tegra: Configure default tap values Aapo Vienamo
                   ` (21 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Parse the default inbound and outbound sampling trimmer values from
the device tree.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/mmc/host/sdhci-tegra.c | 22 ++++++++++++++++++++++
 1 file changed, 22 insertions(+)

diff --git a/drivers/mmc/host/sdhci-tegra.c b/drivers/mmc/host/sdhci-tegra.c
index e82fb92..0c39c54 100644
--- a/drivers/mmc/host/sdhci-tegra.c
+++ b/drivers/mmc/host/sdhci-tegra.c
@@ -107,6 +107,9 @@ struct sdhci_tegra {
 	struct pinctrl_state *pinctrl_state_1v8;
 
 	struct sdhci_tegra_autocal_offsets autocal_offsets;
+
+	u32 default_tap;
+	u32 default_trim;
 };
 
 static u16 tegra_sdhci_readw(struct sdhci_host *host, int reg)
@@ -461,6 +464,23 @@ static void tegra_sdhci_parse_pad_autocal_dt(struct sdhci_host *host)
 		autocal->pull_down_hs400 = autocal->pull_down_1v8;
 }
 
+static void tegra_sdhci_parse_default_tap_and_trim(struct sdhci_host *host)
+{
+	struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
+	struct sdhci_tegra *tegra_host = sdhci_pltfm_priv(pltfm_host);
+	int err;
+
+	err = device_property_read_u32(host->mmc->parent, "nvidia,default-tap",
+				       &tegra_host->default_tap);
+	if (err)
+		tegra_host->default_tap = 0;
+
+	err = device_property_read_u32(host->mmc->parent, "nvidia,default-trim",
+				       &tegra_host->default_trim);
+	if (err)
+		tegra_host->default_trim = 0;
+}
+
 static void tegra_sdhci_set_clock(struct sdhci_host *host, unsigned int clock)
 {
 	struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
@@ -866,6 +886,8 @@ static int sdhci_tegra_probe(struct platform_device *pdev)
 
 	tegra_sdhci_parse_pad_autocal_dt(host);
 
+	tegra_sdhci_parse_default_tap_and_trim(host);
+
 	tegra_host->power_gpio = devm_gpiod_get_optional(&pdev->dev, "power",
 							 GPIOD_OUT_HIGH);
 	if (IS_ERR(tegra_host->power_gpio)) {
-- 
2.7.4


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

* [PATCH v2 22/40] mmc: tegra: Configure default tap values
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (20 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 21/40] mmc: tegra: Parse default trim and tap from dt Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 23/40] mmc: tegra: Configure default trim value on reset Aapo Vienamo
                   ` (20 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Set the default inbound timing adjustment tap value on reset and on
non-tunable modes.

The default tap value is not programmed on tunable modes because the
tuning sequence is used instead to determine the tap value.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/mmc/host/sdhci-tegra.c | 132 ++++++++++++++++++++++++-----------------
 1 file changed, 77 insertions(+), 55 deletions(-)

diff --git a/drivers/mmc/host/sdhci-tegra.c b/drivers/mmc/host/sdhci-tegra.c
index 0c39c54..208a269 100644
--- a/drivers/mmc/host/sdhci-tegra.c
+++ b/drivers/mmc/host/sdhci-tegra.c
@@ -213,6 +213,58 @@ static bool tegra_sdhci_is_pad_and_regulator_valid(struct sdhci_host *host)
 	return true;
 }
 
+static bool tegra_sdhci_configure_card_clk(struct sdhci_host *host, bool enable)
+{
+	bool status;
+	u32 reg;
+
+	reg = sdhci_readw(host, SDHCI_CLOCK_CONTROL);
+	status = !!(reg & SDHCI_CLOCK_CARD_EN);
+
+	if (status == enable)
+		return status;
+
+	if (enable)
+		reg |= SDHCI_CLOCK_CARD_EN;
+	else
+		reg &= ~SDHCI_CLOCK_CARD_EN;
+
+	sdhci_writew(host, reg, SDHCI_CLOCK_CONTROL);
+
+	return status;
+}
+
+
+static void tegra_sdhci_set_tap(struct sdhci_host *host, unsigned int tap)
+{
+	struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
+	struct sdhci_tegra *tegra_host = sdhci_pltfm_priv(pltfm_host);
+	const struct sdhci_tegra_soc_data *soc_data = tegra_host->soc_data;
+	bool card_clk_enabled = false;
+	u32 reg;
+
+	/*
+	 * Touching the tap values is a bit tricky on some SoC generations.
+	 * The quirk enables a workaround for a glitch that sometimes occurs if
+	 * the tap values are changed.
+	 */
+
+	if (soc_data->nvquirks & NVQUIRK_DIS_CARD_CLK_CONFIG_TAP)
+		card_clk_enabled = tegra_sdhci_configure_card_clk(host, false);
+
+	reg = sdhci_readl(host, SDHCI_TEGRA_VENDOR_CLOCK_CTRL);
+	reg &= ~SDHCI_CLOCK_CTRL_TAP_MASK;
+	reg |= tap << SDHCI_CLOCK_CTRL_TAP_SHIFT;
+	sdhci_writel(host, reg, SDHCI_TEGRA_VENDOR_CLOCK_CTRL);
+
+	if (soc_data->nvquirks & NVQUIRK_DIS_CARD_CLK_CONFIG_TAP &&
+	    card_clk_enabled) {
+		udelay(1);
+		sdhci_reset(host, SDHCI_RESET_CMD | SDHCI_RESET_DATA);
+		tegra_sdhci_configure_card_clk(host, card_clk_enabled);
+	}
+}
+
 static void tegra_sdhci_reset(struct sdhci_host *host, u8 mask)
 {
 	struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
@@ -225,6 +277,8 @@ static void tegra_sdhci_reset(struct sdhci_host *host, u8 mask)
 	if (!(mask & SDHCI_RESET_ALL))
 		return;
 
+	tegra_sdhci_set_tap(host, tegra_host->default_tap);
+
 	misc_ctrl = sdhci_readl(host, SDHCI_TEGRA_VENDOR_MISC_CTRL);
 	clk_ctrl = sdhci_readl(host, SDHCI_TEGRA_VENDOR_CLOCK_CTRL);
 
@@ -286,27 +340,6 @@ static void tegra_sdhci_configure_cal_pad(struct sdhci_host *host, bool enable)
 		usleep_range(1, 2);
 }
 
-static bool tegra_sdhci_configure_card_clk(struct sdhci_host *host, bool enable)
-{
-	bool status;
-	u32 reg;
-
-	reg = sdhci_readw(host, SDHCI_CLOCK_CONTROL);
-	status = !!(reg & SDHCI_CLOCK_CARD_EN);
-
-	if (status == enable)
-		return status;
-
-	if (enable)
-		reg |= SDHCI_CLOCK_CARD_EN;
-	else
-		reg &= ~SDHCI_CLOCK_CARD_EN;
-
-	sdhci_writew(host, reg, SDHCI_CLOCK_CONTROL);
-
-	return status;
-}
-
 static void tegra_sdhci_set_pad_autocal_offset(struct sdhci_host *host,
 					       u16 pdpu)
 {
@@ -502,19 +535,6 @@ static void tegra_sdhci_set_clock(struct sdhci_host *host, unsigned int clock)
 	}
 }
 
-static void tegra_sdhci_set_uhs_signaling(struct sdhci_host *host,
-					  unsigned timing)
-{
-	struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
-	struct sdhci_tegra *tegra_host = sdhci_pltfm_priv(pltfm_host);
-
-	if (timing == MMC_TIMING_UHS_DDR50 ||
-	    timing == MMC_TIMING_MMC_DDR52)
-		tegra_host->ddr_signaling = true;
-
-	sdhci_set_uhs_signaling(host, timing);
-}
-
 static unsigned int tegra_sdhci_get_max_clock(struct sdhci_host *host)
 {
 	struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
@@ -522,34 +542,36 @@ static unsigned int tegra_sdhci_get_max_clock(struct sdhci_host *host)
 	return clk_round_rate(pltfm_host->clk, UINT_MAX);
 }
 
-static void tegra_sdhci_set_tap(struct sdhci_host *host, unsigned int tap)
+static void tegra_sdhci_set_uhs_signaling(struct sdhci_host *host,
+					  unsigned timing)
 {
 	struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
 	struct sdhci_tegra *tegra_host = sdhci_pltfm_priv(pltfm_host);
-	const struct sdhci_tegra_soc_data *soc_data = tegra_host->soc_data;
-	bool card_clk_enabled = false;
-	u32 reg;
+	bool set_default_tap = false;
 
-	/*
-	 * Touching the tap values is a bit tricky on some SoC generations.
-	 * The quirk enables a workaround for a glitch that sometimes occurs if
-	 * the tap values are changed.
-	 */
+	switch (timing) {
+	case MMC_TIMING_UHS_SDR50:
+	case MMC_TIMING_UHS_SDR104:
+	case MMC_TIMING_MMC_HS200:
+	case MMC_TIMING_MMC_HS400:
+		/* Don't set default tap on tunable modes. */
+		break;
+	case MMC_TIMING_MMC_DDR52:
+	case MMC_TIMING_UHS_DDR50:
+		tegra_host->ddr_signaling = true;
+		set_default_tap = true;
+		break;
+	default:
+		set_default_tap = true;
+		break;
+	}
 
-	if (soc_data->nvquirks & NVQUIRK_DIS_CARD_CLK_CONFIG_TAP)
-		card_clk_enabled = tegra_sdhci_configure_card_clk(host, false);
+	sdhci_set_uhs_signaling(host, timing);
 
-	reg = sdhci_readl(host, SDHCI_TEGRA_VENDOR_CLOCK_CTRL);
-	reg &= ~SDHCI_CLOCK_CTRL_TAP_MASK;
-	reg |= tap << SDHCI_CLOCK_CTRL_TAP_SHIFT;
-	sdhci_writel(host, reg, SDHCI_TEGRA_VENDOR_CLOCK_CTRL);
+	tegra_sdhci_pad_autocalib(host);
 
-	if (soc_data->nvquirks & NVQUIRK_DIS_CARD_CLK_CONFIG_TAP &&
-	    card_clk_enabled) {
-		usleep_range(1, 2);
-		sdhci_reset(host, SDHCI_RESET_CMD | SDHCI_RESET_DATA);
-		tegra_sdhci_configure_card_clk(host, card_clk_enabled);
-	}
+	if (set_default_tap)
+		tegra_sdhci_set_tap(host, tegra_host->default_tap);
 }
 
 static int tegra_sdhci_execute_tuning(struct sdhci_host *host, u32 opcode)
-- 
2.7.4


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

* [PATCH v2 23/40] mmc: tegra: Configure default trim value on reset
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (21 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 22/40] mmc: tegra: Configure default tap values Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 24/40] mmc: tegra: Use standard SDHCI tuning on Tegra210 and Tegra186 Aapo Vienamo
                   ` (19 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Program the outbound sampling trim value in tegra_sdhci_reset(). Unlike
the outbound tap value this does not depend on the signaling mode and
needs to be only programmed once.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/mmc/host/sdhci-tegra.c | 7 ++++++-
 1 file changed, 6 insertions(+), 1 deletion(-)

diff --git a/drivers/mmc/host/sdhci-tegra.c b/drivers/mmc/host/sdhci-tegra.c
index 208a269..7f1b0b4 100644
--- a/drivers/mmc/host/sdhci-tegra.c
+++ b/drivers/mmc/host/sdhci-tegra.c
@@ -37,6 +37,8 @@
 #define SDHCI_TEGRA_VENDOR_CLOCK_CTRL			0x100
 #define SDHCI_CLOCK_CTRL_TAP_MASK			0x00ff0000
 #define SDHCI_CLOCK_CTRL_TAP_SHIFT			16
+#define SDHCI_CLOCK_CTRL_TRIM_MASK			0x1f000000
+#define SDHCI_CLOCK_CTRL_TRIM_SHIFT			24
 #define SDHCI_CLOCK_CTRL_SDR50_TUNING_OVERRIDE		BIT(5)
 #define SDHCI_CLOCK_CTRL_PADPIPE_CLKEN_OVERRIDE		BIT(3)
 #define SDHCI_CLOCK_CTRL_SPI_MODE_CLKEN_OVERRIDE	BIT(2)
@@ -287,7 +289,8 @@ static void tegra_sdhci_reset(struct sdhci_host *host, u8 mask)
 		       SDHCI_MISC_CTRL_ENABLE_DDR50 |
 		       SDHCI_MISC_CTRL_ENABLE_SDR104);
 
-	clk_ctrl &= ~SDHCI_CLOCK_CTRL_SPI_MODE_CLKEN_OVERRIDE;
+	clk_ctrl &= ~(SDHCI_CLOCK_CTRL_TRIM_MASK |
+		      SDHCI_CLOCK_CTRL_SPI_MODE_CLKEN_OVERRIDE);
 
 	if (tegra_sdhci_is_pad_and_regulator_valid(host)) {
 		/* Erratum: Enable SDHCI spec v3.00 support */
@@ -304,6 +307,8 @@ static void tegra_sdhci_reset(struct sdhci_host *host, u8 mask)
 			clk_ctrl |= SDHCI_CLOCK_CTRL_SDR50_TUNING_OVERRIDE;
 	}
 
+	clk_ctrl |= tegra_host->default_trim << SDHCI_CLOCK_CTRL_TRIM_SHIFT;
+
 	sdhci_writel(host, misc_ctrl, SDHCI_TEGRA_VENDOR_MISC_CTRL);
 	sdhci_writel(host, clk_ctrl, SDHCI_TEGRA_VENDOR_CLOCK_CTRL);
 
-- 
2.7.4


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

* [PATCH v2 24/40] mmc: tegra: Use standard SDHCI tuning on Tegra210 and Tegra186
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (22 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 23/40] mmc: tegra: Configure default trim value on reset Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 25/40] mmc: sdhci: Add a quirk to disable card clock during tuning Aapo Vienamo
                   ` (18 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Add a new sdhci_ops struct for Tegra210 and Tegra186 which doesn't
set the custom tuning callback used on previous SoC generations.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/mmc/host/sdhci-tegra.c | 17 +++++++++++++++--
 1 file changed, 15 insertions(+), 2 deletions(-)

diff --git a/drivers/mmc/host/sdhci-tegra.c b/drivers/mmc/host/sdhci-tegra.c
index 7f1b0b4..bac2034 100644
--- a/drivers/mmc/host/sdhci-tegra.c
+++ b/drivers/mmc/host/sdhci-tegra.c
@@ -816,6 +816,19 @@ static const struct sdhci_tegra_soc_data soc_data_tegra124 = {
 	.pdata = &sdhci_tegra124_pdata,
 };
 
+static const struct sdhci_ops tegra210_sdhci_ops = {
+	.get_ro     = tegra_sdhci_get_ro,
+	.read_w     = tegra_sdhci_readw,
+	.write_w    = tegra_sdhci_writew,
+	.write_l    = tegra_sdhci_writel,
+	.set_clock  = tegra_sdhci_set_clock,
+	.set_bus_width = sdhci_set_bus_width,
+	.reset      = tegra_sdhci_reset,
+	.set_uhs_signaling = tegra_sdhci_set_uhs_signaling,
+	.voltage_switch = tegra_sdhci_voltage_switch,
+	.get_max_clock = tegra_sdhci_get_max_clock,
+};
+
 static const struct sdhci_pltfm_data sdhci_tegra210_pdata = {
 	.quirks = SDHCI_QUIRK_BROKEN_TIMEOUT_VAL |
 		  SDHCI_QUIRK_DATA_TIMEOUT_USES_SDCLK |
@@ -824,7 +837,7 @@ static const struct sdhci_pltfm_data sdhci_tegra210_pdata = {
 		  SDHCI_QUIRK_BROKEN_ADMA_ZEROLEN_DESC |
 		  SDHCI_QUIRK_CAP_CLOCK_BASE_BROKEN,
 	.quirks2 = SDHCI_QUIRK2_PRESET_VALUE_BROKEN,
-	.ops  = &tegra114_sdhci_ops,
+	.ops  = &tegra210_sdhci_ops,
 };
 
 static const struct sdhci_tegra_soc_data soc_data_tegra210 = {
@@ -850,7 +863,7 @@ static const struct sdhci_pltfm_data sdhci_tegra186_pdata = {
 		    * But it is not supported as of now.
 		    */
 		   SDHCI_QUIRK2_BROKEN_64_BIT_DMA,
-	.ops  = &tegra114_sdhci_ops,
+	.ops  = &tegra210_sdhci_ops,
 };
 
 static const struct sdhci_tegra_soc_data soc_data_tegra186 = {
-- 
2.7.4


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

* [PATCH v2 25/40] mmc: sdhci: Add a quirk to disable card clock during tuning
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (23 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 24/40] mmc: tegra: Use standard SDHCI tuning on Tegra210 and Tegra186 Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-27 11:25   ` Adrian Hunter
  2018-08-10 18:08 ` [PATCH v2 26/40] mmc: tegra: Enable workaround for tuning transfer mode bug Aapo Vienamo
                   ` (17 subsequent siblings)
  42 siblings, 1 reply; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Add a quirk to disable card clock when the tuning command is sent.

This has to be done to prevent the SDHCI controller from hanging on
Tegra210. Without the quirk enabled there appears to be around 10%
chance that the tuning sequence will fail and time out due to the
controller locking up.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/mmc/host/sdhci.c | 15 +++++++++++++++
 drivers/mmc/host/sdhci.h |  2 ++
 2 files changed, 17 insertions(+)

diff --git a/drivers/mmc/host/sdhci.c b/drivers/mmc/host/sdhci.c
index 04dc443..166b16f 100644
--- a/drivers/mmc/host/sdhci.c
+++ b/drivers/mmc/host/sdhci.c
@@ -2175,6 +2175,7 @@ static void sdhci_send_tuning(struct sdhci_host *host, u32 opcode)
 	struct mmc_request mrq = {};
 	unsigned long flags;
 	u32 b = host->sdma_boundary;
+	u16 clk;
 
 	spin_lock_irqsave(&host->lock, flags);
 
@@ -2183,6 +2184,13 @@ static void sdhci_send_tuning(struct sdhci_host *host, u32 opcode)
 	cmd.mrq = &mrq;
 
 	mrq.cmd = &cmd;
+
+	if (host->quirks2 & SDHCI_QUIRK2_TUNE_DIS_CARD_CLK) {
+		clk = sdhci_readw(host, SDHCI_CLOCK_CONTROL);
+		clk &= ~SDHCI_CLOCK_CARD_EN;
+		sdhci_writew(host, clk, SDHCI_CLOCK_CONTROL);
+	}
+
 	/*
 	 * In response to CMD19, the card sends 64 bytes of tuning
 	 * block to the Host Controller. So we set the block size
@@ -2213,6 +2221,13 @@ static void sdhci_send_tuning(struct sdhci_host *host, u32 opcode)
 	mmiowb();
 	spin_unlock_irqrestore(&host->lock, flags);
 
+	if (host->quirks2 & SDHCI_QUIRK2_TUNE_DIS_CARD_CLK) {
+		udelay(1);
+		clk = sdhci_readw(host, SDHCI_CLOCK_CONTROL);
+		clk |= SDHCI_CLOCK_CARD_EN;
+		sdhci_writew(host, clk, SDHCI_CLOCK_CONTROL);
+	}
+
 	/* Wait for Buffer Read Ready interrupt */
 	wait_event_timeout(host->buf_ready_int, (host->tuning_done == 1),
 			   msecs_to_jiffies(50));
diff --git a/drivers/mmc/host/sdhci.h b/drivers/mmc/host/sdhci.h
index 0a99008..cc411b0 100644
--- a/drivers/mmc/host/sdhci.h
+++ b/drivers/mmc/host/sdhci.h
@@ -452,6 +452,8 @@ struct sdhci_host {
 #define SDHCI_QUIRK2_DISABLE_HW_TIMEOUT			(1<<17)
 /* Don't clear the SDHCI_TRANSFER_MODE register on tuning commands */
 #define SDHCI_QUIRK2_TUNE_SKIP_XFERMODE_REG_PROG	(1<<18)
+/* Disable card clock during tuning */
+#define SDHCI_QUIRK2_TUNE_DIS_CARD_CLK			(1<<19)
 
 	int irq;		/* Device IRQ */
 	void __iomem *ioaddr;	/* Mapped address */
-- 
2.7.4


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

* [PATCH v2 26/40] mmc: tegra: Enable workaround for tuning transfer mode bug
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (24 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 25/40] mmc: sdhci: Add a quirk to disable card clock during tuning Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 27/40] mmc: tegra: Set SDHCI_QUIRK2_TUNE_DIS_CARD_CLK on Tegra210 Aapo Vienamo
                   ` (16 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Set SDHCI_QUIRK2_TUNE_SKIP_XFERMODE_REG_PROG on Tegra210 and Tegra186.
This prevents the controller from hanging during tuning. This bug does
not seem to be documented but it's handled in a similar way in the
downstream kernel.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/mmc/host/sdhci-tegra.c | 6 ++++--
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/drivers/mmc/host/sdhci-tegra.c b/drivers/mmc/host/sdhci-tegra.c
index bac2034..3a53593 100644
--- a/drivers/mmc/host/sdhci-tegra.c
+++ b/drivers/mmc/host/sdhci-tegra.c
@@ -836,7 +836,8 @@ static const struct sdhci_pltfm_data sdhci_tegra210_pdata = {
 		  SDHCI_QUIRK_NO_HISPD_BIT |
 		  SDHCI_QUIRK_BROKEN_ADMA_ZEROLEN_DESC |
 		  SDHCI_QUIRK_CAP_CLOCK_BASE_BROKEN,
-	.quirks2 = SDHCI_QUIRK2_PRESET_VALUE_BROKEN,
+	.quirks2 = SDHCI_QUIRK2_PRESET_VALUE_BROKEN |
+		   SDHCI_QUIRK2_TUNE_SKIP_XFERMODE_REG_PROG,
 	.ops  = &tegra210_sdhci_ops,
 };
 
@@ -862,7 +863,8 @@ static const struct sdhci_pltfm_data sdhci_tegra186_pdata = {
 		    * to 32-bit dma mask. Ideally 40-bit dma mask would work,
 		    * But it is not supported as of now.
 		    */
-		   SDHCI_QUIRK2_BROKEN_64_BIT_DMA,
+		   SDHCI_QUIRK2_BROKEN_64_BIT_DMA |
+		   SDHCI_QUIRK2_TUNE_SKIP_XFERMODE_REG_PROG,
 	.ops  = &tegra210_sdhci_ops,
 };
 
-- 
2.7.4


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

* [PATCH v2 27/40] mmc: tegra: Set SDHCI_QUIRK2_TUNE_DIS_CARD_CLK on Tegra210
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (25 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 26/40] mmc: tegra: Enable workaround for tuning transfer mode bug Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 28/40] mmc: tegra: Enable UHS and HS200 modes for Tegra210 Aapo Vienamo
                   ` (15 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

This prevents a possible hardware hang during tuning.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/mmc/host/sdhci-tegra.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/drivers/mmc/host/sdhci-tegra.c b/drivers/mmc/host/sdhci-tegra.c
index 3a53593..0959102 100644
--- a/drivers/mmc/host/sdhci-tegra.c
+++ b/drivers/mmc/host/sdhci-tegra.c
@@ -837,7 +837,8 @@ static const struct sdhci_pltfm_data sdhci_tegra210_pdata = {
 		  SDHCI_QUIRK_BROKEN_ADMA_ZEROLEN_DESC |
 		  SDHCI_QUIRK_CAP_CLOCK_BASE_BROKEN,
 	.quirks2 = SDHCI_QUIRK2_PRESET_VALUE_BROKEN |
-		   SDHCI_QUIRK2_TUNE_SKIP_XFERMODE_REG_PROG,
+		   SDHCI_QUIRK2_TUNE_SKIP_XFERMODE_REG_PROG |
+		   SDHCI_QUIRK2_TUNE_DIS_CARD_CLK,
 	.ops  = &tegra210_sdhci_ops,
 };
 
-- 
2.7.4


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

* [PATCH v2 28/40] mmc: tegra: Enable UHS and HS200 modes for Tegra210
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (26 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 27/40] mmc: tegra: Set SDHCI_QUIRK2_TUNE_DIS_CARD_CLK on Tegra210 Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 29/40] mmc: tegra: Enable UHS and HS200 modes for Tegra186 Aapo Vienamo
                   ` (14 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Set nvquirks to enable higher speed modes.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/mmc/host/sdhci-tegra.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/drivers/mmc/host/sdhci-tegra.c b/drivers/mmc/host/sdhci-tegra.c
index 0959102..8cfa8f4 100644
--- a/drivers/mmc/host/sdhci-tegra.c
+++ b/drivers/mmc/host/sdhci-tegra.c
@@ -846,7 +846,9 @@ static const struct sdhci_tegra_soc_data soc_data_tegra210 = {
 	.pdata = &sdhci_tegra210_pdata,
 	.nvquirks = NVQUIRK_NEEDS_PAD_CONTROL |
 		    NVQUIRK_HAS_PADCALIB |
-		    NVQUIRK_DIS_CARD_CLK_CONFIG_TAP,
+		    NVQUIRK_DIS_CARD_CLK_CONFIG_TAP |
+		    NVQUIRK_ENABLE_SDR50 |
+		    NVQUIRK_ENABLE_SDR104,
 };
 
 static const struct sdhci_pltfm_data sdhci_tegra186_pdata = {
-- 
2.7.4


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

* [PATCH v2 29/40] mmc: tegra: Enable UHS and HS200 modes for Tegra186
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (27 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 28/40] mmc: tegra: Enable UHS and HS200 modes for Tegra210 Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 30/40] arm64: dts: Add Tegra210 sdmmc pinctrl voltage states Aapo Vienamo
                   ` (13 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Set nvquirks to enable higher speed modes.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 drivers/mmc/host/sdhci-tegra.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/drivers/mmc/host/sdhci-tegra.c b/drivers/mmc/host/sdhci-tegra.c
index 8cfa8f4..2d775ad 100644
--- a/drivers/mmc/host/sdhci-tegra.c
+++ b/drivers/mmc/host/sdhci-tegra.c
@@ -875,7 +875,9 @@ static const struct sdhci_tegra_soc_data soc_data_tegra186 = {
 	.pdata = &sdhci_tegra186_pdata,
 	.nvquirks = NVQUIRK_NEEDS_PAD_CONTROL |
 		    NVQUIRK_HAS_PADCALIB |
-		    NVQUIRK_DIS_CARD_CLK_CONFIG_TAP,
+		    NVQUIRK_DIS_CARD_CLK_CONFIG_TAP |
+		    NVQUIRK_ENABLE_SDR50 |
+		    NVQUIRK_ENABLE_SDR104,
 };
 
 static const struct of_device_id sdhci_tegra_dt_match[] = {
-- 
2.7.4


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

* [PATCH v2 30/40] arm64: dts: Add Tegra210 sdmmc pinctrl voltage states
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (28 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 29/40] mmc: tegra: Enable UHS and HS200 modes for Tegra186 Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 31/40] arm64: dts: Add Tegra186 " Aapo Vienamo
                   ` (12 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Add pad voltage configuration nodes for sdmmc pads with configurable
voltages on Tegra210.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
Reviewed-by: Mikko Perttunen <mperttunen@nvidia.com>
---
 arch/arm64/boot/dts/nvidia/tegra210.dtsi | 27 +++++++++++++++++++++++++++
 1 file changed, 27 insertions(+)

diff --git a/arch/arm64/boot/dts/nvidia/tegra210.dtsi b/arch/arm64/boot/dts/nvidia/tegra210.dtsi
index 3be920e..bc1918e 100644
--- a/arch/arm64/boot/dts/nvidia/tegra210.dtsi
+++ b/arch/arm64/boot/dts/nvidia/tegra210.dtsi
@@ -3,6 +3,7 @@
 #include <dt-bindings/gpio/tegra-gpio.h>
 #include <dt-bindings/memory/tegra210-mc.h>
 #include <dt-bindings/pinctrl/pinctrl-tegra.h>
+#include <dt-bindings/pinctrl/pinctrl-tegra-io-pad.h>
 #include <dt-bindings/interrupt-controller/arm-gic.h>
 #include <dt-bindings/thermal/tegra124-soctherm.h>
 
@@ -776,6 +777,26 @@
 				#power-domain-cells = <0>;
 			};
 		};
+
+		sdmmc1_3v3: sdmmc1-3v3 {
+			pins = "sdmmc1";
+			power-source = <TEGRA_IO_PAD_VOLTAGE_3V3>;
+		};
+
+		sdmmc1_1v8: sdmmc1-1v8 {
+			pins = "sdmmc1";
+			power-source = <TEGRA_IO_PAD_VOLTAGE_1V8>;
+		};
+
+		sdmmc3_3v3: sdmmc3-3v3 {
+			pins = "sdmmc3";
+			power-source = <TEGRA_IO_PAD_VOLTAGE_3V3>;
+		};
+
+		sdmmc3_1v8: sdmmc3-1v8 {
+			pins = "sdmmc3";
+			power-source = <TEGRA_IO_PAD_VOLTAGE_1V8>;
+		};
 	};
 
 	fuse@7000f800 {
@@ -1027,6 +1048,9 @@
 		clock-names = "sdhci";
 		resets = <&tegra_car 14>;
 		reset-names = "sdhci";
+		pinctrl-names = "sdmmc-3v3", "sdmmc-1v8";
+		pinctrl-0 = <&sdmmc1_3v3>;
+		pinctrl-1 = <&sdmmc1_1v8>;
 		status = "disabled";
 	};
 
@@ -1049,6 +1073,9 @@
 		clock-names = "sdhci";
 		resets = <&tegra_car 69>;
 		reset-names = "sdhci";
+		pinctrl-names = "sdmmc-3v3", "sdmmc-1v8";
+		pinctrl-0 = <&sdmmc3_3v3>;
+		pinctrl-1 = <&sdmmc3_1v8>;
 		status = "disabled";
 	};
 
-- 
2.7.4


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

* [PATCH v2 31/40] arm64: dts: Add Tegra186 sdmmc pinctrl voltage states
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (29 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 30/40] arm64: dts: Add Tegra210 sdmmc pinctrl voltage states Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 32/40] arm64: dts: tegra210-p2180: Allow ldo2 to go down to 1.8 V Aapo Vienamo
                   ` (11 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Add pad voltage configuration nodes for sdmmc pads with configurable
voltages on Tegra186.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
Reviewed-by: Mikko Perttunen <mperttunen@nvidia.com>
---
 arch/arm64/boot/dts/nvidia/tegra186.dtsi | 40 ++++++++++++++++++++++++++++++++
 1 file changed, 40 insertions(+)

diff --git a/arch/arm64/boot/dts/nvidia/tegra186.dtsi b/arch/arm64/boot/dts/nvidia/tegra186.dtsi
index b762227..7669756 100644
--- a/arch/arm64/boot/dts/nvidia/tegra186.dtsi
+++ b/arch/arm64/boot/dts/nvidia/tegra186.dtsi
@@ -4,6 +4,7 @@
 #include <dt-bindings/interrupt-controller/arm-gic.h>
 #include <dt-bindings/mailbox/tegra186-hsp.h>
 #include <dt-bindings/memory/tegra186-mc.h>
+#include <dt-bindings/pinctrl/pinctrl-tegra-io-pad.h>
 #include <dt-bindings/power/tegra186-powergate.h>
 #include <dt-bindings/reset/tegra186-reset.h>
 #include <dt-bindings/thermal/tegra186-bpmp-thermal.h>
@@ -236,6 +237,9 @@
 		clock-names = "sdhci";
 		resets = <&bpmp TEGRA186_RESET_SDMMC1>;
 		reset-names = "sdhci";
+		pinctrl-names = "sdmmc-3v3", "sdmmc-1v8";
+		pinctrl-0 = <&sdmmc1_3v3>;
+		pinctrl-1 = <&sdmmc1_1v8>;
 		status = "disabled";
 	};
 
@@ -247,6 +251,9 @@
 		clock-names = "sdhci";
 		resets = <&bpmp TEGRA186_RESET_SDMMC2>;
 		reset-names = "sdhci";
+		pinctrl-names = "sdmmc-3v3", "sdmmc-1v8";
+		pinctrl-0 = <&sdmmc2_3v3>;
+		pinctrl-1 = <&sdmmc2_1v8>;
 		status = "disabled";
 	};
 
@@ -258,6 +265,9 @@
 		clock-names = "sdhci";
 		resets = <&bpmp TEGRA186_RESET_SDMMC3>;
 		reset-names = "sdhci";
+		pinctrl-names = "sdmmc-3v3", "sdmmc-1v8";
+		pinctrl-0 = <&sdmmc3_3v3>;
+		pinctrl-1 = <&sdmmc3_1v8>;
 		status = "disabled";
 	};
 
@@ -368,6 +378,36 @@
 		      <0 0x0c380000 0 0x10000>,
 		      <0 0x0c390000 0 0x10000>;
 		reg-names = "pmc", "wake", "aotag", "scratch";
+
+		sdmmc1_3v3: sdmmc1-3v3 {
+			pins = "sdmmc1-hv";
+			power-source = <TEGRA_IO_PAD_VOLTAGE_3V3>;
+		};
+
+		sdmmc1_1v8: sdmmc1-1v8 {
+			pins = "sdmmc1-hv";
+			power-source = <TEGRA_IO_PAD_VOLTAGE_1V8>;
+		};
+
+		sdmmc2_3v3: sdmmc2-3v3 {
+			pins = "sdmmc2-hv";
+			power-source = <TEGRA_IO_PAD_VOLTAGE_3V3>;
+		};
+
+		sdmmc2_1v8: sdmmc2-1v8 {
+			pins = "sdmmc2-hv";
+			power-source = <TEGRA_IO_PAD_VOLTAGE_1V8>;
+		};
+
+		sdmmc3_3v3: sdmmc3-3v3 {
+			pins = "sdmmc3-hv";
+			power-source = <TEGRA_IO_PAD_VOLTAGE_3V3>;
+		};
+
+		sdmmc3_1v8: sdmmc3-1v8 {
+			pins = "sdmmc3-hv";
+			power-source = <TEGRA_IO_PAD_VOLTAGE_1V8>;
+		};
 	};
 
 	ccplex@e000000 {
-- 
2.7.4


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

* [PATCH v2 32/40] arm64: dts: tegra210-p2180: Allow ldo2 to go down to 1.8 V
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (30 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 31/40] arm64: dts: Add Tegra186 " Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 33/40] arm64: dts: tegra210-p2180: Correct sdmmc4 vqmmc-supply Aapo Vienamo
                   ` (10 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Set regulator-min-microvolt property of ldo2 to 1.8 V in
tegra210-p2180.dtsi. ldo2 is used by the sdmmc1 SDHCI controller and its
voltage needs to be adjusted down to 1.8 V to support faster signaling
modes. It appears that the comment about the SDHCI driver requesting
invalid voltages no longer applies.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
Reviewed-by: Mikko Perttunen <mperttunen@nvidia.com>
---
 arch/arm64/boot/dts/nvidia/tegra210-p2180.dtsi | 11 +----------
 1 file changed, 1 insertion(+), 10 deletions(-)

diff --git a/arch/arm64/boot/dts/nvidia/tegra210-p2180.dtsi b/arch/arm64/boot/dts/nvidia/tegra210-p2180.dtsi
index 212e663..8496101 100644
--- a/arch/arm64/boot/dts/nvidia/tegra210-p2180.dtsi
+++ b/arch/arm64/boot/dts/nvidia/tegra210-p2180.dtsi
@@ -178,16 +178,7 @@
 
 				vddio_sdmmc: ldo2 {
 					regulator-name = "VDDIO_SDMMC";
-					/*
-					 * Technically this supply should have
-					 * a supported range from 1.8 - 3.3 V.
-					 * However, that would cause the SDHCI
-					 * driver to request 2.7 V upon access
-					 * and that in turn will cause traffic
-					 * to be broken. Leave it at 3.3 V for
-					 * now.
-					 */
-					regulator-min-microvolt = <3300000>;
+					regulator-min-microvolt = <1800000>;
 					regulator-max-microvolt = <3300000>;
 					regulator-always-on;
 					regulator-boot-on;
-- 
2.7.4


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

* [PATCH v2 33/40] arm64: dts: tegra210-p2180: Correct sdmmc4 vqmmc-supply
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (31 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 32/40] arm64: dts: tegra210-p2180: Allow ldo2 to go down to 1.8 V Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 34/40] arm64: dts: tegra210-p2597: Remove no-1-8-v from sdmmc1 Aapo Vienamo
                   ` (9 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

On p2180 sdmmc4 is powered from a fixed 1.8 V regulator.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
Reviewed-by: Mikko Perttunen <mperttunen@nvidia.com>
---
 arch/arm64/boot/dts/nvidia/tegra210-p2180.dtsi | 1 +
 1 file changed, 1 insertion(+)

diff --git a/arch/arm64/boot/dts/nvidia/tegra210-p2180.dtsi b/arch/arm64/boot/dts/nvidia/tegra210-p2180.dtsi
index 8496101..053458a 100644
--- a/arch/arm64/boot/dts/nvidia/tegra210-p2180.dtsi
+++ b/arch/arm64/boot/dts/nvidia/tegra210-p2180.dtsi
@@ -273,6 +273,7 @@
 		status = "okay";
 		bus-width = <8>;
 		non-removable;
+		vqmmc-supply = <&vdd_1v8>;
 	};
 
 	clocks {
-- 
2.7.4


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

* [PATCH v2 34/40] arm64: dts: tegra210-p2597: Remove no-1-8-v from sdmmc1
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (32 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 33/40] arm64: dts: tegra210-p2180: Correct sdmmc4 vqmmc-supply Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 35/40] arm64: dts: tegra186: Add sdmmc pad auto calibration offsets Aapo Vienamo
                   ` (8 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Allow sdmmc1 to set the signaling voltage to 1.8 V in order to support
faster signaling modes.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 arch/arm64/boot/dts/nvidia/tegra210-p2597.dtsi | 1 -
 1 file changed, 1 deletion(-)

diff --git a/arch/arm64/boot/dts/nvidia/tegra210-p2597.dtsi b/arch/arm64/boot/dts/nvidia/tegra210-p2597.dtsi
index 9d5a0e6..365726d 100644
--- a/arch/arm64/boot/dts/nvidia/tegra210-p2597.dtsi
+++ b/arch/arm64/boot/dts/nvidia/tegra210-p2597.dtsi
@@ -1452,7 +1452,6 @@
 	sdhci@700b0000 {
 		status = "okay";
 		bus-width = <4>;
-		no-1-8-v;
 
 		cd-gpios = <&gpio TEGRA_GPIO(Z, 1) GPIO_ACTIVE_LOW>;
 
-- 
2.7.4


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

* [PATCH v2 35/40] arm64: dts: tegra186: Add sdmmc pad auto calibration offsets
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (33 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 34/40] arm64: dts: tegra210-p2597: Remove no-1-8-v from sdmmc1 Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 36/40] arm64: dts: tegra210: " Aapo Vienamo
                   ` (7 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Add the calibration offset properties used for automatic pad drive
strength calibration.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 arch/arm64/boot/dts/nvidia/tegra186.dtsi | 20 ++++++++++++++++++++
 1 file changed, 20 insertions(+)

diff --git a/arch/arm64/boot/dts/nvidia/tegra186.dtsi b/arch/arm64/boot/dts/nvidia/tegra186.dtsi
index 7669756..b7020dd 100644
--- a/arch/arm64/boot/dts/nvidia/tegra186.dtsi
+++ b/arch/arm64/boot/dts/nvidia/tegra186.dtsi
@@ -240,6 +240,12 @@
 		pinctrl-names = "sdmmc-3v3", "sdmmc-1v8";
 		pinctrl-0 = <&sdmmc1_3v3>;
 		pinctrl-1 = <&sdmmc1_1v8>;
+		nvidia,pad-autocal-pull-up-offset-3v3-timeout = <0x07>;
+		nvidia,pad-autocal-pull-down-offset-3v3-timeout = <0x06>;
+		nvidia,pad-autocal-pull-up-offset-1v8-timeout = <0x07>;
+		nvidia,pad-autocal-pull-down-offset-1v8-timeout = <0x07>;
+		nvidia,pad-autocal-pull-up-offset-sdr104 = <0x03>;
+		nvidia,pad-autocal-pull-down-offset-sdr104 = <0x05>;
 		status = "disabled";
 	};
 
@@ -254,6 +260,10 @@
 		pinctrl-names = "sdmmc-3v3", "sdmmc-1v8";
 		pinctrl-0 = <&sdmmc2_3v3>;
 		pinctrl-1 = <&sdmmc2_1v8>;
+		nvidia,pad-autocal-pull-up-offset-3v3-timeout = <0x07>;
+		nvidia,pad-autocal-pull-down-offset-3v3-timeout = <0x06>;
+		nvidia,pad-autocal-pull-up-offset-1v8-timeout = <0x07>;
+		nvidia,pad-autocal-pull-down-offset-1v8-timeout = <0x07>;
 		status = "disabled";
 	};
 
@@ -268,6 +278,12 @@
 		pinctrl-names = "sdmmc-3v3", "sdmmc-1v8";
 		pinctrl-0 = <&sdmmc3_3v3>;
 		pinctrl-1 = <&sdmmc3_1v8>;
+		nvidia,pad-autocal-pull-up-offset-1v8 = <0x00>;
+		nvidia,pad-autocal-pull-down-offset-1v8 = <0x7a>;
+		nvidia,pad-autocal-pull-up-offset-3v3-timeout = <0x07>;
+		nvidia,pad-autocal-pull-down-offset-3v3-timeout = <0x06>;
+		nvidia,pad-autocal-pull-up-offset-1v8-timeout = <0x07>;
+		nvidia,pad-autocal-pull-down-offset-1v8-timeout = <0x07>;
 		status = "disabled";
 	};
 
@@ -279,6 +295,10 @@
 		clock-names = "sdhci";
 		resets = <&bpmp TEGRA186_RESET_SDMMC4>;
 		reset-names = "sdhci";
+		nvidia,pad-autocal-pull-up-offset-hs400 = <0x05>;
+		nvidia,pad-autocal-pull-down-offset-hs400 = <0x05>;
+		nvidia,pad-autocal-pull-up-offset-1v8-timeout = <0x0a>;
+		nvidia,pad-autocal-pull-down-offset-1v8-timeout = <0x0a>;
 		status = "disabled";
 	};
 
-- 
2.7.4


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

* [PATCH v2 36/40] arm64: dts: tegra210: Add sdmmc pad auto calibration offsets
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (34 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 35/40] arm64: dts: tegra186: Add sdmmc pad auto calibration offsets Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 37/40] arm64: dts: tegra210: Add SDHCI tap and trim values Aapo Vienamo
                   ` (6 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Add the calibration offset properties used for automatic pad drive
strength calibration.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 arch/arm64/boot/dts/nvidia/tegra210.dtsi | 12 ++++++++++++
 1 file changed, 12 insertions(+)

diff --git a/arch/arm64/boot/dts/nvidia/tegra210.dtsi b/arch/arm64/boot/dts/nvidia/tegra210.dtsi
index bc1918e..2a80f2b 100644
--- a/arch/arm64/boot/dts/nvidia/tegra210.dtsi
+++ b/arch/arm64/boot/dts/nvidia/tegra210.dtsi
@@ -1051,6 +1051,10 @@
 		pinctrl-names = "sdmmc-3v3", "sdmmc-1v8";
 		pinctrl-0 = <&sdmmc1_3v3>;
 		pinctrl-1 = <&sdmmc1_1v8>;
+		nvidia,pad-autocal-pull-up-offset-3v3 = <0x00>;
+		nvidia,pad-autocal-pull-down-offset-3v3 = <0x7d>;
+		nvidia,pad-autocal-pull-up-offset-1v8 = <0x7b>;
+		nvidia,pad-autocal-pull-down-offset-1v8 = <0x7b>;
 		status = "disabled";
 	};
 
@@ -1062,6 +1066,8 @@
 		clock-names = "sdhci";
 		resets = <&tegra_car 9>;
 		reset-names = "sdhci";
+		nvidia,pad-autocal-pull-up-offset-1v8 = <0x05>;
+		nvidia,pad-autocal-pull-down-offset-1v8 = <0x05>;
 		status = "disabled";
 	};
 
@@ -1076,6 +1082,10 @@
 		pinctrl-names = "sdmmc-3v3", "sdmmc-1v8";
 		pinctrl-0 = <&sdmmc3_3v3>;
 		pinctrl-1 = <&sdmmc3_1v8>;
+		nvidia,pad-autocal-pull-up-offset-3v3 = <0x00>;
+		nvidia,pad-autocal-pull-down-offset-3v3 = <0x7d>;
+		nvidia,pad-autocal-pull-up-offset-1v8 = <0x7b>;
+		nvidia,pad-autocal-pull-down-offset-1v8 = <0x7b>;
 		status = "disabled";
 	};
 
@@ -1087,6 +1097,8 @@
 		clock-names = "sdhci";
 		resets = <&tegra_car 15>;
 		reset-names = "sdhci";
+		nvidia,pad-autocal-pull-up-offset-1v8 = <0x05>;
+		nvidia,pad-autocal-pull-down-offset-1v8 = <0x05>;
 		status = "disabled";
 	};
 
-- 
2.7.4


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

* [PATCH v2 37/40] arm64: dts: tegra210: Add SDHCI tap and trim values
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (35 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 36/40] arm64: dts: tegra210: " Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 38/40] arm64: dts: tegra186: " Aapo Vienamo
                   ` (5 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Add SDHCI inbound and outbound SDHCI sampling trimmer values for
Tegra210.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 arch/arm64/boot/dts/nvidia/tegra210.dtsi | 8 ++++++++
 1 file changed, 8 insertions(+)

diff --git a/arch/arm64/boot/dts/nvidia/tegra210.dtsi b/arch/arm64/boot/dts/nvidia/tegra210.dtsi
index 2a80f2b..0951acc 100644
--- a/arch/arm64/boot/dts/nvidia/tegra210.dtsi
+++ b/arch/arm64/boot/dts/nvidia/tegra210.dtsi
@@ -1055,6 +1055,8 @@
 		nvidia,pad-autocal-pull-down-offset-3v3 = <0x7d>;
 		nvidia,pad-autocal-pull-up-offset-1v8 = <0x7b>;
 		nvidia,pad-autocal-pull-down-offset-1v8 = <0x7b>;
+		nvidia,default-tap = <0x2>;
+		nvidia,default-trim = <0x4>;
 		status = "disabled";
 	};
 
@@ -1068,6 +1070,8 @@
 		reset-names = "sdhci";
 		nvidia,pad-autocal-pull-up-offset-1v8 = <0x05>;
 		nvidia,pad-autocal-pull-down-offset-1v8 = <0x05>;
+		nvidia,default-tap = <0x8>;
+		nvidia,default-trim = <0x0>;
 		status = "disabled";
 	};
 
@@ -1086,6 +1090,8 @@
 		nvidia,pad-autocal-pull-down-offset-3v3 = <0x7d>;
 		nvidia,pad-autocal-pull-up-offset-1v8 = <0x7b>;
 		nvidia,pad-autocal-pull-down-offset-1v8 = <0x7b>;
+		nvidia,default-tap = <0x3>;
+		nvidia,default-trim = <0x3>;
 		status = "disabled";
 	};
 
@@ -1099,6 +1105,8 @@
 		reset-names = "sdhci";
 		nvidia,pad-autocal-pull-up-offset-1v8 = <0x05>;
 		nvidia,pad-autocal-pull-down-offset-1v8 = <0x05>;
+		nvidia,default-tap = <0x8>;
+		nvidia,default-trim = <0x0>;
 		status = "disabled";
 	};
 
-- 
2.7.4


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

* [PATCH v2 38/40] arm64: dts: tegra186: Add SDHCI tap and trim values
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (36 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 37/40] arm64: dts: tegra210: Add SDHCI tap and trim values Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 39/40] arm64: dts: tegra186: Assign clocks for sdmmc1 and sdmmc4 Aapo Vienamo
                   ` (4 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Add SDHCI inbound and outbound SDHCI sampling trimmer values for
Tegra186.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 arch/arm64/boot/dts/nvidia/tegra186.dtsi | 8 ++++++++
 1 file changed, 8 insertions(+)

diff --git a/arch/arm64/boot/dts/nvidia/tegra186.dtsi b/arch/arm64/boot/dts/nvidia/tegra186.dtsi
index b7020dd..3b2fe0d 100644
--- a/arch/arm64/boot/dts/nvidia/tegra186.dtsi
+++ b/arch/arm64/boot/dts/nvidia/tegra186.dtsi
@@ -246,6 +246,8 @@
 		nvidia,pad-autocal-pull-down-offset-1v8-timeout = <0x07>;
 		nvidia,pad-autocal-pull-up-offset-sdr104 = <0x03>;
 		nvidia,pad-autocal-pull-down-offset-sdr104 = <0x05>;
+		nvidia,default-tap = <0x5>;
+		nvidia,default-trim = <0xb>;
 		status = "disabled";
 	};
 
@@ -264,6 +266,8 @@
 		nvidia,pad-autocal-pull-down-offset-3v3-timeout = <0x06>;
 		nvidia,pad-autocal-pull-up-offset-1v8-timeout = <0x07>;
 		nvidia,pad-autocal-pull-down-offset-1v8-timeout = <0x07>;
+		nvidia,default-tap = <0x5>;
+		nvidia,default-trim = <0xb>;
 		status = "disabled";
 	};
 
@@ -284,6 +288,8 @@
 		nvidia,pad-autocal-pull-down-offset-3v3-timeout = <0x06>;
 		nvidia,pad-autocal-pull-up-offset-1v8-timeout = <0x07>;
 		nvidia,pad-autocal-pull-down-offset-1v8-timeout = <0x07>;
+		nvidia,default-tap = <0x5>;
+		nvidia,default-trim = <0xb>;
 		status = "disabled";
 	};
 
@@ -299,6 +305,8 @@
 		nvidia,pad-autocal-pull-down-offset-hs400 = <0x05>;
 		nvidia,pad-autocal-pull-up-offset-1v8-timeout = <0x0a>;
 		nvidia,pad-autocal-pull-down-offset-1v8-timeout = <0x0a>;
+		nvidia,default-tap = <0x5>;
+		nvidia,default-trim = <0x9>;
 		status = "disabled";
 	};
 
-- 
2.7.4


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

* [PATCH v2 39/40] arm64: dts: tegra186: Assign clocks for sdmmc1 and sdmmc4
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (37 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 38/40] arm64: dts: tegra186: " Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-10 18:08 ` [PATCH v2 40/40] arm64: dts: tegra210: " Aapo Vienamo
                   ` (3 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Configure sdmmc4 parent clock to pllc4 and sdmmc1 to pllp_out0 by
setting the assigned-clocks device tree properties. pllc4 offer
better jitter performance and should be used with higher speed
modes like HS200 and HS400.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 arch/arm64/boot/dts/nvidia/tegra186.dtsi | 6 ++++++
 1 file changed, 6 insertions(+)

diff --git a/arch/arm64/boot/dts/nvidia/tegra186.dtsi b/arch/arm64/boot/dts/nvidia/tegra186.dtsi
index 3b2fe0d..6e9ef26 100644
--- a/arch/arm64/boot/dts/nvidia/tegra186.dtsi
+++ b/arch/arm64/boot/dts/nvidia/tegra186.dtsi
@@ -248,6 +248,9 @@
 		nvidia,pad-autocal-pull-down-offset-sdr104 = <0x05>;
 		nvidia,default-tap = <0x5>;
 		nvidia,default-trim = <0xb>;
+		assigned-clocks = <&bpmp TEGRA186_CLK_SDMMC1>,
+				  <&bpmp TEGRA186_CLK_PLLP_OUT0>;
+		assigned-clock-parents = <&bpmp TEGRA186_CLK_PLLP_OUT0>;
 		status = "disabled";
 	};
 
@@ -299,6 +302,9 @@
 		interrupts = <GIC_SPI 65 IRQ_TYPE_LEVEL_HIGH>;
 		clocks = <&bpmp TEGRA186_CLK_SDMMC4>;
 		clock-names = "sdhci";
+		assigned-clocks = <&bpmp TEGRA186_CLK_SDMMC4>,
+				  <&bpmp TEGRA186_CLK_PLLC4_VCO>;
+		assigned-clock-parents = <&bpmp TEGRA186_CLK_PLLC4_VCO>;
 		resets = <&bpmp TEGRA186_RESET_SDMMC4>;
 		reset-names = "sdhci";
 		nvidia,pad-autocal-pull-up-offset-hs400 = <0x05>;
-- 
2.7.4


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

* [PATCH v2 40/40] arm64: dts: tegra210: Assign clocks for sdmmc1 and sdmmc4
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (38 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 39/40] arm64: dts: tegra186: Assign clocks for sdmmc1 and sdmmc4 Aapo Vienamo
@ 2018-08-10 18:08 ` Aapo Vienamo
  2018-08-23  8:47 ` [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Thierry Reding
                   ` (2 subsequent siblings)
  42 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-10 18:08 UTC (permalink / raw)
  To: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Adrian Hunter, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc, Aapo Vienamo

Use assigned-clock properties to configure pllc4 as the parent clock
for sdmmc4 on Tegra210. pllc4 offers better jitter perfomance than
the default pllp and is required by HS200 and HS400 modes.

Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
---
 arch/arm64/boot/dts/nvidia/tegra210.dtsi | 8 ++++++++
 1 file changed, 8 insertions(+)

diff --git a/arch/arm64/boot/dts/nvidia/tegra210.dtsi b/arch/arm64/boot/dts/nvidia/tegra210.dtsi
index 0951acc..14da98a 100644
--- a/arch/arm64/boot/dts/nvidia/tegra210.dtsi
+++ b/arch/arm64/boot/dts/nvidia/tegra210.dtsi
@@ -1057,6 +1057,11 @@
 		nvidia,pad-autocal-pull-down-offset-1v8 = <0x7b>;
 		nvidia,default-tap = <0x2>;
 		nvidia,default-trim = <0x4>;
+		assigned-clocks = <&tegra_car TEGRA210_CLK_SDMMC4>,
+				  <&tegra_car TEGRA210_CLK_PLL_C4_OUT0>,
+				  <&tegra_car TEGRA210_CLK_PLL_C4>;
+		assigned-clock-parents = <&tegra_car TEGRA210_CLK_PLL_C4_OUT0>;
+		assigned-clock-rates = <200000000>, <1000000000>, <1000000000>;
 		status = "disabled";
 	};
 
@@ -1107,6 +1112,9 @@
 		nvidia,pad-autocal-pull-down-offset-1v8 = <0x05>;
 		nvidia,default-tap = <0x8>;
 		nvidia,default-trim = <0x0>;
+		assigned-clocks = <&tegra_car TEGRA210_CLK_SDMMC4>,
+				  <&tegra_car TEGRA210_CLK_PLL_C4_OUT0>;
+		assigned-clock-parents = <&tegra_car TEGRA210_CLK_PLL_C4_OUT0>;
 		status = "disabled";
 	};
 
-- 
2.7.4


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

* Re: [PATCH v2 03/40] dt-bindings: Add Tegra SDHCI pad pdpu offset bindings
  2018-08-10 18:08 ` [PATCH v2 03/40] dt-bindings: Add Tegra SDHCI pad pdpu offset bindings Aapo Vienamo
@ 2018-08-13 19:24   ` Rob Herring
  0 siblings, 0 replies; 57+ messages in thread
From: Rob Herring @ 2018-08-13 19:24 UTC (permalink / raw)
  To: Aapo Vienamo
  Cc: Mark Rutland, Thierry Reding, Jonathan Hunter, Ulf Hansson,
	Adrian Hunter, Mikko Perttunen, Stefan Agner, devicetree,
	linux-tegra, linux-kernel, linux-mmc

On Fri, Aug 10, 2018 at 09:08:05PM +0300, Aapo Vienamo wrote:
> Add bindings documentation for pad pull up and pull down offset values to be
> programmed before executing automatic pad drive strength calibration.
> 
> Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
> ---
>  .../bindings/mmc/nvidia,tegra20-sdhci.txt          | 35 ++++++++++++++++++++++
>  1 file changed, 35 insertions(+)

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

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

* Re: [PATCH v2 04/40] dt-bindings: mmc: Add Tegra SDHCI sampling trimmer values
  2018-08-10 18:08 ` [PATCH v2 04/40] dt-bindings: mmc: Add Tegra SDHCI sampling trimmer values Aapo Vienamo
@ 2018-08-13 19:25   ` Rob Herring
  0 siblings, 0 replies; 57+ messages in thread
From: Rob Herring @ 2018-08-13 19:25 UTC (permalink / raw)
  To: Aapo Vienamo
  Cc: Mark Rutland, Thierry Reding, Jonathan Hunter, Ulf Hansson,
	Adrian Hunter, Mikko Perttunen, Stefan Agner, devicetree,
	linux-tegra, linux-kernel, linux-mmc

On Fri, Aug 10, 2018 at 09:08:06PM +0300, Aapo Vienamo wrote:
> Document the Tegra SDHCI inbound and outbound sampling trimmer values.
> 
> Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
> ---
>  .../devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt          | 11 +++++++++++
>  1 file changed, 11 insertions(+)

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

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

* Re: [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (39 preceding siblings ...)
  2018-08-10 18:08 ` [PATCH v2 40/40] arm64: dts: tegra210: " Aapo Vienamo
@ 2018-08-23  8:47 ` Thierry Reding
  2018-08-23 10:42   ` Ulf Hansson
  2018-08-27 10:10 ` Thierry Reding
  2018-08-27 14:10 ` Marcel Ziswiler
  42 siblings, 1 reply; 57+ messages in thread
From: Thierry Reding @ 2018-08-23  8:47 UTC (permalink / raw)
  To: Ulf Hansson, Adrian Hunter
  Cc: Aapo Vienamo, Rob Herring, Mark Rutland, Jonathan Hunter,
	Mikko Perttunen, Stefan Agner, devicetree, linux-tegra,
	linux-kernel, linux-mmc

[-- Attachment #1: Type: text/plain, Size: 6638 bytes --]

On Fri, Aug 10, 2018 at 09:08:02PM +0300, Aapo Vienamo wrote:
> Hi all,
> 
> This series implements support for faster signaling modes on Tegra
> SDHCI controllers. This series consist of several parts: changes
> requried for 1.8 V signaling and pad control, pad calibration, and
> tuning. Following earlies patch sets have been merged into this
> larger set: "Tegra PMC pinctrl pad configuration", "Tegra SDHCI enable
> 1.8 V signaling on Tegar210 and Tegra186", "Tegra SDHCI update the
> padautocal procedure". Also the patches for enabling SDHCI tuning
> are added.
> 
> Changelog:
> v2:
> 	- Fix grammar in PMC device tree bindings docs
> 	- Remove a stray line from tegra sdhci bindings
> 	- Cosmetic changes to PMC pinctrl driver
> 	- Fix a typo in "soc/tegra: pmc: Implement
> 	  tegra_io_pad_is_powered()" commit message
> 	- Declare mask and value on the same line in
> 	  tegra_io_pad_is_powered()
> 	- Move the call to tegra_sdhci_is_pad_and_regulator_valid() to
> 	  inside the if condition in tegra_sdhci_reset()
> 	- Use usleep_range() in tegra_sdhci_configure_cal_pad()
> 	- Move sdhci_writel() out of the enable if-else body in
> 	  tegra_sdhci_configure_cal_pad()
> 	- Add a delay before starting polling in
> 	  tegra_sdhci_pad_autocalib()
> 	- Use usleep_range() in tegra_sdhci_set_tap()
> 	- Rename orig_enabled to status in
> 	  tegra_sdhci_configure_card_clk()
> 	- Fix if condition wrapping alignment in tegra_sdhci_set_tap()
> 
> v1:
> 	- Probe the regulator voltage capabilities to determine whether pinctrl
> 	  is needed in tegra_sdhci_r eset
> 	- Don't remove tegra_sdhci_voltage_switch()
> 	- Use dev_warn() in tegra_sdhci_init_pinctrl_info()
> 	- Don't change start_signal_voltage_switch callback if pinctrl info
> 	  invalid
> 	- Only call udelay(1) on enable in tegra_sdhci_configure_cal_pad()
> 	- Add nvidia, prefix to pad autocal offset dt props in the example
> 
> See the original patch sets for earlier changelogs.
> 
> Aapo Vienamo (40):
>   dt-bindings: Add Tegra PMC pad configuration bindings
>   dt-bindings: mmc: tegra: Add pad voltage control properties
>   dt-bindings: Add Tegra SDHCI pad pdpu offset bindings
>   dt-bindings: mmc: Add Tegra SDHCI sampling trimmer values
>   soc/tegra: pmc: Fix pad voltage configuration for Tegra186
>   soc/tegra: pmc: Factor out DPD register bit calculation
>   soc/tegra: pmc: Implement tegra_io_pad_is_powered()
>   soc/tegra: pmc: Use X macro to generate IO pad tables
>   soc/tegra: pmc: Remove public pad voltage APIs
>   soc/tegra: pmc: Implement pad configuration via pinctrl
>   mmc: sdhci: Add a quirk to skip clearing the transfer mode register on
>     tuning
>   mmc: tegra: Reconfigure pad voltages during voltage switching
>   mmc: tegra: Poll for calibration completion
>   mmc: tegra: Set calibration pad voltage reference
>   mmc: tegra: Power on the calibration pad
>   mmc: tegra: Disable card clock during pad calibration
>   mmc: tegra: Program pad autocal offsets from dt
>   mmc: tegra: Perform pad calibration after voltage switch
>   mmc: tegra: Enable pad calibration on Tegra210 and Tegra186
>   mmc: tegra: Add a workaround for tap value change glitch
>   mmc: tegra: Parse default trim and tap from dt
>   mmc: tegra: Configure default tap values
>   mmc: tegra: Configure default trim value on reset
>   mmc: tegra: Use standard SDHCI tuning on Tegra210 and Tegra186
>   mmc: sdhci: Add a quirk to disable card clock during tuning
>   mmc: tegra: Enable workaround for tuning transfer mode bug
>   mmc: tegra: Set SDHCI_QUIRK2_TUNE_DIS_CARD_CLK on Tegra210
>   mmc: tegra: Enable UHS and HS200 modes for Tegra210
>   mmc: tegra: Enable UHS and HS200 modes for Tegra186
>   arm64: dts: Add Tegra210 sdmmc pinctrl voltage states
>   arm64: dts: Add Tegra186 sdmmc pinctrl voltage states
>   arm64: dts: tegra210-p2180: Allow ldo2 to go down to 1.8 V
>   arm64: dts: tegra210-p2180: Correct sdmmc4 vqmmc-supply
>   arm64: dts: tegra210-p2597: Remove no-1-8-v from sdmmc1
>   arm64: dts: tegra186: Add sdmmc pad auto calibration offsets
>   arm64: dts: tegra210: Add sdmmc pad auto calibration offsets
>   arm64: dts: tegra210: Add SDHCI tap and trim values
>   arm64: dts: tegra186: Add SDHCI tap and trim values
>   arm64: dts: tegra186: Assign clocks for sdmmc1 and sdmmc4
>   arm64: dts: tegra210: Assign clocks for sdmmc1 and sdmmc4
> 
>  .../bindings/arm/tegra/nvidia,tegra186-pmc.txt     |  93 ++++
>  .../bindings/arm/tegra/nvidia,tegra20-pmc.txt      | 103 ++++
>  .../bindings/mmc/nvidia,tegra20-sdhci.txt          |  68 +++
>  arch/arm64/boot/dts/nvidia/tegra186.dtsi           |  74 +++
>  arch/arm64/boot/dts/nvidia/tegra210-p2180.dtsi     |  12 +-
>  arch/arm64/boot/dts/nvidia/tegra210-p2597.dtsi     |   1 -
>  arch/arm64/boot/dts/nvidia/tegra210.dtsi           |  55 ++
>  drivers/mmc/host/sdhci-tegra.c                     | 556 +++++++++++++++++++--
>  drivers/mmc/host/sdhci.c                           |  21 +
>  drivers/mmc/host/sdhci.h                           |   4 +
>  drivers/soc/tegra/pmc.c                            | 511 ++++++++++++++-----
>  include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h |  18 +
>  include/soc/tegra/pmc.h                            |  20 +-
>  13 files changed, 1324 insertions(+), 212 deletions(-)
>  create mode 100644 include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h

Hi Ulf, Adrian,

I've been running some tests on this on various Tegra boards and this
all seems to work fine. I'm also pretty happy with how this turned out,
so the whole series is:

Acked-by: Thierry Reding <treding@nvidia.com>

In order to get this merged, I think it'd be best for you guys to pick
up the MMC patches, since they are all independent of the rest. There is
a runtime dependency on the PMC bits for the faster modes, but things
will fallback to the status quo if those bits are not enabled. The only
dependency here is between the PMC and DTS changes, which I usually pick
up into the Tegra tree anyway, so I can sort that out there.

Since I've already gone through the process of splitting up the series,
I can offer to rebase the MMC patches on top of v4.19-rc1 when it's out
and send a pull request for the MMC patches. Alternatively I can further
split that branch up into two parts, one with the two patches that touch
the core and another with the remainder, if that's what you prefer. Or
you can of course feel free to apply all of the MMC patches yourselves
with my above Acked-by if you want to.

Any thought on the above?

Thanks,
Thierry

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 833 bytes --]

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

* Re: [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling
  2018-08-23  8:47 ` [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Thierry Reding
@ 2018-08-23 10:42   ` Ulf Hansson
  0 siblings, 0 replies; 57+ messages in thread
From: Ulf Hansson @ 2018-08-23 10:42 UTC (permalink / raw)
  To: Thierry Reding
  Cc: Adrian Hunter, Aapo Vienamo, Rob Herring, Mark Rutland,
	Jonathan Hunter, Mikko Perttunen, Stefan Agner, DTML,
	linux-tegra, Linux Kernel Mailing List, linux-mmc

On 23 August 2018 at 10:47, Thierry Reding <thierry.reding@gmail.com> wrote:
> On Fri, Aug 10, 2018 at 09:08:02PM +0300, Aapo Vienamo wrote:
>> Hi all,
>>
>> This series implements support for faster signaling modes on Tegra
>> SDHCI controllers. This series consist of several parts: changes
>> requried for 1.8 V signaling and pad control, pad calibration, and
>> tuning. Following earlies patch sets have been merged into this
>> larger set: "Tegra PMC pinctrl pad configuration", "Tegra SDHCI enable
>> 1.8 V signaling on Tegar210 and Tegra186", "Tegra SDHCI update the
>> padautocal procedure". Also the patches for enabling SDHCI tuning
>> are added.
>>
>> Changelog:
>> v2:
>>       - Fix grammar in PMC device tree bindings docs
>>       - Remove a stray line from tegra sdhci bindings
>>       - Cosmetic changes to PMC pinctrl driver
>>       - Fix a typo in "soc/tegra: pmc: Implement
>>         tegra_io_pad_is_powered()" commit message
>>       - Declare mask and value on the same line in
>>         tegra_io_pad_is_powered()
>>       - Move the call to tegra_sdhci_is_pad_and_regulator_valid() to
>>         inside the if condition in tegra_sdhci_reset()
>>       - Use usleep_range() in tegra_sdhci_configure_cal_pad()
>>       - Move sdhci_writel() out of the enable if-else body in
>>         tegra_sdhci_configure_cal_pad()
>>       - Add a delay before starting polling in
>>         tegra_sdhci_pad_autocalib()
>>       - Use usleep_range() in tegra_sdhci_set_tap()
>>       - Rename orig_enabled to status in
>>         tegra_sdhci_configure_card_clk()
>>       - Fix if condition wrapping alignment in tegra_sdhci_set_tap()
>>
>> v1:
>>       - Probe the regulator voltage capabilities to determine whether pinctrl
>>         is needed in tegra_sdhci_r eset
>>       - Don't remove tegra_sdhci_voltage_switch()
>>       - Use dev_warn() in tegra_sdhci_init_pinctrl_info()
>>       - Don't change start_signal_voltage_switch callback if pinctrl info
>>         invalid
>>       - Only call udelay(1) on enable in tegra_sdhci_configure_cal_pad()
>>       - Add nvidia, prefix to pad autocal offset dt props in the example
>>
>> See the original patch sets for earlier changelogs.
>>
>> Aapo Vienamo (40):
>>   dt-bindings: Add Tegra PMC pad configuration bindings
>>   dt-bindings: mmc: tegra: Add pad voltage control properties
>>   dt-bindings: Add Tegra SDHCI pad pdpu offset bindings
>>   dt-bindings: mmc: Add Tegra SDHCI sampling trimmer values
>>   soc/tegra: pmc: Fix pad voltage configuration for Tegra186
>>   soc/tegra: pmc: Factor out DPD register bit calculation
>>   soc/tegra: pmc: Implement tegra_io_pad_is_powered()
>>   soc/tegra: pmc: Use X macro to generate IO pad tables
>>   soc/tegra: pmc: Remove public pad voltage APIs
>>   soc/tegra: pmc: Implement pad configuration via pinctrl
>>   mmc: sdhci: Add a quirk to skip clearing the transfer mode register on
>>     tuning
>>   mmc: tegra: Reconfigure pad voltages during voltage switching
>>   mmc: tegra: Poll for calibration completion
>>   mmc: tegra: Set calibration pad voltage reference
>>   mmc: tegra: Power on the calibration pad
>>   mmc: tegra: Disable card clock during pad calibration
>>   mmc: tegra: Program pad autocal offsets from dt
>>   mmc: tegra: Perform pad calibration after voltage switch
>>   mmc: tegra: Enable pad calibration on Tegra210 and Tegra186
>>   mmc: tegra: Add a workaround for tap value change glitch
>>   mmc: tegra: Parse default trim and tap from dt
>>   mmc: tegra: Configure default tap values
>>   mmc: tegra: Configure default trim value on reset
>>   mmc: tegra: Use standard SDHCI tuning on Tegra210 and Tegra186
>>   mmc: sdhci: Add a quirk to disable card clock during tuning
>>   mmc: tegra: Enable workaround for tuning transfer mode bug
>>   mmc: tegra: Set SDHCI_QUIRK2_TUNE_DIS_CARD_CLK on Tegra210
>>   mmc: tegra: Enable UHS and HS200 modes for Tegra210
>>   mmc: tegra: Enable UHS and HS200 modes for Tegra186
>>   arm64: dts: Add Tegra210 sdmmc pinctrl voltage states
>>   arm64: dts: Add Tegra186 sdmmc pinctrl voltage states
>>   arm64: dts: tegra210-p2180: Allow ldo2 to go down to 1.8 V
>>   arm64: dts: tegra210-p2180: Correct sdmmc4 vqmmc-supply
>>   arm64: dts: tegra210-p2597: Remove no-1-8-v from sdmmc1
>>   arm64: dts: tegra186: Add sdmmc pad auto calibration offsets
>>   arm64: dts: tegra210: Add sdmmc pad auto calibration offsets
>>   arm64: dts: tegra210: Add SDHCI tap and trim values
>>   arm64: dts: tegra186: Add SDHCI tap and trim values
>>   arm64: dts: tegra186: Assign clocks for sdmmc1 and sdmmc4
>>   arm64: dts: tegra210: Assign clocks for sdmmc1 and sdmmc4
>>
>>  .../bindings/arm/tegra/nvidia,tegra186-pmc.txt     |  93 ++++
>>  .../bindings/arm/tegra/nvidia,tegra20-pmc.txt      | 103 ++++
>>  .../bindings/mmc/nvidia,tegra20-sdhci.txt          |  68 +++
>>  arch/arm64/boot/dts/nvidia/tegra186.dtsi           |  74 +++
>>  arch/arm64/boot/dts/nvidia/tegra210-p2180.dtsi     |  12 +-
>>  arch/arm64/boot/dts/nvidia/tegra210-p2597.dtsi     |   1 -
>>  arch/arm64/boot/dts/nvidia/tegra210.dtsi           |  55 ++
>>  drivers/mmc/host/sdhci-tegra.c                     | 556 +++++++++++++++++++--
>>  drivers/mmc/host/sdhci.c                           |  21 +
>>  drivers/mmc/host/sdhci.h                           |   4 +
>>  drivers/soc/tegra/pmc.c                            | 511 ++++++++++++++-----
>>  include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h |  18 +
>>  include/soc/tegra/pmc.h                            |  20 +-
>>  13 files changed, 1324 insertions(+), 212 deletions(-)
>>  create mode 100644 include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h
>
> Hi Ulf, Adrian,
>
> I've been running some tests on this on various Tegra boards and this
> all seems to work fine. I'm also pretty happy with how this turned out,
> so the whole series is:
>
> Acked-by: Thierry Reding <treding@nvidia.com>
>
> In order to get this merged, I think it'd be best for you guys to pick
> up the MMC patches, since they are all independent of the rest. There is
> a runtime dependency on the PMC bits for the faster modes, but things
> will fallback to the status quo if those bits are not enabled. The only
> dependency here is between the PMC and DTS changes, which I usually pick
> up into the Tegra tree anyway, so I can sort that out there.

Great, thanks for clarifying the dependency.

>
> Since I've already gone through the process of splitting up the series,
> I can offer to rebase the MMC patches on top of v4.19-rc1 when it's out
> and send a pull request for the MMC patches.

That sounds convenient for me. Please also include the corresponding
dt doc changes for mmc, as I am normally queuing these via my mmc
tree.

Although, I think it's better to wait until Adrian has given his ack
for the series.

> Alternatively I can further
> split that branch up into two parts, one with the two patches that touch
> the core and another with the remainder, if that's what you prefer. Or
> you can of course feel free to apply all of the MMC patches yourselves
> with my above Acked-by if you want to.
>
> Any thought on the above?

Let's see how it goes, if there are any struggles, I don't have a
problem to cherry-pick the mmc parts of the series.

Kind regards
Uffe

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

* Re: [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (40 preceding siblings ...)
  2018-08-23  8:47 ` [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Thierry Reding
@ 2018-08-27 10:10 ` Thierry Reding
  2018-08-27 10:26   ` Adrian Hunter
  2018-08-27 14:10 ` Marcel Ziswiler
  42 siblings, 1 reply; 57+ messages in thread
From: Thierry Reding @ 2018-08-27 10:10 UTC (permalink / raw)
  To: Adrian Hunter
  Cc: Aapo Vienamo, Rob Herring, Mark Rutland, Jonathan Hunter,
	Ulf Hansson, Mikko Perttunen, Stefan Agner, devicetree,
	linux-tegra, linux-kernel, linux-mmc

[-- Attachment #1: Type: text/plain, Size: 5648 bytes --]

On Fri, Aug 10, 2018 at 09:08:02PM +0300, Aapo Vienamo wrote:
> Hi all,
> 
> This series implements support for faster signaling modes on Tegra
> SDHCI controllers. This series consist of several parts: changes
> requried for 1.8 V signaling and pad control, pad calibration, and
> tuning. Following earlies patch sets have been merged into this
> larger set: "Tegra PMC pinctrl pad configuration", "Tegra SDHCI enable
> 1.8 V signaling on Tegar210 and Tegra186", "Tegra SDHCI update the
> padautocal procedure". Also the patches for enabling SDHCI tuning
> are added.
> 
> Changelog:
> v2:
> 	- Fix grammar in PMC device tree bindings docs
> 	- Remove a stray line from tegra sdhci bindings
> 	- Cosmetic changes to PMC pinctrl driver
> 	- Fix a typo in "soc/tegra: pmc: Implement
> 	  tegra_io_pad_is_powered()" commit message
> 	- Declare mask and value on the same line in
> 	  tegra_io_pad_is_powered()
> 	- Move the call to tegra_sdhci_is_pad_and_regulator_valid() to
> 	  inside the if condition in tegra_sdhci_reset()
> 	- Use usleep_range() in tegra_sdhci_configure_cal_pad()
> 	- Move sdhci_writel() out of the enable if-else body in
> 	  tegra_sdhci_configure_cal_pad()
> 	- Add a delay before starting polling in
> 	  tegra_sdhci_pad_autocalib()
> 	- Use usleep_range() in tegra_sdhci_set_tap()
> 	- Rename orig_enabled to status in
> 	  tegra_sdhci_configure_card_clk()
> 	- Fix if condition wrapping alignment in tegra_sdhci_set_tap()
> 
> v1:
> 	- Probe the regulator voltage capabilities to determine whether pinctrl
> 	  is needed in tegra_sdhci_r eset
> 	- Don't remove tegra_sdhci_voltage_switch()
> 	- Use dev_warn() in tegra_sdhci_init_pinctrl_info()
> 	- Don't change start_signal_voltage_switch callback if pinctrl info
> 	  invalid
> 	- Only call udelay(1) on enable in tegra_sdhci_configure_cal_pad()
> 	- Add nvidia, prefix to pad autocal offset dt props in the example
> 
> See the original patch sets for earlier changelogs.
> 
> Aapo Vienamo (40):
>   dt-bindings: Add Tegra PMC pad configuration bindings
>   dt-bindings: mmc: tegra: Add pad voltage control properties
>   dt-bindings: Add Tegra SDHCI pad pdpu offset bindings
>   dt-bindings: mmc: Add Tegra SDHCI sampling trimmer values
>   soc/tegra: pmc: Fix pad voltage configuration for Tegra186
>   soc/tegra: pmc: Factor out DPD register bit calculation
>   soc/tegra: pmc: Implement tegra_io_pad_is_powered()
>   soc/tegra: pmc: Use X macro to generate IO pad tables
>   soc/tegra: pmc: Remove public pad voltage APIs
>   soc/tegra: pmc: Implement pad configuration via pinctrl
>   mmc: sdhci: Add a quirk to skip clearing the transfer mode register on
>     tuning
>   mmc: tegra: Reconfigure pad voltages during voltage switching
>   mmc: tegra: Poll for calibration completion
>   mmc: tegra: Set calibration pad voltage reference
>   mmc: tegra: Power on the calibration pad
>   mmc: tegra: Disable card clock during pad calibration
>   mmc: tegra: Program pad autocal offsets from dt
>   mmc: tegra: Perform pad calibration after voltage switch
>   mmc: tegra: Enable pad calibration on Tegra210 and Tegra186
>   mmc: tegra: Add a workaround for tap value change glitch
>   mmc: tegra: Parse default trim and tap from dt
>   mmc: tegra: Configure default tap values
>   mmc: tegra: Configure default trim value on reset
>   mmc: tegra: Use standard SDHCI tuning on Tegra210 and Tegra186
>   mmc: sdhci: Add a quirk to disable card clock during tuning
>   mmc: tegra: Enable workaround for tuning transfer mode bug
>   mmc: tegra: Set SDHCI_QUIRK2_TUNE_DIS_CARD_CLK on Tegra210
>   mmc: tegra: Enable UHS and HS200 modes for Tegra210
>   mmc: tegra: Enable UHS and HS200 modes for Tegra186
>   arm64: dts: Add Tegra210 sdmmc pinctrl voltage states
>   arm64: dts: Add Tegra186 sdmmc pinctrl voltage states
>   arm64: dts: tegra210-p2180: Allow ldo2 to go down to 1.8 V
>   arm64: dts: tegra210-p2180: Correct sdmmc4 vqmmc-supply
>   arm64: dts: tegra210-p2597: Remove no-1-8-v from sdmmc1
>   arm64: dts: tegra186: Add sdmmc pad auto calibration offsets
>   arm64: dts: tegra210: Add sdmmc pad auto calibration offsets
>   arm64: dts: tegra210: Add SDHCI tap and trim values
>   arm64: dts: tegra186: Add SDHCI tap and trim values
>   arm64: dts: tegra186: Assign clocks for sdmmc1 and sdmmc4
>   arm64: dts: tegra210: Assign clocks for sdmmc1 and sdmmc4
> 
>  .../bindings/arm/tegra/nvidia,tegra186-pmc.txt     |  93 ++++
>  .../bindings/arm/tegra/nvidia,tegra20-pmc.txt      | 103 ++++
>  .../bindings/mmc/nvidia,tegra20-sdhci.txt          |  68 +++
>  arch/arm64/boot/dts/nvidia/tegra186.dtsi           |  74 +++
>  arch/arm64/boot/dts/nvidia/tegra210-p2180.dtsi     |  12 +-
>  arch/arm64/boot/dts/nvidia/tegra210-p2597.dtsi     |   1 -
>  arch/arm64/boot/dts/nvidia/tegra210.dtsi           |  55 ++
>  drivers/mmc/host/sdhci-tegra.c                     | 556 +++++++++++++++++++--
>  drivers/mmc/host/sdhci.c                           |  21 +
>  drivers/mmc/host/sdhci.h                           |   4 +
>  drivers/soc/tegra/pmc.c                            | 511 ++++++++++++++-----
>  include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h |  18 +
>  include/soc/tegra/pmc.h                            |  20 +-
>  13 files changed, 1324 insertions(+), 212 deletions(-)
>  create mode 100644 include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h

Adrian,

these patches are also a prerequisite for the UHS signalling changes in
the other two series that Aapo posted. It'd be great if you could take a
quick look and weigh in.

Thanks,
Thierry

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 833 bytes --]

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

* Re: [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling
  2018-08-27 10:10 ` Thierry Reding
@ 2018-08-27 10:26   ` Adrian Hunter
  2018-08-27 11:43     ` Adrian Hunter
  0 siblings, 1 reply; 57+ messages in thread
From: Adrian Hunter @ 2018-08-27 10:26 UTC (permalink / raw)
  To: Thierry Reding
  Cc: Aapo Vienamo, Rob Herring, Mark Rutland, Jonathan Hunter,
	Ulf Hansson, Mikko Perttunen, Stefan Agner, devicetree,
	linux-tegra, linux-kernel, linux-mmc

On 27/08/18 13:10, Thierry Reding wrote:
> On Fri, Aug 10, 2018 at 09:08:02PM +0300, Aapo Vienamo wrote:
>> Hi all,
>>
>> This series implements support for faster signaling modes on Tegra
>> SDHCI controllers. This series consist of several parts: changes
>> requried for 1.8 V signaling and pad control, pad calibration, and
>> tuning. Following earlies patch sets have been merged into this
>> larger set: "Tegra PMC pinctrl pad configuration", "Tegra SDHCI enable
>> 1.8 V signaling on Tegar210 and Tegra186", "Tegra SDHCI update the
>> padautocal procedure". Also the patches for enabling SDHCI tuning
>> are added.
>>
>> Changelog:
>> v2:
>> 	- Fix grammar in PMC device tree bindings docs
>> 	- Remove a stray line from tegra sdhci bindings
>> 	- Cosmetic changes to PMC pinctrl driver
>> 	- Fix a typo in "soc/tegra: pmc: Implement
>> 	  tegra_io_pad_is_powered()" commit message
>> 	- Declare mask and value on the same line in
>> 	  tegra_io_pad_is_powered()
>> 	- Move the call to tegra_sdhci_is_pad_and_regulator_valid() to
>> 	  inside the if condition in tegra_sdhci_reset()
>> 	- Use usleep_range() in tegra_sdhci_configure_cal_pad()
>> 	- Move sdhci_writel() out of the enable if-else body in
>> 	  tegra_sdhci_configure_cal_pad()
>> 	- Add a delay before starting polling in
>> 	  tegra_sdhci_pad_autocalib()
>> 	- Use usleep_range() in tegra_sdhci_set_tap()
>> 	- Rename orig_enabled to status in
>> 	  tegra_sdhci_configure_card_clk()
>> 	- Fix if condition wrapping alignment in tegra_sdhci_set_tap()
>>
>> v1:
>> 	- Probe the regulator voltage capabilities to determine whether pinctrl
>> 	  is needed in tegra_sdhci_r eset
>> 	- Don't remove tegra_sdhci_voltage_switch()
>> 	- Use dev_warn() in tegra_sdhci_init_pinctrl_info()
>> 	- Don't change start_signal_voltage_switch callback if pinctrl info
>> 	  invalid
>> 	- Only call udelay(1) on enable in tegra_sdhci_configure_cal_pad()
>> 	- Add nvidia, prefix to pad autocal offset dt props in the example
>>
>> See the original patch sets for earlier changelogs.
>>
>> Aapo Vienamo (40):
>>   dt-bindings: Add Tegra PMC pad configuration bindings
>>   dt-bindings: mmc: tegra: Add pad voltage control properties
>>   dt-bindings: Add Tegra SDHCI pad pdpu offset bindings
>>   dt-bindings: mmc: Add Tegra SDHCI sampling trimmer values
>>   soc/tegra: pmc: Fix pad voltage configuration for Tegra186
>>   soc/tegra: pmc: Factor out DPD register bit calculation
>>   soc/tegra: pmc: Implement tegra_io_pad_is_powered()
>>   soc/tegra: pmc: Use X macro to generate IO pad tables
>>   soc/tegra: pmc: Remove public pad voltage APIs
>>   soc/tegra: pmc: Implement pad configuration via pinctrl
>>   mmc: sdhci: Add a quirk to skip clearing the transfer mode register on
>>     tuning
>>   mmc: tegra: Reconfigure pad voltages during voltage switching
>>   mmc: tegra: Poll for calibration completion
>>   mmc: tegra: Set calibration pad voltage reference
>>   mmc: tegra: Power on the calibration pad
>>   mmc: tegra: Disable card clock during pad calibration
>>   mmc: tegra: Program pad autocal offsets from dt
>>   mmc: tegra: Perform pad calibration after voltage switch
>>   mmc: tegra: Enable pad calibration on Tegra210 and Tegra186
>>   mmc: tegra: Add a workaround for tap value change glitch
>>   mmc: tegra: Parse default trim and tap from dt
>>   mmc: tegra: Configure default tap values
>>   mmc: tegra: Configure default trim value on reset
>>   mmc: tegra: Use standard SDHCI tuning on Tegra210 and Tegra186
>>   mmc: sdhci: Add a quirk to disable card clock during tuning
>>   mmc: tegra: Enable workaround for tuning transfer mode bug
>>   mmc: tegra: Set SDHCI_QUIRK2_TUNE_DIS_CARD_CLK on Tegra210
>>   mmc: tegra: Enable UHS and HS200 modes for Tegra210
>>   mmc: tegra: Enable UHS and HS200 modes for Tegra186
>>   arm64: dts: Add Tegra210 sdmmc pinctrl voltage states
>>   arm64: dts: Add Tegra186 sdmmc pinctrl voltage states
>>   arm64: dts: tegra210-p2180: Allow ldo2 to go down to 1.8 V
>>   arm64: dts: tegra210-p2180: Correct sdmmc4 vqmmc-supply
>>   arm64: dts: tegra210-p2597: Remove no-1-8-v from sdmmc1
>>   arm64: dts: tegra186: Add sdmmc pad auto calibration offsets
>>   arm64: dts: tegra210: Add sdmmc pad auto calibration offsets
>>   arm64: dts: tegra210: Add SDHCI tap and trim values
>>   arm64: dts: tegra186: Add SDHCI tap and trim values
>>   arm64: dts: tegra186: Assign clocks for sdmmc1 and sdmmc4
>>   arm64: dts: tegra210: Assign clocks for sdmmc1 and sdmmc4
>>
>>  .../bindings/arm/tegra/nvidia,tegra186-pmc.txt     |  93 ++++
>>  .../bindings/arm/tegra/nvidia,tegra20-pmc.txt      | 103 ++++
>>  .../bindings/mmc/nvidia,tegra20-sdhci.txt          |  68 +++
>>  arch/arm64/boot/dts/nvidia/tegra186.dtsi           |  74 +++
>>  arch/arm64/boot/dts/nvidia/tegra210-p2180.dtsi     |  12 +-
>>  arch/arm64/boot/dts/nvidia/tegra210-p2597.dtsi     |   1 -
>>  arch/arm64/boot/dts/nvidia/tegra210.dtsi           |  55 ++
>>  drivers/mmc/host/sdhci-tegra.c                     | 556 +++++++++++++++++++--
>>  drivers/mmc/host/sdhci.c                           |  21 +
>>  drivers/mmc/host/sdhci.h                           |   4 +
>>  drivers/soc/tegra/pmc.c                            | 511 ++++++++++++++-----
>>  include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h |  18 +
>>  include/soc/tegra/pmc.h                            |  20 +-
>>  13 files changed, 1324 insertions(+), 212 deletions(-)
>>  create mode 100644 include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h
> 
> Adrian,
> 
> these patches are also a prerequisite for the UHS signalling changes in
> the other two series that Aapo posted. It'd be great if you could take a
> quick look and weigh in.

Sure, I'll try and have a look today.

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

* Re: [PATCH v2 11/40] mmc: sdhci: Add a quirk to skip clearing the transfer mode register on tuning
  2018-08-10 18:08 ` [PATCH v2 11/40] mmc: sdhci: Add a quirk to skip clearing the transfer mode register on tuning Aapo Vienamo
@ 2018-08-27 11:01   ` Adrian Hunter
  2018-08-28 14:45     ` Aapo Vienamo
  0 siblings, 1 reply; 57+ messages in thread
From: Adrian Hunter @ 2018-08-27 11:01 UTC (permalink / raw)
  To: Aapo Vienamo, Rob Herring, Mark Rutland, Thierry Reding,
	Jonathan Hunter, Ulf Hansson, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc

On 10/08/18 21:08, Aapo Vienamo wrote:
> Add SDHCI_QUIRK2_TUNE_SKIP_XFERRMODE_REG_PROG to skip programming the
> SDHCI_TRANSFER_MODE in sdhci_set_transfer_mode() if tuning command is
> being sent.
> 
> On Tegra210 and Tegra186 the tuning sequence hangs if the SDHCI
> transfer mode register is touched.
> 
> Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
> ---
>  drivers/mmc/host/sdhci.c | 6 ++++++
>  drivers/mmc/host/sdhci.h | 2 ++
>  2 files changed, 8 insertions(+)
> 
> diff --git a/drivers/mmc/host/sdhci.c b/drivers/mmc/host/sdhci.c
> index a7b5602..04dc443 100644
> --- a/drivers/mmc/host/sdhci.c
> +++ b/drivers/mmc/host/sdhci.c
> @@ -1028,6 +1028,12 @@ static void sdhci_set_transfer_mode(struct sdhci_host *host,
>  
>  	if (data == NULL) {
>  		if (host->quirks2 &
> +			SDHCI_QUIRK2_TUNE_SKIP_XFERMODE_REG_PROG &&
> +				(cmd->opcode == MMC_SEND_TUNING_BLOCK ||
> +				 cmd->opcode == MMC_SEND_TUNING_BLOCK_HS200)) {
> +			return;
> +		}

Rather than introduce a quirk, can't we just dodge the unnecessary write e.g.

diff --git a/drivers/mmc/host/sdhci.c b/drivers/mmc/host/sdhci.c
index 1b3fbd9bd5c5..68af6a67e397 100644
--- a/drivers/mmc/host/sdhci.c
+++ b/drivers/mmc/host/sdhci.c
@@ -1033,10 +1033,19 @@ static void sdhci_set_transfer_mode(struct sdhci_host *host,
 			if (cmd->opcode != MMC_SEND_TUNING_BLOCK_HS200)
 				sdhci_writew(host, 0x0, SDHCI_TRANSFER_MODE);
 		} else {
-		/* clear Auto CMD settings for no data CMDs */
+			u16 orig;
+
+			/* clear Auto CMD settings for no data CMDs */
 			mode = sdhci_readw(host, SDHCI_TRANSFER_MODE);
-			sdhci_writew(host, mode & ~(SDHCI_TRNS_AUTO_CMD12 |
-				SDHCI_TRNS_AUTO_CMD23), SDHCI_TRANSFER_MODE);
+			orig = mode;
+			mode &= ~(SDHCI_TRNS_AUTO_CMD12 | SDHCI_TRNS_AUTO_CMD23);
+			/*
+			 * Do not write transfer mode unnecessarily because it
+			 * can upset some host controllers (e.g. sdhci-tregra)
+			 * during tuning.
+			 */
+			if (mode != orig)
+				sdhci_writew(host, new_mode, SDHCI_TRANSFER_MODE);
 		}
 		return;
 	}


Alternatively 

> +		if (host->quirks2 &
>  			SDHCI_QUIRK2_CLEAR_TRANSFERMODE_REG_BEFORE_CMD) {
>  			sdhci_writew(host, 0x0, SDHCI_TRANSFER_MODE);
>  		} else {
> diff --git a/drivers/mmc/host/sdhci.h b/drivers/mmc/host/sdhci.h
> index 23966f8..0a99008 100644
> --- a/drivers/mmc/host/sdhci.h
> +++ b/drivers/mmc/host/sdhci.h
> @@ -450,6 +450,8 @@ struct sdhci_host {
>   * obtainable timeout.
>   */
>  #define SDHCI_QUIRK2_DISABLE_HW_TIMEOUT			(1<<17)
> +/* Don't clear the SDHCI_TRANSFER_MODE register on tuning commands */
> +#define SDHCI_QUIRK2_TUNE_SKIP_XFERMODE_REG_PROG	(1<<18)
>  
>  	int irq;		/* Device IRQ */
>  	void __iomem *ioaddr;	/* Mapped address */
> 


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

* Re: [PATCH v2 25/40] mmc: sdhci: Add a quirk to disable card clock during tuning
  2018-08-10 18:08 ` [PATCH v2 25/40] mmc: sdhci: Add a quirk to disable card clock during tuning Aapo Vienamo
@ 2018-08-27 11:25   ` Adrian Hunter
  2018-08-28 15:41     ` Aapo Vienamo
  0 siblings, 1 reply; 57+ messages in thread
From: Adrian Hunter @ 2018-08-27 11:25 UTC (permalink / raw)
  To: Aapo Vienamo, Rob Herring, Mark Rutland, Thierry Reding,
	Jonathan Hunter, Ulf Hansson, Mikko Perttunen, Stefan Agner
  Cc: devicetree, linux-tegra, linux-kernel, linux-mmc

On 10/08/18 21:08, Aapo Vienamo wrote:
> Add a quirk to disable card clock when the tuning command is sent.
> 
> This has to be done to prevent the SDHCI controller from hanging on
> Tegra210. Without the quirk enabled there appears to be around 10%
> chance that the tuning sequence will fail and time out due to the
> controller locking up.
> 
> Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
> ---
>  drivers/mmc/host/sdhci.c | 15 +++++++++++++++
>  drivers/mmc/host/sdhci.h |  2 ++
>  2 files changed, 17 insertions(+)
> 
> diff --git a/drivers/mmc/host/sdhci.c b/drivers/mmc/host/sdhci.c
> index 04dc443..166b16f 100644
> --- a/drivers/mmc/host/sdhci.c
> +++ b/drivers/mmc/host/sdhci.c
> @@ -2175,6 +2175,7 @@ static void sdhci_send_tuning(struct sdhci_host *host, u32 opcode)
>  	struct mmc_request mrq = {};
>  	unsigned long flags;
>  	u32 b = host->sdma_boundary;
> +	u16 clk;
>  
>  	spin_lock_irqsave(&host->lock, flags);
>  
> @@ -2183,6 +2184,13 @@ static void sdhci_send_tuning(struct sdhci_host *host, u32 opcode)
>  	cmd.mrq = &mrq;
>  
>  	mrq.cmd = &cmd;
> +
> +	if (host->quirks2 & SDHCI_QUIRK2_TUNE_DIS_CARD_CLK) {
> +		clk = sdhci_readw(host, SDHCI_CLOCK_CONTROL);
> +		clk &= ~SDHCI_CLOCK_CARD_EN;
> +		sdhci_writew(host, clk, SDHCI_CLOCK_CONTROL);

Rather than using a quirk, could you use the sdhci I/O accessors to disable
the clock before the tuning comment is written, udelay(1), and then enable
it again?

> +	}
> +
>  	/*
>  	 * In response to CMD19, the card sends 64 bytes of tuning
>  	 * block to the Host Controller. So we set the block size
> @@ -2213,6 +2221,13 @@ static void sdhci_send_tuning(struct sdhci_host *host, u32 opcode)
>  	mmiowb();
>  	spin_unlock_irqrestore(&host->lock, flags);
>  
> +	if (host->quirks2 & SDHCI_QUIRK2_TUNE_DIS_CARD_CLK) {
> +		udelay(1);
> +		clk = sdhci_readw(host, SDHCI_CLOCK_CONTROL);
> +		clk |= SDHCI_CLOCK_CARD_EN;
> +		sdhci_writew(host, clk, SDHCI_CLOCK_CONTROL);
> +	}
> +
>  	/* Wait for Buffer Read Ready interrupt */
>  	wait_event_timeout(host->buf_ready_int, (host->tuning_done == 1),
>  			   msecs_to_jiffies(50));
> diff --git a/drivers/mmc/host/sdhci.h b/drivers/mmc/host/sdhci.h
> index 0a99008..cc411b0 100644
> --- a/drivers/mmc/host/sdhci.h
> +++ b/drivers/mmc/host/sdhci.h
> @@ -452,6 +452,8 @@ struct sdhci_host {
>  #define SDHCI_QUIRK2_DISABLE_HW_TIMEOUT			(1<<17)
>  /* Don't clear the SDHCI_TRANSFER_MODE register on tuning commands */
>  #define SDHCI_QUIRK2_TUNE_SKIP_XFERMODE_REG_PROG	(1<<18)
> +/* Disable card clock during tuning */
> +#define SDHCI_QUIRK2_TUNE_DIS_CARD_CLK			(1<<19)
>  
>  	int irq;		/* Device IRQ */
>  	void __iomem *ioaddr;	/* Mapped address */
> 


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

* Re: [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling
  2018-08-27 10:26   ` Adrian Hunter
@ 2018-08-27 11:43     ` Adrian Hunter
  0 siblings, 0 replies; 57+ messages in thread
From: Adrian Hunter @ 2018-08-27 11:43 UTC (permalink / raw)
  To: Thierry Reding
  Cc: Aapo Vienamo, Rob Herring, Mark Rutland, Jonathan Hunter,
	Ulf Hansson, Mikko Perttunen, Stefan Agner, devicetree,
	linux-tegra, linux-kernel, linux-mmc

On 27/08/18 13:26, Adrian Hunter wrote:
> On 27/08/18 13:10, Thierry Reding wrote:
>> On Fri, Aug 10, 2018 at 09:08:02PM +0300, Aapo Vienamo wrote:
>>> Hi all,
>>>
>>> This series implements support for faster signaling modes on Tegra
>>> SDHCI controllers. This series consist of several parts: changes
>>> requried for 1.8 V signaling and pad control, pad calibration, and
>>> tuning. Following earlies patch sets have been merged into this
>>> larger set: "Tegra PMC pinctrl pad configuration", "Tegra SDHCI enable
>>> 1.8 V signaling on Tegar210 and Tegra186", "Tegra SDHCI update the
>>> padautocal procedure". Also the patches for enabling SDHCI tuning
>>> are added.
>>>
>>> Changelog:
>>> v2:
>>> 	- Fix grammar in PMC device tree bindings docs
>>> 	- Remove a stray line from tegra sdhci bindings
>>> 	- Cosmetic changes to PMC pinctrl driver
>>> 	- Fix a typo in "soc/tegra: pmc: Implement
>>> 	  tegra_io_pad_is_powered()" commit message
>>> 	- Declare mask and value on the same line in
>>> 	  tegra_io_pad_is_powered()
>>> 	- Move the call to tegra_sdhci_is_pad_and_regulator_valid() to
>>> 	  inside the if condition in tegra_sdhci_reset()
>>> 	- Use usleep_range() in tegra_sdhci_configure_cal_pad()
>>> 	- Move sdhci_writel() out of the enable if-else body in
>>> 	  tegra_sdhci_configure_cal_pad()
>>> 	- Add a delay before starting polling in
>>> 	  tegra_sdhci_pad_autocalib()
>>> 	- Use usleep_range() in tegra_sdhci_set_tap()
>>> 	- Rename orig_enabled to status in
>>> 	  tegra_sdhci_configure_card_clk()
>>> 	- Fix if condition wrapping alignment in tegra_sdhci_set_tap()
>>>
>>> v1:
>>> 	- Probe the regulator voltage capabilities to determine whether pinctrl
>>> 	  is needed in tegra_sdhci_r eset
>>> 	- Don't remove tegra_sdhci_voltage_switch()
>>> 	- Use dev_warn() in tegra_sdhci_init_pinctrl_info()
>>> 	- Don't change start_signal_voltage_switch callback if pinctrl info
>>> 	  invalid
>>> 	- Only call udelay(1) on enable in tegra_sdhci_configure_cal_pad()
>>> 	- Add nvidia, prefix to pad autocal offset dt props in the example
>>>
>>> See the original patch sets for earlier changelogs.
>>>
>>> Aapo Vienamo (40):
>>>   dt-bindings: Add Tegra PMC pad configuration bindings
>>>   dt-bindings: mmc: tegra: Add pad voltage control properties
>>>   dt-bindings: Add Tegra SDHCI pad pdpu offset bindings
>>>   dt-bindings: mmc: Add Tegra SDHCI sampling trimmer values
>>>   soc/tegra: pmc: Fix pad voltage configuration for Tegra186
>>>   soc/tegra: pmc: Factor out DPD register bit calculation
>>>   soc/tegra: pmc: Implement tegra_io_pad_is_powered()
>>>   soc/tegra: pmc: Use X macro to generate IO pad tables
>>>   soc/tegra: pmc: Remove public pad voltage APIs
>>>   soc/tegra: pmc: Implement pad configuration via pinctrl
>>>   mmc: sdhci: Add a quirk to skip clearing the transfer mode register on
>>>     tuning
>>>   mmc: tegra: Reconfigure pad voltages during voltage switching
>>>   mmc: tegra: Poll for calibration completion
>>>   mmc: tegra: Set calibration pad voltage reference
>>>   mmc: tegra: Power on the calibration pad
>>>   mmc: tegra: Disable card clock during pad calibration
>>>   mmc: tegra: Program pad autocal offsets from dt
>>>   mmc: tegra: Perform pad calibration after voltage switch
>>>   mmc: tegra: Enable pad calibration on Tegra210 and Tegra186
>>>   mmc: tegra: Add a workaround for tap value change glitch
>>>   mmc: tegra: Parse default trim and tap from dt
>>>   mmc: tegra: Configure default tap values
>>>   mmc: tegra: Configure default trim value on reset
>>>   mmc: tegra: Use standard SDHCI tuning on Tegra210 and Tegra186
>>>   mmc: sdhci: Add a quirk to disable card clock during tuning
>>>   mmc: tegra: Enable workaround for tuning transfer mode bug
>>>   mmc: tegra: Set SDHCI_QUIRK2_TUNE_DIS_CARD_CLK on Tegra210
>>>   mmc: tegra: Enable UHS and HS200 modes for Tegra210
>>>   mmc: tegra: Enable UHS and HS200 modes for Tegra186
>>>   arm64: dts: Add Tegra210 sdmmc pinctrl voltage states
>>>   arm64: dts: Add Tegra186 sdmmc pinctrl voltage states
>>>   arm64: dts: tegra210-p2180: Allow ldo2 to go down to 1.8 V
>>>   arm64: dts: tegra210-p2180: Correct sdmmc4 vqmmc-supply
>>>   arm64: dts: tegra210-p2597: Remove no-1-8-v from sdmmc1
>>>   arm64: dts: tegra186: Add sdmmc pad auto calibration offsets
>>>   arm64: dts: tegra210: Add sdmmc pad auto calibration offsets
>>>   arm64: dts: tegra210: Add SDHCI tap and trim values
>>>   arm64: dts: tegra186: Add SDHCI tap and trim values
>>>   arm64: dts: tegra186: Assign clocks for sdmmc1 and sdmmc4
>>>   arm64: dts: tegra210: Assign clocks for sdmmc1 and sdmmc4
>>>
>>>  .../bindings/arm/tegra/nvidia,tegra186-pmc.txt     |  93 ++++
>>>  .../bindings/arm/tegra/nvidia,tegra20-pmc.txt      | 103 ++++
>>>  .../bindings/mmc/nvidia,tegra20-sdhci.txt          |  68 +++
>>>  arch/arm64/boot/dts/nvidia/tegra186.dtsi           |  74 +++
>>>  arch/arm64/boot/dts/nvidia/tegra210-p2180.dtsi     |  12 +-
>>>  arch/arm64/boot/dts/nvidia/tegra210-p2597.dtsi     |   1 -
>>>  arch/arm64/boot/dts/nvidia/tegra210.dtsi           |  55 ++
>>>  drivers/mmc/host/sdhci-tegra.c                     | 556 +++++++++++++++++++--
>>>  drivers/mmc/host/sdhci.c                           |  21 +
>>>  drivers/mmc/host/sdhci.h                           |   4 +
>>>  drivers/soc/tegra/pmc.c                            | 511 ++++++++++++++-----
>>>  include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h |  18 +
>>>  include/soc/tegra/pmc.h                            |  20 +-
>>>  13 files changed, 1324 insertions(+), 212 deletions(-)
>>>  create mode 100644 include/dt-bindings/pinctrl/pinctrl-tegra-io-pad.h
>>
>> Adrian,
>>
>> these patches are also a prerequisite for the UHS signalling changes in
>> the other two series that Aapo posted. It'd be great if you could take a
>> quick look and weigh in.
> 
> Sure, I'll try and have a look today.

Apart from the 2 new quirks which I made comments on, the rest seems fine.


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

* Re: [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling
  2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
                   ` (41 preceding siblings ...)
  2018-08-27 10:10 ` Thierry Reding
@ 2018-08-27 14:10 ` Marcel Ziswiler
  2018-08-27 15:50   ` Thierry Reding
  42 siblings, 1 reply; 57+ messages in thread
From: Marcel Ziswiler @ 2018-08-27 14:10 UTC (permalink / raw)
  To: robh+dt, jonathanh, mperttunen, stefan, thierry.reding,
	mark.rutland, ulf.hansson, avienamo, adrian.hunter
  Cc: linux-kernel, linux-mmc, linux-tegra, devicetree

On Fri, 2018-08-10 at 21:08 +0300, Aapo Vienamo wrote:
> Hi all,
> 
> This series implements support for faster signaling modes on Tegra
> SDHCI controllers. This series consist of several parts: changes
> requried for 1.8 V signaling and pad control, pad calibration, and
> tuning. Following earlies patch sets have been merged into this
> larger set: "Tegra PMC pinctrl pad configuration", "Tegra SDHCI
> enable
> 1.8 V signaling on Tegar210 and Tegra186", "Tegra SDHCI update the
> padautocal procedure". Also the patches for enabling SDHCI tuning
> are added.

I tried your tkln/hs200 branch on Colibri T20, Apalis/Colibri T30 and
Apalis TK1. It at least does not seem to make things any worse but
HS200 on TK1 still seems to behave strangely. During boot I do get the
following message (mmc0 being the SDHCI instance of one of them SD card
slots):

[    3.238360] mmc0: Internal clock never stabilised.
[    3.243183] mmc0: sdhci: ============ SDHCI REGISTER DUMP
===========
[    3.249649] mmc0: sdhci: Sys addr:  0x00000000 |
Version:  0x00000303
[    3.256138] mmc0: sdhci: Blk size:  0x00000000 | Blk
cnt:  0x00000000
[    3.262657] mmc0: sdhci: Argument:  0x00000000 | Trn mode:
0x00000000
[    3.269119] mmc0: sdhci: Present:   0x01fb00f0 | Host ctl:
0x00000000
[    3.275580] mmc0: sdhci: Power:     0x0000000f | Blk
gap:  0x00000000
[    3.282041] mmc0: sdhci: Wake-up:   0x00000000 |
Clock:    0x00000401
[    3.288485] mmc0: sdhci: Timeout:   0x00000000 | Int stat:
0x00000000
[    3.295037] mmc0: sdhci: Int enab:  0x00ff0003 | Sig enab:
0x00fc0003
[    3.301559] mmc0: sdhci: AC12 err:  0x00000000 | Slot int:
0x00000000
[    3.308022] mmc0: sdhci: Caps:      0x376fd080 |
Caps_1:   0x10000f70
[    3.314527] mmc0: sdhci: Cmd:       0x00000000 | Max curr:
0x00000000
[    3.321159] mmc0: sdhci: Resp[0]:   0x00000000 |
Resp[1]:  0x00000000
[    3.327642] mmc0: sdhci: Resp[2]:   0x00000000 |
Resp[3]:  0x00000000
[    3.334144] mmc0: sdhci: Host ctl2: 0x00000000
[    3.338613] mmc0: sdhci: ADMA Err:  0x00000000 | ADMA Ptr:
0x00000000
[    3.345110] mmc0: sdhci:
============================================

And it subsequently stalls waiting for interrupt for more than 8
seconds before continuing to mount the rootfs as follows (mmc2 being
the SDHCI instance of the eMMC):

[    4.874017] tegra-hdmi 54280000.hdmi: cannot set audio to 48000 Hz
at 297000000 Hz pixel clock
[   13.930136] mmc2: Timeout waiting for hardware interrupt.
[   13.935603] mmc2: sdhci: ============ SDHCI REGISTER DUMP
===========
[   13.942071] mmc2: sdhci: Sys addr:  0x00000000 |
Version:  0x00000303
[   13.948511] mmc2: sdhci: Blk size:  0x00007080 | Blk
cnt:  0x00000001
[   13.954948] mmc2: sdhci: Argument:  0x00000000 | Trn mode:
0x00000013
[   13.961385] mmc2: sdhci: Present:   0x01fb00f0 | Host ctl:
0x00000031
[   13.967821] mmc2: sdhci: Power:     0x00000001 | Blk
gap:  0x00000000
[   13.974263] mmc2: sdhci: Wake-up:   0x00000000 |
Clock:    0x00000007
[   13.980692] mmc2: sdhci: Timeout:   0x0000000e | Int stat:
0x00000000
[   13.987119] mmc2: sdhci: Int enab:  0x02ff000b | Sig enab:
0x02fc000b
[   13.993546] mmc2: sdhci: AC12 err:  0x00000000 | Slot int:
0x00000000
[   13.999974] mmc2: sdhci: Caps:      0x376fd080 |
Caps_1:   0x10000f70
[   14.006415] mmc2: sdhci: Cmd:       0x0000153a | Max curr:
0x00000000
[   14.012845] mmc2: sdhci: Resp[0]:   0x00000b00 |
Resp[1]:  0x048062bf
[   14.019272] mmc2: sdhci: Resp[2]:   0x314a8000 |
Resp[3]:  0x00000240
[   14.025697] mmc2: sdhci: Host ctl2: 0x0000000b
[   14.030132] mmc2: sdhci: ADMA Err:  0x00000000 | ADMA Ptr:
0xfbc6b208
[   14.036561] mmc2: sdhci:
============================================
[   14.044332] mmc2: new HS200 MMC card at address 0001
[   14.050656] mmcblk2: mmc2:0001 016G30 14.7 GiB
[   14.056376] mmcblk2boot0: mmc2:0001 016G30 partition 1 4.00 MiB
[   14.063563] mmcblk2boot1: mmc2:0001 016G30 partition 2 4.00 MiB
[   14.069589] mmcblk2rpmb: mmc2:0001 016G30 partition 3 4.00 MiB,
chardev (247:0)
[   14.078260]  mmcblk2: p1 p2

After that it actually seems to work quite nicely:

root@apalis-tk1-mainline:~# cat /sys/kernel/debug/mmc2/ios
clock:          200000000 Hz
actual clock:   163200000 Hz
vdd:            21 (3.3 ~ 3.4 V)
bus mode:       2 (push-pull)
chip select:    0 (don't care)
power mode:     2 (on)
bus width:      3 (8 bits)
timing spec:    9 (mmc HS200)
signal voltage: 1 (1.80 V)
driver type:    0 (driver type B)
root@apalis-tk1-mainline:~# hdparm -t /dev/mmcblk2

/dev/mmcblk2:
 Timing buffered disk reads: 408 MB in  3.01 seconds = 135.39 MB/sec

Have you ever observed similar behaviour? What could cause this?

Anybody else tried it on TK1?

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

* Re: [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling
  2018-08-27 14:10 ` Marcel Ziswiler
@ 2018-08-27 15:50   ` Thierry Reding
  2018-08-27 15:57     ` Thierry Reding
                       ` (2 more replies)
  0 siblings, 3 replies; 57+ messages in thread
From: Thierry Reding @ 2018-08-27 15:50 UTC (permalink / raw)
  To: Marcel Ziswiler, Aapo Vienamo
  Cc: robh+dt, jonathanh, mperttunen, stefan, mark.rutland,
	ulf.hansson, adrian.hunter, linux-kernel, linux-mmc, linux-tegra,
	devicetree

[-- Attachment #1: Type: text/plain, Size: 5948 bytes --]

On Mon, Aug 27, 2018 at 02:10:58PM +0000, Marcel Ziswiler wrote:
> On Fri, 2018-08-10 at 21:08 +0300, Aapo Vienamo wrote:
> > Hi all,
> > 
> > This series implements support for faster signaling modes on Tegra
> > SDHCI controllers. This series consist of several parts: changes
> > requried for 1.8 V signaling and pad control, pad calibration, and
> > tuning. Following earlies patch sets have been merged into this
> > larger set: "Tegra PMC pinctrl pad configuration", "Tegra SDHCI
> > enable
> > 1.8 V signaling on Tegar210 and Tegra186", "Tegra SDHCI update the
> > padautocal procedure". Also the patches for enabling SDHCI tuning
> > are added.
> 
> I tried your tkln/hs200 branch on Colibri T20, Apalis/Colibri T30 and
> Apalis TK1. It at least does not seem to make things any worse but
> HS200 on TK1 still seems to behave strangely. During boot I do get the
> following message (mmc0 being the SDHCI instance of one of them SD card
> slots):
> 
> [    3.238360] mmc0: Internal clock never stabilised.
> [    3.243183] mmc0: sdhci: ============ SDHCI REGISTER DUMP
> ===========
> [    3.249649] mmc0: sdhci: Sys addr:  0x00000000 |
> Version:  0x00000303
> [    3.256138] mmc0: sdhci: Blk size:  0x00000000 | Blk
> cnt:  0x00000000
> [    3.262657] mmc0: sdhci: Argument:  0x00000000 | Trn mode:
> 0x00000000
> [    3.269119] mmc0: sdhci: Present:   0x01fb00f0 | Host ctl:
> 0x00000000
> [    3.275580] mmc0: sdhci: Power:     0x0000000f | Blk
> gap:  0x00000000
> [    3.282041] mmc0: sdhci: Wake-up:   0x00000000 |
> Clock:    0x00000401
> [    3.288485] mmc0: sdhci: Timeout:   0x00000000 | Int stat:
> 0x00000000
> [    3.295037] mmc0: sdhci: Int enab:  0x00ff0003 | Sig enab:
> 0x00fc0003
> [    3.301559] mmc0: sdhci: AC12 err:  0x00000000 | Slot int:
> 0x00000000
> [    3.308022] mmc0: sdhci: Caps:      0x376fd080 |
> Caps_1:   0x10000f70
> [    3.314527] mmc0: sdhci: Cmd:       0x00000000 | Max curr:
> 0x00000000
> [    3.321159] mmc0: sdhci: Resp[0]:   0x00000000 |
> Resp[1]:  0x00000000
> [    3.327642] mmc0: sdhci: Resp[2]:   0x00000000 |
> Resp[3]:  0x00000000
> [    3.334144] mmc0: sdhci: Host ctl2: 0x00000000
> [    3.338613] mmc0: sdhci: ADMA Err:  0x00000000 | ADMA Ptr:
> 0x00000000
> [    3.345110] mmc0: sdhci:
> ============================================
> 
> And it subsequently stalls waiting for interrupt for more than 8
> seconds before continuing to mount the rootfs as follows (mmc2 being
> the SDHCI instance of the eMMC):
> 
> [    4.874017] tegra-hdmi 54280000.hdmi: cannot set audio to 48000 Hz
> at 297000000 Hz pixel clock
> [   13.930136] mmc2: Timeout waiting for hardware interrupt.
> [   13.935603] mmc2: sdhci: ============ SDHCI REGISTER DUMP
> ===========
> [   13.942071] mmc2: sdhci: Sys addr:  0x00000000 |
> Version:  0x00000303
> [   13.948511] mmc2: sdhci: Blk size:  0x00007080 | Blk
> cnt:  0x00000001
> [   13.954948] mmc2: sdhci: Argument:  0x00000000 | Trn mode:
> 0x00000013
> [   13.961385] mmc2: sdhci: Present:   0x01fb00f0 | Host ctl:
> 0x00000031
> [   13.967821] mmc2: sdhci: Power:     0x00000001 | Blk
> gap:  0x00000000
> [   13.974263] mmc2: sdhci: Wake-up:   0x00000000 |
> Clock:    0x00000007
> [   13.980692] mmc2: sdhci: Timeout:   0x0000000e | Int stat:
> 0x00000000
> [   13.987119] mmc2: sdhci: Int enab:  0x02ff000b | Sig enab:
> 0x02fc000b
> [   13.993546] mmc2: sdhci: AC12 err:  0x00000000 | Slot int:
> 0x00000000
> [   13.999974] mmc2: sdhci: Caps:      0x376fd080 |
> Caps_1:   0x10000f70
> [   14.006415] mmc2: sdhci: Cmd:       0x0000153a | Max curr:
> 0x00000000
> [   14.012845] mmc2: sdhci: Resp[0]:   0x00000b00 |
> Resp[1]:  0x048062bf
> [   14.019272] mmc2: sdhci: Resp[2]:   0x314a8000 |
> Resp[3]:  0x00000240
> [   14.025697] mmc2: sdhci: Host ctl2: 0x0000000b
> [   14.030132] mmc2: sdhci: ADMA Err:  0x00000000 | ADMA Ptr:
> 0xfbc6b208
> [   14.036561] mmc2: sdhci:
> ============================================
> [   14.044332] mmc2: new HS200 MMC card at address 0001
> [   14.050656] mmcblk2: mmc2:0001 016G30 14.7 GiB
> [   14.056376] mmcblk2boot0: mmc2:0001 016G30 partition 1 4.00 MiB
> [   14.063563] mmcblk2boot1: mmc2:0001 016G30 partition 2 4.00 MiB
> [   14.069589] mmcblk2rpmb: mmc2:0001 016G30 partition 3 4.00 MiB,
> chardev (247:0)
> [   14.078260]  mmcblk2: p1 p2
> 
> After that it actually seems to work quite nicely:
> 
> root@apalis-tk1-mainline:~# cat /sys/kernel/debug/mmc2/ios
> clock:          200000000 Hz
> actual clock:   163200000 Hz
> vdd:            21 (3.3 ~ 3.4 V)
> bus mode:       2 (push-pull)
> chip select:    0 (don't care)
> power mode:     2 (on)
> bus width:      3 (8 bits)
> timing spec:    9 (mmc HS200)
> signal voltage: 1 (1.80 V)
> driver type:    0 (driver type B)
> root@apalis-tk1-mainline:~# hdparm -t /dev/mmcblk2
> 
> /dev/mmcblk2:
>  Timing buffered disk reads: 408 MB in  3.01 seconds = 135.39 MB/sec
> 
> Have you ever observed similar behaviour? What could cause this?
> 
> Anybody else tried it on TK1?

I can't reproduce this on Jetson TK1. Things boot normally and I don't
see the controllers switch into HS200 for either eMMC or SD card.

Did you update the device tree to enable HS200 on Apalis?

Aapo, isn't there a mechanism to prevent HS200 on devices where it
hasn't explicitly been tested (and enabled)? I thought we had discussed
that this was going to depend on pinmux DTS entries, but I can't find
the actual code where any of that would be checked. I only see checking
NVQUIRK_NEEDS_PAD_CONTROL in tegra_sdhci_is_pad_and_regulator_valid(),
but since we don't enable that quirk on Tegra124, it would seem to me
that we always enable fast modes on boards that don't need pad control.
Is that really what we want?

Also, if the above is correct, then why am I not seeing faster modes
getting enabled on Jetson TK1?

Thierry

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 833 bytes --]

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

* Re: [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling
  2018-08-27 15:50   ` Thierry Reding
@ 2018-08-27 15:57     ` Thierry Reding
  2018-08-27 16:27     ` Aapo Vienamo
  2018-08-27 21:35     ` Marcel Ziswiler
  2 siblings, 0 replies; 57+ messages in thread
From: Thierry Reding @ 2018-08-27 15:57 UTC (permalink / raw)
  To: Marcel Ziswiler, Aapo Vienamo
  Cc: robh+dt, jonathanh, mperttunen, stefan, mark.rutland,
	ulf.hansson, adrian.hunter, linux-kernel, linux-mmc, linux-tegra,
	devicetree

[-- Attachment #1: Type: text/plain, Size: 7070 bytes --]

On Mon, Aug 27, 2018 at 05:50:53PM +0200, Thierry Reding wrote:
> On Mon, Aug 27, 2018 at 02:10:58PM +0000, Marcel Ziswiler wrote:
> > On Fri, 2018-08-10 at 21:08 +0300, Aapo Vienamo wrote:
> > > Hi all,
> > > 
> > > This series implements support for faster signaling modes on Tegra
> > > SDHCI controllers. This series consist of several parts: changes
> > > requried for 1.8 V signaling and pad control, pad calibration, and
> > > tuning. Following earlies patch sets have been merged into this
> > > larger set: "Tegra PMC pinctrl pad configuration", "Tegra SDHCI
> > > enable
> > > 1.8 V signaling on Tegar210 and Tegra186", "Tegra SDHCI update the
> > > padautocal procedure". Also the patches for enabling SDHCI tuning
> > > are added.
> > 
> > I tried your tkln/hs200 branch on Colibri T20, Apalis/Colibri T30 and
> > Apalis TK1. It at least does not seem to make things any worse but
> > HS200 on TK1 still seems to behave strangely. During boot I do get the
> > following message (mmc0 being the SDHCI instance of one of them SD card
> > slots):
> > 
> > [    3.238360] mmc0: Internal clock never stabilised.
> > [    3.243183] mmc0: sdhci: ============ SDHCI REGISTER DUMP
> > ===========
> > [    3.249649] mmc0: sdhci: Sys addr:  0x00000000 |
> > Version:  0x00000303
> > [    3.256138] mmc0: sdhci: Blk size:  0x00000000 | Blk
> > cnt:  0x00000000
> > [    3.262657] mmc0: sdhci: Argument:  0x00000000 | Trn mode:
> > 0x00000000
> > [    3.269119] mmc0: sdhci: Present:   0x01fb00f0 | Host ctl:
> > 0x00000000
> > [    3.275580] mmc0: sdhci: Power:     0x0000000f | Blk
> > gap:  0x00000000
> > [    3.282041] mmc0: sdhci: Wake-up:   0x00000000 |
> > Clock:    0x00000401
> > [    3.288485] mmc0: sdhci: Timeout:   0x00000000 | Int stat:
> > 0x00000000
> > [    3.295037] mmc0: sdhci: Int enab:  0x00ff0003 | Sig enab:
> > 0x00fc0003
> > [    3.301559] mmc0: sdhci: AC12 err:  0x00000000 | Slot int:
> > 0x00000000
> > [    3.308022] mmc0: sdhci: Caps:      0x376fd080 |
> > Caps_1:   0x10000f70
> > [    3.314527] mmc0: sdhci: Cmd:       0x00000000 | Max curr:
> > 0x00000000
> > [    3.321159] mmc0: sdhci: Resp[0]:   0x00000000 |
> > Resp[1]:  0x00000000
> > [    3.327642] mmc0: sdhci: Resp[2]:   0x00000000 |
> > Resp[3]:  0x00000000
> > [    3.334144] mmc0: sdhci: Host ctl2: 0x00000000
> > [    3.338613] mmc0: sdhci: ADMA Err:  0x00000000 | ADMA Ptr:
> > 0x00000000
> > [    3.345110] mmc0: sdhci:
> > ============================================
> > 
> > And it subsequently stalls waiting for interrupt for more than 8
> > seconds before continuing to mount the rootfs as follows (mmc2 being
> > the SDHCI instance of the eMMC):
> > 
> > [    4.874017] tegra-hdmi 54280000.hdmi: cannot set audio to 48000 Hz
> > at 297000000 Hz pixel clock
> > [   13.930136] mmc2: Timeout waiting for hardware interrupt.
> > [   13.935603] mmc2: sdhci: ============ SDHCI REGISTER DUMP
> > ===========
> > [   13.942071] mmc2: sdhci: Sys addr:  0x00000000 |
> > Version:  0x00000303
> > [   13.948511] mmc2: sdhci: Blk size:  0x00007080 | Blk
> > cnt:  0x00000001
> > [   13.954948] mmc2: sdhci: Argument:  0x00000000 | Trn mode:
> > 0x00000013
> > [   13.961385] mmc2: sdhci: Present:   0x01fb00f0 | Host ctl:
> > 0x00000031
> > [   13.967821] mmc2: sdhci: Power:     0x00000001 | Blk
> > gap:  0x00000000
> > [   13.974263] mmc2: sdhci: Wake-up:   0x00000000 |
> > Clock:    0x00000007
> > [   13.980692] mmc2: sdhci: Timeout:   0x0000000e | Int stat:
> > 0x00000000
> > [   13.987119] mmc2: sdhci: Int enab:  0x02ff000b | Sig enab:
> > 0x02fc000b
> > [   13.993546] mmc2: sdhci: AC12 err:  0x00000000 | Slot int:
> > 0x00000000
> > [   13.999974] mmc2: sdhci: Caps:      0x376fd080 |
> > Caps_1:   0x10000f70
> > [   14.006415] mmc2: sdhci: Cmd:       0x0000153a | Max curr:
> > 0x00000000
> > [   14.012845] mmc2: sdhci: Resp[0]:   0x00000b00 |
> > Resp[1]:  0x048062bf
> > [   14.019272] mmc2: sdhci: Resp[2]:   0x314a8000 |
> > Resp[3]:  0x00000240
> > [   14.025697] mmc2: sdhci: Host ctl2: 0x0000000b
> > [   14.030132] mmc2: sdhci: ADMA Err:  0x00000000 | ADMA Ptr:
> > 0xfbc6b208
> > [   14.036561] mmc2: sdhci:
> > ============================================
> > [   14.044332] mmc2: new HS200 MMC card at address 0001
> > [   14.050656] mmcblk2: mmc2:0001 016G30 14.7 GiB
> > [   14.056376] mmcblk2boot0: mmc2:0001 016G30 partition 1 4.00 MiB
> > [   14.063563] mmcblk2boot1: mmc2:0001 016G30 partition 2 4.00 MiB
> > [   14.069589] mmcblk2rpmb: mmc2:0001 016G30 partition 3 4.00 MiB,
> > chardev (247:0)
> > [   14.078260]  mmcblk2: p1 p2
> > 
> > After that it actually seems to work quite nicely:
> > 
> > root@apalis-tk1-mainline:~# cat /sys/kernel/debug/mmc2/ios
> > clock:          200000000 Hz
> > actual clock:   163200000 Hz
> > vdd:            21 (3.3 ~ 3.4 V)
> > bus mode:       2 (push-pull)
> > chip select:    0 (don't care)
> > power mode:     2 (on)
> > bus width:      3 (8 bits)
> > timing spec:    9 (mmc HS200)
> > signal voltage: 1 (1.80 V)
> > driver type:    0 (driver type B)
> > root@apalis-tk1-mainline:~# hdparm -t /dev/mmcblk2
> > 
> > /dev/mmcblk2:
> >  Timing buffered disk reads: 408 MB in  3.01 seconds = 135.39 MB/sec
> > 
> > Have you ever observed similar behaviour? What could cause this?
> > 
> > Anybody else tried it on TK1?
> 
> I can't reproduce this on Jetson TK1. Things boot normally and I don't
> see the controllers switch into HS200 for either eMMC or SD card.
> 
> Did you update the device tree to enable HS200 on Apalis?
> 
> Aapo, isn't there a mechanism to prevent HS200 on devices where it
> hasn't explicitly been tested (and enabled)? I thought we had discussed
> that this was going to depend on pinmux DTS entries, but I can't find
> the actual code where any of that would be checked. I only see checking
> NVQUIRK_NEEDS_PAD_CONTROL in tegra_sdhci_is_pad_and_regulator_valid(),
> but since we don't enable that quirk on Tegra124, it would seem to me
> that we always enable fast modes on boards that don't need pad control.
> Is that really what we want?
> 
> Also, if the above is correct, then why am I not seeing faster modes
> getting enabled on Jetson TK1?

I also just ran into what seems to be a typo. Do we want the below fix?

diff --git a/drivers/mmc/host/sdhci-tegra.c b/drivers/mmc/host/sdhci-tegra.c
index ef18a0c6ed3a..a6053e5004da 100644
--- a/drivers/mmc/host/sdhci-tegra.c
+++ b/drivers/mmc/host/sdhci-tegra.c
@@ -336,7 +336,7 @@ static void tegra_sdhci_reset(struct sdhci_host *host, u8 mask)
                        misc_ctrl |= SDHCI_MISC_CTRL_ENABLE_DDR50;
                if (soc_data->nvquirks & NVQUIRK_ENABLE_SDR104)
                        misc_ctrl |= SDHCI_MISC_CTRL_ENABLE_SDR104;
-               if (soc_data->nvquirks & SDHCI_MISC_CTRL_ENABLE_SDR50)
+               if (soc_data->nvquirks & NVQUIRK_ENABLE_SDR50)
                        clk_ctrl |= SDHCI_CLOCK_CTRL_SDR50_TUNING_OVERRIDE;
        }
 

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 833 bytes --]

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

* Re: [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling
  2018-08-27 15:50   ` Thierry Reding
  2018-08-27 15:57     ` Thierry Reding
@ 2018-08-27 16:27     ` Aapo Vienamo
  2018-08-27 21:35     ` Marcel Ziswiler
  2 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-27 16:27 UTC (permalink / raw)
  To: Thierry Reding
  Cc: Marcel Ziswiler, robh+dt, jonathanh, mperttunen, stefan,
	mark.rutland, ulf.hansson, adrian.hunter, linux-kernel,
	linux-mmc, linux-tegra, devicetree

On Mon, 27 Aug 2018 17:50:53 +0200
Thierry Reding <thierry.reding@gmail.com> wrote:

> On Mon, Aug 27, 2018 at 02:10:58PM +0000, Marcel Ziswiler wrote:
> > On Fri, 2018-08-10 at 21:08 +0300, Aapo Vienamo wrote:  
> > > Hi all,
> > > 
> > > This series implements support for faster signaling modes on Tegra
> > > SDHCI controllers. This series consist of several parts: changes
> > > requried for 1.8 V signaling and pad control, pad calibration, and
> > > tuning. Following earlies patch sets have been merged into this
> > > larger set: "Tegra PMC pinctrl pad configuration", "Tegra SDHCI
> > > enable
> > > 1.8 V signaling on Tegar210 and Tegra186", "Tegra SDHCI update the
> > > padautocal procedure". Also the patches for enabling SDHCI tuning
> > > are added.  
> > 
> > I tried your tkln/hs200 branch on Colibri T20, Apalis/Colibri T30 and
> > Apalis TK1. It at least does not seem to make things any worse but
> > HS200 on TK1 still seems to behave strangely. During boot I do get the
> > following message (mmc0 being the SDHCI instance of one of them SD card
> > slots):
> > 
> > [    3.238360] mmc0: Internal clock never stabilised.
> > [    3.243183] mmc0: sdhci: ============ SDHCI REGISTER DUMP
> > ===========
> > [    3.249649] mmc0: sdhci: Sys addr:  0x00000000 |
> > Version:  0x00000303
> > [    3.256138] mmc0: sdhci: Blk size:  0x00000000 | Blk
> > cnt:  0x00000000
> > [    3.262657] mmc0: sdhci: Argument:  0x00000000 | Trn mode:
> > 0x00000000
> > [    3.269119] mmc0: sdhci: Present:   0x01fb00f0 | Host ctl:
> > 0x00000000
> > [    3.275580] mmc0: sdhci: Power:     0x0000000f | Blk
> > gap:  0x00000000
> > [    3.282041] mmc0: sdhci: Wake-up:   0x00000000 |
> > Clock:    0x00000401
> > [    3.288485] mmc0: sdhci: Timeout:   0x00000000 | Int stat:
> > 0x00000000
> > [    3.295037] mmc0: sdhci: Int enab:  0x00ff0003 | Sig enab:
> > 0x00fc0003
> > [    3.301559] mmc0: sdhci: AC12 err:  0x00000000 | Slot int:
> > 0x00000000
> > [    3.308022] mmc0: sdhci: Caps:      0x376fd080 |
> > Caps_1:   0x10000f70
> > [    3.314527] mmc0: sdhci: Cmd:       0x00000000 | Max curr:
> > 0x00000000
> > [    3.321159] mmc0: sdhci: Resp[0]:   0x00000000 |
> > Resp[1]:  0x00000000
> > [    3.327642] mmc0: sdhci: Resp[2]:   0x00000000 |
> > Resp[3]:  0x00000000
> > [    3.334144] mmc0: sdhci: Host ctl2: 0x00000000
> > [    3.338613] mmc0: sdhci: ADMA Err:  0x00000000 | ADMA Ptr:
> > 0x00000000
> > [    3.345110] mmc0: sdhci:
> > ============================================
> > 
> > And it subsequently stalls waiting for interrupt for more than 8
> > seconds before continuing to mount the rootfs as follows (mmc2 being
> > the SDHCI instance of the eMMC):
> > 
> > [    4.874017] tegra-hdmi 54280000.hdmi: cannot set audio to 48000 Hz
> > at 297000000 Hz pixel clock
> > [   13.930136] mmc2: Timeout waiting for hardware interrupt.
> > [   13.935603] mmc2: sdhci: ============ SDHCI REGISTER DUMP
> > ===========
> > [   13.942071] mmc2: sdhci: Sys addr:  0x00000000 |
> > Version:  0x00000303
> > [   13.948511] mmc2: sdhci: Blk size:  0x00007080 | Blk
> > cnt:  0x00000001
> > [   13.954948] mmc2: sdhci: Argument:  0x00000000 | Trn mode:
> > 0x00000013
> > [   13.961385] mmc2: sdhci: Present:   0x01fb00f0 | Host ctl:
> > 0x00000031
> > [   13.967821] mmc2: sdhci: Power:     0x00000001 | Blk
> > gap:  0x00000000
> > [   13.974263] mmc2: sdhci: Wake-up:   0x00000000 |
> > Clock:    0x00000007
> > [   13.980692] mmc2: sdhci: Timeout:   0x0000000e | Int stat:
> > 0x00000000
> > [   13.987119] mmc2: sdhci: Int enab:  0x02ff000b | Sig enab:
> > 0x02fc000b
> > [   13.993546] mmc2: sdhci: AC12 err:  0x00000000 | Slot int:
> > 0x00000000
> > [   13.999974] mmc2: sdhci: Caps:      0x376fd080 |
> > Caps_1:   0x10000f70
> > [   14.006415] mmc2: sdhci: Cmd:       0x0000153a | Max curr:
> > 0x00000000
> > [   14.012845] mmc2: sdhci: Resp[0]:   0x00000b00 |
> > Resp[1]:  0x048062bf
> > [   14.019272] mmc2: sdhci: Resp[2]:   0x314a8000 |
> > Resp[3]:  0x00000240
> > [   14.025697] mmc2: sdhci: Host ctl2: 0x0000000b
> > [   14.030132] mmc2: sdhci: ADMA Err:  0x00000000 | ADMA Ptr:
> > 0xfbc6b208
> > [   14.036561] mmc2: sdhci:
> > ============================================
> > [   14.044332] mmc2: new HS200 MMC card at address 0001
> > [   14.050656] mmcblk2: mmc2:0001 016G30 14.7 GiB
> > [   14.056376] mmcblk2boot0: mmc2:0001 016G30 partition 1 4.00 MiB
> > [   14.063563] mmcblk2boot1: mmc2:0001 016G30 partition 2 4.00 MiB
> > [   14.069589] mmcblk2rpmb: mmc2:0001 016G30 partition 3 4.00 MiB,
> > chardev (247:0)
> > [   14.078260]  mmcblk2: p1 p2
> > 
> > After that it actually seems to work quite nicely:
> > 
> > root@apalis-tk1-mainline:~# cat /sys/kernel/debug/mmc2/ios
> > clock:          200000000 Hz
> > actual clock:   163200000 Hz
> > vdd:            21 (3.3 ~ 3.4 V)
> > bus mode:       2 (push-pull)
> > chip select:    0 (don't care)
> > power mode:     2 (on)
> > bus width:      3 (8 bits)
> > timing spec:    9 (mmc HS200)
> > signal voltage: 1 (1.80 V)
> > driver type:    0 (driver type B)
> > root@apalis-tk1-mainline:~# hdparm -t /dev/mmcblk2
> > 
> > /dev/mmcblk2:
> >  Timing buffered disk reads: 408 MB in  3.01 seconds = 135.39 MB/sec
> > 
> > Have you ever observed similar behaviour? What could cause this?
> > 
> > Anybody else tried it on TK1?  
> 
> I can't reproduce this on Jetson TK1. Things boot normally and I don't
> see the controllers switch into HS200 for either eMMC or SD card.
> 
> Did you update the device tree to enable HS200 on Apalis?
> 
> Aapo, isn't there a mechanism to prevent HS200 on devices where it
> hasn't explicitly been tested (and enabled)? I thought we had discussed
> that this was going to depend on pinmux DTS entries, but I can't find
> the actual code where any of that would be checked. I only see checking
> NVQUIRK_NEEDS_PAD_CONTROL in tegra_sdhci_is_pad_and_regulator_valid(),
> but since we don't enable that quirk on Tegra124, it would seem to me
> that we always enable fast modes on boards that don't need pad control.
> Is that really what we want?

The HS200 mode is enabled by setting NVQUIRK_ENABLE_SDR104 in nvquirks.
This quirk bit shouldn't be currently set on Tegra124.

> Also, if the above is correct, then why am I not seeing faster modes
> getting enabled on Jetson TK1?

I spent last week looking into it. One really weird issue I found was
that when the tuning command is sent, the timeout in sdhci_send_tuning()
sometimes expires. This seems to happen only on certain SD cards and
only if the tap values are modified faster than 10 ms apart. 10 ms is a
really long time which makes this really weird.

Downstream has reimplemented a register polling version of
mmc_send_tuning(), supposedly to avoid interrupt overheads, which oddly
enough seems to work.

 -Aapo

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

* Re: [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling
  2018-08-27 15:50   ` Thierry Reding
  2018-08-27 15:57     ` Thierry Reding
  2018-08-27 16:27     ` Aapo Vienamo
@ 2018-08-27 21:35     ` Marcel Ziswiler
  2 siblings, 0 replies; 57+ messages in thread
From: Marcel Ziswiler @ 2018-08-27 21:35 UTC (permalink / raw)
  To: avienamo, thierry.reding
  Cc: linux-kernel, robh+dt, jonathanh, stefan, linux-mmc, mperttunen,
	devicetree, mark.rutland, ulf.hansson, linux-tegra,
	adrian.hunter

On Mon, 2018-08-27 at 17:50 +0200, Thierry Reding wrote:
> On Mon, Aug 27, 2018 at 02:10:58PM +0000, Marcel Ziswiler wrote:
> > On Fri, 2018-08-10 at 21:08 +0300, Aapo Vienamo wrote:
> > > Hi all,
> > > 
> > > This series implements support for faster signaling modes on
> > > Tegra
> > > SDHCI controllers. This series consist of several parts: changes
> > > requried for 1.8 V signaling and pad control, pad calibration,
> > > and
> > > tuning. Following earlies patch sets have been merged into this
> > > larger set: "Tegra PMC pinctrl pad configuration", "Tegra SDHCI
> > > enable
> > > 1.8 V signaling on Tegar210 and Tegra186", "Tegra SDHCI update
> > > the
> > > padautocal procedure". Also the patches for enabling SDHCI tuning
> > > are added.
> > 
> > I tried your tkln/hs200 branch on Colibri T20, Apalis/Colibri T30
> > and
> > Apalis TK1. It at least does not seem to make things any worse but
> > HS200 on TK1 still seems to behave strangely. During boot I do get
> > the
> > following message (mmc0 being the SDHCI instance of one of them SD
> > card
> > slots):
> > 
> > [    3.238360] mmc0: Internal clock never stabilised.
> > [    3.243183] mmc0: sdhci: ============ SDHCI REGISTER DUMP
> > ===========
> > [    3.249649] mmc0: sdhci: Sys addr:  0x00000000 |
> > Version:  0x00000303
> > [    3.256138] mmc0: sdhci: Blk size:  0x00000000 | Blk
> > cnt:  0x00000000
> > [    3.262657] mmc0: sdhci: Argument:  0x00000000 | Trn mode:
> > 0x00000000
> > [    3.269119] mmc0: sdhci: Present:   0x01fb00f0 | Host ctl:
> > 0x00000000
> > [    3.275580] mmc0: sdhci: Power:     0x0000000f | Blk
> > gap:  0x00000000
> > [    3.282041] mmc0: sdhci: Wake-up:   0x00000000 |
> > Clock:    0x00000401
> > [    3.288485] mmc0: sdhci: Timeout:   0x00000000 | Int stat:
> > 0x00000000
> > [    3.295037] mmc0: sdhci: Int enab:  0x00ff0003 | Sig enab:
> > 0x00fc0003
> > [    3.301559] mmc0: sdhci: AC12 err:  0x00000000 | Slot int:
> > 0x00000000
> > [    3.308022] mmc0: sdhci: Caps:      0x376fd080 |
> > Caps_1:   0x10000f70
> > [    3.314527] mmc0: sdhci: Cmd:       0x00000000 | Max curr:
> > 0x00000000
> > [    3.321159] mmc0: sdhci: Resp[0]:   0x00000000 |
> > Resp[1]:  0x00000000
> > [    3.327642] mmc0: sdhci: Resp[2]:   0x00000000 |
> > Resp[3]:  0x00000000
> > [    3.334144] mmc0: sdhci: Host ctl2: 0x00000000
> > [    3.338613] mmc0: sdhci: ADMA Err:  0x00000000 | ADMA Ptr:
> > 0x00000000
> > [    3.345110] mmc0: sdhci:
> > ============================================
> > 
> > And it subsequently stalls waiting for interrupt for more than 8
> > seconds before continuing to mount the rootfs as follows (mmc2
> > being
> > the SDHCI instance of the eMMC):
> > 
> > [    4.874017] tegra-hdmi 54280000.hdmi: cannot set audio to 48000
> > Hz
> > at 297000000 Hz pixel clock
> > [   13.930136] mmc2: Timeout waiting for hardware interrupt.
> > [   13.935603] mmc2: sdhci: ============ SDHCI REGISTER DUMP
> > ===========
> > [   13.942071] mmc2: sdhci: Sys addr:  0x00000000 |
> > Version:  0x00000303
> > [   13.948511] mmc2: sdhci: Blk size:  0x00007080 | Blk
> > cnt:  0x00000001
> > [   13.954948] mmc2: sdhci: Argument:  0x00000000 | Trn mode:
> > 0x00000013
> > [   13.961385] mmc2: sdhci: Present:   0x01fb00f0 | Host ctl:
> > 0x00000031
> > [   13.967821] mmc2: sdhci: Power:     0x00000001 | Blk
> > gap:  0x00000000
> > [   13.974263] mmc2: sdhci: Wake-up:   0x00000000 |
> > Clock:    0x00000007
> > [   13.980692] mmc2: sdhci: Timeout:   0x0000000e | Int stat:
> > 0x00000000
> > [   13.987119] mmc2: sdhci: Int enab:  0x02ff000b | Sig enab:
> > 0x02fc000b
> > [   13.993546] mmc2: sdhci: AC12 err:  0x00000000 | Slot int:
> > 0x00000000
> > [   13.999974] mmc2: sdhci: Caps:      0x376fd080 |
> > Caps_1:   0x10000f70
> > [   14.006415] mmc2: sdhci: Cmd:       0x0000153a | Max curr:
> > 0x00000000
> > [   14.012845] mmc2: sdhci: Resp[0]:   0x00000b00 |
> > Resp[1]:  0x048062bf
> > [   14.019272] mmc2: sdhci: Resp[2]:   0x314a8000 |
> > Resp[3]:  0x00000240
> > [   14.025697] mmc2: sdhci: Host ctl2: 0x0000000b
> > [   14.030132] mmc2: sdhci: ADMA Err:  0x00000000 | ADMA Ptr:
> > 0xfbc6b208
> > [   14.036561] mmc2: sdhci:
> > ============================================
> > [   14.044332] mmc2: new HS200 MMC card at address 0001
> > [   14.050656] mmcblk2: mmc2:0001 016G30 14.7 GiB
> > [   14.056376] mmcblk2boot0: mmc2:0001 016G30 partition 1 4.00 MiB
> > [   14.063563] mmcblk2boot1: mmc2:0001 016G30 partition 2 4.00 MiB
> > [   14.069589] mmcblk2rpmb: mmc2:0001 016G30 partition 3 4.00 MiB,
> > chardev (247:0)
> > [   14.078260]  mmcblk2: p1 p2
> > 
> > After that it actually seems to work quite nicely:
> > 
> > root@apalis-tk1-mainline:~# cat /sys/kernel/debug/mmc2/ios
> > clock:          200000000 Hz
> > actual clock:   163200000 Hz
> > vdd:            21 (3.3 ~ 3.4 V)
> > bus mode:       2 (push-pull)
> > chip select:    0 (don't care)
> > power mode:     2 (on)
> > bus width:      3 (8 bits)
> > timing spec:    9 (mmc HS200)
> > signal voltage: 1 (1.80 V)
> > driver type:    0 (driver type B)
> > root@apalis-tk1-mainline:~# hdparm -t /dev/mmcblk2
> > 
> > /dev/mmcblk2:
> >  Timing buffered disk reads: 408 MB in  3.01 seconds = 135.39
> > MB/sec
> > 
> > Have you ever observed similar behaviour? What could cause this?
> > 
> > Anybody else tried it on TK1?
> 
> I can't reproduce this on Jetson TK1. Things boot normally and I
> don't
> see the controllers switch into HS200 for either eMMC or SD card.
> 
> Did you update the device tree to enable HS200 on Apalis?

Yes, sorry. I forgot to mention that I added the mmc-hs200-1_8v
property to my eMMC's sdhci node.

> Aapo, isn't there a mechanism to prevent HS200 on devices where it
> hasn't explicitly been tested (and enabled)? I thought we had
> discussed
> that this was going to depend on pinmux DTS entries, but I can't find
> the actual code where any of that would be checked. I only see
> checking
> NVQUIRK_NEEDS_PAD_CONTROL in
> tegra_sdhci_is_pad_and_regulator_valid(),
> but since we don't enable that quirk on Tegra124, it would seem to me
> that we always enable fast modes on boards that don't need pad
> control.
> Is that really what we want?
> 
> Also, if the above is correct, then why am I not seeing faster modes
> getting enabled on Jetson TK1?
> 
> Thierry

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

* Re: [PATCH v2 11/40] mmc: sdhci: Add a quirk to skip clearing the transfer mode register on tuning
  2018-08-27 11:01   ` Adrian Hunter
@ 2018-08-28 14:45     ` Aapo Vienamo
  0 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-28 14:45 UTC (permalink / raw)
  To: Adrian Hunter
  Cc: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Mikko Perttunen, Stefan Agner, devicetree,
	linux-tegra, linux-kernel, linux-mmc

On Mon, 27 Aug 2018 14:01:52 +0300
Adrian Hunter <adrian.hunter@intel.com> wrote:

> On 10/08/18 21:08, Aapo Vienamo wrote:
> > Add SDHCI_QUIRK2_TUNE_SKIP_XFERRMODE_REG_PROG to skip programming the
> > SDHCI_TRANSFER_MODE in sdhci_set_transfer_mode() if tuning command is
> > being sent.
> > 
> > On Tegra210 and Tegra186 the tuning sequence hangs if the SDHCI
> > transfer mode register is touched.
> > 
> > Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
> > ---
> >  drivers/mmc/host/sdhci.c | 6 ++++++
> >  drivers/mmc/host/sdhci.h | 2 ++
> >  2 files changed, 8 insertions(+)
> > 
> > diff --git a/drivers/mmc/host/sdhci.c b/drivers/mmc/host/sdhci.c
> > index a7b5602..04dc443 100644
> > --- a/drivers/mmc/host/sdhci.c
> > +++ b/drivers/mmc/host/sdhci.c
> > @@ -1028,6 +1028,12 @@ static void sdhci_set_transfer_mode(struct sdhci_host *host,
> >  
> >  	if (data == NULL) {
> >  		if (host->quirks2 &
> > +			SDHCI_QUIRK2_TUNE_SKIP_XFERMODE_REG_PROG &&
> > +				(cmd->opcode == MMC_SEND_TUNING_BLOCK ||
> > +				 cmd->opcode == MMC_SEND_TUNING_BLOCK_HS200)) {
> > +			return;
> > +		}  
> 
> Rather than introduce a quirk, can't we just dodge the unnecessary write e.g.
> 
> diff --git a/drivers/mmc/host/sdhci.c b/drivers/mmc/host/sdhci.c
> index 1b3fbd9bd5c5..68af6a67e397 100644
> --- a/drivers/mmc/host/sdhci.c
> +++ b/drivers/mmc/host/sdhci.c
> @@ -1033,10 +1033,19 @@ static void sdhci_set_transfer_mode(struct sdhci_host *host,
>  			if (cmd->opcode != MMC_SEND_TUNING_BLOCK_HS200)
>  				sdhci_writew(host, 0x0, SDHCI_TRANSFER_MODE);
>  		} else {
> -		/* clear Auto CMD settings for no data CMDs */
> +			u16 orig;
> +
> +			/* clear Auto CMD settings for no data CMDs */
>  			mode = sdhci_readw(host, SDHCI_TRANSFER_MODE);
> -			sdhci_writew(host, mode & ~(SDHCI_TRNS_AUTO_CMD12 |
> -				SDHCI_TRNS_AUTO_CMD23), SDHCI_TRANSFER_MODE);
> +			orig = mode;
> +			mode &= ~(SDHCI_TRNS_AUTO_CMD12 | SDHCI_TRNS_AUTO_CMD23);
> +			/*
> +			 * Do not write transfer mode unnecessarily because it
> +			 * can upset some host controllers (e.g. sdhci-tregra)
> +			 * during tuning.
> +			 */
> +			if (mode != orig)
> +				sdhci_writew(host, new_mode, SDHCI_TRANSFER_MODE);
>  		}
>  		return;
>  	}
> 
> 
> Alternatively 
> 
> > +		if (host->quirks2 &
> >  			SDHCI_QUIRK2_CLEAR_TRANSFERMODE_REG_BEFORE_CMD) {
> >  			sdhci_writew(host, 0x0, SDHCI_TRANSFER_MODE);
> >  		} else {
> > diff --git a/drivers/mmc/host/sdhci.h b/drivers/mmc/host/sdhci.h
> > index 23966f8..0a99008 100644
> > --- a/drivers/mmc/host/sdhci.h
> > +++ b/drivers/mmc/host/sdhci.h
> > @@ -450,6 +450,8 @@ struct sdhci_host {
> >   * obtainable timeout.
> >   */
> >  #define SDHCI_QUIRK2_DISABLE_HW_TIMEOUT			(1<<17)
> > +/* Don't clear the SDHCI_TRANSFER_MODE register on tuning commands */
> > +#define SDHCI_QUIRK2_TUNE_SKIP_XFERMODE_REG_PROG	(1<<18)
> >  
> >  	int irq;		/* Device IRQ */
> >  	void __iomem *ioaddr;	/* Mapped address */
> >   
> 

Looks like writes to the transfer mode register are deferred until the
command register is written by tegra_sdhci_writew(). This code was
introduced due to a quirk in Tegra114/124. The Tegra114 ops struct was
probably just copied over when support for Tegra210 was added, so we
end up with this code also getting run on Tegra210.

The issue with tegra_sdhci_writew() is that it breaks successive
read-modify-write operations. The value written to the transfer mode
register isn't returned on read until the command register is also
touched. Removing the write_w accessor from tegra210_sdhci_ops seems to
make the issue originally addressed by this patch to go away.

 -Aapo

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

* Re: [PATCH v2 25/40] mmc: sdhci: Add a quirk to disable card clock during tuning
  2018-08-27 11:25   ` Adrian Hunter
@ 2018-08-28 15:41     ` Aapo Vienamo
  0 siblings, 0 replies; 57+ messages in thread
From: Aapo Vienamo @ 2018-08-28 15:41 UTC (permalink / raw)
  To: Adrian Hunter
  Cc: Rob Herring, Mark Rutland, Thierry Reding, Jonathan Hunter,
	Ulf Hansson, Mikko Perttunen, Stefan Agner, devicetree,
	linux-tegra, linux-kernel, linux-mmc

On Mon, 27 Aug 2018 14:25:44 +0300
Adrian Hunter <adrian.hunter@intel.com> wrote:

> On 10/08/18 21:08, Aapo Vienamo wrote:
> > Add a quirk to disable card clock when the tuning command is sent.
> > 
> > This has to be done to prevent the SDHCI controller from hanging on
> > Tegra210. Without the quirk enabled there appears to be around 10%
> > chance that the tuning sequence will fail and time out due to the
> > controller locking up.
> > 
> > Signed-off-by: Aapo Vienamo <avienamo@nvidia.com>
> > ---
> >  drivers/mmc/host/sdhci.c | 15 +++++++++++++++
> >  drivers/mmc/host/sdhci.h |  2 ++
> >  2 files changed, 17 insertions(+)
> > 
> > diff --git a/drivers/mmc/host/sdhci.c b/drivers/mmc/host/sdhci.c
> > index 04dc443..166b16f 100644
> > --- a/drivers/mmc/host/sdhci.c
> > +++ b/drivers/mmc/host/sdhci.c
> > @@ -2175,6 +2175,7 @@ static void sdhci_send_tuning(struct sdhci_host *host, u32 opcode)
> >  	struct mmc_request mrq = {};
> >  	unsigned long flags;
> >  	u32 b = host->sdma_boundary;
> > +	u16 clk;
> >  
> >  	spin_lock_irqsave(&host->lock, flags);
> >  
> > @@ -2183,6 +2184,13 @@ static void sdhci_send_tuning(struct sdhci_host *host, u32 opcode)
> >  	cmd.mrq = &mrq;
> >  
> >  	mrq.cmd = &cmd;
> > +
> > +	if (host->quirks2 & SDHCI_QUIRK2_TUNE_DIS_CARD_CLK) {
> > +		clk = sdhci_readw(host, SDHCI_CLOCK_CONTROL);
> > +		clk &= ~SDHCI_CLOCK_CARD_EN;
> > +		sdhci_writew(host, clk, SDHCI_CLOCK_CONTROL);  
> 
> Rather than using a quirk, could you use the sdhci I/O accessors to disable
> the clock before the tuning comment is written, udelay(1), and then enable
> it again?

This was the way it was implemented in the downstream kernel. However,
doing it in the IO accessor when a tuning command is sent seems to work
too.

 -Aapo

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

end of thread, other threads:[~2018-08-28 15:41 UTC | newest]

Thread overview: 57+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2018-08-10 18:08 [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 01/40] dt-bindings: Add Tegra PMC pad configuration bindings Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 02/40] dt-bindings: mmc: tegra: Add pad voltage control properties Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 03/40] dt-bindings: Add Tegra SDHCI pad pdpu offset bindings Aapo Vienamo
2018-08-13 19:24   ` Rob Herring
2018-08-10 18:08 ` [PATCH v2 04/40] dt-bindings: mmc: Add Tegra SDHCI sampling trimmer values Aapo Vienamo
2018-08-13 19:25   ` Rob Herring
2018-08-10 18:08 ` [PATCH v2 05/40] soc/tegra: pmc: Fix pad voltage configuration for Tegra186 Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 06/40] soc/tegra: pmc: Factor out DPD register bit calculation Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 07/40] soc/tegra: pmc: Implement tegra_io_pad_is_powered() Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 08/40] soc/tegra: pmc: Use X macro to generate IO pad tables Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 09/40] soc/tegra: pmc: Remove public pad voltage APIs Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 10/40] soc/tegra: pmc: Implement pad configuration via pinctrl Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 11/40] mmc: sdhci: Add a quirk to skip clearing the transfer mode register on tuning Aapo Vienamo
2018-08-27 11:01   ` Adrian Hunter
2018-08-28 14:45     ` Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 12/40] mmc: tegra: Reconfigure pad voltages during voltage switching Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 13/40] mmc: tegra: Poll for calibration completion Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 14/40] mmc: tegra: Set calibration pad voltage reference Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 15/40] mmc: tegra: Power on the calibration pad Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 16/40] mmc: tegra: Disable card clock during pad calibration Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 17/40] mmc: tegra: Program pad autocal offsets from dt Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 18/40] mmc: tegra: Perform pad calibration after voltage switch Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 19/40] mmc: tegra: Enable pad calibration on Tegra210 and Tegra186 Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 20/40] mmc: tegra: Add a workaround for tap value change glitch Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 21/40] mmc: tegra: Parse default trim and tap from dt Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 22/40] mmc: tegra: Configure default tap values Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 23/40] mmc: tegra: Configure default trim value on reset Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 24/40] mmc: tegra: Use standard SDHCI tuning on Tegra210 and Tegra186 Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 25/40] mmc: sdhci: Add a quirk to disable card clock during tuning Aapo Vienamo
2018-08-27 11:25   ` Adrian Hunter
2018-08-28 15:41     ` Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 26/40] mmc: tegra: Enable workaround for tuning transfer mode bug Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 27/40] mmc: tegra: Set SDHCI_QUIRK2_TUNE_DIS_CARD_CLK on Tegra210 Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 28/40] mmc: tegra: Enable UHS and HS200 modes for Tegra210 Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 29/40] mmc: tegra: Enable UHS and HS200 modes for Tegra186 Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 30/40] arm64: dts: Add Tegra210 sdmmc pinctrl voltage states Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 31/40] arm64: dts: Add Tegra186 " Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 32/40] arm64: dts: tegra210-p2180: Allow ldo2 to go down to 1.8 V Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 33/40] arm64: dts: tegra210-p2180: Correct sdmmc4 vqmmc-supply Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 34/40] arm64: dts: tegra210-p2597: Remove no-1-8-v from sdmmc1 Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 35/40] arm64: dts: tegra186: Add sdmmc pad auto calibration offsets Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 36/40] arm64: dts: tegra210: " Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 37/40] arm64: dts: tegra210: Add SDHCI tap and trim values Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 38/40] arm64: dts: tegra186: " Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 39/40] arm64: dts: tegra186: Assign clocks for sdmmc1 and sdmmc4 Aapo Vienamo
2018-08-10 18:08 ` [PATCH v2 40/40] arm64: dts: tegra210: " Aapo Vienamo
2018-08-23  8:47 ` [PATCH v2 00/40] Tegra SDHCI add support for HS200 and UHS signaling Thierry Reding
2018-08-23 10:42   ` Ulf Hansson
2018-08-27 10:10 ` Thierry Reding
2018-08-27 10:26   ` Adrian Hunter
2018-08-27 11:43     ` Adrian Hunter
2018-08-27 14:10 ` Marcel Ziswiler
2018-08-27 15:50   ` Thierry Reding
2018-08-27 15:57     ` Thierry Reding
2018-08-27 16:27     ` Aapo Vienamo
2018-08-27 21:35     ` Marcel Ziswiler

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).