免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
查看: 3449 | 回复: 7
打印 上一主题 下一主题

linux I2C 驱动编写笔记 [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2012-10-22 09:11 |只看该作者 |倒序浏览
I2C驱动组成有三部分:
  A.i2c 核心驱动   B. i2c总线驱动  C. i2c设备驱动
I2C驱动相关的重要结构:
1.
/**
* struct i2c_driver - represent an I2C device driver
* @class: What kind of i2c device we instantiate (for detect)
* @attach_adapter: Callback for bus addition (deprecated)
* @detach_adapter: Callback for bus removal (deprecated)
* @probe: Callback for device binding
* @remove: Callback for device unbinding
* @shutdown: Callback for device shutdown
* @suspend: Callback for device suspend
* @resume: Callback for device resume
* @alert: Alert callback, for example for the SMBus alert protocol
* @command: Callback for bus-wide signaling (optional)
* @driver: Device driver model driver
* @id_table: List of I2C devices supported by this driver
* @detect: Callback for device detection
* @address_list: The I2C addresses to probe (for detect)
* @clients: List of detected clients we created (for i2c-core use only)
*
* The driver.owner field should be set to the module owner of this driver.
* The driver.name field should be set to the name of this driver.
*
* For automatic device detection, both @detect and @address_data must
* be defined. @class should also be set, otherwise only devices forced
* with module parameters will be created. The detect function must
* fill at least the name field of the i2c_board_info structure it is
* handed upon successful detection, and possibly also the flags field.
*
* If @detect is missing, the driver will still work fine for enumerated
* devices. Detected devices simply won't be supported. This is expected
* for the many I2C/SMBus devices which can't be detected reliably, and
* the ones which can always be enumerated in practice.
*
* The i2c_client structure which is handed to the @detect callback is
* not a real i2c_client. It is initialized just enough so that you can
* call i2c_smbus_read_byte_data and friends on it. Don't do anything
* else with it. In particular, calling dev_dbg and friends on it is
* not allowed.
*/
struct i2c_driver {
        unsigned int class;

        /* Notifies the driver that a new bus has appeared or is about to be
         * removed. You should avoid using this, it will be removed in a
         * near future.
         */
        int (*attach_adapter)(struct i2c_adapter *) __deprecated;
        int (*detach_adapter)(struct i2c_adapter *) __deprecated;

        /* Standard driver model interfaces */
        int (*probe)(struct i2c_client *, const struct i2c_device_id *);
        int (*remove)(struct i2c_client *);

        /* driver model interfaces that don't relate to enumeration  */
        void (*shutdown)(struct i2c_client *);
        int (*suspend)(struct i2c_client *, pm_message_t mesg);
        int (*resume)(struct i2c_client *);

        /* Alert callback, for example for the SMBus alert protocol.
         * The format and meaning of the data value depends on the protocol.
         * For the SMBus alert protocol, there is a single bit of data passed
         * as the alert response's low bit ("event flag").
         */
        void (*alert)(struct i2c_client *, unsigned int data);

        /* a ioctl like command that can be used to perform specific functions
         * with the device.
         */
        int (*command)(struct i2c_client *client, unsigned int cmd, void *arg);

        struct device_driver driver;
        const struct i2c_device_id *id_table;

        /* Device detection callback for automatic device creation */
        int (*detect)(struct i2c_client *, struct i2c_board_info *);
        const unsigned short *address_list;
        struct list_head clients;
};
2.
/**
* struct i2c_client - represent an I2C slave device
* @flags: I2C_CLIENT_TEN indicates the device uses a ten bit chip address;
*        I2C_CLIENT_PEC indicates it uses SMBus Packet Error Checking
* @addr: Address used on the I2C bus connected to the parent adapter.
* @name: Indicates the type of the device, usually a chip name that's
*        generic enough to hide second-sourcing and compatible revisions.
* @adapter: manages the bus segment hosting this I2C device
* @driver: device's driver, hence pointer to access routines
* @dev: Driver model device node for the slave.
* @irq: indicates the IRQ generated by this device (if any)
* @detected: member of an i2c_driver.clients list or i2c-core's
*        userspace_devices list
*
* An i2c_client identifies a single device (i.e. chip) connected to an
* i2c bus. The behaviour exposed to Linux is defined by the driver
* managing the device.
*/
struct i2c_client {
        unsigned short flags;                /* div., see below                */
        unsigned short addr;                /* chip address - NOTE: 7bit        */
                                        /* addresses are stored in the        */
                                        /* _LOWER_ 7 bits                */
        char name[I2C_NAME_SIZE];
        struct i2c_adapter *adapter;        /* the adapter we sit on        */
        struct i2c_driver *driver;        /* and our access routines        */
        struct device dev;                /* the device structure                */
        int irq;                        /* irq issued by device                */
        struct list_head detected;
};
3.
*
* i2c_adapter is the structure used to identify a physical i2c bus along
* with the access algorithms necessary to access it.
*/
struct i2c_adapter {
        struct module *owner;
        unsigned int class;                  /* classes to allow probing for */
        const struct i2c_algorithm *algo; /* the algorithm to access the bus */
        void *algo_data;

        /* data fields that are valid for all devices        */
        struct rt_mutex bus_lock;

        int timeout;                        /* in jiffies */
        int retries;
        struct device dev;                /* the adapter device */

        int nr;
        char name[48];
        struct completion dev_released;

        struct mutex userspace_clients_lock;
        struct list_head userspace_clients;
};
4.
/*
* The following structs are for those who like to implement new bus drivers:
* i2c_algorithm is the interface to a class of hardware solutions which can
* be addressed using the same bus algorithms - i.e. bit-banging or the PCF8584
* to name two of the most common.
*/
struct i2c_algorithm {
        /* If an adapter algorithm can't do I2C-level access, set master_xfer
           to NULL. If an adapter algorithm can do SMBus access, set
           smbus_xfer. If set to NULL, the SMBus protocol is simulated
           using common I2C messages */
        /* master_xfer should return the number of messages successfully
           processed, or a negative value on error */
        int (*master_xfer)(struct i2c_adapter *adap, struct i2c_msg *msgs,
                           int num);
        int (*smbus_xfer) (struct i2c_adapter *adap, u16 addr,
                           unsigned short flags, char read_write,
                           u8 command, int size, union i2c_smbus_data *data);

        /* To determine what the adapter supports */
        u32 (*functionality) (struct i2c_adapter *);
};

论坛徽章:
0
2 [报告]
发表于 2012-10-22 09:40 |只看该作者
问题1:  i2c_adapter结构中rt_mutex 和 mutex 结构的区别

/**
* The rt_mutex structure
*
* @wait_lock:        spinlock to protect the structure
* @wait_list:        pilist head to enqueue waiters in priority order
* @owner:        the mutex owner
*/
struct rt_mutex {
        raw_spinlock_t                wait_lock;
        struct plist_head        wait_list;
        struct task_struct        *owner;
#ifdef CONFIG_DEBUG_RT_MUTEXES
        int                        save_state;
        const char                 *name, *file;
        int                        line;
        void                        *magic;
#endif
};

struct mutex {
        /* 1: unlocked, 0: locked, negative: locked, possible waiters */
        atomic_t                count;
        spinlock_t                wait_lock;
        struct list_head        wait_list;
#if defined(CONFIG_DEBUG_MUTEXES) || defined(CONFIG_SMP)
        struct thread_info        *owner;
#endif
#ifdef CONFIG_DEBUG_MUTEXES
        const char                 *name;
        void                        *magic;
#endif
#ifdef CONFIG_DEBUG_LOCK_ALLOC
        struct lockdep_map        dep_map;
#endif
};

论坛徽章:
0
3 [报告]
发表于 2012-10-22 18:10 |只看该作者
问题2:master_xfer()完成了 驱动和硬件的直接通信。
具体是怎么实现的?

论坛徽章:
0
4 [报告]
发表于 2012-10-22 18:11 |只看该作者
问题3:各各结构之间的关系,是什么样的?
要查看结构体之间的联系,需要知道I2C驱动 的构架/

论坛徽章:
0
5 [报告]
发表于 2012-11-01 10:08 |只看该作者
在论坛找到很好的一个资源
http://blog.chinaunix.net/u3/91522/showart_1886369.html

论坛徽章:
0
6 [报告]
发表于 2013-04-10 10:53 |只看该作者
楼主在linux i2c驱动编写方面有经验吗?    后续有问题想请教请教。

论坛徽章:
0
7 [报告]
发表于 2013-04-10 16:33 |只看该作者
回复 6# txgc_wm


    很久之前做的。。说说看,不知能不能帮你

论坛徽章:
0
8 [报告]
发表于 2013-04-10 17:57 |只看该作者
回复 7# xfortune

暂时没有,以后做了可能会遇到问题。这里,事先打个招呼嘛。^_^
   
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP