STM32-Zombie-0.2.0: src/App/TimerDMA.hs
----------------------------------------------------------------------------
-- |
-- Module : App.TimerDMA
-- Copyright : (c) Marc Fontaine 2017
-- License : BSD3
--
-- Maintainer : Marc.Fontaine@gmx.de
-- Stability : experimental
-- Portability : GHC-only
--
-- This example show the combination of hardware timers with hardware DMA.
-- Timer 4 triggers DMA1_Channel7 and the DMA writes data to the USART.
-- Instead of the USART its also possible to write to any other peripheral.
-- Applications are wave-form-generation or hard-real-time control.
module App.TimerDMA
where
import Control.Monad
import STM32.API
import qualified STM32.USART as USART
import STM32.DMA as DMA
import STM32.Timer as Timer
import Data.ByteString.Char8 as BS (pack)
sendCommTimer :: IO ()
sendCommTimer
= runMI $ sendCommTimer_Port USART.stm32F103_UartPort1 USART.defaultConfig
-- only works for USART.stm32F103_UartPort1 at the moment
sendCommTimer_Port :: USART.UartPort -> USART.Config -> MI ()
sendCommTimer_Port port config = do
initMI
resetHalt
USART.configure port config
let dmaBuffer = 0x20001000
dmaConfig = DMA.Config {
_BufferSize = 16
,_Direction = PeripheralDST
,_MemoryBaseAddr = dmaBuffer
,_MemoryDataSize = Byte
,_MemoryInc = True
,DMA._Mode = Circular
,_PeripheralBaseAddr = regToAddr USART1 DR
,_PeripheralDataSize = Byte
,_PeripheralInc = False
,_Priority = Low
}
peripheralClockOn DMA1
peripheralClockOn TIM4
DMA.deInit DMA1_Channel7
writeMem8 dmaBuffer $ BS.pack "abcdefghABCD123\n"
DMA.disable DMA1_Channel7
DMA.init DMA1_Channel7 dmaConfig
DMA.enable DMA1_Channel7
let timeBase = TimeBase {
_Prescaler = 7200 -- 72 Mhz clock _Period counts in 0.1 ms
,_CounterMode = Down
,_Period = 10000 -- 1s
,_ClockDevision = CKD_DIV1
,_RepetitionCounter =0
}
Timer.deInit TIM4
Timer.timeBaseInit TIM4 timeBase
bitReset TIM4 CR1_URS
bitSet TIM4 DIER_UDE
bitSet TIM4 CR1_CEN