数码资讯
linux驱动下平台总线的详细解决方案
在设备驱动程序中经常看到相关的字段和平台,分布在多个角落的驱动程序中,其中一个更为重要的机制在2.6内核中,了解其原理后,对驱动程序的分析很有帮助,下面简单介绍一下: 在Linux2.6内核设备模型,我们在乎的总线,设备和三个实体。总线绑定设备和驱动程序。当系统注册一个设备时,它会找到与其匹配的驱动
选购提示
关注价格、性能、续航、售后和真实使用场景,理性比较后再下单。
在设备驱动程序中经常看到相关的字段和平台,分布在多个角落的驱动程序中,其中一个更为重要的机制在2.6内核中,了解其原理后,对驱动程序的分析很有帮助,下面简单介绍一下:
在Linux2.6内核设备模型,我们在乎的总线,设备和三个实体。总线绑定设备和驱动程序。当系统注册一个设备时,它会找到与其匹配的驱动程序,相反,当系统为每个驱动程序注册时,就会找到匹配设备,匹配是由总线完成的。
一个真正的Linux设备驱动程序通常需要挂在总线上,本身依赖于PCI、USB、I2C、SPI等设备,这是没有问题的,但在嵌入式系统中,嵌入式系统,集成外设控制器独立挂在内存空间之外,它是没有连接到总线的基础上。这样的背景下,发明了一种称为Linux虚拟总线平台总线。
集成在SOC系统中的集成外围设备(I2C、LCD、SPI、RTC等)被视为平台设备,它们本身就是字符类型的设备。
从Linux2.6内核,一套新的驾驶员管理和注册机制,介绍了platform_device和platform_driver,。在Linux大多数的设备驱动程序可以使用这个机制,该装置是在platform_device表示,和司机登记platform_driver。
platform_device结构包括 / / H platform_device Linux。
结构platform_device
{
常量名称*
U32 ID;
结构设备开发;
U32 num_resources; / /各种二手设备的资源数量
结构资源*;资源的使用
}
platform_driver结构包括 / / H platform_device Linux。
结构platform_driver
{
Int(探头)(结构platform_device *);
Int(*删除)(结构platform_device *);
void(*关机)(结构platform_device *);
Int(*暂停)(结构platform_device *,pm_message_t状态);
Int(* suspend_late)(结构platform_device *,pm_message_t状态);
Int(* resume_early)(结构platform_device *);
Int(*简历)(结构platform_device *);
结构pm_ext_ops下午;
device_driver驱动结构;
};
系统定义了平台总线platform_bus_type bus_type实例,并决定了其成员的功能匹配和驱动匹配设备()。
匹配platform_device和platform_driver主要看是否这两个字段的名称是相同的。(名称必须匹配相同)
使用platform_device_register()函数来登记一个平台装置。
一般来说,platform_device是平台的BSP文件定义,平台和设备注册到系统通过platform_add_devices()函数
登记和注销platform_driver:
platform_driver_register()
platform_driver_unregister()
以S3C2440 LCD驱动器为例:
在BSP文件中:
结构platform_device s3c_device_lcd = { {
名称
id = 1,
num_resources = array_size(s3c_lcd_resource),
s3c_lcd_resource资源=,
。
dma_mask = s3c_device_lcd_dmamask,
coherent_dma_mask = 0xfffffffful。
}
};
为了完成LCD设备注册,放进smdk2440_devices数组定义在 / / /弓臂mach-s3c2440 / mach-smdk2440 C:
静态结构platform_device * smdk2440_devices __initdata = { { { }
…
…
s3c_device_lcd,
};
通过platform_add_devices(smdk2440_devices,array_size(smdk2440_devices));注册
在相应的驱动程序文件:( / / / s3c2410fb司机视频。C)
静态结构platform_driver s3c2410fb_driver = { {
。探头= s3c2410fb_probe /驱动器检测
。删除= __devexit_p(s3c2410fb_remove), / /删除驱动
s3c2410fb_suspend暂停=,
s3c2410fb_resume简历=,
驱动程序{ {
名称
业主= this_module,
},
};
静态变量__devinit s3c2410_fb_init(void)
{
返回platform_driver_register(s3c2410fb_driver);
}
静态__exit s3c2410fb_cleanup(void)
{
platform_driver_unregister(s3c2410fb_driver);
}
当注册成功时,您将在以下两个目录中看到设备节点:
系统/平台/设备/
系统/平台/
平台设备资源与数据:
资源结构:
结构资源
{
resource_size_t开始;
resource_size_t结束;
常量char *名称;
无符号长标志;
结构资源*父,*兄弟,*子;
};
我们通常关心开始、结束和标志的3个字段,它们表示开始值、结束值和资源、标志的类型。
它可以ioresource_io,ioresource_mem,ioresource_irq,ioresource_dma等等。
如lcd资源:
静态结构资源s3c_lcd_resource { } = { {
{ 0 } { {
。开始= s3c24xx_pa_lcd, / /的液晶显示器(LCD控制器的IO资源开始登记地址)
s3c24xx_pa_lcd + s3c24xx_sz_lcd。= 1 / /结束地址
ioresource_mem旗帜=,
},
{ 1 } { {
。开始= irq_lcd, / /液晶中断号
irq_lcd结束=,
ioresource_irq旗帜=,
}
};
在platform_get_resource驱动等功能获得设备资源()或()platform_get_irq
结构资源* platform_get_resource(struct platform_device *,unsigned int unsigned int);
国际platform_get_irq(struct platform_device * dev,unsigned int num);
获得的内存或IO资源可以使用之前需要ioremap
进入IRQ资源需要request_irq
除了BSP的设备资源定义外,还可以附加一些数据,因为设备硬件描述除了中断、内存、DMA通道外,还可能有一些配置信息,配置信息也依赖于主板,不适合直接放置在。
备用驱动器本身,因此,平台还提供了platform_data支持。
platform_data可以自定义,如DM9000的驱动程序,来描述一些与platform_data属性:
静态结构dm9000_plat_data s3c_dm9000_platdata = { {
dm9000_platf_16bitonly旗帜=,
};
静态结构platform_device s3c_device_dm9000 = { {
名称=DM9000
id = 0,
num_resources = array_size(s3c_dm9000_resource),
s3c_dm9000_resource资源=,
。
platform_data = s3c_dm9000_platdata,
}
};
在相应的驱动器中使用:
结构dm9000_plat_data *数据= pdev -> dev.platform_data;
访问platform_data
找到一个与平台相关的驱动程序,从BSP文件中分析其结构,分析其底层硬件操作,使之很快熟悉平台的工作原理。
在Linux2.6内核设备模型,我们在乎的总线,设备和三个实体。总线绑定设备和驱动程序。当系统注册一个设备时,它会找到与其匹配的驱动程序,相反,当系统为每个驱动程序注册时,就会找到匹配设备,匹配是由总线完成的。
一个真正的Linux设备驱动程序通常需要挂在总线上,本身依赖于PCI、USB、I2C、SPI等设备,这是没有问题的,但在嵌入式系统中,嵌入式系统,集成外设控制器独立挂在内存空间之外,它是没有连接到总线的基础上。这样的背景下,发明了一种称为Linux虚拟总线平台总线。
集成在SOC系统中的集成外围设备(I2C、LCD、SPI、RTC等)被视为平台设备,它们本身就是字符类型的设备。
从Linux2.6内核,一套新的驾驶员管理和注册机制,介绍了platform_device和platform_driver,。在Linux大多数的设备驱动程序可以使用这个机制,该装置是在platform_device表示,和司机登记platform_driver。
platform_device结构包括 / / H platform_device Linux。
结构platform_device
{
常量名称*
U32 ID;
结构设备开发;
U32 num_resources; / /各种二手设备的资源数量
结构资源*;资源的使用
}
platform_driver结构包括 / / H platform_device Linux。
结构platform_driver
{
Int(探头)(结构platform_device *);
Int(*删除)(结构platform_device *);
void(*关机)(结构platform_device *);
Int(*暂停)(结构platform_device *,pm_message_t状态);
Int(* suspend_late)(结构platform_device *,pm_message_t状态);
Int(* resume_early)(结构platform_device *);
Int(*简历)(结构platform_device *);
结构pm_ext_ops下午;
device_driver驱动结构;
};
系统定义了平台总线platform_bus_type bus_type实例,并决定了其成员的功能匹配和驱动匹配设备()。
匹配platform_device和platform_driver主要看是否这两个字段的名称是相同的。(名称必须匹配相同)
使用platform_device_register()函数来登记一个平台装置。
一般来说,platform_device是平台的BSP文件定义,平台和设备注册到系统通过platform_add_devices()函数
登记和注销platform_driver:
platform_driver_register()
platform_driver_unregister()
以S3C2440 LCD驱动器为例:
在BSP文件中:
结构platform_device s3c_device_lcd = { {
名称
id = 1,
num_resources = array_size(s3c_lcd_resource),
s3c_lcd_resource资源=,
。
dma_mask = s3c_device_lcd_dmamask,
coherent_dma_mask = 0xfffffffful。
}
};
为了完成LCD设备注册,放进smdk2440_devices数组定义在 / / /弓臂mach-s3c2440 / mach-smdk2440 C:
静态结构platform_device * smdk2440_devices __initdata = { { { }
…
…
s3c_device_lcd,
};
通过platform_add_devices(smdk2440_devices,array_size(smdk2440_devices));注册
在相应的驱动程序文件:( / / / s3c2410fb司机视频。C)
静态结构platform_driver s3c2410fb_driver = { {
。探头= s3c2410fb_probe /驱动器检测
。删除= __devexit_p(s3c2410fb_remove), / /删除驱动
s3c2410fb_suspend暂停=,
s3c2410fb_resume简历=,
驱动程序{ {
名称
业主= this_module,
},
};
静态变量__devinit s3c2410_fb_init(void)
{
返回platform_driver_register(s3c2410fb_driver);
}
静态__exit s3c2410fb_cleanup(void)
{
platform_driver_unregister(s3c2410fb_driver);
}
当注册成功时,您将在以下两个目录中看到设备节点:
系统/平台/设备/
系统/平台/
平台设备资源与数据:
资源结构:
结构资源
{
resource_size_t开始;
resource_size_t结束;
常量char *名称;
无符号长标志;
结构资源*父,*兄弟,*子;
};
我们通常关心开始、结束和标志的3个字段,它们表示开始值、结束值和资源、标志的类型。
它可以ioresource_io,ioresource_mem,ioresource_irq,ioresource_dma等等。
如lcd资源:
静态结构资源s3c_lcd_resource { } = { {
{ 0 } { {
。开始= s3c24xx_pa_lcd, / /的液晶显示器(LCD控制器的IO资源开始登记地址)
s3c24xx_pa_lcd + s3c24xx_sz_lcd。= 1 / /结束地址
ioresource_mem旗帜=,
},
{ 1 } { {
。开始= irq_lcd, / /液晶中断号
irq_lcd结束=,
ioresource_irq旗帜=,
}
};
在platform_get_resource驱动等功能获得设备资源()或()platform_get_irq
结构资源* platform_get_resource(struct platform_device *,unsigned int unsigned int);
国际platform_get_irq(struct platform_device * dev,unsigned int num);
获得的内存或IO资源可以使用之前需要ioremap
进入IRQ资源需要request_irq
除了BSP的设备资源定义外,还可以附加一些数据,因为设备硬件描述除了中断、内存、DMA通道外,还可能有一些配置信息,配置信息也依赖于主板,不适合直接放置在。
备用驱动器本身,因此,平台还提供了platform_data支持。
platform_data可以自定义,如DM9000的驱动程序,来描述一些与platform_data属性:
静态结构dm9000_plat_data s3c_dm9000_platdata = { {
dm9000_platf_16bitonly旗帜=,
};
静态结构platform_device s3c_device_dm9000 = { {
名称=DM9000
id = 0,
num_resources = array_size(s3c_dm9000_resource),
s3c_dm9000_resource资源=,
。
platform_data = s3c_dm9000_platdata,
}
};
在相应的驱动器中使用:
结构dm9000_plat_data *数据= pdev -> dev.platform_data;
访问platform_data
找到一个与平台相关的驱动程序,从BSP文件中分析其结构,分析其底层硬件操作,使之很快熟悉平台的工作原理。
声明:本文内容用于数码产品信息整理与选购参考,具体价格、库存、售后政策以官方渠道和电商页面实时信息为准。