/* * Copyright (c) 2013-2016 ARM Limited. All rights reserved. * Copyright (c) 2016, Freescale Semiconductor, Inc. Not a Contribution. * Copyright 2016-2021 NXP. Not a Contribution. * * SPDX-License-Identifier: Apache-2.0 * * Licensed under the Apache License, Version 2.0 (the License); you may * not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an AS IS BASIS, WITHOUT * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ #include "fsl_ecspi_cmsis.h" /* Component ID definition, used by tools. */ #ifndef FSL_COMPONENT_ID #define FSL_COMPONENT_ID "platform.drivers.ecspi_cmsis" #endif #if ((defined(RTE_SPI1) && RTE_SPI1) || (defined(RTE_SPI2) && RTE_SPI2) || (defined(RTE_SPI3) && RTE_SPI3)) #define ARM_SPI_DRV_VERSION ARM_DRIVER_VERSION_MAJOR_MINOR(2, 2) /* driver version */ /* * ARMCC does not support split the data section automatically, so the driver * needs to split the data to separate sections explicitly, to reduce codesize. */ #if defined(__CC_ARM) || defined(__ARMCC_VERSION) #define ARMCC_SECTION(section_name) __attribute__((section(section_name))) #endif typedef const struct _cmsis_ecspi_resource { ECSPI_Type *base; uint32_t instance; uint32_t (*GetFreq)(void); } cmsis_ecspi_resource_t; #if ((defined(RTE_SPI1_DMA_EN) && RTE_SPI1_DMA_EN) || (defined(RTE_SPI2_DMA_EN) && RTE_SPI2_DMA_EN) || \ (defined(RTE_SPI3_DMA_EN) && RTE_SPI3_DMA_EN)) #if (defined(FSL_FEATURE_SOC_SDMA_COUNT) && FSL_FEATURE_SOC_SDMA_COUNT) typedef const struct _cmsis_ecspi_sdma_resource { SDMAARM_Type *txSdmaBase; uint32_t txSdmaChannel; uint32_t txSdmaRequest; uint8_t txSdmaPriority; sdma_context_data_t *txSdmaContext; SDMAARM_Type *rxSdmaBase; uint32_t rxSdmaChannel; uint32_t rxSdmaRequest; uint8_t rxSdmaPriority; sdma_context_data_t *rxSdmaContext; } cmsis_ecspi_sdma_resource_t; typedef struct _cmsis_ecspi_sdma_driver_state { cmsis_ecspi_resource_t *resource; cmsis_ecspi_sdma_resource_t *sdmaResource; ecspi_sdma_handle_t *handle; sdma_handle_t *sdmaRxDataHandle; sdma_handle_t *sdmaTxDataHandle; uint32_t baudRate_Bps; ARM_SPI_SignalEvent_t cb_event; uint8_t flags; /*!< Control and state flags. */ } cmsis_ecspi_sdma_driver_state_t; #endif #else /* SDMA unused. */ typedef struct _cmsis_ecspi_interrupt_driver_state { cmsis_ecspi_resource_t *resource; ecspi_master_handle_t *handle; ARM_SPI_SignalEvent_t cb_event; uint32_t baudRate_Bps; uint8_t flags; /*!< Control and state flags. */ } cmsis_ecspi_interrupt_driver_state_t; #endif /* Driver Version */ static const ARM_DRIVER_VERSION s_ECSPIDriverVersion = {ARM_SPI_API_VERSION, ARM_SPI_DRV_VERSION}; /* Driver Capabilities */ static const ARM_SPI_CAPABILITIES s_ECSPIDriverCapabilities = { 1, /* Simplex Mode (Master and Slave) */ 0, /* TI Synchronous Serial Interface */ 0, /* Microwire Interface */ 0 /* Signal Mode Fault event: \ref ARM_SPI_EVENT_MODE_FAULT */ }; /******************************************************************************* * Code ******************************************************************************/ static void ECSPI_MasterCommonControl(uint32_t control, cmsis_ecspi_resource_t *resource, ecspi_master_config_t *masterConfig) { switch (control & (uint32_t)ARM_SPI_SS_MASTER_MODE_Msk) { /* * Note: * ARM_SPI_SS_MASTER_HW_OUTPUT is default configuration in driver, if ARM_SPI_SS_MASTER_UNUSED or * ARM_SPI_SS_MASTER_SW is wanted, please disable pin function in SPIx_InitPins() which is configured * by user in extern file. Besides, ARM_SPI_SS_MASTER_HW_INPUT is not supported in this driver. */ case ARM_SPI_SS_MASTER_UNUSED: /*!< SPI Slave Select when Master: Not used */ break; case ARM_SPI_SS_MASTER_SW: /*!< SPI Slave Select when Master: Software controlled. */ break; case ARM_SPI_SS_MASTER_HW_OUTPUT: /*!< SPI Slave Select when Master: Hardware controlled Output */ break; case ARM_SPI_SS_MASTER_HW_INPUT: /*!< SPI Slave Select when Master: Hardware monitored Input */ break; default: /* Avoid MISRA 16.4 violations. */ break; } /* Configure the channel to be used. Default channel is channel0. */ switch (resource->instance) { case 1: #if defined(RTE_SPI1_TRANSFER_CHANNEL) masterConfig->channel = RTE_SPI1_TRANSFER_CHANNEL; #endif break; case 2: #if defined(RTE_SPI2_TRANSFER_CHANNEL) masterConfig->channel = RTE_SPI2_TRANSFER_CHANNEL; #endif break; case 3: #if defined(RTE_SPI3_TRANSFER_CHANNEL) masterConfig->channel = RTE_SPI3_TRANSFER_CHANNEL; #endif break; default: /* Avoid MISRA 16.4 violations. */ break; } switch (control & (uint32_t)ARM_SPI_FRAME_FORMAT_Msk) { case ARM_SPI_CPOL0_CPHA0: masterConfig->channelConfig.polarity = kECSPI_PolarityActiveHigh; masterConfig->channelConfig.phase = kECSPI_ClockPhaseFirstEdge; break; case ARM_SPI_CPOL0_CPHA1: masterConfig->channelConfig.polarity = kECSPI_PolarityActiveHigh; masterConfig->channelConfig.phase = kECSPI_ClockPhaseSecondEdge; break; case ARM_SPI_CPOL1_CPHA0: masterConfig->channelConfig.polarity = kECSPI_PolarityActiveLow; masterConfig->channelConfig.phase = kECSPI_ClockPhaseFirstEdge; break; case ARM_SPI_CPOL1_CPHA1: masterConfig->channelConfig.polarity = kECSPI_PolarityActiveLow; masterConfig->channelConfig.phase = kECSPI_ClockPhaseSecondEdge; break; default: /* Avoid MISRA 16.4 violations. */ break; } /* setting Number of burst length. */ if ((control & (uint32_t)ARM_SPI_DATA_BITS_Msk) != 0U) { masterConfig->burstLength = (uint8_t)((control & ARM_SPI_DATA_BITS_Msk) >> ARM_SPI_DATA_BITS_Pos); } } static void ECSPI_SlaveCommonControl(uint32_t control, cmsis_ecspi_resource_t *resource, ecspi_slave_config_t *slaveConfig) { /* The SPI slave select is controlled by hardware, software mode is not supported by current driver. */ switch (control & (uint32_t)ARM_SPI_SS_SLAVE_MODE_Msk) { case ARM_SPI_SS_SLAVE_HW: break; case ARM_SPI_SS_SLAVE_SW: break; default: /* Avoid MISRA 16.4 violations. */ break; } /* Configure the channel to be used. Default channel is channel0. */ switch (resource->instance) { case 1: #if defined(RTE_SPI1_TRANSFER_CHANNEL) slaveConfig->channel = RTE_SPI1_TRANSFER_CHANNEL; #endif break; case 2: #if defined(RTE_SPI2_TRANSFER_CHANNEL) slaveConfig->channel = RTE_SPI2_TRANSFER_CHANNEL; #endif break; case 3: #if defined(RTE_SPI3_TRANSFER_CHANNEL) slaveConfig->channel = RTE_SPI3_TRANSFER_CHANNEL; #endif break; default: /* Avoid MISRA 16.4 violations. */ break; } switch (control & (uint32_t)ARM_SPI_FRAME_FORMAT_Msk) { case ARM_SPI_CPOL0_CPHA0: slaveConfig->channelConfig.polarity = kECSPI_PolarityActiveHigh; slaveConfig->channelConfig.phase = kECSPI_ClockPhaseFirstEdge; break; case ARM_SPI_CPOL0_CPHA1: slaveConfig->channelConfig.polarity = kECSPI_PolarityActiveHigh; slaveConfig->channelConfig.phase = kECSPI_ClockPhaseSecondEdge; break; case ARM_SPI_CPOL1_CPHA0: slaveConfig->channelConfig.polarity = kECSPI_PolarityActiveLow; slaveConfig->channelConfig.phase = kECSPI_ClockPhaseFirstEdge; break; case ARM_SPI_CPOL1_CPHA1: slaveConfig->channelConfig.polarity = kECSPI_PolarityActiveLow; slaveConfig->channelConfig.phase = kECSPI_ClockPhaseSecondEdge; break; default: /* Avoid MISRA 16.4 violations. */ break; } if ((control & (uint32_t)ARM_SPI_DATA_BITS_Msk) != 0U) /* setting Number of Data bits */ { slaveConfig->burstLength = (uint8_t)((control & (uint32_t)ARM_SPI_DATA_BITS_Msk) >> ARM_SPI_DATA_BITS_Pos); } } static ARM_DRIVER_VERSION ECSPIx_GetVersion(void) { return s_ECSPIDriverVersion; } static ARM_SPI_CAPABILITIES ECSPIx_GetCapabilities(void) { return s_ECSPIDriverCapabilities; } #endif #if ((defined(RTE_SPI1_DMA_EN) && RTE_SPI1_DMA_EN) || (defined(RTE_SPI2_DMA_EN) && RTE_SPI2_DMA_EN) || \ (defined(RTE_SPI3_DMA_EN) && RTE_SPI3_DMA_EN)) #if (defined(FSL_FEATURE_SOC_SDMA_COUNT) && FSL_FEATURE_SOC_SDMA_COUNT) static void KSDK_ECSPI_MasterSDMACallback(ECSPI_Type *base, ecspi_sdma_handle_t *handle, status_t status, void *userData) { uint32_t event = 0U; if (kStatus_Success == status) { event = ARM_SPI_EVENT_TRANSFER_COMPLETE; } /* User data is actually CMSIS driver callback. */ if (userData != NULL) { ((ARM_SPI_SignalEvent_t)userData)(event); } } static void KSDK_ECSPI_SlaveSDMACallback(ECSPI_Type *base, ecspi_sdma_handle_t *handle, status_t status, void *userData) { uint32_t event = 0U; if (kStatus_Success == status) { event = ARM_SPI_EVENT_TRANSFER_COMPLETE; } /* User data is actually CMSIS driver callback. */ if (userData != NULL) { ((ARM_SPI_SignalEvent_t)userData)(event); } } static int32_t ECSPI_SDMAInitialize(ARM_SPI_SignalEvent_t cb_event, cmsis_ecspi_sdma_driver_state_t *ecspi) { if (0U == (ecspi->flags & (uint8_t)SPI_FLAG_INIT)) { ecspi->cb_event = cb_event; ecspi->flags = (uint8_t)SPI_FLAG_INIT; } return ARM_DRIVER_OK; } static int32_t ECSPI_SDMAUninitialize(cmsis_ecspi_sdma_driver_state_t *ecspi) { ecspi->flags = (uint8_t)SPI_FLAG_UNINIT; return ARM_DRIVER_OK; } static int32_t ECSPI_SDMAPowerControl(ARM_POWER_STATE state, cmsis_ecspi_sdma_driver_state_t *ecspi) { int32_t result = ARM_DRIVER_OK; switch (state) { case ARM_POWER_OFF: if ((ecspi->flags & (uint8_t)SPI_FLAG_POWER) != 0U) { ECSPI_Deinit(ecspi->resource->base); ecspi->flags &= ~(uint8_t)SPI_FLAG_POWER; } break; case ARM_POWER_LOW: result = ARM_DRIVER_ERROR_UNSUPPORTED; break; case ARM_POWER_FULL: if (ecspi->flags == (uint8_t)SPI_FLAG_UNINIT) { result = ARM_DRIVER_ERROR; break; } if ((ecspi->flags & (uint8_t)SPI_FLAG_POWER) != 0U) { /* Driver already powered */ break; } ecspi->flags |= (uint8_t)SPI_FLAG_POWER; break; default: result = ARM_DRIVER_ERROR_UNSUPPORTED; break; } return result; } static int32_t ECSPI_SDMASend(const void *data, uint32_t num, cmsis_ecspi_sdma_driver_state_t *ecspi) { int32_t ret; status_t status; ecspi_transfer_t xfer = {0}; uint32_t datawidth = (ecspi->resource->base->CONREG & (uint32_t)ECSPI_CONREG_BURST_LENGTH_MASK) >> ECSPI_CONREG_BURST_LENGTH_SHIFT; xfer.rxData = NULL; xfer.txData = (uint32_t *)data; xfer.dataSize = num * ((datawidth + 8U) / 8U); xfer.channel = kECSPI_Channel0; /* Configure the channel to be used. */ switch (ecspi->resource->instance) { case 1: #if defined(RTE_SPI1_TRANSFER_CHANNEL) xfer.channel = RTE_SPI1_TRANSFER_CHANNEL; #endif break; case 2: #if defined(RTE_SPI2_TRANSFER_CHANNEL) xfer.channel = RTE_SPI2_TRANSFER_CHANNEL; #endif break; case 3: #if defined(RTE_SPI3_TRANSFER_CHANNEL) xfer.channel = RTE_SPI3_TRANSFER_CHANNEL; #endif break; default: /* Avoid MISRA 16.4 violations. */ break; } if ((ecspi->flags & (uint8_t)SPI_FLAG_MASTER) != 0U) { status = ECSPI_MasterTransferSDMA(ecspi->resource->base, ecspi->handle, &xfer); } else { status = ECSPI_SlaveTransferSDMA(ecspi->resource->base, ecspi->handle, &xfer); } switch (status) { case kStatus_Success: ret = ARM_DRIVER_OK; break; case kStatus_InvalidArgument: ret = ARM_DRIVER_ERROR_PARAMETER; break; case kStatus_ECSPI_Busy: ret = ARM_DRIVER_ERROR_BUSY; break; default: ret = ARM_DRIVER_ERROR; break; } return ret; } static int32_t ECSPI_SDMAReceive(void *data, uint32_t num, cmsis_ecspi_sdma_driver_state_t *ecspi) { int32_t ret; status_t status; ecspi_transfer_t xfer = {0}; uint32_t datawidth = (ecspi->resource->base->CONREG & (uint32_t)ECSPI_CONREG_BURST_LENGTH_MASK) >> ECSPI_CONREG_BURST_LENGTH_SHIFT; xfer.txData = NULL; xfer.rxData = (uint32_t *)data; xfer.dataSize = num * ((datawidth + 8U) / 8U); xfer.channel = kECSPI_Channel0; /* Configure the channel to be used. */ switch (ecspi->resource->instance) { case 1: #if defined(RTE_SPI1_TRANSFER_CHANNEL) xfer.channel = RTE_SPI1_TRANSFER_CHANNEL; #endif break; case 2: #if defined(RTE_SPI2_TRANSFER_CHANNEL) xfer.channel = RTE_SPI2_TRANSFER_CHANNEL; #endif break; case 3: #if defined(RTE_SPI3_TRANSFER_CHANNEL) xfer.channel = RTE_SPI3_TRANSFER_CHANNEL; #endif break; default: /* Avoid MISRA 16.4 violations. */ break; } if ((ecspi->flags & (uint8_t)SPI_FLAG_MASTER) != 0U) { status = ECSPI_MasterTransferSDMA(ecspi->resource->base, ecspi->handle, &xfer); } else { status = ECSPI_SlaveTransferSDMA(ecspi->resource->base, ecspi->handle, &xfer); } switch (status) { case kStatus_Success: ret = ARM_DRIVER_OK; break; case kStatus_InvalidArgument: ret = ARM_DRIVER_ERROR_PARAMETER; break; case kStatus_ECSPI_Busy: ret = ARM_DRIVER_ERROR_BUSY; break; default: ret = ARM_DRIVER_ERROR; break; } return ret; } static int32_t ECSPI_SDMATransfer(const void *data_out, void *data_in, uint32_t num, cmsis_ecspi_sdma_driver_state_t *ecspi) { int32_t ret; status_t status; ecspi_transfer_t xfer = {0}; uint32_t datawidth = (ecspi->resource->base->CONREG & (uint32_t)ECSPI_CONREG_BURST_LENGTH_MASK) >> ECSPI_CONREG_BURST_LENGTH_SHIFT; xfer.txData = (uint32_t *)data_out; xfer.rxData = (uint32_t *)data_in; xfer.dataSize = num * ((datawidth + 8U) / 8U); xfer.channel = kECSPI_Channel0; /* Configure the channel to be used. */ switch (ecspi->resource->instance) { case 1: #if defined(RTE_SPI1_TRANSFER_CHANNEL) xfer.channel = RTE_SPI1_TRANSFER_CHANNEL; #endif break; case 2: #if defined(RTE_SPI2_TRANSFER_CHANNEL) xfer.channel = RTE_SPI2_TRANSFER_CHANNEL; #endif break; case 3: #if defined(RTE_SPI3_TRANSFER_CHANNEL) xfer.channel = RTE_SPI3_TRANSFER_CHANNEL; #endif break; default: /* Avoid MISRA 16.4 violations. */ break; } if ((ecspi->flags & (uint8_t)SPI_FLAG_MASTER) != 0U) { status = ECSPI_MasterTransferSDMA(ecspi->resource->base, ecspi->handle, &xfer); } else { status = ECSPI_SlaveTransferSDMA(ecspi->resource->base, ecspi->handle, &xfer); } switch (status) { case kStatus_Success: ret = ARM_DRIVER_OK; break; case kStatus_InvalidArgument: ret = ARM_DRIVER_ERROR_PARAMETER; break; case kStatus_ECSPI_Busy: ret = ARM_DRIVER_ERROR_BUSY; break; default: ret = ARM_DRIVER_ERROR; break; } return ret; } static uint32_t ECSPI_SDMAGetCount(cmsis_ecspi_sdma_driver_state_t *ecspi) { /* Unsupported by current driver. */ return 0U; } static int32_t ECSPI_SDMAControl(uint32_t control, uint32_t arg, cmsis_ecspi_sdma_driver_state_t *ecspi) { int32_t result = ARM_DRIVER_OK; bool isDone = false; if (0U == (ecspi->flags & (uint8_t)SPI_FLAG_POWER)) { return ARM_DRIVER_ERROR; } switch (control & ARM_SPI_CONTROL_Msk) { case ARM_SPI_MODE_INACTIVE: ECSPI_Enable(ecspi->resource->base, false); isDone = true; break; case ARM_SPI_MODE_MASTER: ecspi->baudRate_Bps = arg; ecspi->flags |= (uint8_t)SPI_FLAG_MASTER; break; case ARM_SPI_MODE_SLAVE: ecspi->flags &= ~(uint8_t)SPI_FLAG_MASTER; break; case ARM_SPI_SET_BUS_SPEED: if (0U == (ecspi->flags & (uint8_t)SPI_FLAG_MASTER)) { result = ARM_DRIVER_ERROR_UNSUPPORTED; break; } ECSPI_SetBaudRate(ecspi->resource->base, arg, ecspi->resource->GetFreq()); ecspi->baudRate_Bps = arg; isDone = true; break; case ARM_SPI_GET_BUS_SPEED: /* Set Bus Speed in bps; arg = value */ if (0U == (ecspi->flags & (uint8_t)SPI_FLAG_MASTER)) { result = ARM_DRIVER_ERROR_UNSUPPORTED; break; } result = (int32_t)ecspi->baudRate_Bps; isDone = true; break; case ARM_SPI_CONTROL_SS: result = ARM_DRIVER_ERROR_UNSUPPORTED; break; case ARM_SPI_ABORT_TRANSFER: if ((ecspi->flags & (uint8_t)SPI_FLAG_MASTER) != 0U) { ECSPI_MasterTransferAbortSDMA(ecspi->resource->base, ecspi->handle); } else { ECSPI_SlaveTransferAbortSDMA(ecspi->resource->base, ecspi->handle); } isDone = true; break; case ARM_SPI_SET_DEFAULT_TX_VALUE: /* Set default Transmit value; arg = value */ /* Unsupported by current driver. */ result = ARM_DRIVER_ERROR_UNSUPPORTED; break; case ARM_SPI_MODE_MASTER_SIMPLEX: /* SPI Master (Output/Input on MOSI); arg = Bus Speed in bps */ /* Mode is not supported by current driver. */ result = ARM_DRIVER_ERROR_UNSUPPORTED; break; case ARM_SPI_MODE_SLAVE_SIMPLEX: /* SPI Slave (Output/Input on MISO) */ /* Mode is not supported by current driver. */ result = ARM_DRIVER_ERROR_UNSUPPORTED; break; default: /* Avoid MISRA 16.4 violation */ break; } if ((result != ARM_DRIVER_OK) || isDone) { return result; } if ((ecspi->flags & (uint8_t)SPI_FLAG_MASTER) != 0U) { ecspi_master_config_t masterConfig; ECSPI_MasterGetDefaultConfig(&masterConfig); masterConfig.baudRate_Bps = ecspi->baudRate_Bps; ECSPI_MasterCommonControl(control, ecspi->resource, &masterConfig); if ((ecspi->flags & (uint8_t)SPI_FLAG_CONFIGURED) != 0U) { ECSPI_Deinit(ecspi->resource->base); } ECSPI_MasterInit(ecspi->resource->base, &masterConfig, ecspi->resource->GetFreq()); SDMA_CreateHandle(ecspi->sdmaTxDataHandle, ecspi->sdmaResource->txSdmaBase, ecspi->sdmaResource->txSdmaChannel, ecspi->sdmaResource->txSdmaContext); SDMA_CreateHandle(ecspi->sdmaRxDataHandle, ecspi->sdmaResource->rxSdmaBase, ecspi->sdmaResource->rxSdmaChannel, ecspi->sdmaResource->rxSdmaContext); ECSPI_MasterTransferCreateHandleSDMA(ecspi->resource->base, ecspi->handle, KSDK_ECSPI_MasterSDMACallback, (void *)ecspi->cb_event, ecspi->sdmaTxDataHandle, ecspi->sdmaRxDataHandle, ecspi->sdmaResource->txSdmaRequest, ecspi->sdmaResource->rxSdmaRequest, ecspi->sdmaResource->txSdmaChannel, ecspi->sdmaResource->rxSdmaChannel); SDMA_SetChannelPriority(ecspi->sdmaResource->txSdmaBase, ecspi->sdmaResource->txSdmaChannel, ecspi->sdmaResource->txSdmaPriority); SDMA_SetChannelPriority(ecspi->sdmaResource->rxSdmaBase, ecspi->sdmaResource->rxSdmaChannel, ecspi->sdmaResource->rxSdmaPriority); ecspi->flags |= (uint8_t)SPI_FLAG_CONFIGURED; } else { ecspi_slave_config_t slaveConfig; ECSPI_SlaveGetDefaultConfig(&slaveConfig); ECSPI_SlaveCommonControl(control, ecspi->resource, &slaveConfig); if ((ecspi->flags & (uint8_t)SPI_FLAG_CONFIGURED) != 0U) { ECSPI_Deinit(ecspi->resource->base); } ECSPI_SlaveInit(ecspi->resource->base, &slaveConfig); SDMA_CreateHandle(ecspi->sdmaTxDataHandle, ecspi->sdmaResource->txSdmaBase, ecspi->sdmaResource->txSdmaChannel, ecspi->sdmaResource->txSdmaContext); SDMA_CreateHandle(ecspi->sdmaRxDataHandle, ecspi->sdmaResource->rxSdmaBase, ecspi->sdmaResource->rxSdmaChannel, ecspi->sdmaResource->rxSdmaContext); ECSPI_SlaveTransferCreateHandleSDMA(ecspi->resource->base, ecspi->handle, KSDK_ECSPI_SlaveSDMACallback, (void *)ecspi->cb_event, ecspi->sdmaTxDataHandle, ecspi->sdmaRxDataHandle, ecspi->sdmaResource->txSdmaRequest, ecspi->sdmaResource->rxSdmaRequest, ecspi->sdmaResource->txSdmaChannel, ecspi->sdmaResource->rxSdmaChannel); SDMA_SetChannelPriority(ecspi->sdmaResource->txSdmaBase, ecspi->sdmaResource->txSdmaChannel, ecspi->sdmaResource->txSdmaPriority); SDMA_SetChannelPriority(ecspi->sdmaResource->rxSdmaBase, ecspi->sdmaResource->rxSdmaChannel, ecspi->sdmaResource->rxSdmaPriority); ecspi->flags |= (uint8_t)SPI_FLAG_CONFIGURED; } return ARM_DRIVER_OK; } static ARM_SPI_STATUS ECSPI_SDMAGetStatus(cmsis_ecspi_sdma_driver_state_t *ecspi) { ARM_SPI_STATUS stat = {0}; stat.busy = ((ecspi->handle->txInProgress == true) || (ecspi->handle->rxInProgress == true)) ? (0U) : (1U); stat.data_lost = 0U; stat.mode_fault = 0U; stat.reserved = 0U; return stat; } #endif /* defined(FSL_FEATURE_SOC_DMA_COUNT) */ #endif #if ((defined(RTE_SPI1) && RTE_SPI1 && !RTE_SPI1_DMA_EN) || (defined(RTE_SPI2) && RTE_SPI2 && !RTE_SPI2_DMA_EN) || \ (defined(RTE_SPI3) && RTE_SPI3 && !RTE_SPI3_DMA_EN)) static void KSDK_ECSPI_MasterInterruptCallback(ECSPI_Type *base, ecspi_master_handle_t *handle, status_t status, void *userData) { uint32_t event = 0U; if (kStatus_Success == status) { event = ARM_SPI_EVENT_TRANSFER_COMPLETE; } if (kStatus_ECSPI_HardwareOverFlow == status) { event = ARM_SPI_EVENT_DATA_LOST; } /* User data is actually CMSIS driver callback. */ if (userData != NULL) { ((ARM_SPI_SignalEvent_t)userData)(event); } } static void KSDK_ECSPI_SlaveInterruptCallback(ECSPI_Type *base, ecspi_slave_handle_t *handle, status_t status, void *userData) { uint32_t event = 0; if (kStatus_Success == status) { event = ARM_SPI_EVENT_TRANSFER_COMPLETE; } if (kStatus_ECSPI_HardwareOverFlow == status) { event = ARM_SPI_EVENT_DATA_LOST; } /* User data is actually CMSIS driver callback. */ if (userData != NULL) { ((ARM_SPI_SignalEvent_t)userData)(event); } } static int32_t ECSPI_InterruptInitialize(ARM_SPI_SignalEvent_t cb_event, cmsis_ecspi_interrupt_driver_state_t *ecspi) { if (0U == (ecspi->flags & (uint8_t)SPI_FLAG_INIT)) { ecspi->cb_event = cb_event; ecspi->flags = (uint8_t)SPI_FLAG_INIT; } return ARM_DRIVER_OK; } static int32_t ECSPI_InterruptUninitialize(cmsis_ecspi_interrupt_driver_state_t *ecspi) { ecspi->flags = (uint8_t)SPI_FLAG_UNINIT; return ARM_DRIVER_OK; } static int32_t ECSPI_InterruptPowerControl(ARM_POWER_STATE state, cmsis_ecspi_interrupt_driver_state_t *ecspi) { int32_t result = ARM_DRIVER_OK; switch (state) { case ARM_POWER_OFF: if ((ecspi->flags & (uint8_t)SPI_FLAG_POWER) != 0U) { ECSPI_Deinit(ecspi->resource->base); ecspi->flags &= ~(uint8_t)SPI_FLAG_POWER; } break; case ARM_POWER_LOW: result = ARM_DRIVER_ERROR_UNSUPPORTED; break; case ARM_POWER_FULL: if (ecspi->flags == (uint8_t)SPI_FLAG_UNINIT) { return ARM_DRIVER_ERROR; } /* Driver already powered */ if ((ecspi->flags & (uint8_t)SPI_FLAG_POWER) != 0U) { break; } ecspi->flags |= (uint8_t)SPI_FLAG_POWER; break; default: result = ARM_DRIVER_ERROR_UNSUPPORTED; break; } return result; } static int32_t ECSPI_InterruptSend(const void *data, uint32_t num, cmsis_ecspi_interrupt_driver_state_t *ecspi) { int32_t ret; status_t status; ecspi_transfer_t xfer = {0}; uint32_t datawidth = (ecspi->resource->base->CONREG & (uint32_t)ECSPI_CONREG_BURST_LENGTH_MASK) >> ECSPI_CONREG_BURST_LENGTH_SHIFT; xfer.rxData = NULL; xfer.txData = (uint32_t *)data; xfer.dataSize = num * ((datawidth + 8U) / 8U); xfer.channel = kECSPI_Channel0; /* Configure the channel to be used. */ switch (ecspi->resource->instance) { case 1: #if defined(RTE_SPI1_TRANSFER_CHANNEL) xfer.channel = RTE_SPI1_TRANSFER_CHANNEL; #endif break; case 2: #if defined(RTE_SPI2_TRANSFER_CHANNEL) xfer.channel = RTE_SPI2_TRANSFER_CHANNEL; #endif break; case 3: #if defined(RTE_SPI3_TRANSFER_CHANNEL) xfer.channel = RTE_SPI3_TRANSFER_CHANNEL; #endif break; default: /* Avoid MISRA 16.4 violations. */ break; } if ((ecspi->flags & (uint8_t)SPI_FLAG_MASTER) != 0U) { status = ECSPI_MasterTransferNonBlocking(ecspi->resource->base, ecspi->handle, &xfer); } else { status = ECSPI_SlaveTransferNonBlocking(ecspi->resource->base, ecspi->handle, &xfer); } switch (status) { case kStatus_Success: ret = ARM_DRIVER_OK; break; case kStatus_InvalidArgument: ret = ARM_DRIVER_ERROR_PARAMETER; break; case kStatus_ECSPI_Busy: ret = ARM_DRIVER_ERROR_BUSY; break; default: ret = ARM_DRIVER_ERROR; break; } return ret; } static int32_t ECSPI_InterruptReceive(void *data, uint32_t num, cmsis_ecspi_interrupt_driver_state_t *ecspi) { int32_t ret; status_t status; ecspi_transfer_t xfer = {0}; uint32_t datawidth = (ecspi->resource->base->CONREG & ECSPI_CONREG_BURST_LENGTH_MASK) >> ECSPI_CONREG_BURST_LENGTH_SHIFT; xfer.txData = NULL; xfer.rxData = (uint32_t *)data; xfer.dataSize = num * ((datawidth + 8U) / 8U); xfer.channel = kECSPI_Channel0; /* Configure the channel to be used. */ switch (ecspi->resource->instance) { case 1: #if defined(RTE_SPI1_TRANSFER_CHANNEL) xfer.channel = RTE_SPI1_TRANSFER_CHANNEL; #endif break; case 2: #if defined(RTE_SPI2_TRANSFER_CHANNEL) xfer.channel = RTE_SPI2_TRANSFER_CHANNEL; #endif break; case 3: #if defined(RTE_SPI3_TRANSFER_CHANNEL) xfer.channel = RTE_SPI3_TRANSFER_CHANNEL; #endif break; default: /* Avoid MISRA 16.4 violations. */ break; } if ((ecspi->flags & (uint8_t)SPI_FLAG_MASTER) != 0U) { status = ECSPI_MasterTransferNonBlocking(ecspi->resource->base, ecspi->handle, &xfer); } else { status = ECSPI_SlaveTransferNonBlocking(ecspi->resource->base, ecspi->handle, &xfer); } switch (status) { case kStatus_Success: ret = ARM_DRIVER_OK; break; case kStatus_InvalidArgument: ret = ARM_DRIVER_ERROR_PARAMETER; break; case kStatus_ECSPI_Busy: ret = ARM_DRIVER_ERROR_BUSY; break; default: ret = ARM_DRIVER_ERROR; break; } return ret; } static int32_t ECSPI_InterruptTransfer(const void *data_out, void *data_in, uint32_t num, cmsis_ecspi_interrupt_driver_state_t *ecspi) { int32_t ret; status_t status; ecspi_transfer_t xfer = {0}; uint32_t datawidth = (ecspi->resource->base->CONREG & (uint32_t)ECSPI_CONREG_BURST_LENGTH_MASK) >> ECSPI_CONREG_BURST_LENGTH_SHIFT; xfer.txData = (uint32_t *)data_out; xfer.rxData = (uint32_t *)data_in; xfer.dataSize = num * ((datawidth + 8U) / 8U); xfer.channel = kECSPI_Channel0; /* Configure the channel to be used. */ switch (ecspi->resource->instance) { case 1: #if defined(RTE_SPI1_TRANSFER_CHANNEL) xfer.channel = RTE_SPI1_TRANSFER_CHANNEL; #endif break; case 2: #if defined(RTE_SPI2_TRANSFER_CHANNEL) xfer.channel = RTE_SPI2_TRANSFER_CHANNEL; #endif break; case 3: #if defined(RTE_SPI3_TRANSFER_CHANNEL) xfer.channel = RTE_SPI3_TRANSFER_CHANNEL; #endif break; default: /* Avoid MISRA 16.4 violations. */ break; } if ((ecspi->flags & (uint8_t)SPI_FLAG_MASTER) != 0U) { status = ECSPI_MasterTransferNonBlocking(ecspi->resource->base, ecspi->handle, &xfer); } else { status = ECSPI_SlaveTransferNonBlocking(ecspi->resource->base, ecspi->handle, &xfer); } switch (status) { case kStatus_Success: ret = ARM_DRIVER_OK; break; case kStatus_InvalidArgument: ret = ARM_DRIVER_ERROR_PARAMETER; break; case kStatus_ECSPI_Busy: ret = ARM_DRIVER_ERROR_BUSY; break; default: ret = ARM_DRIVER_ERROR; break; } return ret; } static uint32_t ECSPI_InterruptGetCount(cmsis_ecspi_interrupt_driver_state_t *ecspi) { uint32_t datawidth = (ecspi->resource->base->CONREG & (uint32_t)ECSPI_CONREG_BURST_LENGTH_MASK) >> ECSPI_CONREG_BURST_LENGTH_SHIFT; uint32_t cnt = ecspi->handle->transferSize - ecspi->handle->rxRemainingBytes; cnt /= ((datawidth + 8U) / 8U); return cnt; } static int32_t ECSPI_InterruptControl(uint32_t control, uint32_t arg, cmsis_ecspi_interrupt_driver_state_t *ecspi) { int32_t result = ARM_DRIVER_OK; bool isContinue = false; if (0U == (ecspi->flags & (uint8_t)SPI_FLAG_POWER)) { return ARM_DRIVER_ERROR; } switch (control & ARM_SPI_CONTROL_Msk) { case ARM_SPI_MODE_MASTER: /* SPI Master (Output on MOSI, Input on MISO); arg = Bus Speed in bps */ ecspi->baudRate_Bps = arg; ecspi->flags |= (uint8_t)SPI_FLAG_MASTER; isContinue = true; break; case ARM_SPI_MODE_SLAVE: /* SPI Slave (Output on MISO, Input on MOSI) */ ecspi->flags &= ~(uint8_t)SPI_FLAG_MASTER; isContinue = true; break; case ARM_SPI_GET_BUS_SPEED: /* Get Bus Speed in bps */ if (0U == (ecspi->flags & (uint8_t)SPI_FLAG_MASTER)) { return ARM_DRIVER_ERROR_UNSUPPORTED; } result = (int32_t)ecspi->baudRate_Bps; break; case ARM_SPI_SET_BUS_SPEED: /* Set Bus Speed in bps; */ if (0U == (ecspi->flags & (uint8_t)SPI_FLAG_MASTER)) { return ARM_DRIVER_ERROR_UNSUPPORTED; } ECSPI_SetBaudRate(ecspi->resource->base, arg, ecspi->resource->GetFreq()); ecspi->baudRate_Bps = arg; break; case ARM_SPI_CONTROL_SS: result = ARM_DRIVER_ERROR_UNSUPPORTED; break; case ARM_SPI_ABORT_TRANSFER: /* Abort current data transfer */ if ((ecspi->flags & (uint8_t)SPI_FLAG_MASTER) != 0U) { ECSPI_MasterTransferAbort(ecspi->resource->base, ecspi->handle); } else { ECSPI_SlaveTransferAbort(ecspi->resource->base, ecspi->handle); } break; case ARM_SPI_SET_DEFAULT_TX_VALUE: /* Set default Transmit value; arg = value */ /* Mode is not supported by current driver. */ result = ARM_DRIVER_ERROR_UNSUPPORTED; break; case ARM_SPI_MODE_MASTER_SIMPLEX: /* SPI Master (Output/Input on MOSI); arg = Bus Speed in bps */ /* Mode is not supported by current driver. */ result = ARM_DRIVER_ERROR_UNSUPPORTED; break; case ARM_SPI_MODE_SLAVE_SIMPLEX: /* SPI Slave (Output/Input on MISO) */ /* Mode is not supported by current driver. */ result = ARM_DRIVER_ERROR_UNSUPPORTED; break; default: isContinue = true; /* Avoid MISRA 16.4 violation */ break; } if (!isContinue) { return result; } if ((ecspi->flags & (uint8_t)SPI_FLAG_MASTER) != 0U) { ecspi_master_config_t masterConfig; ECSPI_MasterGetDefaultConfig(&masterConfig); masterConfig.baudRate_Bps = ecspi->baudRate_Bps; ECSPI_MasterCommonControl(control, ecspi->resource, &masterConfig); if ((ecspi->flags & (uint8_t)SPI_FLAG_CONFIGURED) != 0U) { ECSPI_Deinit(ecspi->resource->base); } ECSPI_MasterInit(ecspi->resource->base, &masterConfig, ecspi->resource->GetFreq()); ECSPI_MasterTransferCreateHandle(ecspi->resource->base, ecspi->handle, KSDK_ECSPI_MasterInterruptCallback, (void *)ecspi->cb_event); ecspi->flags |= (uint8_t)SPI_FLAG_CONFIGURED; } else { ecspi_slave_config_t slaveConfig; ECSPI_SlaveGetDefaultConfig(&slaveConfig); ECSPI_SlaveCommonControl(control, ecspi->resource, &slaveConfig); if ((ecspi->flags & (uint8_t)SPI_FLAG_CONFIGURED) != 0U) { ECSPI_Deinit(ecspi->resource->base); } ECSPI_SlaveInit(ecspi->resource->base, &slaveConfig); ECSPI_SlaveTransferCreateHandle(ecspi->resource->base, ecspi->handle, KSDK_ECSPI_SlaveInterruptCallback, (void *)ecspi->cb_event); ecspi->flags |= (uint8_t)SPI_FLAG_CONFIGURED; } return result; } static ARM_SPI_STATUS ECSPI_InterruptGetStatus(cmsis_ecspi_interrupt_driver_state_t *ecspi) { ARM_SPI_STATUS stat = {0}; stat.busy = ((ecspi->handle->txRemainingBytes > 0U) || (ecspi->handle->rxRemainingBytes > 0U)) ? (0U) : (1U); stat.data_lost = 0U; stat.mode_fault = 0U; stat.reserved = 0U; return stat; } #endif #if defined(ECSPI1) && defined(RTE_SPI1) && RTE_SPI1 /* User needs to provide the implementation for ECSPI1_GetFreq/InitPins/DeinitPins * in the application for enabling according instance. */ extern uint32_t ECSPI1_GetFreq(void); static cmsis_ecspi_resource_t ECSPI1_Resource = {ECSPI1, 1, ECSPI1_GetFreq}; #if defined(RTE_SPI1_DMA_EN) && RTE_SPI1_DMA_EN AT_NONCACHEABLE_SECTION_ALIGN(static ecspi_sdma_handle_t ECSPI1_SdmaHandle, 4); AT_NONCACHEABLE_SECTION_ALIGN(static sdma_handle_t ECSPI1_TxSdmaHandle, 4); AT_NONCACHEABLE_SECTION_ALIGN(static sdma_handle_t ECSPI1_RxSdmaHandle, 4); AT_NONCACHEABLE_SECTION_ALIGN(static sdma_context_data_t ECSPI1_TxSdmaContext, 4); AT_NONCACHEABLE_SECTION_ALIGN(static sdma_context_data_t ECSPI1_RxSdmaContext, 4); static cmsis_ecspi_sdma_resource_t ECSPI1_SDMAResource = { RTE_SPI1_DMA_TX_DMA_BASE, RTE_SPI1_DMA_TX_CH, RTE_SPI1_DMA_TX_CH_REQUEST, RTE_SPI1_DMA_TX_CH_PRIORITY, &ECSPI1_TxSdmaContext, RTE_SPI1_DMA_RX_DMA_BASE, RTE_SPI1_DMA_RX_CH, RTE_SPI1_DMA_RX_CH_REQUEST, RTE_SPI1_DMA_RX_CH_PRIORITY, &ECSPI1_RxSdmaContext}; #if defined(__CC_ARM) || defined(__ARMCC_VERSION) ARMCC_SECTION("ecspi1_sdma_driver_state") static cmsis_ecspi_sdma_driver_state_t ECSPI1_SDMADriverState = { #else static cmsis_ecspi_sdma_driver_state_t ECSPI1_SDMADriverState = { #endif &ECSPI1_Resource, &ECSPI1_SDMAResource, &ECSPI1_SdmaHandle, &ECSPI1_RxSdmaHandle, &ECSPI1_TxSdmaHandle}; static int32_t ECSPI1_SDMAInitialize(ARM_SPI_SignalEvent_t cb_event) { #ifdef RTE_SPI1_PIN_INIT RTE_SPI1_PIN_INIT(); #endif return ECSPI_SDMAInitialize(cb_event, &ECSPI1_SDMADriverState); } static int32_t ECSPI1_SDMAUninitialize(void) { #ifdef RTE_SPI1_PIN_DEINIT RTE_SPI1_PIN_DEINIT(); #endif return ECSPI_SDMAUninitialize(&ECSPI1_SDMADriverState); } static int32_t ECSPI1_SDMAPowerControl(ARM_POWER_STATE state) { return ECSPI_SDMAPowerControl(state, &ECSPI1_SDMADriverState); } static int32_t ECSPI1_SDMASend(const void *data, uint32_t num) { return ECSPI_SDMASend(data, num, &ECSPI1_SDMADriverState); } static int32_t ECSPI1_SDMAReceive(void *data, uint32_t num) { return ECSPI_SDMAReceive(data, num, &ECSPI1_SDMADriverState); } static int32_t ECSPI1_SDMATransfer(const void *data_out, void *data_in, uint32_t num) { return ECSPI_SDMATransfer(data_out, data_in, num, &ECSPI1_SDMADriverState); } static uint32_t ECSPI1_SDMAGetCount(void) { return ECSPI_SDMAGetCount(&ECSPI1_SDMADriverState); } static int32_t ECSPI1_SDMAControl(uint32_t control, uint32_t arg) { return ECSPI_SDMAControl(control, arg, &ECSPI1_SDMADriverState); } static ARM_SPI_STATUS ECSPI1_SDMAGetStatus(void) { return ECSPI_SDMAGetStatus(&ECSPI1_SDMADriverState); } #else static ecspi_master_handle_t ECSPI1_Handle; #if defined(__CC_ARM) || defined(__ARMCC_VERSION) ARMCC_SECTION("ecspi1_interrupt_driver_state") static cmsis_ecspi_interrupt_driver_state_t ECSPI1_InterruptDriverState = { #else static cmsis_ecspi_interrupt_driver_state_t ECSPI1_InterruptDriverState = { #endif &ECSPI1_Resource, &ECSPI1_Handle, }; static int32_t ECSPI1_InterruptInitialize(ARM_SPI_SignalEvent_t cb_event) { #ifdef RTE_SPI1_PIN_INIT RTE_SPI1_PIN_INIT(); #endif return ECSPI_InterruptInitialize(cb_event, &ECSPI1_InterruptDriverState); } static int32_t ECSPI1_InterruptUninitialize(void) { #ifdef RTE_SPI1_PIN_DEINIT RTE_SPI1_PIN_DEINIT(); #endif return ECSPI_InterruptUninitialize(&ECSPI1_InterruptDriverState); } static int32_t ECSPI1_InterruptPowerControl(ARM_POWER_STATE state) { return ECSPI_InterruptPowerControl(state, &ECSPI1_InterruptDriverState); } static int32_t ECSPI1_InterruptSend(const void *data, uint32_t num) { return ECSPI_InterruptSend(data, num, &ECSPI1_InterruptDriverState); } static int32_t ECSPI1_InterruptReceive(void *data, uint32_t num) { return ECSPI_InterruptReceive(data, num, &ECSPI1_InterruptDriverState); } static int32_t ECSPI1_InterruptTransfer(const void *data_out, void *data_in, uint32_t num) { return ECSPI_InterruptTransfer(data_out, data_in, num, &ECSPI1_InterruptDriverState); } static uint32_t ECSPI1_InterruptGetCount(void) { return ECSPI_InterruptGetCount(&ECSPI1_InterruptDriverState); } static int32_t ECSPI1_InterruptControl(uint32_t control, uint32_t arg) { return ECSPI_InterruptControl(control, arg, &ECSPI1_InterruptDriverState); } static ARM_SPI_STATUS ECSPI1_InterruptGetStatus(void) { return ECSPI_InterruptGetStatus(&ECSPI1_InterruptDriverState); } #endif ARM_DRIVER_SPI Driver_SPI1 = { ECSPIx_GetVersion, ECSPIx_GetCapabilities, #if defined(RTE_SPI1_DMA_EN) && RTE_SPI1_DMA_EN ECSPI1_SDMAInitialize, ECSPI1_SDMAUninitialize, ECSPI1_SDMAPowerControl, ECSPI1_SDMASend, ECSPI1_SDMAReceive, ECSPI1_SDMATransfer, ECSPI1_SDMAGetCount, ECSPI1_SDMAControl, ECSPI1_SDMAGetStatus #else ECSPI1_InterruptInitialize, ECSPI1_InterruptUninitialize, ECSPI1_InterruptPowerControl, ECSPI1_InterruptSend, ECSPI1_InterruptReceive, ECSPI1_InterruptTransfer, ECSPI1_InterruptGetCount, ECSPI1_InterruptControl, ECSPI1_InterruptGetStatus #endif }; #endif /* ECSPI1 */ #if defined(ECSPI2) && defined(RTE_SPI2) && RTE_SPI2 /* User needs to provide the implementation for ECSPI2_GetFreq/InitPins/DeinitPins * in the application for enabling according instance. */ extern uint32_t ECSPI2_GetFreq(void); static cmsis_ecspi_resource_t ECSPI2_Resource = {ECSPI2, 2, ECSPI2_GetFreq}; #if defined(RTE_SPI2_DMA_EN) && RTE_SPI2_DMA_EN AT_NONCACHEABLE_SECTION_ALIGN(static ecspi_sdma_handle_t ECSPI2_SdmaHandle, 4); AT_NONCACHEABLE_SECTION_ALIGN(static sdma_handle_t ECSPI2_TxSdmaHandle, 4); AT_NONCACHEABLE_SECTION_ALIGN(static sdma_handle_t ECSPI2_RxSdmaHandle, 4); AT_NONCACHEABLE_SECTION_ALIGN(static sdma_context_data_t ECSPI2_TxSdmaContext, 4); AT_NONCACHEABLE_SECTION_ALIGN(static sdma_context_data_t ECSPI2_RxSdmaContext, 4); static cmsis_ecspi_sdma_resource_t ECSPI2_SDMAResource = { RTE_SPI2_DMA_TX_DMA_BASE, RTE_SPI2_DMA_TX_CH, RTE_SPI2_DMA_TX_CH_REQUEST, RTE_SPI2_DMA_TX_CH_PRIORITY, &ECSPI2_TxSdmaContext, RTE_SPI2_DMA_RX_DMA_BASE, RTE_SPI2_DMA_RX_CH, RTE_SPI2_DMA_RX_CH_REQUEST, RTE_SPI2_DMA_RX_CH_PRIORITY, &ECSPI2_RxSdmaContext}; #if defined(__CC_ARM) || defined(__ARMCC_VERSION) ARMCC_SECTION("ecspi2_sdma_driver_state") static cmsis_ecspi_sdma_driver_state_t ECSPI2_SDMADriverState = { #else static cmsis_ecspi_sdma_driver_state_t ECSPI2_SDMADriverState = { #endif &ECSPI2_Resource, &ECSPI2_SDMAResource, &ECSPI2_SdmaHandle, &ECSPI2_TxSdmaHandle, &ECSPI2_RxSdmaHandle, }; static int32_t ECSPI2_SDMAInitialize(ARM_SPI_SignalEvent_t cb_event) { #ifdef RTE_SPI2_PIN_INIT RTE_SPI2_PIN_INIT(); #endif return ECSPI_SDMAInitialize(cb_event, &ECSPI2_SDMADriverState); } static int32_t ECSPI2_SDMAUninitialize(void) { #ifdef RTE_SPI2_PIN_DEINIT RTE_SPI2_PIN_DEINIT(); #endif return ECSPI_SDMAUninitialize(&ECSPI2_SDMADriverState); } static int32_t ECSPI2_SDMAPowerControl(ARM_POWER_STATE state) { return ECSPI_SDMAPowerControl(state, &ECSPI2_SDMADriverState); } static int32_t ECSPI2_SDMASend(const void *data, uint32_t num) { return ECSPI_SDMASend(data, num, &ECSPI2_SDMADriverState); } static int32_t ECSPI2_SDMAReceive(void *data, uint32_t num) { return ECSPI_SDMAReceive(data, num, &ECSPI2_SDMADriverState); } static int32_t ECSPI2_SDMATransfer(const void *data_out, void *data_in, uint32_t num) { return ECSPI_SDMATransfer(data_out, data_in, num, &ECSPI2_SDMADriverState); } static uint32_t ECSPI2_SDMAGetCount(void) { return ECSPI_SDMAGetCount(&ECSPI2_SDMADriverState); } static int32_t ECSPI2_SDMAControl(uint32_t control, uint32_t arg) { return ECSPI_SDMAControl(control, arg, &ECSPI2_SDMADriverState); } static ARM_SPI_STATUS ECSPI2_SDMAGetStatus(void) { return ECSPI_SDMAGetStatus(&ECSPI2_SDMADriverState); } #else static ecspi_master_handle_t ECSPI2_Handle; #if defined(__CC_ARM) || defined(__ARMCC_VERSION) ARMCC_SECTION("ecspi2_interrupt_driver_state") static cmsis_ecspi_interrupt_driver_state_t ECSPI2_InterruptDriverState = { #else static cmsis_ecspi_interrupt_driver_state_t ECSPI2_InterruptDriverState = { #endif &ECSPI2_Resource, &ECSPI2_Handle, }; static int32_t ECSPI2_InterruptInitialize(ARM_SPI_SignalEvent_t cb_event) { #ifdef RTE_SPI2_PIN_INIT RTE_SPI2_PIN_INIT(); #endif return ECSPI_InterruptInitialize(cb_event, &ECSPI2_InterruptDriverState); } static int32_t ECSPI2_InterruptUninitialize(void) { #ifdef RTE_SPI2_PIN_DEINIT RTE_SPI2_PIN_DEINIT(); #endif return ECSPI_InterruptUninitialize(&ECSPI2_InterruptDriverState); } static int32_t ECSPI2_InterruptPowerControl(ARM_POWER_STATE state) { return ECSPI_InterruptPowerControl(state, &ECSPI2_InterruptDriverState); } static int32_t ECSPI2_InterruptSend(const void *data, uint32_t num) { return ECSPI_InterruptSend(data, num, &ECSPI2_InterruptDriverState); } static int32_t ECSPI2_InterruptReceive(void *data, uint32_t num) { return ECSPI_InterruptReceive(data, num, &ECSPI2_InterruptDriverState); } static int32_t ECSPI2_InterruptTransfer(const void *data_out, void *data_in, uint32_t num) { return ECSPI_InterruptTransfer(data_out, data_in, num, &ECSPI2_InterruptDriverState); } static uint32_t ECSPI2_InterruptGetCount(void) { return ECSPI_InterruptGetCount(&ECSPI2_InterruptDriverState); } static int32_t ECSPI2_InterruptControl(uint32_t control, uint32_t arg) { return ECSPI_InterruptControl(control, arg, &ECSPI2_InterruptDriverState); } static ARM_SPI_STATUS ECSPI2_InterruptGetStatus(void) { return ECSPI_InterruptGetStatus(&ECSPI2_InterruptDriverState); } #endif ARM_DRIVER_SPI Driver_SPI2 = { ECSPIx_GetVersion, ECSPIx_GetCapabilities, #if defined(RTE_SPI2_DMA_EN) && RTE_SPI2_DMA_EN ECSPI2_SDMAInitialize, ECSPI2_SDMAUninitialize, ECSPI2_SDMAPowerControl, ECSPI2_SDMASend, ECSPI2_SDMAReceive, ECSPI2_SDMATransfer, ECSPI2_SDMAGetCount, ECSPI2_SDMAControl, ECSPI2_SDMAGetStatus #else ECSPI2_InterruptInitialize, ECSPI2_InterruptUninitialize, ECSPI2_InterruptPowerControl, ECSPI2_InterruptSend, ECSPI2_InterruptReceive, ECSPI2_InterruptTransfer, ECSPI2_InterruptGetCount, ECSPI2_InterruptControl, ECSPI2_InterruptGetStatus #endif }; #endif /* ECSPI2 */ #if defined(ECSPI3) && defined(RTE_SPI3) && RTE_SPI3 /* User needs to provide the implementation for ECSPI3_GetFreq/InitPins/DeinitPins * in the application for enabling according instance. */ extern uint32_t ECSPI3_GetFreq(void); static cmsis_ecspi_resource_t ECSPI3_Resource = {ECSPI3, 3, ECSPI3_GetFreq}; #if defined(RTE_SPI3_DMA_EN) && RTE_SPI3_DMA_EN) AT_NONCACHEABLE_SECTION_ALIGN(static ecspi_sdma_handle_t ECSPI3_SdmaHandle, 4); AT_NONCACHEABLE_SECTION_ALIGN(static sdma_handle_t ECSPI3_TxSdmaHandle, 4); AT_NONCACHEABLE_SECTION_ALIGN(static sdma_handle_t ECSPI3_RxSdmaHandle, 4); AT_NONCACHEABLE_SECTION_ALIGN(static sdma_context_data_t ECSPI3_TxSdmaContext, 4); AT_NONCACHEABLE_SECTION_ALIGN(static sdma_context_data_t ECSPI3_RxSdmaContext, 4); static cmsis_ecspi_sdma_resource_t ECSPI3_SDMAResource = { RTE_SPI3_DMA_TX_DMA_BASE, RTE_SPI3_DMA_TX_CH, RTE_SPI3_DMA_TX_CH_REQUEST, RTE_SPI3_DMA_TX_CH_PRIORITY, &ECSPI3_TxSdmaContext, RTE_SPI3_DMA_RX_DMA_BASE, RTE_SPI3_DMA_RX_CH, RTE_SPI3_DMA_RX_CH_REQUEST, RTE_SPI3_DMA_RX_CH_PRIORITY, &ECSPI3_RxSdmaContext}; #if defined(__CC_ARM) || defined(__ARMCC_VERSION) ARMCC_SECTION("ecspi3_sdma_driver_state") static cmsis_ecspi_sdma_driver_state_t ECSPI3_SDMADriverState = { #else static cmsis_ecspi_sdma_driver_state_t ECSPI3_SDMADriverState = { #endif &ECSPI3_Resource, &ECSPI3_SDMAResource, &ECSPI3_SdmaHandle, &ECSPI3_TxSdmaHandle, &ECSPI3_RxSdmaHandle, }; static int32_t ECSPI3_SDMAInitialize(ARM_SPI_SignalEvent_t cb_event) { #ifdef RTE_SPI3_PIN_INIT RTE_SPI3_PIN_INIT(); #endif return ECSPI_SDMAInitialize(cb_event, &ECSPI3_SDMADriverState); } static int32_t ECSPI3_SDMAUninitialize(void) { #ifdef RTE_SPI3_PIN_DEINIT RTE_SPI3_PIN_DEINIT(); #endif return ECSPI_SDMAUninitialize(&ECSPI3_SDMADriverState); } static int32_t ECSPI3_SDMAPowerControl(ARM_POWER_STATE state) { return ECSPI_SDMAPowerControl(state, &ECSPI3_SDMADriverState); } static int32_t ECSPI3_SDMASend(const void *data, uint32_t num) { return ECSPI_SDMASend(data, num, &ECSPI3_SDMADriverState); } static int32_t ECSPI3_SDMAReceive(void *data, uint32_t num) { return ECSPI_SDMAReceive(data, num, &ECSPI3_SDMADriverState); } static int32_t ECSPI3_SDMATransfer(const void *data_out, void *data_in, uint32_t num) { return ECSPI_SDMATransfer(data_out, data_in, num, &ECSPI3_SDMADriverState); } static uint32_t ECSPI3_SDMAGetCount(void) { return ECSPI_SDMAGetCount(&ECSPI3_SDMADriverState); } static int32_t ECSPI3_SDMAControl(uint32_t control, uint32_t arg) { return ECSPI_SDMAControl(control, arg, &ECSPI3_SDMADriverState); } static ARM_SPI_STATUS ECSPI3_SDMAGetStatus(void) { return ECSPI_SDMAGetStatus(&ECSPI3_SDMADriverState); } #else static ecspi_master_handle_t ECSPI3_Handle; #if defined(__CC_ARM) || defined(__ARMCC_VERSION) ARMCC_SECTION("ecspi3_interrupt_driver_state") static cmsis_ecspi_interrupt_driver_state_t ECSPI3_InterruptDriverState = { #else static cmsis_ecspi_interrupt_driver_state_t ECSPI3_InterruptDriverState = { #endif &ECSPI3_Resource, &ECSPI3_Handle, }; static int32_t ECSPI3_InterruptInitialize(ARM_SPI_SignalEvent_t cb_event) { #ifdef RTE_SPI3_PIN_INIT RTE_SPI3_PIN_INIT(); #endif return ECSPI_InterruptInitialize(cb_event, &ECSPI3_InterruptDriverState); } static int32_t ECSPI3_InterruptUninitialize(void) { #ifdef RTE_SPI3_PIN_DEINIT RTE_SPI3_PIN_DEINIT(); #endif return ECSPI_InterruptUninitialize(&ECSPI3_InterruptDriverState); } static int32_t ECSPI3_InterruptPowerControl(ARM_POWER_STATE state) { return ECSPI_InterruptPowerControl(state, &ECSPI3_InterruptDriverState); } static int32_t ECSPI3_InterruptSend(const void *data, uint32_t num) { return ECSPI_InterruptSend(data, num, &ECSPI3_InterruptDriverState); } static int32_t ECSPI3_InterruptReceive(void *data, uint32_t num) { return ECSPI_InterruptReceive(data, num, &ECSPI3_InterruptDriverState); } static int32_t ECSPI3_InterruptTransfer(const void *data_out, void *data_in, uint32_t num) { return ECSPI_InterruptTransfer(data_out, data_in, num, &ECSPI3_InterruptDriverState); } static uint32_t ECSPI3_InterruptGetCount(void) { return ECSPI_InterruptGetCount(&ECSPI3_InterruptDriverState); } static int32_t ECSPI3_InterruptControl(uint32_t control, uint32_t arg) { return ECSPI_InterruptControl(control, arg, &ECSPI3_InterruptDriverState); } static ARM_SPI_STATUS ECSPI3_InterruptGetStatus(void) { return ECSPI_InterruptGetStatus(&ECSPI3_InterruptDriverState); } #endif ARM_DRIVER_SPI Driver_SPI3 = { ECSPIx_GetVersion, ECSPIx_GetCapabilities, #if defined(RTE_SPI3_DMA_EN) && RTE_SPI3_DMA_EN ECSPI3_SDMAInitialize, ECSPI3_SDMAUninitialize, ECSPI3_SDMAPowerControl, ECSPI3_SDMASend, ECSPI3_SDMAReceive, ECSPI3_SDMATransfer, ECSPI3_SDMAGetCount, ECSPI3_SDMAControl, ECSPI3_SDMAGetStatus #else ECSPI3_InterruptInitialize, ECSPI3_InterruptUninitialize, ECSPI3_InterruptPowerControl, ECSPI3_InterruptSend, ECSPI3_InterruptReceive, ECSPI3_InterruptTransfer, ECSPI3_InterruptGetCount, ECSPI3_InterruptControl, ECSPI3_InterruptGetStatus #endif }; #endif /* ECSPI3 */