1 iic adapter驱动架构
i2c adapter设备是挂载于platform bus
整体重点架构如下
-
分配
struct i2c_adapter *adap = kzalloc(sizeof(struct i2c_adapter), GFP_KERNEL);
-
设置
adapter->owner = THIS_MODULE; adapter->algo = &i2c_algo;
-
注册
ret = i2c_add_adapter(adapter); // 动态分配nr ret = i2c_add_numbered_adapter(adapter); // nr = -1则动态分配nr,否则则指定nr
-
卸载
i2c_del_adapter(adapter);
2 常用数据结构解析
2.1 i2c_adapter
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 */
const struct i2c_lock_operations *lock_ops;
struct rt_mutex bus_lock;
struct rt_mutex mux_lock;
int timeout; /* in jiffies */
int retries;
struct device dev; /* the adapter device */
unsigned long locked_flags; /* owned by the I2C core */
#define I2C_ALF_IS_SUSPENDED 0
#define I2C_ALF_SUSPEND_REPORTED 1
int nr;
char name[48];
struct completion dev_released;
struct mutex userspace_clients_lock;
struct list_head userspace_clients;
struct i2c_bus_recovery_info *bus_recovery_info;
const struct i2c_adapter_quirks *quirks;
struct irq_domain *host_notify_domain;
};
2.2 i2c_algorithm
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 (*master_xfer_atomic)(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);
int (*smbus_xfer_atomic)(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 *adap);
#if IS_ENABLED(CONFIG_I2C_SLAVE)
int (*reg_slave)(struct i2c_client *client);
int (*unreg_slave)(struct i2c_client *client);
#endif
};
-
master_xfer
i2c传输
-
mas_terxfer_atomic
原子传输
-
smbus_xfer
smbus传输,如果没有提供此函数。则回使用master_xfer来进行模拟
-
smbus_xfer_atomic
smbus的原子传输
-
functionality
返回此algo支持的功能
-
reg_slave/unreg_slave
reg_slave将一个i2c client注册到i2c adapter。即让i2c adapter模拟i2c client
unreg_slave卸载i2c adapter模拟的i2c client