1 /**
2   ******************************************************************************
3   * @file    stm32f1xx_ll_dma.c
4   * @author  MCD Application Team
5   * @brief   DMA LL module driver.
6   ******************************************************************************
7   * @attention
8   *
9   * Copyright (c) 2016 STMicroelectronics.
10   * All rights reserved.
11   *
12   * This software is licensed under terms that can be found in the LICENSE file in
13   * the root directory of this software component.
14   * If no LICENSE file comes with this software, it is provided AS-IS.
15   *
16   ******************************************************************************
17   */
18 
19 #if defined(USE_FULL_LL_DRIVER)
20 
21 /* Includes ------------------------------------------------------------------*/
22 #include "stm32f1xx_ll_dma.h"
23 #include "stm32f1xx_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 STM32F1xx_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 #define IS_LL_DMA_PRIORITY(__VALUE__)           (((__VALUE__) == LL_DMA_PRIORITY_LOW)    || \
71                                                  ((__VALUE__) == LL_DMA_PRIORITY_MEDIUM) || \
72                                                  ((__VALUE__) == LL_DMA_PRIORITY_HIGH)   || \
73                                                  ((__VALUE__) == LL_DMA_PRIORITY_VERYHIGH))
74 
75 #if defined (DMA2)
76 #define IS_LL_DMA_ALL_CHANNEL_INSTANCE(INSTANCE, CHANNEL)  ((((INSTANCE) == DMA1) && \
77                                                             (((CHANNEL) == LL_DMA_CHANNEL_1) || \
78                                                              ((CHANNEL) == LL_DMA_CHANNEL_2) || \
79                                                              ((CHANNEL) == LL_DMA_CHANNEL_3) || \
80                                                              ((CHANNEL) == LL_DMA_CHANNEL_4) || \
81                                                              ((CHANNEL) == LL_DMA_CHANNEL_5) || \
82                                                              ((CHANNEL) == LL_DMA_CHANNEL_6) || \
83                                                              ((CHANNEL) == LL_DMA_CHANNEL_7))) || \
84                                                             (((INSTANCE) == DMA2) && \
85                                                             (((CHANNEL) == LL_DMA_CHANNEL_1) || \
86                                                              ((CHANNEL) == LL_DMA_CHANNEL_2) || \
87                                                              ((CHANNEL) == LL_DMA_CHANNEL_3) || \
88                                                              ((CHANNEL) == LL_DMA_CHANNEL_4) || \
89                                                              ((CHANNEL) == LL_DMA_CHANNEL_5))))
90 #else
91 #define IS_LL_DMA_ALL_CHANNEL_INSTANCE(INSTANCE, CHANNEL)  ((((INSTANCE) == DMA1) && \
92                                                             (((CHANNEL) == LL_DMA_CHANNEL_1) || \
93                                                              ((CHANNEL) == LL_DMA_CHANNEL_2) || \
94                                                              ((CHANNEL) == LL_DMA_CHANNEL_3) || \
95                                                              ((CHANNEL) == LL_DMA_CHANNEL_4) || \
96                                                              ((CHANNEL) == LL_DMA_CHANNEL_5) || \
97                                                              ((CHANNEL) == LL_DMA_CHANNEL_6) || \
98                                                              ((CHANNEL) == LL_DMA_CHANNEL_7))))
99 #endif
100 /**
101   * @}
102   */
103 
104 /* Private function prototypes -----------------------------------------------*/
105 /* Exported functions --------------------------------------------------------*/
106 /** @addtogroup DMA_LL_Exported_Functions
107   * @{
108   */
109 
110 /** @addtogroup DMA_LL_EF_Init
111   * @{
112   */
113 
114 /**
115   * @brief  De-initialize the DMA registers to their default reset values.
116   * @param  DMAx DMAx Instance
117   * @param  Channel This parameter can be one of the following values:
118   *         @arg @ref LL_DMA_CHANNEL_1
119   *         @arg @ref LL_DMA_CHANNEL_2
120   *         @arg @ref LL_DMA_CHANNEL_3
121   *         @arg @ref LL_DMA_CHANNEL_4
122   *         @arg @ref LL_DMA_CHANNEL_5
123   *         @arg @ref LL_DMA_CHANNEL_6
124   *         @arg @ref LL_DMA_CHANNEL_7
125   * @retval An ErrorStatus enumeration value:
126   *          - SUCCESS: DMA registers are de-initialized
127   *          - ERROR: DMA registers are not de-initialized
128   */
LL_DMA_DeInit(DMA_TypeDef * DMAx,uint32_t Channel)129 uint32_t LL_DMA_DeInit(DMA_TypeDef *DMAx, uint32_t Channel)
130 {
131   DMA_Channel_TypeDef *tmp = (DMA_Channel_TypeDef *)DMA1_Channel1;
132   ErrorStatus status = SUCCESS;
133 
134   /* Check the DMA Instance DMAx and Channel parameters*/
135   assert_param(IS_LL_DMA_ALL_CHANNEL_INSTANCE(DMAx, Channel));
136 
137   tmp = (DMA_Channel_TypeDef *)(__LL_DMA_GET_CHANNEL_INSTANCE(DMAx, Channel));
138 
139   /* Disable the selected DMAx_Channely */
140   CLEAR_BIT(tmp->CCR, DMA_CCR_EN);
141 
142   /* Reset DMAx_Channely control register */
143   LL_DMA_WriteReg(tmp, CCR, 0U);
144 
145   /* Reset DMAx_Channely remaining bytes register */
146   LL_DMA_WriteReg(tmp, CNDTR, 0U);
147 
148   /* Reset DMAx_Channely peripheral address register */
149   LL_DMA_WriteReg(tmp, CPAR, 0U);
150 
151   /* Reset DMAx_Channely memory address register */
152   LL_DMA_WriteReg(tmp, CMAR, 0U);
153 
154   if (Channel == LL_DMA_CHANNEL_1)
155   {
156     /* Reset interrupt pending bits for DMAx Channel1 */
157     LL_DMA_ClearFlag_GI1(DMAx);
158   }
159   else if (Channel == LL_DMA_CHANNEL_2)
160   {
161     /* Reset interrupt pending bits for DMAx Channel2 */
162     LL_DMA_ClearFlag_GI2(DMAx);
163   }
164   else if (Channel == LL_DMA_CHANNEL_3)
165   {
166     /* Reset interrupt pending bits for DMAx Channel3 */
167     LL_DMA_ClearFlag_GI3(DMAx);
168   }
169   else if (Channel == LL_DMA_CHANNEL_4)
170   {
171     /* Reset interrupt pending bits for DMAx Channel4 */
172     LL_DMA_ClearFlag_GI4(DMAx);
173   }
174   else if (Channel == LL_DMA_CHANNEL_5)
175   {
176     /* Reset interrupt pending bits for DMAx Channel5 */
177     LL_DMA_ClearFlag_GI5(DMAx);
178   }
179 
180   else if (Channel == LL_DMA_CHANNEL_6)
181   {
182     /* Reset interrupt pending bits for DMAx Channel6 */
183     LL_DMA_ClearFlag_GI6(DMAx);
184   }
185   else if (Channel == LL_DMA_CHANNEL_7)
186   {
187     /* Reset interrupt pending bits for DMAx Channel7 */
188     LL_DMA_ClearFlag_GI7(DMAx);
189   }
190   else
191   {
192     status = ERROR;
193   }
194 
195   return status;
196 }
197 
198 /**
199   * @brief  Initialize the DMA registers according to the specified parameters in DMA_InitStruct.
200   * @note   To convert DMAx_Channely Instance to DMAx Instance and Channely, use helper macros :
201   *         @arg @ref __LL_DMA_GET_INSTANCE
202   *         @arg @ref __LL_DMA_GET_CHANNEL
203   * @param  DMAx DMAx Instance
204   * @param  Channel This parameter can be one of the following values:
205   *         @arg @ref LL_DMA_CHANNEL_1
206   *         @arg @ref LL_DMA_CHANNEL_2
207   *         @arg @ref LL_DMA_CHANNEL_3
208   *         @arg @ref LL_DMA_CHANNEL_4
209   *         @arg @ref LL_DMA_CHANNEL_5
210   *         @arg @ref LL_DMA_CHANNEL_6
211   *         @arg @ref LL_DMA_CHANNEL_7
212   * @param  DMA_InitStruct pointer to a @ref LL_DMA_InitTypeDef structure.
213   * @retval An ErrorStatus enumeration value:
214   *          - SUCCESS: DMA registers are initialized
215   *          - ERROR: Not applicable
216   */
LL_DMA_Init(DMA_TypeDef * DMAx,uint32_t Channel,LL_DMA_InitTypeDef * DMA_InitStruct)217 uint32_t LL_DMA_Init(DMA_TypeDef *DMAx, uint32_t Channel, LL_DMA_InitTypeDef *DMA_InitStruct)
218 {
219   /* Check the DMA Instance DMAx and Channel parameters*/
220   assert_param(IS_LL_DMA_ALL_CHANNEL_INSTANCE(DMAx, Channel));
221 
222   /* Check the DMA parameters from DMA_InitStruct */
223   assert_param(IS_LL_DMA_DIRECTION(DMA_InitStruct->Direction));
224   assert_param(IS_LL_DMA_MODE(DMA_InitStruct->Mode));
225   assert_param(IS_LL_DMA_PERIPHINCMODE(DMA_InitStruct->PeriphOrM2MSrcIncMode));
226   assert_param(IS_LL_DMA_MEMORYINCMODE(DMA_InitStruct->MemoryOrM2MDstIncMode));
227   assert_param(IS_LL_DMA_PERIPHDATASIZE(DMA_InitStruct->PeriphOrM2MSrcDataSize));
228   assert_param(IS_LL_DMA_MEMORYDATASIZE(DMA_InitStruct->MemoryOrM2MDstDataSize));
229   assert_param(IS_LL_DMA_NBDATA(DMA_InitStruct->NbData));
230   assert_param(IS_LL_DMA_PRIORITY(DMA_InitStruct->Priority));
231 
232   /*---------------------------- DMAx CCR Configuration ------------------------
233    * Configure DMAx_Channely: data transfer direction, data transfer mode,
234    *                          peripheral and memory increment mode,
235    *                          data size alignment and  priority level with parameters :
236    * - Direction:      DMA_CCR_DIR and DMA_CCR_MEM2MEM bits
237    * - Mode:           DMA_CCR_CIRC bit
238    * - PeriphOrM2MSrcIncMode:  DMA_CCR_PINC bit
239    * - MemoryOrM2MDstIncMode:  DMA_CCR_MINC bit
240    * - PeriphOrM2MSrcDataSize: DMA_CCR_PSIZE[1:0] bits
241    * - MemoryOrM2MDstDataSize: DMA_CCR_MSIZE[1:0] bits
242    * - Priority:               DMA_CCR_PL[1:0] bits
243    */
244   LL_DMA_ConfigTransfer(DMAx, Channel, DMA_InitStruct->Direction | \
245                         DMA_InitStruct->Mode                   | \
246                         DMA_InitStruct->PeriphOrM2MSrcIncMode  | \
247                         DMA_InitStruct->MemoryOrM2MDstIncMode  | \
248                         DMA_InitStruct->PeriphOrM2MSrcDataSize | \
249                         DMA_InitStruct->MemoryOrM2MDstDataSize | \
250                         DMA_InitStruct->Priority);
251 
252   /*-------------------------- DMAx CMAR Configuration -------------------------
253    * Configure the memory or destination base address with parameter :
254    * - MemoryOrM2MDstAddress: DMA_CMAR_MA[31:0] bits
255    */
256   LL_DMA_SetMemoryAddress(DMAx, Channel, DMA_InitStruct->MemoryOrM2MDstAddress);
257 
258   /*-------------------------- DMAx CPAR Configuration -------------------------
259    * Configure the peripheral or source base address with parameter :
260    * - PeriphOrM2MSrcAddress: DMA_CPAR_PA[31:0] bits
261    */
262   LL_DMA_SetPeriphAddress(DMAx, Channel, DMA_InitStruct->PeriphOrM2MSrcAddress);
263 
264   /*--------------------------- DMAx CNDTR Configuration -----------------------
265    * Configure the peripheral base address with parameter :
266    * - NbData: DMA_CNDTR_NDT[15:0] bits
267    */
268   LL_DMA_SetDataLength(DMAx, Channel, DMA_InitStruct->NbData);
269 
270   return SUCCESS;
271 }
272 
273 /**
274   * @brief  Set each @ref LL_DMA_InitTypeDef field to default value.
275   * @param  DMA_InitStruct Pointer to a @ref LL_DMA_InitTypeDef structure.
276   * @retval None
277   */
LL_DMA_StructInit(LL_DMA_InitTypeDef * DMA_InitStruct)278 void LL_DMA_StructInit(LL_DMA_InitTypeDef *DMA_InitStruct)
279 {
280   /* Set DMA_InitStruct fields to default values */
281   DMA_InitStruct->PeriphOrM2MSrcAddress  = 0x00000000U;
282   DMA_InitStruct->MemoryOrM2MDstAddress  = 0x00000000U;
283   DMA_InitStruct->Direction              = LL_DMA_DIRECTION_PERIPH_TO_MEMORY;
284   DMA_InitStruct->Mode                   = LL_DMA_MODE_NORMAL;
285   DMA_InitStruct->PeriphOrM2MSrcIncMode  = LL_DMA_PERIPH_NOINCREMENT;
286   DMA_InitStruct->MemoryOrM2MDstIncMode  = LL_DMA_MEMORY_NOINCREMENT;
287   DMA_InitStruct->PeriphOrM2MSrcDataSize = LL_DMA_PDATAALIGN_BYTE;
288   DMA_InitStruct->MemoryOrM2MDstDataSize = LL_DMA_MDATAALIGN_BYTE;
289   DMA_InitStruct->NbData                 = 0x00000000U;
290   DMA_InitStruct->Priority               = LL_DMA_PRIORITY_LOW;
291 }
292 
293 /**
294   * @}
295   */
296 
297 /**
298   * @}
299   */
300 
301 /**
302   * @}
303   */
304 
305 #endif /* DMA1 || DMA2 */
306 
307 /**
308   * @}
309   */
310 
311 #endif /* USE_FULL_LL_DRIVER */
312 
313