Mercurial > public > ostc4
annotate Small_CPU/Src/spi.c @ 554:3328189786e7
Added external ADC interface functionality (MCP3424):
Added communication protocoll to read data from external ADC. At the moment 16bit and 18bit resolutions are supported. External data will be read and forwarded depending on the conversion time of the ADC.
author | Ideenmodellierer |
---|---|
date | Thu, 12 Nov 2020 19:46:03 +0100 |
parents | 2fc08a0d1ec3 |
children | 84a4e1200726 |
rev | line source |
---|---|
38 | 1 /** |
89 | 2 ****************************************************************************** |
3 * @file spi.c | |
4 * @author heinrichs weikamp gmbh | |
5 * @version V0.0.1 | |
6 * @date 16-Sept-2014 | |
7 * @brief Source code for spi control | |
8 * | |
9 @verbatim | |
10 ============================================================================== | |
11 ##### How to use ##### | |
12 ============================================================================== | |
13 @endverbatim | |
14 ****************************************************************************** | |
15 * @attention | |
16 * | |
17 * <h2><center>© COPYRIGHT(c) 2014 heinrichs weikamp</center></h2> | |
18 * | |
19 ****************************************************************************** | |
20 */ | |
38 | 21 |
22 /* Includes ------------------------------------------------------------------*/ | |
143 | 23 |
24 #include "global_constants.h" | |
38 | 25 #include "spi.h" |
120 | 26 #include "dma.h" |
408
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
27 #include "batteryGasGauge.h" |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
28 #include "pressure.h" |
143 | 29 |
38 | 30 //#include "gpio.h" |
31 | |
32 /* USER CODE BEGIN 0 */ | |
33 #include "scheduler.h" | |
34 | |
120 | 35 #ifdef DEBUG_GPIO |
38 | 36 extern void GPIO_new_DEBUG_LOW(void); |
37 extern void GPIO_new_DEBUG_HIGH(void); | |
120 | 38 #endif |
38 | 39 |
89 | 40 uint8_t data_error = 0; |
41 uint32_t data_error_time = 0; | |
143 | 42 uint8_t SPIDataRX = 0; /* Flag to signal that SPI RX callback has been triggered */ |
38 | 43 |
44 static void SPI_Error_Handler(void); | |
45 | |
46 /* USER CODE END 0 */ | |
47 | |
48 static uint8_t SPI_check_header_and_footer_ok(void); | |
143 | 49 static uint8_t DataEX_check_header_and_footer_shifted(void); |
38 | 50 |
51 SPI_HandleTypeDef hspi1; | |
52 SPI_HandleTypeDef hspi3; | |
53 | |
54 DMA_HandleTypeDef hdma_tx; | |
55 DMA_HandleTypeDef hdma_rx; | |
56 | |
57 // SPI3 init function | |
89 | 58 void MX_SPI3_Init(void) { |
59 hspi3.Instance = SPI3; | |
60 hspi3.Init.Mode = SPI_MODE_MASTER; | |
61 hspi3.Init.Direction = SPI_DIRECTION_2LINES; | |
62 hspi3.Init.DataSize = SPI_DATASIZE_8BIT; | |
63 hspi3.Init.CLKPolarity = SPI_POLARITY_HIGH; | |
64 hspi3.Init.CLKPhase = SPI_PHASE_1EDGE; | |
65 hspi3.Init.NSS = SPI_NSS_SOFT; | |
66 hspi3.Init.BaudRatePrescaler = SPI_BAUDRATEPRESCALER_256; | |
67 hspi3.Init.FirstBit = SPI_FIRSTBIT_MSB; | |
68 hspi3.Init.TIMode = SPI_TIMODE_DISABLED; | |
69 hspi3.Init.CRCCalculation = SPI_CRCCALCULATION_DISABLED; | |
70 hspi3.Init.CRCPolynomial = 7; | |
71 HAL_SPI_Init(&hspi3); | |
38 | 72 } |
73 | |
89 | 74 void MX_SPI3_DeInit(void) { |
75 HAL_SPI_DeInit(&hspi3); | |
38 | 76 } |
77 | |
89 | 78 uint8_t SPI3_ButtonAdjust(uint8_t *arrayInput, uint8_t *arrayOutput) { |
38 | 79 HAL_StatusTypeDef status; |
80 uint8_t answer[10]; | |
81 uint8_t rework[10]; | |
82 | |
83 rework[0] = 0xFF; | |
89 | 84 for (int i = 0; i < 3; i++) { |
38 | 85 // limiter |
89 | 86 if (arrayInput[i] == 0xFF) |
38 | 87 arrayInput[i] = 0xFE; |
89 | 88 if (arrayInput[i] >= 15) { |
82 | 89 // copy - ausl�se-schwelle |
89 | 90 rework[i + 1] = arrayInput[i]; |
38 | 91 // wieder-scharf-schalte-schwelle |
89 | 92 rework[i + 3 + 1] = arrayInput[i] - 10; |
93 } else if (arrayInput[i] >= 10) { | |
82 | 94 // copy - ausl�se-schwelle |
89 | 95 rework[i + 1] = arrayInput[i]; |
38 | 96 // wieder-scharf-schalte-schwelle |
89 | 97 rework[i + 3 + 1] = arrayInput[i] - 5; |
98 } else { | |
82 | 99 // copy - ausl�se-schwelle |
89 | 100 rework[i + 1] = 7; |
38 | 101 // wieder-scharf-schalte-schwelle |
89 | 102 rework[i + 3 + 1] = 6; |
38 | 103 } |
104 } | |
105 | |
106 status = HAL_OK; /* = 0 */ | |
89 | 107 HAL_GPIO_WritePin(GPIOC, GPIO_PIN_9, GPIO_PIN_SET); |
108 for (int i = 0; i < 7; i++) { | |
109 HAL_Delay(10); | |
110 HAL_GPIO_WritePin(GPIOC, GPIO_PIN_9, GPIO_PIN_RESET); | |
63 | 111 HAL_Delay(10); |
89 | 112 status += HAL_SPI_TransmitReceive(&hspi3, &rework[i], &answer[i], 1, |
113 20); | |
63 | 114 HAL_Delay(10); |
89 | 115 HAL_GPIO_WritePin(GPIOC, GPIO_PIN_9, GPIO_PIN_SET); |
38 | 116 } |
89 | 117 |
118 if (status == HAL_OK) { | |
119 for (int i = 0; i < 3; i++) { | |
120 arrayOutput[i] = answer[i + 2]; // first not, return of 0xFF not | |
121 } | |
38 | 122 return 1; |
89 | 123 } else |
124 | |
38 | 125 return 0; |
126 } | |
127 | |
128 // SPI5 init function | |
89 | 129 void MX_SPI1_Init(void) { |
130 hspi1.Instance = SPI1; | |
131 hspi1.Init.Mode = SPI_MODE_SLAVE; | |
132 hspi1.Init.Direction = SPI_DIRECTION_2LINES; | |
133 hspi1.Init.DataSize = SPI_DATASIZE_8BIT; | |
134 hspi1.Init.CLKPolarity = SPI_POLARITY_LOW; | |
135 hspi1.Init.CLKPhase = SPI_PHASE_1EDGE; | |
136 hspi1.Init.NSS = SPI_NSS_HARD_INPUT; //SPI_NSS_SOFT; | |
148
ee744c7160ce
Use SPI TX callback to synchronize to main CPU
Ideenmodellierer
parents:
143
diff
changeset
|
137 hspi1.Init.BaudRatePrescaler = SPI_BAUDRATEPRESCALER_128; |
89 | 138 hspi1.Init.FirstBit = SPI_FIRSTBIT_MSB; |
139 hspi1.Init.TIMode = SPI_TIMODE_DISABLED; | |
140 hspi1.Init.CRCCalculation = SPI_CRCCALCULATION_DISABLED; //_DISABLED; _ENABLED; | |
141 hspi1.Init.CRCPolynomial = 7; | |
142 HAL_SPI_Init(&hspi1); | |
38 | 143 } |
144 | |
89 | 145 void MX_SPI_DeInit(void) { |
146 HAL_SPI_DeInit(&hspi1); | |
38 | 147 } |
148 | |
89 | 149 void HAL_SPI_MspInit(SPI_HandleTypeDef* hspi) { |
38 | 150 |
89 | 151 GPIO_InitTypeDef GPIO_InitStruct; |
38 | 152 |
89 | 153 if (hspi->Instance == SPI1) { |
148
ee744c7160ce
Use SPI TX callback to synchronize to main CPU
Ideenmodellierer
parents:
143
diff
changeset
|
154 SPIDataRX = 0; |
89 | 155 // Peripheral clock enable |
156 __SPI1_CLK_ENABLE(); | |
157 __GPIOA_CLK_ENABLE(); | |
38 | 158 //SPI1 GPIO Configuration |
159 //PA4 ------> SPI1_CS | |
160 //PA5 ------> SPI1_SCK | |
161 //PA6 ------> SPI1_MISO | |
162 //PA7 ------> SPI1_MOSI | |
89 | 163 |
164 GPIO_InitStruct.Pin = GPIO_PIN_4 | GPIO_PIN_5 | GPIO_PIN_6 | GPIO_PIN_7; | |
38 | 165 // GPIO_InitStruct.Pin = GPIO_PIN_5|GPIO_PIN_6|GPIO_PIN_7; |
89 | 166 GPIO_InitStruct.Mode = GPIO_MODE_AF_PP; |
167 GPIO_InitStruct.Pull = GPIO_PULLUP; | |
124
4b355396557a
Change GPIO speed for SPI communication as recommended by STM32 Errata
Ideenmodellierer
parents:
120
diff
changeset
|
168 GPIO_InitStruct.Speed = GPIO_SPEED_FAST; /* Decision is based on errata which recommends FAST for GPIO at 90Mhz */ |
89 | 169 GPIO_InitStruct.Alternate = GPIO_AF5_SPI1; |
170 HAL_GPIO_Init(GPIOA, &GPIO_InitStruct); | |
38 | 171 |
172 //##-3- Configure the DMA streams ########################################## | |
173 // Configure the DMA handler for Transmission process | |
89 | 174 hdma_tx.Instance = DMA2_Stream3; |
175 hdma_tx.Init.Channel = DMA_CHANNEL_3; | |
176 hdma_tx.Init.Direction = DMA_MEMORY_TO_PERIPH; | |
177 hdma_tx.Init.PeriphInc = DMA_PINC_DISABLE; | |
178 hdma_tx.Init.MemInc = DMA_MINC_ENABLE; | |
38 | 179 hdma_tx.Init.PeriphDataAlignment = DMA_PDATAALIGN_BYTE; |
89 | 180 hdma_tx.Init.MemDataAlignment = DMA_MDATAALIGN_BYTE; |
181 hdma_tx.Init.Mode = DMA_NORMAL; | |
182 hdma_tx.Init.Priority = DMA_PRIORITY_VERY_HIGH; | |
183 hdma_tx.Init.FIFOMode = DMA_FIFOMODE_DISABLE; | |
184 hdma_tx.Init.FIFOThreshold = DMA_FIFO_THRESHOLD_FULL; | |
185 hdma_tx.Init.MemBurst = DMA_MBURST_INC4; | |
186 hdma_tx.Init.PeriphBurst = DMA_PBURST_INC4; | |
187 | |
188 HAL_DMA_Init(&hdma_tx); | |
189 | |
38 | 190 // Associate the initialized DMA handle to the the SPI handle |
191 __HAL_LINKDMA(hspi, hdmatx, hdma_tx); | |
89 | 192 |
38 | 193 // Configure the DMA handler for Transmission process |
89 | 194 hdma_rx.Instance = DMA2_Stream0; |
195 hdma_rx.Init.Channel = DMA_CHANNEL_3; | |
196 hdma_rx.Init.Direction = DMA_PERIPH_TO_MEMORY; | |
197 hdma_rx.Init.PeriphInc = DMA_PINC_DISABLE; | |
198 hdma_rx.Init.MemInc = DMA_MINC_ENABLE; | |
38 | 199 hdma_rx.Init.PeriphDataAlignment = DMA_PDATAALIGN_BYTE; |
89 | 200 hdma_rx.Init.MemDataAlignment = DMA_MDATAALIGN_BYTE; |
201 hdma_rx.Init.Mode = DMA_NORMAL; | |
202 hdma_rx.Init.Priority = DMA_PRIORITY_HIGH; | |
203 hdma_rx.Init.FIFOMode = DMA_FIFOMODE_DISABLE; | |
204 hdma_rx.Init.FIFOThreshold = DMA_FIFO_THRESHOLD_FULL; | |
205 hdma_rx.Init.MemBurst = DMA_MBURST_INC4; | |
206 hdma_rx.Init.PeriphBurst = DMA_PBURST_INC4; | |
38 | 207 |
208 HAL_DMA_Init(&hdma_rx); | |
89 | 209 |
210 // Associate the initialized DMA handle to the the SPI handle | |
211 __HAL_LINKDMA(hspi, hdmarx, hdma_rx); | |
38 | 212 |
89 | 213 //##-4- Configure the NVIC for DMA ######################################### |
214 //NVIC configuration for DMA transfer complete interrupt (SPI3_RX) | |
215 HAL_NVIC_SetPriority(DMA2_Stream0_IRQn, 1, 0); | |
216 HAL_NVIC_EnableIRQ(DMA2_Stream0_IRQn); | |
217 | |
218 // NVIC configuration for DMA transfer complete interrupt (SPI1_TX) | |
219 HAL_NVIC_SetPriority(DMA2_Stream3_IRQn, 1, 1); | |
220 HAL_NVIC_EnableIRQ(DMA2_Stream3_IRQn); | |
221 } else if (hspi->Instance == SPI3) { | |
222 __GPIOC_CLK_ENABLE(); | |
223 __SPI3_CLK_ENABLE(); | |
38 | 224 |
225 //SPI1 GPIO Configuration | |
226 //PC10 ------> SPI3_SCK | |
227 //PC11 ------> SPI3_MISO | |
228 //PC12 ------> SPI3_MOSI | |
229 //PA15 ------> SPI3_NSS (official) | |
230 //PC9 ------> SPI3_NSS (hw) | |
89 | 231 |
232 GPIO_InitStruct.Pin = GPIO_PIN_10 | GPIO_PIN_11 | GPIO_PIN_12; | |
233 GPIO_InitStruct.Mode = GPIO_MODE_AF_PP; | |
234 GPIO_InitStruct.Pull = GPIO_PULLUP; | |
235 GPIO_InitStruct.Speed = GPIO_SPEED_FAST; | |
236 GPIO_InitStruct.Alternate = GPIO_AF6_SPI3; | |
237 HAL_GPIO_Init(GPIOC, &GPIO_InitStruct); | |
38 | 238 |
239 GPIO_InitStruct.Pin = GPIO_PIN_9; | |
240 GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP; | |
241 GPIO_InitStruct.Pull = GPIO_PULLUP; | |
242 GPIO_InitStruct.Speed = GPIO_SPEED_LOW; | |
89 | 243 HAL_GPIO_Init(GPIOC, &GPIO_InitStruct); |
38 | 244 |
89 | 245 HAL_GPIO_WritePin(GPIOC, GPIO_PIN_9, GPIO_PIN_SET); |
38 | 246 } |
247 } | |
248 | |
89 | 249 void HAL_SPI_MspDeInit(SPI_HandleTypeDef* hspi) { |
250 if (hspi->Instance == SPI1) { | |
38 | 251 __SPI1_FORCE_RESET(); |
252 __SPI1_RELEASE_RESET(); | |
253 | |
254 //SPI1 GPIO Configuration | |
255 //PA5 ------> SPI1_SCK | |
256 //PA6 ------> SPI1_MISO | |
257 //PA7 ------> SPI1_MOSI | |
89 | 258 |
259 HAL_GPIO_DeInit(GPIOA, GPIO_PIN_5 | GPIO_PIN_6 | GPIO_PIN_7); | |
38 | 260 |
261 HAL_DMA_DeInit(&hdma_tx); | |
262 HAL_DMA_DeInit(&hdma_rx); | |
89 | 263 |
38 | 264 HAL_NVIC_DisableIRQ(DMA2_Stream3_IRQn); |
265 HAL_NVIC_DisableIRQ(DMA2_Stream0_IRQn); | |
89 | 266 } else if (hspi->Instance == SPI3) { |
38 | 267 __SPI3_FORCE_RESET(); |
268 __SPI3_RELEASE_RESET(); | |
269 | |
270 //SPI1 GPIO Configuration | |
271 //PC10 ------> SPI3_SCK | |
272 //PC11 ------> SPI3_MISO | |
273 //PC12 ------> SPI3_MOSI | |
274 //PA15 ------> SPI3_NSS (official) | |
275 //PC9 ------> SPI3_NSS (hw) | |
89 | 276 HAL_GPIO_DeInit(GPIOC, GPIO_PIN_10 | GPIO_PIN_11 | GPIO_PIN_12); |
38 | 277 } |
278 } | |
279 | |
89 | 280 void SPI_synchronize_with_Master(void) { |
148
ee744c7160ce
Use SPI TX callback to synchronize to main CPU
Ideenmodellierer
parents:
143
diff
changeset
|
281 #ifdef USE_OLD_SYNC_METHOD |
136
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
282 GPIO_InitTypeDef GPIO_InitStruct; |
89 | 283 // |
136
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
284 __GPIOA_CLK_ENABLE(); |
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
285 /**SPI1 GPIO Configuration |
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
286 PA5 ------> SPI1_SCK |
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
287 */ |
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
288 GPIO_InitStruct.Pin = GPIO_PIN_4 | GPIO_PIN_5; |
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
289 GPIO_InitStruct.Mode = GPIO_MODE_INPUT; |
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
290 GPIO_InitStruct.Pull = GPIO_PULLUP; |
148
ee744c7160ce
Use SPI TX callback to synchronize to main CPU
Ideenmodellierer
parents:
143
diff
changeset
|
291 GPIO_InitStruct.Speed = GPIO_SPEED_FAST; |
136
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
292 HAL_GPIO_Init(GPIOA, &GPIO_InitStruct); |
89 | 293 // |
136
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
294 HAL_Delay(10); |
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
295 while (HAL_GPIO_ReadPin(GPIOA, GPIO_PIN_4) == 0); |
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
296 HAL_Delay(10); |
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
297 while (HAL_GPIO_ReadPin(GPIOA, GPIO_PIN_5) == 1); |
148
ee744c7160ce
Use SPI TX callback to synchronize to main CPU
Ideenmodellierer
parents:
143
diff
changeset
|
298 HAL_Delay(50); |
136
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
299 #endif |
38 | 300 } |
301 | |
89 | 302 void SPI_Start_single_TxRx_with_Master(void) { |
408
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
303 static uint8_t DevicedataDelayCnt = 10; |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
304 static uint8_t DeviceDataPending = 0; |
38 | 305 uint8_t * pOutput; |
136
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
306 HAL_StatusTypeDef retval; |
38 | 307 |
408
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
308 if ((global.dataSendToSlave.getDeviceDataNow) || (DeviceDataPending)) |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
309 { |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
310 if(((DevicedataDelayCnt == 0) || (((get_voltage() != 6.0) && (get_temperature() != 0.0))))) /* devicedata complete? */ |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
311 { |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
312 global.dataSendToSlave.getDeviceDataNow = 0; |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
313 DeviceDataPending = 0; |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
314 pOutput = (uint8_t*) &(global.deviceDataSendToMaster); |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
315 } |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
316 else |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
317 { |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
318 DeviceDataPending = 1; |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
319 DevicedataDelayCnt--; |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
320 pOutput = (uint8_t*) &(global.dataSendToMaster); |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
321 } |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
322 |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
323 } |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
324 else |
2fc08a0d1ec3
Bugfix invalid voltage / temperatur after coldstart:
ideenmodellierer
parents:
277
diff
changeset
|
325 { |
89 | 326 pOutput = (uint8_t*) &(global.dataSendToMaster); |
38 | 327 } |
136
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
328 retval = HAL_SPI_TransmitReceive_DMA(&hspi1, pOutput,(uint8_t*) &(global.dataSendToSlave), EXCHANGE_BUFFERSIZE); |
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
329 if ( retval!= HAL_OK) { |
38 | 330 SPI_Error_Handler(); |
331 } | |
332 } | |
333 | |
89 | 334 void HAL_SPI_TxRxCpltCallback(SPI_HandleTypeDef *hspi) { |
335 /* restart SPI */ | |
136
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
336 if (hspi == &hspi1) |
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
337 { |
264
b3685fbada3b
Sync to Main 100ms time stamp & added Reinitialization of globals after startup
ideenmodellierer
parents:
239
diff
changeset
|
338 if(SPI_check_header_and_footer_ok()) /* process timestamp provided by main */ |
b3685fbada3b
Sync to Main 100ms time stamp & added Reinitialization of globals after startup
ideenmodellierer
parents:
239
diff
changeset
|
339 { |
b3685fbada3b
Sync to Main 100ms time stamp & added Reinitialization of globals after startup
ideenmodellierer
parents:
239
diff
changeset
|
340 Scheduler_SyncToSPI(global.dataSendToSlave.header.checkCode[SPI_HEADER_INDEX_TX_TICK]); |
b3685fbada3b
Sync to Main 100ms time stamp & added Reinitialization of globals after startup
ideenmodellierer
parents:
239
diff
changeset
|
341 } |
b3685fbada3b
Sync to Main 100ms time stamp & added Reinitialization of globals after startup
ideenmodellierer
parents:
239
diff
changeset
|
342 else |
b3685fbada3b
Sync to Main 100ms time stamp & added Reinitialization of globals after startup
ideenmodellierer
parents:
239
diff
changeset
|
343 { |
b3685fbada3b
Sync to Main 100ms time stamp & added Reinitialization of globals after startup
ideenmodellierer
parents:
239
diff
changeset
|
344 Scheduler_SyncToSPI(0); /* => no async will be calculated */ |
b3685fbada3b
Sync to Main 100ms time stamp & added Reinitialization of globals after startup
ideenmodellierer
parents:
239
diff
changeset
|
345 } |
b3685fbada3b
Sync to Main 100ms time stamp & added Reinitialization of globals after startup
ideenmodellierer
parents:
239
diff
changeset
|
346 |
143 | 347 SPIDataRX = 1; |
348 | |
89 | 349 /* stop data exchange? */ |
350 if (global.mode == MODE_SHUTDOWN) { | |
351 global.mode = MODE_SLEEP; | |
352 global.dataSendToSlavePending = 0; | |
353 global.dataSendToSlaveIsValid = 1; | |
354 global.dataSendToSlaveIsNotValidCount = 0; | |
355 } | |
143 | 356 } |
357 } | |
82 | 358 |
264
b3685fbada3b
Sync to Main 100ms time stamp & added Reinitialization of globals after startup
ideenmodellierer
parents:
239
diff
changeset
|
359 uint8_t SPI_Evaluate_RX_Data() |
143 | 360 { |
208 | 361 uint8_t resettimeout = 1; |
264
b3685fbada3b
Sync to Main 100ms time stamp & added Reinitialization of globals after startup
ideenmodellierer
parents:
239
diff
changeset
|
362 uint8_t ret = SPIDataRX; |
208 | 363 |
143 | 364 if ((global.mode != MODE_SHUTDOWN) && ( global.mode != MODE_SLEEP) && (SPIDataRX)) |
365 { | |
366 SPIDataRX = 0; | |
89 | 367 /* data consistent? */ |
368 if (SPI_check_header_and_footer_ok()) { | |
208 | 369 global.dataSendToMaster.header.checkCode[SPI_HEADER_INDEX_RX_STATE] = SPI_RX_STATE_OK; |
143 | 370 // GPIO_new_DEBUG_HIGH(); //For debug. |
89 | 371 global.dataSendToSlaveIsValid = 1; |
372 global.dataSendToSlaveIsNotValidCount = 0; | |
208 | 373 /* Master signal a data shift outside of his control => reset own DMA and resync */ |
374 if(global.dataSendToSlave.header.checkCode[SPI_HEADER_INDEX_RX_STATE] == SPI_RX_STATE_SHIFTED) | |
143 | 375 { |
376 HAL_SPI_Abort_IT(&hspi1); | |
208 | 377 Scheduler_Request_sync_with_SPI(SPI_SYNC_METHOD_HARD); |
143 | 378 } |
277 | 379 else |
380 { | |
381 } | |
382 SPI_Start_single_TxRx_with_Master(); | |
208 | 383 } |
384 else | |
385 { | |
143 | 386 // GPIO_new_DEBUG_LOW(); //For debug. |
136
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
387 global.dataSendToSlaveIsValid = 0; |
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
388 global.dataSendToSlaveIsNotValidCount++; |
143 | 389 if(DataEX_check_header_and_footer_shifted()) |
390 { | |
208 | 391 |
392 /* Reset own DMA */ | |
393 if ((global.dataSendToSlaveIsNotValidCount % 10) == 1) //% 10 | |
143 | 394 { |
395 HAL_SPI_Abort_IT(&hspi1); /* reset DMA only once */ | |
396 } | |
208 | 397 /* Signal problem to master */ |
398 if ((global.dataSendToSlaveIsNotValidCount ) >= 2) | |
399 { | |
400 global.dataSendToMaster.header.checkCode[SPI_HEADER_INDEX_RX_STATE] = SPI_RX_STATE_SHIFTED; | |
401 } | |
143 | 402 } |
208 | 403 else /* handle received data as if no data would have been received */ |
404 { | |
405 global.dataSendToMaster.header.checkCode[SPI_HEADER_INDEX_RX_STATE] = SPI_RX_STATE_OFFLINE; | |
406 resettimeout = 0; | |
407 } | |
277 | 408 HAL_SPI_TransmitReceive_DMA(&hspi1,(uint8_t*) &(global.dataSendToMaster),(uint8_t*) &(global.dataSendToSlave), EXCHANGE_BUFFERSIZE); |
208 | 409 } |
143 | 410 |
89 | 411 global.dataSendToMaster.power_on_reset = 0; |
412 global.deviceDataSendToMaster.power_on_reset = 0; | |
413 | |
143 | 414 scheduleSpecial_Evaluate_DataSendToSlave(); |
136
6ae8ba5683d6
Introduces abort of communication in case of a out of sync DMA transfer
Ideenmodellierer
parents:
124
diff
changeset
|
415 |
264
b3685fbada3b
Sync to Main 100ms time stamp & added Reinitialization of globals after startup
ideenmodellierer
parents:
239
diff
changeset
|
416 if(resettimeout) |
b3685fbada3b
Sync to Main 100ms time stamp & added Reinitialization of globals after startup
ideenmodellierer
parents:
239
diff
changeset
|
417 { |
b3685fbada3b
Sync to Main 100ms time stamp & added Reinitialization of globals after startup
ideenmodellierer
parents:
239
diff
changeset
|
418 global.check_sync_not_running = 0; |
b3685fbada3b
Sync to Main 100ms time stamp & added Reinitialization of globals after startup
ideenmodellierer
parents:
239
diff
changeset
|
419 } |
208 | 420 } |
264
b3685fbada3b
Sync to Main 100ms time stamp & added Reinitialization of globals after startup
ideenmodellierer
parents:
239
diff
changeset
|
421 return ret; |
38 | 422 } |
423 | |
89 | 424 static uint8_t SPI_check_header_and_footer_ok(void) { |
425 if (global.dataSendToSlave.header.checkCode[0] != 0xBB) | |
38 | 426 return 0; |
148
ee744c7160ce
Use SPI TX callback to synchronize to main CPU
Ideenmodellierer
parents:
143
diff
changeset
|
427 #ifdef USE_OLD_HEADER_FORMAT |
89 | 428 if (global.dataSendToSlave.header.checkCode[1] != 0x01) |
38 | 429 return 0; |
89 | 430 if (global.dataSendToSlave.header.checkCode[2] != 0x01) |
38 | 431 return 0; |
143 | 432 #endif |
89 | 433 if (global.dataSendToSlave.header.checkCode[3] != 0xBB) |
38 | 434 return 0; |
89 | 435 if (global.dataSendToSlave.footer.checkCode[0] != 0xF4) |
38 | 436 return 0; |
89 | 437 if (global.dataSendToSlave.footer.checkCode[1] != 0xF3) |
38 | 438 return 0; |
89 | 439 if (global.dataSendToSlave.footer.checkCode[2] != 0xF2) |
38 | 440 return 0; |
89 | 441 if (global.dataSendToSlave.footer.checkCode[3] != 0xF1) |
38 | 442 return 0; |
443 | |
444 return 1; | |
445 } | |
446 | |
143 | 447 |
448 /* Check if there is an empty frame providec by RTE (all 0) or even no data provided by RTE (all 0xFF) | |
449 * If that is not the case the DMA is somehow not in sync | |
450 */ | |
451 uint8_t DataEX_check_header_and_footer_shifted() | |
452 { | |
453 uint8_t ret = 1; | |
454 if((global.dataSendToSlave.footer.checkCode[0] == 0x00) | |
455 && (global.dataSendToSlave.footer.checkCode[1] == 0x00) | |
456 && (global.dataSendToSlave.footer.checkCode[2] == 0x00) | |
457 && (global.dataSendToSlave.footer.checkCode[3] == 0x00)) { ret = 0; } | |
458 | |
459 if((global.dataSendToSlave.footer.checkCode[0] == 0xff) | |
460 && (global.dataSendToSlave.footer.checkCode[1] == 0xff) | |
461 && (global.dataSendToSlave.footer.checkCode[2] == 0xff) | |
462 && (global.dataSendToSlave.footer.checkCode[3] == 0xff)) { ret = 0; } | |
463 | |
464 return ret; | |
465 } | |
466 | |
89 | 467 static void SPI_Error_Handler(void) { |
82 | 468 //The device is locks. Hard to recover. |
469 // while(1) | |
470 // { | |
471 // } | |
38 | 472 } |
473 | |
474 /** | |
89 | 475 * @} |
476 */ | |
38 | 477 |
478 /** | |
89 | 479 * @} |
480 */ | |
38 | 481 |
482 /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/ |