hal_dma.c 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319
  1. ////////////////////////////////////////////////////////////////////////////////
  2. /// @file hal_dma.c
  3. /// @author AE TEAM
  4. /// @brief THIS FILE PROVIDES ALL THE DMA FIRMWARE FUNCTIONS.
  5. ////////////////////////////////////////////////////////////////////////////////
  6. /// @attention
  7. ///
  8. /// THE EXISTING FIRMWARE IS ONLY FOR REFERENCE, WHICH IS DESIGNED TO PROVIDE
  9. /// CUSTOMERS WITH CODING INFORMATION ABOUT THEIR PRODUCTS SO THEY CAN SAVE
  10. /// TIME. THEREFORE, MINDMOTION SHALL NOT BE LIABLE FOR ANY DIRECT, INDIRECT OR
  11. /// CONSEQUENTIAL DAMAGES ABOUT ANY CLAIMS ARISING OUT OF THE CONTENT OF SUCH
  12. /// HARDWARE AND/OR THE USE OF THE CODING INFORMATION CONTAINED HEREIN IN
  13. /// CONNECTION WITH PRODUCTS MADE BY CUSTOMERS.
  14. ///
  15. /// <H2><CENTER>&COPY; COPYRIGHT MINDMOTION </CENTER></H2>
  16. ////////////////////////////////////////////////////////////////////////////////
  17. // Define to prevent recursive inclusion
  18. #define _HAL_DMA_C_
  19. // Files includes
  20. #include "types.h"
  21. #include "hal_dma.h"
  22. ////////////////////////////////////////////////////////////////////////////////
  23. /// @addtogroup MM32_Hardware_Abstract_Layer
  24. /// @{
  25. ////////////////////////////////////////////////////////////////////////////////
  26. /// @addtogroup DMA_HAL
  27. /// @{
  28. ////////////////////////////////////////////////////////////////////////////////
  29. /// @addtogroup DMA_Exported_Functions
  30. /// @{
  31. ////////////////////////////////////////////////////////////////////////////////
  32. /// @brief Deinitializes the DMA Channeln registers to their default reset
  33. /// values.
  34. /// @param select the DMA Channel.
  35. /// @retval None.
  36. ////////////////////////////////////////////////////////////////////////////////
  37. void DMA_DeInit(DMA_Channel_TypeDef* channel)
  38. {
  39. channel->CCR &= ~DMA_CCR_EN;
  40. channel->CCR = 0;
  41. channel->CNDTR = 0;
  42. channel->CPAR = 0;
  43. channel->CMAR = 0;
  44. if((*(vu32*)&channel) >= (*(vu32*)DMA2_Channel1_BASE)) {
  45. DMA2->IFCR |= (u32)0x0F << (((*(vu32*)&channel & (u32)0xff) - 8) / 5);
  46. }
  47. else {
  48. DMA1->IFCR |= (u32)0x0F << (((*(vu32*)&channel & (u32)0xff) - 8) / 5);
  49. }
  50. }
  51. ////////////////////////////////////////////////////////////////////////////////
  52. /// @brief Initializes the DMA Channeln according to the specified
  53. /// parameters in the init_struct.
  54. /// @param select the DMA Channel.
  55. /// @param init_struct: pointer to a DMA_InitTypeDef structure that
  56. /// contains the configuration information for the specified DMA
  57. /// Channel.
  58. /// @retval None.
  59. ////////////////////////////////////////////////////////////////////////////////
  60. void DMA_Init(DMA_Channel_TypeDef* channel, DMA_InitTypeDef* init_struct)
  61. {
  62. MODIFY_REG(
  63. channel->CCR,
  64. (DMA_CCR_DIR | DMA_CCR_CIRC | DMA_CCR_PINC | DMA_CCR_MINC | DMA_CCR_PSIZE | DMA_CCR_MSIZE | DMA_CCR_PL | DMA_CCR_M2M),
  65. ((u32)init_struct->DMA_DIR | (u32)init_struct->DMA_Mode | (u32)init_struct->DMA_PeripheralInc |
  66. (u32)init_struct->DMA_MemoryInc | (u32)init_struct->DMA_PeripheralDataSize | (u32)init_struct->DMA_MemoryDataSize |
  67. (u32)init_struct->DMA_Priority | (u32)init_struct->DMA_M2M));
  68. MODIFY_REG(channel->CCR, DMA_CCR_ARE, init_struct->DMA_Auto_reload);
  69. channel->CNDTR = init_struct->DMA_BufferSize;
  70. channel->CPAR = init_struct->DMA_PeripheralBaseAddr;
  71. channel->CMAR = init_struct->DMA_MemoryBaseAddr;
  72. }
  73. ////////////////////////////////////////////////////////////////////////////////
  74. /// @brief Fills each init_struct member with its default value.
  75. /// @param init_struct : pointer to a DMA_InitTypeDef structure which will
  76. /// be initialized.
  77. /// @retval None.
  78. ////////////////////////////////////////////////////////////////////////////////
  79. void DMA_StructInit(DMA_InitTypeDef* init_struct)
  80. {
  81. init_struct->DMA_PeripheralBaseAddr = 0;
  82. init_struct->DMA_MemoryBaseAddr = 0;
  83. init_struct->DMA_DIR = DMA_DIR_PeripheralSRC;
  84. init_struct->DMA_BufferSize = 0;
  85. init_struct->DMA_PeripheralInc = DMA_PeripheralInc_Disable;
  86. init_struct->DMA_MemoryInc = DMA_MemoryInc_Disable;
  87. init_struct->DMA_PeripheralDataSize = DMA_PeripheralDataSize_Byte;
  88. init_struct->DMA_MemoryDataSize = DMA_MemoryDataSize_Byte;
  89. init_struct->DMA_Mode = DMA_Mode_Normal;
  90. init_struct->DMA_Priority = DMA_Priority_Low;
  91. init_struct->DMA_M2M = DMA_M2M_Disable;
  92. init_struct->DMA_Auto_reload = DMA_Auto_Reload_Disable;
  93. }
  94. ////////////////////////////////////////////////////////////////////////////////
  95. /// @brief Enables or disables the specified DMA Channeln.
  96. /// @param channel: select the DMA Channel.
  97. /// @param state: new state of the DMA Channeln.
  98. /// This parameter can be: ENABLE or DISABLE.
  99. /// @retval None.
  100. ////////////////////////////////////////////////////////////////////////////////
  101. void DMA_Cmd(DMA_Channel_TypeDef* channel, FunctionalState state)
  102. {
  103. MODIFY_REG(channel->CCR, DMA_CCR_EN, state << DMA_CCR_EN_Pos);
  104. }
  105. ////////////////////////////////////////////////////////////////////////////////
  106. /// @brief Enables or disables the specified DMA Channeln interrupts.
  107. /// @param channel: select the DMA Channel.
  108. /// @param it: specifies the DMA interrupts sources to be enabled
  109. /// or disabled.
  110. /// This parameter can be any combination of the following values:
  111. /// @arg DMA_IT_TC: Transfer complete interrupt mask
  112. /// @arg DMA_IT_HT: Half transfer interrupt mask
  113. /// @arg DMA_IT_TE: Transfer error interrupt mask
  114. /// @param state: new state of the specified DMA interrupts.
  115. /// This parameter can be: ENABLE or DISABLE.
  116. /// @retval None.
  117. ////////////////////////////////////////////////////////////////////////////////
  118. void DMA_ITConfig(DMA_Channel_TypeDef* channel, DMA_Interrupt_EN_TypeDef it, FunctionalState state)
  119. {
  120. (state) ? (channel->CCR |= it) : (channel->CCR &= ~it);
  121. }
  122. ////////////////////////////////////////////////////////////////////////////////
  123. /// @brief Sets the number of data units in the select the DMA Channel .
  124. /// @param channel: select the DMA Channel
  125. /// @param DataNumber: The number of data units in the current DMAy Channelx
  126. /// transfer.
  127. /// @note This function can only be used when the DMAy_Channelx is disabled.
  128. /// @retval None.
  129. ////////////////////////////////////////////////////////////////////////////////
  130. void DMA_SetCurrDataCounter(DMA_Channel_TypeDef* channel, u16 length)
  131. {
  132. channel->CNDTR = length;
  133. }
  134. ////////////////////////////////////////////////////////////////////////////////
  135. /// @brief Returns the number of remaining data units in the current
  136. /// DMA Channeln transfer.
  137. /// @param channel: select the DMA Channel.
  138. /// @retval The number of remaining data units in the current DMA Channeln
  139. /// transfer.
  140. ////////////////////////////////////////////////////////////////////////////////
  141. u16 DMA_GetCurrDataCounter(DMA_Channel_TypeDef* channel)
  142. {
  143. return channel->CNDTR;
  144. }
  145. ////////////////////////////////////////////////////////////////////////////////
  146. /// @brief Checks whether the specified DMA Channeln flag is set or not.
  147. /// @param flag: specifies the flag to check.
  148. /// This parameter can be one of the following values:
  149. /// @arg DMA1_FLAG_GLn: DMA1 Channeln global flag(n = 1..7).
  150. /// @arg DMA1_FLAG_TCn: DMA1 Channeln transfer complete flag(n = 1..7).
  151. /// @arg DMA1_FLAG_HTn: DMA1 Channeln half transfer flag(n = 1..7).
  152. /// @arg DMA1_FLAG_TEn: DMA1 Channeln transfer error flag(n = 1..7).
  153. /// @arg DMA2_FLAG_GLn: DMA1 Channeln global flag(n = 1..5).
  154. /// @arg DMA2_FLAG_TCn: DMA1 Channeln transfer complete flag(n = 1..5).
  155. /// @arg DMA2_FLAG_HTn: DMA1 Channeln half transfer flag(n = 1..5).
  156. /// @arg DMA2_FLAG_TEn: DMA1 Channeln transfer error flag(n = 1..5).
  157. /// @retval The new state of DMAy_FLAG (SET or RESET).
  158. ////////////////////////////////////////////////////////////////////////////////
  159. FlagStatus DMA_GetFlagStatus(DMA_Flags_TypeDef flag)
  160. {
  161. if(flag >= DMA2_FLAG_GL1 ) {
  162. return (DMA2->ISR & flag) ? SET : RESET;
  163. }
  164. return (DMA1->ISR & flag) ? SET : RESET;
  165. }
  166. ////////////////////////////////////////////////////////////////////////////////
  167. /// @brief Clears the DMA Channeln's pending flags.
  168. /// @param flag: specifies the flag to clear.
  169. /// This parameter can be any combination (for the same DMA) of the
  170. /// following values:
  171. /// @arg DMA1_FLAG_GLn: DMA1 Channeln global flag(n = 1..7).
  172. /// @arg DMA1_FLAG_TCn: DMA1 Channeln transfer complete flag(n = 1..7).
  173. /// @arg DMA1_FLAG_HTn: DMA1 Channeln half transfer flag(n = 1..7).
  174. /// @arg DMA1_FLAG_TEn: DMA1 Channeln transfer error flag(n = 1..7).
  175. /// @arg DMA2_FLAG_GLn: DMA1 Channeln global flag(n = 1..5).
  176. /// @arg DMA2_FLAG_TCn: DMA1 Channeln transfer complete flag(n = 1..5).
  177. /// @arg DMA2_FLAG_HTn: DMA1 Channeln half transfer flag(n = 1..5).
  178. /// @arg DMA2_FLAG_TEn: DMA1 Channeln transfer error flag(n = 1..5).
  179. /// @retval None.
  180. ////////////////////////////////////////////////////////////////////////////////
  181. void DMA_ClearFlag(DMA_Flags_TypeDef flag)
  182. {
  183. if(flag >= DMA2_FLAG_GL1 ) {
  184. DMA2->IFCR = flag;
  185. return ;
  186. }
  187. DMA1->IFCR = flag;
  188. }
  189. ////////////////////////////////////////////////////////////////////////////////
  190. /// @brief Checks whether the specified DMA Channeln interrupt has occurred or
  191. /// not.
  192. /// @param it: specifies the DMA interrupt source to check.
  193. /// This parameter can be one of the following values:
  194. /// @arg DMA1_IT_GLn: DMA1 Channeln global interrupt(n = 1..7).
  195. /// @arg DMA1_IT_TCn: DMA1 Channeln transfer complete interrupt(n = 1..7).
  196. /// @arg DMA1_IT_HTn: DMA1 Channeln half transfer interrupt(n = 1..7).
  197. /// @arg DMA1_IT_TEn: DMA1 Channeln transfer error interrupt(n = 1..7).
  198. /// @arg DMA2_IT_GLn: DMA1 Channeln global flag(n = 1..5).
  199. /// @arg DMA2_IT_TCn: DMA1 Channeln transfer complete flag(n = 1..5).
  200. /// @arg DMA2_IT_HTn: DMA1 Channeln half transfer flag(n = 1..5).
  201. /// @arg DMA2_IT_TEn: DMA1 Channeln transfer error flag(n = 1..5).
  202. /// @retval The new state of DMAy_IT (SET or RESET).
  203. ////////////////////////////////////////////////////////////////////////////////
  204. ITStatus DMA_GetITStatus(DMA_Interrupts_TypeDef it)
  205. {
  206. if(it >= DMA2_IT_GL1 ) {
  207. return (DMA2->ISR & it) ? SET : RESET;
  208. }
  209. return (DMA1->ISR & it) ? SET : RESET;
  210. }
  211. ////////////////////////////////////////////////////////////////////////////////
  212. /// @brief Clears the DMA Channeln's interrupt pending bits.
  213. /// @param it: specifies the DMA interrupt pending bit to clear.
  214. /// This parameter can be any combination (for the same DMA) of the
  215. /// following values:
  216. /// @arg DMA1_IT_GLn: DMA1 Channeln global interrupt(n = 1..7).
  217. /// @arg DMA1_IT_TCn: DMA1 Channeln transfer complete interrupt(n = 1..7).
  218. /// @arg DMA1_IT_HTn: DMA1 Channeln half transfer interrupt(n = 1..7).
  219. /// @arg DMA1_IT_TEn: DMA1 Channeln transfer error interrupt(n = 1..7).
  220. /// @arg DMA2_IT_GLn: DMA1 Channeln global flag(n = 1..5).
  221. /// @arg DMA2_IT_TCn: DMA1 Channeln transfer complete flag(n = 1..5).
  222. /// @arg DMA2_IT_HTn: DMA1 Channeln half transfer flag(n = 1..5).
  223. /// @arg DMA2_IT_TEn: DMA1 Channeln transfer error flag(n = 1..5).
  224. /// @retval None.
  225. ////////////////////////////////////////////////////////////////////////////////
  226. void DMA_ClearITPendingBit(DMA_Interrupts_TypeDef it)
  227. {
  228. if(it >= DMA2_IT_GL1 ) {
  229. DMA2->IFCR = it;
  230. return ;
  231. }
  232. DMA1->IFCR = it;
  233. }
  234. ////////////////////////////////////////////////////////////////////////////////
  235. /// @brief Set the DMA Channeln's Peripheral address.
  236. /// @param channel : where n can be 1 to 7 for DMA1 to select the DMA Channel.
  237. /// @param address : DMA Peripheral address.
  238. /// @retval None.
  239. ////////////////////////////////////////////////////////////////////////////////
  240. void exDMA_SetPeripheralAddress(DMA_Channel_TypeDef* channel, u32 address)
  241. {
  242. channel->CPAR = address;
  243. }
  244. ////////////////////////////////////////////////////////////////////////////////
  245. /// @brief Set the DMA Channeln's Peripheral address.
  246. /// @param channel : select the DMA Channel.
  247. /// @param length : Transmit lengths.
  248. /// @retval None.
  249. ////////////////////////////////////////////////////////////////////////////////
  250. void exDMA_SetTransmitLen(DMA_Channel_TypeDef* channel, u16 length)
  251. {
  252. channel->CNDTR = length;
  253. }
  254. ////////////////////////////////////////////////////////////////////////////////
  255. /// @brief Set the DMA Channeln's Peripheral address.
  256. /// @param channel :select the DMA Channel.
  257. /// @param address : DMA memery address.
  258. /// @retval None.
  259. ////////////////////////////////////////////////////////////////////////////////
  260. void exDMA_SetMemoryAddress(DMA_Channel_TypeDef* channel, u32 address)
  261. {
  262. channel->CMAR = address;
  263. }
  264. ////////////////////////////////////////////////////////////////////////////////
  265. /// @brief Clears the DMA Channeln's interrupt pending bits.
  266. /// @param it: specifies the DMA interrupt pending bit to clear.
  267. /// This parameter can be any combination (for the same DMA) of the
  268. /// following values:
  269. /// @arg DMA1_IT_GLn: DMA1 Channeln global interrupt(n = 1..7).
  270. /// @arg DMA1_IT_TCn: DMA1 Channeln transfer complete interrupt(n = 1..7).
  271. /// @arg DMA1_IT_HTn: DMA1 Channeln half transfer interrupt(n = 1..7).
  272. /// @arg DMA1_IT_TEn: DMA1 Channeln transfer error interrupt(n = 1..7).
  273. /// @arg DMA2_IT_GLn: DMA1 Channeln global flag(n = 1..5).
  274. /// @arg DMA2_IT_TCn: DMA1 Channeln transfer complete flag(n = 1..5).
  275. /// @arg DMA2_IT_HTn: DMA1 Channeln half transfer flag(n = 1..5).
  276. /// @arg DMA2_IT_TEn: DMA1 Channeln transfer error flag(n = 1..5).
  277. /// @retval None.
  278. ////////////////////////////////////////////////////////////////////////////////
  279. void exDMA_ClearITPendingBit(DMA_Channel_TypeDef* channel, u32 it)
  280. {
  281. if(it >= DMA2_IT_GL1 ) {
  282. DMA2->IFCR |= (u32)0x0F << (((*(vu32*)&channel & (u32)0xff) - 8) / 5);
  283. DMA2->IFCR = it;
  284. return ;
  285. }
  286. DMA1->IFCR |= (u32)0x0F << (((*(vu32*)&channel & (u32)0xff) - 8) / 5);
  287. DMA1->IFCR = it;
  288. }
  289. /// @}
  290. /// @}
  291. /// @}