Linux平臺驅動設備總線模型
阿新 • • 發佈:2019-03-17
gist linux 分開 圖片 color ase const code 而且
Linux中的Platform總線是虛擬總線,它把驅動和設備的註冊都分開來,對於他們的牽紅線(匹配)過程,提供了“總線-設備-驅動”模型。
它的結構如下圖所示:
- 為什麽要這麽做?
試想,如果設備和驅動不分開,那麽不同設備將會產生大量驅動(代碼冗余),而且維護起來工作量很大。
Platform模型則把穩定不變的部分放在driver,把盡量可變需要設置的部分放到device端,並且兩邊分別註冊管理。
這樣做有如下好處:
- 平臺設備都掛在一條Platform總線上
- 設備和驅動代碼隔離,可移植性和擴展性強
- 適用範圍
適用於可選的平臺資源,例如燈、按鍵、LCD等
- 常用API
註冊設備
int platform_device_register(struct platform_device *pdev);
註銷設備
void platform_device_unregister(struct platform_device *pdev);
註冊驅動
int platform_driver_register(struct platform_driver *drv);
註銷驅動
void platform_driver_unregister(struct platform_driver *drv);
獲取平臺資源
struct resource *platform_get_resource(struct platform_device *dev, unsigned int type, unsigned int num); int platform_get_irq(struct platform_device *dev, unsigned int num); struct resource *platform_get_resource_byname(struct platform_device *dev, unsigned int type, const char *name);int platform_get_irq_byname(struct platform_device *dev, const char *name);
- 基本使用
設備端註冊
1 /************************ arch/xxx/xxx_platform.c ************************/ 2 static void device_release(struct device *dev) 3 { 4 } 5 6 static struct resource xxx_res[]={ 7 [0]={ 8 .start = 11, 9 .end = 22, 10 .flags = IORESOURCE_MEM, 11 }, 12 [1]={ 13 .start = 33, 14 .end = 44, 15 .flags = IORESOURCE_IRQ, 16 }, 17 }; 18 19 struct platform_device xxx_device = { 20 .id = -1, 21 .name = "xxx_device" 22 .resource = xxx_res, 23 .num_resources = ARRAY_SIZE(xxx_res); 24 .dev = { 25 .release = device_release, /* 一般要有改函數,否則驅動卸載會異常 */ 26 }, 27 }; 28 29 static int __init xxx_platform_init(void) 30 { 31 return platform_device_register(&xxx_device); 32 } 33 34 static void __exit xxx_platform_exit(void) 35 { 36 platform_device_unregister(&xxx_device); 37 } 38 39 module_init(xxx_platform_init); 40 module_exit(xxx_platform_exit);
驅動註冊
1 /************************ driver/xxx/xxx_driver.c ************************/ 2 static int driver_probe(struct platform_device *dev) 3 { 4 struct resource * res = platform_get_resource(dev, IORESOURCE_MEM, 0); 5 ... 6 res=platform_get_resource(dev,IORESOURCE_IRQ,0); 7 ... 8 return 0; 9 } 10 11 static int driver_remove(struct platform_device *dev) 12 { 13 return 0; 14 } 15 16 static sturct platform_driver xxx_driver = { 17 .probe = driver_probe, 18 .remove = driver_remove, 19 .driver = { 20 .name = "xxx_device" 21 }, 22 }; 23 24 static int __init xxx_driver_init(void) 25 { 26 return platform_driver_register(&xxx_driver); 27 } 28 29 static void __exit xxx_driver_exit(void) 30 { 31 platform_driver_unregister(&xxx_driver); 32 } 33 34 module_init(xxx_driver_init); 35 module_exit(xxx_driver_exit);
- 實現原理
TBD
Linux平臺驅動設備總線模型