SPI内核模块,如何实例化驱动?

问题描述 投票:0回答:2

我的任务是将 spi 驱动程序导入到运行 Openwrt 的现有平台中。
在“成功”构建完整的 Openwrt:软件包和与平台中运行的软件包和内核相匹配的内核(包括 spidev 内核模块)后,我在使该模块工作时遇到了一些麻烦。
驱动程序的**insmod**无错误地终止,并且我看到在**/sys/class**中创建了目录**spidev**,但它是空的。
查看 spidev 内核模块的代码,**probe** 函数引起了我的注意。我的感觉是这个函数实际上是分配次设备号并使设备可供使用。但我不清楚它是谁,或者应该叫什么。
我的另一个疑问是关于架构的。 spi 取决于底层架构,在我的例子中是 MT7620 soc,它是一个 mipsel 架构,具有特定的 spi 代码。根据我的理解,这个 SOC 特定代码由 spidev 内核模块包装,这两个实体之间的链接应该是
status = spi_register_driver(&spidev_spi_driver);

static int __init spidev_init(void)

功能。
再说一次,我还不太确定自己在写什么,我来这里寻求指导。

kernel-module spi
2个回答
1
投票

首先,您可能需要阅读 Linux 设备驱动程序 - 第 14 章

一般来说,在 Linux 内核中,

devices
drivers
位于
bus
(
subsystem
) 上。您必须使用函数
register_device()
register_driver()
来注册它们(确切的名称取决于子系统)。当设备或驱动程序注册时,
subsystem
将尝试将
devices
drivers
匹配。如果它们匹配,则
subsystem
调用驱动程序的函数
probe()
。因此,
probe()
函数的执行可以由驱动程序注册或设备注册触发。这也意味着该设备在执行
probe()

之前就存在

回到您的具体案例:SPI。要注册设备实例,您需要使用spi_alloc_devicespi_add_devicespi_new_device。这段代码该放在哪里?这取决于您的需要。通常,SPI 设备在某些架构文件或设备树描述中声明。也许你也可以在模块中完成它(不确定)。

spidev
是一个Linux设备驱动程序,它将SPI原始接口导出到用户空间。这意味着一旦您注册了 SPI 设备实例,驱动程序
spidev
就会控制它。实际上,
spidev
什么也不做:它等待用户空间程序在 SPI 总线上读/写数据。因此,您最终将在用户空间中为您的设备编写驱动程序。


0
投票

首先我们讨论的是SPI控制器驱动程序还是SPI设备驱动程序? 我认为是后者。

简而言之,

spidev
只是一个用户空间接口,一个不知道任何底层协议的字符设备驱动程序。

spidev
不能也无法识别正在与之通信的设备,它不知道它是FLASH、CODEC、EEPROM,并且不了解协议,它不了解它处理的数据部分是地址、操作码还是数据。

您需要针对特定 SPI 设备的特定内核驱动程序。

内核将尝试通过设备树 SPI 节点的设备树兼容属性将您的驱动程序与设备进行匹配:

.compatible = "tcg,tpm_tis-spi"n

如果匹配,它将调用驱动程序内的

probe()
函数,该函数 将使用设备树 SPI 节点中提供的数据初始化驱动程序和设备。

并尝试与设备本身进行通信,读取ID寄存器以进一步识别设备,因为该驱动程序知道该设备使用的协议。

© www.soinside.com 2019 - 2024. All rights reserved.