Commit 77bfa0fc authored by Jim Lin's avatar Jim Lin Committed by Greg Kroah-Hartman

phy: tegra: xusb: add utmi pad power on/down ops

Add utmi_pad_power_on/down ops for each SOC instead of exporting
tegra_phy_xusb_utmi_pad_power_on/down directly for Tegra186 chip.
Signed-off-by: default avatarBH Hsieh <bhsieh@nvidia.com>
Signed-off-by: default avatarJim Lin <jilin@nvidia.com>
Link: https://lore.kernel.org/r/20220816082353.13390-2-jilin@nvidia.comSigned-off-by: default avatarGreg Kroah-Hartman <gregkh@linuxfoundation.org>
parent b7db5733
// SPDX-License-Identifier: GPL-2.0 // SPDX-License-Identifier: GPL-2.0
/* /*
* Copyright (c) 2016-2020, NVIDIA CORPORATION. All rights reserved. * Copyright (c) 2016-2022, NVIDIA CORPORATION. All rights reserved.
*/ */
#include <linux/delay.h> #include <linux/delay.h>
...@@ -638,7 +638,7 @@ static void tegra186_utmi_bias_pad_power_off(struct tegra_xusb_padctl *padctl) ...@@ -638,7 +638,7 @@ static void tegra186_utmi_bias_pad_power_off(struct tegra_xusb_padctl *padctl)
mutex_unlock(&padctl->lock); mutex_unlock(&padctl->lock);
} }
static void tegra_phy_xusb_utmi_pad_power_on(struct phy *phy) static void tegra186_utmi_pad_power_on(struct phy *phy)
{ {
struct tegra_xusb_lane *lane = phy_get_drvdata(phy); struct tegra_xusb_lane *lane = phy_get_drvdata(phy);
struct tegra_xusb_padctl *padctl = lane->pad->padctl; struct tegra_xusb_padctl *padctl = lane->pad->padctl;
...@@ -656,6 +656,8 @@ static void tegra_phy_xusb_utmi_pad_power_on(struct phy *phy) ...@@ -656,6 +656,8 @@ static void tegra_phy_xusb_utmi_pad_power_on(struct phy *phy)
return; return;
} }
dev_dbg(dev, "power on UTMI pad %u\n", index);
tegra186_utmi_bias_pad_power_on(padctl); tegra186_utmi_bias_pad_power_on(padctl);
udelay(2); udelay(2);
...@@ -669,7 +671,7 @@ static void tegra_phy_xusb_utmi_pad_power_on(struct phy *phy) ...@@ -669,7 +671,7 @@ static void tegra_phy_xusb_utmi_pad_power_on(struct phy *phy)
padctl_writel(padctl, value, XUSB_PADCTL_USB2_OTG_PADX_CTL1(index)); padctl_writel(padctl, value, XUSB_PADCTL_USB2_OTG_PADX_CTL1(index));
} }
static void tegra_phy_xusb_utmi_pad_power_down(struct phy *phy) static void tegra186_utmi_pad_power_down(struct phy *phy)
{ {
struct tegra_xusb_lane *lane = phy_get_drvdata(phy); struct tegra_xusb_lane *lane = phy_get_drvdata(phy);
struct tegra_xusb_padctl *padctl = lane->pad->padctl; struct tegra_xusb_padctl *padctl = lane->pad->padctl;
...@@ -679,6 +681,8 @@ static void tegra_phy_xusb_utmi_pad_power_down(struct phy *phy) ...@@ -679,6 +681,8 @@ static void tegra_phy_xusb_utmi_pad_power_down(struct phy *phy)
if (!phy) if (!phy)
return; return;
dev_dbg(padctl->dev, "power down UTMI pad %u\n", index);
value = padctl_readl(padctl, XUSB_PADCTL_USB2_OTG_PADX_CTL0(index)); value = padctl_readl(padctl, XUSB_PADCTL_USB2_OTG_PADX_CTL0(index));
value |= USB2_OTG_PD; value |= USB2_OTG_PD;
padctl_writel(padctl, value, XUSB_PADCTL_USB2_OTG_PADX_CTL0(index)); padctl_writel(padctl, value, XUSB_PADCTL_USB2_OTG_PADX_CTL0(index));
...@@ -849,15 +853,14 @@ static int tegra186_utmi_phy_power_on(struct phy *phy) ...@@ -849,15 +853,14 @@ static int tegra186_utmi_phy_power_on(struct phy *phy)
value |= RPD_CTRL(priv->calib.rpd_ctrl); value |= RPD_CTRL(priv->calib.rpd_ctrl);
padctl_writel(padctl, value, XUSB_PADCTL_USB2_OTG_PADX_CTL1(index)); padctl_writel(padctl, value, XUSB_PADCTL_USB2_OTG_PADX_CTL1(index));
/* TODO: pad power saving */ tegra186_utmi_pad_power_on(phy);
tegra_phy_xusb_utmi_pad_power_on(phy);
return 0; return 0;
} }
static int tegra186_utmi_phy_power_off(struct phy *phy) static int tegra186_utmi_phy_power_off(struct phy *phy)
{ {
/* TODO: pad power saving */ tegra186_utmi_pad_power_down(phy);
tegra_phy_xusb_utmi_pad_power_down(phy);
return 0; return 0;
} }
...@@ -1486,6 +1489,8 @@ static const struct tegra_xusb_padctl_ops tegra186_xusb_padctl_ops = { ...@@ -1486,6 +1489,8 @@ static const struct tegra_xusb_padctl_ops tegra186_xusb_padctl_ops = {
.suspend_noirq = tegra186_xusb_padctl_suspend_noirq, .suspend_noirq = tegra186_xusb_padctl_suspend_noirq,
.resume_noirq = tegra186_xusb_padctl_resume_noirq, .resume_noirq = tegra186_xusb_padctl_resume_noirq,
.vbus_override = tegra186_xusb_padctl_vbus_override, .vbus_override = tegra186_xusb_padctl_vbus_override,
.utmi_pad_power_on = tegra186_utmi_pad_power_on,
.utmi_pad_power_down = tegra186_utmi_pad_power_down,
}; };
#if IS_ENABLED(CONFIG_ARCH_TEGRA_186_SOC) #if IS_ENABLED(CONFIG_ARCH_TEGRA_186_SOC)
......
// SPDX-License-Identifier: GPL-2.0-only // SPDX-License-Identifier: GPL-2.0-only
/* /*
* Copyright (c) 2014-2020, NVIDIA CORPORATION. All rights reserved. * Copyright (c) 2014-2022, NVIDIA CORPORATION. All rights reserved.
*/ */
#include <linux/delay.h> #include <linux/delay.h>
...@@ -1458,6 +1458,26 @@ int tegra_phy_xusb_utmi_port_reset(struct phy *phy) ...@@ -1458,6 +1458,26 @@ int tegra_phy_xusb_utmi_port_reset(struct phy *phy)
} }
EXPORT_SYMBOL_GPL(tegra_phy_xusb_utmi_port_reset); EXPORT_SYMBOL_GPL(tegra_phy_xusb_utmi_port_reset);
void tegra_phy_xusb_utmi_pad_power_on(struct phy *phy)
{
struct tegra_xusb_lane *lane = phy_get_drvdata(phy);
struct tegra_xusb_padctl *padctl = lane->pad->padctl;
if (padctl->soc->ops->utmi_pad_power_on)
padctl->soc->ops->utmi_pad_power_on(phy);
}
EXPORT_SYMBOL_GPL(tegra_phy_xusb_utmi_pad_power_on);
void tegra_phy_xusb_utmi_pad_power_down(struct phy *phy)
{
struct tegra_xusb_lane *lane = phy_get_drvdata(phy);
struct tegra_xusb_padctl *padctl = lane->pad->padctl;
if (padctl->soc->ops->utmi_pad_power_down)
padctl->soc->ops->utmi_pad_power_down(phy);
}
EXPORT_SYMBOL_GPL(tegra_phy_xusb_utmi_pad_power_down);
int tegra_xusb_padctl_get_usb3_companion(struct tegra_xusb_padctl *padctl, int tegra_xusb_padctl_get_usb3_companion(struct tegra_xusb_padctl *padctl,
unsigned int port) unsigned int port)
{ {
......
/* SPDX-License-Identifier: GPL-2.0-only */ /* SPDX-License-Identifier: GPL-2.0-only */
/* /*
* Copyright (c) 2014-2020, NVIDIA CORPORATION. All rights reserved. * Copyright (c) 2014-2022, NVIDIA CORPORATION. All rights reserved.
* Copyright (c) 2015, Google Inc. * Copyright (c) 2015, Google Inc.
*/ */
...@@ -412,6 +412,8 @@ struct tegra_xusb_padctl_ops { ...@@ -412,6 +412,8 @@ struct tegra_xusb_padctl_ops {
unsigned int index, bool enable); unsigned int index, bool enable);
int (*vbus_override)(struct tegra_xusb_padctl *padctl, bool set); int (*vbus_override)(struct tegra_xusb_padctl *padctl, bool set);
int (*utmi_port_reset)(struct phy *phy); int (*utmi_port_reset)(struct phy *phy);
void (*utmi_pad_power_on)(struct phy *phy);
void (*utmi_pad_power_down)(struct phy *phy);
}; };
struct tegra_xusb_padctl_soc { struct tegra_xusb_padctl_soc {
......
/* SPDX-License-Identifier: GPL-2.0-only */ /* SPDX-License-Identifier: GPL-2.0-only */
/* /*
* Copyright (c) 2016-2020, NVIDIA CORPORATION. All rights reserved. * Copyright (c) 2016-2022, NVIDIA CORPORATION. All rights reserved.
*/ */
#ifndef PHY_TEGRA_XUSB_H #ifndef PHY_TEGRA_XUSB_H
...@@ -21,6 +21,8 @@ int tegra_xusb_padctl_usb3_set_lfps_detect(struct tegra_xusb_padctl *padctl, ...@@ -21,6 +21,8 @@ int tegra_xusb_padctl_usb3_set_lfps_detect(struct tegra_xusb_padctl *padctl,
unsigned int port, bool enable); unsigned int port, bool enable);
int tegra_xusb_padctl_set_vbus_override(struct tegra_xusb_padctl *padctl, int tegra_xusb_padctl_set_vbus_override(struct tegra_xusb_padctl *padctl,
bool val); bool val);
void tegra_phy_xusb_utmi_pad_power_on(struct phy *phy);
void tegra_phy_xusb_utmi_pad_power_down(struct phy *phy);
int tegra_phy_xusb_utmi_port_reset(struct phy *phy); int tegra_phy_xusb_utmi_port_reset(struct phy *phy);
int tegra_xusb_padctl_get_usb3_companion(struct tegra_xusb_padctl *padctl, int tegra_xusb_padctl_get_usb3_companion(struct tegra_xusb_padctl *padctl,
unsigned int port); unsigned int port);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment