drivers/ufs/host/ufs-qcom.c
Source file repositories/reference/linux-study-clean/drivers/ufs/host/ufs-qcom.c
File Facts
- System
- Linux kernel
- Corpus path
drivers/ufs/host/ufs-qcom.c- Extension
.c- Size
- 83815 bytes
- Lines
- 3051
- Domain
- Driver Families
- Bucket
- drivers/ufs
- 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.
- 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.
- Touches IRQ or DMA behavior; this matters for the representative real-device path.
- Allocates kernel memory; connect allocation flags and lifetime to context constraints.
- Defines or uses C structs; map object ownership, embedded links, reference counts, and lock ownership.
Dependency Surface
linux/acpi.hlinux/clk.hlinux/cleanup.hlinux/delay.hlinux/devfreq.hlinux/gpio/consumer.hlinux/interconnect.hlinux/module.hlinux/of.hlinux/phy/phy.hlinux/platform_device.hlinux/pm_domain.hlinux/reset-controller.hlinux/time.hlinux/unaligned.hlinux/units.hsoc/qcom/ice.hufs/ufshcd.hufs/ufshci.hufs/ufs_quirks.hufs/unipro.hufshcd-pltfrm.hufs-qcom.h
Detected Declarations
struct dump_infostruct ufs_qcom_irqfunction ufs_qcom_config_ice_allocatorfunction ufs_qcom_ice_enablefunction ufs_qcom_ice_initfunction ufs_qcom_ice_resumefunction ufs_qcom_ice_suspendfunction ufs_qcom_ice_keyslot_programfunction ufs_qcom_ice_keyslot_evictfunction ufs_qcom_ice_derive_sw_secretfunction ufs_qcom_ice_import_keyfunction ufs_qcom_ice_generate_keyfunction ufs_qcom_ice_prepare_keyfunction ufs_qcom_ice_enablefunction ufs_qcom_ice_resumefunction ufs_qcom_ice_suspendfunction ufs_qcom_config_ice_allocatorfunction ufs_qcom_enable_lane_clksfunction ufs_qcom_init_lane_clksfunction ufs_qcom_check_hibern8function ufs_qcom_select_unipro_modefunction ufs_qcom_host_resetfunction ufs_qcom_get_hs_gearfunction ufs_qcom_power_up_sequencefunction cellsfunction ufs_qcom_hce_enable_notifyfunction ufs_qcom_fw_managed_hce_enable_notifyfunction ufs_qcom_cfg_timersfunction list_for_each_entryfunction ufs_qcom_link_startup_post_changefunction ufs_qcom_link_startup_notifyfunction ufs_qcom_device_reset_ctrlfunction ufs_qcom_suspendfunction ufs_qcom_resumefunction ufs_qcom_fw_managed_suspendfunction ufs_qcom_fw_managed_resumefunction ufs_qcom_dev_ref_clk_ctrlfunction ufs_qcom_icc_set_bwfunction ufs_qcom_get_bw_tablefunction ufs_qcom_icc_update_bwfunction ufs_qcom_set_tx_hs_equalizerfunction ufs_qcom_negotiate_pwr_modefunction ufs_qcom_pwr_change_notifyfunction ufs_qcom_quirk_host_pa_saveconfigtimefunction ufs_qcom_override_pa_tx_hsg1_sync_lenfunction ufs_qcom_limit_max_gearfunction ufs_qcom_fixup_tx_adapt_l0l1l2l3function ufs_qcom_apply_dev_quirks
Annotated Snippet
struct dump_info {
void __iomem *base;
size_t offset;
size_t len;
const char *prefix;
};
struct dump_info mcq_dumps[] = {
{hba->mcq_base, 0x0, 256 * 4, "MCQ HCI-0 "},
{hba->mcq_base, 0x400, 256 * 4, "MCQ HCI-1 "},
{mcq_vs_base, 0x0, 5 * 4, "MCQ VS-0 "},
{opr->base, 0x0, 256 * 4, "MCQ SQD-0 "},
{opr->base, 0x400, 256 * 4, "MCQ SQD-1 "},
{opr->base, 0x800, 256 * 4, "MCQ SQD-2 "},
{opr->base, 0xc00, 256 * 4, "MCQ SQD-3 "},
{opr->base, 0x1000, 256 * 4, "MCQ SQD-4 "},
{opr->base, 0x1400, 256 * 4, "MCQ SQD-5 "},
{opr->base, 0x1800, 256 * 4, "MCQ SQD-6 "},
{opr->base, 0x1c00, 256 * 4, "MCQ SQD-7 "},
};
for (int i = 0; i < ARRAY_SIZE(mcq_dumps); i++) {
ufs_qcom_dump_regs(hba, mcq_dumps[i].offset, mcq_dumps[i].len,
mcq_dumps[i].prefix, mcq_dumps[i].base);
cond_resched();
}
}
static void ufs_qcom_dump_dbg_regs(struct ufs_hba *hba)
{
u32 reg;
struct ufs_qcom_host *host;
host = ufshcd_get_variant(hba);
dev_err(hba->dev, "HW_H8_ENTER_CNT=%d\n", ufshcd_readl(hba, REG_UFS_HW_H8_ENTER_CNT));
dev_err(hba->dev, "HW_H8_EXIT_CNT=%d\n", ufshcd_readl(hba, REG_UFS_HW_H8_EXIT_CNT));
dev_err(hba->dev, "SW_H8_ENTER_CNT=%d\n", ufshcd_readl(hba, REG_UFS_SW_H8_ENTER_CNT));
dev_err(hba->dev, "SW_H8_EXIT_CNT=%d\n", ufshcd_readl(hba, REG_UFS_SW_H8_EXIT_CNT));
dev_err(hba->dev, "SW_AFTER_HW_H8_ENTER_CNT=%d\n",
ufshcd_readl(hba, REG_UFS_SW_AFTER_HW_H8_ENTER_CNT));
ufshcd_dump_regs(hba, REG_UFS_SYS1CLK_1US, 16 * 4,
"HCI Vendor Specific Registers ");
reg = ufs_qcom_get_debug_reg_offset(host, UFS_UFS_DBG_RD_REG_OCSC);
ufshcd_dump_regs(hba, reg, 44 * 4, "UFS_UFS_DBG_RD_REG_OCSC ");
reg = ufshcd_readl(hba, REG_UFS_CFG1);
reg |= UTP_DBG_RAMS_EN;
ufshcd_writel(hba, reg, REG_UFS_CFG1);
reg = ufs_qcom_get_debug_reg_offset(host, UFS_UFS_DBG_RD_EDTL_RAM);
ufshcd_dump_regs(hba, reg, 32 * 4, "UFS_UFS_DBG_RD_EDTL_RAM ");
reg = ufs_qcom_get_debug_reg_offset(host, UFS_UFS_DBG_RD_DESC_RAM);
ufshcd_dump_regs(hba, reg, 128 * 4, "UFS_UFS_DBG_RD_DESC_RAM ");
reg = ufs_qcom_get_debug_reg_offset(host, UFS_UFS_DBG_RD_PRDT_RAM);
ufshcd_dump_regs(hba, reg, 64 * 4, "UFS_UFS_DBG_RD_PRDT_RAM ");
/* clear bit 17 - UTP_DBG_RAMS_EN */
ufshcd_rmwl(hba, UTP_DBG_RAMS_EN, 0, REG_UFS_CFG1);
reg = ufs_qcom_get_debug_reg_offset(host, UFS_DBG_RD_REG_UAWM);
ufshcd_dump_regs(hba, reg, 4 * 4, "UFS_DBG_RD_REG_UAWM ");
reg = ufs_qcom_get_debug_reg_offset(host, UFS_DBG_RD_REG_UARM);
ufshcd_dump_regs(hba, reg, 4 * 4, "UFS_DBG_RD_REG_UARM ");
reg = ufs_qcom_get_debug_reg_offset(host, UFS_DBG_RD_REG_TXUC);
ufshcd_dump_regs(hba, reg, 48 * 4, "UFS_DBG_RD_REG_TXUC ");
reg = ufs_qcom_get_debug_reg_offset(host, UFS_DBG_RD_REG_RXUC);
ufshcd_dump_regs(hba, reg, 27 * 4, "UFS_DBG_RD_REG_RXUC ");
reg = ufs_qcom_get_debug_reg_offset(host, UFS_DBG_RD_REG_DFC);
ufshcd_dump_regs(hba, reg, 19 * 4, "UFS_DBG_RD_REG_DFC ");
reg = ufs_qcom_get_debug_reg_offset(host, UFS_DBG_RD_REG_TRLUT);
ufshcd_dump_regs(hba, reg, 34 * 4, "UFS_DBG_RD_REG_TRLUT ");
reg = ufs_qcom_get_debug_reg_offset(host, UFS_DBG_RD_REG_TMRLUT);
ufshcd_dump_regs(hba, reg, 9 * 4, "UFS_DBG_RD_REG_TMRLUT ");
if (hba->mcq_enabled) {
reg = ufs_qcom_get_debug_reg_offset(host, UFS_RD_REG_MCQ);
Annotation
- Immediate include surface: `linux/acpi.h`, `linux/clk.h`, `linux/cleanup.h`, `linux/delay.h`, `linux/devfreq.h`, `linux/gpio/consumer.h`, `linux/interconnect.h`, `linux/module.h`.
- Detected declarations: `struct dump_info`, `struct ufs_qcom_irq`, `function ufs_qcom_config_ice_allocator`, `function ufs_qcom_ice_enable`, `function ufs_qcom_ice_init`, `function ufs_qcom_ice_resume`, `function ufs_qcom_ice_suspend`, `function ufs_qcom_ice_keyslot_program`, `function ufs_qcom_ice_keyslot_evict`, `function ufs_qcom_ice_derive_sw_secret`.
- Atlas domain: Driver Families / drivers/ufs.
- Implementation status: source implementation candidate.
- IRQ or DMA behavior appears here, which is relevant to the selected PCIe/NVMe device path.
Implementation Notes
- This generated page is the file-by-file coverage layer; curated subsystem chapters should link here when they synthesize a multi-file control flow.
- Core OS pages should be promoted from atlas-only to deep-reviewed when they explain data structures, invariants, locking, lifecycle, and C implementation snippets.
- Driver-family pages are intentionally pattern-oriented unless they are part of the selected PCIe/NVMe representative device path.