arch/mips/pci/pci-rt3883.c

Source file repositories/reference/linux-study-clean/arch/mips/pci/pci-rt3883.c

File Facts

System
Linux kernel
Corpus path
arch/mips/pci/pci-rt3883.c
Extension
.c
Size
14762 bytes
Lines
582
Domain
Architecture Layer
Bucket
arch/mips
Inferred role
Architecture Layer: exported/initcall integration point
Status
integration implementation candidate

Why This File Exists

CPU and platform-specific kernel glue: boot entry, traps, syscall entry, interrupts, page tables, context switch, and low-level barriers.

Dependency Surface

Detected Declarations

Annotated Snippet

struct rt3883_pci_controller {
	void __iomem *base;

	struct device_node *intc_of_node;
	struct irq_domain *irq_domain;

	struct pci_controller pci_controller;
	struct resource io_res;
	struct resource mem_res;

	bool pcie_ready;
};

static inline struct rt3883_pci_controller *
pci_bus_to_rt3883_controller(struct pci_bus *bus)
{
	struct pci_controller *hose;

	hose = (struct pci_controller *) bus->sysdata;
	return container_of(hose, struct rt3883_pci_controller, pci_controller);
}

static inline u32 rt3883_pci_r32(struct rt3883_pci_controller *rpc,
				 unsigned reg)
{
	return ioread32(rpc->base + reg);
}

static inline void rt3883_pci_w32(struct rt3883_pci_controller *rpc,
				  u32 val, unsigned reg)
{
	iowrite32(val, rpc->base + reg);
}

static inline u32 rt3883_pci_get_cfgaddr(unsigned int bus, unsigned int slot,
					 unsigned int func, unsigned int where)
{
	return (bus << 16) | (slot << 11) | (func << 8) | (where & 0xfc) |
	       0x80000000;
}

static u32 rt3883_pci_read_cfg32(struct rt3883_pci_controller *rpc,
			       unsigned bus, unsigned slot,
			       unsigned func, unsigned reg)
{
	u32 address;

	address = rt3883_pci_get_cfgaddr(bus, slot, func, reg);

	rt3883_pci_w32(rpc, address, RT3883_PCI_REG_CFGADDR);

	return rt3883_pci_r32(rpc, RT3883_PCI_REG_CFGDATA);
}

static void rt3883_pci_write_cfg32(struct rt3883_pci_controller *rpc,
				 unsigned bus, unsigned slot,
				 unsigned func, unsigned reg, u32 val)
{
	u32 address;

	address = rt3883_pci_get_cfgaddr(bus, slot, func, reg);

	rt3883_pci_w32(rpc, address, RT3883_PCI_REG_CFGADDR);
	rt3883_pci_w32(rpc, val, RT3883_PCI_REG_CFGDATA);
}

static void rt3883_pci_irq_handler(struct irq_desc *desc)
{
	struct rt3883_pci_controller *rpc;
	u32 pending;

	rpc = irq_desc_get_handler_data(desc);

	pending = rt3883_pci_r32(rpc, RT3883_PCI_REG_PCIINT) &
		  rt3883_pci_r32(rpc, RT3883_PCI_REG_PCIENA);

	if (!pending) {
		spurious_interrupt();
		return;
	}

	while (pending) {
		unsigned bit = __ffs(pending);

		generic_handle_domain_irq(rpc->irq_domain, bit);

		pending &= ~BIT(bit);
	}
}

Annotation

Implementation Notes