Linux内核必备知识点 platform_driver

平台驱动程序(Linux内核的基本知识)
平台总线是学习linux驱动时必须掌握的知识点 。
本文参考已经发表:Linux 3.14内核
一、概念嵌入式系统中有很多物理总线:I2c、SPI、USB、uart、PCIE、APB、AHB 。
从2.6开始,Linux加入了新的驱动管理和注册机制 。平台总线是虚拟总线,不是物理总线 。
与PCI和USB相比,它主要用于描述SOC上的片上资源 。平台描述的资源有一个共同点:都是在CPU的总线上直接访问的 。
平台被分配一个名称(用于驱动程序绑定)和一系列资源,如地址和中断请求号(IRQ) 。
设备由platform_device表示,驱动程序由platform_driver注册 。
与传统的总线/设备/驱动机制相比,平台由内核统一管理,使用驱动中的资源,提高了代码的安全性和可移植性 。
二、platform1. platform总线两个最重要的结构体平台维护的所有驱动程序都必须用以下结构定义:
platform_driverstruct platform_driver { int (*probe)(struct platform_device *); // int (*remove)(struct platform_device *); void (*shutdown)(struct platform_device *); int (*suspend)(struct platform_device *, pm_message_t state); int (*resume)(struct platform_device *); struct device_driver driver; const struct platform_device_id *id_table; bool prevent_deferred_probe;};该结构用于将驱动程序注册到平台总线,

写驱动的时候,我们经常需要填写上面的成员 。
platform_device平台总线是一种用于描述设备硬件信息的结构,包括硬件的所有资源(io、内存、中断、DMA等) 。).
struct platform_device { const char *name; int id; bool id_auto; struct device dev; u32 num_resources; struct resource *resource; const struct platform_device_id *id_entry; /* MFD cell pointer */ struct mfd_cell *mfd_cell; /* arch specific additions */ struct pdev_archdata archdata;};

必须实现Struct设备开发版本() 。
描述硬件信息的成员结构资源
0x139d0000
struct resource { resource_size_t start; //表示资源的起始值, resource_size_t end; //表示资源的最后一个字节的地址, 如果是中断,end和satrt相同 const char *name; // 可不写 unsigned long flags; //资源的类型 struct resource *parent, *sibling, *child;};flags的类型说明#define IORESOURCE_MEM 0x00000200 //内存#define IORESOURCE_IRQ 0x00000400 //中断所有由内核管理的驱动程序必须包含一个名为struct device_driver的成员,所描述的硬件必须包含struct device结构的成员 。/
struct device_driver { const char *name;struct bus_type *bus; struct module *owner; const char *mod_name; /* used for built-in modules */ bool suppress_bind_attrs; /* disables bind/unbind via sysfs */ const struct of_device_id *of_match_table; const struct acpi_device_id *acpi_match_table; int (*probe) (struct device *dev); int (*remove) (struct device *dev); void (*shutdown) (struct device *dev); int (*suspend) (struct device *dev, pm_message_t state); int (*resume) (struct device *dev); const struct attribute_group **groups; const struct dev_pm_ops *pm; struct driver_private *p;};其中包括:
const char *name;用于与硬件匹配 。
内核描述硬件,必须包含结构设备结构的成员:
struct device { struct device *parent; struct device_private *p; struct kobject kobj; const char *init_name; /* initial name of the device */ const struct device_type *type; struct mutex mutex; /* mutex to synchronize calls to * its driver. */ struct bus_type *bus; /* type of bus device is on */ struct device_driver *driver; /* which driver has allocated this device */ void *platform_data; /* Platform specific data, device core doesn t touch it */ struct dev_pm_info power; struct dev_pm_domain *pm_domain;#ifdef CONFIG_PINCTRL struct dev_pin_info *pins;#endif#ifdef CONFIG_NUMA int numa_node; /* NUMA node this device is close to */#endif u64 *dma_mask; /* dma mask (if dma able device) */ u64 coherent_dma_mask;/* Like dma_mask, but for alloc_coherent mappings as not all hardware supports 64 bit addresses for consistent allocations such descriptors. */ struct device_dma_parameters *dma_parms; struct list_head dma_pools; /* dma pools (if dma ble) */ struct dma_coherent_mem *dma_mem; /* internal for coherent mem override */#ifdef CONFIG_DMA_CMA struct cma *cma_area; /* contiguous memory area for dma allocations */#endif /* arch specific additions */ struct dev_archdata archdata; struct device_node *of_node; /* associated device tree node */ struct acpi_dev_node acpi_node; /* associated ACPI device node */ dev_t devt; /* dev_t, creates the sysfsdev*/ u32 id; /* device instance */ spinlock_t devres_lock; struct list_head devres_head; struct klist_node knode_class; struct class *class; const struct attribute_group **groups; /* optional groups */ void (*release)(struct device *dev); struct iommu_group *iommu_group; bool offline_disabled:1; bool offline:1;};其中包括:
void (*release)(struct device *dev);它不能是空 。

推荐阅读