i2c控制代码
dws配置
i2c控制代码片段
lk阶段
#include <cust_gpio_usage.h>
#include <cust_i2c.h>
#include <platform/mt_gpio.h>
#include <platform/mt_i2c.h>
#include <platform/mt_pmic.h>
//i2c slave address 7 bit
/*
cust_i2c.h 文件生成的变量可以直接使用
#define I2C_CHANNEL_1 1
#define I2C_LT9211_AUTO_DETECT FALSE
#define I2C_LT9211_CHANNEL I2C_CHANNEL_1
#define I2C_LT9211_SLAVE_7_BIT_ADDR 0x2d
*/
#define LT9211_SLAVE_ADDR 0x2d
struct mt_i2c_t lt9211_i2c;
int lt9211_write_byte(u8 addr, u8 value);
int lt9211_read_byte(u8 addr, u8 *dataBuffer);
int lt9211_write_byte(u8 addr, u8 value) {
int ret_code = 0;
u8 write_data[2];
unsigned int len;
write_data[0] = addr;
write_data[1] = value;
lt9211_i2c.id = 1; /* I2C0; */ // i2c总线号
lt9211_i2c.addr = (LT9211_SLAVE_ADDR);
lt9211_i2c.mode = ST_MODE;
lt9211_i2c.speed = 100;
len = 2;
ret_code = i2c_write(<9211_i2c, write_data, len);
if (ret_code < 0)
printf("%s: lt9211_write_byte error: ret_code: %d\n", __func__, ret_code);
// printf("%s: lk success: ret_code: %d\n", __func__, ret_code);
return ret_code;
}
int lt9211_read_byte(u8 addr, u8 *dataBuffer) {
int ret_code = 0;
unsigned int len;
*dataBuffer = addr;
lt9211_i2c.id = 1; /* I2C0; */
lt9211_i2c.addr = (LT9211_SLAVE_ADDR);
lt9211_i2c.mode = ST_MODE;
lt9211_i2c.speed = 100;
lt9211_i2c.st_rs = I2C_TRANS_REPEATED_START;
len = 1;
ret_code = i2c_write_read(<9211_i2c, dataBuffer, len, len);
if (ret_code < 0)
printf("%s: lk error : ret_code: %d,ic:0x%x\n", __func__, ret_code,
*dataBuffer);
// printf("%s: lk success: ret_code: %d, dataBuffer = %x\n", __func__,
// ret_code, *dataBuffer);
return ret_code;
}
kernel阶段
dts片段
&i2c1 {
#address-cells = <1>;
#size-cells = <0>;
lt9211@2d {
compatible = "mediatek,lt9211";
reg = <0x2d>;
status = "okay";
};
isl97900crz_l@29 {
compatible = "mediatek,isl97900crz_l";
reg = <0x29>;
status = "okay";
};
isl97900crz_r@28 {
compatible = "mediatek,isl97900crz_r";
reg = <0x28>;
status = "okay";
};
ovp0921_l@05 {
compatible = "mediatek,ovp0921_l";
reg = <0x05>;
status = "okay";
};
ovp0921_r@04 {
compatible = "mediatek,ovp0921_r";
reg = <0x04>;
status = "okay";
};
};
代码片段
#include <linux/string.h>
#include <linux/delay.h>
#include <linux/fs.h>
#include <linux/gpio.h>
#include <linux/i2c.h>
#include <linux/init.h>
#include <linux/input.h>
#include <linux/interrupt.h>
#include <linux/io.h>
#include <linux/irq.h>
#include <linux/kernel.h>
#include <linux/list.h>
#include <linux/module.h>
#include <linux/of.h>
#include <linux/of_gpio.h>
#include <linux/of_irq.h>
#include <linux/platform_device.h>
#include <linux/printk.h>
#include <linux/proc_fs.h> //proc file use
#include <linux/slab.h>
#include <linux/uaccess.h>
#include <mach/gpio_const.h>
#include <mt-plat/mt_gpio.h>
#define I2C_LT9211_ID_NAME "lt9211"
static const struct of_device_id lt9211_of_match[] = {
{.compatible = "mediatek,LT9211"},
{},
};
static struct i2c_client *lt9211_i2c_client;
static DEFINE_MUTEX(lt9211_i2c_access);
static int lt9211_probe(struct i2c_client *client,
const struct i2c_device_id *id);
static int lt9211_remove(struct i2c_client *client);
struct lt9211_dev {
struct i2c_client *client;
};
static const struct i2c_device_id lt9211_id[] = {
{
.name = I2C_LT9211_ID_NAME,
.driver_data = 0,
},
};
static struct i2c_driver lt9211_iic_driver = {
.id_table = lt9211_id,
.probe = lt9211_probe,
.remove = lt9211_remove,
.driver =
{
.owner = THIS_MODULE,
.name = "lt9211",
.of_match_table = lt9211_of_match,
},
};
static int i2c_write_byte(struct i2c_client *client, u8 reg, u8 val) {
int rc = 0;
u8 txbuf[512] = {0};
if (!client) {
printk("%s i2c_write_byte-> client == null \n", __func__);
return -EINVAL;
}
struct i2c_msg msg[] = {
{
.addr = client->addr,
.flags = 0,
.len = 2,
.buf = txbuf,
},
};
txbuf[0] = reg;
txbuf[1] = val;
rc = i2c_transfer(client->adapter, msg, 1);
if (rc < 0) {
printk("%s i2c_transfer i2c write error rc= 0d%d\n", __func__, rc);
// rc = -EIO;
return rc;
}
// printk("%s lt9211 success rc= 0d[%d]\n", __func__, rc);
return rc;
}
static int i2c_read_byte(struct i2c_client *client, u8 reg, u8 *buf, u32 size) {
int rc = 0;
u8 rxbuf[512] = {0};
if (!client || !buf) {
// printk("%s i2c_write_byte-> client == null || buf == null \n", __func__);
return -EINVAL;
}
struct i2c_msg msg[] = {
{
.addr = client->addr,
.flags = 0,
.len = 1,
.buf = rxbuf,
},
{
.addr = client->addr,
.flags = I2C_M_RD,
.len = 1,
.buf = rxbuf,
},
};
rxbuf[0] = reg;
// printk("%s addr = %x \n", __func__, client->addr);
rc = i2c_transfer(client->adapter, msg, 2);
if (rc < 0) {
printk("%s i2c_transfer error rc=0d%d\n", __func__, rc);
// rc = -EIO;
return rc;
}
*buf = rxbuf[0];
// printk("%s lt9211 success rc=0d[%d], rxbuf[0] = 0x%x, *buf = 0x%x\n",
// __func__, rc, rxbuf[0], *buf);
return rc;
}
int lt9211_write_bytes(u8 cmd, u8 writeData) {
int ret = 0;
if (lt9211_i2c_client == NULL) {
printk("lt9211_write_bytes lt9211_i2c_client == NULL !!\n");
return -1;
}
mutex_lock(<9211_i2c_access);
ret = i2c_write_byte(lt9211_i2c_client, cmd, writeData);
if (ret < 0) {
mutex_unlock(<9211_i2c_access);
printk("lt9211_write_bytes i2c_master_send fail ret= 0d%d!!\n", ret);
return ret;
}
mutex_unlock(<9211_i2c_access);
// printk("%s success end ret=0d%d \n", __func__, ret);
return ret;
}
int lt9211_read_bytes(u8 cmd, u8 *returnData) {
int ret = 0;
u8 readData = 0;
if (lt9211_i2c_client == NULL) {
printk(" lt9211_read_bytes lt9211_i2c_client == NULL \n");
return -1;
}
mutex_lock(<9211_i2c_access);
ret = i2c_read_byte(lt9211_i2c_client, cmd, &readData, 1);
if (ret < 0) {
mutex_unlock(<9211_i2c_access);
printk("lt9211_write_bytes i2c_master_send fail ret= 0d%d!!\n", ret);
return ret;
}
*returnData = readData;
mutex_unlock(<9211_i2c_access);
// printk("%s success end ret=0d%d readData=0x%x\n", __func__, ret, readData);
return ret;
}
static int lt9211_probe(struct i2c_client *client,
const struct i2c_device_id *id) {
printk("lt9211_iic_probe\n");
printk("%s ==>name=%s addr=0x%x\n", __func__, client->name, client->addr);
lt9211_i2c_client = client;
return 0;
}
static int lt9211_remove(struct i2c_client *client) {
printk("lt9211_remove\n");
lt9211_i2c_client = NULL;
i2c_unregister_device(client);
return 0;
}
static int __init lt9211_init(void) {
printk("lt9211_iic_init\n");
i2c_add_driver(<9211_iic_driver);
printk("lt9211_iic_init success\n");
return 0;
}
static void __exit lt9211_exit(void) {
printk("lt9211_iic_exit\n");
i2c_del_driver(<9211_iic_driver);
}
module_init(lt9211_init);
module_exit(lt9211_exit);
MODULE_AUTHOR("Xiaokuan Shi");
MODULE_DESCRIPTION("MTK lt9211 I2C Driver");
i2c控制代码移植包