160 likes | 275 Views
Advanced Operating Systems. The I 2 C Bus. I 2 C bus. Inter-Integrated Circuit Bus Designed for low-cost, medium data rate applications. Characteristics: Synchronous; serial; multiple-master; fixed-priority arbitration. Several microcontrollers come with built-in I 2 C controllers.
E N D
Advanced Operating Systems The I2C Bus
I2C bus • Inter-Integrated Circuit Bus • Designed for low-cost, medium data rate applications. • Characteristics: • Synchronous; • serial; • multiple-master; • fixed-priority arbitration. • Several microcontrollers come with built-in I2C controllers. • PC based version is called SMBus
I2C physical layer master 1 master 2 data line SDL clock line SCL slave 1 slave 2
I2C data format ... SCL ... ... SDL ack start MSB
I2C electrical interface + SDL + SCL
I2C signaling • Sender pulls down bus for 0. • Sender listens to bus---if it tried to send a 1 and heard a 0, someone else is simultaneously transmitting. • Transmissions occur in 8-bit bytes.
I2C data link layer • Every device has an address (7 bits in standard, 10 bits in extension). • Bit 8 of address signals read or write. • General call address allows broadcast.
I2C bus arbitration • Sender listens while sending address. • When sender hears a conflict, if its address is higher, it stops signaling. • Low-priority senders relinquish control early enough in clock cycle to allow bit to be transmitted reliably.
I2C transmissions multi-byte write S adrs 0 data data P read from slave S adrs 1 data P write, then read S adrs 0 data S adrs 1 data P
I2C on the Puppeteer • I2C is used on the puppeteer board • Used to control VNRAM on an EEPROM –ATMEL AT24C02AN • Also used for clock RTC-8563SA/JE • Has two external connection – via liberator connector & via the expansion socket at the end of the board • The BSP use I2C for setting up the boards setting – user access is through config and config commit
I2C on the Puppeteer • The use of I2C on the Puppeteer is instructive • The onboard eeprom holds non-volatile data • Boot settings • Default uarts • Ethernet MAC address • FPGA set up code base address • Why not use Flash?
I2C on the Puppeteer • The SDA and SCL lines are connected through the StrongARM’s General Purpose IO lines • SDA 15 • SDC 14 • There is some set up required to make sure that these pins are for this dedicated function.
#define GPIO_BASE 0x90040000 struct gpioreg { int gplr; // R int gpdr; // RW int gpsr; // W int gpcr; // W int grer; // RW int gfer; // RW int gedr; // RW int gafr; // RW }; /* * I2C data (SDA) and clock (SCL) lines. craig */ #define BIT1 0x02 #define BIT14 0x4000 #define BIT15 0x8000 #define I2C_SDA BIT14 /* GPIO 14 */ #define I2C_SCL BIT15 /* GPIO 15 */
*-------------------------------------------------------------------*------------------------------------------------------------------- * FUNCTION NAME : Init * ARGUMENTS : I2CLineDriver_t* pThis - Pointer to driver. * RETURNS : - * DESCRIPTION : Initialises hardware related to the * : I2C data and clock lines. *------------------------------------------------------------------*/ static void Init( I2CLineDriver_t* pThis) { volatile struct gpioreg* pGPIORegs = (volatile struct gpioreg*)GPIO_BASE; /************************************************ * * Check arguments. * ***********************************************/ if (!pThis) return; /************************************************ * * Return if routine has already been called. * ***********************************************/
if (pThis->bInitialised) return; /************************************************ * If required, configure the I2C clock and * data pins as GPIO lines in the alternate * function register (GAFR) ***********************************************/ if (I2C_SCL > BIT1) pGPIORegs->gafr &= ~(I2C_SCL); if (I2C_SDA > BIT1) pGPIORegs->gafr &= ~(I2C_SDA); /************************************************ * Initially set the pins up as inputs (no drive * from CPU, hence should be pulled high by the * external resistors). ***********************************************/ pGPIORegs->gpdr &= ~(I2C_SCL | I2C_SDA); /************************************************ * Set the initialised flag. * ***********************************************/ pThis->bInitialised = TRUE; } /* end Init */
*-------------------------------------------------------------------*------------------------------------------------------------------- * FUNCTION NAME : GetData * ARGUMENTS : I2CLineDriver_t* pThis - Pointer to driver. * RETURNS : - * DESCRIPTION : Returns the state of the I2C data line. *------------------------------------------------------------------*/ static BOOL GetData(I2CLineDriver_t* pThis) { volatile struct gpioreg* pGPIORegs = (volatile struct gpioreg*)GPIO_BASE; if (!pThis) return FALSE; /************************************************ * Ensure that the driver has been initialised. ***********************************************/ if (!pThis->bInitialised) pThis->Init(pThis); /************************************************ * Configure the I2C data line as an input. ***********************************************/ pGPIORegs->gpdr &= ~(I2C_SDA); /************************************************ * Sample the data line. ***********************************************/ if (pGPIORegs->gplr & I2C_SDA) return TRUE; else return FALSE; } /* end GetData */