mbed official / mbed-dev

Dependents:   Nucleo_Hello_Encoder BLE_iBeaconScan AM1805_DEMO DISCO-F429ZI_ExportTemplate1 ... more

Committer:
AnnaBridge
Date:
Wed Oct 11 12:45:49 2017 +0100
Revision:
175:af195413fb11
Parent:
targets/TARGET_NXP/TARGET_MCUXpresso_MCUS/TARGET_LPC54608/drivers/fsl_i2s.c@170:19eb464bc2be
Child:
182:a56a73fd2a6f
This updates the lib to the mbed lib v 153

Who changed what in which revision?

UserRevisionLine numberNew contents of line
Kojto 170:19eb464bc2be 1 /*
Kojto 170:19eb464bc2be 2 * Copyright (c) 2016, Freescale Semiconductor, Inc.
Kojto 170:19eb464bc2be 3 * Copyright 2016-2017 NXP
Kojto 170:19eb464bc2be 4 *
Kojto 170:19eb464bc2be 5 * Redistribution and use in source and binary forms, with or without modification,
Kojto 170:19eb464bc2be 6 * are permitted provided that the following conditions are met:
Kojto 170:19eb464bc2be 7 *
Kojto 170:19eb464bc2be 8 * o Redistributions of source code must retain the above copyright notice, this list
Kojto 170:19eb464bc2be 9 * of conditions and the following disclaimer.
Kojto 170:19eb464bc2be 10 *
Kojto 170:19eb464bc2be 11 * o Redistributions in binary form must reproduce the above copyright notice, this
Kojto 170:19eb464bc2be 12 * list of conditions and the following disclaimer in the documentation and/or
Kojto 170:19eb464bc2be 13 * other materials provided with the distribution.
Kojto 170:19eb464bc2be 14 *
Kojto 170:19eb464bc2be 15 * o Neither the name of the copyright holder nor the names of its
Kojto 170:19eb464bc2be 16 * contributors may be used to endorse or promote products derived from this
Kojto 170:19eb464bc2be 17 * software without specific prior written permission.
Kojto 170:19eb464bc2be 18 *
Kojto 170:19eb464bc2be 19 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
Kojto 170:19eb464bc2be 20 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
Kojto 170:19eb464bc2be 21 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
Kojto 170:19eb464bc2be 22 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
Kojto 170:19eb464bc2be 23 * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
Kojto 170:19eb464bc2be 24 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
Kojto 170:19eb464bc2be 25 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
Kojto 170:19eb464bc2be 26 * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
Kojto 170:19eb464bc2be 27 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
Kojto 170:19eb464bc2be 28 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
Kojto 170:19eb464bc2be 29 */
Kojto 170:19eb464bc2be 30
Kojto 170:19eb464bc2be 31 #include "fsl_i2s.h"
Kojto 170:19eb464bc2be 32 #include "fsl_flexcomm.h"
Kojto 170:19eb464bc2be 33 #include <string.h>
Kojto 170:19eb464bc2be 34
Kojto 170:19eb464bc2be 35 /*******************************************************************************
Kojto 170:19eb464bc2be 36 * Definitions
Kojto 170:19eb464bc2be 37 ******************************************************************************/
Kojto 170:19eb464bc2be 38
Kojto 170:19eb464bc2be 39 /* TODO - absent in device header files, should be there */
Kojto 170:19eb464bc2be 40 #define I2S_FIFOCFG_TXI2SE0_MASK (0x4U)
Kojto 170:19eb464bc2be 41 #define I2S_FIFOCFG_TXI2SE0_SHIFT (2U)
Kojto 170:19eb464bc2be 42 #define I2S_FIFOCFG_TXI2SE0(x) (((uint32_t)(((uint32_t)(x)) << I2S_FIFOCFG_TXI2SE0_SHIFT)) & I2S_FIFOCFG_TXI2SE0_MASK)
Kojto 170:19eb464bc2be 43 #define I2S_FIFOCFG_PACK48_MASK (0x8U)
Kojto 170:19eb464bc2be 44 #define I2S_FIFOCFG_PACK48_SHIFT (3U)
Kojto 170:19eb464bc2be 45 #define I2S_FIFOCFG_PACK48(x) (((uint32_t)(((uint32_t)(x)) << I2S_FIFOCFG_PACK48_SHIFT)) & I2S_FIFOCFG_PACK48_MASK)
Kojto 170:19eb464bc2be 46
Kojto 170:19eb464bc2be 47 /*! @brief I2S states. */
Kojto 170:19eb464bc2be 48 enum _i2s_state
Kojto 170:19eb464bc2be 49 {
Kojto 170:19eb464bc2be 50 kI2S_StateIdle = 0x0, /*!< Not performing transfer */
Kojto 170:19eb464bc2be 51 kI2S_StateTx, /*!< Performing transmit */
Kojto 170:19eb464bc2be 52 kI2S_StateTxWaitToWriteDummyData, /*!< Wait on FIFO in order to write final dummy data there */
Kojto 170:19eb464bc2be 53 kI2S_StateTxWaitForEmptyFifo, /*!< Wait for FIFO to be flushed */
Kojto 170:19eb464bc2be 54 kI2S_StateRx, /*!< Performing receive */
Kojto 170:19eb464bc2be 55 };
Kojto 170:19eb464bc2be 56
Kojto 170:19eb464bc2be 57 /*******************************************************************************
Kojto 170:19eb464bc2be 58 * Prototypes
Kojto 170:19eb464bc2be 59 ******************************************************************************/
Kojto 170:19eb464bc2be 60
Kojto 170:19eb464bc2be 61 static void I2S_Config(I2S_Type *base, const i2s_config_t *config);
Kojto 170:19eb464bc2be 62 static status_t I2S_ValidateBuffer(i2s_handle_t *handle, i2s_transfer_t *transfer);
Kojto 170:19eb464bc2be 63
Kojto 170:19eb464bc2be 64 /*******************************************************************************
Kojto 170:19eb464bc2be 65 * Code
Kojto 170:19eb464bc2be 66 ******************************************************************************/
Kojto 170:19eb464bc2be 67
Kojto 170:19eb464bc2be 68 void I2S_TxInit(I2S_Type *base, const i2s_config_t *config)
Kojto 170:19eb464bc2be 69 {
Kojto 170:19eb464bc2be 70 uint32_t cfg = 0U;
Kojto 170:19eb464bc2be 71 uint32_t trig = 0U;
Kojto 170:19eb464bc2be 72
Kojto 170:19eb464bc2be 73 FLEXCOMM_Init(base, FLEXCOMM_PERIPH_I2S_TX);
Kojto 170:19eb464bc2be 74 I2S_Config(base, config);
Kojto 170:19eb464bc2be 75
Kojto 170:19eb464bc2be 76 /* Configure FIFO */
Kojto 170:19eb464bc2be 77
Kojto 170:19eb464bc2be 78 cfg |= I2S_FIFOCFG_ENABLETX(1U); /* enable TX FIFO */
Kojto 170:19eb464bc2be 79 cfg |= I2S_FIFOCFG_EMPTYTX(1U); /* empty TX FIFO */
Kojto 170:19eb464bc2be 80 cfg |= I2S_FIFOCFG_TXI2SE0(config->txEmptyZero); /* transmit zero when buffer becomes empty or last item */
Kojto 170:19eb464bc2be 81 cfg |= I2S_FIFOCFG_PACK48(config->pack48); /* set pack 48-bit format or not */
Kojto 170:19eb464bc2be 82 trig |= I2S_FIFOTRIG_TXLVLENA(1U); /* enable TX FIFO trigger */
Kojto 170:19eb464bc2be 83 trig |= I2S_FIFOTRIG_TXLVL(config->watermark); /* set TX FIFO trigger level */
Kojto 170:19eb464bc2be 84
Kojto 170:19eb464bc2be 85 base->FIFOCFG = cfg;
Kojto 170:19eb464bc2be 86 base->FIFOTRIG = trig;
Kojto 170:19eb464bc2be 87 }
Kojto 170:19eb464bc2be 88
Kojto 170:19eb464bc2be 89 void I2S_RxInit(I2S_Type *base, const i2s_config_t *config)
Kojto 170:19eb464bc2be 90 {
Kojto 170:19eb464bc2be 91 uint32_t cfg = 0U;
Kojto 170:19eb464bc2be 92 uint32_t trig = 0U;
Kojto 170:19eb464bc2be 93
Kojto 170:19eb464bc2be 94 FLEXCOMM_Init(base, FLEXCOMM_PERIPH_I2S_RX);
Kojto 170:19eb464bc2be 95 I2S_Config(base, config);
Kojto 170:19eb464bc2be 96
Kojto 170:19eb464bc2be 97 /* Configure FIFO */
Kojto 170:19eb464bc2be 98
Kojto 170:19eb464bc2be 99 cfg |= I2S_FIFOCFG_ENABLERX(1U); /* enable RX FIFO */
Kojto 170:19eb464bc2be 100 cfg |= I2S_FIFOCFG_EMPTYRX(1U); /* empty RX FIFO */
Kojto 170:19eb464bc2be 101 cfg |= I2S_FIFOCFG_PACK48(config->pack48); /* set pack 48-bit format or not */
Kojto 170:19eb464bc2be 102 trig |= I2S_FIFOTRIG_RXLVLENA(1U); /* enable RX FIFO trigger */
Kojto 170:19eb464bc2be 103 trig |= I2S_FIFOTRIG_RXLVL(config->watermark); /* set RX FIFO trigger level */
Kojto 170:19eb464bc2be 104
Kojto 170:19eb464bc2be 105 base->FIFOCFG = cfg;
Kojto 170:19eb464bc2be 106 base->FIFOTRIG = trig;
Kojto 170:19eb464bc2be 107 }
Kojto 170:19eb464bc2be 108
Kojto 170:19eb464bc2be 109 void I2S_TxGetDefaultConfig(i2s_config_t *config)
Kojto 170:19eb464bc2be 110 {
Kojto 170:19eb464bc2be 111 config->masterSlave = kI2S_MasterSlaveNormalMaster;
Kojto 170:19eb464bc2be 112 config->mode = kI2S_ModeI2sClassic;
Kojto 170:19eb464bc2be 113 config->rightLow = false;
Kojto 170:19eb464bc2be 114 config->leftJust = false;
Kojto 170:19eb464bc2be 115 config->pdmData = false;
Kojto 170:19eb464bc2be 116 config->sckPol = false;
Kojto 170:19eb464bc2be 117 config->wsPol = false;
Kojto 170:19eb464bc2be 118 config->divider = 1U;
Kojto 170:19eb464bc2be 119 config->oneChannel = false;
Kojto 170:19eb464bc2be 120 config->dataLength = 16U;
Kojto 170:19eb464bc2be 121 config->frameLength = 32U;
Kojto 170:19eb464bc2be 122 config->position = 0U;
Kojto 170:19eb464bc2be 123 config->watermark = 4U;
Kojto 170:19eb464bc2be 124 config->txEmptyZero = true;
Kojto 170:19eb464bc2be 125 config->pack48 = false;
Kojto 170:19eb464bc2be 126 }
Kojto 170:19eb464bc2be 127
Kojto 170:19eb464bc2be 128 void I2S_RxGetDefaultConfig(i2s_config_t *config)
Kojto 170:19eb464bc2be 129 {
Kojto 170:19eb464bc2be 130 config->masterSlave = kI2S_MasterSlaveNormalSlave;
Kojto 170:19eb464bc2be 131 config->mode = kI2S_ModeI2sClassic;
Kojto 170:19eb464bc2be 132 config->rightLow = false;
Kojto 170:19eb464bc2be 133 config->leftJust = false;
Kojto 170:19eb464bc2be 134 config->pdmData = false;
Kojto 170:19eb464bc2be 135 config->sckPol = false;
Kojto 170:19eb464bc2be 136 config->wsPol = false;
Kojto 170:19eb464bc2be 137 config->divider = 1U;
Kojto 170:19eb464bc2be 138 config->oneChannel = false;
Kojto 170:19eb464bc2be 139 config->dataLength = 16U;
Kojto 170:19eb464bc2be 140 config->frameLength = 32U;
Kojto 170:19eb464bc2be 141 config->position = 0U;
Kojto 170:19eb464bc2be 142 config->watermark = 4U;
Kojto 170:19eb464bc2be 143 config->txEmptyZero = false;
Kojto 170:19eb464bc2be 144 config->pack48 = false;
Kojto 170:19eb464bc2be 145 }
Kojto 170:19eb464bc2be 146
Kojto 170:19eb464bc2be 147 static void I2S_Config(I2S_Type *base, const i2s_config_t *config)
Kojto 170:19eb464bc2be 148 {
Kojto 170:19eb464bc2be 149 assert(config);
Kojto 170:19eb464bc2be 150
Kojto 170:19eb464bc2be 151 uint32_t cfg1 = 0U;
Kojto 170:19eb464bc2be 152 uint32_t cfg2 = 0U;
Kojto 170:19eb464bc2be 153
Kojto 170:19eb464bc2be 154 /* set master/slave configuration */
Kojto 170:19eb464bc2be 155 cfg1 |= I2S_CFG1_MSTSLVCFG(config->masterSlave);
Kojto 170:19eb464bc2be 156
Kojto 170:19eb464bc2be 157 /* set I2S mode */
Kojto 170:19eb464bc2be 158 cfg1 |= I2S_CFG1_MODE(config->mode);
Kojto 170:19eb464bc2be 159
Kojto 170:19eb464bc2be 160 /* set right low (channel swap) */
Kojto 170:19eb464bc2be 161 cfg1 |= I2S_CFG1_RIGHTLOW(config->rightLow);
Kojto 170:19eb464bc2be 162
Kojto 170:19eb464bc2be 163 /* set data justification */
Kojto 170:19eb464bc2be 164 cfg1 |= I2S_CFG1_LEFTJUST(config->leftJust);
Kojto 170:19eb464bc2be 165
Kojto 170:19eb464bc2be 166 /* set source to PDM dmic */
Kojto 170:19eb464bc2be 167 cfg1 |= I2S_CFG1_PDMDATA(config->pdmData);
Kojto 170:19eb464bc2be 168
Kojto 170:19eb464bc2be 169 /* set SCLK polarity */
Kojto 170:19eb464bc2be 170 cfg1 |= I2S_CFG1_SCK_POL(config->sckPol);
Kojto 170:19eb464bc2be 171
Kojto 170:19eb464bc2be 172 /* set WS polarity */
Kojto 170:19eb464bc2be 173 cfg1 |= I2S_CFG1_WS_POL(config->wsPol);
Kojto 170:19eb464bc2be 174
Kojto 170:19eb464bc2be 175 /* set mono mode */
Kojto 170:19eb464bc2be 176 cfg1 |= I2S_CFG1_ONECHANNEL(config->oneChannel);
Kojto 170:19eb464bc2be 177
Kojto 170:19eb464bc2be 178 /* set data length */
Kojto 170:19eb464bc2be 179 cfg1 |= I2S_CFG1_DATALEN(config->dataLength - 1U);
Kojto 170:19eb464bc2be 180
Kojto 170:19eb464bc2be 181 /* set frame length */
Kojto 170:19eb464bc2be 182 cfg2 |= I2S_CFG2_FRAMELEN(config->frameLength - 1U);
Kojto 170:19eb464bc2be 183
Kojto 170:19eb464bc2be 184 /* set data position of this channel pair within the frame */
Kojto 170:19eb464bc2be 185 cfg2 |= I2S_CFG2_POSITION(config->position);
Kojto 170:19eb464bc2be 186
Kojto 170:19eb464bc2be 187 /* write to registers */
Kojto 170:19eb464bc2be 188 base->CFG1 = cfg1;
Kojto 170:19eb464bc2be 189 base->CFG2 = cfg2;
Kojto 170:19eb464bc2be 190
Kojto 170:19eb464bc2be 191 /* set the clock divider */
Kojto 170:19eb464bc2be 192 base->DIV = I2S_DIV_DIV(config->divider - 1U);
Kojto 170:19eb464bc2be 193 }
Kojto 170:19eb464bc2be 194
Kojto 170:19eb464bc2be 195 void I2S_Deinit(I2S_Type *base)
Kojto 170:19eb464bc2be 196 {
Kojto 170:19eb464bc2be 197 /* TODO gate FLEXCOMM clock via FLEXCOMM driver */
Kojto 170:19eb464bc2be 198 }
Kojto 170:19eb464bc2be 199
Kojto 170:19eb464bc2be 200 void I2S_TxEnable(I2S_Type *base, bool enable)
Kojto 170:19eb464bc2be 201 {
Kojto 170:19eb464bc2be 202 if (enable)
Kojto 170:19eb464bc2be 203 {
Kojto 170:19eb464bc2be 204 I2S_EnableInterrupts(base, kI2S_TxErrorFlag | kI2S_TxLevelFlag);
Kojto 170:19eb464bc2be 205 I2S_Enable(base);
Kojto 170:19eb464bc2be 206 }
Kojto 170:19eb464bc2be 207 else
Kojto 170:19eb464bc2be 208 {
Kojto 170:19eb464bc2be 209 I2S_DisableInterrupts(base, kI2S_TxErrorFlag | kI2S_TxLevelFlag);
Kojto 170:19eb464bc2be 210 I2S_Disable(base);
Kojto 170:19eb464bc2be 211 base->FIFOCFG |= I2S_FIFOCFG_EMPTYTX_MASK;
Kojto 170:19eb464bc2be 212 }
Kojto 170:19eb464bc2be 213 }
Kojto 170:19eb464bc2be 214
Kojto 170:19eb464bc2be 215 void I2S_RxEnable(I2S_Type *base, bool enable)
Kojto 170:19eb464bc2be 216 {
Kojto 170:19eb464bc2be 217 if (enable)
Kojto 170:19eb464bc2be 218 {
Kojto 170:19eb464bc2be 219 I2S_EnableInterrupts(base, kI2S_RxErrorFlag | kI2S_RxLevelFlag);
Kojto 170:19eb464bc2be 220 I2S_Enable(base);
Kojto 170:19eb464bc2be 221 }
Kojto 170:19eb464bc2be 222 else
Kojto 170:19eb464bc2be 223 {
Kojto 170:19eb464bc2be 224 I2S_DisableInterrupts(base, kI2S_RxErrorFlag | kI2S_RxLevelFlag);
Kojto 170:19eb464bc2be 225 I2S_Disable(base);
Kojto 170:19eb464bc2be 226 base->FIFOCFG |= I2S_FIFOCFG_EMPTYRX_MASK;
Kojto 170:19eb464bc2be 227 }
Kojto 170:19eb464bc2be 228 }
Kojto 170:19eb464bc2be 229
Kojto 170:19eb464bc2be 230 static status_t I2S_ValidateBuffer(i2s_handle_t *handle, i2s_transfer_t *transfer)
Kojto 170:19eb464bc2be 231 {
Kojto 170:19eb464bc2be 232 assert(transfer->data);
Kojto 170:19eb464bc2be 233 if (!transfer->data)
Kojto 170:19eb464bc2be 234 {
Kojto 170:19eb464bc2be 235 return kStatus_InvalidArgument;
Kojto 170:19eb464bc2be 236 }
Kojto 170:19eb464bc2be 237
Kojto 170:19eb464bc2be 238 assert(transfer->dataSize > 0U);
Kojto 170:19eb464bc2be 239 if (transfer->dataSize <= 0U)
Kojto 170:19eb464bc2be 240 {
Kojto 170:19eb464bc2be 241 return kStatus_InvalidArgument;
Kojto 170:19eb464bc2be 242 }
Kojto 170:19eb464bc2be 243
Kojto 170:19eb464bc2be 244 if (handle->dataLength == 4U)
Kojto 170:19eb464bc2be 245 {
Kojto 170:19eb464bc2be 246 /* No alignment and data length requirements */
Kojto 170:19eb464bc2be 247 }
Kojto 170:19eb464bc2be 248 else if ((handle->dataLength >= 5U) && (handle->dataLength <= 8U))
Kojto 170:19eb464bc2be 249 {
Kojto 170:19eb464bc2be 250 assert((((uint32_t)transfer->data) % 2U) == 0U);
Kojto 170:19eb464bc2be 251 if ((((uint32_t)transfer->data) % 2U) != 0U)
Kojto 170:19eb464bc2be 252 {
Kojto 170:19eb464bc2be 253 /* Data not 2-bytes aligned */
Kojto 170:19eb464bc2be 254 return kStatus_InvalidArgument;
Kojto 170:19eb464bc2be 255 }
Kojto 170:19eb464bc2be 256
Kojto 170:19eb464bc2be 257 assert((transfer->dataSize % 2U) == 0U);
Kojto 170:19eb464bc2be 258 if ((transfer->dataSize % 2U) != 0U)
Kojto 170:19eb464bc2be 259 {
Kojto 170:19eb464bc2be 260 /* Data not in pairs of left/right channel bytes */
Kojto 170:19eb464bc2be 261 return kStatus_InvalidArgument;
Kojto 170:19eb464bc2be 262 }
Kojto 170:19eb464bc2be 263 }
Kojto 170:19eb464bc2be 264 else if ((handle->dataLength >= 9U) && (handle->dataLength <= 16U))
Kojto 170:19eb464bc2be 265 {
Kojto 170:19eb464bc2be 266 assert((((uint32_t)transfer->data) % 4U) == 0U);
Kojto 170:19eb464bc2be 267 if ((((uint32_t)transfer->data) % 4U) != 0U)
Kojto 170:19eb464bc2be 268 {
Kojto 170:19eb464bc2be 269 /* Data not 4-bytes aligned */
Kojto 170:19eb464bc2be 270 return kStatus_InvalidArgument;
Kojto 170:19eb464bc2be 271 }
Kojto 170:19eb464bc2be 272
Kojto 170:19eb464bc2be 273 assert((transfer->dataSize % 4U) == 0U);
Kojto 170:19eb464bc2be 274 if ((transfer->dataSize % 4U) != 0U)
Kojto 170:19eb464bc2be 275 {
Kojto 170:19eb464bc2be 276 /* Data lenght not multiply of 4 */
Kojto 170:19eb464bc2be 277 return kStatus_InvalidArgument;
Kojto 170:19eb464bc2be 278 }
Kojto 170:19eb464bc2be 279 }
Kojto 170:19eb464bc2be 280 else if ((handle->dataLength >= 17U) && (handle->dataLength <= 24U))
Kojto 170:19eb464bc2be 281 {
Kojto 170:19eb464bc2be 282 assert((transfer->dataSize % 6U) == 0U);
Kojto 170:19eb464bc2be 283 if ((transfer->dataSize % 6U) != 0U)
Kojto 170:19eb464bc2be 284 {
Kojto 170:19eb464bc2be 285 /* Data lenght not multiply of 6 */
Kojto 170:19eb464bc2be 286 return kStatus_InvalidArgument;
Kojto 170:19eb464bc2be 287 }
Kojto 170:19eb464bc2be 288
Kojto 170:19eb464bc2be 289 assert(!((handle->pack48) && ((((uint32_t)transfer->data) % 4U) != 0U)));
Kojto 170:19eb464bc2be 290 if ((handle->pack48) && ((((uint32_t)transfer->data) % 4U) != 0U))
Kojto 170:19eb464bc2be 291 {
Kojto 170:19eb464bc2be 292 /* Data not 4-bytes aligned */
Kojto 170:19eb464bc2be 293 return kStatus_InvalidArgument;
Kojto 170:19eb464bc2be 294 }
Kojto 170:19eb464bc2be 295 }
Kojto 170:19eb464bc2be 296 else /* if (handle->dataLength >= 25U) */
Kojto 170:19eb464bc2be 297 {
Kojto 170:19eb464bc2be 298 assert((((uint32_t)transfer->data) % 4U) == 0U);
Kojto 170:19eb464bc2be 299 if ((((uint32_t)transfer->data) % 4U) != 0U)
Kojto 170:19eb464bc2be 300 {
Kojto 170:19eb464bc2be 301 /* Data not 4-bytes aligned */
Kojto 170:19eb464bc2be 302 return kStatus_InvalidArgument;
Kojto 170:19eb464bc2be 303 }
Kojto 170:19eb464bc2be 304
Kojto 170:19eb464bc2be 305 if (handle->oneChannel)
Kojto 170:19eb464bc2be 306 {
Kojto 170:19eb464bc2be 307 assert((transfer->dataSize % 4U) == 0U);
Kojto 170:19eb464bc2be 308 if ((transfer->dataSize % 4U) != 0U)
Kojto 170:19eb464bc2be 309 {
Kojto 170:19eb464bc2be 310 /* Data lenght not multiply of 4 */
Kojto 170:19eb464bc2be 311 return kStatus_InvalidArgument;
Kojto 170:19eb464bc2be 312 }
Kojto 170:19eb464bc2be 313 }
Kojto 170:19eb464bc2be 314 else
Kojto 170:19eb464bc2be 315 {
Kojto 170:19eb464bc2be 316 assert((transfer->dataSize % 8U) == 0U);
Kojto 170:19eb464bc2be 317 if ((transfer->dataSize % 8U) != 0U)
Kojto 170:19eb464bc2be 318 {
Kojto 170:19eb464bc2be 319 /* Data lenght not multiply of 8 */
Kojto 170:19eb464bc2be 320 return kStatus_InvalidArgument;
Kojto 170:19eb464bc2be 321 }
Kojto 170:19eb464bc2be 322 }
Kojto 170:19eb464bc2be 323 }
Kojto 170:19eb464bc2be 324
Kojto 170:19eb464bc2be 325 return kStatus_Success;
Kojto 170:19eb464bc2be 326 }
Kojto 170:19eb464bc2be 327
Kojto 170:19eb464bc2be 328 void I2S_TxTransferCreateHandle(I2S_Type *base, i2s_handle_t *handle, i2s_transfer_callback_t callback, void *userData)
Kojto 170:19eb464bc2be 329 {
Kojto 170:19eb464bc2be 330 assert(handle);
Kojto 170:19eb464bc2be 331
Kojto 170:19eb464bc2be 332 /* Clear out the handle */
Kojto 170:19eb464bc2be 333 memset(handle, 0U, sizeof(*handle));
Kojto 170:19eb464bc2be 334
Kojto 170:19eb464bc2be 335 /* Save callback and user data */
Kojto 170:19eb464bc2be 336 handle->completionCallback = callback;
Kojto 170:19eb464bc2be 337 handle->userData = userData;
Kojto 170:19eb464bc2be 338
Kojto 170:19eb464bc2be 339 /* Remember some items set previously by configuration */
Kojto 170:19eb464bc2be 340 handle->watermark = ((base->FIFOTRIG & I2S_FIFOTRIG_TXLVL_MASK) >> I2S_FIFOTRIG_TXLVL_SHIFT);
Kojto 170:19eb464bc2be 341 handle->oneChannel = ((base->CFG1 & I2S_CFG1_ONECHANNEL_MASK) >> I2S_CFG1_ONECHANNEL_SHIFT);
Kojto 170:19eb464bc2be 342 handle->dataLength = ((base->CFG1 & I2S_CFG1_DATALEN_MASK) >> I2S_CFG1_DATALEN_SHIFT) + 1U;
Kojto 170:19eb464bc2be 343 handle->pack48 = ((base->FIFOCFG & I2S_FIFOCFG_PACK48_MASK) >> I2S_FIFOCFG_PACK48_SHIFT);
Kojto 170:19eb464bc2be 344
Kojto 170:19eb464bc2be 345 handle->useFifo48H = false;
Kojto 170:19eb464bc2be 346
Kojto 170:19eb464bc2be 347 /* Register IRQ handling */
Kojto 170:19eb464bc2be 348 FLEXCOMM_SetIRQHandler(base, (flexcomm_irq_handler_t)(uintptr_t)I2S_TxHandleIRQ, handle);
Kojto 170:19eb464bc2be 349 }
Kojto 170:19eb464bc2be 350
Kojto 170:19eb464bc2be 351 status_t I2S_TxTransferNonBlocking(I2S_Type *base, i2s_handle_t *handle, i2s_transfer_t transfer)
Kojto 170:19eb464bc2be 352 {
Kojto 170:19eb464bc2be 353 assert(handle);
Kojto 170:19eb464bc2be 354 if (!handle)
Kojto 170:19eb464bc2be 355 {
Kojto 170:19eb464bc2be 356 return kStatus_InvalidArgument;
Kojto 170:19eb464bc2be 357 }
Kojto 170:19eb464bc2be 358
Kojto 170:19eb464bc2be 359 status_t result;
Kojto 170:19eb464bc2be 360
Kojto 170:19eb464bc2be 361 result = I2S_ValidateBuffer(handle, &transfer);
Kojto 170:19eb464bc2be 362 if (result != kStatus_Success)
Kojto 170:19eb464bc2be 363 {
Kojto 170:19eb464bc2be 364 return result;
Kojto 170:19eb464bc2be 365 }
Kojto 170:19eb464bc2be 366
Kojto 170:19eb464bc2be 367 if (handle->i2sQueue[handle->queueUser].dataSize)
Kojto 170:19eb464bc2be 368 {
Kojto 170:19eb464bc2be 369 /* Previously prepared buffers not processed yet */
Kojto 170:19eb464bc2be 370 return kStatus_I2S_Busy;
Kojto 170:19eb464bc2be 371 }
Kojto 170:19eb464bc2be 372
Kojto 170:19eb464bc2be 373 handle->state = kI2S_StateTx;
Kojto 170:19eb464bc2be 374 handle->i2sQueue[handle->queueUser].data = transfer.data;
Kojto 170:19eb464bc2be 375 handle->i2sQueue[handle->queueUser].dataSize = transfer.dataSize;
Kojto 170:19eb464bc2be 376 handle->queueUser = (handle->queueUser + 1U) % I2S_NUM_BUFFERS;
Kojto 170:19eb464bc2be 377
Kojto 170:19eb464bc2be 378 base->FIFOTRIG = (base->FIFOTRIG & (~I2S_FIFOTRIG_TXLVL_MASK)) | I2S_FIFOTRIG_TXLVL(handle->watermark);
Kojto 170:19eb464bc2be 379 I2S_TxEnable(base, true);
Kojto 170:19eb464bc2be 380
Kojto 170:19eb464bc2be 381 return kStatus_Success;
Kojto 170:19eb464bc2be 382 }
Kojto 170:19eb464bc2be 383
Kojto 170:19eb464bc2be 384 void I2S_TxTransferAbort(I2S_Type *base, i2s_handle_t *handle)
Kojto 170:19eb464bc2be 385 {
Kojto 170:19eb464bc2be 386 assert(handle);
Kojto 170:19eb464bc2be 387
Kojto 170:19eb464bc2be 388 /* Disable I2S operation and interrupts */
Kojto 170:19eb464bc2be 389 I2S_TxEnable(base, false);
Kojto 170:19eb464bc2be 390
Kojto 170:19eb464bc2be 391 /* Reset state */
Kojto 170:19eb464bc2be 392 handle->state = kI2S_StateIdle;
Kojto 170:19eb464bc2be 393
Kojto 170:19eb464bc2be 394 /* Clear transfer queue */
Kojto 170:19eb464bc2be 395 memset((void *)&handle->i2sQueue, 0U, sizeof(i2s_transfer_t) * I2S_NUM_BUFFERS);
Kojto 170:19eb464bc2be 396 handle->queueDriver = 0U;
Kojto 170:19eb464bc2be 397 handle->queueUser = 0U;
Kojto 170:19eb464bc2be 398 }
Kojto 170:19eb464bc2be 399
Kojto 170:19eb464bc2be 400 void I2S_RxTransferCreateHandle(I2S_Type *base, i2s_handle_t *handle, i2s_transfer_callback_t callback, void *userData)
Kojto 170:19eb464bc2be 401 {
Kojto 170:19eb464bc2be 402 assert(handle);
Kojto 170:19eb464bc2be 403
Kojto 170:19eb464bc2be 404 /* Clear out the handle */
Kojto 170:19eb464bc2be 405 memset(handle, 0U, sizeof(*handle));
Kojto 170:19eb464bc2be 406
Kojto 170:19eb464bc2be 407 /* Save callback and user data */
Kojto 170:19eb464bc2be 408 handle->completionCallback = callback;
Kojto 170:19eb464bc2be 409 handle->userData = userData;
Kojto 170:19eb464bc2be 410
Kojto 170:19eb464bc2be 411 /* Remember some items set previously by configuration */
Kojto 170:19eb464bc2be 412 handle->watermark = ((base->FIFOTRIG & I2S_FIFOTRIG_RXLVL_MASK) >> I2S_FIFOTRIG_RXLVL_SHIFT);
Kojto 170:19eb464bc2be 413 handle->oneChannel = ((base->CFG1 & I2S_CFG1_ONECHANNEL_MASK) >> I2S_CFG1_ONECHANNEL_SHIFT);
Kojto 170:19eb464bc2be 414 handle->dataLength = ((base->CFG1 & I2S_CFG1_DATALEN_MASK) >> I2S_CFG1_DATALEN_SHIFT) + 1U;
Kojto 170:19eb464bc2be 415 handle->pack48 = ((base->FIFOCFG & I2S_FIFOCFG_PACK48_MASK) >> I2S_FIFOCFG_PACK48_SHIFT);
Kojto 170:19eb464bc2be 416
Kojto 170:19eb464bc2be 417 handle->useFifo48H = false;
Kojto 170:19eb464bc2be 418
Kojto 170:19eb464bc2be 419 /* Register IRQ handling */
Kojto 170:19eb464bc2be 420 FLEXCOMM_SetIRQHandler(base, (flexcomm_irq_handler_t)(uintptr_t)I2S_RxHandleIRQ, handle);
Kojto 170:19eb464bc2be 421 }
Kojto 170:19eb464bc2be 422
Kojto 170:19eb464bc2be 423 status_t I2S_RxTransferNonBlocking(I2S_Type *base, i2s_handle_t *handle, i2s_transfer_t transfer)
Kojto 170:19eb464bc2be 424 {
Kojto 170:19eb464bc2be 425 assert(handle);
Kojto 170:19eb464bc2be 426 if (!handle)
Kojto 170:19eb464bc2be 427 {
Kojto 170:19eb464bc2be 428 return kStatus_InvalidArgument;
Kojto 170:19eb464bc2be 429 }
Kojto 170:19eb464bc2be 430
Kojto 170:19eb464bc2be 431 status_t result;
Kojto 170:19eb464bc2be 432
Kojto 170:19eb464bc2be 433 result = I2S_ValidateBuffer(handle, &transfer);
Kojto 170:19eb464bc2be 434 if (result != kStatus_Success)
Kojto 170:19eb464bc2be 435 {
Kojto 170:19eb464bc2be 436 return result;
Kojto 170:19eb464bc2be 437 }
Kojto 170:19eb464bc2be 438
Kojto 170:19eb464bc2be 439 if (handle->i2sQueue[handle->queueUser].dataSize)
Kojto 170:19eb464bc2be 440 {
Kojto 170:19eb464bc2be 441 /* Previously prepared buffers not processed yet */
Kojto 170:19eb464bc2be 442 return kStatus_I2S_Busy;
Kojto 170:19eb464bc2be 443 }
Kojto 170:19eb464bc2be 444
Kojto 170:19eb464bc2be 445 handle->state = kI2S_StateRx;
Kojto 170:19eb464bc2be 446 handle->i2sQueue[handle->queueUser].data = transfer.data;
Kojto 170:19eb464bc2be 447 handle->i2sQueue[handle->queueUser].dataSize = transfer.dataSize;
Kojto 170:19eb464bc2be 448 handle->queueUser = (handle->queueUser + 1U) % I2S_NUM_BUFFERS;
Kojto 170:19eb464bc2be 449
Kojto 170:19eb464bc2be 450 base->FIFOTRIG = (base->FIFOTRIG & (~I2S_FIFOTRIG_RXLVL_MASK)) | I2S_FIFOTRIG_RXLVL(handle->watermark);
Kojto 170:19eb464bc2be 451 I2S_RxEnable(base, true);
Kojto 170:19eb464bc2be 452
Kojto 170:19eb464bc2be 453 return kStatus_Success;
Kojto 170:19eb464bc2be 454 }
Kojto 170:19eb464bc2be 455
Kojto 170:19eb464bc2be 456 void I2S_RxTransferAbort(I2S_Type *base, i2s_handle_t *handle)
Kojto 170:19eb464bc2be 457 {
Kojto 170:19eb464bc2be 458 assert(handle);
Kojto 170:19eb464bc2be 459
Kojto 170:19eb464bc2be 460 /* Disable I2S operation and interrupts */
Kojto 170:19eb464bc2be 461 I2S_RxEnable(base, false);
Kojto 170:19eb464bc2be 462
Kojto 170:19eb464bc2be 463 /* Reset state */
Kojto 170:19eb464bc2be 464 handle->state = kI2S_StateIdle;
Kojto 170:19eb464bc2be 465
Kojto 170:19eb464bc2be 466 /* Clear transfer queue */
Kojto 170:19eb464bc2be 467 memset((void *)&handle->i2sQueue, 0U, sizeof(i2s_transfer_t) * I2S_NUM_BUFFERS);
Kojto 170:19eb464bc2be 468 handle->queueDriver = 0U;
Kojto 170:19eb464bc2be 469 handle->queueUser = 0U;
Kojto 170:19eb464bc2be 470 }
Kojto 170:19eb464bc2be 471
Kojto 170:19eb464bc2be 472 status_t I2S_TransferGetCount(I2S_Type *base, i2s_handle_t *handle, size_t *count)
Kojto 170:19eb464bc2be 473 {
Kojto 170:19eb464bc2be 474 assert(handle);
Kojto 170:19eb464bc2be 475 if (!handle)
Kojto 170:19eb464bc2be 476 {
Kojto 170:19eb464bc2be 477 return kStatus_InvalidArgument;
Kojto 170:19eb464bc2be 478 }
Kojto 170:19eb464bc2be 479
Kojto 170:19eb464bc2be 480 assert(count);
Kojto 170:19eb464bc2be 481 if (!count)
Kojto 170:19eb464bc2be 482 {
Kojto 170:19eb464bc2be 483 return kStatus_InvalidArgument;
Kojto 170:19eb464bc2be 484 }
Kojto 170:19eb464bc2be 485
Kojto 170:19eb464bc2be 486 if (handle->state == kI2S_StateIdle)
Kojto 170:19eb464bc2be 487 {
Kojto 170:19eb464bc2be 488 return kStatus_NoTransferInProgress;
Kojto 170:19eb464bc2be 489 }
Kojto 170:19eb464bc2be 490
Kojto 170:19eb464bc2be 491 *count = handle->transferCount;
Kojto 170:19eb464bc2be 492
Kojto 170:19eb464bc2be 493 return kStatus_Success;
Kojto 170:19eb464bc2be 494 }
Kojto 170:19eb464bc2be 495
Kojto 170:19eb464bc2be 496 status_t I2S_TransferGetErrorCount(I2S_Type *base, i2s_handle_t *handle, size_t *count)
Kojto 170:19eb464bc2be 497 {
Kojto 170:19eb464bc2be 498 assert(handle);
Kojto 170:19eb464bc2be 499 if (!handle)
Kojto 170:19eb464bc2be 500 {
Kojto 170:19eb464bc2be 501 return kStatus_InvalidArgument;
Kojto 170:19eb464bc2be 502 }
Kojto 170:19eb464bc2be 503
Kojto 170:19eb464bc2be 504 assert(count);
Kojto 170:19eb464bc2be 505 if (!count)
Kojto 170:19eb464bc2be 506 {
Kojto 170:19eb464bc2be 507 return kStatus_InvalidArgument;
Kojto 170:19eb464bc2be 508 }
Kojto 170:19eb464bc2be 509
Kojto 170:19eb464bc2be 510 if (handle->state == kI2S_StateIdle)
Kojto 170:19eb464bc2be 511 {
Kojto 170:19eb464bc2be 512 return kStatus_NoTransferInProgress;
Kojto 170:19eb464bc2be 513 }
Kojto 170:19eb464bc2be 514
Kojto 170:19eb464bc2be 515 *count = handle->errorCount;
Kojto 170:19eb464bc2be 516
Kojto 170:19eb464bc2be 517 return kStatus_Success;
Kojto 170:19eb464bc2be 518 }
Kojto 170:19eb464bc2be 519
Kojto 170:19eb464bc2be 520 void I2S_TxHandleIRQ(I2S_Type *base, i2s_handle_t *handle)
Kojto 170:19eb464bc2be 521 {
Kojto 170:19eb464bc2be 522 uint32_t intstat = base->FIFOINTSTAT;
Kojto 170:19eb464bc2be 523 uint32_t data;
Kojto 170:19eb464bc2be 524
Kojto 170:19eb464bc2be 525 if (intstat & I2S_FIFOINTSTAT_TXERR_MASK)
Kojto 170:19eb464bc2be 526 {
Kojto 170:19eb464bc2be 527 handle->errorCount++;
Kojto 170:19eb464bc2be 528
Kojto 170:19eb464bc2be 529 /* Clear TX error interrupt flag */
Kojto 170:19eb464bc2be 530 base->FIFOSTAT = I2S_FIFOSTAT_TXERR(1U);
Kojto 170:19eb464bc2be 531 }
Kojto 170:19eb464bc2be 532
Kojto 170:19eb464bc2be 533 if (intstat & I2S_FIFOINTSTAT_TXLVL_MASK)
Kojto 170:19eb464bc2be 534 {
Kojto 170:19eb464bc2be 535 if (handle->state == kI2S_StateTx)
Kojto 170:19eb464bc2be 536 {
Kojto 170:19eb464bc2be 537 /* Send data */
Kojto 170:19eb464bc2be 538
Kojto 170:19eb464bc2be 539 while ((base->FIFOSTAT & I2S_FIFOSTAT_TXNOTFULL_MASK) &&
Kojto 170:19eb464bc2be 540 (handle->i2sQueue[handle->queueDriver].dataSize > 0U))
Kojto 170:19eb464bc2be 541 {
Kojto 170:19eb464bc2be 542 /* Write output data */
Kojto 170:19eb464bc2be 543 if (handle->dataLength == 4U)
Kojto 170:19eb464bc2be 544 {
Kojto 170:19eb464bc2be 545 data = *(handle->i2sQueue[handle->queueDriver].data);
Kojto 170:19eb464bc2be 546 base->FIFOWR = ((data & 0xF0U) << 12U) | (data & 0xFU);
Kojto 170:19eb464bc2be 547 handle->i2sQueue[handle->queueDriver].data++;
Kojto 170:19eb464bc2be 548 handle->transferCount++;
Kojto 170:19eb464bc2be 549 handle->i2sQueue[handle->queueDriver].dataSize--;
Kojto 170:19eb464bc2be 550 }
Kojto 170:19eb464bc2be 551 else if (handle->dataLength <= 8U)
Kojto 170:19eb464bc2be 552 {
Kojto 170:19eb464bc2be 553 data = *((uint16_t *)handle->i2sQueue[handle->queueDriver].data);
Kojto 170:19eb464bc2be 554 base->FIFOWR = ((data & 0xFF00U) << 8U) | (data & 0xFFU);
Kojto 170:19eb464bc2be 555 handle->i2sQueue[handle->queueDriver].data += sizeof(uint16_t);
Kojto 170:19eb464bc2be 556 handle->transferCount += sizeof(uint16_t);
Kojto 170:19eb464bc2be 557 handle->i2sQueue[handle->queueDriver].dataSize -= sizeof(uint16_t);
Kojto 170:19eb464bc2be 558 }
Kojto 170:19eb464bc2be 559 else if (handle->dataLength <= 16U)
Kojto 170:19eb464bc2be 560 {
Kojto 170:19eb464bc2be 561 base->FIFOWR = *((uint32_t *)(handle->i2sQueue[handle->queueDriver].data));
Kojto 170:19eb464bc2be 562 handle->i2sQueue[handle->queueDriver].data += sizeof(uint32_t);
Kojto 170:19eb464bc2be 563 handle->transferCount += sizeof(uint32_t);
Kojto 170:19eb464bc2be 564 handle->i2sQueue[handle->queueDriver].dataSize -= sizeof(uint32_t);
Kojto 170:19eb464bc2be 565 }
Kojto 170:19eb464bc2be 566 else if (handle->dataLength <= 24U)
Kojto 170:19eb464bc2be 567 {
Kojto 170:19eb464bc2be 568 if (handle->pack48)
Kojto 170:19eb464bc2be 569 {
Kojto 170:19eb464bc2be 570 if (handle->useFifo48H)
Kojto 170:19eb464bc2be 571 {
Kojto 170:19eb464bc2be 572 base->FIFOWR48H = *((uint16_t *)(handle->i2sQueue[handle->queueDriver].data));
Kojto 170:19eb464bc2be 573 handle->i2sQueue[handle->queueDriver].data += sizeof(uint16_t);
Kojto 170:19eb464bc2be 574 handle->transferCount += sizeof(uint16_t);
Kojto 170:19eb464bc2be 575 handle->i2sQueue[handle->queueDriver].dataSize -= sizeof(uint16_t);
Kojto 170:19eb464bc2be 576 handle->useFifo48H = false;
Kojto 170:19eb464bc2be 577 }
Kojto 170:19eb464bc2be 578 else
Kojto 170:19eb464bc2be 579 {
Kojto 170:19eb464bc2be 580 base->FIFOWR = *((uint32_t *)(handle->i2sQueue[handle->queueDriver].data));
Kojto 170:19eb464bc2be 581 handle->i2sQueue[handle->queueDriver].data += sizeof(uint32_t);
Kojto 170:19eb464bc2be 582 handle->transferCount += sizeof(uint32_t);
Kojto 170:19eb464bc2be 583 handle->i2sQueue[handle->queueDriver].dataSize -= sizeof(uint32_t);
Kojto 170:19eb464bc2be 584 handle->useFifo48H = true;
Kojto 170:19eb464bc2be 585 }
Kojto 170:19eb464bc2be 586 }
Kojto 170:19eb464bc2be 587 else
Kojto 170:19eb464bc2be 588 {
Kojto 170:19eb464bc2be 589 data = (uint32_t)(*(handle->i2sQueue[handle->queueDriver].data++));
Kojto 170:19eb464bc2be 590 data |= ((uint32_t)(*(handle->i2sQueue[handle->queueDriver].data++))) << 8U;
Kojto 170:19eb464bc2be 591 data |= ((uint32_t)(*(handle->i2sQueue[handle->queueDriver].data++))) << 16U;
Kojto 170:19eb464bc2be 592 if (handle->useFifo48H)
Kojto 170:19eb464bc2be 593 {
Kojto 170:19eb464bc2be 594 base->FIFOWR48H = data;
Kojto 170:19eb464bc2be 595 handle->useFifo48H = false;
Kojto 170:19eb464bc2be 596 }
Kojto 170:19eb464bc2be 597 else
Kojto 170:19eb464bc2be 598 {
Kojto 170:19eb464bc2be 599 base->FIFOWR = data;
Kojto 170:19eb464bc2be 600 handle->useFifo48H = true;
Kojto 170:19eb464bc2be 601 }
Kojto 170:19eb464bc2be 602 handle->transferCount += 3U;
Kojto 170:19eb464bc2be 603 handle->i2sQueue[handle->queueDriver].dataSize -= 3U;
Kojto 170:19eb464bc2be 604 }
Kojto 170:19eb464bc2be 605 }
Kojto 170:19eb464bc2be 606 else /* if (handle->dataLength <= 32U) */
Kojto 170:19eb464bc2be 607 {
Kojto 170:19eb464bc2be 608 base->FIFOWR = *((uint32_t *)(handle->i2sQueue[handle->queueDriver].data));
Kojto 170:19eb464bc2be 609 handle->i2sQueue[handle->queueDriver].data += sizeof(uint32_t);
Kojto 170:19eb464bc2be 610 handle->transferCount += sizeof(uint32_t);
Kojto 170:19eb464bc2be 611 handle->i2sQueue[handle->queueDriver].dataSize -= sizeof(uint32_t);
Kojto 170:19eb464bc2be 612 }
Kojto 170:19eb464bc2be 613
Kojto 170:19eb464bc2be 614 if (handle->i2sQueue[handle->queueDriver].dataSize == 0U)
Kojto 170:19eb464bc2be 615 {
Kojto 170:19eb464bc2be 616 /* Actual data buffer sent out, switch to a next one */
Kojto 170:19eb464bc2be 617 handle->queueDriver = (handle->queueDriver + 1U) % I2S_NUM_BUFFERS;
Kojto 170:19eb464bc2be 618
Kojto 170:19eb464bc2be 619 /* Notify user */
Kojto 170:19eb464bc2be 620 if (handle->completionCallback)
Kojto 170:19eb464bc2be 621 {
Kojto 170:19eb464bc2be 622 handle->completionCallback(base, handle, kStatus_I2S_BufferComplete, handle->userData);
Kojto 170:19eb464bc2be 623 }
Kojto 170:19eb464bc2be 624
Kojto 170:19eb464bc2be 625 /* Check if the next buffer contains anything to send */
Kojto 170:19eb464bc2be 626 if (handle->i2sQueue[handle->queueDriver].dataSize == 0U)
Kojto 170:19eb464bc2be 627 {
Kojto 170:19eb464bc2be 628 /* Everything has been written to FIFO */
Kojto 170:19eb464bc2be 629 handle->state = kI2S_StateTxWaitToWriteDummyData;
Kojto 170:19eb464bc2be 630 break;
Kojto 170:19eb464bc2be 631 }
Kojto 170:19eb464bc2be 632 }
Kojto 170:19eb464bc2be 633 }
Kojto 170:19eb464bc2be 634 }
Kojto 170:19eb464bc2be 635 else if (handle->state == kI2S_StateTxWaitToWriteDummyData)
Kojto 170:19eb464bc2be 636 {
Kojto 170:19eb464bc2be 637 /* Write dummy data */
Kojto 170:19eb464bc2be 638 if ((handle->dataLength > 16U) && (handle->dataLength < 25U))
Kojto 170:19eb464bc2be 639 {
Kojto 170:19eb464bc2be 640 if (handle->useFifo48H)
Kojto 170:19eb464bc2be 641 {
Kojto 170:19eb464bc2be 642 base->FIFOWR48H = 0U;
Kojto 170:19eb464bc2be 643 handle->useFifo48H = false;
Kojto 170:19eb464bc2be 644 }
Kojto 170:19eb464bc2be 645 else
Kojto 170:19eb464bc2be 646 {
Kojto 170:19eb464bc2be 647 base->FIFOWR = 0U;
Kojto 170:19eb464bc2be 648 base->FIFOWR48H = 0U;
Kojto 170:19eb464bc2be 649 }
Kojto 170:19eb464bc2be 650 }
Kojto 170:19eb464bc2be 651 else
Kojto 170:19eb464bc2be 652 {
Kojto 170:19eb464bc2be 653 base->FIFOWR = 0U;
Kojto 170:19eb464bc2be 654 }
Kojto 170:19eb464bc2be 655
Kojto 170:19eb464bc2be 656 /* Next time invoke this handler when FIFO becomes empty (TX level 0) */
Kojto 170:19eb464bc2be 657 base->FIFOTRIG &= ~I2S_FIFOTRIG_TXLVL_MASK;
Kojto 170:19eb464bc2be 658 handle->state = kI2S_StateTxWaitForEmptyFifo;
Kojto 170:19eb464bc2be 659 }
Kojto 170:19eb464bc2be 660 else if (handle->state == kI2S_StateTxWaitForEmptyFifo)
Kojto 170:19eb464bc2be 661 {
Kojto 170:19eb464bc2be 662 /* FIFO, including additional dummy data, has been emptied now,
Kojto 170:19eb464bc2be 663 * all relevant data should have been output from peripheral */
Kojto 170:19eb464bc2be 664
Kojto 170:19eb464bc2be 665 /* Stop transfer */
Kojto 170:19eb464bc2be 666 I2S_Disable(base);
Kojto 170:19eb464bc2be 667 I2S_DisableInterrupts(base, kI2S_TxErrorFlag | kI2S_TxLevelFlag);
Kojto 170:19eb464bc2be 668 base->FIFOCFG |= I2S_FIFOCFG_EMPTYTX_MASK;
Kojto 170:19eb464bc2be 669
Kojto 170:19eb464bc2be 670 /* Reset state */
Kojto 170:19eb464bc2be 671 handle->state = kI2S_StateIdle;
Kojto 170:19eb464bc2be 672
Kojto 170:19eb464bc2be 673 /* Notify user */
Kojto 170:19eb464bc2be 674 if (handle->completionCallback)
Kojto 170:19eb464bc2be 675 {
Kojto 170:19eb464bc2be 676 handle->completionCallback(base, handle, kStatus_I2S_Done, handle->userData);
Kojto 170:19eb464bc2be 677 }
Kojto 170:19eb464bc2be 678 }
Kojto 170:19eb464bc2be 679 else
Kojto 170:19eb464bc2be 680 {
Kojto 170:19eb464bc2be 681 /* Do nothing */
Kojto 170:19eb464bc2be 682 }
Kojto 170:19eb464bc2be 683
Kojto 170:19eb464bc2be 684 /* Clear TX level interrupt flag */
Kojto 170:19eb464bc2be 685 base->FIFOSTAT = I2S_FIFOSTAT_TXLVL(1U);
Kojto 170:19eb464bc2be 686 }
Kojto 170:19eb464bc2be 687 }
Kojto 170:19eb464bc2be 688
Kojto 170:19eb464bc2be 689 void I2S_RxHandleIRQ(I2S_Type *base, i2s_handle_t *handle)
Kojto 170:19eb464bc2be 690 {
Kojto 170:19eb464bc2be 691 uint32_t intstat = base->FIFOINTSTAT;
Kojto 170:19eb464bc2be 692 uint32_t data;
Kojto 170:19eb464bc2be 693
Kojto 170:19eb464bc2be 694 if (intstat & I2S_FIFOINTSTAT_RXERR_MASK)
Kojto 170:19eb464bc2be 695 {
Kojto 170:19eb464bc2be 696 handle->errorCount++;
Kojto 170:19eb464bc2be 697
Kojto 170:19eb464bc2be 698 /* Clear RX error interrupt flag */
Kojto 170:19eb464bc2be 699 base->FIFOSTAT = I2S_FIFOSTAT_RXERR(1U);
Kojto 170:19eb464bc2be 700 }
Kojto 170:19eb464bc2be 701
Kojto 170:19eb464bc2be 702 if (intstat & I2S_FIFOINTSTAT_RXLVL_MASK)
Kojto 170:19eb464bc2be 703 {
Kojto 170:19eb464bc2be 704 while ((base->FIFOSTAT & I2S_FIFOSTAT_RXNOTEMPTY_MASK) && (handle->i2sQueue[handle->queueDriver].dataSize > 0U))
Kojto 170:19eb464bc2be 705 {
Kojto 170:19eb464bc2be 706 /* Read input data */
Kojto 170:19eb464bc2be 707 if (handle->dataLength == 4U)
Kojto 170:19eb464bc2be 708 {
Kojto 170:19eb464bc2be 709 data = base->FIFORD;
Kojto 170:19eb464bc2be 710 *(handle->i2sQueue[handle->queueDriver].data) = ((data & 0x000F0000U) >> 12U) | (data & 0x0000000FU);
Kojto 170:19eb464bc2be 711 handle->i2sQueue[handle->queueDriver].data++;
Kojto 170:19eb464bc2be 712 handle->transferCount++;
Kojto 170:19eb464bc2be 713 handle->i2sQueue[handle->queueDriver].dataSize--;
Kojto 170:19eb464bc2be 714 }
Kojto 170:19eb464bc2be 715 else if (handle->dataLength <= 8U)
Kojto 170:19eb464bc2be 716 {
Kojto 170:19eb464bc2be 717 data = base->FIFORD;
Kojto 170:19eb464bc2be 718 *((uint16_t *)handle->i2sQueue[handle->queueDriver].data) = ((data >> 8U) & 0xFF00U) | (data & 0xFFU);
Kojto 170:19eb464bc2be 719 handle->i2sQueue[handle->queueDriver].data += sizeof(uint16_t);
Kojto 170:19eb464bc2be 720 handle->transferCount += sizeof(uint16_t);
Kojto 170:19eb464bc2be 721 handle->i2sQueue[handle->queueDriver].dataSize -= sizeof(uint16_t);
Kojto 170:19eb464bc2be 722 }
Kojto 170:19eb464bc2be 723 else if (handle->dataLength <= 16U)
Kojto 170:19eb464bc2be 724 {
Kojto 170:19eb464bc2be 725 data = base->FIFORD;
Kojto 170:19eb464bc2be 726 *((uint32_t *)handle->i2sQueue[handle->queueDriver].data) = data;
Kojto 170:19eb464bc2be 727 handle->i2sQueue[handle->queueDriver].data += sizeof(uint32_t);
Kojto 170:19eb464bc2be 728 handle->transferCount += sizeof(uint32_t);
Kojto 170:19eb464bc2be 729 handle->i2sQueue[handle->queueDriver].dataSize -= sizeof(uint32_t);
Kojto 170:19eb464bc2be 730 }
Kojto 170:19eb464bc2be 731 else if (handle->dataLength <= 24U)
Kojto 170:19eb464bc2be 732 {
Kojto 170:19eb464bc2be 733 if (handle->pack48)
Kojto 170:19eb464bc2be 734 {
Kojto 170:19eb464bc2be 735 if (handle->useFifo48H)
Kojto 170:19eb464bc2be 736 {
Kojto 170:19eb464bc2be 737 data = base->FIFORD48H;
Kojto 170:19eb464bc2be 738 handle->useFifo48H = false;
Kojto 170:19eb464bc2be 739
Kojto 170:19eb464bc2be 740 *((uint16_t *)handle->i2sQueue[handle->queueDriver].data) = data;
Kojto 170:19eb464bc2be 741 handle->i2sQueue[handle->queueDriver].data += sizeof(uint16_t);
Kojto 170:19eb464bc2be 742 handle->transferCount += sizeof(uint16_t);
Kojto 170:19eb464bc2be 743 handle->i2sQueue[handle->queueDriver].dataSize -= sizeof(uint16_t);
Kojto 170:19eb464bc2be 744 }
Kojto 170:19eb464bc2be 745 else
Kojto 170:19eb464bc2be 746 {
Kojto 170:19eb464bc2be 747 data = base->FIFORD;
Kojto 170:19eb464bc2be 748 handle->useFifo48H = true;
Kojto 170:19eb464bc2be 749
Kojto 170:19eb464bc2be 750 *((uint32_t *)handle->i2sQueue[handle->queueDriver].data) = data;
Kojto 170:19eb464bc2be 751 handle->i2sQueue[handle->queueDriver].data += sizeof(uint32_t);
Kojto 170:19eb464bc2be 752 handle->transferCount += sizeof(uint32_t);
Kojto 170:19eb464bc2be 753 handle->i2sQueue[handle->queueDriver].dataSize -= sizeof(uint32_t);
Kojto 170:19eb464bc2be 754 }
Kojto 170:19eb464bc2be 755 }
Kojto 170:19eb464bc2be 756 else
Kojto 170:19eb464bc2be 757 {
Kojto 170:19eb464bc2be 758 if (handle->useFifo48H)
Kojto 170:19eb464bc2be 759 {
Kojto 170:19eb464bc2be 760 data = base->FIFORD48H;
Kojto 170:19eb464bc2be 761 handle->useFifo48H = false;
Kojto 170:19eb464bc2be 762 }
Kojto 170:19eb464bc2be 763 else
Kojto 170:19eb464bc2be 764 {
Kojto 170:19eb464bc2be 765 data = base->FIFORD;
Kojto 170:19eb464bc2be 766 handle->useFifo48H = true;
Kojto 170:19eb464bc2be 767 }
Kojto 170:19eb464bc2be 768
Kojto 170:19eb464bc2be 769 *(handle->i2sQueue[handle->queueDriver].data++) = data & 0xFFU;
Kojto 170:19eb464bc2be 770 *(handle->i2sQueue[handle->queueDriver].data++) = (data >> 8U) & 0xFFU;
Kojto 170:19eb464bc2be 771 *(handle->i2sQueue[handle->queueDriver].data++) = (data >> 16U) & 0xFFU;
Kojto 170:19eb464bc2be 772 handle->transferCount += 3U;
Kojto 170:19eb464bc2be 773 handle->i2sQueue[handle->queueDriver].dataSize -= 3U;
Kojto 170:19eb464bc2be 774 }
Kojto 170:19eb464bc2be 775 }
Kojto 170:19eb464bc2be 776 else /* if (handle->dataLength <= 32U) */
Kojto 170:19eb464bc2be 777 {
Kojto 170:19eb464bc2be 778 data = base->FIFORD;
Kojto 170:19eb464bc2be 779 *((uint32_t *)handle->i2sQueue[handle->queueDriver].data) = data;
Kojto 170:19eb464bc2be 780 handle->i2sQueue[handle->queueDriver].data += sizeof(uint32_t);
Kojto 170:19eb464bc2be 781 handle->transferCount += sizeof(uint32_t);
Kojto 170:19eb464bc2be 782 handle->i2sQueue[handle->queueDriver].dataSize -= sizeof(uint32_t);
Kojto 170:19eb464bc2be 783 }
Kojto 170:19eb464bc2be 784
Kojto 170:19eb464bc2be 785 if (handle->i2sQueue[handle->queueDriver].dataSize == 0U)
Kojto 170:19eb464bc2be 786 {
Kojto 170:19eb464bc2be 787 /* Actual data buffer filled with input data, switch to a next one */
Kojto 170:19eb464bc2be 788 handle->queueDriver = (handle->queueDriver + 1U) % I2S_NUM_BUFFERS;
Kojto 170:19eb464bc2be 789
Kojto 170:19eb464bc2be 790 /* Notify user */
Kojto 170:19eb464bc2be 791 if (handle->completionCallback)
Kojto 170:19eb464bc2be 792 {
Kojto 170:19eb464bc2be 793 handle->completionCallback(base, handle, kStatus_I2S_BufferComplete, handle->userData);
Kojto 170:19eb464bc2be 794 }
Kojto 170:19eb464bc2be 795
Kojto 170:19eb464bc2be 796 if (handle->i2sQueue[handle->queueDriver].dataSize == 0U)
Kojto 170:19eb464bc2be 797 {
Kojto 170:19eb464bc2be 798 /* No other buffer prepared to receive data into */
Kojto 170:19eb464bc2be 799
Kojto 170:19eb464bc2be 800 /* Disable I2S operation and interrupts */
Kojto 170:19eb464bc2be 801 I2S_Disable(base);
Kojto 170:19eb464bc2be 802 I2S_DisableInterrupts(base, kI2S_RxErrorFlag | kI2S_RxLevelFlag);
Kojto 170:19eb464bc2be 803 base->FIFOCFG |= I2S_FIFOCFG_EMPTYRX_MASK;
Kojto 170:19eb464bc2be 804
Kojto 170:19eb464bc2be 805 /* Reset state */
Kojto 170:19eb464bc2be 806 handle->state = kI2S_StateIdle;
Kojto 170:19eb464bc2be 807
Kojto 170:19eb464bc2be 808 /* Notify user */
Kojto 170:19eb464bc2be 809 if (handle->completionCallback)
Kojto 170:19eb464bc2be 810 {
Kojto 170:19eb464bc2be 811 handle->completionCallback(base, handle, kStatus_I2S_Done, handle->userData);
Kojto 170:19eb464bc2be 812 }
Kojto 170:19eb464bc2be 813
Kojto 170:19eb464bc2be 814 /* Clear RX level interrupt flag */
Kojto 170:19eb464bc2be 815 base->FIFOSTAT = I2S_FIFOSTAT_RXLVL(1U);
Kojto 170:19eb464bc2be 816
Kojto 170:19eb464bc2be 817 return;
Kojto 170:19eb464bc2be 818 }
Kojto 170:19eb464bc2be 819 }
Kojto 170:19eb464bc2be 820 }
Kojto 170:19eb464bc2be 821
Kojto 170:19eb464bc2be 822 /* Clear RX level interrupt flag */
Kojto 170:19eb464bc2be 823 base->FIFOSTAT = I2S_FIFOSTAT_RXLVL(1U);
Kojto 170:19eb464bc2be 824 }
Kojto 170:19eb464bc2be 825 }