drivers/pci/controller/pcie-aspeed.c

Source file repositories/reference/linux-study-clean/drivers/pci/controller/pcie-aspeed.c

File Facts

System
Linux kernel
Corpus path
drivers/pci/controller/pcie-aspeed.c
Extension
.c
Size
31828 bytes
Lines
1112
Domain
Representative Device Path
Bucket
PCIe NVMe Storage Path
Inferred role
Representative Device Path: implementation source
Status
source implementation candidate

Why This File Exists

Part of the selected hardware vertical slice: PCI discovery, driver binding, NVMe queues, block requests, DMA, interrupts, and completion.

Dependency Surface

Detected Declarations

Annotated Snippet

struct aspeed_pcie_port {
	struct list_head list;
	struct aspeed_pcie *pcie;
	struct clk *clk;
	struct phy *phy;
	struct reset_control *perst;
	u32 slot;
};

/**
 * struct aspeed_pcie - PCIe RC information
 * @host: pointer to PCIe host bridge
 * @dev: pointer to device structure
 * @reg: PCIe host register base address
 * @ahbc: pointer to AHHC register map
 * @cfg: pointer to Aspeed PCIe configuration register map
 * @platform: platform specific information
 * @ports: list of PCIe ports
 * @tx_tag: current TX tag for the port
 * @root_bus_nr: bus number of the host bridge
 * @h2xrst: pointer to H2X reset control
 * @intx_domain: IRQ domain for INTx interrupts
 * @msi_domain: IRQ domain for MSI interrupts
 * @lock: mutex to protect MSI bitmap variable
 * @msi_irq_in_use: bitmap to track used MSI host IRQs
 * @clear_msi_twice: AST2700 workaround to clear MSI status twice
 */
struct aspeed_pcie {
	struct pci_host_bridge *host;
	struct device *dev;
	void __iomem *reg;
	struct regmap *ahbc;
	struct regmap *cfg;
	const struct aspeed_pcie_rc_platform *platform;
	struct list_head ports;

	u8 tx_tag;
	u8 root_bus_nr;

	struct reset_control *h2xrst;

	struct irq_domain *intx_domain;
	struct irq_domain *msi_domain;
	struct mutex lock;
	DECLARE_BITMAP(msi_irq_in_use, MAX_MSI_HOST_IRQS);

	bool clear_msi_twice;		/* AST2700 workaround */
};

/**
 * struct aspeed_pcie_rc_platform - Platform information
 * @setup: initialization function
 * @pcie_map_ranges: function to map PCIe address ranges
 * @reg_intx_en: INTx enable register offset
 * @reg_intx_sts: INTx status register offset
 * @reg_msi_en: MSI enable register offset
 * @reg_msi_sts: MSI enable register offset
 * @msi_address: HW fixed MSI address
 */
struct aspeed_pcie_rc_platform {
	int (*setup)(struct platform_device *pdev);
	void (*pcie_map_ranges)(struct aspeed_pcie *pcie, u64 pci_addr);
	int reg_intx_en;
	int reg_intx_sts;
	int reg_msi_en;
	int reg_msi_sts;
	u32 msi_address;
};

static void aspeed_pcie_intx_irq_ack(struct irq_data *d)
{
	struct aspeed_pcie *pcie = irq_data_get_irq_chip_data(d);
	int intx_en = pcie->platform->reg_intx_en;
	u32 en;

	en = readl(pcie->reg + intx_en);
	en |= BIT(d->hwirq);
	writel(en, pcie->reg + intx_en);
}

static void aspeed_pcie_intx_irq_mask(struct irq_data *d)
{
	struct aspeed_pcie *pcie = irq_data_get_irq_chip_data(d);
	int intx_en = pcie->platform->reg_intx_en;
	u32 en;

	en = readl(pcie->reg + intx_en);
	en &= ~BIT(d->hwirq);
	writel(en, pcie->reg + intx_en);
}

Annotation

Implementation Notes