summaryrefslogtreecommitdiff
path: root/chip/stm32/dma.c
diff options
context:
space:
mode:
authorJack Rosenthal <jrosenth@chromium.org>2021-11-04 12:11:58 -0600
committerCommit Bot <commit-bot@chromium.org>2021-11-05 04:22:34 +0000
commit252457d4b21f46889eebad61d4c0a65331919cec (patch)
tree01856c4d31d710b20e85a74c8d7b5836e35c3b98 /chip/stm32/dma.c
parent08f5a1e6fc2c9467230444ac9b582dcf4d9f0068 (diff)
downloadchrome-ec-stabilize-14526.84.B-ish.tar.gz
In the interest of making long-term branch maintenance incur as little technical debt on us as possible, we should not maintain any files on the branch we are not actually using. This has the added effect of making it extremely clear when merging CLs from the main branch when changes have the possibility to affect us. The follow-on CL adds a convenience script to actually pull updates from the main branch and generate a CL for the update. BUG=b:204206272 BRANCH=ish TEST=make BOARD=arcada_ish && make BOARD=drallion_ish Signed-off-by: Jack Rosenthal <jrosenth@chromium.org> Change-Id: I17e4694c38219b5a0823e0a3e55a28d1348f4b18 Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/platform/ec/+/3262038 Reviewed-by: Jett Rink <jettrink@chromium.org> Reviewed-by: Tom Hughes <tomhughes@chromium.org>
Diffstat (limited to 'chip/stm32/dma.c')
-rw-r--r--chip/stm32/dma.c410
1 files changed, 0 insertions, 410 deletions
diff --git a/chip/stm32/dma.c b/chip/stm32/dma.c
deleted file mode 100644
index 55317ba003..0000000000
--- a/chip/stm32/dma.c
+++ /dev/null
@@ -1,410 +0,0 @@
-/* Copyright 2013 The Chromium OS Authors. All rights reserved.
- * Use of this source code is governed by a BSD-style license that can be
- * found in the LICENSE file.
- */
-
-#include "clock.h"
-#include "common.h"
-#include "console.h"
-#include "dma.h"
-#include "hooks.h"
-#include "registers.h"
-#include "task.h"
-#include "timer.h"
-#include "util.h"
-
-/* Console output macros */
-#define CPUTS(outstr) cputs(CC_DMA, outstr)
-#define CPRINTF(format, args...) cprintf(CC_DMA, format, ## args)
-
-/* Callback data to use when IRQ fires */
-static struct {
- void (*cb)(void *); /* Callback function to call */
- void *cb_data; /* Callback data for callback function */
-} dma_irq[STM32_DMAC_COUNT];
-
-
-/**
- * Return the IRQ for the DMA channel
- *
- * @param channel Channel number
- * @return IRQ for the channel
- */
-static int dma_get_irq(enum dma_channel channel)
-{
-#ifdef CHIP_FAMILY_STM32F0
- if (channel == STM32_DMAC_CH1)
- return STM32_IRQ_DMA_CHANNEL_1;
-
- return channel > STM32_DMAC_CH3 ?
- STM32_IRQ_DMA_CHANNEL_4_7 :
- STM32_IRQ_DMA_CHANNEL_2_3;
-#elif defined(CHIP_FAMILY_STM32L4)
- if (channel < STM32_DMAC_PER_CTLR)
- return STM32_IRQ_DMA_CHANNEL_1 + channel;
- else {
- if (channel <= STM32_DMAC_CH13)
- return STM32_IRQ_DMA2_CHANNEL1 +
- (channel - STM32_DMAC_PER_CTLR);
- else
- return STM32_IRQ_DMA2_CHANNEL6 +
- (channel - STM32_DMAC_PER_CTLR - 5);
- }
-#else
- if (channel < STM32_DMAC_PER_CTLR)
- return STM32_IRQ_DMA_CHANNEL_1 + channel;
- else
- return STM32_IRQ_DMA2_CHANNEL1 +
- (channel - STM32_DMAC_PER_CTLR);
-#endif
-}
-
-/*
- * Note, you must decrement the channel value by 1 from what is specified
- * in the datasheets, as they index from 1 and this indexes from 0!
- */
-stm32_dma_chan_t *dma_get_channel(enum dma_channel channel)
-{
- stm32_dma_regs_t *dma = STM32_DMA_REGS(channel);
-
- return &dma->chan[channel % STM32_DMAC_PER_CTLR];
-}
-
-#ifdef STM32_DMAMUX_CxCR
-void dma_select_channel(enum dma_channel channel, uint8_t req)
-{
- /*
- * STM32G4 includes a DMAMUX block which is used to handle dma requests
- * by peripherals. The correct 'req' number for a given peripheral is
- * given in ST doc RM0440.
- */
- STM32_DMAMUX_CxCR(channel) = req;
-}
-#elif defined(STM32_DMA_CSELR)
-void dma_select_channel(enum dma_channel channel, unsigned char stream)
-{
- /* Local channel # starting from 0 on each DMA controller */
- const unsigned char ch = channel % STM32_DMAC_PER_CTLR;
- const unsigned char shift = STM32_DMA_PERIPHERALS_PER_CHANNEL;
- const unsigned char mask = BIT(shift) - 1;
- uint32_t val;
-
- ASSERT(ch < STM32_DMAC_PER_CTLR);
- ASSERT(stream <= mask);
- val = STM32_DMA_CSELR(channel) & ~(mask << ch * shift);
- STM32_DMA_CSELR(channel) = val | (stream << ch * shift);
-}
-#endif /* STM32_DMAMUX_CxCR/STM32_DMA_CSELR */
-
-void dma_disable(enum dma_channel channel)
-{
- stm32_dma_chan_t *chan = dma_get_channel(channel);
-
- if (chan->ccr & STM32_DMA_CCR_EN)
- chan->ccr &= ~STM32_DMA_CCR_EN;
-}
-
-void dma_disable_all(void)
-{
- int ch;
-
- for (ch = 0; ch < STM32_DMAC_COUNT; ch++) {
- stm32_dma_chan_t *chan = dma_get_channel(ch);
-
- chan->ccr &= ~STM32_DMA_CCR_EN;
- }
-}
-
-/**
- * Prepare a channel for use and start it
- *
- * @param chan Channel to read
- * @param count Number of bytes to transfer
- * @param periph Pointer to peripheral data register
- * @param memory Pointer to memory address for receive/transmit
- * @param flags DMA flags for the control register, normally:
- * STM32_DMA_CCR_MINC | STM32_DMA_CCR_DIR for tx
- * 0 for rx
- */
-static void prepare_channel(enum dma_channel channel, unsigned int count,
- void *periph, void *memory, unsigned int flags)
-{
- stm32_dma_chan_t *chan = dma_get_channel(channel);
- uint32_t ccr = STM32_DMA_CCR_PL_VERY_HIGH;
-
- dma_disable(channel);
- dma_clear_isr(channel);
-
- /* Following the order in Doc ID 15965 Rev 5 p194 */
- chan->cpar = (uint32_t)periph;
- chan->cmar = (uint32_t)memory;
- chan->cndtr = count;
- chan->ccr = ccr;
- ccr |= flags;
- chan->ccr = ccr;
-}
-
-void dma_go(stm32_dma_chan_t *chan)
-{
- /* Flush data in write buffer so that DMA can get the latest data */
- asm volatile("dsb;");
-
- /* Fire it up */
- chan->ccr |= STM32_DMA_CCR_EN;
-}
-
-void dma_prepare_tx(const struct dma_option *option, unsigned int count,
- const void *memory)
-{
- /*
- * Cast away const for memory pointer; this is ok because we know
- * we're preparing the channel for transmit.
- */
- prepare_channel(option->channel, count, option->periph, (void *)memory,
- STM32_DMA_CCR_MINC | STM32_DMA_CCR_DIR |
- option->flags);
-}
-
-void dma_start_rx(const struct dma_option *option, unsigned int count,
- void *memory)
-{
- stm32_dma_chan_t *chan = dma_get_channel(option->channel);
-
- prepare_channel(option->channel, count, option->periph, memory,
- STM32_DMA_CCR_MINC | option->flags);
- dma_go(chan);
-}
-
-int dma_bytes_done(stm32_dma_chan_t *chan, int orig_count)
-{
- return orig_count - chan->cndtr;
-}
-
-bool dma_is_enabled(stm32_dma_chan_t *chan)
-{
- return (chan->ccr & STM32_DMA_CCR_EN);
-}
-
-#ifdef CONFIG_DMA_HELP
-void dma_dump(enum dma_channel channel)
-{
- stm32_dma_regs_t *dma = STM32_DMA_REGS(channel);
- stm32_dma_chan_t *chan = dma_get_channel(channel);
-
- CPRINTF("ccr=%x, cndtr=%x, cpar=%x, cmar=%x\n", chan->ccr,
- chan->cndtr, chan->cpar, chan->cmar);
- CPRINTF("chan %d, isr=%x, ifcr=%x\n",
- channel,
- (dma->isr >> ((channel % STM32_DMAC_PER_CTLR) * 4)) & 0xf,
- (dma->ifcr >> ((channel % STM32_DMAC_PER_CTLR) * 4)) & 0xf);
-}
-
-void dma_check(enum dma_channel channel, char *buf)
-{
- stm32_dma_chan_t *chan;
- int count;
- int i;
-
- chan = dma_get_channel(channel);
- count = chan->cndtr;
- CPRINTF("c=%d\n", count);
- udelay(100 * MSEC);
- CPRINTF("c=%d\n", chan->cndtr);
- for (i = 0; i < count; i++)
- CPRINTF("%02x ", buf[i]);
- udelay(100 * MSEC);
- CPRINTF("c=%d\n", chan->cndtr);
- for (i = 0; i < count; i++)
- CPRINTF("%02x ", buf[i]);
-}
-
-/* Run a check of memory-to-memory DMA */
-void dma_test(enum dma_channel channel)
-{
- stm32_dma_chan_t *chan = dma_get_channel(channel);
- uint32_t ctrl;
- char periph[16], memory[16];
- unsigned int count = sizeof(periph);
- int i;
-
- memset(memory, '\0', sizeof(memory));
- for (i = 0; i < count; i++)
- periph[i] = 10 + i;
-
- /* Following the order in Doc ID 15965 Rev 5 p194 */
- chan->cpar = (uint32_t)periph;
- chan->cmar = (uint32_t)memory;
- chan->cndtr = count;
- ctrl = STM32_DMA_CCR_PL_MEDIUM;
- chan->ccr = ctrl;
-
- ctrl |= STM32_DMA_CCR_MINC; /* | STM32_DMA_CCR_DIR */;
- ctrl |= STM32_DMA_CCR_MEM2MEM;
- ctrl |= STM32_DMA_CCR_PINC;
-/* ctrl |= STM32_DMA_CCR_MSIZE_32_BIT; */
-/* ctrl |= STM32_DMA_CCR_PSIZE_32_BIT; */
- chan->ccr = ctrl;
- chan->ccr = ctrl | STM32_DMA_CCR_EN;
-
- for (i = 0; i < count; i++)
- CPRINTF("%d/%d ", periph[i], memory[i]);
- CPRINTF("\ncount=%d\n", chan->cndtr);
-}
-#endif /* CONFIG_DMA_HELP */
-
-void dma_init(void)
-{
-#if defined(CHIP_FAMILY_STM32L4) || defined(CHIP_FAMILY_STM32L5)
- STM32_RCC_AHB1ENR |= STM32_RCC_AHB1ENR_DMA1EN|STM32_RCC_AHB1ENR_DMA2EN;
-#elif defined(CHIP_FAMILY_STM32G4)
- STM32_RCC_AHB1ENR |= STM32_RCC_AHB1ENR_DMA1EN|STM32_RCC_AHB1ENR_DMA2EN |
- STM32_RCC_AHB1ENR_DMAMUXEN;
-#else
- STM32_RCC_AHBENR |= STM32_RCC_HB_DMA1;
-#endif
-#ifdef CHIP_FAMILY_STM32F3
- STM32_RCC_AHBENR |= STM32_RCC_HB_DMA2;
-#endif
- /* Delay 1 AHB clock cycle after the clock is enabled */
- clock_wait_bus_cycles(BUS_AHB, 1);
-}
-
-int dma_wait(enum dma_channel channel)
-{
- stm32_dma_regs_t *dma = STM32_DMA_REGS(channel);
- const uint32_t mask = STM32_DMA_ISR_TCIF(channel);
- timestamp_t deadline;
-
- deadline.val = get_time().val + DMA_TRANSFER_TIMEOUT_US;
- while ((dma->isr & mask) != mask) {
- if (deadline.val <= get_time().val)
- return EC_ERROR_TIMEOUT;
-
- udelay(DMA_POLLING_INTERVAL_US);
- }
- return EC_SUCCESS;
-}
-
-static inline void _dma_wake_callback(void *cb_data)
-{
- task_id_t id = (task_id_t)(int)cb_data;
-
- if (id != TASK_ID_INVALID)
- task_set_event(id, TASK_EVENT_DMA_TC);
-}
-
-void dma_enable_tc_interrupt(enum dma_channel channel)
-{
- dma_enable_tc_interrupt_callback(channel, _dma_wake_callback,
- (void *)(int)task_get_current());
-}
-
-void dma_enable_tc_interrupt_callback(enum dma_channel channel,
- void (*callback)(void *),
- void *callback_data)
-{
- stm32_dma_chan_t *chan = dma_get_channel(channel);
-
- dma_irq[channel].cb = callback;
- dma_irq[channel].cb_data = callback_data;
-
- chan->ccr |= STM32_DMA_CCR_TCIE;
- task_enable_irq(dma_get_irq(channel));
-}
-
-void dma_disable_tc_interrupt(enum dma_channel channel)
-{
- stm32_dma_chan_t *chan = dma_get_channel(channel);
-
- chan->ccr &= ~STM32_DMA_CCR_TCIE;
- task_disable_irq(dma_get_irq(channel));
-
- dma_irq[channel].cb = NULL;
- dma_irq[channel].cb_data = NULL;
-}
-
-void dma_clear_isr(enum dma_channel channel)
-{
- stm32_dma_regs_t *dma = STM32_DMA_REGS(channel);
-
- dma->ifcr |= STM32_DMA_ISR_ALL(channel);
-}
-
-#ifdef CONFIG_DMA_DEFAULT_HANDLERS
-#ifdef CHIP_FAMILY_STM32F0
-void dma_event_interrupt_channel_1(void)
-{
- if (STM32_DMA1_REGS->isr & STM32_DMA_ISR_TCIF(STM32_DMAC_CH1)) {
- dma_clear_isr(STM32_DMAC_CH1);
- if (dma_irq[STM32_DMAC_CH1].cb != NULL)
- (*dma_irq[STM32_DMAC_CH1].cb)
- (dma_irq[STM32_DMAC_CH1].cb_data);
- }
-}
-DECLARE_IRQ(STM32_IRQ_DMA_CHANNEL_1, dma_event_interrupt_channel_1, 1);
-
-void dma_event_interrupt_channel_2_3(void)
-{
- int i;
-
- for (i = STM32_DMAC_CH2; i <= STM32_DMAC_CH3; i++) {
- if (STM32_DMA1_REGS->isr & STM32_DMA_ISR_TCIF(i)) {
- dma_clear_isr(i);
- if (dma_irq[i].cb != NULL)
- (*dma_irq[i].cb)(dma_irq[i].cb_data);
- }
- }
-}
-DECLARE_IRQ(STM32_IRQ_DMA_CHANNEL_2_3, dma_event_interrupt_channel_2_3, 1);
-
-void dma_event_interrupt_channel_4_7(void)
-{
- int i;
- const unsigned int max_chan = MIN(STM32_DMAC_CH7, STM32_DMAC_COUNT);
-
- for (i = STM32_DMAC_CH4; i <= max_chan; i++) {
- if (STM32_DMA1_REGS->isr & STM32_DMA_ISR_TCIF(i)) {
- dma_clear_isr(i);
- if (dma_irq[i].cb != NULL)
- (*dma_irq[i].cb)(dma_irq[i].cb_data);
- }
- }
-}
-DECLARE_IRQ(STM32_IRQ_DMA_CHANNEL_4_7, dma_event_interrupt_channel_4_7, 1);
-
-#else /* !CHIP_FAMILY_STM32F0 */
-
-#define DECLARE_DMA_IRQ(x) \
- void CONCAT2(dma_event_interrupt_channel_, x)(void) \
- { \
- dma_clear_isr(CONCAT2(STM32_DMAC_CH, x)); \
- if (dma_irq[CONCAT2(STM32_DMAC_CH, x)].cb != NULL) \
- (*dma_irq[CONCAT2(STM32_DMAC_CH, x)].cb) \
- (dma_irq[CONCAT2(STM32_DMAC_CH, x)].cb_data); \
- } \
- DECLARE_IRQ(CONCAT2(STM32_IRQ_DMA_CHANNEL_, x), \
- CONCAT2(dma_event_interrupt_channel_, x), 1)
-
-DECLARE_DMA_IRQ(1);
-DECLARE_DMA_IRQ(2);
-DECLARE_DMA_IRQ(3);
-DECLARE_DMA_IRQ(4);
-DECLARE_DMA_IRQ(5);
-DECLARE_DMA_IRQ(6);
-DECLARE_DMA_IRQ(7);
-#ifdef CHIP_FAMILY_STM32F3
-DECLARE_DMA_IRQ(9);
-DECLARE_DMA_IRQ(10);
-#endif
-#ifdef CHIP_FAMILY_STM32L4
-DECLARE_DMA_IRQ(9);
-DECLARE_DMA_IRQ(10);
-DECLARE_DMA_IRQ(11);
-DECLARE_DMA_IRQ(12);
-DECLARE_DMA_IRQ(13);
-DECLARE_DMA_IRQ(14);
-DECLARE_DMA_IRQ(15);
-#endif
-
-#endif /* CHIP_FAMILY_STM32F0 */
-#endif /* CONFIG_DMA_DEFAULT_HANDLERS */