您的位置:首页 > 运维架构 > Linux

LinuxI2C子系统之一实例化IC2设备(Client)的四种方法(三、四)

2013-03-22 14:00 337 查看
原创作品,转载时请务必以超链接形式标明文章原始出处:http://blog.csdn.net/gqb666/article/details/8698856,作者:gqb666

终于翻译完了,有不准确的地方,还请大家多多指教。
上接博文:LinuxI2C子系统之一实例化IC2设备(Client)的四种方法(一、二)

 原文件位置:linux源码目录\Documentation\i2c\instantiating-devices                      

                      ===========================================

                                                    怎么实例化I2C设备

                      ===========================================

     与PCI与USB总线不同,I2C总线不能在硬件层就将挂在其上的设备枚举出来。相反地,软件必须清楚哪个设备挂在哪个I2C总线上及各个设备的地址ID。所以,内核驱动代码必须显式地“手动”实例化I2C设备。针对不同设备操作的复杂度及项目及其他需要,目前有四种实例化I2C设备的方法:

第三:为特定的设备枚举I2C总线

   有些时候我们无法获取足够的I2C设备信息,怎么调用i2c_new_probed_device()则更是无从谈起。一个典型的例子是为数众多的主板以及其上的多种显示芯片,这里有几十种搭配方式并且每种的地址就可能有25种(这句理解地不好,请多多指教)。即使给定这些数目巨大的主板信息,也几乎不可能建立起一个完整的可用显示芯片列表,幸运地是可以使用这类显示芯片都有制造商和设备ID寄存器,对其进行枚举并唯一地标示它们。
     这种情况下,I2C设备既不能提前定义然后注册又不能显式地实例化。相反地,i2c-core核心驱动将会在它们的驱动程序加载时尽可能快地枚举它们,如果枚举成功,那么这些I2C设备将会被自动地实例化。为了避免这种机制的副作用,必须保证以下两点:
(1)I2C设备驱动程序必须实现detect()函数,该方法用来读取设备专用寄存器以标示特定设备。
(2)只有可能存在挂载设备和允许被枚举的I2C总线才会被枚举。例如,在TV适配器枚举显示芯片,这是不允许的。
举例:
    见  drivers/hwmon/lm90.c文件中lm90_driver and lm90_detect()函数。
成功枚举并被实例化的设备会在两种情况下(不受先后顺序影响)自动被释放:(1)探测到该设备的驱动程序被卸载的时候(2)所挂的总线要被卸载的时候。
    这里所描述的方法3实际上与内核2.4或者说2.6之前I2C子系统的驱动实现非常类似,但有两点重要的区别:
(1)在不得以的情况下枚举法才可以作为一种实例化设备的方法。如果有可能,方法1和方法2都是(优于方法3)值得推荐的方法。方法可能会引起一些意想不到的副作用,所以在万不得以的情况下不要使用它。
(2)I2C总线必须显式地指定哪类I2C设备驱动可以对它进行枚举(通过填充类位域的方式),尽管所有I2C总线会按默认设置被枚举,而实际上这里的默认设置是空,也就是不会有枚举发生(这段翻译可能有争议)。设置类位域的目的是避免上文所述不可预期的副作用。
    需要再次强调的是,方法3应尽可能的避免使用,显式地实例化设备(方法1和方法2)有更好的安全性和更高的效率。
第四:在用户空间实例化设备

    通常来讲,内核必须要知道I2C设备挂到哪个I2C总线上以及I2C设备的地址(设备ID)。然而有些情况并不是这样,所以Linux使用sysfs接口让用户空间提供这些信息给内核。这种接口在每个I2C总线目录下提供了两个文件结点(new_device和delete_device),这两个文件结点都是只写的,用户必须向它们写入正确的参数来(实例化)创建或者删除I2C设备。
    new_device
有两个参数:I2C设备的名字(字符串)和I2C设备的地址(一个数字,通过用以0x开头的十六进制表示,也可以用十进制表示)。
    delete_device只有一个参数:I2D设备地址。因为同一个I2C总线上不可能挂两个相同设备地址的设备,所以这个地址可以唯一地标示设备。
举例:
创建设备:  

# echo eeprom 0x50 > /sys/bus/i2c/devices/i2c-3/new_device


删除设备:

# echo 0x50 > /sys/bus/i2c/devices/i2c-3/delete_device


   虽然说sysfs接口方法只能在内核代码无法定义设备的情况下使用,但该方法在下列情况非常有用:

(1)I2C设备驱动通过枚举总线的方式来探测设备,但设备所挂的I2C总线却没有将枚举类位域置位,因为枚举将不可能发生的情况。

(2)I2C设备驱动探测设备时,设备的地址却不是预知的。

(3)I2C设备驱动探测设备时,探测过程因为探测过程太严格或者设备不支持探测(你不能预先知道设备商未支持)而失败。

(4)为实验板自己焊上的I2C设备开发驱动程序测试使用时。

    这种sysfs接口被认为是一些I2C驱动架构中实现的force_*模块参数的替代品,该接口已经在I2C核心层得以实现而不是在个别的I2C设备驱动中。它优点突出而且还有个特性:在改变设置时不需要重新装载驱动程序。更有意思的是,你可以在设备驱动装载之前或者不知驱动是否可用的情况下实例化(创建)一个设备,而且你也不需要关心与这个设备对应的驱动程序是哪个。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息