summaryrefslogtreecommitdiff
path: root/arch
diff options
context:
space:
mode:
authorStefan Agner <stefan.agner@toradex.com>2016-02-25 15:24:46 -0800
committerStefan Agner <stefan.agner@toradex.com>2016-02-25 15:24:46 -0800
commitc56482b2363615d35a9f4241c0e9069c69085536 (patch)
tree5244195224bbbe75e5ff223e81fb735872a360b9 /arch
parenta9e6324c87ee7357211714d95da44036bbca9789 (diff)
ARM: dts: vf610: do not control reset line on warm reset
When entering and resuming from suspend-to-RAM (LPSTOP2), the current pinmux and the automatic restore of the last GPIO state lead to an "uncontrolled" hard reset. The wm9712 driver tries to warm reset the codec, which succeeds due to the previous hard reset. Since the warm reset succeeded, the wm9712 driver will not restore the codecs registers, hence those will accidentially stay in reset state. To avoid this extra hard reset we need to leave the pad floating during suspend (the external pull-down will make sure that the line has a defined state). After suspend snd_soc_ac97_warm_reset will request the pinctrl states "ac97-warm-reset" and "ac97-running", we need to make sure that both states do not change the state of the reset line since it would introduce a similar "uncontrolled" hard reset. Therefor, remove pinctrl configurations for those states. With this change, we disable the output driver of the reset signal when entering suspend mode ("sleep" pinctrl state). Current Colibri VF61 1.2A module have an external pull-down, hence the reset signal will be low during suspend. With this change, the reset signal will stay low during resume even when the GPIO state gets restored (since the output driver is still disabled). This will keep the codec in reset, and the wm9712 drivers warm reset will fail. The driver will fall back to an explicit cold reset and due to the cold reset restore the registers properly. Future Colibri VF61 modules could use an external pull-up. This would mean that the warm reset on resume will succeed, and the driver would not need to restore the registers. Note: pinctrl with the AC97 pin states is rather delicate. It seems that when playing audio, the stack always selects the "default" state. Before, the "running" state has been used as "default" state. However, the "running" state is harmful during boot for initial cold reset (maybe test mode?). Therefor we use a minimalistic "default" pinmux. Only when the stack explicitily requests "running", we actually mux the real functions on the affected pins. Note 2: If there is a pull-up, we relly on the pull-up after suspend and resume since the cold reset function does not explicitly set the GPIO again... Signed-off-by: Stefan Agner <stefan.agner@toradex.com>
Diffstat (limited to 'arch')
-rw-r--r--arch/arm/boot/dts/vf610-colibri.dtsi60
1 files changed, 43 insertions, 17 deletions
diff --git a/arch/arm/boot/dts/vf610-colibri.dtsi b/arch/arm/boot/dts/vf610-colibri.dtsi
index 09d46c34fc23..0bd1f7ceb53d 100644
--- a/arch/arm/boot/dts/vf610-colibri.dtsi
+++ b/arch/arm/boot/dts/vf610-colibri.dtsi
@@ -43,13 +43,13 @@
&sai2 {
compatible = "fsl,vf610-sai-ac97";
#sound-dai-cells = <0>;
-
- pinctrl-names = "default", "ac97-running", "ac97-reset",
+ pinctrl-names = "default", "sleep", "ac97-running", "ac97-reset",
"ac97-warm-reset";
- pinctrl-0 = <&pinctrl_sai2_ac97_running>;
- pinctrl-1 = <&pinctrl_sai2_ac97_running>;
- pinctrl-2 = <&pinctrl_sai2_ac97_reset>;
+ pinctrl-0 = <&pinctrl_sai2_ac97_default>;
+ pinctrl-1 = <&pinctrl_sai2_ac97_sleep>;
+ pinctrl-2 = <&pinctrl_sai2_ac97_running>;
pinctrl-3 = <&pinctrl_sai2_ac97_reset>;
+ pinctrl-4 = <&pinctrl_sai2_ac97_warm_reset>;
ac97-gpios = <&gpio0 9 GPIO_ACTIVE_HIGH &gpio0 8 GPIO_ACTIVE_HIGH
&gpio0 13 GPIO_ACTIVE_HIGH>;
status = "okay";
@@ -62,20 +62,25 @@
VF610_PAD_PTB23__SAI0_TX_BCLK 0x31C3
>;
};
- pinctrl_sai2_ac97_reset: sai2grp_1 {
+
+ pinctrl_sai2_ac97_default: sai2grp_1 {
fsl,pins = <
/* Pen-down */
VF610_PAD_PTA11__GPIO_4 0x22ed
- /* AC97 SData Out (test mode selection) */
- VF610_PAD_PTA18__GPIO_8 0x22ed
- /* AC97 Sync (warm reset) */
- VF610_PAD_PTA19__GPIO_9 0x22ed
- /* AC97 Reset (cold reset) */
- VF610_PAD_PTA23__GPIO_13 0x22eb
+
+ /* GenIRQ */
+ VF610_PAD_PTB2__GPIO_24 0x22e1
>;
};
- pinctrl_sai2_ac97_running: sai2grp_2 {
+ pinctrl_sai2_ac97_sleep: sai2grp_2 {
+ fsl,pins = <
+ /* AC97 Reset (cold reset) floating */
+ VF610_PAD_PTA23__GPIO_13 0x22c1
+ >;
+ };
+
+ pinctrl_sai2_ac97_running: sai2grp_3 {
fsl,pins = <
/* AC97 Bit clock */
VF610_PAD_PTA16__SAI2_TX_BCLK 0x31C3
@@ -88,13 +93,34 @@
/* AC97 SData In */
VF610_PAD_PTA22__SAI2_RX_DATA 0x0041
+ >;
+ };
- /* AC97 Reset (cold reset, keep output buffer on) */
- VF610_PAD_PTA23__GPIO_13 0x22eb
+ pinctrl_sai2_ac97_reset: sai2grp_4 {
+ fsl,pins = <
+ VF610_PAD_PTA16__SAI2_TX_BCLK 0x31C1
- /* GenIRQ */
- VF610_PAD_PTB2__GPIO_24 0x22ed
+ /* AC97 SData Out (test mode selection) */
+ VF610_PAD_PTA18__GPIO_8 0x22c1
+
+ /* AC97 Sync (warm reset) */
+ VF610_PAD_PTA19__GPIO_9 0x22c1
+
+ /* AC97 Reset (cold reset) */
+ VF610_PAD_PTA23__GPIO_13 0x22c1
+ >;
+ };
+
+ pinctrl_sai2_ac97_warm_reset: sai2grp_5 {
+ fsl,pins = <
+ /* AC97 SData Out (test mode selection) */
+ VF610_PAD_PTA18__GPIO_8 0x22c1
+
+ /* AC97 Sync (warm reset) */
+ VF610_PAD_PTA19__GPIO_9 0x22c1
>;
};
+
+
};
};