2 * @brief I2C Driver Implementation File
8 /* (c) Texas Instruments 2009-2012, All rights reserved. */
10 /* USER CODE BEGIN (0) */
13 #include "sys/ti_drv_i2c.h"
15 /* USER CODE BEGIN (1) */
18 /** @struct g_I2CTransfer
19 * @brief Interrupt mode globals
29 /* USER CODE BEGIN (2) */
32 /** @fn void i2cInit(void)
33 * @brief Initializes the i2c Driver
35 * This function initializes the i2c module.
39 /* USER CODE BEGIN (3) */
42 /** @b intialize @b I2C */
44 /** - i2c out of reset */
45 i2cREG1->MDR = (1 << 5);
48 i2cREG1->MDR = (0 << 15) /* nack mode */
49 | (0 << 14) /* free running */
50 | 0 /* start condtion - master mode only */
51 | (1 <<11) /* stop condtion */
52 | (1 <<10) /* Master/Slave mode */
53 | (I2C_TRANSMITTER) /* Transmitter/receiver */
54 | (I2C_7BIT_AMODE) /* xpanded address */
55 | (0 << 7) /* repeat mode */
56 | (0 << 6) /* digital loopback */
57 | (0 << 4) /* start byte - master only */
58 | (0) /* free data format */
59 | I2C_8_BIT; /* bit count */
62 /** - set i2c extended mode */
63 i2cREG1->EMDR = (0 << 25);
65 /** - set i2c data count */
68 /** - disable all interrupts */
74 /** - set clock rate */
78 /** - set i2c pins functional mode */
81 /** - set i2c pins default output value */
82 i2cREG1->DOUT = (0 << 1) /* sda pin */
85 /** - set i2c pins output direction */
86 i2cREG1->DIR = (1 << 1) /* sda pin */
89 /** - set i2c pins open drain enable */
90 i2cREG1->ODR = (0 << 1) /* sda pin */
93 /** - set i2c pins pullup/pulldown enable */
94 i2cREG1->PD = (0 << 1) /* sda pin */
97 /** - set i2c pins pullup/pulldown select */
98 i2cREG1->PSL = (1 << 1) /* sda pin */
101 /** - set interrupt enable */
102 i2cREG1->IMR = (0 << 6) /* Address as slave interrupt */
103 | (0 << 5) /* Stop Condition detect interrupt */
104 | (1 << 4) /* Transmit data ready interrupt */
105 | (1 << 3) /* Receive data ready interrupt */
106 | (0 << 2) /* Register Access ready interrupt */
107 | (0 << 1) /* No Acknowledgement interrupt */
108 | (1); /* Arbitration Lost interrupt */
110 i2cREG1->MDR |= I2C_RESET_OUT; /* i2c out of reset */
112 /** - inialise global transfer variables */
113 g_i2cTransfer[0].mode = 1 << 8;
114 g_i2cTransfer[0].length = 0;
116 /* USER CODE BEGIN (4) */
121 /** @fn void i2cSetOwnAdd(i2cBASE_t *i2c, uint32_t oadd)
122 * @brief Set I2C Own Address
123 * @param[in] oadd - I2C Own address (7-bit or 10 -bit address)
124 * @param[in] i2c - i2c module base address
125 * Set the Own address of the I2C module.
127 void i2cSetOwnAdd(i2cBASE_t *i2c, uint32_t oadd)
129 i2cREG1->OAR = oadd; /* set own address */
132 /** @fn void i2cSetSlaveAdd(i2cBASE_t *i2c, uint32_t sadd)
133 * @brief Set Port Direction
134 * @param[in] sadd - I2C Slave address
135 * @param[in] i2c - i2c module base address
136 * Set the Slave address to communicate which is must in Master mode.
138 void i2cSetSlaveAdd(i2cBASE_t *i2c, uint32_t sadd)
140 i2cREG1->SAR = sadd; /* set slave address */
143 /** @fn void i2cSetBaudrate(i2cBASE_t *i2c, uint32_t baud)
144 * @brief Change baudrate at runtime.
145 * @param[in] i2c - i2c module base address
146 * @param[in] baud - baudrate in KHz
148 * Change the i2c baudrate at runtime.
150 void i2cSetBaudrate(i2cBASE_t *i2c, uint32_t baud)
155 double vclk = 80.000 * 1000000.0;
157 /* USER CODE BEGIN (5) */
159 prescale = (uint32_t) ((vclk /8000000) - 1);
167 d = prescale ? 6 : 7;
170 ck = ((vclk)/(2*baud*1000*(prescale+1)))-d;
172 i2cREG1->PSC = prescale;
176 /* USER CODE BEGIN (6) */
181 /** @fn void i2cSetStart(i2cBASE_t *i2c)
182 * @brief Set i2c start condition
183 * @param[in] i2c - i2c module base address
184 * Set i2c to generate a start bit (Only in Master mode)
186 void i2cSetStart(i2cBASE_t *i2c)
188 /* USER CODE BEGIN (7) */
191 i2cREG1->MDR |= I2C_START_COND; /* set start condition */
193 /* USER CODE BEGIN (8) */
197 /** @fn void i2cSetStop(i2cBASE_t *i2c)
198 * @brief Set i2c stop condition
199 * @param[in] i2c - i2c module base address
200 * Set i2c to generate a stop bit (Only in Master mode)
202 void i2cSetStop(i2cBASE_t *i2c)
204 /* USER CODE BEGIN (9) */
207 i2cREG1->MDR |= I2C_STOP_COND; /* generate stop condition */
209 /* USER CODE BEGIN (10) */
213 /** @fn void i2cSetCount(i2cBASE_t *i2c,uint32_t cnt)
214 * @brief Set i2c data count
215 * @param[in] i2c - i2c module base address
216 * @param[in] cnt - data count
217 * Set i2c count to a transfer value after which the stop condition needs to be generated.
218 * (Only in Master Mode)
220 void i2cSetCount(i2cBASE_t *i2c ,uint32_t cnt)
222 /* USER CODE BEGIN (11) */
225 i2cREG1->CNT = cnt; /* set i2c count */
227 /* USER CODE BEGIN (12) */
231 /** @fn uint32_t i2cIsTxReady(i2cBASE_t *i2c)
232 * @brief Check if Tx buffer empty
233 * @param[in] i2c - i2c module base address
235 * @return The TX ready flag
237 * Checks to see if the Tx buffer ready flag is set, returns
238 * 0 is flags not set otherwise will return the Tx flag itself.
240 uint32_t i2cIsTxReady(i2cBASE_t *i2c)
242 /* USER CODE BEGIN (13) */
245 return i2cREG1->STR & I2C_TX_INT;
247 /* USER CODE BEGIN (14) */
251 /** @fn void i2cSendByte(i2cBASE_t *i2c, uint8_t byte)
253 * @param[in] i2c - i2c module base address
254 * @param[in] byte - byte to transfer
256 * Sends a single byte in polling mode, will wait in the
257 * routine until the transmit buffer is empty before sending
258 * the byte. Use i2cIsTxReady to check for Tx buffer empty
259 * before calling i2cSendByte to avoid waiting.
261 void i2cSendByte(i2cBASE_t *i2c, uint8_t byte)
263 /* USER CODE BEGIN (15) */
266 while ((i2cREG1->STR & I2C_TX_INT) == 0) { /* wait */ };
269 /* USER CODE BEGIN (16) */
273 /** @fn void i2cSend(i2cBASE_t *i2c, uint32_t length, uint8_t *data)
275 * @param[in] i2c - i2c module base address
276 * @param[in] length - number of data words to transfer
277 * @param[in] data - pointer to data to send
279 * Send a block of data pointed to by 'data' and 'length' bytes
280 * long. If interrupts have been enabled the data is sent using
281 * interrupt mode, otherwise polling mode is used. In interrupt
282 * mode transmition of the first byte is started and the routine
283 * returns imediatly, i2cSend must not be called again until the
284 * transfer is complete, when the i2cNotification callback will
285 * be called. In polling mode, i2cSend will not return until
286 * the transfer is complete.
288 * @note if data word is less than 8 bits, then the data must be left
289 * aligned in the data byte.
291 void i2cSend(i2cBASE_t *i2c, uint32_t length, uint8_t *data)
293 uint32_t index = i2c == i2cREG1 ? 0 : 1;
295 /* USER CODE BEGIN (17) */
298 if ((g_i2cTransfer[index].mode & I2C_TX_INT) != 0)
300 /* we are in interrupt mode */
302 g_i2cTransfer[index].length = length;
303 g_i2cTransfer[index].data = data;
305 /* start transmit by sending first byte */
306 i2cREG1->DXR = *g_i2cTransfer[index].data++;
307 i2cREG1->IMR = I2C_TX_INT;
314 while ((i2cREG1->STR & I2C_TX_INT) == 0) { /* wait */ };
315 i2cREG1->DXR = *data++;
318 /* USER CODE BEGIN (18) */
322 /** @fn uint32_t i2cIsRxReady(i2cBASE_t *i2c)
323 * @brief Check if Rx buffer full
324 * @param[in] i2c - i2c module base address
326 * @return The Rx ready flag
328 * Checks to see if the Rx buffer full flag is set, returns
329 * 0 is flags not set otherwise will return the Rx flag itself.
331 uint32_t i2cIsRxReady(i2cBASE_t *i2c)
333 /* USER CODE BEGIN (19) */
336 return i2cREG1->STR & I2C_RX_INT;
338 /* USER CODE BEGIN (20) */
343 /** @fn uint32_t i2cRxError(i2cBASE_t *i2c)
344 * @brief Return Rx Error flags
345 * @param[in] i2c - i2c module base address
347 * @return The Rx error flags
349 * Returns the Rx framing, overun and parity errors flags,
350 * also clears the error flags before returning.
352 uint32_t i2cRxError(i2cBASE_t *i2c)
354 uint32_t status = i2cREG1->STR & (I2C_AL_INT | I2C_NACK_INT);
356 /* USER CODE BEGIN (21) */
359 i2cREG1->STR = I2C_AL_INT | I2C_NACK_INT;
361 /* USER CODE BEGIN (22) */
368 /** @fn void i2cClearSCD(i2cBASE_t *i2c)
369 * @brief Clears the Stop condition detect flags.
370 * @param[in] i2c - i2c module base address
372 * This sunction is called to clear the Stop condition detect(SCD) flag
374 void i2cClearSCD(i2cBASE_t *i2c)
376 /* USER CODE BEGIN (23) */
379 i2cREG1->STR = I2C_SCD_INT;
381 /* USER CODE BEGIN (24) */
385 /** @fn uint32_t i2cReceiveByte(i2cBASE_t *i2c)
386 * @brief Receive Byte
387 * @param[in] i2c - i2c module base address
389 * @return Received byte
391 * Recieves a single byte in polling mode. If there is
392 * not a byte in the receive buffer the routine will wait
393 * until one is received. Use i2cIsRxReady to check to
394 * see if the buffer is full to avoid waiting.
396 uint32_t i2cReceiveByte(i2cBASE_t *i2c)
398 while ((i2cREG1->STR & I2C_RX_INT) == 0) { /* wait */ };
400 /* USER CODE BEGIN (25) */
406 /** @fn void i2cReceive(i2cBASE_t *i2c, uint32_t length, uint8_t *data)
407 * @brief Receive Data
408 * @param[in] i2c - i2c module base address
409 * @param[in] length - number of data words to transfer
410 * @param[in] data - pointer to data buffer
412 * Receive a block of 'length' bytes long and place it into the
413 * data buffer pointed to by 'data'. If interrupts have been
414 * enabled the data is received using interrupt mode, otherwise
415 * polling mode is used. In interrupt mode receive is setup and
416 * the routine returns imediatly, i2cReceive must not be called
417 * again until the transfer is complete, when the i2cNotification
418 * callback will be called. In polling mode, i2cReceive will not
419 * return until the transfer is complete.
421 void i2cReceive(i2cBASE_t *i2c, uint32_t length, uint8_t *data)
424 /* USER CODE BEGIN (26) */
426 if ((i2cREG1->IMR & I2C_RX_INT) != 0)
428 /* we are in interrupt mode */
429 uint32_t index = i2c == i2cREG1 ? 0 : 1;
431 /* clear error flags */
432 i2cREG1->STR = I2C_AL_INT | I2C_NACK_INT;
434 g_i2cTransfer[index].length = length;
435 g_i2cTransfer[index].data = data;
441 while ((i2cREG1->STR & I2C_RX_INT) == 0) { /* wait */ };
442 *data++ = i2cREG1->DRR;
446 /* USER CODE BEGIN (27) */
450 /** @fn void i2cEnableLoopback(i2cBASE_t *i2c)
451 * @brief Enable Loopback mode for self test
452 * @param[in] i2c - i2c module base address
454 * This function enables the Loopback mode for self test.
456 void i2cEnableLoopback(i2cBASE_t *i2c)
458 /* USER CODE BEGIN (28) */
461 /* enable digital loopback */
462 i2cREG1->MDR |= (1 << 6);
464 /* USER CODE BEGIN (29) */
468 /** @fn void i2cDisableLoopback(i2cBASE_t *i2c)
469 * @brief Enable Loopback mode for self test
470 * @param[in] i2c - i2c module base address
472 * This function disable the Loopback mode.
474 void i2cDisableLoopback(i2cBASE_t *i2c)
476 /* USER CODE BEGIN (30) */
479 /* Disable Loopback Mode */
480 i2cREG1->MDR &= 0xFFFFFFBF;
482 /* USER CODE BEGIN (31) */
486 /** @fn i2cEnableNotification(i2cBASE_t *i2c, uint32_t flags)
487 * @brief Enable interrupts
488 * @param[in] i2c - i2c module base address
489 * @param[in] flags - Interrupts to be enabled, can be ored value of:
490 * i2c_FE_INT - framming error,
491 * i2c_OE_INT - overrun error,
492 * i2c_PE_INT - parity error,
493 * i2c_RX_INT - receive buffer ready,
494 * i2c_TX_INT - transmit buffer ready,
495 * i2c_WAKE_INT - wakeup,
496 * i2c_BREAK_INT - break detect
498 void i2cEnableNotification(i2cBASE_t *i2c, uint32_t flags)
500 uint32_t index = i2c == i2cREG1 ? 0 : 1;
502 /* USER CODE BEGIN (32) */
505 g_i2cTransfer[index].mode |= (flags & I2C_TX_INT);
506 i2cREG1->IMR = (flags & ~I2C_TX_INT);
509 /** @fn i2cDisableNotification(i2cBASE_t *i2c, uint32_t flags)
510 * @brief Disable interrupts
511 * @param[in] i2c - i2c module base address
512 * @param[in] flags - Interrupts to be disabled, can be ored value of:
513 * i2c_FE_INT - framming error,
514 * i2c_OE_INT - overrun error,
515 * i2c_PE_INT - parity error,
516 * i2c_RX_INT - receive buffer ready,
517 * i2c_TX_INT - transmit buffer ready,
518 * i2c_WAKE_INT - wakeup,
519 * i2c_BREAK_INT - break detect
521 void i2cDisableNotification(i2cBASE_t *i2c, uint32_t flags)
523 uint32_t index = i2c == i2cREG1 ? 0 : 1;
525 /* USER CODE BEGIN (33) */
528 g_i2cTransfer[index].mode &= ~(flags & I2C_TX_INT);
529 i2cREG1->IMR = (flags & ~I2C_TX_INT);
532 /** @fn void i2cInterrupt(void)
533 * @brief Interrupt for I2C
535 #pragma INTERRUPT(i2cInterrupt, IRQ)
537 void i2cInterrupt(void)
539 uint32_t vec = (i2cREG1->IVR & 0x00000007);
541 /* USER CODE BEGIN (34) */
547 /* USER CODE BEGIN (35) */
549 i2cNotification(i2cREG1, I2C_AL_INT);
552 /* USER CODE BEGIN (36) */
554 i2cNotification(i2cREG1, I2C_NACK_INT);
557 /* USER CODE BEGIN (37) */
559 i2cNotification(i2cREG1, I2C_ARDY_INT);
562 /* USER CODE BEGIN (38) */
565 { uint32_t byte = i2cREG1->DRR;
567 if (g_i2cTransfer[0].length > 0)
569 *g_i2cTransfer[0].data++ = byte;
570 g_i2cTransfer[0].length--;
571 if (g_i2cTransfer[0].length == 0)
573 i2cNotification(i2cREG1, I2C_RX_INT);
579 /* USER CODE BEGIN (39) */
582 if (--g_i2cTransfer[0].length > 0)
584 i2cREG1->DXR = *g_i2cTransfer[0].data++;
588 i2cREG1->STR = I2C_TX_INT;
589 i2cNotification(i2cREG1, I2C_TX_INT);
595 /* USER CODE BEGIN (40) */
598 i2cNotification(i2cREG1, I2C_SCD_INT);
602 /* USER CODE BEGIN (41) */
604 i2cNotification(i2cREG1, I2C_AAS_INT);
608 /* USER CODE BEGIN (42) */
610 /* phantom interrupt, clear flags and return */
611 i2cREG1->STR = 0x000007FF;
614 /* USER CODE BEGIN (43) */