diff --git a/drivers/dma.c b/drivers/dma.c index 0e7f98f..1cb0f03 100644 --- a/drivers/dma.c +++ b/drivers/dma.c @@ -13,21 +13,22 @@ #include "nvic.h" #include "rcc.h" +#include "stddef.h" + //--local definitions----------------------------------------------------------- static void configure_dma(volatile struct DMA* dma, enum DmaChannel channel, enum DmaConfig config_mask, void* periph, void* mem, uint16_t size); -static uint32_t periph_regs(enum DmaPeriph periph, volatile struct DMA** regs); //--local variables------------------------------------------------------------- static volatile struct DMA* const dma1 = (struct DMA*)DMA1_BASE_ADDRESS; static volatile struct DMA* const dma2 = (struct DMA*)DMA2_BASE_ADDRESS; -static DmaCallback dm1_callbacks[7]; -static DmaCallback dm2_callbacks[5]; +static DmaCallback dma1_callbacks[7]; +static DmaCallback dma2_callbacks[5]; //--public functions------------------------------------------------------------ @@ -44,7 +45,7 @@ void dma_configure(enum DmaPeriph dma, enum DmaChannel channel, rcc_enable(RCC_AHB_DMA1, RCC_APB1_NONE, RCC_APB2_NONE); configure_dma(dma1, channel, config_mask, periph, mem, size); if (callback) { - dm1_callbacks[channel] = callback; + dma1_callbacks[channel] = callback; nvic_enable(NVIC_IRQ_DMA1_CHANNEL1 + channel); } break; @@ -52,7 +53,7 @@ void dma_configure(enum DmaPeriph dma, enum DmaChannel channel, rcc_enable(RCC_AHB_DMA2, RCC_APB1_NONE, RCC_APB2_NONE); configure_dma(dma2, channel, config_mask, periph, mem, size); if (callback) { - dm2_callbacks[channel] = callback; + dma2_callbacks[channel] = callback; nvic_enable(NVIC_IRQ_DMA2_CHANNEL1 + channel); } break; @@ -69,10 +70,12 @@ void dma_reset(enum DmaPeriph dma, enum DmaChannel channel) switch (dma) { case DMA_PERIPH_1: periph = dma1; + dma1_callbacks[channel] = NULL; nvic_disable(NVIC_IRQ_DMA1_CHANNEL1 + channel); break; case DMA_PERIPH_2: periph = dma2; + dma2_callbacks[channel] = NULL; nvic_disable(NVIC_IRQ_DMA2_CHANNEL1 + channel); break; default: @@ -88,6 +91,48 @@ void dma_reset(enum DmaPeriph dma, enum DmaChannel channel) regs->CPAR = 0; } +void dma_enable(enum DmaPeriph dma, enum DmaChannel channel) +{ + switch (dma) { + case DMA_PERIPH_1: + reg_set(dma1->CHANNELS[channel].CCR, DMA_CCR_EN); + if (dma1_callbacks[channel]) { + nvic_enable(NVIC_IRQ_DMA1_CHANNEL1 + channel); + } + break; + case DMA_PERIPH_2: + reg_set(dma2->CHANNELS[channel].CCR, DMA_CCR_EN); + if (dma2_callbacks[channel]) { + nvic_enable(NVIC_IRQ_DMA2_CHANNEL1 + channel); + } + break; + default: + return; + break; + } +} + +void dma_disable(enum DmaPeriph dma, enum DmaChannel channel) +{ + switch (dma) { + case DMA_PERIPH_1: + reg_reset(dma1->CHANNELS[channel].CCR, DMA_CCR_EN); + if (dma1_callbacks[channel]) { + nvic_disable(NVIC_IRQ_DMA1_CHANNEL1 + channel); + } + break; + case DMA_PERIPH_2: + reg_reset(dma2->CHANNELS[channel].CCR, DMA_CCR_EN); + if (dma2_callbacks[channel]) { + nvic_disable(NVIC_IRQ_DMA2_CHANNEL1 + channel); + } + break; + default: + return; + break; + } +} + //--local functions------------------------------------------------------------- @@ -107,23 +152,6 @@ static void configure_dma(volatile struct DMA* dma, enum DmaChannel channel, reg_set(regs->CCR, DMA_CCR_EN); } -static uint32_t periph_regs(enum DmaPeriph periph, volatile struct DMA** regs) -{ - switch (periph) { - case DMA_PERIPH_1: - *regs = dma1; - break; - case DMA_PERIPH_2: - *regs = dma2; - break; - default: - return 1; - break; - } - - return 0; -} - //--ISRs------------------------------------------------------------------------ @@ -134,7 +162,7 @@ void hdr_dma1_channel1(void) enum DmaIRQSource src = (dma1->IFCR.word >> 1) & 0x7; reg_set(dma1->IFCR, DMA_IFCR_CGIF1); - dm1_callbacks[0](src); + dma1_callbacks[0](src); } void hdr_dma1_channel2(void) @@ -144,7 +172,7 @@ void hdr_dma1_channel2(void) enum DmaIRQSource src = (dma1->IFCR.word >> 5) & 0x7; reg_set(dma1->IFCR, DMA_IFCR_CGIF2); - dm1_callbacks[1](src); + dma1_callbacks[1](src); } void hdr_dma1_channel3(void) @@ -154,7 +182,7 @@ void hdr_dma1_channel3(void) enum DmaIRQSource src = (dma1->IFCR.word >> 9) & 0x7; reg_set(dma1->IFCR, DMA_IFCR_CGIF3); - dm1_callbacks[2](src); + dma1_callbacks[2](src); } void hdr_dma1_channel4(void) @@ -164,7 +192,7 @@ void hdr_dma1_channel4(void) enum DmaIRQSource src = (dma1->IFCR.word >> 13) & 0x7; reg_set(dma1->IFCR, DMA_IFCR_CGIF4); - dm1_callbacks[3](src); + dma1_callbacks[3](src); } void hdr_dma1_channel5(void) @@ -174,7 +202,7 @@ void hdr_dma1_channel5(void) enum DmaIRQSource src = (dma1->IFCR.word >> 17) & 0x7; reg_set(dma1->IFCR, DMA_IFCR_CGIF5); - dm1_callbacks[4](src); + dma1_callbacks[4](src); } void hdr_dma1_channel6(void) @@ -184,7 +212,7 @@ void hdr_dma1_channel6(void) enum DmaIRQSource src = (dma1->IFCR.word >> 21) & 0x7; reg_set(dma1->IFCR, DMA_IFCR_CGIF6); - dm1_callbacks[5](src); + dma1_callbacks[5](src); } void hdr_dma1_channel7(void) @@ -194,7 +222,7 @@ void hdr_dma1_channel7(void) enum DmaIRQSource src = (dma1->IFCR.word >> 25) & 0x7; reg_set(dma1->IFCR, DMA_IFCR_CGIF7); - dm1_callbacks[6](src); + dma1_callbacks[6](src); } void hdr_dma2_channel1(void) @@ -204,7 +232,7 @@ void hdr_dma2_channel1(void) enum DmaIRQSource src = (dma2->IFCR.word >> 1) & 0x7; reg_set(dma2->IFCR, DMA_IFCR_CGIF1); - dm1_callbacks[0](src); + dma1_callbacks[0](src); } void hdr_dma2_channel2(void) @@ -214,7 +242,7 @@ void hdr_dma2_channel2(void) enum DmaIRQSource src = (dma2->IFCR.word >> 5) & 0x7; reg_set(dma2->IFCR, DMA_IFCR_CGIF2); - dm2_callbacks[1](src); + dma2_callbacks[1](src); } void hdr_dma2_channel3(void) @@ -224,7 +252,7 @@ void hdr_dma2_channel3(void) enum DmaIRQSource src = (dma2->IFCR.word >> 9) & 0x7; reg_set(dma2->IFCR, DMA_IFCR_CGIF3); - dm2_callbacks[2](src); + dma2_callbacks[2](src); } void hdr_dma2_channel4_5(void) @@ -234,13 +262,13 @@ void hdr_dma2_channel4_5(void) enum DmaIRQSource src = (dma2->IFCR.word >> 13) & 0x7; if (src != 0) { reg_set(dma2->IFCR, DMA_IFCR_CGIF4); - dm1_callbacks[3](src); + dma1_callbacks[3](src); } src = (dma2->IFCR.word >> 17) & 0x7; if (src != 0) { reg_set(dma2->IFCR, DMA_IFCR_CGIF5); - dm1_callbacks[4](src); + dma1_callbacks[4](src); } }