drivers/usb/phy/phy-tegra-usb.c

Source file repositories/reference/linux-study-clean/drivers/usb/phy/phy-tegra-usb.c

File Facts

System
Linux kernel
Corpus path
drivers/usb/phy/phy-tegra-usb.c
Extension
.c
Size
43791 bytes
Lines
1656
Domain
Driver Families
Bucket
drivers/usb
Inferred role
Driver Families: implementation source
Status
source implementation candidate

Why This File Exists

Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.

Dependency Surface

Detected Declarations

Annotated Snippet

struct tegra_xtal_freq {
	unsigned int freq;
	u8 enable_delay;
	u8 stable_count;
	u8 active_delay;
	u8 utmi_xtal_freq_count;
	u16 hsic_xtal_freq_count;
	u16 debounce;
};

static const struct tegra_xtal_freq tegra_freq_table[] = {
	{
		.freq = 12000000,
		.enable_delay = 0x02,
		.stable_count = 0x2F,
		.active_delay = 0x04,
		.utmi_xtal_freq_count = 0x76,
		.hsic_xtal_freq_count = 0x1CA,
		.debounce = 0x7530,
	},
	{
		.freq = 13000000,
		.enable_delay = 0x02,
		.stable_count = 0x33,
		.active_delay = 0x05,
		.utmi_xtal_freq_count = 0x7F,
		.hsic_xtal_freq_count = 0x1F0,
		.debounce = 0x7EF4,
	},
	{
		.freq = 19200000,
		.enable_delay = 0x03,
		.stable_count = 0x4B,
		.active_delay = 0x06,
		.utmi_xtal_freq_count = 0xBB,
		.hsic_xtal_freq_count = 0x2DD,
		.debounce = 0xBB80,
	},
	{
		.freq = 26000000,
		.enable_delay = 0x04,
		.stable_count = 0x66,
		.active_delay = 0x09,
		.utmi_xtal_freq_count = 0xFE,
		.hsic_xtal_freq_count = 0x3E0,
		.debounce = 0xFDE8,
	},
};

static inline struct tegra_usb_phy *to_tegra_usb_phy(struct usb_phy *u_phy)
{
	return container_of(u_phy, struct tegra_usb_phy, u_phy);
}

static void set_pts(struct tegra_usb_phy *phy, u8 pts_val)
{
	void __iomem *base = phy->regs;
	u32 val;

	if (phy->soc_config->has_hostpc) {
		val = readl_relaxed(base + TEGRA_USB_HOSTPC1_DEVLC);
		val &= ~TEGRA_USB_HOSTPC1_DEVLC_PTS(~0);
		val |= TEGRA_USB_HOSTPC1_DEVLC_PTS(pts_val);
		writel_relaxed(val, base + TEGRA_USB_HOSTPC1_DEVLC);
	} else {
		val = readl_relaxed(base + TEGRA_USB_PORTSC1);
		val &= ~TEGRA_PORTSC1_RWC_BITS;
		val &= ~TEGRA_USB_PORTSC1_PTS(~0);
		val |= TEGRA_USB_PORTSC1_PTS(pts_val);
		writel_relaxed(val, base + TEGRA_USB_PORTSC1);
	}
}

static void set_phcd(struct tegra_usb_phy *phy, bool enable)
{
	void __iomem *base = phy->regs;
	u32 val;

	if (phy->soc_config->has_hostpc) {
		val = readl_relaxed(base + TEGRA_USB_HOSTPC1_DEVLC);
		if (enable)
			val |= TEGRA_USB_HOSTPC1_DEVLC_PHCD;
		else
			val &= ~TEGRA_USB_HOSTPC1_DEVLC_PHCD;
		writel_relaxed(val, base + TEGRA_USB_HOSTPC1_DEVLC);
	} else {
		val = readl_relaxed(base + TEGRA_USB_PORTSC1) & ~PORT_RWC_BITS;
		if (enable)
			val |= TEGRA_USB_PORTSC1_PHCD;
		else

Annotation

Implementation Notes