1

从一般的角度来看,我试图弄清楚如何从用户空间访问平台设备。更具体地说,我有一个 EMIF 控制器和 SoC,我已将其添加到我的设备树中,我相信它已正确绑定到预先编写的 EMIF 平台设备驱动程序。现在我想弄清楚如何从用户空间应用程序访问这个 EMIF 设备。我遇到了几个不同的主题,这些主题似乎与这个问题有一些联系,但我不太清楚它们之间的关系。

1)当我读到似乎大多数 I/O 是通过使用由创建的设备节点完成的mknod(),我是否需要创建一个设备节点才能访问该设备?

2)我读过一些关于编写内核模块(字符?块?)的线程,该模块可以与用户空间和平台设备驱动程序接口,并将其用作中介。

3) 我已经阅读了关于使用mmap()将我的平台设备的内存映射到我的虚拟内存空间的可能性。这可能吗?

4)似乎当EMIF驱动被实例化时,它调用了probe()函数。用户空间应用程序会在驱动程序中调用哪些函数?

4

2 回答 2

2

目前尚不完全清楚您需要做什么(我应该提醒一下,我没有使用 EMIF 或专门使用“平台设备”的经验),但这里有一些概述可以帮助您入门:

  1. 是的,提供对设备的访问的常用方法是通过设备节点。通常这种访问是由字符设备驱动程序提供的,除非有一些更具体的方式来提供它。大多数情况下,如果应用程序“直接”与您的驱动程序对话,它就是一个字符设备。大多数其他类型的设备用于与其他内核子系统的接口:例如,块设备通常用于提供从文件系统驱动程序(例如)到底层磁盘驱动器的访问;网络驱动程序提供从内核 TCP/IP 堆栈等对网络的访问。

    您的驱动程序可以支持几种字符设备方法或入口点,但最常见的是“读取”(即,如果用户空间程序打开您的设备并从中执行读取(2)),“写入” (类似于 write(2))和“ioctl”(通常用于配置/管理任务,这些任务不会自然地陷入读取或写入)。请注意,mknod(2) 仅创建设备的用户空间端。内核中需要有相应的设备驱动程序(在 mknod 调用中给出的“主要设备号”将用户空间节点与驱动程序链接起来)。

    对于在文件系统中实际创建设备节点,如果您在设置设备时调用正确的内核函数,这可以是自动化的(即该节点将自动显示在 /dev 中)。有一个特殊的守护进程从内核获取通知并通过执行 mknod(2) 系统调用来响应。

  2. 内核模块只是一种创建驱动程序或其他内核扩展的动态可加载方式。它可以创建角色、块或网络设备(等),但静态链接模块也可以。功能上存在一些差异,主要是因为并非您可能想要使用的所有内核函数都“导出”到(即可见)动态加载的模块。

  3. 可以支持将设备内存映射到用户虚拟内存空间。这将由另一个驱动程序入口点 (mmap) 实现。有关 char 驱动程序可以支持的所有入口点,请参见 struct file_operations。

  4. 这几乎取决于您:这取决于应用程序需要能够做什么。内核中有许多驱动程序不向用户空间提供直接功能,只为其他内核代码提供功能。至于“probe”,各种接口中定义了很多probe函数。在大多数情况下,这些由内核(或者可能由“更高级别的“类”驱动程序')调用,以允许特定的驱动程序发现、识别和“声明”单个设备。它们(探测功能)通常与提供来自用户空间的访问没有任何直接关系,但我很可能在特定界面中遗漏了一些东西。

于 2014-04-08T22:03:13.537 回答
0

您需要创建一个设备节点才能访问该设备。

当驱动程序找到匹配的设备时,会调用探测函数。

有关平台设备 API 的信息,以下文章可能会有用。

平台设备 API 平台设备和设备树

于 2014-04-10T10:17:56.643 回答