1 /* 2 * Copyright (c) 2015 - 2018, Nordic Semiconductor ASA 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions are met: 7 * 8 * 1. Redistributions of source code must retain the above copyright notice, this 9 * list of conditions and the following disclaimer. 10 * 11 * 2. Redistributions in binary form must reproduce the above copyright 12 * notice, this list of conditions and the following disclaimer in the 13 * documentation and/or other materials provided with the distribution. 14 * 15 * 3. Neither the name of the copyright holder nor the names of its 16 * contributors may be used to endorse or promote products derived from this 17 * software without specific prior written permission. 18 * 19 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 20 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 21 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 22 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE 23 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 29 * POSSIBILITY OF SUCH DAMAGE. 30 */ 31 32 #ifndef NRF_SPIM_H__ 33 #define NRF_SPIM_H__ 34 35 #include <nrfx.h> 36 37 #ifdef __cplusplus 38 extern "C" { 39 #endif 40 41 /** 42 * @defgroup nrf_spim_hal SPIM HAL 43 * @{ 44 * @ingroup nrf_spim 45 * @brief Hardware access layer for managing the SPIM peripheral. 46 */ 47 48 /** 49 * @brief This value can be used as a parameter for the @ref nrf_spim_pins_set 50 * function to specify that a given SPI signal (SCK, MOSI, or MISO) 51 * shall not be connected to a physical pin. 52 */ 53 #define NRF_SPIM_PIN_NOT_CONNECTED 0xFFFFFFFF 54 55 #if defined(SPIM_DCXCNT_DCXCNT_Msk) || defined(__NRFX_DOXYGEN__) 56 /** 57 * @brief This value specified in the DCX line configuration causes this line 58 * to be set low during whole transmission (all transmitted bytes are 59 * marked as command bytes). Any lower value causes the DCX line to be 60 * switched from low to high after this number of bytes is transmitted 61 * (all remaining bytes are marked as data bytes). 62 */ 63 #define NRF_SPIM_DCX_CNT_ALL_CMD 0xF 64 #endif 65 66 #define NRF_SPIM_HW_CSN_PRESENT \ 67 (NRFX_CHECK(SPIM0_FEATURE_HARDWARE_CSN_PRESENT) || \ 68 NRFX_CHECK(SPIM1_FEATURE_HARDWARE_CSN_PRESENT) || \ 69 NRFX_CHECK(SPIM2_FEATURE_HARDWARE_CSN_PRESENT) || \ 70 NRFX_CHECK(SPIM3_FEATURE_HARDWARE_CSN_PRESENT)) 71 72 /** 73 * @brief SPIM tasks. 74 */ 75 typedef enum 76 { 77 /*lint -save -e30*/ 78 NRF_SPIM_TASK_START = offsetof(NRF_SPIM_Type, TASKS_START), ///< Start SPI transaction. 79 NRF_SPIM_TASK_STOP = offsetof(NRF_SPIM_Type, TASKS_STOP), ///< Stop SPI transaction. 80 NRF_SPIM_TASK_SUSPEND = offsetof(NRF_SPIM_Type, TASKS_SUSPEND), ///< Suspend SPI transaction. 81 NRF_SPIM_TASK_RESUME = offsetof(NRF_SPIM_Type, TASKS_RESUME) ///< Resume SPI transaction. 82 /*lint -restore*/ 83 } nrf_spim_task_t; 84 85 /** 86 * @brief SPIM events. 87 */ 88 typedef enum 89 { 90 /*lint -save -e30*/ 91 NRF_SPIM_EVENT_STOPPED = offsetof(NRF_SPIM_Type, EVENTS_STOPPED), ///< SPI transaction has stopped. 92 NRF_SPIM_EVENT_ENDRX = offsetof(NRF_SPIM_Type, EVENTS_ENDRX), ///< End of RXD buffer reached. 93 NRF_SPIM_EVENT_END = offsetof(NRF_SPIM_Type, EVENTS_END), ///< End of RXD buffer and TXD buffer reached. 94 NRF_SPIM_EVENT_ENDTX = offsetof(NRF_SPIM_Type, EVENTS_ENDTX), ///< End of TXD buffer reached. 95 NRF_SPIM_EVENT_STARTED = offsetof(NRF_SPIM_Type, EVENTS_STARTED) ///< Transaction started. 96 /*lint -restore*/ 97 } nrf_spim_event_t; 98 99 /** 100 * @brief SPIM shortcuts. 101 */ 102 typedef enum 103 { 104 NRF_SPIM_SHORT_END_START_MASK = SPIM_SHORTS_END_START_Msk, ///< Shortcut between END event and START task. 105 NRF_SPIM_ALL_SHORTS_MASK = SPIM_SHORTS_END_START_Msk ///< All SPIM shortcuts. 106 } nrf_spim_short_mask_t; 107 108 /** 109 * @brief SPIM interrupts. 110 */ 111 typedef enum 112 { 113 NRF_SPIM_INT_STOPPED_MASK = SPIM_INTENSET_STOPPED_Msk, ///< Interrupt on STOPPED event. 114 NRF_SPIM_INT_ENDRX_MASK = SPIM_INTENSET_ENDRX_Msk, ///< Interrupt on ENDRX event. 115 NRF_SPIM_INT_END_MASK = SPIM_INTENSET_END_Msk, ///< Interrupt on END event. 116 NRF_SPIM_INT_ENDTX_MASK = SPIM_INTENSET_ENDTX_Msk, ///< Interrupt on ENDTX event. 117 NRF_SPIM_INT_STARTED_MASK = SPIM_INTENSET_STARTED_Msk, ///< Interrupt on STARTED event. 118 NRF_SPIM_ALL_INTS_MASK = SPIM_INTENSET_STOPPED_Msk | 119 SPIM_INTENSET_ENDRX_Msk | 120 SPIM_INTENSET_END_Msk | 121 SPIM_INTENSET_ENDTX_Msk | 122 SPIM_INTENSET_STARTED_Msk ///< All SPIM interrupts. 123 } nrf_spim_int_mask_t; 124 125 /** 126 * @brief SPI master data rates. 127 */ 128 typedef enum 129 { 130 NRF_SPIM_FREQ_125K = SPIM_FREQUENCY_FREQUENCY_K125, ///< 125 kbps. 131 NRF_SPIM_FREQ_250K = SPIM_FREQUENCY_FREQUENCY_K250, ///< 250 kbps. 132 NRF_SPIM_FREQ_500K = SPIM_FREQUENCY_FREQUENCY_K500, ///< 500 kbps. 133 NRF_SPIM_FREQ_1M = SPIM_FREQUENCY_FREQUENCY_M1, ///< 1 Mbps. 134 NRF_SPIM_FREQ_2M = SPIM_FREQUENCY_FREQUENCY_M2, ///< 2 Mbps. 135 NRF_SPIM_FREQ_4M = SPIM_FREQUENCY_FREQUENCY_M4, ///< 4 Mbps. 136 // [conversion to 'int' needed to prevent compilers from complaining 137 // that the provided value (0x80000000UL) is out of range of "int"] 138 NRF_SPIM_FREQ_8M = (int)SPIM_FREQUENCY_FREQUENCY_M8, ///< 8 Mbps. 139 #if defined(SPIM_FREQUENCY_FREQUENCY_M16) || defined(__NRFX_DOXYGEN__) 140 NRF_SPIM_FREQ_16M = SPIM_FREQUENCY_FREQUENCY_M16, ///< 16 Mbps. 141 #endif 142 #if defined(SPIM_FREQUENCY_FREQUENCY_M32) || defined(__NRFX_DOXYGEN__) 143 NRF_SPIM_FREQ_32M = SPIM_FREQUENCY_FREQUENCY_M32 ///< 32 Mbps. 144 #endif 145 } nrf_spim_frequency_t; 146 147 /** 148 * @brief SPI modes. 149 */ 150 typedef enum 151 { 152 NRF_SPIM_MODE_0, ///< SCK active high, sample on leading edge of clock. 153 NRF_SPIM_MODE_1, ///< SCK active high, sample on trailing edge of clock. 154 NRF_SPIM_MODE_2, ///< SCK active low, sample on leading edge of clock. 155 NRF_SPIM_MODE_3 ///< SCK active low, sample on trailing edge of clock. 156 } nrf_spim_mode_t; 157 158 /** 159 * @brief SPI bit orders. 160 */ 161 typedef enum 162 { 163 NRF_SPIM_BIT_ORDER_MSB_FIRST = SPIM_CONFIG_ORDER_MsbFirst, ///< Most significant bit shifted out first. 164 NRF_SPIM_BIT_ORDER_LSB_FIRST = SPIM_CONFIG_ORDER_LsbFirst ///< Least significant bit shifted out first. 165 } nrf_spim_bit_order_t; 166 167 #if (NRF_SPIM_HW_CSN_PRESENT) || defined(__NRFX_DOXYGEN__) 168 /** 169 * @brief SPI CSN pin polarity. 170 */ 171 typedef enum 172 { 173 NRF_SPIM_CSN_POL_LOW = SPIM_CSNPOL_CSNPOL_LOW, ///< Active low (idle state high). 174 NRF_SPIM_CSN_POL_HIGH = SPIM_CSNPOL_CSNPOL_HIGH ///< Active high (idle state low). 175 } nrf_spim_csn_pol_t; 176 #endif // (NRF_SPIM_HW_CSN_PRESENT) || defined(__NRFX_DOXYGEN__) 177 178 /** 179 * @brief Function for activating a specific SPIM task. 180 * 181 * @param[in] p_reg Pointer to the peripheral registers structure. 182 * @param[in] spim_task Task to activate. 183 */ 184 __STATIC_INLINE void nrf_spim_task_trigger(NRF_SPIM_Type * p_reg, 185 nrf_spim_task_t spim_task); 186 187 /** 188 * @brief Function for getting the address of a specific SPIM task register. 189 * 190 * @param[in] p_reg Pointer to the peripheral registers structure. 191 * @param[in] spim_task Requested task. 192 * 193 * @return Address of the specified task register. 194 */ 195 __STATIC_INLINE uint32_t nrf_spim_task_address_get(NRF_SPIM_Type * p_reg, 196 nrf_spim_task_t spim_task); 197 198 /** 199 * @brief Function for clearing a specific SPIM event. 200 * 201 * @param[in] p_reg Pointer to the peripheral registers structure. 202 * @param[in] spim_event Event to clear. 203 */ 204 __STATIC_INLINE void nrf_spim_event_clear(NRF_SPIM_Type * p_reg, 205 nrf_spim_event_t spim_event); 206 207 /** 208 * @brief Function for checking the state of a specific SPIM event. 209 * 210 * @param[in] p_reg Pointer to the peripheral registers structure. 211 * @param[in] spim_event Event to check. 212 * 213 * @retval true If the event is set. 214 * @retval false If the event is not set. 215 */ 216 __STATIC_INLINE bool nrf_spim_event_check(NRF_SPIM_Type * p_reg, 217 nrf_spim_event_t spim_event); 218 219 /** 220 * @brief Function for getting the address of a specific SPIM event register. 221 * 222 * @param[in] p_reg Pointer to the peripheral registers structure. 223 * @param[in] spim_event Requested event. 224 * 225 * @return Address of the specified event register. 226 */ 227 __STATIC_INLINE uint32_t nrf_spim_event_address_get(NRF_SPIM_Type * p_reg, 228 nrf_spim_event_t spim_event); 229 /** 230 * @brief Function for enabling specified shortcuts. 231 * 232 * @param[in] p_reg Pointer to the peripheral registers structure. 233 * @param[in] spim_shorts_mask Shortcuts to enable. 234 */ 235 __STATIC_INLINE void nrf_spim_shorts_enable(NRF_SPIM_Type * p_reg, 236 uint32_t spim_shorts_mask); 237 238 /** 239 * @brief Function for disabling specified shortcuts. 240 * 241 * @param[in] p_reg Pointer to the peripheral registers structure. 242 * @param[in] spim_shorts_mask Shortcuts to disable. 243 */ 244 __STATIC_INLINE void nrf_spim_shorts_disable(NRF_SPIM_Type * p_reg, 245 uint32_t spim_shorts_mask); 246 247 /** 248 * @brief Function for getting shorts setting. 249 * 250 * @param[in] p_reg Pointer to the peripheral registers structure. 251 */ 252 __STATIC_INLINE uint32_t nrf_spim_shorts_get(NRF_SPIM_Type * p_reg); 253 254 /** 255 * @brief Function for enabling specified interrupts. 256 * 257 * @param[in] p_reg Pointer to the peripheral registers structure. 258 * @param[in] spim_int_mask Interrupts to enable. 259 */ 260 __STATIC_INLINE void nrf_spim_int_enable(NRF_SPIM_Type * p_reg, 261 uint32_t spim_int_mask); 262 263 /** 264 * @brief Function for disabling specified interrupts. 265 * 266 * @param[in] p_reg Pointer to the peripheral registers structure. 267 * @param[in] spim_int_mask Interrupts to disable. 268 */ 269 __STATIC_INLINE void nrf_spim_int_disable(NRF_SPIM_Type * p_reg, 270 uint32_t spim_int_mask); 271 272 /** 273 * @brief Function for retrieving the state of a given interrupt. 274 * 275 * @param[in] p_reg Pointer to the peripheral registers structure. 276 * @param[in] spim_int Interrupt to check. 277 * 278 * @retval true If the interrupt is enabled. 279 * @retval false If the interrupt is not enabled. 280 */ 281 __STATIC_INLINE bool nrf_spim_int_enable_check(NRF_SPIM_Type * p_reg, 282 nrf_spim_int_mask_t spim_int); 283 284 #if defined(DPPI_PRESENT) || defined(__NRFX_DOXYGEN__) 285 /** 286 * @brief Function for setting the subscribe configuration for a given 287 * SPIM task. 288 * 289 * @param[in] p_reg Pointer to the structure of registers of the peripheral. 290 * @param[in] task Task for which to set the configuration. 291 * @param[in] channel Channel through which to subscribe events. 292 */ 293 __STATIC_INLINE void nrf_spim_subscribe_set(NRF_SPIM_Type * p_reg, 294 nrf_spim_task_t task, 295 uint8_t channel); 296 297 /** 298 * @brief Function for clearing the subscribe configuration for a given 299 * SPIM task. 300 * 301 * @param[in] p_reg Pointer to the structure of registers of the peripheral. 302 * @param[in] task Task for which to clear the configuration. 303 */ 304 __STATIC_INLINE void nrf_spim_subscribe_clear(NRF_SPIM_Type * p_reg, 305 nrf_spim_task_t task); 306 307 /** 308 * @brief Function for setting the publish configuration for a given 309 * SPIM event. 310 * 311 * @param[in] p_reg Pointer to the structure of registers of the peripheral. 312 * @param[in] event Event for which to set the configuration. 313 * @param[in] channel Channel through which to publish the event. 314 */ 315 __STATIC_INLINE void nrf_spim_publish_set(NRF_SPIM_Type * p_reg, 316 nrf_spim_event_t event, 317 uint8_t channel); 318 319 /** 320 * @brief Function for clearing the publish configuration for a given 321 * SPIM event. 322 * 323 * @param[in] p_reg Pointer to the structure of registers of the peripheral. 324 * @param[in] event Event for which to clear the configuration. 325 */ 326 __STATIC_INLINE void nrf_spim_publish_clear(NRF_SPIM_Type * p_reg, 327 nrf_spim_event_t event); 328 #endif // defined(DPPI_PRESENT) || defined(__NRFX_DOXYGEN__) 329 330 /** 331 * @brief Function for enabling the SPIM peripheral. 332 * 333 * @param[in] p_reg Pointer to the peripheral registers structure. 334 */ 335 __STATIC_INLINE void nrf_spim_enable(NRF_SPIM_Type * p_reg); 336 337 /** 338 * @brief Function for disabling the SPIM peripheral. 339 * 340 * @param[in] p_reg Pointer to the peripheral registers structure. 341 */ 342 __STATIC_INLINE void nrf_spim_disable(NRF_SPIM_Type * p_reg); 343 344 /** 345 * @brief Function for configuring SPIM pins. 346 * 347 * If a given signal is not needed, pass the @ref NRF_SPIM_PIN_NOT_CONNECTED 348 * value instead of its pin number. 349 * 350 * @param[in] p_reg Pointer to the peripheral registers structure. 351 * @param[in] sck_pin SCK pin number. 352 * @param[in] mosi_pin MOSI pin number. 353 * @param[in] miso_pin MISO pin number. 354 */ 355 __STATIC_INLINE void nrf_spim_pins_set(NRF_SPIM_Type * p_reg, 356 uint32_t sck_pin, 357 uint32_t mosi_pin, 358 uint32_t miso_pin); 359 360 #if (NRF_SPIM_HW_CSN_PRESENT) || defined(__NRFX_DOXYGEN__) 361 /** 362 * @brief Function for configuring the SPIM hardware CSN pin. 363 * 364 * If this signal is not needed, pass the @ref NRF_SPIM_PIN_NOT_CONNECTED 365 * value instead of its pin number. 366 * 367 * @param[in] p_reg Pointer to the peripheral registers structure. 368 * @param[in] pin CSN pin number. 369 * @param[in] polarity CSN pin polarity. 370 * @param[in] duration Minimum duration between the edge of CSN and the edge of SCK 371 * and minimum duration of CSN must stay unselected between transactions. 372 * The value is specified in number of 64 MHz clock cycles (15.625 ns). 373 */ 374 __STATIC_INLINE void nrf_spim_csn_configure(NRF_SPIM_Type * p_reg, 375 uint32_t pin, 376 nrf_spim_csn_pol_t polarity, 377 uint32_t duration); 378 #endif // (NRF_SPIM_HW_CSN_PRESENT) || defined(__NRFX_DOXYGEN__) 379 380 #if defined(SPIM_PSELDCX_CONNECT_Msk) || defined(__NRFX_DOXYGEN__) 381 /** 382 * @brief Function for configuring the SPIM DCX pin. 383 * 384 * If this signal is not needed, pass the @ref NRF_SPIM_PIN_NOT_CONNECTED 385 * value instead of its pin number. 386 * 387 * @param[in] p_reg Pointer to the peripheral registers structure. 388 * @param[in] dcx_pin DCX pin number. 389 */ 390 __STATIC_INLINE void nrf_spim_dcx_pin_set(NRF_SPIM_Type * p_reg, 391 uint32_t dcx_pin); 392 393 /** 394 * @brief Function for configuring the number of command bytes. 395 * 396 * Maximum value available for dividing the transmitted bytes into command 397 * bytes and data bytes is @ref NRF_SPIM_DCX_CNT_ALL_CMD - 1. 398 * The @ref NRF_SPIM_DCX_CNT_ALL_CMD value passed as the @c count parameter 399 * causes all transmitted bytes to be marked as command bytes. 400 * 401 * @param[in] p_reg Pointer to the peripheral registers structure. 402 * @param[in] count Number of command bytes preceding the data bytes. 403 */ 404 __STATIC_INLINE void nrf_spim_dcx_cnt_set(NRF_SPIM_Type * p_reg, 405 uint32_t count); 406 #endif // defined(SPIM_PSELDCX_CONNECT_Msk) || defined(__NRFX_DOXYGEN__) 407 408 #if defined(SPIM_IFTIMING_RXDELAY_RXDELAY_Msk) || defined(__NRFX_DOXYGEN__) 409 /** 410 * @brief Function for configuring the extended SPIM interface. 411 * @param p_reg Pointer to the peripheral registers structure. 412 * @param rxdelay Sample delay for input serial data on MISO, 413 * specified in 64 MHz clock cycles (15.625 ns) from the sampling edge of SCK. 414 */ 415 __STATIC_INLINE void nrf_spim_iftiming_set(NRF_SPIM_Type * p_reg, 416 uint32_t rxdelay); 417 #endif // defined(SPIM_IFTIMING_RXDELAY_RXDELAY_Msk) || defined(__NRFX_DOXYGEN__) 418 419 #if defined(SPIM_STALLSTAT_RX_Msk) || defined(__NRFX_DOXYGEN__) 420 /** 421 * @brief Function for clearing stall status for RX EasyDMA RAM accesses. 422 * 423 * @param p_reg Pointer to the peripheral registers structure. 424 */ 425 __STATIC_INLINE void nrf_spim_stallstat_rx_clear(NRF_SPIM_Type * p_reg); 426 427 /** 428 * @brief Function for getting stall status for RX EasyDMA RAM accesses. 429 * 430 * @param p_reg Pointer to the peripheral registers structure. 431 * 432 * @return Stall status of RX EasyDMA RAM accesses. 433 */ 434 __STATIC_INLINE bool nrf_spim_stallstat_rx_get(NRF_SPIM_Type * p_reg); 435 #endif // defined(SPIM_STALLSTAT_RX_Msk) || defined(__NRFX_DOXYGEN__) 436 437 #if defined(SPIM_STALLSTAT_TX_Msk) || defined(__NRFX_DOXYGEN__) 438 /** 439 * @brief Function for clearing stall status for TX EasyDMA RAM accesses. 440 * 441 * @param p_reg Pointer to the peripheral registers structure. 442 */ 443 __STATIC_INLINE void nrf_spim_stallstat_tx_clear(NRF_SPIM_Type * p_reg); 444 445 /** 446 * @brief Function for getting stall status for TX EasyDMA RAM accesses. 447 * 448 * @param p_reg Pointer to the peripheral registers structure. 449 * 450 * @return Stall status of TX EasyDMA RAM accesses. 451 */ 452 __STATIC_INLINE bool nrf_spim_stallstat_tx_get(NRF_SPIM_Type * p_reg); 453 #endif // defined(SPIM_STALLSTAT_TX_Msk) || defined(__NRFX_DOXYGEN__) 454 455 /** 456 * @brief Function for setting the SPI master data rate. 457 * 458 * @param[in] p_reg Pointer to the peripheral registers structure. 459 * @param[in] frequency SPI frequency. 460 */ 461 __STATIC_INLINE void nrf_spim_frequency_set(NRF_SPIM_Type * p_reg, 462 nrf_spim_frequency_t frequency); 463 464 /** 465 * @brief Function for setting the transmit buffer. 466 * 467 * @param[in] p_reg Pointer to the peripheral registers structure. 468 * @param[in] p_buffer Pointer to the buffer with data to send. 469 * @param[in] length Maximum number of data bytes to transmit. 470 */ 471 __STATIC_INLINE void nrf_spim_tx_buffer_set(NRF_SPIM_Type * p_reg, 472 uint8_t const * p_buffer, 473 size_t length); 474 475 /** 476 * @brief Function for setting the receive buffer. 477 * 478 * @param[in] p_reg Pointer to the peripheral registers structure. 479 * @param[in] p_buffer Pointer to the buffer for received data. 480 * @param[in] length Maximum number of data bytes to receive. 481 */ 482 __STATIC_INLINE void nrf_spim_rx_buffer_set(NRF_SPIM_Type * p_reg, 483 uint8_t * p_buffer, 484 size_t length); 485 486 /** 487 * @brief Function for setting the SPI configuration. 488 * 489 * @param[in] p_reg Pointer to the peripheral registers structure. 490 * @param[in] spi_mode SPI mode. 491 * @param[in] spi_bit_order SPI bit order. 492 */ 493 __STATIC_INLINE void nrf_spim_configure(NRF_SPIM_Type * p_reg, 494 nrf_spim_mode_t spi_mode, 495 nrf_spim_bit_order_t spi_bit_order); 496 497 /** 498 * @brief Function for setting the over-read character. 499 * 500 * @param[in] p_reg Pointer to the peripheral registers structure. 501 * @param[in] orc Over-read character that is clocked out in case of 502 * an over-read of the TXD buffer. 503 */ 504 __STATIC_INLINE void nrf_spim_orc_set(NRF_SPIM_Type * p_reg, 505 uint8_t orc); 506 507 /** 508 * @brief Function for enabling the TX list feature. 509 * 510 * @param[in] p_reg Pointer to the peripheral registers structure. 511 */ 512 __STATIC_INLINE void nrf_spim_tx_list_enable(NRF_SPIM_Type * p_reg); 513 514 /** 515 * @brief Function for disabling the TX list feature. 516 * 517 * @param[in] p_reg Pointer to the peripheral registers structure. 518 */ 519 __STATIC_INLINE void nrf_spim_tx_list_disable(NRF_SPIM_Type * p_reg); 520 521 /** 522 * @brief Function for enabling the RX list feature. 523 * 524 * @param[in] p_reg Pointer to the peripheral registers structure. 525 */ 526 __STATIC_INLINE void nrf_spim_rx_list_enable(NRF_SPIM_Type * p_reg); 527 528 /** 529 * @brief Function for disabling the RX list feature. 530 * 531 * @param[in] p_reg Pointer to the peripheral registers structure. 532 */ 533 __STATIC_INLINE void nrf_spim_rx_list_disable(NRF_SPIM_Type * p_reg); 534 535 #ifndef SUPPRESS_INLINE_IMPLEMENTATION 536 537 __STATIC_INLINE void nrf_spim_task_trigger(NRF_SPIM_Type * p_reg, 538 nrf_spim_task_t spim_task) 539 { 540 *((volatile uint32_t *)((uint8_t *)p_reg + (uint32_t)spim_task)) = 0x1UL; 541 } 542 543 __STATIC_INLINE uint32_t nrf_spim_task_address_get(NRF_SPIM_Type * p_reg, 544 nrf_spim_task_t spim_task) 545 { 546 return (uint32_t)((uint8_t *)p_reg + (uint32_t)spim_task); 547 } 548 549 __STATIC_INLINE void nrf_spim_event_clear(NRF_SPIM_Type * p_reg, 550 nrf_spim_event_t spim_event) 551 { 552 *((volatile uint32_t *)((uint8_t *)p_reg + (uint32_t)spim_event)) = 0x0UL; 553 #if __CORTEX_M == 0x04 554 volatile uint32_t dummy = *((volatile uint32_t *)((uint8_t *)p_reg + (uint32_t)spim_event)); 555 (void)dummy; 556 #endif 557 } 558 559 __STATIC_INLINE bool nrf_spim_event_check(NRF_SPIM_Type * p_reg, 560 nrf_spim_event_t spim_event) 561 { 562 return (bool)*(volatile uint32_t *)((uint8_t *)p_reg + (uint32_t)spim_event); 563 } 564 565 __STATIC_INLINE uint32_t nrf_spim_event_address_get(NRF_SPIM_Type * p_reg, 566 nrf_spim_event_t spim_event) 567 { 568 return (uint32_t)((uint8_t *)p_reg + (uint32_t)spim_event); 569 } 570 571 __STATIC_INLINE void nrf_spim_shorts_enable(NRF_SPIM_Type * p_reg, 572 uint32_t spim_shorts_mask) 573 { 574 p_reg->SHORTS |= spim_shorts_mask; 575 } 576 577 __STATIC_INLINE void nrf_spim_shorts_disable(NRF_SPIM_Type * p_reg, 578 uint32_t spim_shorts_mask) 579 { 580 p_reg->SHORTS &= ~(spim_shorts_mask); 581 } 582 583 __STATIC_INLINE uint32_t nrf_spim_shorts_get(NRF_SPIM_Type * p_reg) 584 { 585 return p_reg->SHORTS; 586 } 587 588 __STATIC_INLINE void nrf_spim_int_enable(NRF_SPIM_Type * p_reg, 589 uint32_t spim_int_mask) 590 { 591 p_reg->INTENSET = spim_int_mask; 592 } 593 594 __STATIC_INLINE void nrf_spim_int_disable(NRF_SPIM_Type * p_reg, 595 uint32_t spim_int_mask) 596 { 597 p_reg->INTENCLR = spim_int_mask; 598 } 599 600 __STATIC_INLINE bool nrf_spim_int_enable_check(NRF_SPIM_Type * p_reg, 601 nrf_spim_int_mask_t spim_int) 602 { 603 return (bool)(p_reg->INTENSET & spim_int); 604 } 605 606 #if defined(DPPI_PRESENT) 607 __STATIC_INLINE void nrf_spim_subscribe_set(NRF_SPIM_Type * p_reg, 608 nrf_spim_task_t task, 609 uint8_t channel) 610 { 611 *((volatile uint32_t *) ((uint8_t *) p_reg + (uint32_t) task + 0x80uL)) = 612 ((uint32_t)channel | SPIM_SUBSCRIBE_START_EN_Msk); 613 } 614 615 __STATIC_INLINE void nrf_spim_subscribe_clear(NRF_SPIM_Type * p_reg, 616 nrf_spim_task_t task) 617 { 618 *((volatile uint32_t *) ((uint8_t *) p_reg + (uint32_t) task + 0x80uL)) = 0; 619 } 620 621 __STATIC_INLINE void nrf_spim_publish_set(NRF_SPIM_Type * p_reg, 622 nrf_spim_event_t event, 623 uint8_t channel) 624 { 625 *((volatile uint32_t *) ((uint8_t *) p_reg + (uint32_t) event + 0x80uL)) = 626 ((uint32_t)channel | SPIM_PUBLISH_STARTED_EN_Msk); 627 } 628 629 __STATIC_INLINE void nrf_spim_publish_clear(NRF_SPIM_Type * p_reg, 630 nrf_spim_event_t event) 631 { 632 *((volatile uint32_t *) ((uint8_t *) p_reg + (uint32_t) event + 0x80uL)) = 0; 633 } 634 #endif // defined(DPPI_PRESENT) 635 636 __STATIC_INLINE void nrf_spim_enable(NRF_SPIM_Type * p_reg) 637 { 638 p_reg->ENABLE = (SPIM_ENABLE_ENABLE_Enabled << SPIM_ENABLE_ENABLE_Pos); 639 } 640 641 __STATIC_INLINE void nrf_spim_disable(NRF_SPIM_Type * p_reg) 642 { 643 p_reg->ENABLE = (SPIM_ENABLE_ENABLE_Disabled << SPIM_ENABLE_ENABLE_Pos); 644 } 645 646 __STATIC_INLINE void nrf_spim_pins_set(NRF_SPIM_Type * p_reg, 647 uint32_t sck_pin, 648 uint32_t mosi_pin, 649 uint32_t miso_pin) 650 { 651 p_reg->PSEL.SCK = sck_pin; 652 p_reg->PSEL.MOSI = mosi_pin; 653 p_reg->PSEL.MISO = miso_pin; 654 } 655 656 #if (NRF_SPIM_HW_CSN_PRESENT) 657 __STATIC_INLINE void nrf_spim_csn_configure(NRF_SPIM_Type * p_reg, 658 uint32_t pin, 659 nrf_spim_csn_pol_t polarity, 660 uint32_t duration) 661 { 662 p_reg->PSEL.CSN = pin; 663 p_reg->CSNPOL = polarity; 664 p_reg->IFTIMING.CSNDUR = duration; 665 } 666 #endif // defined(NRF_SPIM_HW_CSN_PRESENT) 667 668 #if defined(SPIM_PSELDCX_CONNECT_Msk) 669 __STATIC_INLINE void nrf_spim_dcx_pin_set(NRF_SPIM_Type * p_reg, 670 uint32_t dcx_pin) 671 { 672 p_reg->PSELDCX = dcx_pin; 673 } 674 675 __STATIC_INLINE void nrf_spim_dcx_cnt_set(NRF_SPIM_Type * p_reg, 676 uint32_t dcx_cnt) 677 { 678 p_reg->DCXCNT = dcx_cnt; 679 } 680 #endif // defined(SPIM_PSELDCX_CONNECT_Msk) 681 682 #if defined(SPIM_IFTIMING_RXDELAY_RXDELAY_Msk) 683 __STATIC_INLINE void nrf_spim_iftiming_set(NRF_SPIM_Type * p_reg, 684 uint32_t rxdelay) 685 { 686 p_reg->IFTIMING.RXDELAY = rxdelay; 687 } 688 #endif // defined(SPIM_IFTIMING_RXDELAY_RXDELAY_Msk) 689 690 #if defined(SPIM_STALLSTAT_RX_Msk) 691 __STATIC_INLINE void nrf_spim_stallstat_rx_clear(NRF_SPIM_Type * p_reg) 692 { 693 p_reg->STALLSTAT &= ~(SPIM_STALLSTAT_RX_Msk); 694 } 695 696 __STATIC_INLINE bool nrf_spim_stallstat_rx_get(NRF_SPIM_Type * p_reg) 697 { 698 return (p_reg->STALLSTAT & SPIM_STALLSTAT_RX_Msk) != 0; 699 } 700 #endif // defined(SPIM_STALLSTAT_RX_Msk) 701 702 #if defined(SPIM_STALLSTAT_TX_Msk) 703 __STATIC_INLINE void nrf_spim_stallstat_tx_clear(NRF_SPIM_Type * p_reg) 704 { 705 p_reg->STALLSTAT &= ~(SPIM_STALLSTAT_TX_Msk); 706 } 707 708 __STATIC_INLINE bool nrf_spim_stallstat_tx_get(NRF_SPIM_Type * p_reg) 709 { 710 return (p_reg->STALLSTAT & SPIM_STALLSTAT_TX_Msk) != 0; 711 } 712 #endif // defined(SPIM_STALLSTAT_TX_Msk) 713 714 __STATIC_INLINE void nrf_spim_frequency_set(NRF_SPIM_Type * p_reg, 715 nrf_spim_frequency_t frequency) 716 { 717 p_reg->FREQUENCY = frequency; 718 } 719 720 __STATIC_INLINE void nrf_spim_tx_buffer_set(NRF_SPIM_Type * p_reg, 721 uint8_t const * p_buffer, 722 size_t length) 723 { 724 p_reg->TXD.PTR = (uint32_t)p_buffer; 725 p_reg->TXD.MAXCNT = length; 726 } 727 728 __STATIC_INLINE void nrf_spim_rx_buffer_set(NRF_SPIM_Type * p_reg, 729 uint8_t * p_buffer, 730 size_t length) 731 { 732 p_reg->RXD.PTR = (uint32_t)p_buffer; 733 p_reg->RXD.MAXCNT = length; 734 } 735 736 __STATIC_INLINE void nrf_spim_configure(NRF_SPIM_Type * p_reg, 737 nrf_spim_mode_t spi_mode, 738 nrf_spim_bit_order_t spi_bit_order) 739 { 740 uint32_t config = (spi_bit_order == NRF_SPIM_BIT_ORDER_MSB_FIRST ? 741 SPIM_CONFIG_ORDER_MsbFirst : SPIM_CONFIG_ORDER_LsbFirst); 742 switch (spi_mode) 743 { 744 default: 745 case NRF_SPIM_MODE_0: 746 config |= (SPIM_CONFIG_CPOL_ActiveHigh << SPIM_CONFIG_CPOL_Pos) | 747 (SPIM_CONFIG_CPHA_Leading << SPIM_CONFIG_CPHA_Pos); 748 break; 749 750 case NRF_SPIM_MODE_1: 751 config |= (SPIM_CONFIG_CPOL_ActiveHigh << SPIM_CONFIG_CPOL_Pos) | 752 (SPIM_CONFIG_CPHA_Trailing << SPIM_CONFIG_CPHA_Pos); 753 break; 754 755 case NRF_SPIM_MODE_2: 756 config |= (SPIM_CONFIG_CPOL_ActiveLow << SPIM_CONFIG_CPOL_Pos) | 757 (SPIM_CONFIG_CPHA_Leading << SPIM_CONFIG_CPHA_Pos); 758 break; 759 760 case NRF_SPIM_MODE_3: 761 config |= (SPIM_CONFIG_CPOL_ActiveLow << SPIM_CONFIG_CPOL_Pos) | 762 (SPIM_CONFIG_CPHA_Trailing << SPIM_CONFIG_CPHA_Pos); 763 break; 764 } 765 p_reg->CONFIG = config; 766 } 767 768 __STATIC_INLINE void nrf_spim_orc_set(NRF_SPIM_Type * p_reg, 769 uint8_t orc) 770 { 771 p_reg->ORC = orc; 772 } 773 774 775 __STATIC_INLINE void nrf_spim_tx_list_enable(NRF_SPIM_Type * p_reg) 776 { 777 p_reg->TXD.LIST = 1; 778 } 779 780 __STATIC_INLINE void nrf_spim_tx_list_disable(NRF_SPIM_Type * p_reg) 781 { 782 p_reg->TXD.LIST = 0; 783 } 784 785 __STATIC_INLINE void nrf_spim_rx_list_enable(NRF_SPIM_Type * p_reg) 786 { 787 p_reg->RXD.LIST = 1; 788 } 789 790 __STATIC_INLINE void nrf_spim_rx_list_disable(NRF_SPIM_Type * p_reg) 791 { 792 p_reg->RXD.LIST = 0; 793 } 794 795 #endif // SUPPRESS_INLINE_IMPLEMENTATION 796 797 /** @} */ 798 799 #ifdef __cplusplus 800 } 801 #endif 802 803 #endif // NRF_SPIM_H__ 804