static void spi_transceive_internal(spi_device_t* device, uint8_t* read_buffer, const uint8_t* write_buffer, size_t size) { xSemaphoreTake(device->mutex, portMAX_DELAY); device->xf_setup.rx_data = read_buffer; device->xf_setup.tx_data = (void*) write_buffer; device->xf_setup.length = size; device->xf_setup.rx_cnt = 0; device->xf_setup.tx_cnt = 0; Chip_SSP_Int_FlushData(device->ssp_device); Chip_SSP_Int_RWFrames8Bits(device->ssp_device, &device->xf_setup); Chip_SSP_Int_Enable(device->ssp_device); // Wait till done xSemaphoreTake(device->sem_ready, portMAX_DELAY); xSemaphoreGive(device->mutex); }
void ssp_write_read( uint8_t id, uint8_t *tx_buf, uint32_t tx_len, uint8_t *rx_buf, uint32_t rx_len, uint32_t timeout ) { Chip_SSP_DATA_SETUP_T * data_st = &ssp_cfg[id].xf_setup; tx_ssp = pvPortMalloc(tx_len); rx_ssp = pvPortMalloc(rx_len+tx_len); memcpy(tx_ssp, tx_buf, tx_len); ssp_cfg[id].caller_task = xTaskGetCurrentTaskHandle(); data_st->tx_cnt = 0; data_st->rx_cnt = 0; data_st->tx_data = tx_ssp; data_st->rx_data = rx_ssp; data_st->length = rx_len+tx_len; /* Assert Slave Select pin to enable the transfer */ ssp_ssel_control(id, ASSERT); if (ssp_cfg[id].polling) { Chip_SSP_RWFrames_Blocking(ssp_cfg[id].lpc_id, data_st); ssp_ssel_control(id, DEASSERT); } else { Chip_SSP_Int_FlushData(ssp_cfg[id].lpc_id); /* Enable interrupt-based data transmission */ Chip_SSP_Int_Enable( ssp_cfg[id].lpc_id ); /* User defined timeout ? */ /* Wait until the transfer is finished */ ulTaskNotifyTake(pdTRUE, timeout); } if (rx_buf && rx_len > 0) { memcpy(rx_buf, rx_ssp, rx_len+tx_len); } vPortFree(rx_ssp); vPortFree(tx_ssp); }
/* Select the Transfer mode : Polling, Interrupt or DMA */ static void appSSPTest(void) { int key; DEBUGOUT(sspTransferModeSel); dmaChSSPTx = Chip_GPDMA_GetFreeChannel(LPC_GPDMA, LPC_GPDMA_SSP_TX); dmaChSSPRx = Chip_GPDMA_GetFreeChannel(LPC_GPDMA, LPC_GPDMA_SSP_RX); xf_setup.length = BUFFER_SIZE; xf_setup.tx_data = Tx_Buf; xf_setup.rx_data = Rx_Buf; while (1) { key = 0xFF; do { key = DEBUGIN(); } while ((key & 0xFF) == 0xFF); Buffer_Init(); switch (key) { case SSP_POLLING_SEL: /* SSP Polling Read Write Mode */ DEBUGOUT(sspWaitingMenu); xf_setup.rx_cnt = xf_setup.tx_cnt = 0; Chip_SSP_RWFrames_Blocking(LPC_SSP, &xf_setup); if (Buffer_Verify() == 0) { DEBUGOUT(sspPassedMenu); } else { DEBUGOUT(sspFailedMenu); } break; case SSP_INTERRUPT_SEL: DEBUGOUT(sspIntWaitingMenu); isXferCompleted = 0; xf_setup.rx_cnt = xf_setup.tx_cnt = 0; Chip_SSP_Int_FlushData(LPC_SSP);/* flush dummy data from SSP FiFO */ if (SSP_DATA_BYTES(ssp_format.bits) == 1) { Chip_SSP_Int_RWFrames8Bits(LPC_SSP, &xf_setup); } else { Chip_SSP_Int_RWFrames16Bits(LPC_SSP, &xf_setup); } Chip_SSP_Int_Enable(LPC_SSP); /* enable interrupt */ while (!isXferCompleted) {} if (Buffer_Verify() == 0) { DEBUGOUT(sspPassedMenu); } else { DEBUGOUT(sspFailedMenu); } break; case SSP_DMA_SEL: /* SSP DMA Read and Write: fixed on 8bits */ DEBUGOUT(sspDMAWaitingMenu); isDmaTxfCompleted = isDmaRxfCompleted = 0; Chip_SSP_DMA_Enable(LPC_SSP); /* data Tx_Buf --> SSP */ Chip_GPDMA_Transfer(LPC_GPDMA, dmaChSSPTx, (uint32_t) &Tx_Buf[0], LPC_GPDMA_SSP_TX, GPDMA_TRANSFERTYPE_M2P_CONTROLLER_DMA, BUFFER_SIZE); /* data SSP --> Rx_Buf */ Chip_GPDMA_Transfer(LPC_GPDMA, dmaChSSPRx, LPC_GPDMA_SSP_RX, (uint32_t) &Rx_Buf[0], GPDMA_TRANSFERTYPE_P2M_CONTROLLER_DMA, BUFFER_SIZE); while (!isDmaTxfCompleted || !isDmaRxfCompleted) {} if (Buffer_Verify() == 0) { DEBUGOUT(sspPassedMenu); } else { DEBUGOUT(sspFailedMenu); } Chip_SSP_DMA_Disable(LPC_SSP); break; case 'q': case 'Q': Chip_GPDMA_Stop(LPC_GPDMA, dmaChSSPTx); Chip_GPDMA_Stop(LPC_GPDMA, dmaChSSPRx); return; default: break; } DEBUGOUT(sspTransferModeSel); } }