Hi
I wanted to do a i2c read - write operation on imx6 . So i have added the following code.
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/ioctl.h>
#include <fcntl.h>
#include <linux/fs.h>
#include <errno.h>
#include <string.h>
#include <linux/i2c-dev.h>
#include <linux/i2c.h>
int main(void)
{
unsigned char rbuf[16];
int i2c_addr = 0x21;
int status;
unsigned short int i;
// OPENING I2C DEVICE
int fd = open("/dev/i2c-2", O_RDWR);
if (fd < 0)
{
printf("ERROR: open(%d) failed\n", fd);
return -1;
}
printf("\nSUCCESS: open(%d) passed\n", fd);
status = ioctl(fd, I2C_SLAVE, i2c_addr>>1);
if (status < 0)
{
printf("ERROR: ioctl(fd, I2C_SLAVE, 0x%02X) failed\n", i2c_addr);
close(fd);
return -1;
}
printf("\nSUCCESS: ioctl(fd, I2C_SLAVE, 0x%02X>>1) passed\n", i2c_addr);
printf ("\nPerforming MONZA Read operation\n");
if (read(fd,rbuf,16) != 16)
{
printf("ERROR: read() failed\n");
close(fd);
return -1;
}
for(i = 0; i< 16; i++)
printf("ReadBuffer[%d] %d \r\n", i, rbuf[i]);
printf("\nSUCCESS: Data READ from the MONZA\n");
printf("\n MONZA test successfull \n");
close(fd);
}
When i run this code i get read error
SUCCESS: open(3) passed
SUCCESS: ioctl(fd, I2C_SLAVE, 0x21) passed
Performing MONZA Read operation
ERROR: read() failed
read: Input/output error
errno = 5
My Device is connected i2c-dev 2. I observed it using i2cdetect-2. My slave address came to be 0x21.
Can somebody please help me out?
Hello, Agnes!
I use struct i2c_rdwr_ioctl_data for this, follow example:
int I2C::read8(unsigned char reg) const
{
i2c_rdwr_ioctl_data data;
i2c_msg msgs[2];
__u8 buf[sizeof(__u8) * 1] = {static_cast<__u8>(reg)};
int r;
msgs[0].addr = static_cast<__u16>(_address);
msgs[0].buf = buf;
msgs[0].flags = 0;
msgs[0].len = static_cast<__u16>(sizeof(unsigned char));
msgs[1].addr = static_cast<__u16>(_address);
msgs[1].flags = I2C_M_RD;
msgs[1].len = static_cast<__u8>(sizeof(unsigned char));
msgs[1].buf = buf;
data.msgs = msgs;
data.nmsgs = 2;
r = ioctl(_fd, I2C_RDWR, &data);
return (-1 == r) ? r : buf[0];
}
bool I2C::write(unsigned char reg, unsigned char val, bool check) const
{
i2c_rdwr_ioctl_data data;
i2c_msg msgs;
__u8 buf[sizeof(__u8) * 2] = {0};
int r;
buf[0] = static_cast<__u8>(reg);
buf[1] = static_cast<__u8>(val);
memset(&data, 0, sizeof(data));
msgs.addr = static_cast<__u16>(_address);
msgs.buf = buf;
msgs.flags = 0;
msgs.len =
static_cast<__u16>(sizeof(unsigned char) + sizeof(unsigned char));
data.msgs = &msgs;
data.nmsgs = 1;
r = ioctl(_fd, I2C_RDWR, &data);
if (r < 0)
return false;
if (check) {
usleep(1000);
return read8(reg) == static_cast<int>(val);
}
return true;
}
Hope this help you.
Hi AGNES,
also hardware better first to test with SDK
"MX6_PLATFORM_SDK "
http://www.freescale.com/webapp/sps/site/prod_summary.jsp?code=i.MX6Q&nodeId=018rH3ZrDRB24A&fpsp=1&t...
Best regards
chip
-----------------------------------------------------------------------------------------------------------------------
Note: If this post answers your question, please click the Correct Answer button. Thank you!
-----------------------------------------------------------------------------------------------------------------------
Hello, Agnes!
I use struct i2c_rdwr_ioctl_data for this, follow example:
int I2C::read8(unsigned char reg) const
{
i2c_rdwr_ioctl_data data;
i2c_msg msgs[2];
__u8 buf[sizeof(__u8) * 1] = {static_cast<__u8>(reg)};
int r;
msgs[0].addr = static_cast<__u16>(_address);
msgs[0].buf = buf;
msgs[0].flags = 0;
msgs[0].len = static_cast<__u16>(sizeof(unsigned char));
msgs[1].addr = static_cast<__u16>(_address);
msgs[1].flags = I2C_M_RD;
msgs[1].len = static_cast<__u8>(sizeof(unsigned char));
msgs[1].buf = buf;
data.msgs = msgs;
data.nmsgs = 2;
r = ioctl(_fd, I2C_RDWR, &data);
return (-1 == r) ? r : buf[0];
}
bool I2C::write(unsigned char reg, unsigned char val, bool check) const
{
i2c_rdwr_ioctl_data data;
i2c_msg msgs;
__u8 buf[sizeof(__u8) * 2] = {0};
int r;
buf[0] = static_cast<__u8>(reg);
buf[1] = static_cast<__u8>(val);
memset(&data, 0, sizeof(data));
msgs.addr = static_cast<__u16>(_address);
msgs.buf = buf;
msgs.flags = 0;
msgs.len =
static_cast<__u16>(sizeof(unsigned char) + sizeof(unsigned char));
data.msgs = &msgs;
data.nmsgs = 1;
r = ioctl(_fd, I2C_RDWR, &data);
if (r < 0)
return false;
if (check) {
usleep(1000);
return read8(reg) == static_cast<int>(val);
}
return true;
}
Hope this help you.