以下是在学习电池驱动中遇到的知识点之_iomem

A new I/O memory access mechanism


Most reasonably current cards for the PCI bus (and others) provide one or more I/O memory regions to the bus. By accessing those regions, the

现在绝大多数PCI总线卡(和其他人)提供一个或多个I / O总线的内存区域。通过访问这些内存区域,

processor can communicate with the peripheral and make things happen. A look at /proc/iomem will show the I/O memory regions which have been registered on a given system.

处理器可以与外围设备通信和做出一些反应。查看/ proc / iomem将显示I / O内存区域已被注册在一个给定的系统中的信息。如下:

[fulinux@centos6 ~]$ vim /proc/iomem 
 /p/iomem                                                                                                                           
00000000-00000fff : reserved
00001000-0009f7ff : System RAM
0009f800-0009ffff : reserved
000a0000-000bffff : PCI Bus 0000:00
000c0000-000dffff : PCI Bus 0000:00
  000c0000-000cdbff : Video ROM
  000cdc00-000cffff : pnp 00:0d
000e0000-000effff : pnp 00:0d
000f0000-000fffff : reserved
  000f0000-000fffff : System ROM
00100000-dafcffff : System RAM
  01000000-014f4774 : Kernel code
  014f4775-01c07c6f : Kernel data
  01d4c000-02010023 : Kernel bss
  03000000-0affffff : Crash kernel
dafd0000-dafd2fff : ACPI Non-volatile Storage
dafd3000-dafeffff : ACPI Tables
daff0000-daffffff : reserved
db000000-dbffffff : RAM buffer
dfa00000-febfffff : PCI Bus 0000:00
  dfa00000-dfbfffff : PCI Bus 0000:01
  dfc00000-dfdfffff : PCI Bus 0000:01
  e0000000-efffffff : 0000:00:02.0
  f4000000-f7ffffff : PCI MMCONFIG 0 [00-3f]
    f4000000-f7ffffff : reserved
      f4000000-f7ffffff : pnp 00:0c
  fb800000-fbbfffff : 0000:00:02.0
  fbe00000-fbefffff : PCI Bus 0000:02
    fbec0000-fbefffff : 0000:02:00.0
      fbec0000-fbefffff : atl1c
  fbff8000-fbffbfff : 0000:00:1b.0
    fbff8000-fbffbfff : ICH HD audio
  fbffc000-fbffc0ff : 0000:00:1f.3
  fbffd000-fbffd3ff : 0000:00:1d.0
    fbffd000-fbffd3ff : ehci_hcd
  fbffe000-fbffe3ff : 0000:00:1a.0
    fbffe000-fbffe3ff : ehci_hcd
  fbfff000-fbfff00f : 0000:00:16.0
fec00000-ffffffff : reserved
  fec00000-fec00fff : IOAPIC 0
  fed00000-fed003ff : HPET 0
  fed10000-fed1dfff : pnp 00:0d
  fed20000-fed8ffff : pnp 00:0d
  fee00000-fee00fff : Local APIC
    fee00000-fee00fff : pnp 00:0d
  ffb00000-ffb7ffff : pnp 00:0d
  fff00000-ffffffff : pnp 00:0d
100000000-21fdfffff : System RAM
21fe00000-21fffffff : RAM buffer

Advertisement

介绍

To work with an I/O memory region, a driver is supposed to map that region with a call to 
ioremap(). The return value from 
ioremap() is a magic cookie which can be passed to a set of accessor functions (with names
为了处理一个I/O存储区域,设备驱动通过ioremap()函数调用来映射这片区域。ioremap()函数的返回一个a magic cookie值可以用来传输到存取函数中去(例如
 like 
readb() or 
writel()) to actually move data to or from the I/O memory. On some architectures (notably x86), I/O memory is truly mapped into the kernel's memory space, so those accessor functions turn into a
名为readb()和writel()函数),用来将数据放入或取出这片区域。在一些体系架构中(尤其是x86体系架构),I/O存储区域被映射到内核存储空间中去,所以那些存取函数就

 straightforward pointer dereference. Other architectures require more complicated operations.
