/*******************************************************************************
 * eUSCIB1 ISR. The repeated start and transmit/receive operations happen
 * within this ISR.
 ******************************************************************************/
void euscib1_isr(void)
{
    uint_fast16_t status;
    status = MAP_I2C_getEnabledInterruptStatus(EUSCI_B0_BASE);
    MAP_I2C_clearInterruptFlag(EUSCI_B0_BASE, status);
    static bool inAlert = false;


    if (status & EUSCI_B_I2C_STOP_INTERRUPT) {
#ifdef EVDEBUG
    	eventArr[eventIx++] = STOP;
#endif
    	if (inAlert) {
    		inAlert = false;
    		I2C_AlertDone();
    	}
    	else
    		i2c_l2_buf.stop();
    	return;
    }
    if (status & EUSCI_B_I2C_NAK_INTERRUPT) {
#ifdef EVDEBUG
        eventArr[eventIx++] = NAK;
#endif
        i2c_l2_buf.nak();
        return;
    }


    /* RXIFG */
    if (status & EUSCI_B_I2C_RECEIVE_INTERRUPT0)
    {
#ifdef EVDEBUG
    	eventArr[eventIx++] = RECEIVE;
#endif
    	i2c_l2_buf.put(MAP_I2C_slaveGetData(EUSCI_B0_BASE));
    }

    /* TXIFG */
    if (status & EUSCI_B_I2C_TRANSMIT_INTERRUPT0)
    {
#ifdef EVDEBUG
    	eventArr[eventIx++] = TRANSMIT;
#endif
        MAP_I2C_slavePutData(EUSCI_B0_BASE, i2c_l2_buf.get());
    }

    if (status & EUSCI_B_I2C_TRANSMIT_INTERRUPT1)
    {
    	// SMbus alert response. Put my address as a reply
    #ifdef EVDEBUG
       	eventArr[eventIx++] = TRANSMIT_SMBUS_ADDR;
    #endif
       	inAlert = true;
    	MAP_I2C_slavePutData(EUSCI_B0_BASE, SLAVE_ADDRESS << 1);
    }
#ifdef EVDEBUG
    if (eventIx == 50) eventIx = 0;
#endif
}
/******************************************************************************
 * The USCI_B0 data ISR RX vector is used to move received data from the I2C
 * master to the MSP432 memory.
 ******************************************************************************/
void euscib0_isr(void)
{
    uint_fast16_t status;

    status = MAP_I2C_getEnabledInterruptStatus(EUSCI_B0_MODULE);
    MAP_I2C_clearInterruptFlag(EUSCI_B0_MODULE, status);

    /* RXIFG for Slave Address 1*/
    if (status & EUSCI_B_I2C_TRANSMIT_INTERRUPT0)
    {
        MAP_I2C_slavePutData(EUSCI_B0_MODULE, TXData[xferIndex++]);

        /* Resetting the index if we are at the end. Also resetting the GPIO
         * if we are on the last byte */
        if (xferIndex  == NUM_OF_RX_BYTES)
        {
            MAP_I2C_disableInterrupt(EUSCI_B0_MODULE, EUSCI_B_I2C_TRANSMIT_INTERRUPT0);
            MAP_GPIO_setAsInputPin(GPIO_PORT_P1, GPIO_PIN0);
            MAP_Interrupt_disableSleepOnIsrExit();
            xferIndex = 0;

            /* IMPORTANT: Clearing out the TX Buffer for the next transfer.
             * This is required to compensate for the shift/buffer settings
             * of the I2C module */
            MAP_I2C_slavePutData(EUSCI_B0_MODULE, 0);
        }
    }
}
Example #3
0
/**
 * Handle a request ISL as a slave
 */
void DWire::_handleRequestSlave( void ) 
{
    // Check whether a user interrupt has been set
    if ( !user_onRequest )
        return;

    // If no message has been set, then call the user interrupt to set
    if (!(*pTxBufferIndex)) 
    {
        user_onRequest( );

        *pTxBufferSize = *pTxBufferIndex - 1;
        *pTxBufferIndex = 0;
    }

    // If we've transmitted the entire message, then reset the tx buffer
    if (*pTxBufferIndex > *pTxBufferSize) 
    {
        *pTxBufferIndex = 0;
        *pTxBufferSize = 0;
    } 
    else 
    {
        // Transmit a byte
        MAP_I2C_slavePutData( module, pTxBuffer[*pTxBufferIndex] );
        (*pTxBufferIndex)++;
    }
}
Example #4
0
/**
 * The main (global) interrupt  handler
 */
void IRQHandler(IRQParam param) {

	uint_fast16_t status;

	status = MAP_I2C_getEnabledInterruptStatus(param.module);
	MAP_I2C_clearInterruptFlag(param.module, status);

	/* RXIFG */
	// Triggered when data has been received
	if (status & EUSCI_B_I2C_RECEIVE_INTERRUPT0) {

		// If the rxBufferSize > 0, then we're a master performing a request
		if (*param.rxBufferSize > 0) {
			param.rxBuffer[*param.rxBufferIndex] =
			MAP_I2C_masterReceiveMultiByteNext(param.module);
			(*param.rxBufferIndex)++;

			if (*param.rxBufferIndex == *param.rxBufferSize) {
				DWire * instance = getInstance(param.module);
				if (instance) {
					instance->_finishRequest();
				}
			}

			// Otherwise we're a slave receiving data
		} else {
			param.rxBuffer[*param.rxBufferIndex] = MAP_I2C_slaveGetData(
					param.module);
			(*param.rxBufferIndex)++;
		}
	}

	// As master: triggered when a byte has been transmitted
	// As slave: triggered on request */
	if (status & EUSCI_B_I2C_TRANSMIT_INTERRUPT0) {
		DWire * instance = getInstance(param.module);

		if (instance) {

			// If the module is setup as a master, then we're transmitting data
			if (instance->isMaster()) {
				// If we've transmitted the last byte from the buffer, then send a stop
				if (!(*param.txBufferIndex)) {
					if (instance->_isSendStop(false))
						MAP_I2C_masterSendMultiByteStop(param.module);
					instance->_isSendStop(true);

				} else {
					// If we still have data left in the buffer, then transmit that
					MAP_I2C_masterSendMultiByteNext(param.module,
							param.txBuffer[(*param.txBufferSize)
									- (*param.txBufferIndex)]);
					(*param.txBufferIndex)--;
				}
				// Otherwise we're a slave and a master is requesting data
			} else {
				instance->_handleRequestSlave();
			}
		}
	}

	// Handle a NAK
	if (status & EUSCI_B_I2C_NAK_INTERRUPT) {
		//MAP_I2C_masterSendStart(param.module);
		DWire * instance = getInstance(param.module);
		//*param.txBufferIndex = 0;
		if (instance)
			if (*param.rxBufferSize > 0) {
			}
		instance->_finishRequest(true);
	}

	/* STPIFG
	 * Called when a STOP is received
	 */
	if (status & EUSCI_B_I2C_STOP_INTERRUPT) {
		DWire * instance = getInstance(param.module);
		if (instance) {
			if (*param.txBufferIndex != 0 && !instance->isMaster()) {
				MAP_I2C_slavePutData(instance->module, 0);
				*param.rxBufferIndex = 0;
				*param.rxBufferSize = 0;
			} else if (*param.rxBufferIndex != 0) {
				instance->_handleReceive(param.rxBuffer);
			}
		}
	}
}