WIFI_API_20150524e
WIFI_Driver/nordic/spi_master.c@0:a2de37bf5f3d, 2015-06-09 (annotated)
- Committer:
- Marcomissyou
- Date:
- Tue Jun 09 06:04:13 2015 +0000
- Revision:
- 0:a2de37bf5f3d
update to WIFI_API_20150524e
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
Marcomissyou | 0:a2de37bf5f3d | 1 | /* Copyright (c) 2009 Nordic Semiconductor. All Rights Reserved. |
Marcomissyou | 0:a2de37bf5f3d | 2 | * |
Marcomissyou | 0:a2de37bf5f3d | 3 | * The information contained herein is property of Nordic Semiconductor ASA. |
Marcomissyou | 0:a2de37bf5f3d | 4 | * Terms and conditions of usage are described in detail in NORDIC |
Marcomissyou | 0:a2de37bf5f3d | 5 | * SEMICONDUCTOR STANDARD SOFTWARE LICENSE AGREEMENT. |
Marcomissyou | 0:a2de37bf5f3d | 6 | * |
Marcomissyou | 0:a2de37bf5f3d | 7 | * Licensees are granted free, non-transferable use of the information. NO |
Marcomissyou | 0:a2de37bf5f3d | 8 | * WARRANTY of ANY KIND is provided. This heading must NOT be removed from |
Marcomissyou | 0:a2de37bf5f3d | 9 | * the file. |
Marcomissyou | 0:a2de37bf5f3d | 10 | * |
Marcomissyou | 0:a2de37bf5f3d | 11 | */ |
Marcomissyou | 0:a2de37bf5f3d | 12 | |
Marcomissyou | 0:a2de37bf5f3d | 13 | #include <spi_master.h> |
Marcomissyou | 0:a2de37bf5f3d | 14 | //#include "nrf_delay.h" |
Marcomissyou | 0:a2de37bf5f3d | 15 | #include "nrf_gpio.h" |
Marcomissyou | 0:a2de37bf5f3d | 16 | //#include "common.h" |
Marcomissyou | 0:a2de37bf5f3d | 17 | #include "spi_master_config.h" // This file must be in the application folder |
Marcomissyou | 0:a2de37bf5f3d | 18 | |
Marcomissyou | 0:a2de37bf5f3d | 19 | uint32_t* spi_master_init(SPIModuleNumber module_number, SPIMode mode, bool lsb_first) |
Marcomissyou | 0:a2de37bf5f3d | 20 | { |
Marcomissyou | 0:a2de37bf5f3d | 21 | uint32_t config_mode; |
Marcomissyou | 0:a2de37bf5f3d | 22 | |
Marcomissyou | 0:a2de37bf5f3d | 23 | NRF_SPI_Type *spi_base_address = (SPI0 == module_number)? NRF_SPI0 : (NRF_SPI_Type *)NRF_SPI1; |
Marcomissyou | 0:a2de37bf5f3d | 24 | |
Marcomissyou | 0:a2de37bf5f3d | 25 | if(SPI0 == module_number) |
Marcomissyou | 0:a2de37bf5f3d | 26 | { |
Marcomissyou | 0:a2de37bf5f3d | 27 | /* Configure GPIO pins used for pselsck, pselmosi, pselmiso and pselss for SPI0 */ |
Marcomissyou | 0:a2de37bf5f3d | 28 | nrf_gpio_cfg_output(SPI_PSELSCK0); |
Marcomissyou | 0:a2de37bf5f3d | 29 | nrf_gpio_cfg_output(SPI_PSELMOSI0); |
Marcomissyou | 0:a2de37bf5f3d | 30 | nrf_gpio_cfg_input(SPI_PSELMISO0, NRF_GPIO_PIN_PULLUP); |
Marcomissyou | 0:a2de37bf5f3d | 31 | nrf_gpio_cfg_output(SPI_PSELSS0); |
Marcomissyou | 0:a2de37bf5f3d | 32 | nrf_gpio_cfg_output(SPI_PSELSS1_flash); //added by Tsungta |
Marcomissyou | 0:a2de37bf5f3d | 33 | |
Marcomissyou | 0:a2de37bf5f3d | 34 | /* Configure pins, frequency and mode */ |
Marcomissyou | 0:a2de37bf5f3d | 35 | spi_base_address->PSELSCK = SPI_PSELSCK0; |
Marcomissyou | 0:a2de37bf5f3d | 36 | spi_base_address->PSELMOSI = SPI_PSELMOSI0; |
Marcomissyou | 0:a2de37bf5f3d | 37 | spi_base_address->PSELMISO = SPI_PSELMISO0; |
Marcomissyou | 0:a2de37bf5f3d | 38 | nrf_gpio_pin_set(SPI_PSELSS0); /* disable Set slave select (inactive high) */ |
Marcomissyou | 0:a2de37bf5f3d | 39 | nrf_gpio_pin_set(SPI_PSELSS1_flash); //added by Tsungta |
Marcomissyou | 0:a2de37bf5f3d | 40 | } |
Marcomissyou | 0:a2de37bf5f3d | 41 | else |
Marcomissyou | 0:a2de37bf5f3d | 42 | { |
Marcomissyou | 0:a2de37bf5f3d | 43 | /* Configure GPIO pins used for pselsck, pselmosi, pselmiso and pselss for SPI1*/ |
Marcomissyou | 0:a2de37bf5f3d | 44 | nrf_gpio_cfg_output(SPI_PSELSCK1); |
Marcomissyou | 0:a2de37bf5f3d | 45 | nrf_gpio_cfg_output(SPI_PSELMOSI1); |
Marcomissyou | 0:a2de37bf5f3d | 46 | nrf_gpio_cfg_input(SPI_PSELMISO1, NRF_GPIO_PIN_PULLUP); |
Marcomissyou | 0:a2de37bf5f3d | 47 | nrf_gpio_cfg_output(SPI_PSELSS1); |
Marcomissyou | 0:a2de37bf5f3d | 48 | nrf_gpio_cfg_output(SPI_PSELSS1_flash); //added by Tsungta |
Marcomissyou | 0:a2de37bf5f3d | 49 | |
Marcomissyou | 0:a2de37bf5f3d | 50 | /* Configure pins, frequency and mode */ |
Marcomissyou | 0:a2de37bf5f3d | 51 | spi_base_address->PSELSCK = SPI_PSELSCK1; |
Marcomissyou | 0:a2de37bf5f3d | 52 | spi_base_address->PSELMOSI = SPI_PSELMOSI1; |
Marcomissyou | 0:a2de37bf5f3d | 53 | spi_base_address->PSELMISO = SPI_PSELMISO1; |
Marcomissyou | 0:a2de37bf5f3d | 54 | nrf_gpio_pin_set(SPI_PSELSS1); /* disable Set slave select (inactive high) */ |
Marcomissyou | 0:a2de37bf5f3d | 55 | nrf_gpio_pin_set(SPI_PSELSS1_flash); //added by Tsungta |
Marcomissyou | 0:a2de37bf5f3d | 56 | } |
Marcomissyou | 0:a2de37bf5f3d | 57 | spi_base_address->FREQUENCY = (uint32_t) SPI_OPERATING_FREQUENCY_4M; //modified by Tsungta, 4MHz is max. speed for 1.8V |
Marcomissyou | 0:a2de37bf5f3d | 58 | |
Marcomissyou | 0:a2de37bf5f3d | 59 | /*lint -e845 -save // A zero has been given as right argument to operator '!'" */ |
Marcomissyou | 0:a2de37bf5f3d | 60 | /** @snippet [SPI Select mode] */ |
Marcomissyou | 0:a2de37bf5f3d | 61 | switch (mode ) |
Marcomissyou | 0:a2de37bf5f3d | 62 | { |
Marcomissyou | 0:a2de37bf5f3d | 63 | |
Marcomissyou | 0:a2de37bf5f3d | 64 | case SPI_MODE0: |
Marcomissyou | 0:a2de37bf5f3d | 65 | config_mode = (SPI_CONFIG_CPHA_Leading << SPI_CONFIG_CPHA_Pos) | (SPI_CONFIG_CPOL_ActiveHigh << SPI_CONFIG_CPOL_Pos); |
Marcomissyou | 0:a2de37bf5f3d | 66 | break; |
Marcomissyou | 0:a2de37bf5f3d | 67 | case SPI_MODE1: |
Marcomissyou | 0:a2de37bf5f3d | 68 | config_mode = (SPI_CONFIG_CPHA_Trailing << SPI_CONFIG_CPHA_Pos) | (SPI_CONFIG_CPOL_ActiveHigh << SPI_CONFIG_CPOL_Pos); |
Marcomissyou | 0:a2de37bf5f3d | 69 | break; |
Marcomissyou | 0:a2de37bf5f3d | 70 | case SPI_MODE2: |
Marcomissyou | 0:a2de37bf5f3d | 71 | config_mode = (SPI_CONFIG_CPHA_Leading << SPI_CONFIG_CPHA_Pos) | (SPI_CONFIG_CPOL_ActiveLow << SPI_CONFIG_CPOL_Pos); |
Marcomissyou | 0:a2de37bf5f3d | 72 | break; |
Marcomissyou | 0:a2de37bf5f3d | 73 | case SPI_MODE3: |
Marcomissyou | 0:a2de37bf5f3d | 74 | config_mode = (SPI_CONFIG_CPHA_Trailing << SPI_CONFIG_CPHA_Pos) | (SPI_CONFIG_CPOL_ActiveLow << SPI_CONFIG_CPOL_Pos); |
Marcomissyou | 0:a2de37bf5f3d | 75 | break; |
Marcomissyou | 0:a2de37bf5f3d | 76 | default: |
Marcomissyou | 0:a2de37bf5f3d | 77 | config_mode = 0; |
Marcomissyou | 0:a2de37bf5f3d | 78 | break; |
Marcomissyou | 0:a2de37bf5f3d | 79 | |
Marcomissyou | 0:a2de37bf5f3d | 80 | } |
Marcomissyou | 0:a2de37bf5f3d | 81 | /** @snippet [SPI Select mode] */ |
Marcomissyou | 0:a2de37bf5f3d | 82 | /*lint -restore */ |
Marcomissyou | 0:a2de37bf5f3d | 83 | |
Marcomissyou | 0:a2de37bf5f3d | 84 | /*lint -e845 -save // A zero has been given as right argument to operator '!'" */ |
Marcomissyou | 0:a2de37bf5f3d | 85 | /** @snippet [SPI Select endianess] */ |
Marcomissyou | 0:a2de37bf5f3d | 86 | if (lsb_first) |
Marcomissyou | 0:a2de37bf5f3d | 87 | { |
Marcomissyou | 0:a2de37bf5f3d | 88 | spi_base_address->CONFIG = (config_mode | (SPI_CONFIG_ORDER_LsbFirst << SPI_CONFIG_ORDER_Pos)); |
Marcomissyou | 0:a2de37bf5f3d | 89 | } |
Marcomissyou | 0:a2de37bf5f3d | 90 | else |
Marcomissyou | 0:a2de37bf5f3d | 91 | { |
Marcomissyou | 0:a2de37bf5f3d | 92 | spi_base_address->CONFIG = (config_mode | (SPI_CONFIG_ORDER_MsbFirst << SPI_CONFIG_ORDER_Pos)); |
Marcomissyou | 0:a2de37bf5f3d | 93 | } |
Marcomissyou | 0:a2de37bf5f3d | 94 | /** @snippet [SPI Select endianess] */ |
Marcomissyou | 0:a2de37bf5f3d | 95 | /*lint -restore */ |
Marcomissyou | 0:a2de37bf5f3d | 96 | |
Marcomissyou | 0:a2de37bf5f3d | 97 | spi_base_address->EVENTS_READY = 0U; |
Marcomissyou | 0:a2de37bf5f3d | 98 | #if 1 |
Marcomissyou | 0:a2de37bf5f3d | 99 | |
Marcomissyou | 0:a2de37bf5f3d | 100 | /* Enable */ |
Marcomissyou | 0:a2de37bf5f3d | 101 | if(SPI0 == module_number) |
Marcomissyou | 0:a2de37bf5f3d | 102 | spi_base_address->ENABLE = (SPI_ENABLE_ENABLE_Enabled << SPI_ENABLE_ENABLE_Pos); |
Marcomissyou | 0:a2de37bf5f3d | 103 | #endif |
Marcomissyou | 0:a2de37bf5f3d | 104 | return (uint32_t *)spi_base_address; |
Marcomissyou | 0:a2de37bf5f3d | 105 | } |
Marcomissyou | 0:a2de37bf5f3d | 106 | |
Marcomissyou | 0:a2de37bf5f3d | 107 | //bool spi_master_tx_rx(uint32_t *spi_base_address, uint16_t transfer_size, const uint8_t *tx_data, uint8_t *rx_data) |
Marcomissyou | 0:a2de37bf5f3d | 108 | bool spi_master_tx_rx(SPIModuleNumber module_number, uint16_t transfer_size, const uint8_t *tx_data, uint8_t *rx_data) |
Marcomissyou | 0:a2de37bf5f3d | 109 | { |
Marcomissyou | 0:a2de37bf5f3d | 110 | uint32_t counter = 0; |
Marcomissyou | 0:a2de37bf5f3d | 111 | uint16_t number_of_txd_bytes = 0; |
Marcomissyou | 0:a2de37bf5f3d | 112 | uint32_t SEL_SS_PINOUT; |
Marcomissyou | 0:a2de37bf5f3d | 113 | /*lint -e{826} //Are too small pointer conversion */ |
Marcomissyou | 0:a2de37bf5f3d | 114 | // NRF_SPI_Type *spi_base = (NRF_SPI_Type *)spi_base_address; |
Marcomissyou | 0:a2de37bf5f3d | 115 | NRF_SPI_Type *spi_base = (SPI0 == module_number)? NRF_SPI0 : (NRF_SPI_Type *)NRF_SPI1; |
Marcomissyou | 0:a2de37bf5f3d | 116 | volatile uint32_t dummyread; |
Marcomissyou | 0:a2de37bf5f3d | 117 | |
Marcomissyou | 0:a2de37bf5f3d | 118 | if(NRF_SPI0 == spi_base) |
Marcomissyou | 0:a2de37bf5f3d | 119 | spi_base->ENABLE = (SPI_ENABLE_ENABLE_Enabled << SPI_ENABLE_ENABLE_Pos); |
Marcomissyou | 0:a2de37bf5f3d | 120 | // nrf_delay_ms(10); |
Marcomissyou | 0:a2de37bf5f3d | 121 | |
Marcomissyou | 0:a2de37bf5f3d | 122 | // if( (uint32_t *)NRF_SPI0 == spi_base_address) |
Marcomissyou | 0:a2de37bf5f3d | 123 | if(NRF_SPI0 == spi_base) |
Marcomissyou | 0:a2de37bf5f3d | 124 | { |
Marcomissyou | 0:a2de37bf5f3d | 125 | SEL_SS_PINOUT = SPI_PSELSS0; |
Marcomissyou | 0:a2de37bf5f3d | 126 | } |
Marcomissyou | 0:a2de37bf5f3d | 127 | else |
Marcomissyou | 0:a2de37bf5f3d | 128 | { |
Marcomissyou | 0:a2de37bf5f3d | 129 | SEL_SS_PINOUT = SPI_PSELSS1; |
Marcomissyou | 0:a2de37bf5f3d | 130 | } |
Marcomissyou | 0:a2de37bf5f3d | 131 | |
Marcomissyou | 0:a2de37bf5f3d | 132 | /* enable slave (slave select active low) */ |
Marcomissyou | 0:a2de37bf5f3d | 133 | if (SEL_SS_PINOUT == SPI_PSELSS0) |
Marcomissyou | 0:a2de37bf5f3d | 134 | nrf_gpio_pin_clear(SEL_SS_PINOUT); |
Marcomissyou | 0:a2de37bf5f3d | 135 | |
Marcomissyou | 0:a2de37bf5f3d | 136 | while(number_of_txd_bytes < transfer_size) |
Marcomissyou | 0:a2de37bf5f3d | 137 | { |
Marcomissyou | 0:a2de37bf5f3d | 138 | counter = 0;//Tsungta; FIXED for 4MHz issue |
Marcomissyou | 0:a2de37bf5f3d | 139 | if(tx_data == 0) |
Marcomissyou | 0:a2de37bf5f3d | 140 | { |
Marcomissyou | 0:a2de37bf5f3d | 141 | spi_base->TXD = 0x0;//0xFF; |
Marcomissyou | 0:a2de37bf5f3d | 142 | } |
Marcomissyou | 0:a2de37bf5f3d | 143 | else |
Marcomissyou | 0:a2de37bf5f3d | 144 | spi_base->TXD = (uint32_t)(tx_data[number_of_txd_bytes]); |
Marcomissyou | 0:a2de37bf5f3d | 145 | |
Marcomissyou | 0:a2de37bf5f3d | 146 | /* Wait for the transaction complete or timeout (about 10ms - 20 ms) */ |
Marcomissyou | 0:a2de37bf5f3d | 147 | while ((spi_base->EVENTS_READY == 0U) && (counter < TIMEOUT_COUNTER)) |
Marcomissyou | 0:a2de37bf5f3d | 148 | { |
Marcomissyou | 0:a2de37bf5f3d | 149 | counter++; |
Marcomissyou | 0:a2de37bf5f3d | 150 | } |
Marcomissyou | 0:a2de37bf5f3d | 151 | |
Marcomissyou | 0:a2de37bf5f3d | 152 | if (counter == TIMEOUT_COUNTER) |
Marcomissyou | 0:a2de37bf5f3d | 153 | { |
Marcomissyou | 0:a2de37bf5f3d | 154 | /* timed out, disable slave (slave select active low) and return with error */ |
Marcomissyou | 0:a2de37bf5f3d | 155 | if (SEL_SS_PINOUT == SPI_PSELSS0) |
Marcomissyou | 0:a2de37bf5f3d | 156 | nrf_gpio_pin_set(SEL_SS_PINOUT); |
Marcomissyou | 0:a2de37bf5f3d | 157 | return false; |
Marcomissyou | 0:a2de37bf5f3d | 158 | } |
Marcomissyou | 0:a2de37bf5f3d | 159 | else |
Marcomissyou | 0:a2de37bf5f3d | 160 | { /* clear the event to be ready to receive next messages */ |
Marcomissyou | 0:a2de37bf5f3d | 161 | spi_base->EVENTS_READY = 0U; |
Marcomissyou | 0:a2de37bf5f3d | 162 | } |
Marcomissyou | 0:a2de37bf5f3d | 163 | |
Marcomissyou | 0:a2de37bf5f3d | 164 | if(rx_data == 0) |
Marcomissyou | 0:a2de37bf5f3d | 165 | { |
Marcomissyou | 0:a2de37bf5f3d | 166 | dummyread = spi_base->RXD; |
Marcomissyou | 0:a2de37bf5f3d | 167 | } |
Marcomissyou | 0:a2de37bf5f3d | 168 | else |
Marcomissyou | 0:a2de37bf5f3d | 169 | rx_data[number_of_txd_bytes] = (uint8_t)spi_base->RXD; |
Marcomissyou | 0:a2de37bf5f3d | 170 | number_of_txd_bytes++; |
Marcomissyou | 0:a2de37bf5f3d | 171 | }; |
Marcomissyou | 0:a2de37bf5f3d | 172 | |
Marcomissyou | 0:a2de37bf5f3d | 173 | /* disable slave (slave select active low) */ |
Marcomissyou | 0:a2de37bf5f3d | 174 | if (SEL_SS_PINOUT == SPI_PSELSS0) |
Marcomissyou | 0:a2de37bf5f3d | 175 | nrf_gpio_pin_set(SEL_SS_PINOUT); |
Marcomissyou | 0:a2de37bf5f3d | 176 | |
Marcomissyou | 0:a2de37bf5f3d | 177 | if(NRF_SPI0 == spi_base) |
Marcomissyou | 0:a2de37bf5f3d | 178 | spi_base->ENABLE = (SPI_ENABLE_ENABLE_Disabled << SPI_ENABLE_ENABLE_Pos); |
Marcomissyou | 0:a2de37bf5f3d | 179 | // nrf_delay_ms(10); |
Marcomissyou | 0:a2de37bf5f3d | 180 | |
Marcomissyou | 0:a2de37bf5f3d | 181 | return true; |
Marcomissyou | 0:a2de37bf5f3d | 182 | } |
Marcomissyou | 0:a2de37bf5f3d | 183 |