明确的变为了指针,其他的体系结构需要复杂的操作。

There have been some longstanding problems with this scheme. Drivers written for the x86 architecture have often been known to simply dereference I/O memory addresses directly, rather than using the accessor functions. That approach works on the x86, but breaks on other architectures. Other drivers, knowing that I/O memory addresses are not real pointers, store them in integer variables; that works until they encounter a system with a physical address space which doesn't fit into 32 bits. And, in any case, readb() and friends perform no type checking, and thus fail to catch errors which could be found at compile time.

The 2.6.9 kernel will contain a series of changes designed to improve how the kernel works with I/O memory. The first of these is a new __iomem annotation used to mark pointers to I/O memory. These annotations work much like the __user markers, except that they reference a different address space. As with __user, the__iomem marker serves a documentation role in the kernel code; it is ignored by the compiler. When checking the code with sparse, however, developers will see a whole new set of warnings caused by code which mixes normal pointers with __iomem pointers, or which dereferences those pointers.

The next step is the addition of a new set of accessor functions which explicitly require a pointer argument. These functions are:

    unsigned int ioread8(void __iomem *addr);
unsigned int ioread16(void __iomem *addr);
unsigned int ioread32(void __iomem *addr);
void iowrite8(u8 value, void __iomem *addr);
void iowrite16(u16 value, void __iomem *addr);
void iowrite32(u32 value, void __iomem *addr);

By default, these functions are simply wrappers around readb() and friends. The explicit pointer type for the argument will generate warnings, however, if a driver passes in an integer type.

There are "string" versions of these operations:

    extern void ioread8_rep(void __iomem *port, void *buf,
unsigned long count);

All of the other variants are defined as well, of course.

There is actually one other twist to these functions. Some drivers have to be able to use either I/O memory or I/O ports, depending on the architecture and the device. Some such drivers have gone to considerable lengths to try to avoid duplicating code in those two cases. With the new accessors, a driver which finds it needs to work with x86-style ports can call:

    void __iomem *ioport_map(unsigned long port, unsigned int count);

The return value will be a cookie which allows the mapped ports to be treated as if they were I/O memory; functions like ioread8() will automatically do the right thing. For PCI devices, there is a new function:

    void __iomem *pci_iomap(struct pci_dev *dev, int base,
unsigned long maxlen);

For this function, the base can be either a port number or an I/O memory address, and the right thing will be done.

As of 2.6.9-rc2, there are no in-tree users of the new interface. That can be expected to change soon as patches get merged and the kernel janitors get to work. For more information on the new I/O memory interface and the motivation behind it, see this explanation from Linus.

