1 /*
2  * Copyright (c) 2016, Freescale Semiconductor, Inc.
3  * Copyright 2017-2020 NXP
4  * All rights reserved.
5  *
6  *
7  * SPDX-License-Identifier: BSD-3-Clause
8  */
9 
10 #ifndef FSL_SPDIF_H_
11 #define FSL_SPDIF_H_
12 
13 #include "fsl_common.h"
14 
15 /*!
16  * @addtogroup spdif
17  * @{
18  */
19 
20 /*******************************************************************************
21  * Definitions
22  ******************************************************************************/
23 
24 /*! @name Driver version */
25 /*! @{ */
26 #define FSL_SPDIF_DRIVER_VERSION (MAKE_VERSION(2, 0, 6)) /*!< Version 2.0.6 */
27 /*! @} */
28 
29 /*! @brief SPDIF return status*/
30 enum
31 {
32     kStatus_SPDIF_RxDPLLLocked     = MAKE_STATUS(kStatusGroup_SPDIF, 0), /*!< SPDIF Rx PLL locked. */
33     kStatus_SPDIF_TxFIFOError      = MAKE_STATUS(kStatusGroup_SPDIF, 1), /*!< SPDIF Tx FIFO error. */
34     kStatus_SPDIF_TxFIFOResync     = MAKE_STATUS(kStatusGroup_SPDIF, 2), /*!< SPDIF Tx left and right FIFO resync. */
35     kStatus_SPDIF_RxCnew           = MAKE_STATUS(kStatusGroup_SPDIF, 3), /*!< SPDIF Rx status channel value updated. */
36     kStatus_SPDIF_ValidatyNoGood   = MAKE_STATUS(kStatusGroup_SPDIF, 4), /*!< SPDIF validaty flag not good. */
37     kStatus_SPDIF_RxIllegalSymbol  = MAKE_STATUS(kStatusGroup_SPDIF, 5), /*!< SPDIF Rx receive illegal symbol. */
38     kStatus_SPDIF_RxParityBitError = MAKE_STATUS(kStatusGroup_SPDIF, 6), /*!< SPDIF Rx parity bit error. */
39     kStatus_SPDIF_UChannelOverrun  = MAKE_STATUS(kStatusGroup_SPDIF, 7), /*!< SPDIF receive U channel overrun. */
40     kStatus_SPDIF_QChannelOverrun  = MAKE_STATUS(kStatusGroup_SPDIF, 8), /*!< SPDIF receive Q channel overrun. */
41     kStatus_SPDIF_UQChannelSync    = MAKE_STATUS(kStatusGroup_SPDIF, 9), /*!< SPDIF U/Q channel sync found. */
42     kStatus_SPDIF_UQChannelFrameError = MAKE_STATUS(kStatusGroup_SPDIF, 10), /*!< SPDIF U/Q channel frame error. */
43     kStatus_SPDIF_RxFIFOError         = MAKE_STATUS(kStatusGroup_SPDIF, 11), /*!< SPDIF Rx FIFO error. */
44     kStatus_SPDIF_RxFIFOResync = MAKE_STATUS(kStatusGroup_SPDIF, 12), /*!< SPDIF Rx left and right FIFO resync. */
45     kStatus_SPDIF_LockLoss     = MAKE_STATUS(kStatusGroup_SPDIF, 13), /*!< SPDIF Rx PLL clock lock loss. */
46     kStatus_SPDIF_TxIdle       = MAKE_STATUS(kStatusGroup_SPDIF, 14), /*!< SPDIF Tx is idle */
47     kStatus_SPDIF_RxIdle       = MAKE_STATUS(kStatusGroup_SPDIF, 15), /*!< SPDIF Rx is idle */
48     kStatus_SPDIF_QueueFull    = MAKE_STATUS(kStatusGroup_SPDIF, 16)  /*!< SPDIF queue full */
49 };
50 
51 /*! @brief SPDIF Rx FIFO full falg select, it decides when assert the rx full flag */
52 typedef enum _spdif_rxfull_select
53 {
54     kSPDIF_RxFull1Sample = 0x0u, /*!< Rx full at least 1 sample in left and right FIFO */
55     kSPDIF_RxFull4Samples,       /*!< Rx full at least 4 sample in left and right FIFO*/
56     kSPDIF_RxFull8Samples,       /*!< Rx full at least 8 sample in left and right FIFO*/
57     kSPDIF_RxFull16Samples,      /*!< Rx full at least 16 sample in left and right FIFO*/
58 } spdif_rxfull_select_t;
59 
60 /*! @brief SPDIF tx FIFO EMPTY falg select, it decides when assert the tx empty flag */
61 typedef enum _spdif_txempty_select
62 {
63     kSPDIF_TxEmpty0Sample = 0x0u, /*!< Tx empty at most 0 sample in left and right FIFO */
64     kSPDIF_TxEmpty4Samples,       /*!< Tx empty at most 4 sample in left and right FIFO*/
65     kSPDIF_TxEmpty8Samples,       /*!< Tx empty at most 8 sample in left and right FIFO*/
66     kSPDIF_TxEmpty12Samples,      /*!< Tx empty at most 12 sample in left and right FIFO*/
67 } spdif_txempty_select_t;
68 
69 /*! @brief SPDIF U channel source */
70 typedef enum _spdif_uchannel_source
71 {
72     kSPDIF_NoUChannel     = 0x0U, /*!< No embedded U channel */
73     kSPDIF_UChannelFromRx = 0x1U, /*!< U channel from receiver, it is CD mode */
74     kSPDIF_UChannelFromTx = 0x3U, /*!< U channel from on chip tx */
75 } spdif_uchannel_source_t;
76 
77 /*! @brief SPDIF clock gain*/
78 typedef enum _spdif_gain_select
79 {
80     kSPDIF_GAIN_24 = 0x0U, /*!< Gain select is 24 */
81     kSPDIF_GAIN_16,        /*!< Gain select is 16 */
82     kSPDIF_GAIN_12,        /*!< Gain select is 12 */
83     kSPDIF_GAIN_8,         /*!< Gain select is 8 */
84     kSPDIF_GAIN_6,         /*!< Gain select is 6 */
85     kSPDIF_GAIN_4,         /*!< Gain select is 4 */
86     kSPDIF_GAIN_3,         /*!< Gain select is 3 */
87 } spdif_gain_select_t;
88 
89 /*! @brief SPDIF tx data source */
90 typedef enum _spdif_tx_source
91 {
92     kSPDIF_txFromReceiver = 0x1U, /*!< Tx data directly through SPDIF receiver */
93     kSPDIF_txNormal       = 0x5U, /*!< Normal operation, data from processor */
94 } spdif_tx_source_t;
95 
96 /*! @brief SPDIF tx data source */
97 typedef enum _spdif_validity_config
98 {
99     kSPDIF_validityFlagAlwaysSet = 0x0U, /*!< Outgoing validity flags always set */
100     kSPDIF_validityFlagAlwaysClear,      /*!< Outgoing validity flags always clear */
101 } spdif_validity_config_t;
102 
103 /*! @brief The SPDIF interrupt enable flag */
104 enum
105 {
106     kSPDIF_RxDPLLLocked                   = SPDIF_SIE_LOCK_MASK,        /*!< SPDIF DPLL locked */
107     kSPDIF_TxFIFOError                    = SPDIF_SIE_TXUNOV_MASK,      /*!< Tx FIFO underrun or overrun */
108     kSPDIF_TxFIFOResync                   = SPDIF_SIE_TXRESYN_MASK,     /*!< Tx FIFO left and right channel resync */
109     kSPDIF_RxControlChannelChange         = SPDIF_SIE_CNEW_MASK,        /*!< SPDIF Rx control channel value changed */
110     kSPDIF_ValidityFlagNoGood             = SPDIF_SIE_VALNOGOOD_MASK,   /*!< SPDIF validity flag no good */
111     kSPDIF_RxIllegalSymbol                = SPDIF_SIE_SYMERR_MASK,      /*!< SPDIF receiver found illegal symbol */
112     kSPDIF_RxParityBitError               = SPDIF_SIE_BITERR_MASK,      /*!< SPDIF receiver found parity bit error */
113     kSPDIF_UChannelReceiveRegisterFull    = SPDIF_SIE_URXFUL_MASK,      /*!< SPDIF U channel revceive register full */
114     kSPDIF_UChannelReceiveRegisterOverrun = SPDIF_SIE_URXOV_MASK,       /*!< SPDIF U channel receive register overrun */
115     kSPDIF_QChannelReceiveRegisterFull    = SPDIF_SIE_QRXFUL_MASK,      /*!< SPDIF Q channel receive reigster full */
116     kSPDIF_QChannelReceiveRegisterOverrun = SPDIF_SIE_QRXOV_MASK,       /*!< SPDIF Q channel receive register overrun */
117     kSPDIF_UQChannelSync                  = SPDIF_SIE_UQSYNC_MASK,      /*!< SPDIF U/Q channel sync found */
118     kSPDIF_UQChannelFrameError            = SPDIF_SIE_UQERR_MASK,       /*!< SPDIF U/Q channel frame error */
119     kSPDIF_RxFIFOError                    = SPDIF_SIE_RXFIFOUNOV_MASK,  /*!< SPDIF Rx FIFO underrun/overrun */
120     kSPDIF_RxFIFOResync                   = SPDIF_SIE_RXFIFORESYN_MASK, /*!< SPDIF Rx left and right FIFO resync */
121     kSPDIF_LockLoss                       = SPDIF_SIE_LOCKLOSS_MASK,    /*!< SPDIF receiver loss of lock */
122     kSPDIF_TxFIFOEmpty                    = SPDIF_SIE_TXEM_MASK,        /*!< SPDIF Tx FIFO empty */
123     kSPDIF_RxFIFOFull                     = SPDIF_SIE_RXFIFOFUL_MASK,   /*!< SPDIF Rx FIFO full */
124     kSPDIF_AllInterrupt                   = kSPDIF_RxDPLLLocked | kSPDIF_TxFIFOError | kSPDIF_TxFIFOResync |
125                           kSPDIF_RxControlChannelChange | kSPDIF_ValidityFlagNoGood | kSPDIF_RxIllegalSymbol |
126                           kSPDIF_RxParityBitError | kSPDIF_UChannelReceiveRegisterFull |
127                           kSPDIF_UChannelReceiveRegisterOverrun | kSPDIF_QChannelReceiveRegisterFull |
128                           kSPDIF_QChannelReceiveRegisterOverrun | kSPDIF_UQChannelSync | kSPDIF_UQChannelFrameError |
129                           kSPDIF_RxFIFOError | kSPDIF_RxFIFOResync | kSPDIF_LockLoss | kSPDIF_TxFIFOEmpty |
130                           kSPDIF_RxFIFOFull, /*!< all interrupt */
131 };
132 
133 /*! @brief The DMA request sources */
134 enum
135 {
136     kSPDIF_RxDMAEnable = SPDIF_SCR_DMA_RX_EN_MASK, /*!< Rx FIFO full */
137     kSPDIF_TxDMAEnable = SPDIF_SCR_DMA_TX_EN_MASK, /*!< Tx FIFO empty */
138 };
139 
140 /*! @brief SPDIF user configuration structure */
141 typedef struct _spdif_config
142 {
143     bool isTxAutoSync;                      /*!< If auto sync mechanism open */
144     bool isRxAutoSync;                      /*!< If auto sync mechanism open */
145     uint8_t DPLLClkSource;                  /*!< SPDIF DPLL clock source, range from 0~15, meaning is chip-specific */
146     uint8_t txClkSource;                    /*!< SPDIF tx clock source, range from 0~7, meaning is chip-specific */
147     spdif_rxfull_select_t rxFullSelect;     /*!< SPDIF rx buffer full select */
148     spdif_txempty_select_t txFullSelect;    /*!< SPDIF tx buffer empty select */
149     spdif_uchannel_source_t uChannelSrc;    /*!< U channel source */
150     spdif_tx_source_t txSource;             /*!< SPDIF tx data source */
151     spdif_validity_config_t validityConfig; /*!< Validity flag config */
152     spdif_gain_select_t gain;               /*!< Rx receive clock measure gain parameter. */
153 } spdif_config_t;
154 
155 /*!@brief SPDIF transfer queue size, user can refine it according to use case. */
156 #define SPDIF_XFER_QUEUE_SIZE (4U)
157 
158 /*! @brief SPDIF transfer structure */
159 typedef struct _spdif_transfer
160 {
161     uint8_t *data;   /*!< Data start address to transfer. */
162     uint8_t *qdata;  /*!< Data buffer for Q channel */
163     uint8_t *udata;  /*!< Data buffer for C channel */
164     size_t dataSize; /*!< Transfer size. */
165 } spdif_transfer_t;
166 
167 typedef struct _spdif_handle spdif_handle_t;
168 
169 /*! @brief SPDIF transfer callback prototype */
170 typedef void (*spdif_transfer_callback_t)(SPDIF_Type *base, spdif_handle_t *handle, status_t status, void *userData);
171 
172 /*! @brief SPDIF handle structure */
173 struct _spdif_handle
174 {
175     uint32_t state;                                     /*!< Transfer status */
176     spdif_transfer_callback_t callback;                 /*!< Callback function called at transfer event*/
177     void *userData;                                     /*!< Callback parameter passed to callback function*/
178     spdif_transfer_t spdifQueue[SPDIF_XFER_QUEUE_SIZE]; /*!< Transfer queue storing queued transfer */
179     size_t transferSize[SPDIF_XFER_QUEUE_SIZE];         /*!< Data bytes need to transfer */
180     volatile uint8_t queueUser;                         /*!< Index for user to queue transfer */
181     volatile uint8_t queueDriver;                       /*!< Index for driver to get the transfer data and size */
182     uint8_t watermark;                                  /*!< Watermark value */
183 };
184 
185 /*******************************************************************************
186  * API
187  ******************************************************************************/
188 
189 #if defined(__cplusplus)
190 extern "C" {
191 #endif /*_cplusplus*/
192 
193 /*!
194  * @name Initialization and deinitialization
195  * @{
196  */
197 
198 /*!
199  * @brief Initializes the SPDIF peripheral.
200  *
201  * Ungates the SPDIF clock, resets the module, and configures SPDIF with a configuration structure.
202  * The configuration structure can be custom filled or set with default values by
203  * SPDIF_GetDefaultConfig().
204  *
205  * @note  This API should be called at the beginning of the application to use
206  * the SPDIF driver. Otherwise, accessing the SPDIF module can cause a hard fault
207  * because the clock is not enabled.
208  *
209  * @param base SPDIF base pointer
210  * @param config SPDIF configuration structure.
211  */
212 void SPDIF_Init(SPDIF_Type *base, const spdif_config_t *config);
213 
214 /*!
215  * @brief  Sets the SPDIF configuration structure to default values.
216  *
217  * This API initializes the configuration structure for use in SPDIF_Init.
218  * The initialized structure can remain unchanged in SPDIF_Init, or it can be modified
219  *  before calling SPDIF_Init.
220  * This is an example.
221    @code
222    spdif_config_t config;
223    SPDIF_GetDefaultConfig(&config);
224    @endcode
225  *
226  * @param config pointer to master configuration structure
227  */
228 void SPDIF_GetDefaultConfig(spdif_config_t *config);
229 
230 /*!
231  * @brief De-initializes the SPDIF peripheral.
232  *
233  * This API gates the SPDIF clock. The SPDIF module can't operate unless SPDIF_Init is called to enable the clock.
234  *
235  * @param base SPDIF base pointer
236  */
237 void SPDIF_Deinit(SPDIF_Type *base);
238 
239 /*!
240  * @brief Get the instance number for SPDIF.
241  *
242  * @param base SPDIF base pointer.
243  */
244 uint32_t SPDIF_GetInstance(SPDIF_Type *base);
245 
246 /*!
247  * @brief Resets the SPDIF Tx.
248  *
249  * This function makes Tx FIFO in reset mode.
250  *
251  * @param base SPDIF base pointer
252  */
SPDIF_TxFIFOReset(SPDIF_Type * base)253 static inline void SPDIF_TxFIFOReset(SPDIF_Type *base)
254 {
255     base->SCR |= SPDIF_SCR_RXFIFO_RST_MASK;
256 }
257 
258 /*!
259  * @brief Resets the SPDIF Rx.
260  *
261  * This function enables the software reset and FIFO reset of SPDIF Rx. After reset, clear the reset bit.
262  *
263  * @param base SPDIF base pointer
264  */
SPDIF_RxFIFOReset(SPDIF_Type * base)265 static inline void SPDIF_RxFIFOReset(SPDIF_Type *base)
266 {
267     base->SCR |= SPDIF_SCR_RXFIFO_RST_MASK;
268 }
269 
270 /*!
271  * @brief Enables/disables the SPDIF Tx.
272  *
273  * @param base SPDIF base pointer
274  * @param enable True means enable SPDIF Tx, false means disable.
275  */
276 void SPDIF_TxEnable(SPDIF_Type *base, bool enable);
277 
278 /*!
279  * @brief Enables/disables the SPDIF Rx.
280  *
281  * @param base SPDIF base pointer
282  * @param enable True means enable SPDIF Rx, false means disable.
283  */
SPDIF_RxEnable(SPDIF_Type * base,bool enable)284 static inline void SPDIF_RxEnable(SPDIF_Type *base, bool enable)
285 {
286     if (enable)
287     {
288         /* Open Rx FIFO */
289         base->SCR &= ~(SPDIF_SCR_RXFIFO_CTRL_MASK | SPDIF_SCR_RXFIFO_OFF_ON_MASK);
290     }
291     else
292     {
293         base->SCR |= SPDIF_SCR_RXFIFO_OFF_ON_MASK;
294     }
295 }
296 
297 /*! @} */
298 
299 /*!
300  * @name Status
301  * @{
302  */
303 
304 /*!
305  * @brief Gets the SPDIF status flag state.
306  *
307  * @param base SPDIF base pointer
308  * @return SPDIF status flag value. Use the _spdif_interrupt_enable_t to get the status value needed.
309  */
SPDIF_GetStatusFlag(SPDIF_Type * base)310 static inline uint32_t SPDIF_GetStatusFlag(SPDIF_Type *base)
311 {
312     return base->SIS;
313 }
314 
315 /*!
316  * @brief Clears the SPDIF status flag state.
317  *
318  * @param base SPDIF base pointer
319  * @param mask State mask. It can be a combination of the _spdif_interrupt_enable_t member. Notice these members
320  *             cannot be included, as these flags cannot be cleared by writing 1 to these bits:
321  *        @arg kSPDIF_UChannelReceiveRegisterFull
322  *        @arg kSPDIF_QChannelReceiveRegisterFull
323  *        @arg kSPDIF_TxFIFOEmpty
324  *        @arg kSPDIF_RxFIFOFull
325  */
SPDIF_ClearStatusFlags(SPDIF_Type * base,uint32_t mask)326 static inline void SPDIF_ClearStatusFlags(SPDIF_Type *base, uint32_t mask)
327 {
328     base->SIC = mask;
329 }
330 
331 /*! @} */
332 
333 /*!
334  * @name Interrupts
335  * @{
336  */
337 
338 /*!
339  * @brief Enables the SPDIF Tx interrupt requests.
340  *
341  * @param base SPDIF base pointer
342  * @param mask interrupt source
343  *     The parameter can be a combination of the following sources if defined.
344  *     @arg kSPDIF_WordStartInterruptEnable
345  *     @arg kSPDIF_SyncErrorInterruptEnable
346  *     @arg kSPDIF_FIFOWarningInterruptEnable
347  *     @arg kSPDIF_FIFORequestInterruptEnable
348  *     @arg kSPDIF_FIFOErrorInterruptEnable
349  */
SPDIF_EnableInterrupts(SPDIF_Type * base,uint32_t mask)350 static inline void SPDIF_EnableInterrupts(SPDIF_Type *base, uint32_t mask)
351 {
352     base->SIE |= mask;
353 }
354 
355 /*!
356  * @brief Disables the SPDIF Tx interrupt requests.
357  *
358  * @param base SPDIF base pointer
359  * @param mask interrupt source
360  *     The parameter can be a combination of the following sources if defined.
361  *     @arg kSPDIF_WordStartInterruptEnable
362  *     @arg kSPDIF_SyncErrorInterruptEnable
363  *     @arg kSPDIF_FIFOWarningInterruptEnable
364  *     @arg kSPDIF_FIFORequestInterruptEnable
365  *     @arg kSPDIF_FIFOErrorInterruptEnable
366  */
SPDIF_DisableInterrupts(SPDIF_Type * base,uint32_t mask)367 static inline void SPDIF_DisableInterrupts(SPDIF_Type *base, uint32_t mask)
368 {
369     base->SIE &= ~mask;
370 }
371 
372 /*! @} */
373 
374 /*!
375  * @name DMA Control
376  * @{
377  */
378 
379 /*!
380  * @brief Enables/disables the SPDIF DMA requests.
381  * @param base SPDIF base pointer
382  * @param mask SPDIF DMA enable mask, The parameter can be a combination of the following sources if defined
383  *      @arg kSPDIF_RxDMAEnable
384  *      @arg kSPDIF_TxDMAEnable
385  * @param enable True means enable DMA, false means disable DMA.
386  */
SPDIF_EnableDMA(SPDIF_Type * base,uint32_t mask,bool enable)387 static inline void SPDIF_EnableDMA(SPDIF_Type *base, uint32_t mask, bool enable)
388 {
389     if (enable)
390     {
391         base->SCR |= mask;
392     }
393     else
394     {
395         base->SCR &= ~mask;
396     }
397 }
398 
399 /*!
400  * @brief  Gets the SPDIF Tx left data register address.
401  *
402  * This API is used to provide a transfer address for the SPDIF DMA transfer configuration.
403  *
404  * @param base SPDIF base pointer.
405  * @return data register address.
406  */
SPDIF_TxGetLeftDataRegisterAddress(SPDIF_Type * base)407 static inline uint32_t SPDIF_TxGetLeftDataRegisterAddress(SPDIF_Type *base)
408 {
409     return (uint32_t)(&(base->STL));
410 }
411 
412 /*!
413  * @brief  Gets the SPDIF Tx right data register address.
414  *
415  * This API is used to provide a transfer address for the SPDIF DMA transfer configuration.
416  *
417  * @param base SPDIF base pointer.
418  * @return data register address.
419  */
SPDIF_TxGetRightDataRegisterAddress(SPDIF_Type * base)420 static inline uint32_t SPDIF_TxGetRightDataRegisterAddress(SPDIF_Type *base)
421 {
422     return (uint32_t)(&(base->STR));
423 }
424 
425 /*!
426  * @brief  Gets the SPDIF Rx left data register address.
427  *
428  * This API is used to provide a transfer address for the SPDIF DMA transfer configuration.
429  *
430  * @param base SPDIF base pointer.
431  * @return data register address.
432  */
SPDIF_RxGetLeftDataRegisterAddress(SPDIF_Type * base)433 static inline uint32_t SPDIF_RxGetLeftDataRegisterAddress(SPDIF_Type *base)
434 {
435     return (uint32_t)(&(base->SRL));
436 }
437 
438 /*!
439  * @brief  Gets the SPDIF Rx right data register address.
440  *
441  * This API is used to provide a transfer address for the SPDIF DMA transfer configuration.
442  *
443  * @param base SPDIF base pointer.
444  * @return data register address.
445  */
SPDIF_RxGetRightDataRegisterAddress(SPDIF_Type * base)446 static inline uint32_t SPDIF_RxGetRightDataRegisterAddress(SPDIF_Type *base)
447 {
448     return (uint32_t)(&(base->SRR));
449 }
450 
451 /*! @} */
452 
453 /*!
454  * @name Bus Operations
455  * @{
456  */
457 
458 /*!
459  * @brief Configures the SPDIF Tx sample rate.
460  *
461  * The audio format can be changed at run-time. This function configures the sample rate.
462  *
463  * @param base SPDIF base pointer.
464  * @param sampleRate_Hz SPDIF sample rate frequency in Hz.
465  * @param sourceClockFreq_Hz SPDIF tx clock source frequency in Hz.
466  */
467 void SPDIF_TxSetSampleRate(SPDIF_Type *base, uint32_t sampleRate_Hz, uint32_t sourceClockFreq_Hz);
468 
469 /*!
470  * @brief Configures the SPDIF Rx audio format.
471  *
472  * The audio format can be changed at run-time. This function configures the sample rate and audio data
473  * format to be transferred.
474  *
475  * @param base SPDIF base pointer.
476  * @param clockSourceFreq_Hz SPDIF system clock frequency in hz.
477  */
478 uint32_t SPDIF_GetRxSampleRate(SPDIF_Type *base, uint32_t clockSourceFreq_Hz);
479 
480 /*!
481  * @brief Sends data using a blocking method.
482  *
483  * @note This function blocks by polling until data is ready to be sent.
484  *
485  * @param base SPDIF base pointer.
486  * @param buffer Pointer to the data to be written.
487  * @param size Bytes to be written.
488  */
489 void SPDIF_WriteBlocking(SPDIF_Type *base, uint8_t *buffer, uint32_t size);
490 
491 /*!
492  * @brief Writes data into SPDIF FIFO.
493  *
494  * @param base SPDIF base pointer.
495  * @param data Data needs to be written.
496  */
SPDIF_WriteLeftData(SPDIF_Type * base,uint32_t data)497 static inline void SPDIF_WriteLeftData(SPDIF_Type *base, uint32_t data)
498 {
499     base->STL = data;
500 }
501 
502 /*!
503  * @brief Writes data into SPDIF FIFO.
504  *
505  * @param base SPDIF base pointer.
506  * @param data Data needs to be written.
507  */
SPDIF_WriteRightData(SPDIF_Type * base,uint32_t data)508 static inline void SPDIF_WriteRightData(SPDIF_Type *base, uint32_t data)
509 {
510     base->STR = data;
511 }
512 
513 /*!
514  * @brief Writes data into SPDIF FIFO.
515  *
516  * @param base SPDIF base pointer.
517  * @param data Data needs to be written.
518  */
SPDIF_WriteChannelStatusHigh(SPDIF_Type * base,uint32_t data)519 static inline void SPDIF_WriteChannelStatusHigh(SPDIF_Type *base, uint32_t data)
520 {
521     base->STCSCH = data;
522 }
523 
524 /*!
525  * @brief Writes data into SPDIF FIFO.
526  *
527  * @param base SPDIF base pointer.
528  * @param data Data needs to be written.
529  */
SPDIF_WriteChannelStatusLow(SPDIF_Type * base,uint32_t data)530 static inline void SPDIF_WriteChannelStatusLow(SPDIF_Type *base, uint32_t data)
531 {
532     base->STCSCL = data;
533 }
534 
535 /*!
536  * @brief Receives data using a blocking method.
537  *
538  * @note This function blocks by polling until data is ready to be sent.
539  *
540  * @param base SPDIF base pointer.
541  * @param buffer Pointer to the data to be read.
542  * @param size Bytes to be read.
543  */
544 void SPDIF_ReadBlocking(SPDIF_Type *base, uint8_t *buffer, uint32_t size);
545 
546 /*!
547  * @brief Reads data from the SPDIF FIFO.
548  *
549  * @param base SPDIF base pointer.
550  * @return Data in SPDIF FIFO.
551  */
SPDIF_ReadLeftData(SPDIF_Type * base)552 static inline uint32_t SPDIF_ReadLeftData(SPDIF_Type *base)
553 {
554     return base->SRL;
555 }
556 
557 /*!
558  * @brief Reads data from the SPDIF FIFO.
559  *
560  * @param base SPDIF base pointer.
561  * @return Data in SPDIF FIFO.
562  */
SPDIF_ReadRightData(SPDIF_Type * base)563 static inline uint32_t SPDIF_ReadRightData(SPDIF_Type *base)
564 {
565     return base->SRR;
566 }
567 
568 /*!
569  * @brief Reads data from the SPDIF FIFO.
570  *
571  * @param base SPDIF base pointer.
572  * @return Data in SPDIF FIFO.
573  */
SPDIF_ReadChannelStatusHigh(SPDIF_Type * base)574 static inline uint32_t SPDIF_ReadChannelStatusHigh(SPDIF_Type *base)
575 {
576     return base->SRCSH;
577 }
578 
579 /*!
580  * @brief Reads data from the SPDIF FIFO.
581  *
582  * @param base SPDIF base pointer.
583  * @return Data in SPDIF FIFO.
584  */
SPDIF_ReadChannelStatusLow(SPDIF_Type * base)585 static inline uint32_t SPDIF_ReadChannelStatusLow(SPDIF_Type *base)
586 {
587     return base->SRCSL;
588 }
589 
590 /*!
591  * @brief Reads data from the SPDIF FIFO.
592  *
593  * @param base SPDIF base pointer.
594  * @return Data in SPDIF FIFO.
595  */
SPDIF_ReadQChannel(SPDIF_Type * base)596 static inline uint32_t SPDIF_ReadQChannel(SPDIF_Type *base)
597 {
598     return base->SRQ;
599 }
600 
601 /*!
602  * @brief Reads data from the SPDIF FIFO.
603  *
604  * @param base SPDIF base pointer.
605  * @return Data in SPDIF FIFO.
606  */
SPDIF_ReadUChannel(SPDIF_Type * base)607 static inline uint32_t SPDIF_ReadUChannel(SPDIF_Type *base)
608 {
609     return base->SRU;
610 }
611 
612 /*! @} */
613 
614 /*!
615  * @name Transactional
616  * @{
617  */
618 
619 /*!
620  * @brief Initializes the SPDIF Tx handle.
621  *
622  * This function initializes the Tx handle for the SPDIF Tx transactional APIs. Call
623  * this function once to get the handle initialized.
624  *
625  * @param base SPDIF base pointer
626  * @param handle SPDIF handle pointer.
627  * @param callback Pointer to the user callback function.
628  * @param userData User parameter passed to the callback function
629  */
630 void SPDIF_TransferTxCreateHandle(SPDIF_Type *base,
631                                   spdif_handle_t *handle,
632                                   spdif_transfer_callback_t callback,
633                                   void *userData);
634 
635 /*!
636  * @brief Initializes the SPDIF Rx handle.
637  *
638  * This function initializes the Rx handle for the SPDIF Rx transactional APIs. Call
639  * this function once to get the handle initialized.
640  *
641  * @param base SPDIF base pointer.
642  * @param handle SPDIF handle pointer.
643  * @param callback Pointer to the user callback function.
644  * @param userData User parameter passed to the callback function.
645  */
646 void SPDIF_TransferRxCreateHandle(SPDIF_Type *base,
647                                   spdif_handle_t *handle,
648                                   spdif_transfer_callback_t callback,
649                                   void *userData);
650 
651 /*!
652  * @brief Performs an interrupt non-blocking send transfer on SPDIF.
653  *
654  * @note This API returns immediately after the transfer initiates.
655  * Call the SPDIF_TxGetTransferStatusIRQ to poll the transfer status and check whether
656  * the transfer is finished. If the return status is not kStatus_SPDIF_Busy, the transfer
657  * is finished.
658  *
659  * @param base SPDIF base pointer.
660  * @param handle Pointer to the spdif_handle_t structure which stores the transfer state.
661  * @param xfer Pointer to the spdif_transfer_t structure.
662  * @retval kStatus_Success Successfully started the data receive.
663  * @retval kStatus_SPDIF_TxBusy Previous receive still not finished.
664  * @retval kStatus_InvalidArgument The input parameter is invalid.
665  */
666 status_t SPDIF_TransferSendNonBlocking(SPDIF_Type *base, spdif_handle_t *handle, spdif_transfer_t *xfer);
667 
668 /*!
669  * @brief Performs an interrupt non-blocking receive transfer on SPDIF.
670  *
671  * @note This API returns immediately after the transfer initiates.
672  * Call the SPDIF_RxGetTransferStatusIRQ to poll the transfer status and check whether
673  * the transfer is finished. If the return status is not kStatus_SPDIF_Busy, the transfer
674  * is finished.
675  *
676  * @param base SPDIF base pointer
677  * @param handle Pointer to the spdif_handle_t structure which stores the transfer state.
678  * @param xfer Pointer to the spdif_transfer_t structure.
679  * @retval kStatus_Success Successfully started the data receive.
680  * @retval kStatus_SPDIF_RxBusy Previous receive still not finished.
681  * @retval kStatus_InvalidArgument The input parameter is invalid.
682  */
683 status_t SPDIF_TransferReceiveNonBlocking(SPDIF_Type *base, spdif_handle_t *handle, spdif_transfer_t *xfer);
684 
685 /*!
686  * @brief Gets a set byte count.
687  *
688  * @param base SPDIF base pointer.
689  * @param handle Pointer to the spdif_handle_t structure which stores the transfer state.
690  * @param count Bytes count sent.
691  * @retval kStatus_Success Succeed get the transfer count.
692  * @retval kStatus_NoTransferInProgress There is not a non-blocking transaction currently in progress.
693  */
694 status_t SPDIF_TransferGetSendCount(SPDIF_Type *base, spdif_handle_t *handle, size_t *count);
695 
696 /*!
697  * @brief Gets a received byte count.
698  *
699  * @param base SPDIF base pointer.
700  * @param handle Pointer to the spdif_handle_t structure which stores the transfer state.
701  * @param count Bytes count received.
702  * @retval kStatus_Success Succeed get the transfer count.
703  * @retval kStatus_NoTransferInProgress There is not a non-blocking transaction currently in progress.
704  */
705 status_t SPDIF_TransferGetReceiveCount(SPDIF_Type *base, spdif_handle_t *handle, size_t *count);
706 
707 /*!
708  * @brief Aborts the current send.
709  *
710  * @note This API can be called any time when an interrupt non-blocking transfer initiates
711  * to abort the transfer early.
712  *
713  * @param base SPDIF base pointer.
714  * @param handle Pointer to the spdif_handle_t structure which stores the transfer state.
715  */
716 void SPDIF_TransferAbortSend(SPDIF_Type *base, spdif_handle_t *handle);
717 
718 /*!
719  * @brief Aborts the current IRQ receive.
720  *
721  * @note This API can be called when an interrupt non-blocking transfer initiates
722  * to abort the transfer early.
723  *
724  * @param base SPDIF base pointer
725  * @param handle Pointer to the spdif_handle_t structure which stores the transfer state.
726  */
727 void SPDIF_TransferAbortReceive(SPDIF_Type *base, spdif_handle_t *handle);
728 
729 /*!
730  * @brief Tx interrupt handler.
731  *
732  * @param base SPDIF base pointer.
733  * @param handle Pointer to the spdif_handle_t structure.
734  */
735 void SPDIF_TransferTxHandleIRQ(SPDIF_Type *base, spdif_handle_t *handle);
736 
737 /*!
738  * @brief Tx interrupt handler.
739  *
740  * @param base SPDIF base pointer.
741  * @param handle Pointer to the spdif_handle_t structure.
742  */
743 void SPDIF_TransferRxHandleIRQ(SPDIF_Type *base, spdif_handle_t *handle);
744 
745 /*! @} */
746 
747 #if defined(__cplusplus)
748 }
749 #endif /*_cplusplus*/
750 
751 /*! @} */
752 
753 #endif /* FSL_SPDIF_H_ */
754