1 /*
2  * Copyright (c) 2021 - 2023, Nordic Semiconductor ASA
3  * All rights reserved.
4  *
5  * SPDX-License-Identifier: BSD-3-Clause
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions are met:
9  *
10  * 1. Redistributions of source code must retain the above copyright notice, this
11  *    list of conditions and the following disclaimer.
12  *
13  * 2. Redistributions in binary form must reproduce the above copyright
14  *    notice, this list of conditions and the following disclaimer in the
15  *    documentation and/or other materials provided with the distribution.
16  *
17  * 3. Neither the name of the copyright holder nor the names of its
18  *    contributors may be used to endorse or promote products derived from this
19  *    software without specific prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
22  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
25  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
26  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
27  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
28  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
29  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
30  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
31  * POSSIBILITY OF SUCH DAMAGE.
32  */
33 
34 #ifndef NRFY_I2S_H__
35 #define NRFY_I2S_H__
36 
37 #include <nrfx.h>
38 #include <hal/nrf_i2s.h>
39 
40 #ifdef __cplusplus
41 extern "C" {
42 #endif
43 
44 typedef struct nrfy_i2s_xfer_desc_t nrfy_i2s_xfer_desc_t;
45 
46 NRFY_STATIC_INLINE bool __nrfy_internal_i2s_event_handle(NRF_I2S_Type *  p_reg,
47                                                          uint32_t        mask,
48                                                          nrf_i2s_event_t event,
49                                                          uint32_t *      p_evt_mask);
50 
51 NRFY_STATIC_INLINE uint32_t __nrfy_internal_i2s_events_process(NRF_I2S_Type *               p_reg,
52                                                                uint32_t                     mask,
53                                                                nrfy_i2s_xfer_desc_t const * p_xfer);
54 
55 NRFY_STATIC_INLINE void __nrfy_internal_i2s_event_enabled_clear(NRF_I2S_Type *  p_reg,
56                                                                 uint32_t        mask,
57                                                                 nrf_i2s_event_t event);
58 
59 
60 /**
61  * @defgroup nrfy_i2s I2S HALY
62  * @{
63  * @ingroup nrf_i2s
64  * @brief   Hardware access layer with cache and barrier support for managing the I2S peripheral.
65  */
66 
67 /** @brief Structure for I2S configuration. */
68 typedef struct
69 {
70     nrf_i2s_config_t config;        ///< Peripheral configuration.
71     nrf_i2s_pins_t   pins;          ///< Pins to be used.
72 #if NRF_I2S_HAS_CLKCONFIG
73     nrf_i2s_clksrc_t clksrc;        ///< Clock source selection.
74     bool             enable_bypass; ///< Bypass clock generator. MCK will be equal to source input.
75 #endif
76     bool             skip_psel_cfg; ///< Skip pin selection configuration.
77                                     /**< When set to true, the driver does not modify
78                                      *   pin select registers in the peripheral.
79                                      *   Those registers are supposed to be set up
80                                      *   externally before the driver is initialized.
81                                      *   @note When both GPIO configuration and pin
82                                      *   selection are to be skipped, the structure
83                                      *   fields that specify pins can be omitted,
84                                      *   as they are ignored anyway. */
85 } nrfy_i2s_config_t;
86 
87 #if !NRFX_API_VER_AT_LEAST(3, 3, 0)
88 /** @brief I2S driver buffers structure. */
89 typedef struct
90 {
91     uint32_t       * p_rx_buffer; ///< Pointer to the buffer for received data.
92     uint32_t const * p_tx_buffer; ///< Pointer to the buffer with data to be sent.
93 } nrfy_i2s_buffers_t;
94 #endif
95 
96 /** @brief Structure describing single I2S transfer. */
97 struct nrfy_i2s_xfer_desc_t
98 {
99     uint32_t       * p_rx_buffer; ///< Pointer to the buffer for received data.
100     uint32_t const * p_tx_buffer; ///< Pointer to the buffer with data to be sent.
101     uint16_t         buffer_size; ///< Size of buffers.
102 };
103 
104 /**
105  * @brief Function for configuring the I2S.
106  *
107  * @param[in] p_reg    Pointer to the structure of registers of the peripheral.
108  * @param[in] p_config Pointer to the peripheral configuration structure.
109  */
nrfy_i2s_periph_configure(NRF_I2S_Type * p_reg,nrfy_i2s_config_t const * p_config)110 NRFY_STATIC_INLINE void nrfy_i2s_periph_configure(NRF_I2S_Type *            p_reg,
111                                                   nrfy_i2s_config_t const * p_config)
112 {
113     nrf_i2s_configure(p_reg, &p_config->config);
114 
115 #if NRF_I2S_HAS_CLKCONFIG
116     nrf_i2s_clk_configure(p_reg, p_config->clksrc, p_config->enable_bypass);
117 #endif
118     if (!p_config->skip_psel_cfg)
119     {
120         nrf_i2s_pins_set(p_reg, &p_config->pins);
121     }
122     nrf_barrier_w();
123 }
124 
125 /**
126  * @brief Function for initializing the specified I2S interrupts.
127  *
128  * @param[in] p_reg        Pointer to the structure of registers of the peripheral.
129  * @param[in] mask         Mask of interrupts to be initialized.
130  * @param[in] irq_priority Interrupt priority.
131  * @param[in] enable       True if interrupts are to be enabled, false otherwise.
132  */
nrfy_i2s_int_init(NRF_I2S_Type * p_reg,uint32_t mask,uint8_t irq_priority,bool enable)133 NRFY_STATIC_INLINE void nrfy_i2s_int_init(NRF_I2S_Type * p_reg,
134                                           uint32_t       mask,
135                                           uint8_t        irq_priority,
136                                           bool           enable)
137 {
138     __nrfy_internal_i2s_event_enabled_clear(p_reg, mask, NRF_I2S_EVENT_RXPTRUPD);
139     __nrfy_internal_i2s_event_enabled_clear(p_reg, mask, NRF_I2S_EVENT_TXPTRUPD);
140     __nrfy_internal_i2s_event_enabled_clear(p_reg, mask, NRF_I2S_EVENT_STOPPED);
141 #if NRF_I2S_HAS_FRAMESTART
142     __nrfy_internal_i2s_event_enabled_clear(p_reg, mask, NRF_I2S_EVENT_FRAMESTART);
143 #endif
144     nrf_barrier_w();
145 
146     NRFX_IRQ_PRIORITY_SET(nrfx_get_irq_number(p_reg), irq_priority);
147     NRFX_IRQ_ENABLE(nrfx_get_irq_number(p_reg));
148 
149     if (enable)
150     {
151         nrf_i2s_int_enable(p_reg, mask);
152     }
153     nrf_barrier_w();
154 }
155 
156 /**
157  * @brief Function for uninitializing the I2S interrupts.
158  *
159  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
160  */
nrfy_i2s_int_uninit(NRF_I2S_Type * p_reg)161 NRFY_STATIC_INLINE void nrfy_i2s_int_uninit(NRF_I2S_Type * p_reg)
162 {
163     NRFX_IRQ_DISABLE(nrfx_get_irq_number(p_reg));
164     nrf_barrier_w();
165 }
166 
167 /**
168  * @brief Function for processing the specified I2S events.
169  *
170  * @param[in] p_reg  Pointer to the structure of registers of the peripheral.
171  * @param[in] mask   Mask of events to be processed,
172  *                   created by @ref NRFY_EVENT_TO_INT_BITMASK().
173  * @param[in] p_xfer Pointer to the structure containing buffers associated with the last transaction.
174  *                   Can be NULL.
175  *
176  * @return Mask of events that were generated and processed.
177  *         To be checked against the result of @ref NRFY_EVENT_TO_INT_BITMASK().
178  */
nrfy_i2s_events_process(NRF_I2S_Type * p_reg,uint32_t mask,nrfy_i2s_xfer_desc_t * p_xfer)179 NRFY_STATIC_INLINE uint32_t nrfy_i2s_events_process(NRF_I2S_Type *         p_reg,
180                                                     uint32_t               mask,
181                                                     nrfy_i2s_xfer_desc_t * p_xfer)
182 {
183     uint32_t evt_mask = __nrfy_internal_i2s_events_process(p_reg, mask, p_xfer);
184     nrf_barrier_w();
185     return evt_mask;
186 }
187 
188 /**
189  * @brief Function for setting the I2S transaction buffers.
190  *
191  * If the transfer in a given direction is not required, pass NULL instead of the pointer
192  * to the corresponding buffer.
193  *
194  * @param[in] p_reg  Pointer to the structure of registers of the peripheral.
195  * @param[in] p_xfer Pointer to the structure containing transaction buffers.
196  */
nrfy_i2s_buffers_set(NRF_I2S_Type * p_reg,nrfy_i2s_xfer_desc_t const * p_xfer)197 NRFY_STATIC_INLINE void nrfy_i2s_buffers_set(NRF_I2S_Type *               p_reg,
198                                              nrfy_i2s_xfer_desc_t const * p_xfer)
199 {
200     if (p_xfer->p_tx_buffer != NULL)
201     {
202         NRFY_CACHE_WB(p_xfer->p_tx_buffer, (p_xfer->buffer_size * sizeof(uint32_t)));
203     }
204 
205     nrf_i2s_transfer_set(p_reg,
206                          p_xfer->buffer_size,
207                          p_xfer->p_rx_buffer,
208                          p_xfer->p_tx_buffer);
209 
210     nrf_barrier_w();
211 }
212 
213 /**
214  * @brief Function for starting the I2S transaction.
215  *
216  * If the transfer in a given direction is not required, pass NULL instead of the pointer
217  * to the corresponding buffer.
218  *
219  * @param[in] p_reg  Pointer to the structure of registers of the peripheral.
220  * @param[in] p_xfer Pointer to the structure containing transaction buffers
221  *                   if the transaction is to be blocking. NULL for non-blocking transactions.
222  */
nrfy_i2s_xfer_start(NRF_I2S_Type * p_reg,nrfy_i2s_xfer_desc_t const * p_xfer)223 NRFY_STATIC_INLINE void nrfy_i2s_xfer_start(NRF_I2S_Type *               p_reg,
224                                             nrfy_i2s_xfer_desc_t const * p_xfer)
225 {
226 
227     nrf_i2s_task_trigger(p_reg, NRF_I2S_TASK_START);
228 
229     if (p_xfer)
230     {
231         nrf_barrier_w();
232 
233         bool tx_done = false, rx_done = false;
234 
235         while (!((tx_done || (p_xfer->p_tx_buffer == NULL)) &&
236                  (rx_done || (p_xfer->p_rx_buffer == NULL))))
237         {
238             if (__nrfy_internal_i2s_events_process(p_reg,
239                     NRFY_EVENT_TO_INT_BITMASK(NRF_I2S_EVENT_TXPTRUPD),
240                     p_xfer))
241             {
242                 tx_done = true;
243             }
244             if (__nrfy_internal_i2s_events_process(p_reg,
245                     NRFY_EVENT_TO_INT_BITMASK(NRF_I2S_EVENT_RXPTRUPD),
246                     p_xfer))
247             {
248                 rx_done = true;
249             }
250         }
251     }
252 
253     nrf_barrier_w();
254 }
255 
256 /**
257  * @brief Function for aborting the ongoing I2S transaction.
258  *
259  * @param[in] p_reg  Pointer to the structure of registers of the peripheral.
260  * @param[in] p_xfer Pointer to the structure containing transaction buffers
261  *                   if the abort is to be blocking. NULL for non-blocking operation.
262  */
nrfy_i2s_abort(NRF_I2S_Type * p_reg,nrfy_i2s_xfer_desc_t const * p_xfer)263 NRFY_STATIC_INLINE void nrfy_i2s_abort(NRF_I2S_Type * p_reg, nrfy_i2s_xfer_desc_t const * p_xfer)
264 {
265     nrf_i2s_task_trigger(p_reg, NRF_I2S_TASK_STOP);
266     if (p_xfer)
267     {
268         nrf_barrier_w();
269         uint32_t evt_mask = NRFY_EVENT_TO_INT_BITMASK(NRF_I2S_EVENT_STOPPED);
270         while (!__nrfy_internal_i2s_events_process(p_reg, evt_mask, p_xfer))
271         {}
272     }
273     nrf_barrier_w();
274 }
275 
276 /**
277  * @brief Function for getting the pins selection.
278  *
279  * @param[in] p_reg  Pointer to the structure of registers of the peripheral.
280  * @param[in] p_pins Pointer to the I2S pin configuration structure.
281  *
282  */
nrfy_i2s_pins_get(NRF_I2S_Type const * p_reg,nrf_i2s_pins_t * p_pins)283 NRFY_STATIC_INLINE void nrfy_i2s_pins_get(NRF_I2S_Type const * p_reg,
284                                           nrf_i2s_pins_t *     p_pins)
285 {
286     nrf_barrier_rw();
287 
288     p_pins->sck_pin   = nrf_i2s_sck_pin_get(p_reg),
289     p_pins->lrck_pin  = nrf_i2s_lrck_pin_get(p_reg),
290     p_pins->mck_pin   = nrf_i2s_mck_pin_get(p_reg),
291     p_pins->sdout_pin = nrf_i2s_sdout_pin_get(p_reg),
292     p_pins->sdin_pin  = nrf_i2s_sdin_pin_get(p_reg),
293 
294     nrf_barrier_r();
295 }
296 
297 /** @refhal{nrf_i2s_task_trigger} */
nrfy_i2s_task_trigger(NRF_I2S_Type * p_reg,nrf_i2s_task_t task)298 NRFY_STATIC_INLINE void nrfy_i2s_task_trigger(NRF_I2S_Type * p_reg, nrf_i2s_task_t task)
299 {
300     nrf_i2s_task_trigger(p_reg, task);
301     nrf_barrier_w();
302 }
303 
304 /** @refhal{nrf_i2s_task_address_get} */
nrfy_i2s_task_address_get(NRF_I2S_Type const * p_reg,nrf_i2s_task_t task)305 NRFY_STATIC_INLINE uint32_t nrfy_i2s_task_address_get(NRF_I2S_Type const * p_reg,
306                                                       nrf_i2s_task_t       task)
307 {
308     return nrf_i2s_task_address_get(p_reg, task);
309 }
310 
311 /** @refhal{nrf_i2s_event_clear} */
nrfy_i2s_event_clear(NRF_I2S_Type * p_reg,nrf_i2s_event_t event)312 NRFY_STATIC_INLINE void nrfy_i2s_event_clear(NRF_I2S_Type *  p_reg,
313                                              nrf_i2s_event_t event)
314 {
315     nrf_i2s_event_clear(p_reg, event);
316     nrf_barrier_w();
317 }
318 
319 /** @refhal{nrf_i2s_event_check} */
nrfy_i2s_event_check(NRF_I2S_Type const * p_reg,nrf_i2s_event_t event)320 NRFY_STATIC_INLINE bool nrfy_i2s_event_check(NRF_I2S_Type const * p_reg,
321                                              nrf_i2s_event_t      event)
322 {
323     nrf_barrier_r();
324     bool check = nrf_i2s_event_check(p_reg, event);
325     nrf_barrier_r();
326     return check;
327 }
328 
329 /** @refhal{nrf_i2s_event_address_get} */
nrfy_i2s_event_address_get(NRF_I2S_Type const * p_reg,nrf_i2s_event_t event)330 NRFY_STATIC_INLINE uint32_t nrfy_i2s_event_address_get(NRF_I2S_Type const * p_reg,
331                                                        nrf_i2s_event_t      event)
332 {
333     return nrf_i2s_event_address_get(p_reg, event);
334 }
335 
336 /** @refhal{nrf_i2s_int_enable} */
nrfy_i2s_int_enable(NRF_I2S_Type * p_reg,uint32_t mask)337 NRFY_STATIC_INLINE void nrfy_i2s_int_enable(NRF_I2S_Type * p_reg, uint32_t mask)
338 {
339     nrf_i2s_int_enable(p_reg, mask);
340     nrf_barrier_w();
341 }
342 
343 /** @refhal{nrf_i2s_int_disable} */
nrfy_i2s_int_disable(NRF_I2S_Type * p_reg,uint32_t mask)344 NRFY_STATIC_INLINE void nrfy_i2s_int_disable(NRF_I2S_Type * p_reg, uint32_t mask)
345 {
346     nrf_i2s_int_disable(p_reg, mask);
347     nrf_barrier_w();
348 }
349 
350 /** @refhal{nrf_i2s_int_enable_check} */
nrfy_i2s_int_enable_check(NRF_I2S_Type const * p_reg,uint32_t mask)351 NRFY_STATIC_INLINE uint32_t nrfy_i2s_int_enable_check(NRF_I2S_Type const * p_reg, uint32_t mask)
352 {
353     nrf_barrier_rw();
354     uint32_t check = nrf_i2s_int_enable_check(p_reg, mask);
355     nrf_barrier_r();
356     return check;
357 }
358 
359 /** @refhal{nrf_i2s_enable} */
nrfy_i2s_enable(NRF_I2S_Type * p_reg)360 NRFY_STATIC_INLINE void nrfy_i2s_enable(NRF_I2S_Type * p_reg)
361 {
362     nrf_i2s_enable(p_reg);
363     nrf_barrier_w();
364 }
365 
366 /** @refhal{nrf_i2s_disable} */
nrfy_i2s_disable(NRF_I2S_Type * p_reg)367 NRFY_STATIC_INLINE void nrfy_i2s_disable(NRF_I2S_Type * p_reg)
368 {
369     nrf_i2s_disable(p_reg);
370     nrf_barrier_w();
371 }
372 
373 #if defined(DPPI_PRESENT) || defined(__NRFX_DOXYGEN__)
374 /** @refhal{nrf_i2s_subscribe_set} */
nrfy_i2s_subscribe_set(NRF_I2S_Type * p_reg,nrf_i2s_task_t task,uint8_t channel)375 NRFY_STATIC_INLINE void nrfy_i2s_subscribe_set(NRF_I2S_Type * p_reg,
376                                                nrf_i2s_task_t task,
377                                                uint8_t        channel)
378 {
379     nrf_i2s_subscribe_set(p_reg, task, channel);
380     nrf_barrier_w();
381 }
382 
383 /** @refhal{nrf_i2s_subscribe_clear} */
nrfy_i2s_subscribe_clear(NRF_I2S_Type * p_reg,nrf_i2s_task_t task)384 NRFY_STATIC_INLINE void nrfy_i2s_subscribe_clear(NRF_I2S_Type * p_reg,
385                                                  nrf_i2s_task_t task)
386 {
387     nrf_i2s_subscribe_clear(p_reg, task);
388     nrf_barrier_w();
389 }
390 
391 /** @refhal{nrf_i2s_publish_set} */
nrfy_i2s_publish_set(NRF_I2S_Type * p_reg,nrf_i2s_event_t event,uint8_t channel)392 NRFY_STATIC_INLINE void nrfy_i2s_publish_set(NRF_I2S_Type *  p_reg,
393                                              nrf_i2s_event_t event,
394                                              uint8_t         channel)
395 {
396     nrf_i2s_publish_set(p_reg, event, channel);
397     nrf_barrier_w();
398 }
399 
400 /** @refhal{nrf_i2s_publish_clear} */
nrfy_i2s_publish_clear(NRF_I2S_Type * p_reg,nrf_i2s_event_t event)401 NRFY_STATIC_INLINE void nrfy_i2s_publish_clear(NRF_I2S_Type *  p_reg,
402                                                nrf_i2s_event_t event)
403 {
404     nrf_i2s_publish_clear(p_reg, event);
405     nrf_barrier_w();
406 }
407 #endif
408 
409 /** @refhal{nrf_i2s_pins_set} */
nrfy_i2s_pins_set(NRF_I2S_Type * p_reg,nrf_i2s_pins_t const * p_pins)410 NRFY_STATIC_INLINE void nrfy_i2s_pins_set(NRF_I2S_Type * p_reg, nrf_i2s_pins_t const * p_pins)
411 {
412     nrf_i2s_pins_set(p_reg, p_pins);
413     nrf_barrier_w();
414 }
415 
416 /** @refhal{nrf_i2s_sck_pin_get} */
nrfy_i2s_sck_pin_get(NRF_I2S_Type const * p_reg)417 NRFY_STATIC_INLINE uint32_t nrfy_i2s_sck_pin_get(NRF_I2S_Type const * p_reg)
418 {
419     nrf_barrier_rw();
420     uint32_t pin = nrf_i2s_sck_pin_get(p_reg);
421     nrf_barrier_r();
422     return pin;
423 }
424 
425 /** @refhal{nrf_i2s_lrck_pin_get} */
nrfy_i2s_lrck_pin_get(NRF_I2S_Type const * p_reg)426 NRFY_STATIC_INLINE uint32_t nrfy_i2s_lrck_pin_get(NRF_I2S_Type const * p_reg)
427 {
428     nrf_barrier_rw();
429     uint32_t pin = nrf_i2s_lrck_pin_get(p_reg);
430     nrf_barrier_r();
431     return pin;
432 }
433 
434 /** @refhal{nrf_i2s_mck_pin_get} */
nrfy_i2s_mck_pin_get(NRF_I2S_Type const * p_reg)435 NRFY_STATIC_INLINE uint32_t nrfy_i2s_mck_pin_get(NRF_I2S_Type const * p_reg)
436 {
437     nrf_barrier_rw();
438     uint32_t pin = nrf_i2s_mck_pin_get(p_reg);
439     nrf_barrier_r();
440     return pin;
441 }
442 
443 /** @refhal{nrf_i2s_sdout_pin_get} */
nrfy_i2s_sdout_pin_get(NRF_I2S_Type const * p_reg)444 NRFY_STATIC_INLINE uint32_t nrfy_i2s_sdout_pin_get(NRF_I2S_Type const * p_reg)
445 {
446     nrf_barrier_rw();
447     uint32_t pin = nrf_i2s_sdout_pin_get(p_reg);
448     nrf_barrier_r();
449     return pin;
450 }
451 
452 /** @refhal{nrf_i2s_sdin_pin_get} */
nrfy_i2s_sdin_pin_get(NRF_I2S_Type const * p_reg)453 NRFY_STATIC_INLINE uint32_t nrfy_i2s_sdin_pin_get(NRF_I2S_Type const * p_reg)
454 {
455     nrf_barrier_rw();
456     uint32_t pin = nrf_i2s_sdin_pin_get(p_reg);
457     nrf_barrier_r();
458     return pin;
459 }
460 
461 /** @refhal{nrf_i2s_configure} */
nrfy_i2s_configure(NRF_I2S_Type * p_reg,nrf_i2s_config_t const * p_config)462 NRFY_STATIC_INLINE void nrfy_i2s_configure(NRF_I2S_Type * p_reg, nrf_i2s_config_t const * p_config)
463 {
464     nrf_i2s_configure(p_reg, p_config);
465     nrf_barrier_w();
466 }
467 
468 /** @refhal{nrf_i2s_transfer_set} */
nrfy_i2s_transfer_set(NRF_I2S_Type * p_reg,uint16_t size,uint32_t * p_rx_buffer,uint32_t const * p_tx_buffer)469 NRFY_STATIC_INLINE void nrfy_i2s_transfer_set(NRF_I2S_Type *   p_reg,
470                                               uint16_t         size,
471                                               uint32_t *       p_rx_buffer,
472                                               uint32_t const * p_tx_buffer)
473 {
474     nrf_i2s_transfer_set(p_reg, size, p_rx_buffer, p_tx_buffer);
475     nrf_barrier_w();
476 }
477 
478 /** @refhal{nrf_i2s_rx_buffer_set} */
nrfy_i2s_rx_buffer_set(NRF_I2S_Type * p_reg,uint32_t * p_buffer)479 NRFY_STATIC_INLINE void nrfy_i2s_rx_buffer_set(NRF_I2S_Type * p_reg,
480                                                uint32_t *     p_buffer)
481 {
482     nrf_i2s_rx_buffer_set(p_reg, p_buffer);
483     nrf_barrier_w();
484 }
485 
486 /** @refhal{nrf_i2s_rx_buffer_get} */
nrfy_i2s_rx_buffer_get(NRF_I2S_Type const * p_reg)487 NRFY_STATIC_INLINE uint32_t * nrfy_i2s_rx_buffer_get(NRF_I2S_Type const * p_reg)
488 {
489     nrf_barrier_rw();
490     uint32_t * p_buffer = nrfy_i2s_rx_buffer_get(p_reg);
491     nrf_barrier_r();
492     return p_buffer;
493 }
494 
495 /** @refhal{nrf_i2s_tx_buffer_set} */
nrfy_i2s_tx_buffer_set(NRF_I2S_Type * p_reg,uint32_t const * p_buffer)496 NRFY_STATIC_INLINE void nrfy_i2s_tx_buffer_set(NRF_I2S_Type *   p_reg,
497                                                uint32_t const * p_buffer)
498 {
499     nrf_i2s_tx_buffer_set(p_reg, p_buffer);
500     nrf_barrier_w();
501 }
502 
503 /** @refhal{nrf_i2s_tx_buffer_get} */
nrfy_i2s_tx_buffer_get(NRF_I2S_Type const * p_reg)504 NRFY_STATIC_INLINE uint32_t * nrfy_i2s_tx_buffer_get(NRF_I2S_Type const * p_reg)
505 {
506     nrf_barrier_rw();
507     uint32_t * p_buffer = nrfy_i2s_tx_buffer_get(p_reg);
508     nrf_barrier_r();
509     return p_buffer;
510 }
511 
512 /** @} */
513 
__nrfy_internal_i2s_event_handle(NRF_I2S_Type * p_reg,uint32_t mask,nrf_i2s_event_t event,uint32_t * p_event_mask)514 NRFY_STATIC_INLINE bool __nrfy_internal_i2s_event_handle(NRF_I2S_Type *  p_reg,
515                                                          uint32_t        mask,
516                                                          nrf_i2s_event_t event,
517                                                          uint32_t *      p_event_mask)
518 {
519     if ((mask & NRFY_EVENT_TO_INT_BITMASK(event)) && nrf_i2s_event_check(p_reg, event))
520     {
521         nrf_i2s_event_clear(p_reg, event);
522         if (p_event_mask)
523         {
524             *p_event_mask |= NRFY_EVENT_TO_INT_BITMASK(event);
525         }
526         return true;
527     }
528     return false;
529 }
530 
__nrfy_internal_i2s_events_process(NRF_I2S_Type * p_reg,uint32_t mask,nrfy_i2s_xfer_desc_t const * p_xfer)531 NRFY_STATIC_INLINE uint32_t __nrfy_internal_i2s_events_process(NRF_I2S_Type *               p_reg,
532                                                                uint32_t                     mask,
533                                                                nrfy_i2s_xfer_desc_t const * p_xfer)
534 {
535     uint32_t event_mask = 0;
536     bool invalidated = false;
537 
538     nrf_barrier_r();
539 #if NRF_I2S_HAS_FRAMESTART
540     (void)__nrfy_internal_i2s_event_handle(p_reg, mask, NRF_I2S_EVENT_FRAMESTART, &event_mask);
541 #endif
542 
543     (void)__nrfy_internal_i2s_event_handle(p_reg, mask, NRF_I2S_EVENT_TXPTRUPD, &event_mask);
544 
545     if (__nrfy_internal_i2s_event_handle(p_reg, mask, NRF_I2S_EVENT_RXPTRUPD, &event_mask) &&
546         p_xfer)
547     {
548         NRFY_CACHE_INV(p_xfer->p_rx_buffer,
549                        (p_xfer->buffer_size * sizeof(uint32_t)));
550         invalidated = true;
551     }
552 
553     if (__nrfy_internal_i2s_event_handle(p_reg, mask, NRF_I2S_EVENT_STOPPED, &event_mask) &&
554         p_xfer && !invalidated)
555     {
556         NRFY_CACHE_INV(p_xfer->p_rx_buffer,
557                        (p_xfer->buffer_size * sizeof(uint32_t)));
558     }
559 
560     return event_mask;
561 }
562 
563 
__nrfy_internal_i2s_event_enabled_clear(NRF_I2S_Type * p_reg,uint32_t mask,nrf_i2s_event_t event)564 NRFY_STATIC_INLINE void __nrfy_internal_i2s_event_enabled_clear(NRF_I2S_Type *  p_reg,
565                                                                 uint32_t        mask,
566                                                                 nrf_i2s_event_t event)
567 {
568     if (mask & NRFY_EVENT_TO_INT_BITMASK(event))
569     {
570         nrf_i2s_event_clear(p_reg, event);
571     }
572 }
573 
574 #ifdef __cplusplus
575 }
576 #endif
577 
578 #endif // NRFY_I2S_H__
579