1 /**
2   ******************************************************************************
3   * @file    stm32l1xx_ll_dma.c
4   * @author  MCD Application Team
5   * @brief   DMA LL module driver.
6   ******************************************************************************
7   * @attention
8   *
9   * <h2><center>&copy; 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 "stm32l1xx_ll_dma.h"
23 #include "stm32l1xx_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 STM32L1xx_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 
54 #define IS_LL_DMA_PERIPHINCMODE(__VALUE__)      (((__VALUE__) == LL_DMA_PERIPH_INCREMENT) || \
55                                                  ((__VALUE__) == LL_DMA_PERIPH_NOINCREMENT))
56 
57 #define IS_LL_DMA_MEMORYINCMODE(__VALUE__)      (((__VALUE__) == LL_DMA_MEMORY_INCREMENT) || \
58                                                  ((__VALUE__) == LL_DMA_MEMORY_NOINCREMENT))
59 
60 #define IS_LL_DMA_PERIPHDATASIZE(__VALUE__)     (((__VALUE__) == LL_DMA_PDATAALIGN_BYTE)      || \
61                                                  ((__VALUE__) == LL_DMA_PDATAALIGN_HALFWORD)  || \
62                                                  ((__VALUE__) == LL_DMA_PDATAALIGN_WORD))
63 
64 #define IS_LL_DMA_MEMORYDATASIZE(__VALUE__)     (((__VALUE__) == LL_DMA_MDATAALIGN_BYTE)      || \
65                                                  ((__VALUE__) == LL_DMA_MDATAALIGN_HALFWORD)  || \
66                                                  ((__VALUE__) == LL_DMA_MDATAALIGN_WORD))
67 
68 #define IS_LL_DMA_NBDATA(__VALUE__)             ((__VALUE__)  <= 0x0000FFFFU)
69 
70 
71 #define IS_LL_DMA_PRIORITY(__VALUE__)           (((__VALUE__) == LL_DMA_PRIORITY_LOW)    || \
72                                                  ((__VALUE__) == LL_DMA_PRIORITY_MEDIUM) || \
73                                                  ((__VALUE__) == LL_DMA_PRIORITY_HIGH)   || \
74                                                  ((__VALUE__) == LL_DMA_PRIORITY_VERYHIGH))
75 
76 #if defined (DMA2)
77 #if defined (DMA2_Channel6) && defined (DMA2_Channel7)
78 #define IS_LL_DMA_ALL_CHANNEL_INSTANCE(INSTANCE, CHANNEL)  ((((INSTANCE) == DMA1) && \
79                                                          (((CHANNEL) == LL_DMA_CHANNEL_1) || \
80                                                           ((CHANNEL) == LL_DMA_CHANNEL_2) || \
81                                                           ((CHANNEL) == LL_DMA_CHANNEL_3) || \
82                                                           ((CHANNEL) == LL_DMA_CHANNEL_4) || \
83                                                           ((CHANNEL) == LL_DMA_CHANNEL_5) || \
84                                                           ((CHANNEL) == LL_DMA_CHANNEL_6) || \
85                                                           ((CHANNEL) == LL_DMA_CHANNEL_7))) || \
86                                                          (((INSTANCE) == DMA2) && \
87                                                          (((CHANNEL) == LL_DMA_CHANNEL_1) || \
88                                                           ((CHANNEL) == LL_DMA_CHANNEL_2) || \
89                                                           ((CHANNEL) == LL_DMA_CHANNEL_3) || \
90                                                           ((CHANNEL) == LL_DMA_CHANNEL_4) || \
91                                                           ((CHANNEL) == LL_DMA_CHANNEL_5) || \
92                                                           ((CHANNEL) == LL_DMA_CHANNEL_6) || \
93                                                           ((CHANNEL) == LL_DMA_CHANNEL_7))))
94 #else
95 #define IS_LL_DMA_ALL_CHANNEL_INSTANCE(INSTANCE, CHANNEL)  ((((INSTANCE) == DMA1) && \
96                                                          (((CHANNEL) == LL_DMA_CHANNEL_1) || \
97                                                           ((CHANNEL) == LL_DMA_CHANNEL_2) || \
98                                                           ((CHANNEL) == LL_DMA_CHANNEL_3) || \
99                                                           ((CHANNEL) == LL_DMA_CHANNEL_4) || \
100                                                           ((CHANNEL) == LL_DMA_CHANNEL_5) || \
101                                                           ((CHANNEL) == LL_DMA_CHANNEL_6) || \
102                                                           ((CHANNEL) == LL_DMA_CHANNEL_7))) || \
103                                                          (((INSTANCE) == DMA2) && \
104                                                          (((CHANNEL) == LL_DMA_CHANNEL_1) || \
105                                                           ((CHANNEL) == LL_DMA_CHANNEL_2) || \
106                                                           ((CHANNEL) == LL_DMA_CHANNEL_3) || \
107                                                           ((CHANNEL) == LL_DMA_CHANNEL_4) || \
108                                                           ((CHANNEL) == LL_DMA_CHANNEL_5))))
109 #endif
110 #else
111 #define IS_LL_DMA_ALL_CHANNEL_INSTANCE(INSTANCE, CHANNEL)  ((((INSTANCE) == DMA1) && \
112                                                             (((CHANNEL) == LL_DMA_CHANNEL_1)|| \
113                                                             ((CHANNEL) == LL_DMA_CHANNEL_2) || \
114                                                             ((CHANNEL) == LL_DMA_CHANNEL_3) || \
115                                                             ((CHANNEL) == LL_DMA_CHANNEL_4) || \
116                                                             ((CHANNEL) == LL_DMA_CHANNEL_5) || \
117                                                             ((CHANNEL) == LL_DMA_CHANNEL_6) || \
118                                                             ((CHANNEL) == LL_DMA_CHANNEL_7))))
119 #endif
120 /**
121   * @}
122   */
123 
124 /* Private function prototypes -----------------------------------------------*/
125 
126 /* Exported functions --------------------------------------------------------*/
127 /** @addtogroup DMA_LL_Exported_Functions
128   * @{
129   */
130 
131 /** @addtogroup DMA_LL_EF_Init
132   * @{
133   */
134 
135 /**
136   * @brief  De-initialize the DMA registers to their default reset values.
137   * @param  DMAx DMAx Instance
138   * @param  Channel This parameter can be one of the following values:
139   *         @arg @ref LL_DMA_CHANNEL_1
140   *         @arg @ref LL_DMA_CHANNEL_2
141   *         @arg @ref LL_DMA_CHANNEL_3
142   *         @arg @ref LL_DMA_CHANNEL_4
143   *         @arg @ref LL_DMA_CHANNEL_5
144   *         @arg @ref LL_DMA_CHANNEL_6
145   *         @arg @ref LL_DMA_CHANNEL_7
146   *         @arg @ref LL_DMA_CHANNEL_ALL
147   * @retval An ErrorStatus enumeration value:
148   *          - SUCCESS: DMA registers are de-initialized
149   *          - ERROR: DMA registers are not de-initialized
150   */
LL_DMA_DeInit(DMA_TypeDef * DMAx,uint32_t Channel)151 uint32_t LL_DMA_DeInit(DMA_TypeDef *DMAx, uint32_t Channel)
152 {
153   DMA_Channel_TypeDef *tmp = (DMA_Channel_TypeDef *)DMA1_Channel1;
154   ErrorStatus status = SUCCESS;
155 
156   /* Check the DMA Instance DMAx and Channel parameters*/
157   assert_param(IS_LL_DMA_ALL_CHANNEL_INSTANCE(DMAx, Channel) || (Channel == LL_DMA_CHANNEL_ALL));
158 
159   if (Channel == LL_DMA_CHANNEL_ALL)
160   {
161     if (DMAx == DMA1)
162     {
163       /* Force reset of DMA clock */
164       LL_AHB1_GRP1_ForceReset(LL_AHB1_GRP1_PERIPH_DMA1);
165 
166       /* Release reset of DMA clock */
167       LL_AHB1_GRP1_ReleaseReset(LL_AHB1_GRP1_PERIPH_DMA1);
168     }
169 #if defined(DMA2)
170     else if (DMAx == DMA2)
171     {
172       /* Force reset of DMA clock */
173       LL_AHB1_GRP1_ForceReset(LL_AHB1_GRP1_PERIPH_DMA2);
174 
175       /* Release reset of DMA clock */
176       LL_AHB1_GRP1_ReleaseReset(LL_AHB1_GRP1_PERIPH_DMA2);
177     }
178 #endif
179     else
180     {
181       status = ERROR;
182     }
183   }
184   else
185   {
186     tmp = (DMA_Channel_TypeDef *)(__LL_DMA_GET_CHANNEL_INSTANCE(DMAx, Channel));
187 
188     /* Disable the selected DMAx_Channely */
189     CLEAR_BIT(tmp->CCR, DMA_CCR_EN);
190 
191     /* Reset DMAx_Channely control register */
192     LL_DMA_WriteReg(tmp, CCR, 0U);
193 
194     /* Reset DMAx_Channely remaining bytes register */
195     LL_DMA_WriteReg(tmp, CNDTR, 0U);
196 
197     /* Reset DMAx_Channely peripheral address register */
198     LL_DMA_WriteReg(tmp, CPAR, 0U);
199 
200     /* Reset DMAx_Channely memory address register */
201     LL_DMA_WriteReg(tmp, CMAR, 0U);
202 
203 
204     if (Channel == LL_DMA_CHANNEL_1)
205     {
206       /* Reset interrupt pending bits for DMAx Channel1 */
207       LL_DMA_ClearFlag_GI1(DMAx);
208     }
209     else if (Channel == LL_DMA_CHANNEL_2)
210     {
211       /* Reset interrupt pending bits for DMAx Channel2 */
212       LL_DMA_ClearFlag_GI2(DMAx);
213     }
214     else if (Channel == LL_DMA_CHANNEL_3)
215     {
216       /* Reset interrupt pending bits for DMAx Channel3 */
217       LL_DMA_ClearFlag_GI3(DMAx);
218     }
219     else if (Channel == LL_DMA_CHANNEL_4)
220     {
221       /* Reset interrupt pending bits for DMAx Channel4 */
222       LL_DMA_ClearFlag_GI4(DMAx);
223     }
224     else if (Channel == LL_DMA_CHANNEL_5)
225     {
226       /* Reset interrupt pending bits for DMAx Channel5 */
227       LL_DMA_ClearFlag_GI5(DMAx);
228     }
229 
230     else if (Channel == LL_DMA_CHANNEL_6)
231     {
232       /* Reset interrupt pending bits for DMAx Channel6 */
233       LL_DMA_ClearFlag_GI6(DMAx);
234     }
235     else if (Channel == LL_DMA_CHANNEL_7)
236     {
237       /* Reset interrupt pending bits for DMAx Channel7 */
238       LL_DMA_ClearFlag_GI7(DMAx);
239     }
240     else
241     {
242       status = ERROR;
243     }
244   }
245 
246   return status;
247 }
248 
249 /**
250   * @brief  Initialize the DMA registers according to the specified parameters in DMA_InitStruct.
251   * @note   To convert DMAx_Channely Instance to DMAx Instance and Channely, use helper macros :
252   *         @arg @ref __LL_DMA_GET_INSTANCE
253   *         @arg @ref __LL_DMA_GET_CHANNEL
254   * @param  DMAx DMAx Instance
255   * @param  Channel This parameter can be one of the following values:
256   *         @arg @ref LL_DMA_CHANNEL_1
257   *         @arg @ref LL_DMA_CHANNEL_2
258   *         @arg @ref LL_DMA_CHANNEL_3
259   *         @arg @ref LL_DMA_CHANNEL_4
260   *         @arg @ref LL_DMA_CHANNEL_5
261   *         @arg @ref LL_DMA_CHANNEL_6
262   *         @arg @ref LL_DMA_CHANNEL_7
263   * @param  DMA_InitStruct pointer to a @ref LL_DMA_InitTypeDef structure.
264   * @retval An ErrorStatus enumeration value:
265   *          - SUCCESS: DMA registers are initialized
266   *          - ERROR: Not applicable
267   */
LL_DMA_Init(DMA_TypeDef * DMAx,uint32_t Channel,LL_DMA_InitTypeDef * DMA_InitStruct)268 uint32_t LL_DMA_Init(DMA_TypeDef *DMAx, uint32_t Channel, LL_DMA_InitTypeDef *DMA_InitStruct)
269 {
270   /* Check the DMA Instance DMAx and Channel parameters*/
271   assert_param(IS_LL_DMA_ALL_CHANNEL_INSTANCE(DMAx, Channel));
272 
273   /* Check the DMA parameters from DMA_InitStruct */
274   assert_param(IS_LL_DMA_DIRECTION(DMA_InitStruct->Direction));
275   assert_param(IS_LL_DMA_MODE(DMA_InitStruct->Mode));
276   assert_param(IS_LL_DMA_PERIPHINCMODE(DMA_InitStruct->PeriphOrM2MSrcIncMode));
277   assert_param(IS_LL_DMA_MEMORYINCMODE(DMA_InitStruct->MemoryOrM2MDstIncMode));
278   assert_param(IS_LL_DMA_PERIPHDATASIZE(DMA_InitStruct->PeriphOrM2MSrcDataSize));
279   assert_param(IS_LL_DMA_MEMORYDATASIZE(DMA_InitStruct->MemoryOrM2MDstDataSize));
280   assert_param(IS_LL_DMA_NBDATA(DMA_InitStruct->NbData));
281   assert_param(IS_LL_DMA_PRIORITY(DMA_InitStruct->Priority));
282 
283   /*---------------------------- DMAx CCR Configuration ------------------------
284    * Configure DMAx_Channely: data transfer direction, data transfer mode,
285    *                          peripheral and memory increment mode,
286    *                          data size alignment and  priority level with parameters :
287    * - Direction:      DMA_CCR_DIR and DMA_CCR_MEM2MEM bits
288    * - Mode:           DMA_CCR_CIRC bit
289    * - PeriphOrM2MSrcIncMode:  DMA_CCR_PINC bit
290    * - MemoryOrM2MDstIncMode:  DMA_CCR_MINC bit
291    * - PeriphOrM2MSrcDataSize: DMA_CCR_PSIZE[1:0] bits
292    * - MemoryOrM2MDstDataSize: DMA_CCR_MSIZE[1:0] bits
293    * - Priority:               DMA_CCR_PL[1:0] bits
294    */
295   LL_DMA_ConfigTransfer(DMAx, Channel, DMA_InitStruct->Direction              | \
296                         DMA_InitStruct->Mode                   | \
297                         DMA_InitStruct->PeriphOrM2MSrcIncMode  | \
298                         DMA_InitStruct->MemoryOrM2MDstIncMode  | \
299                         DMA_InitStruct->PeriphOrM2MSrcDataSize | \
300                         DMA_InitStruct->MemoryOrM2MDstDataSize | \
301                         DMA_InitStruct->Priority);
302 
303   /*-------------------------- DMAx CMAR Configuration -------------------------
304    * Configure the memory or destination base address with parameter :
305    * - MemoryOrM2MDstAddress: DMA_CMAR_MA[31:0] bits
306    */
307   LL_DMA_SetMemoryAddress(DMAx, Channel, DMA_InitStruct->MemoryOrM2MDstAddress);
308 
309   /*-------------------------- DMAx CPAR Configuration -------------------------
310    * Configure the peripheral or source base address with parameter :
311    * - PeriphOrM2MSrcAddress: DMA_CPAR_PA[31:0] bits
312    */
313   LL_DMA_SetPeriphAddress(DMAx, Channel, DMA_InitStruct->PeriphOrM2MSrcAddress);
314 
315   /*--------------------------- DMAx CNDTR Configuration -----------------------
316    * Configure the peripheral base address with parameter :
317    * - NbData: DMA_CNDTR_NDT[15:0] bits
318    */
319   LL_DMA_SetDataLength(DMAx, Channel, DMA_InitStruct->NbData);
320 
321 
322   return SUCCESS;
323 }
324 
325 /**
326   * @brief  Set each @ref LL_DMA_InitTypeDef field to default value.
327   * @param  DMA_InitStruct Pointer to a @ref LL_DMA_InitTypeDef structure.
328   * @retval None
329   */
LL_DMA_StructInit(LL_DMA_InitTypeDef * DMA_InitStruct)330 void LL_DMA_StructInit(LL_DMA_InitTypeDef *DMA_InitStruct)
331 {
332   /* Set DMA_InitStruct fields to default values */
333   DMA_InitStruct->PeriphOrM2MSrcAddress  = 0x00000000U;
334   DMA_InitStruct->MemoryOrM2MDstAddress  = 0x00000000U;
335   DMA_InitStruct->Direction              = LL_DMA_DIRECTION_PERIPH_TO_MEMORY;
336   DMA_InitStruct->Mode                   = LL_DMA_MODE_NORMAL;
337   DMA_InitStruct->PeriphOrM2MSrcIncMode  = LL_DMA_PERIPH_NOINCREMENT;
338   DMA_InitStruct->MemoryOrM2MDstIncMode  = LL_DMA_MEMORY_NOINCREMENT;
339   DMA_InitStruct->PeriphOrM2MSrcDataSize = LL_DMA_PDATAALIGN_BYTE;
340   DMA_InitStruct->MemoryOrM2MDstDataSize = LL_DMA_MDATAALIGN_BYTE;
341   DMA_InitStruct->NbData                 = 0x00000000U;
342   DMA_InitStruct->Priority               = LL_DMA_PRIORITY_LOW;
343 }
344 
345 /**
346   * @}
347   */
348 
349 /**
350   * @}
351   */
352 
353 /**
354   * @}
355   */
356 
357 #endif /* DMA1 || DMA2 */
358 
359 /**
360   * @}
361   */
362 
363 #endif /* USE_FULL_LL_DRIVER */
364 
365 /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/
366