1 /** 2 ****************************************************************************** 3 * @file stm32f4xx_ll_dma.c 4 * @author MCD Application Team 5 * @brief DMA LL module driver. 6 ****************************************************************************** 7 * @attention 8 * 9 * <h2><center>© Copyright (c) 2017 STMicroelectronics. 10 * All rights reserved.</center></h2> 11 * 12 * This software component is licensed by ST under BSD 3-Clause license, 13 * the "License"; You may not use this file except in compliance with the 14 * License. You may obtain a copy of the License at: 15 * opensource.org/licenses/BSD-3-Clause 16 * 17 ****************************************************************************** 18 */ 19 #if defined(USE_FULL_LL_DRIVER) 20 21 /* Includes ------------------------------------------------------------------*/ 22 #include "stm32f4xx_ll_dma.h" 23 #include "stm32f4xx_ll_bus.h" 24 #ifdef USE_FULL_ASSERT 25 #include "stm32_assert.h" 26 #else 27 #define assert_param(expr) ((void)0U) 28 #endif 29 30 /** @addtogroup STM32F4xx_LL_Driver 31 * @{ 32 */ 33 34 #if defined (DMA1) || defined (DMA2) 35 36 /** @defgroup DMA_LL DMA 37 * @{ 38 */ 39 40 /* Private types -------------------------------------------------------------*/ 41 /* Private variables ---------------------------------------------------------*/ 42 /* Private constants ---------------------------------------------------------*/ 43 /* Private macros ------------------------------------------------------------*/ 44 /** @addtogroup DMA_LL_Private_Macros 45 * @{ 46 */ 47 #define IS_LL_DMA_DIRECTION(__VALUE__) (((__VALUE__) == LL_DMA_DIRECTION_PERIPH_TO_MEMORY) || \ 48 ((__VALUE__) == LL_DMA_DIRECTION_MEMORY_TO_PERIPH) || \ 49 ((__VALUE__) == LL_DMA_DIRECTION_MEMORY_TO_MEMORY)) 50 51 #define IS_LL_DMA_MODE(__VALUE__) (((__VALUE__) == LL_DMA_MODE_NORMAL) || \ 52 ((__VALUE__) == LL_DMA_MODE_CIRCULAR) || \ 53 ((__VALUE__) == LL_DMA_MODE_PFCTRL)) 54 55 #define IS_LL_DMA_PERIPHINCMODE(__VALUE__) (((__VALUE__) == LL_DMA_PERIPH_INCREMENT) || \ 56 ((__VALUE__) == LL_DMA_PERIPH_NOINCREMENT)) 57 58 #define IS_LL_DMA_MEMORYINCMODE(__VALUE__) (((__VALUE__) == LL_DMA_MEMORY_INCREMENT) || \ 59 ((__VALUE__) == LL_DMA_MEMORY_NOINCREMENT)) 60 61 #define IS_LL_DMA_PERIPHDATASIZE(__VALUE__) (((__VALUE__) == LL_DMA_PDATAALIGN_BYTE) || \ 62 ((__VALUE__) == LL_DMA_PDATAALIGN_HALFWORD) || \ 63 ((__VALUE__) == LL_DMA_PDATAALIGN_WORD)) 64 65 #define IS_LL_DMA_MEMORYDATASIZE(__VALUE__) (((__VALUE__) == LL_DMA_MDATAALIGN_BYTE) || \ 66 ((__VALUE__) == LL_DMA_MDATAALIGN_HALFWORD) || \ 67 ((__VALUE__) == LL_DMA_MDATAALIGN_WORD)) 68 69 #define IS_LL_DMA_NBDATA(__VALUE__) ((__VALUE__) <= 0x0000FFFFU) 70 71 #define IS_LL_DMA_CHANNEL(__VALUE__) (((__VALUE__) == LL_DMA_CHANNEL_0) || \ 72 ((__VALUE__) == LL_DMA_CHANNEL_1) || \ 73 ((__VALUE__) == LL_DMA_CHANNEL_2) || \ 74 ((__VALUE__) == LL_DMA_CHANNEL_3) || \ 75 ((__VALUE__) == LL_DMA_CHANNEL_4) || \ 76 ((__VALUE__) == LL_DMA_CHANNEL_5) || \ 77 ((__VALUE__) == LL_DMA_CHANNEL_6) || \ 78 ((__VALUE__) == LL_DMA_CHANNEL_7)) 79 80 #define IS_LL_DMA_PRIORITY(__VALUE__) (((__VALUE__) == LL_DMA_PRIORITY_LOW) || \ 81 ((__VALUE__) == LL_DMA_PRIORITY_MEDIUM) || \ 82 ((__VALUE__) == LL_DMA_PRIORITY_HIGH) || \ 83 ((__VALUE__) == LL_DMA_PRIORITY_VERYHIGH)) 84 85 #define IS_LL_DMA_ALL_STREAM_INSTANCE(INSTANCE, STREAM) ((((INSTANCE) == DMA1) && \ 86 (((STREAM) == LL_DMA_STREAM_0) || \ 87 ((STREAM) == LL_DMA_STREAM_1) || \ 88 ((STREAM) == LL_DMA_STREAM_2) || \ 89 ((STREAM) == LL_DMA_STREAM_3) || \ 90 ((STREAM) == LL_DMA_STREAM_4) || \ 91 ((STREAM) == LL_DMA_STREAM_5) || \ 92 ((STREAM) == LL_DMA_STREAM_6) || \ 93 ((STREAM) == LL_DMA_STREAM_7) || \ 94 ((STREAM) == LL_DMA_STREAM_ALL))) ||\ 95 (((INSTANCE) == DMA2) && \ 96 (((STREAM) == LL_DMA_STREAM_0) || \ 97 ((STREAM) == LL_DMA_STREAM_1) || \ 98 ((STREAM) == LL_DMA_STREAM_2) || \ 99 ((STREAM) == LL_DMA_STREAM_3) || \ 100 ((STREAM) == LL_DMA_STREAM_4) || \ 101 ((STREAM) == LL_DMA_STREAM_5) || \ 102 ((STREAM) == LL_DMA_STREAM_6) || \ 103 ((STREAM) == LL_DMA_STREAM_7) || \ 104 ((STREAM) == LL_DMA_STREAM_ALL)))) 105 106 #define IS_LL_DMA_FIFO_MODE_STATE(STATE) (((STATE) == LL_DMA_FIFOMODE_DISABLE ) || \ 107 ((STATE) == LL_DMA_FIFOMODE_ENABLE)) 108 109 #define IS_LL_DMA_FIFO_THRESHOLD(THRESHOLD) (((THRESHOLD) == LL_DMA_FIFOTHRESHOLD_1_4) || \ 110 ((THRESHOLD) == LL_DMA_FIFOTHRESHOLD_1_2) || \ 111 ((THRESHOLD) == LL_DMA_FIFOTHRESHOLD_3_4) || \ 112 ((THRESHOLD) == LL_DMA_FIFOTHRESHOLD_FULL)) 113 114 #define IS_LL_DMA_MEMORY_BURST(BURST) (((BURST) == LL_DMA_MBURST_SINGLE) || \ 115 ((BURST) == LL_DMA_MBURST_INC4) || \ 116 ((BURST) == LL_DMA_MBURST_INC8) || \ 117 ((BURST) == LL_DMA_MBURST_INC16)) 118 119 #define IS_LL_DMA_PERIPHERAL_BURST(BURST) (((BURST) == LL_DMA_PBURST_SINGLE) || \ 120 ((BURST) == LL_DMA_PBURST_INC4) || \ 121 ((BURST) == LL_DMA_PBURST_INC8) || \ 122 ((BURST) == LL_DMA_PBURST_INC16)) 123 124 /** 125 * @} 126 */ 127 128 /* Private function prototypes -----------------------------------------------*/ 129 130 /* Exported functions --------------------------------------------------------*/ 131 /** @addtogroup DMA_LL_Exported_Functions 132 * @{ 133 */ 134 135 /** @addtogroup DMA_LL_EF_Init 136 * @{ 137 */ 138 139 /** 140 * @brief De-initialize the DMA registers to their default reset values. 141 * @param DMAx DMAx Instance 142 * @param Stream This parameter can be one of the following values: 143 * @arg @ref LL_DMA_STREAM_0 144 * @arg @ref LL_DMA_STREAM_1 145 * @arg @ref LL_DMA_STREAM_2 146 * @arg @ref LL_DMA_STREAM_3 147 * @arg @ref LL_DMA_STREAM_4 148 * @arg @ref LL_DMA_STREAM_5 149 * @arg @ref LL_DMA_STREAM_6 150 * @arg @ref LL_DMA_STREAM_7 151 * @arg @ref LL_DMA_STREAM_ALL 152 * @retval An ErrorStatus enumeration value: 153 * - SUCCESS: DMA registers are de-initialized 154 * - ERROR: DMA registers are not de-initialized 155 */ LL_DMA_DeInit(DMA_TypeDef * DMAx,uint32_t Stream)156 uint32_t LL_DMA_DeInit(DMA_TypeDef *DMAx, uint32_t Stream) 157 { 158 DMA_Stream_TypeDef *tmp = (DMA_Stream_TypeDef *)DMA1_Stream0; 159 ErrorStatus status = SUCCESS; 160 161 /* Check the DMA Instance DMAx and Stream parameters*/ 162 assert_param(IS_LL_DMA_ALL_STREAM_INSTANCE(DMAx, Stream)); 163 164 if (Stream == LL_DMA_STREAM_ALL) 165 { 166 if (DMAx == DMA1) 167 { 168 /* Force reset of DMA clock */ 169 LL_AHB1_GRP1_ForceReset(LL_AHB1_GRP1_PERIPH_DMA1); 170 171 /* Release reset of DMA clock */ 172 LL_AHB1_GRP1_ReleaseReset(LL_AHB1_GRP1_PERIPH_DMA1); 173 } 174 else if (DMAx == DMA2) 175 { 176 /* Force reset of DMA clock */ 177 LL_AHB1_GRP1_ForceReset(LL_AHB1_GRP1_PERIPH_DMA2); 178 179 /* Release reset of DMA clock */ 180 LL_AHB1_GRP1_ReleaseReset(LL_AHB1_GRP1_PERIPH_DMA2); 181 } 182 else 183 { 184 status = ERROR; 185 } 186 } 187 else 188 { 189 /* Disable the selected Stream */ 190 LL_DMA_DisableStream(DMAx,Stream); 191 192 /* Get the DMA Stream Instance */ 193 tmp = (DMA_Stream_TypeDef *)(__LL_DMA_GET_STREAM_INSTANCE(DMAx, Stream)); 194 195 /* Reset DMAx_Streamy configuration register */ 196 LL_DMA_WriteReg(tmp, CR, 0U); 197 198 /* Reset DMAx_Streamy remaining bytes register */ 199 LL_DMA_WriteReg(tmp, NDTR, 0U); 200 201 /* Reset DMAx_Streamy peripheral address register */ 202 LL_DMA_WriteReg(tmp, PAR, 0U); 203 204 /* Reset DMAx_Streamy memory address register */ 205 LL_DMA_WriteReg(tmp, M0AR, 0U); 206 207 /* Reset DMAx_Streamy memory address register */ 208 LL_DMA_WriteReg(tmp, M1AR, 0U); 209 210 /* Reset DMAx_Streamy FIFO control register */ 211 LL_DMA_WriteReg(tmp, FCR, 0x00000021U); 212 213 /* Reset Channel register field for DMAx Stream*/ 214 LL_DMA_SetChannelSelection(DMAx, Stream, LL_DMA_CHANNEL_0); 215 216 if(Stream == LL_DMA_STREAM_0) 217 { 218 /* Reset the Stream0 pending flags */ 219 DMAx->LIFCR = 0x0000003FU; 220 } 221 else if(Stream == LL_DMA_STREAM_1) 222 { 223 /* Reset the Stream1 pending flags */ 224 DMAx->LIFCR = 0x00000F40U; 225 } 226 else if(Stream == LL_DMA_STREAM_2) 227 { 228 /* Reset the Stream2 pending flags */ 229 DMAx->LIFCR = 0x003F0000U; 230 } 231 else if(Stream == LL_DMA_STREAM_3) 232 { 233 /* Reset the Stream3 pending flags */ 234 DMAx->LIFCR = 0x0F400000U; 235 } 236 else if(Stream == LL_DMA_STREAM_4) 237 { 238 /* Reset the Stream4 pending flags */ 239 DMAx->HIFCR = 0x0000003FU; 240 } 241 else if(Stream == LL_DMA_STREAM_5) 242 { 243 /* Reset the Stream5 pending flags */ 244 DMAx->HIFCR = 0x00000F40U; 245 } 246 else if(Stream == LL_DMA_STREAM_6) 247 { 248 /* Reset the Stream6 pending flags */ 249 DMAx->HIFCR = 0x003F0000U; 250 } 251 else if(Stream == LL_DMA_STREAM_7) 252 { 253 /* Reset the Stream7 pending flags */ 254 DMAx->HIFCR = 0x0F400000U; 255 } 256 else 257 { 258 status = ERROR; 259 } 260 } 261 262 return status; 263 } 264 265 /** 266 * @brief Initialize the DMA registers according to the specified parameters in DMA_InitStruct. 267 * @note To convert DMAx_Streamy Instance to DMAx Instance and Streamy, use helper macros : 268 * @arg @ref __LL_DMA_GET_INSTANCE 269 * @arg @ref __LL_DMA_GET_STREAM 270 * @param DMAx DMAx Instance 271 * @param Stream This parameter can be one of the following values: 272 * @arg @ref LL_DMA_STREAM_0 273 * @arg @ref LL_DMA_STREAM_1 274 * @arg @ref LL_DMA_STREAM_2 275 * @arg @ref LL_DMA_STREAM_3 276 * @arg @ref LL_DMA_STREAM_4 277 * @arg @ref LL_DMA_STREAM_5 278 * @arg @ref LL_DMA_STREAM_6 279 * @arg @ref LL_DMA_STREAM_7 280 * @param DMA_InitStruct pointer to a @ref LL_DMA_InitTypeDef structure. 281 * @retval An ErrorStatus enumeration value: 282 * - SUCCESS: DMA registers are initialized 283 * - ERROR: Not applicable 284 */ LL_DMA_Init(DMA_TypeDef * DMAx,uint32_t Stream,LL_DMA_InitTypeDef * DMA_InitStruct)285 uint32_t LL_DMA_Init(DMA_TypeDef *DMAx, uint32_t Stream, LL_DMA_InitTypeDef *DMA_InitStruct) 286 { 287 /* Check the DMA Instance DMAx and Stream parameters*/ 288 assert_param(IS_LL_DMA_ALL_STREAM_INSTANCE(DMAx, Stream)); 289 290 /* Check the DMA parameters from DMA_InitStruct */ 291 assert_param(IS_LL_DMA_DIRECTION(DMA_InitStruct->Direction)); 292 assert_param(IS_LL_DMA_MODE(DMA_InitStruct->Mode)); 293 assert_param(IS_LL_DMA_PERIPHINCMODE(DMA_InitStruct->PeriphOrM2MSrcIncMode)); 294 assert_param(IS_LL_DMA_MEMORYINCMODE(DMA_InitStruct->MemoryOrM2MDstIncMode)); 295 assert_param(IS_LL_DMA_PERIPHDATASIZE(DMA_InitStruct->PeriphOrM2MSrcDataSize)); 296 assert_param(IS_LL_DMA_MEMORYDATASIZE(DMA_InitStruct->MemoryOrM2MDstDataSize)); 297 assert_param(IS_LL_DMA_NBDATA(DMA_InitStruct->NbData)); 298 assert_param(IS_LL_DMA_CHANNEL(DMA_InitStruct->Channel)); 299 assert_param(IS_LL_DMA_PRIORITY(DMA_InitStruct->Priority)); 300 assert_param(IS_LL_DMA_FIFO_MODE_STATE(DMA_InitStruct->FIFOMode)); 301 /* Check the memory burst, peripheral burst and FIFO threshold parameters only 302 when FIFO mode is enabled */ 303 if(DMA_InitStruct->FIFOMode != LL_DMA_FIFOMODE_DISABLE) 304 { 305 assert_param(IS_LL_DMA_FIFO_THRESHOLD(DMA_InitStruct->FIFOThreshold)); 306 assert_param(IS_LL_DMA_MEMORY_BURST(DMA_InitStruct->MemBurst)); 307 assert_param(IS_LL_DMA_PERIPHERAL_BURST(DMA_InitStruct->PeriphBurst)); 308 } 309 310 /*---------------------------- DMAx SxCR Configuration ------------------------ 311 * Configure DMAx_Streamy: data transfer direction, data transfer mode, 312 * peripheral and memory increment mode, 313 * data size alignment and priority level with parameters : 314 * - Direction: DMA_SxCR_DIR[1:0] bits 315 * - Mode: DMA_SxCR_CIRC bit 316 * - PeriphOrM2MSrcIncMode: DMA_SxCR_PINC bit 317 * - MemoryOrM2MDstIncMode: DMA_SxCR_MINC bit 318 * - PeriphOrM2MSrcDataSize: DMA_SxCR_PSIZE[1:0] bits 319 * - MemoryOrM2MDstDataSize: DMA_SxCR_MSIZE[1:0] bits 320 * - Priority: DMA_SxCR_PL[1:0] bits 321 */ 322 LL_DMA_ConfigTransfer(DMAx, Stream, DMA_InitStruct->Direction | \ 323 DMA_InitStruct->Mode | \ 324 DMA_InitStruct->PeriphOrM2MSrcIncMode | \ 325 DMA_InitStruct->MemoryOrM2MDstIncMode | \ 326 DMA_InitStruct->PeriphOrM2MSrcDataSize | \ 327 DMA_InitStruct->MemoryOrM2MDstDataSize | \ 328 DMA_InitStruct->Priority 329 ); 330 331 if(DMA_InitStruct->FIFOMode != LL_DMA_FIFOMODE_DISABLE) 332 { 333 /*---------------------------- DMAx SxFCR Configuration ------------------------ 334 * Configure DMAx_Streamy: fifo mode and fifo threshold with parameters : 335 * - FIFOMode: DMA_SxFCR_DMDIS bit 336 * - FIFOThreshold: DMA_SxFCR_FTH[1:0] bits 337 */ 338 LL_DMA_ConfigFifo(DMAx, Stream, DMA_InitStruct->FIFOMode, DMA_InitStruct->FIFOThreshold); 339 340 /*---------------------------- DMAx SxCR Configuration -------------------------- 341 * Configure DMAx_Streamy: memory burst transfer with parameters : 342 * - MemBurst: DMA_SxCR_MBURST[1:0] bits 343 */ 344 LL_DMA_SetMemoryBurstxfer(DMAx,Stream,DMA_InitStruct->MemBurst); 345 346 /*---------------------------- DMAx SxCR Configuration -------------------------- 347 * Configure DMAx_Streamy: peripheral burst transfer with parameters : 348 * - PeriphBurst: DMA_SxCR_PBURST[1:0] bits 349 */ 350 LL_DMA_SetPeriphBurstxfer(DMAx,Stream,DMA_InitStruct->PeriphBurst); 351 } 352 353 /*-------------------------- DMAx SxM0AR Configuration -------------------------- 354 * Configure the memory or destination base address with parameter : 355 * - MemoryOrM2MDstAddress: DMA_SxM0AR_M0A[31:0] bits 356 */ 357 LL_DMA_SetMemoryAddress(DMAx, Stream, DMA_InitStruct->MemoryOrM2MDstAddress); 358 359 /*-------------------------- DMAx SxPAR Configuration --------------------------- 360 * Configure the peripheral or source base address with parameter : 361 * - PeriphOrM2MSrcAddress: DMA_SxPAR_PA[31:0] bits 362 */ 363 LL_DMA_SetPeriphAddress(DMAx, Stream, DMA_InitStruct->PeriphOrM2MSrcAddress); 364 365 /*--------------------------- DMAx SxNDTR Configuration ------------------------- 366 * Configure the peripheral base address with parameter : 367 * - NbData: DMA_SxNDT[15:0] bits 368 */ 369 LL_DMA_SetDataLength(DMAx, Stream, DMA_InitStruct->NbData); 370 371 /*--------------------------- DMA SxCR_CHSEL Configuration ---------------------- 372 * Configure the peripheral base address with parameter : 373 * - PeriphRequest: DMA_SxCR_CHSEL[2:0] bits 374 */ 375 LL_DMA_SetChannelSelection(DMAx, Stream, DMA_InitStruct->Channel); 376 377 return SUCCESS; 378 } 379 380 /** 381 * @brief Set each @ref LL_DMA_InitTypeDef field to default value. 382 * @param DMA_InitStruct Pointer to a @ref LL_DMA_InitTypeDef structure. 383 * @retval None 384 */ LL_DMA_StructInit(LL_DMA_InitTypeDef * DMA_InitStruct)385 void LL_DMA_StructInit(LL_DMA_InitTypeDef *DMA_InitStruct) 386 { 387 /* Set DMA_InitStruct fields to default values */ 388 DMA_InitStruct->PeriphOrM2MSrcAddress = 0x00000000U; 389 DMA_InitStruct->MemoryOrM2MDstAddress = 0x00000000U; 390 DMA_InitStruct->Direction = LL_DMA_DIRECTION_PERIPH_TO_MEMORY; 391 DMA_InitStruct->Mode = LL_DMA_MODE_NORMAL; 392 DMA_InitStruct->PeriphOrM2MSrcIncMode = LL_DMA_PERIPH_NOINCREMENT; 393 DMA_InitStruct->MemoryOrM2MDstIncMode = LL_DMA_MEMORY_NOINCREMENT; 394 DMA_InitStruct->PeriphOrM2MSrcDataSize = LL_DMA_PDATAALIGN_BYTE; 395 DMA_InitStruct->MemoryOrM2MDstDataSize = LL_DMA_MDATAALIGN_BYTE; 396 DMA_InitStruct->NbData = 0x00000000U; 397 DMA_InitStruct->Channel = LL_DMA_CHANNEL_0; 398 DMA_InitStruct->Priority = LL_DMA_PRIORITY_LOW; 399 DMA_InitStruct->FIFOMode = LL_DMA_FIFOMODE_DISABLE; 400 DMA_InitStruct->FIFOThreshold = LL_DMA_FIFOTHRESHOLD_1_4; 401 DMA_InitStruct->MemBurst = LL_DMA_MBURST_SINGLE; 402 DMA_InitStruct->PeriphBurst = LL_DMA_PBURST_SINGLE; 403 } 404 405 /** 406 * @} 407 */ 408 409 /** 410 * @} 411 */ 412 413 /** 414 * @} 415 */ 416 417 #endif /* DMA1 || DMA2 */ 418 419 /** 420 * @} 421 */ 422 423 #endif /* USE_FULL_LL_DRIVER */ 424 425 /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/ 426