Linux PCI Protocol and Device Driver Development Course
This online training is structured into five focused modules, guiding participants from fundamental kernel concepts to the implementation of a full-featured PCI/PCIe device driver.
Module 1: Linux Kernel and Driver Foundations (4 Topics)
• Introduction to Linux Device Drivers: Exploring the fundamental distinction between User Space and Kernel Space. Introduction to Loadable Kernel Modules (LKM), and essential module management tools like insmod, rmmod, and lsmod.
• Kernel Module Basics & Build System: Detailing the structure of a kernel module, including the use of module_init and module_exit entry/exit points. Practical focus on setting up the Kbuild/Makefile environment and utilizing printk for debugging and logging.
• The Linux Device Model: Understanding the abstract framework of the Linux kernel that organizes hardware. Coverage includes the concepts of bus_type, device, and device_driver, and how these structures integrate with the sysfs filesystem.
• Kernel Data Structures & Synchronization: Essential for writing thread-safe drivers. Topics include kernel-specific linked lists, Wait Queues, and critical concurrency primitives like Atomic operations, Spinlocks, and Mutexes.
Module 2: PCI Protocol and Architecture Deep Dive (4 Topics)
• Conventional PCI Overview: Reviewing the legacy parallel bus architecture, including Bus/Device/Function (BDF) numbering and bus arbitration principles.
• PCI Express (PCIe) Architecture: Transitioning to the modern, serial, point-to-point connection model. Detailed look at Lanes (x1, x4, x16), the Root Complex, Switches, and Endpoints.
• PCIe Protocol Layers: In-depth examination of the three-layer protocol stack: Physical, Data Link, and Transaction Layers. Focus on Transaction Layer Packets (TLPs) and Flow Control mechanisms.
• Address Spaces in PCI/PCIe: Differentiating the critical address spaces used for device interaction: Configuration Space, Memory Space, and I/O Space.
Module 3: Device Configuration and Resource Management (4 Topics)
• Configuration Space Access: Mastering the methods for reading and writing to the device's Configuration Space. Identification using Vendor ID, Device ID, and Class Code.
• Base Address Registers (BARs): Comprehensive explanation of BARs—how they are decoded, their role in defining device resource needs, and the kernel process for mapping them.
• Advanced Configuration Registers: Understanding additional configuration capabilities, including Power Management registers and various PCIe Capability Structures.
• Device Enumeration and Initialization: Tracing the process by which the BIOS and operating system discover and configure all PCI devices in the system during boot-up.
Module 4: The Linux PCI Subsystem Framework (4 Topics)
• The pci_driver Structure: Defining the Linux PCI driver structure. Topics include registering the driver using pci_register_driver, matching devices via the pci_device_id table, and the crucial probe and remove callbacks.
• Device Initialization & Mapping: Core steps for making the device operational: enabling the device (pci_enable_device), requesting BAR resources (pci_request_regions), and mapping MMIO space (ioremap).
• Register I/O Access: Hands-on experience with kernel APIs for accessing device registers, focusing on Memory-Mapped I/O (MMIO) using functions like readl and writel. Includes a practical basic register read/write exercise.
• Interrupt Handling (Legacy and Deferred Work): Implementing the initial interrupt request (request_irq) and understanding the division of labor between the Top Half (IRQ handler) and the Bottom Half using Tasklets and Workqueues.
Module 5: High-Performance I/O and Final Integration (4 Topics)
• Message Signaled Interrupts (MSI/MSI-X): Deep dive into the modern, performant interrupt standard. Understanding the advantages of MSI/MSI-X over legacy pin-based interrupts and using kernel APIs to enable them.
• Direct Memory Access (DMA) Theory: Theoretical underpinnings of DMA, including the role of the IOMMU, and the distinction between Coherent and Streaming DMA. Setting up appropriate DMA masks.
• Streaming DMA Implementation: Practical application of streaming DMA using kernel APIs (dma_map_single and dma_unmap_single) to efficiently move large data blocks between system memory and the device.
• Complete Driver Integration and Wrap-up: A final session dedicated to assembling all components—probe logic, configuration, MMIO, IRQ handling, and DMA—into a cohesive, robust, and fully functional Linux PCI device driver and final cleanup logic.