__iomem解析的更多相关文章

  1. Linux 字符设备驱动—— ioremap() 函数解析

    一. ioremap() 函数基础概念 几乎每一种外设都是通过读写设备上的相关寄存器来进行的,通常包括控制寄存器.状态寄存器和数据寄存器三大类,外设的寄存器通常被连续地编址.根据CPU体系结构的不同, ...

  2. linux device tree源代码解析--转

    //Based on Linux v3.14 source code Linux设备树机制(Device Tree) 一.描述 ARM Device Tree起源于OpenFirmware (OF), ...

  3. linux device tree源代码解析【转】

    转自:http://blog.csdn.net/Tommy_wxie/article/details/42806457 //Basedon Linux v3.14 source code Linux设 ...

  4. 【原】Android热更新开源项目Tinker源码解析系列之三:so热更新

    本系列将从以下三个方面对Tinker进行源码解析: Android热更新开源项目Tinker源码解析系列之一:Dex热更新 Android热更新开源项目Tinker源码解析系列之二:资源文件热更新 A ...

  5. .NET Core中的认证管理解析

    .NET Core中的认证管理解析 0x00 问题来源 在新建.NET Core的Web项目时选择“使用个人用户账户”就可以创建一个带有用户和权限管理的项目,已经准备好了用户注册.登录等很多页面,也可 ...

  6. Html Agility Pack 解析Html

    Hello 好久不见 哈哈,今天给大家分享一个解析Html的类库 Html Agility Pack.这个适用于想获取某网页里面的部分内容.今天就拿我的Csdn的博客列表来举例. 打开页面  用Fir ...

  7. 【原】Android热更新开源项目Tinker源码解析系列之一:Dex热更新

    [原]Android热更新开源项目Tinker源码解析系列之一:Dex热更新 Tinker是微信的第一个开源项目,主要用于安卓应用bug的热修复和功能的迭代. Tinker github地址:http ...

  8. 【原】Android热更新开源项目Tinker源码解析系列之二:资源文件热更新

    上一篇文章介绍了Dex文件的热更新流程,本文将会分析Tinker中对资源文件的热更新流程. 同Dex,资源文件的热更新同样包括三个部分:资源补丁生成,资源补丁合成及资源补丁加载. 本系列将从以下三个方 ...

  9. 多线程爬坑之路-Thread和Runable源码解析之基本方法的运用实例

    前面的文章:多线程爬坑之路-学习多线程需要来了解哪些东西?(concurrent并发包的数据结构和线程池,Locks锁,Atomic原子类) 多线程爬坑之路-Thread和Runable源码解析 前面 ...

随机推荐

  1. Filter和FilterChain具体的使用说明

    一.Filter的介绍及使用 什么是过滤器? 与Servlet类似,过滤器是一些web应用程序组件,能够绑定到一个web应用程序中.可是与其它web应用程序组件不同的是,过滤器是"链&quo ...

  2. hdu 4803 贪心/思维题

    http://acm.hdu.edu.cn/showproblem.php?pid=4803 话说C++还卡精度么?  G++  AC  C++ WA 我自己的贪心策略错了 -- 就是尽量下键,然后上 ...

  3. linux编程掌握常用命令

    1)编译应用程序 make -f makefile_5_2 clean make -f makefile_5_2 2)关于共享目录 在linux虚拟机的/mnt/hgfs下可看到该文件夹 3)cd命令 ...

  4. 深入学习微框架:Spring Boot

    Spring Boot是由Pivotal团队提供的全新框架,其设计目的是用来简化新Spring应用的初始搭建以及开发过程.该框架使用了特定的方式来进行配置,从而使开发人员不再需要定义样板化的配置.通过 ...

  5. CloudStack搭建KVM环境

    软件环境:agent:CentOS 6.3,minimal安装,CPU启用VT management server:CentOS 6.3,minimal安装 存储:CentOS 6.3 搭建在mana ...

  6. [IOS]Setting Bundle + StoryBoard

    用storyboard添加一个导航栏,其中首页有一个switch,与setting联动,还有一个button,使用modal连接另一个viewControl,其上也有一个按钮,按下销毁本viewCon ...

  7. Android高手进阶——Adapter深入理解与优化

    Android高手进阶--Adapter深入理解与优化 通常是针对包括多个元素的View,如ListView,GridView.ExpandableListview,的时候我们是给其设置一个Adapt ...

  8. Android中ProgressDialog的应用

    下面通过实现点击按钮来显示加载框,2秒后自动消失. 1.首先在layout的xml中添加一个按钮: <Button android:id="@+id/button1" and ...

  9. finalize过程

    之前说过case有两个 switch (startOpt) { case FORMAT: boolean aborted = format(conf, true); System.exit(abort ...

  10. 与众不同 windows phone (25) - Input(输入)之捕获 UIElement 之外的触控操作, Silverlight 方式捕获手势操作, XNA 方式捕获手势操作, 多点触控

    原文:与众不同 windows phone (25) - Input(输入)之捕获 UIElement 之外的触控操作, Silverlight 方式捕获手势操作, XNA 方式捕获手势操作, 多点触 ...