最近在rk3399平台上更换调试了录音小板,原rk3399的es7243 修改新的adc小板,一开始硬件就有问题,但因为对硬件不熟悉,导致做了汗多无用功,
言归正传,换adc录音小板,首先应该用i2ctools 检测寄存器
硬件i2c ok的情况下能使用i2cdetect 能检测到设备,驱动里配置了地址就显示为UU,没有配置地址显示具体值,比如10
一般寄存器都是8位地址的,i2ctools 里的i2cdump i2cget i2cset,也是设置读取8位的地址,但这次调试的寄存器是16位地址,i2cdump i2cget i2cset 都用不了,这时候就要用到i2ctransfer 了,I2C-Tools 4.0增加了i2ctransfer命令,可以对i2c设备指定定长度进行读写操作
比如在这个16位的寄存器里我们要看 0x0020 开始的寄存器值,向后读取16个字节
i2ctransfer -y -f 1 w2@0x1d 0x00 0x20 r16
读取了16个字节数据
w是写,2是写入2个字节,@0x1d 是寄存器地址,0x00 0x20 是寄存器要设置的地址的高低位,r是读取,16 是读取16个字节
如果我们想修改0x0020 的值可以如下指令
i2ctransfer -y -f 1 w4@0x1d 0x00 0x20 0x77 0x77
可以看到设置成功了
w是写,4是写入4个字节,@0x1d 是寄存器地址,0x00 0x20 是寄存器要设置的地址的高低位,0x77 0x77是要设置的值
加上代码写16位寄存器方法
static int i2c_write(struct i2c_client *client, u16 reg, u16 value)
{
u8 data[4];
data[0] = (reg& 0xFF00)>>8 ;
data[1] = reg& 0x00FF;
data[2] = (value& 0xFF00)>>8;
data[3] = value& 0x00FF;
if (i2c_master_send(client, data, 4) == 4){
printk("send ok\n");
return 0;
}
else{
printk("send failed");
return -EIO;
}
}
int i2c_master_send(struct i2c_client *client,const char *buf ,int count)
{
int ret;
struct i2c_adapter *adap=client->adapter; // 获取adapter信息
struct i2c_msg msg; // 定义一个临时的数据包
msg.addr = client->addr; // 将从机地址写入数据包
msg.flags = client->flags & I2C_M_TEN; // 将从机标志并入数据包
msg.len = count; // 将此次发送的数据字节数写入数据包
msg.buf = (char *)buf; // 将发送数据指针写入数据包
ret = i2c_transfer(adap, &msg, 1); // 调用平台接口发送数据
return (ret == 1) ? count : ret; // 如果发送成功就返回字节数
}
读取16位
static u16 i2c_read(struct i2c_client *client, u16 reg)
{
struct i2c_msg xfer[2];
u8 data[2];
int ret;
u16 result = -1;
u8 reg_buf[2];
reg_buf[0]= (reg& 0xFF00)>>8;
reg_buf[1]= reg& 0x00FF;
/* Write register */
xfer[0].addr = client->addr;
xfer[0].flags = 0;
xfer[0].len = 2;
xfer[0].buf = reg_buf;
/* Read data */
xfer[1].addr = client->addr;
xfer[1].flags = I2C_M_RD;
xfer[1].len = 2;
xfer[1].buf = data;
ret = i2c_transfer(client->adapter, xfer, 2);
if (ret != 2) {
dev_err(&client->dev, "i2c_transfer() returned %d\n", ret);
return 0;
}
result = *(u16 *)data;
printk("read ok data[0] = 0x%0x , data[1] = 0x%0x\n",data[0],data[1]);
//printk("***0x%x***\n",xfer[1].buf[0]);
return result;
}