void task_i2c_slave(uint_32 initial_data)
{
I2C_STATISTICS_STRUCT stats;
initialize_i2c0_slave();
while(TRUE)
{
i2c0_reg_reply();
_time_delay(DELAY_I2C0SLAVE_TASK);
}
}
void initialize_i2c0_slave(void)
{
fd_i2c_slave = fopen ("i2c0:", NULL); // Polled version
if (fd_i2c_slave == NULL)
{
printf ("Failed to open the I2C0 slave driver!\n");
_time_delay (200L);
_mqx_exit (1L);
}
// Set I2C into slave mode & set the slave address
if( I2C_OK == ioctl (fd_i2c_slave, IO_IOCTL_I2C_SET_SLAVE_MODE, NULL) )
{ printf("I2C0 slave mode GOOD\n"); }
else
{ printf("I2C0 slave mode ERROR\n"); }
}
#define REGRD0 0X01
#define REGRD1 0x02
void i2c0_reg_reply(void)
{
static uint_8 buffer[2] = {0x92, 0x15}; // Data to send to master request
uint_32 result;
uint_32 param;
uint_8 recv_buffer[2] = {0, 0};
uint_8 send1[4] = {0xca, 0x19, 0x83, 0xf5}; // Pretend register data
uint_8 send2[5] = {0x83, 0x02, 0xb6, 0xb7, 0x2b}; // pretend register data
uint_8 bytecount = 1;
uint_8 switchval;
result = _lwsem_wait(&lwsem_i2c0); // Capture the semaphore
// This if statement must be in here, otherwise the I2C doesn't ACK correctly
if(result != MQX_OK)
{ printf("\ni2c0_reg_reply lwsem_wait N2 failed 0x%X\n", result); }
param = I2C0_SLAVE_ADDR;
//result = ioctl(fd_i2c_slave, IO_IOCTL_I2C_SET_STATION_ADDRESS, ¶m);
result = ioctl(fd_i2c_slave, IO_IOCTL_I2C_SET_DESTINATION_ADDRESS, ¶m);
if(result != MQX_OK)
{ printf("I2C0 slave mode address ERROR\nCP>"); }
param = I2C0_SLAVE_ADDR;
bytecount = 1;
result = ioctl(fd_i2c_slave, IO_IOCTL_I2C_SET_STATION_ADDRESS, ¶m);
ioctl (fd_i2c_slave, IO_IOCTL_I2C_SET_RX_REQUEST, &bytecount);
result = fread (recv_buffer, 1, bytecount, fd_i2c_slave);
ioctl(fd_i2c_slave, IO_IOCTL_I2C_STOP, NULL); // Get driver to original state
// Take the received register value and act on it
switchval = recv_buffer[0]; // Capture the desired register address
switch(switchval)
{
case REGRD0:
bytecount = 4;
param = I2C0_SLAVE_ADDR;
result = ioctl(fd_i2c_slave, IO_IOCTL_I2C_SET_STATION_ADDRESS, ¶m);
fwrite (&send1, 1, bytecount, fd_i2c_slave);
ioctl (fd_i2c_slave, IO_IOCTL_I2C_STOP, NULL);
break;
case REGRD1:
bytecount = 5;
param = I2C0_SLAVE_ADDR;
result = ioctl(fd_i2c_slave, IO_IOCTL_I2C_SET_STATION_ADDRESS, ¶m);
fwrite (&send2, 1, bytecount, fd_i2c_slave);
ioctl (fd_i2c_slave, IO_IOCTL_I2C_STOP, NULL);
break;
default:
printf("\n%s\n%s", INVALID_I2C_REGISTER, COMMAND_PROMPT);
}
result = _lwsem_post(&lwsem_i2c0); // Release the semaphore
}