Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 99532559 authored by Nicolas Pitre's avatar Nicolas Pitre Committed by Russell King
Browse files

[ARM] 3500/1: fix PXA27x DMA allocation priority



Patch from Nicolas Pitre

Intel PXA27x developers manual section 5.4.1.1 lists a priority
distribution for the DMA channels differently than what the code
currently assumes.  This patch fixes that.

Noticed by Simon Vogl <vogl@soft.uni-linz.ac.at>

Signed-off-by: default avatarNicolas Pitre <nico@cam.org>
Signed-off-by: default avatarRussell King <rmk+kernel@arm.linux.org.uk>
parent b7d7ef87
Loading
Loading
Loading
Loading
+5 −12
Original line number Diff line number Diff line
@@ -45,23 +45,16 @@ int pxa_request_dma (char *name, pxa_dma_prio prio,

	local_irq_save(flags);

	do {
		/* try grabbing a DMA channel with the requested priority */
	for (i = prio; i < prio + PXA_DMA_NBCH(prio); i++) {
		pxa_for_each_dma_prio (i, prio) {
			if (!dma_channels[i].name) {
				found = 1;
				break;
			}
		}

	if (!found) {
		/* requested prio group is full, try hier priorities */
		for (i = prio-1; i >= 0; i--) {
			if (!dma_channels[i].name) {
				found = 1;
				break;
			}
		}
	}
		/* if requested prio group is full, try a hier priority */
	} while (!found && prio--);

	if (found) {
		DCSR(i) = DCSR_STARTINTR|DCSR_ENDINTR|DCSR_BUSERR;
+14 −12
Original line number Diff line number Diff line
@@ -24,27 +24,29 @@ typedef struct pxa_dma_desc {
	volatile u32 dcmd;	/* DCMD value for the current transfer */
} pxa_dma_desc;

typedef enum {
	DMA_PRIO_HIGH = 0,
	DMA_PRIO_MEDIUM = 1,
	DMA_PRIO_LOW = 2
} pxa_dma_prio;

#if defined(CONFIG_PXA27x)

#define PXA_DMA_CHANNELS	32
#define PXA_DMA_NBCH(prio)	((prio == DMA_PRIO_LOW) ? 16 : 8)

typedef enum {
	DMA_PRIO_HIGH = 0,
	DMA_PRIO_MEDIUM = 8,
	DMA_PRIO_LOW = 16
} pxa_dma_prio;
#define pxa_for_each_dma_prio(ch, prio)					\
for (									\
	ch = prio * 4;							\
	ch != (4 << prio) + 16;						\
	ch = (ch + 1 == (4 << prio)) ? (prio * 4 + 16) : (ch + 1)	\
)

#elif defined(CONFIG_PXA25x)

#define PXA_DMA_CHANNELS	16
#define PXA_DMA_NBCH(prio)	((prio == DMA_PRIO_LOW) ? 8 : 4)

typedef enum {
	DMA_PRIO_HIGH = 0,
	DMA_PRIO_MEDIUM = 4,
	DMA_PRIO_LOW = 8
} pxa_dma_prio;
#define pxa_for_each_dma_prio(ch, prio)					\
	for (ch = prio * 4; ch != (4 << prio); ch++)

#endif