4

我正在努力从 Linux 用户空间读取(和写入)硬件寄存器。目标是配置一些 GPIO 引脚,并能够设置和读取这些引脚。

根据处理器的规范(来自飞思卡尔的 imx27),控制 GPIO 的寄存器组的物理地址是 0x10015000

我的假设是我可以使用这样的东西:

unsigned long *gpio;
fd = open("/dev/mem", O_RDWR);
gpio = (unsigned long *) mmap(0, getpagesize(), PROT_READ|PROT_WRITE, MAP_SHARED, fd, 0x10015000);

我现在希望能够读取数据并将数据设置到处理器中的寄存器。问题是我阅读的位置无关紧要,我总是得到 0。

例如,物理位置 0x10015220 中的寄存器包含一个寄存器,显示哪些引脚在我们作为 GPIO。这默认为 0xFFFFFFFF。阅读这个寄存器,我希望得到不同于 0 的东西:

printf("PTC_GIUS: 0x%08lX\n", gpio[0x220]);

PTC_GIUS: 0x00000000.

我哪里错了?

4

3 回答 3

4

应该mmap工作。/dev/mem您是否尝试过以 root 身份运行您的代码?也许某些安全措施阻止您的程序访问地址空间。还要确保您传递了正确的 GPIO 空间的物理地址。

您使用的方法在我的运行 linux 的 Cortex-A8 ARM 板上运行没有问题。

如果你不能让它工作,除了为 gpio 找到或编写一个设备驱动程序之外你无能为力(顺便说一句,编写一个并不)。

幸运的是,有人已经为您做到了。您的文件系统中是否存在名为的节点/dev/gpio?如果是这样,您已经有一个驱动程序。

谷歌搜索/dev/gpio将为您提供有关如何使用它的所有详细信息。您还可以找到一个简单的 gpio 驱动程序的源代码,您可以对其进行修改以满足您的需要。

于 2009-10-09T10:09:08.187 回答
2

此外,如果您使用的是 2009 年及以后的内核源代码,如果您希望您的内存访问不被缓存,则应该/dev/mem使用设置的标志打开。O_SYNC

于 2011-09-27T19:17:43.500 回答
1

如果您使用的是最新版本的 Linux 内核,它可能会阻止对/dev/mem设备的访问。用户模式访问该设备已被弃用且危险。它主要用于用户模式访问 X 中的视频内存。在嵌入式项目中,访问内存映射硬件(如 GPIO)可能很有用。

检查您的内核编译标志CONFIG_STRICT_DEVMEM或其他限制访问/dev/mem. 它可能错误地阻止了对该内存范围的访问。

然而,正如 Nils 提到的,最好的解决方案是为 iMX27 找到一个 gpio 模块或自己编写。

于 2011-06-22T20:13:21.410 回答