diff --git a/driver/CMakeLists.txt b/driver/CMakeLists.txt index b712714..5b686c2 100644 --- a/driver/CMakeLists.txt +++ b/driver/CMakeLists.txt @@ -7,6 +7,7 @@ src/sio.c src/gpio.c src/pio.c src/timer.c +src/dma.c ) set(TARGET driver) diff --git a/driver/inc/dma.h b/driver/inc/dma.h new file mode 100644 index 0000000..bb491b7 --- /dev/null +++ b/driver/inc/dma.h @@ -0,0 +1,185 @@ +#ifndef __HARDWARE_DMA_H__ +#define __HARDWARE_DMA_H__ + +#include "reg.h" +#include "dma_reg.h" + +#define DMA_CHANNEL_0 (0) +#define DMA_CHANNEL_1 (1) +#define DMA_CHANNEL_2 (2) +#define DMA_CHANNEL_3 (3) +#define DMA_CHANNEL_4 (4) +#define DMA_CHANNEL_5 (5) +#define DMA_CHANNEL_6 (6) +#define DMA_CHANNEL_7 (7) +#define DMA_CHANNEL_8 (8) +#define DMA_CHANNEL_9 (9) +#define DMA_CHANNEL_10 (10) +#define DMA_CHANNEL_11 (11) +#define DMA_CHANNEL_MAX (12) +#define DMA_CHANNEL_MASK ((1 << DMA_CHANNEL_MAX) - 1) + +#define DMA_INT_GROUP_0 (0) +#define DMA_INT_GROUP_1 (1) + +#define DMA_REQ_PIO0_TX0 (0) +#define DMA_REQ_PIO0_TX1 (1) +#define DMA_REQ_PIO0_TX2 (2) +#define DMA_REQ_PIO0_TX3 (3) +#define DMA_REQ_PIO0_RX0 (4) +#define DMA_REQ_PIO0_RX1 (5) +#define DMA_REQ_PIO0_RX2 (6) +#define DMA_REQ_PIO0_RX3 (7) +#define DMA_REQ_PIO1_TX0 (8) +#define DMA_REQ_PIO1_TX1 (9) +#define DMA_REQ_PIO1_TX2 (10) +#define DMA_REQ_PIO1_TX3 (11) +#define DMA_REQ_PIO1_RX0 (12) +#define DMA_REQ_PIO1_RX1 (13) +#define DMA_REQ_PIO1_RX2 (14) +#define DMA_REQ_PIO1_RX3 (15) +#define DMA_REQ_SPI0_TX (16) +#define DMA_REQ_SPI0_RX (17) +#define DMA_REQ_SPI1_TX (18) +#define DMA_REQ_SPI1_RX (19) +#define DMA_REQ_UART0_TX (20) +#define DMA_REQ_UART0_RX (21) +#define DMA_REQ_UART1_TX (22) +#define DMA_REQ_UART1_RX (23) +#define DMA_REQ_PWM_WRAP0 (24) +#define DMA_REQ_PWM_WRAP1 (25) +#define DMA_REQ_PWM_WRAP2 (26) +#define DMA_REQ_PWM_WRAP3 (27) +#define DMA_REQ_PWM_WRAP4 (28) +#define DMA_REQ_PWM_WRAP5 (29) +#define DMA_REQ_PWM_WRAP6 (30) +#define DMA_REQ_PWM_WRAP7 (31) +#define DMA_REQ_I2C0_TX (32) +#define DMA_REQ_I2C0_RX (33) +#define DMA_REQ_I2C1_TX (34) +#define DMA_REQ_I2C1_RX (35) +#define DMA_REQ_ADC (36) +#define DMA_REQ_XIP_STREAM (37) +#define DMA_REQ_XIP_SSITX (38) +#define DMA_REQ_XIP_SSIRX (39) +#define DMA_REQ_TIMER_0 (0x3B) +#define DMA_REQ_TIMER_1 (0x3C) +#define DMA_REQ_TIMER_2 (0x3D) +#define DMA_REQ_TIMER_3 (0x3E) +#define DMA_REQ_FOREVER (0x3F) + +#define DMA_DATA_SIZE_8BIT (0) +#define DMA_DATA_SIZE_16BIT (1) +#define DMA_DATA_SIZE_32BIT (2) + +#define DMA_RING_SIZE_NONE (0) +#define DMA_RING_SIZE_2B (1) +#define DMA_RING_SIZE_4B (2) +#define DMA_RING_SIZE_8B (3) +#define DMA_RING_SIZE_16B (4) +#define DMA_RING_SIZE_32B (5) +#define DMA_RING_SIZE_64B (6) +#define DMA_RING_SIZE_128B (7) +#define DMA_RING_SIZE_256B (8) +#define DMA_RING_SIZE_512B (9) +#define DMA_RING_SIZE_1kB (10) +#define DMA_RING_SIZE_2kB (11) +#define DMA_RING_SIZE_4kB (12) +#define DMA_RING_SIZE_8kB (13) +#define DMA_RING_SIZE_16kB (14) +#define DMA_RING_SIZE_32kB (15) + +#define DMA_SNIFF_CALC_CRC32 (0) +#define DMA_SNIFF_CALC_CRC32_BITREV (1) +#define DMA_SNIFF_CALC_CRC16_CCITT (2) +#define DMA_SNIFF_CALC_CRC16_CCITT_BITREV (3) +#define DMA_SNIFF_CALC_EVEN_CHECKSUM (14) +#define DMA_SNIFF_CALC_SUM32 (15) + +union dma_ctrl_s { + struct { + uint32_t en : 1; /* [ 0], r/w */ + uint32_t high_priority : 1; /* [ 1], r/w */ + uint32_t data_size : 2; /* [ 3: 2], r/w */ + uint32_t incr_read : 1; /* [ 4], r/w */ + uint32_t incr_write : 1; /* [ 5], r/w */ + uint32_t ring_size : 4; /* [ 9: 6], r/w */ + uint32_t ring_sel_write : 1; /* [ 10], r/w */ + uint32_t chain_to : 4; /* [14:11], r/w */ + uint32_t request : 6; /* [20:15], r/w */ + uint32_t irq_quiet : 1; /* [ 21], r/w */ + uint32_t byte_swap : 1; /* [ 22], r/w */ + uint32_t sniff_en : 1; /* [ 23], r/w */ + uint32_t busy : 1; /* [ 24], ro */ + uint32_t reserved : 4; /* [28:25], reserved */ + uint32_t error_write : 1; /* [ 29], wc */ + uint32_t error_read : 1; /* [ 30], wc */ + uint32_t error_ahb : 1; /* [ 31], ro */ + } bits; + uint32_t word; +}; + +struct dma_cfg_s { + uint32_t read_addr; + uint32_t write_addr; + uint32_t trans_count; + // union dma_ctrl_s ctrl; + uint8_t channel; + uint8_t request; + uint8_t data_size; + uint8_t incr_read; + uint8_t incr_write; + uint8_t irq_quiet; + uint8_t byte_swap; + uint8_t chain_to; + uint8_t high_priority; + uint8_t ring_sel_write; + uint8_t ring_size; + uint8_t sniff_en; +}; + +struct dma_sniff_cfg_s { + uint8_t channel; + uint8_t calc; + uint8_t byte_swap; + uint8_t out_rev; /* bit = ~bit */ + uint8_t out_inv; /* bit31-0 -> bit0-31 */ +}; + +#ifdef __cplusplus +extern "C" { +#endif + +void dma_init(struct dma_cfg_s *cfg); +void dma_enable_and_trig(uint8_t ch); +void dma_disable(uint8_t ch); +void dma_trig_multi(uint16_t chs); +void dma_abort_multi(uint16_t chs); + +void dma_read_addr_update(uint8_t ch, uint32_t addr); +void dma_write_addr_update(uint8_t ch, uint32_t addr); +void dma_trans_count_update(uint8_t ch, uint8_t count); +uint32_t dma_trans_count_remain_get(uint8_t ch); + +void dma_timer_set(uint8_t ch, uint16_t x, uint16_t y); + +void dma_sniff_init(struct dma_sniff_cfg_s *cfg); +void dma_sniff_enable(void); +void dma_sniff_disable(void); +void dma_sniff_write(uint32_t seed); +uint32_t dma_sniff_read(void); + +uint32_t dma_int_get_raw_status(void); +void dma_int_clear_raw_status(uint32_t chs); +uint32_t dma_int_get_status(uint8_t int_group); +void dma_int_clear(uint8_t group, uint32_t chs); +void dma_int_enable(uint8_t int_group, uint32_t chs); +void dma_int_disable(uint8_t int_group, uint32_t chs); +void dma_int_force(uint8_t int_group, uint32_t chs); +void dma_int_deforce(uint8_t int_group, uint32_t chs); + +#ifdef __cplusplus +} +#endif + +#endif /* __HARDWARE_DMA_H__ */ diff --git a/driver/inc/reg/dma_reg.h b/driver/inc/reg/dma_reg.h new file mode 100644 index 0000000..e55c5cf --- /dev/null +++ b/driver/inc/reg/dma_reg.h @@ -0,0 +1,84 @@ +#ifndef __HARDWARE_DMA_REG_H__ +#define __HARDWARE_DMA_REG_H__ + +#define DMA_CH0_READ_ADDR_OFFSET (0x000) +#define DMA_CH0_WRITE_ADDR_OFFSET (0x004) +#define DMA_CH0_TRANS_COUNT_OFFSET (0x008) +#define DMA_CH0_CTRL_TRIG_OFFSET (0x00C) +#define DMA_CH1_READ_ADDR_OFFSET (0x040) +#define DMA_CH1_WRITE_ADDR_OFFSET (0x044) +#define DMA_CH1_TRANS_COUNT_OFFSET (0x048) +#define DMA_CH1_CTRL_TRIG_OFFSET (0x04C) +#define DMA_INTR_OFFSET (0x400) +#define DMA_INTE0_OFFSET (0x404) +#define DMA_INTF0_OFFSET (0x408) +#define DMA_INTS0_OFFSET (0x40C) +#define DMA_INTE1_OFFSET (0x414) +#define DMA_INTF1_OFFSET (0x418) +#define DMA_INTS1_OFFSET (0x41C) +#define DMA_TIMER0_OFFSET (0x420) +#define DMA_TIMER1_OFFSET (0x424) +#define DMA_TIMER2_OFFSET (0x428) +#define DMA_TIMER3_OFFSET (0x42C) +#define DMA_MULTI_CHAN_TRIGGER_OFFSET (0x430) +#define DMA_SNIFF_CTRL_OFFSET (0x434) +#define DMA_SNIFF_DATA_OFFSET (0x438) +#define DMA_FIFO_LEVELS_OFFSET (0x440) +#define DMA_CHAN_ABORT_OFFSET (0x444) +#define DMA_N_CHANNELS_OFFSET (0x448) + +/* DMA_CHx_CTRL_TRIG_OFFSET @0x00C */ +#define DMA_CTRL_EN (1 << 0U) +#define DMA_CTRL_HIGH_PRIORITY (1 << 0U) +#define DMA_CTRL_DATA_SIZE_POS (2U) +#define DMA_CTRL_DATA_SIZE_MASK (0x3 << DMA_CTRL_DATA_SIZE_POS) +#define DMA_CTRL_INCR_READ (1 << 4U) +#define DMA_CTRL_INCR_WRITE (1 << 5U) +#define DMA_CTRL_RING_SIZE_POS (6U) +#define DMA_CTRL_RING_SIZE_MASK (0xF << DMA_CTRL_RING_SIZE_POS) +#define DMA_CTRL_RING_SEL_WRITE (1 << 10U) +#define DMA_CTRL_CHAIN_TO_POS (11U) +#define DMA_CTRL_CHAIN_TO_MASK (0xF << DMA_CTRL_CHAIN_TO_POS) +#define DMA_CTRL_TREQ_SEL_POS (15U) +#define DMA_CTRL_TREQ_SEL_MASK (0x3F << DMA_CTRL_TREQ_SEL_POS) +#define DMA_CTRL_IRQ_QUIET (1 << 21U) +#define DMA_CTRL_BSWAP (1 << 22U) +#define DMA_CTRL_SNIFF_EN (1 << 23U) +#define DMA_CTRL_BUSY (1 << 24U) +#define DMA_CTRL_WRITE_ERROR (1 << 29U) +#define DMA_CTRL_READ_ERROR (1 << 30U) +#define DMA_CTRL_AHB_ERROR (1 << 31U) + +/* DMA_TIMERx_OFFSET @0x420/0x424/0x428/0x42C */ +#define DMA_TIMER_Y_POS (0U) +#define DMA_TIMER_Y_MASK (0xFFFF << DMA_TIMER_Y_POS) +#define DMA_TIMER_X_POS (16U) +#define DMA_TIMER_X_MASK (0xFFFF << DMA_TIMER_X_POS) + +/* DMA_SNIFF_CTRL_OFFSET @0x434 */ +#define DMA_SNIFF_EN (1 << 0U) +#define DMA_SNIFF_DMACH_POS (1U) +#define DMA_SNIFF_DMACH_MASK (0xF << DMA_SNIFF_DMACH_POS) +#define DMA_SNIFF_CALC_POS (5U) +#define DMA_SNIFF_CALC_MASK (0xF << DMA_SNIFF_CALC_POS) +#define DMA_SNIFF_BSWAP (1 << 9U) +#define DMA_SNIFF_OUT_REV (1 << 10U) +#define DMA_SNIFF_OUT_INV (1 << 11U) + +/* DMA_FIFO_LEVELS_OFFSET @0x440 */ +#define DMA_TDF_LVL_POS (0U) +#define DMA_TDF_LVL_MASK (0xFF << DMA_TDF_LVL_POS) +#define DMA_TAF_LVL_POS (8U) +#define DMA_TAF_LVL_MASK (0xFF << DMA_TAF_LVL_POS) +#define DMA_RAF_LVL_POS (16U) +#define DMA_RAF_LVL_MASK (0xFF << DMA_RAF_LVL_POS) + +#ifdef __cplusplus +extern "C" { +#endif + +#ifdef __cplusplus +} +#endif + +#endif /* __HARDWARE_DMA_REG_H__ */ diff --git a/driver/src/dma.c b/driver/src/dma.c new file mode 100644 index 0000000..1550bf6 --- /dev/null +++ b/driver/src/dma.c @@ -0,0 +1,249 @@ +#include "dma.h" + +void dma_init(struct dma_cfg_s *cfg) +{ + uint32_t val; + uint8_t ch; + + ch = cfg->channel; + /* step1: disable this channel */ + val = getreg32(DMA_BASE + DMA_CH0_CTRL_TRIG_OFFSET + (DMA_CH1_CTRL_TRIG_OFFSET - DMA_CH0_CTRL_TRIG_OFFSET) * ch); + val &= ~DMA_CTRL_EN; + putreg32(val, DMA_BASE + DMA_CH0_CTRL_TRIG_OFFSET + (DMA_CH1_CTRL_TRIG_OFFSET - DMA_CH0_CTRL_TRIG_OFFSET) * ch); + /* step2: config read address */ + putreg32(cfg->read_addr, DMA_BASE + DMA_CH0_READ_ADDR_OFFSET + (DMA_CH1_READ_ADDR_OFFSET - DMA_CH0_READ_ADDR_OFFSET) * ch); + /* step3: config write address */ + putreg32(cfg->write_addr, DMA_BASE + DMA_CH0_WRITE_ADDR_OFFSET + (DMA_CH1_WRITE_ADDR_OFFSET - DMA_CH0_WRITE_ADDR_OFFSET) * ch); + /* step4: config transfer count */ + putreg32(cfg->trans_count, DMA_BASE + DMA_CH0_TRANS_COUNT_OFFSET + (DMA_CH1_TRANS_COUNT_OFFSET - DMA_CH0_TRANS_COUNT_OFFSET) * ch); + /* step5: config others */ + val = getreg32(DMA_BASE + DMA_CH0_CTRL_TRIG_OFFSET + (DMA_CH1_CTRL_TRIG_OFFSET - DMA_CH0_CTRL_TRIG_OFFSET) * ch); + val &= ~DMA_CTRL_EN; + if (cfg->high_priority) { + val |= DMA_CTRL_HIGH_PRIORITY; + } else { + val &= ~DMA_CTRL_HIGH_PRIORITY; + } + val &= ~DMA_CTRL_DATA_SIZE_MASK; + val |= (cfg->data_size << DMA_CTRL_DATA_SIZE_POS); + if (cfg->incr_read) { + val |= DMA_CTRL_INCR_READ; + } else { + val &= ~DMA_CTRL_INCR_READ; + } + if (cfg->incr_write) { + val |= DMA_CTRL_INCR_WRITE; + } else { + val &= ~DMA_CTRL_INCR_WRITE; + } + val &= ~DMA_CTRL_RING_SIZE_MASK; + val |= (cfg->ring_size << DMA_CTRL_RING_SIZE_POS); + if (cfg->ring_sel_write) { + val |= DMA_CTRL_RING_SEL_WRITE; + } else { + val &= ~DMA_CTRL_RING_SEL_WRITE; + } + val &= ~DMA_CTRL_CHAIN_TO_MASK; + val |= (cfg->chain_to << DMA_CTRL_CHAIN_TO_POS); + val &= ~DMA_CTRL_TREQ_SEL_MASK; + val |= (cfg->request << DMA_CTRL_TREQ_SEL_POS); + if (cfg->irq_quiet) { + val |= DMA_CTRL_IRQ_QUIET; + } else { + val &= ~DMA_CTRL_IRQ_QUIET; + } + if (cfg->byte_swap) { + val |= DMA_CTRL_BSWAP; + } else { + val &= ~DMA_CTRL_BSWAP; + } + if (cfg->sniff_en) { + val |= DMA_CTRL_SNIFF_EN; + } else { + val &= ~DMA_CTRL_SNIFF_EN; + } + val |= DMA_CTRL_WRITE_ERROR; + val |= DMA_CTRL_READ_ERROR; + putreg32(val, DMA_BASE + DMA_CH0_CTRL_TRIG_OFFSET + (DMA_CH1_CTRL_TRIG_OFFSET - DMA_CH0_CTRL_TRIG_OFFSET) * ch); +} + +void dma_enable_and_trig(uint8_t ch) +{ + uint32_t val; + + val = getreg32(DMA_BASE + DMA_CH0_CTRL_TRIG_OFFSET + (DMA_CH1_CTRL_TRIG_OFFSET - DMA_CH0_CTRL_TRIG_OFFSET) * ch); + val |= DMA_CTRL_EN; + putreg32(val, DMA_BASE + DMA_CH0_CTRL_TRIG_OFFSET + (DMA_CH1_CTRL_TRIG_OFFSET - DMA_CH0_CTRL_TRIG_OFFSET) * ch); +} + +void dma_disable(uint8_t ch) +{ + uint32_t val; + + val = getreg32(DMA_BASE + DMA_CH0_CTRL_TRIG_OFFSET + (DMA_CH1_CTRL_TRIG_OFFSET - DMA_CH0_CTRL_TRIG_OFFSET) * ch); + val &= ~DMA_CTRL_EN; + putreg32(val, DMA_BASE + DMA_CH0_CTRL_TRIG_OFFSET + (DMA_CH1_CTRL_TRIG_OFFSET - DMA_CH0_CTRL_TRIG_OFFSET) * ch); +} + +void dma_trig_multi(uint16_t chs) +{ + putreg32(chs, DMA_BASE + DMA_MULTI_CHAN_TRIGGER_OFFSET); +} + +void dma_abort_multi(uint16_t chs) +{ + uint32_t val; + + putreg32(chs, DMA_BASE + DMA_CHAN_ABORT_OFFSET); + while (1) { + val = getreg32(DMA_BASE + DMA_CHAN_ABORT_OFFSET); + val &= chs; + if (val == 0) { + break; + } + } +} + +void dma_read_addr_update(uint8_t ch, uint32_t addr) +{ + putreg32(addr, DMA_BASE + DMA_CH0_READ_ADDR_OFFSET + (DMA_CH1_READ_ADDR_OFFSET - DMA_CH0_READ_ADDR_OFFSET) * ch); +} + +void dma_write_addr_update(uint8_t ch, uint32_t addr) +{ + putreg32(addr, DMA_BASE + DMA_CH0_WRITE_ADDR_OFFSET + (DMA_CH1_WRITE_ADDR_OFFSET - DMA_CH0_WRITE_ADDR_OFFSET) * ch); +} + +void dma_trans_count_update(uint8_t ch, uint8_t count) +{ + putreg32(count, DMA_BASE + DMA_CH0_TRANS_COUNT_OFFSET + (DMA_CH1_TRANS_COUNT_OFFSET - DMA_CH0_TRANS_COUNT_OFFSET) * ch); +} + +uint32_t dma_trans_count_remain_get(uint8_t ch) +{ + return getreg32(DMA_BASE + DMA_CH0_TRANS_COUNT_OFFSET + (DMA_CH1_TRANS_COUNT_OFFSET - DMA_CH0_TRANS_COUNT_OFFSET) * ch); +} + +void dma_timer_set(uint8_t ch, uint16_t x, uint16_t y) +{ + uint32_t val; + + val = getreg32(DMA_BASE + DMA_TIMER0_OFFSET + (DMA_TIMER1_OFFSET - DMA_TIMER0_OFFSET) * ch); + val &= ~DMA_TIMER_X_MASK; + val |= (x << DMA_TIMER_X_POS); + val &= ~DMA_TIMER_Y_MASK; + val |= (y << DMA_TIMER_Y_POS); + putreg32(val, DMA_BASE + DMA_TIMER0_OFFSET + (DMA_TIMER1_OFFSET - DMA_TIMER0_OFFSET) * ch); +} + +void dma_sniff_init(struct dma_sniff_cfg_s *cfg) +{ + uint32_t val; + + val = getreg32(DMA_BASE + DMA_SNIFF_CTRL_OFFSET); + val &= ~DMA_SNIFF_EN; + val &= ~DMA_SNIFF_DMACH_MASK; + val |= (cfg->channel << DMA_SNIFF_DMACH_POS); + val &= ~DMA_SNIFF_CALC_MASK; + val |= (cfg->calc << DMA_SNIFF_CALC_POS); + if (cfg->byte_swap) { + val |= DMA_SNIFF_BSWAP; + } else { + val &= ~DMA_SNIFF_BSWAP; + } + if (cfg->out_rev) { + val |= DMA_SNIFF_OUT_REV; + } else { + val &= ~DMA_SNIFF_OUT_REV; + } + if (cfg->out_inv) { + val |= DMA_SNIFF_OUT_INV; + } else { + val &= ~DMA_SNIFF_OUT_INV; + } + putreg32(val, DMA_BASE + DMA_SNIFF_CTRL_OFFSET); +} + +void dma_sniff_enable(void) +{ + uint32_t val; + + val = getreg32(DMA_BASE + DMA_SNIFF_CTRL_OFFSET); + val |= DMA_SNIFF_EN; + putreg32(val, DMA_BASE + DMA_SNIFF_CTRL_OFFSET); +} + +void dma_sniff_disable(void) +{ + uint32_t val; + + val = getreg32(DMA_BASE + DMA_SNIFF_CTRL_OFFSET); + val &= ~DMA_SNIFF_EN; + putreg32(val, DMA_BASE + DMA_SNIFF_CTRL_OFFSET); +} + +void dma_sniff_write(uint32_t seed) +{ + putreg32(seed, DMA_BASE + DMA_SNIFF_DATA_OFFSET); +} + +uint32_t dma_sniff_read(void) +{ + return getreg32(DMA_BASE + DMA_SNIFF_DATA_OFFSET); +} + +uint32_t dma_int_get_raw_status(void) +{ + return getreg32(DMA_BASE + DMA_INTR_OFFSET) & DMA_CHANNEL_MASK; +} + +void dma_int_clear_raw_status(uint32_t chs) +{ + putreg32(chs & DMA_CHANNEL_MASK, DMA_BASE + DMA_INTR_OFFSET); +} + +uint32_t dma_int_get_status(uint8_t int_group) +{ + return getreg32(DMA_BASE + DMA_INTS0_OFFSET + (DMA_INTS1_OFFSET - DMA_INTS0_OFFSET) * int_group) & DMA_CHANNEL_MASK; +} + +void dma_int_clear(uint8_t int_group, uint32_t chs) +{ + putreg32(chs, DMA_BASE + DMA_INTS0_OFFSET + (DMA_INTS1_OFFSET - DMA_INTS0_OFFSET) * int_group); +} + +void dma_int_enable(uint8_t int_group, uint32_t chs) +{ + uint32_t val; + + val = getreg32(DMA_BASE + DMA_INTE0_OFFSET + (DMA_INTE1_OFFSET - DMA_INTE0_OFFSET) * int_group); + val |= (chs & DMA_CHANNEL_MASK); + putreg32(val, DMA_BASE + DMA_INTE0_OFFSET + (DMA_INTE1_OFFSET - DMA_INTE0_OFFSET) * int_group); +} + +void dma_int_disable(uint8_t int_group, uint32_t chs) +{ + uint32_t val; + + val = getreg32(DMA_BASE + DMA_INTE0_OFFSET + (DMA_INTE1_OFFSET - DMA_INTE0_OFFSET) * int_group); + val &= ~(chs & DMA_CHANNEL_MASK); + putreg32(val, DMA_BASE + DMA_INTE0_OFFSET + (DMA_INTE1_OFFSET - DMA_INTE0_OFFSET) * int_group); +} + +void dma_int_force(uint8_t int_group, uint32_t chs) +{ + uint32_t val; + + val = getreg32(DMA_BASE + DMA_INTF0_OFFSET + (DMA_INTF1_OFFSET - DMA_INTF0_OFFSET) * int_group); + val |= (chs & DMA_CHANNEL_MASK); + putreg32(val, DMA_BASE + DMA_INTF0_OFFSET + (DMA_INTF1_OFFSET - DMA_INTF0_OFFSET) * int_group); +} + +void dma_int_deforce(uint8_t int_group, uint32_t chs) +{ + uint32_t val; + + val = getreg32(DMA_BASE + DMA_INTF0_OFFSET + (DMA_INTF1_OFFSET - DMA_INTF0_OFFSET) * int_group); + val &= ~(chs & DMA_CHANNEL_MASK); + putreg32(val, DMA_BASE + DMA_INTF0_OFFSET + (DMA_INTF1_OFFSET - DMA_INTF0_OFFSET) * int_group); +}