I want to interface between 2 Tiva C Launchpad by I2C Interface. Tiva Master get data from Computer by UART and then transmit data to Slave by I2C. Tiva Slave receive data and control LED turn on.
But i have problem, and i don't know what is wrong?
Can anybody help me?
Thank you!
Master Tiva code:
#include <stdbool.h>
#include <stdint.h>
#include "inc/hw_i2c.h"
#include "inc/hw_memmap.h"
#include "inc/hw_types.h"
#include "driverlib/debug.h"
#include "driverlib/gpio.h"
#include "driverlib/i2c.h"
#include "driverlib/pin_map.h"
#include "driverlib/sysctl.h"
#include "driverlib/uart.h"
#include "utils/uartstdio.h"
#include "utils/uartstdio.c"
// address of SLAVE
#define SLAVE_ADDRESS 0x3C
// Configure UART0 to console data which transmitted
void InitConsole(void)
{
SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOA);
GPIOPinConfigure(GPIO_PA0_U0RX);
GPIOPinConfigure(GPIO_PA1_U0TX);
SysCtlPeripheralEnable(SYSCTL_PERIPH_UART0);
UARTClockSourceSet(UART0_BASE, UART_CLOCK_PIOSC);
GPIOPinTypeUART(GPIO_PORTA_BASE, GPIO_PIN_0 | GPIO_PIN_1);
UARTStdioConfig(0, 115200, 16000000);
}
void I2C0_Init(void)
{
SysCtlPeripheralEnable(SYSCTL_PERIPH_I2C0);
SysCtlPeripheralReset(SYSCTL_PERIPH_I2C0);
SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOB);
GPIOPinConfigure(GPIO_PB2_I2C0SCL);
GPIOPinConfigure(GPIO_PB3_I2C0SDA);
GPIOPinTypeI2CSCL(GPIO_PORTB_BASE, GPIO_PIN_2);
GPIOPinTypeI2C(GPIO_PORTB_BASE, GPIO_PIN_3);
//HWREG(I2C0_BASE + I2C_O_MCR) |= 0x01;
I2CMasterInitExpClk(I2C0_BASE, SysCtlClockGet(), false);
}
void I2C0_Send(uint16_t device_address, uint8_t device_data)
{
// Determine Slave address
// false: transmit Master --> Slave
// true: receive Master <-- Slave
I2CMasterSlaveAddrSet(I2C0_BASE, device_address, false);
// Put data
I2CMasterDataPut(I2C0_BASE, device_data);
// Transmit data
I2CMasterControl(I2C0_BASE, I2C_MASTER_CMD_SINGLE_SEND);
// Wait until finish
while(!(I2CSlaveStatus(I2C0_BASE) & I2C_SLAVE_ACT_RREQ));
}
int main(void)
{
uint32_t ui32DataTx;
SysCtlClockSet(SYSCTL_SYSDIV_5 | SYSCTL_USE_PLL | SYSCTL_OSC_MAIN |
SYSCTL_XTAL_16MHZ);
I2C0_Init();
InitConsole();
IntMasterEnable();
UARTprintf("I2C Slave Interrupt Example ->");
UARTprintf("\n Module = I2C0");
UARTprintf("\n Mode = Receive interrupt on the Slave module");
UARTprintf("\n Rate = 100kbps\n\n");
while(1)
{
ui32DataTx = UARTCharGet(UART0_BASE);
UARTprintf("Transferring from: Master -> Slave\n");
UARTprintf(" Sending: '%c'", ui32DataTx);
I2C0_Send(SLAVE_ADDRESS, ui32DataTx);
}
}
Slave Tiva code:
#include <stdbool.h>
#include <stdint.h>
#include "inc/hw_i2c.h"
#include "inc/hw_ints.h"
#include "inc/hw_memmap.h"
#include "inc/hw_types.h"
#include "driverlib/gpio.h"
#include "driverlib/i2c.h"
#include "driverlib/interrupt.h"
#include "driverlib/pin_map.h"
#include "driverlib/sysctl.h"
// address of SLAVE
#define SLAVE_ADDRESS 0x3C
// global variable to receive data
static uint32_t g_ui32DataRx;
// The interrupt handler for the for I2C0 data slave interrupt.
void I2C0SlaveIntHandler(void)
{
// Clear the I2C0 interrupt flag.
I2CSlaveIntClear(I2C0_BASE);
// Read the data from the slave.
g_ui32DataRx = I2CSlaveDataGet(I2C0_BASE);
I2CSlaveStatus(I2C0_BASE);
}
void I2C0_Init(void)
{
SysCtlPeripheralEnable(SYSCTL_PERIPH_I2C0);
SysCtlPeripheralReset(SYSCTL_PERIPH_I2C0);
SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOB);
GPIOPinConfigure(GPIO_PB2_I2C0SCL);
GPIOPinConfigure(GPIO_PB3_I2C0SDA);
GPIOPinTypeI2CSCL(GPIO_PORTB_BASE, GPIO_PIN_2);
GPIOPinTypeI2C(GPIO_PORTB_BASE, GPIO_PIN_3);
//HWREG(I2C0_BASE + I2C_O_MCR) |= 0x01;
//I2CMasterInitExpClk(I2C0_BASE, SysCtlClockGet(), false);
}
int main(void)
{
SysCtlClockSet(SYSCTL_SYSDIV_1 | SYSCTL_USE_OSC | SYSCTL_OSC_MAIN |
SYSCTL_XTAL_16MHZ);
I2C0_Init();
IntEnable(INT_I2C0);
I2CSlaveIntEnableEx(I2C0_BASE, I2C_SLAVE_INT_DATA);
I2CSlaveEnable(I2C0_BASE);
I2CSlaveInit(I2C0_BASE, SLAVE_ADDRESS);
IntMasterEnable();
while(1)
{
switch (g_ui32DataRx)
{
case 'r':
GPIOPinWrite(GPIO_PORTF_BASE, 0x0E, 0);
GPIOPinWrite(GPIO_PORTF_BASE, 0x02, 0x02);
break;
case 'g':
GPIOPinWrite(GPIO_PORTF_BASE, 0x0E, 0);
GPIOPinWrite(GPIO_PORTF_BASE, 0x08, 0x08);
break;
case 'b':
GPIOPinWrite(GPIO_PORTF_BASE, 0x0E, 0);
GPIOPinWrite(GPIO_PORTF_BASE, 0x04, 0x04);
break;
}
}
}