* SVN $Revision: 2152 $\r
* SVN $Date: 2010-02-11 14:44:11 +0000 (Thu, 11 Feb 2010) $\r
*/\r
+\r
+\r
#include "i2c.h"\r
#include "../../CMSIS/mss_assert.h"\r
\r
this_i2c->hw_reg_bit->CTRL_CR1 = (clock_speed >> 1) & 0x01;\r
this_i2c->hw_reg_bit->CTRL_CR0 = clock_speed & 0x01;\r
this_i2c->hw_reg->ADDR = this_i2c->ser_address;\r
+ \r
+ /* The interrupt can cause a context switch, so ensure its priority is\r
+ between configKERNEL_INTERRUPT_PRIORITY and configMAX_SYSCALL_INTERRUPT_PRIORITY. */\r
+ NVIC_SetPriority( this_i2c->irqn, configLIBRARY_MAX_SYSCALL_INTERRUPT_PRIORITY );\r
+ \r
+ vSemaphoreCreateBinary( ( this_i2c->xI2CCompleteSemaphore ) );\r
+ xSemaphoreTake( ( this_i2c->xI2CCompleteSemaphore ), 0 );\r
+ configASSERT( ( this_i2c->xI2CCompleteSemaphore ) );\r
}\r
\r
/*------------------------------------------------------------------------------\r
uint32_t primask;\r
\r
ASSERT( (this_i2c == &g_mss_i2c0) || (this_i2c == &g_mss_i2c1) );\r
+ configASSERT( ( this_i2c->xI2CCompleteSemaphore ) );\r
\r
primask = disable_interrupts();\r
\r
{\r
ASSERT( (this_i2c == &g_mss_i2c0) || (this_i2c == &g_mss_i2c1) );\r
\r
+#ifdef USE_OLD_I2C_POLLING_CODE\r
while ( this_i2c->status == MSS_I2C_IN_PROGRESS )\r
{\r
/* Wait for transaction to compltete.*/\r
;\r
}\r
+#else\r
+ configASSERT( ( this_i2c->xI2CCompleteSemaphore ) );\r
+ if( xTaskGetSchedulerState() == taskSCHEDULER_NOT_STARTED )\r
+ {\r
+ while ( this_i2c->status == MSS_I2C_IN_PROGRESS )\r
+ {\r
+ /* Wait for transaction to compltete.*/\r
+ ;\r
+ }\r
+ }\r
+ else\r
+ {\r
+ xSemaphoreTake( this_i2c->xI2CCompleteSemaphore, portMAX_DELAY );\r
+ }\r
+#endif\r
+\r
return this_i2c->status;\r
}\r
\r
static void mss_i2c_isr\r
(\r
mss_i2c_instance_t * this_i2c\r
-)\r
+ )\r
{\r
volatile uint8_t status;\r
uint8_t data;\r
uint8_t hold_bus;\r
uint8_t clear_irq = 1;\r
+ long lHigherPriorityTaskWoken = pdFALSE;\r
+ configASSERT( ( this_i2c->xI2CCompleteSemaphore ) );\r
\r
ASSERT( (this_i2c == &g_mss_i2c0) || (this_i2c == &g_mss_i2c1) );\r
\r
clear_irq = 0;\r
}\r
this_i2c->status = MSS_I2C_SUCCESS;\r
+ xSemaphoreGiveFromISR( this_i2c->xI2CCompleteSemaphore, &lHigherPriorityTaskWoken );\r
}\r
break;\r
\r
clear_irq = 0;\r
}\r
this_i2c->status = MSS_I2C_SUCCESS;\r
+ xSemaphoreGiveFromISR( this_i2c->xI2CCompleteSemaphore, &lHigherPriorityTaskWoken );\r
}\r
break;\r
\r
case ST_SLAR_NACK: /* SLA+R tx'ed; let's release the bus (send a stop condition) */\r
this_i2c->hw_reg_bit->CTRL_STO = 0x01;\r
this_i2c->status = MSS_I2C_FAILED;\r
+ xSemaphoreGiveFromISR( this_i2c->xI2CCompleteSemaphore, &lHigherPriorityTaskWoken );\r
break;\r
\r
case ST_RX_DATA_ACK: /* Data byte received, ACK returned */\r
}\r
\r
this_i2c->status = MSS_I2C_SUCCESS;\r
+// xSemaphoreGiveFromISR( this_i2c->xI2CCompleteSemaphore, &lHigherPriorityTaskWoken );\r
break;\r
\r
/******************** SLAVE RECEIVER **************************/\r
}\r
/* Mark any previous master write transaction as complete. */\r
this_i2c->status = MSS_I2C_SUCCESS;\r
+// xSemaphoreGiveFromISR( this_i2c->xI2CCompleteSemaphore, &lHigherPriorityTaskWoken );\r
break;\r
\r
case ST_SLV_RST: /* SMBUS ONLY: timeout state. must clear interrupt */\r
/* Read the status register to ensure the last I2C registers write took place\r
* in a system built around a bus making use of posted writes. */\r
status = this_i2c->hw_reg->STATUS;\r
+ \r
+ portEND_SWITCHING_ISR( lHigherPriorityTaskWoken );\r
}\r
\r
/*------------------------------------------------------------------------------\r