[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: Nicolas Pitre <nico@cam.org> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
This commit is contained in:
committed by
Russell King
parent
b7d7ef87e1
commit
99532559dc
@@ -45,23 +45,16 @@ int pxa_request_dma (char *name, pxa_dma_prio prio,
|
|||||||
|
|
||||||
local_irq_save(flags);
|
local_irq_save(flags);
|
||||||
|
|
||||||
/* try grabbing a DMA channel with the requested priority */
|
do {
|
||||||
for (i = prio; i < prio + PXA_DMA_NBCH(prio); i++) {
|
/* try grabbing a DMA channel with the requested priority */
|
||||||
if (!dma_channels[i].name) {
|
pxa_for_each_dma_prio (i, prio) {
|
||||||
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) {
|
if (!dma_channels[i].name) {
|
||||||
found = 1;
|
found = 1;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
/* if requested prio group is full, try a hier priority */
|
||||||
|
} while (!found && prio--);
|
||||||
|
|
||||||
if (found) {
|
if (found) {
|
||||||
DCSR(i) = DCSR_STARTINTR|DCSR_ENDINTR|DCSR_BUSERR;
|
DCSR(i) = DCSR_STARTINTR|DCSR_ENDINTR|DCSR_BUSERR;
|
||||||
|
@@ -24,27 +24,29 @@ typedef struct pxa_dma_desc {
|
|||||||
volatile u32 dcmd; /* DCMD value for the current transfer */
|
volatile u32 dcmd; /* DCMD value for the current transfer */
|
||||||
} pxa_dma_desc;
|
} pxa_dma_desc;
|
||||||
|
|
||||||
|
typedef enum {
|
||||||
|
DMA_PRIO_HIGH = 0,
|
||||||
|
DMA_PRIO_MEDIUM = 1,
|
||||||
|
DMA_PRIO_LOW = 2
|
||||||
|
} pxa_dma_prio;
|
||||||
|
|
||||||
#if defined(CONFIG_PXA27x)
|
#if defined(CONFIG_PXA27x)
|
||||||
|
|
||||||
#define PXA_DMA_CHANNELS 32
|
#define PXA_DMA_CHANNELS 32
|
||||||
#define PXA_DMA_NBCH(prio) ((prio == DMA_PRIO_LOW) ? 16 : 8)
|
|
||||||
|
|
||||||
typedef enum {
|
#define pxa_for_each_dma_prio(ch, prio) \
|
||||||
DMA_PRIO_HIGH = 0,
|
for ( \
|
||||||
DMA_PRIO_MEDIUM = 8,
|
ch = prio * 4; \
|
||||||
DMA_PRIO_LOW = 16
|
ch != (4 << prio) + 16; \
|
||||||
} pxa_dma_prio;
|
ch = (ch + 1 == (4 << prio)) ? (prio * 4 + 16) : (ch + 1) \
|
||||||
|
)
|
||||||
|
|
||||||
#elif defined(CONFIG_PXA25x)
|
#elif defined(CONFIG_PXA25x)
|
||||||
|
|
||||||
#define PXA_DMA_CHANNELS 16
|
#define PXA_DMA_CHANNELS 16
|
||||||
#define PXA_DMA_NBCH(prio) ((prio == DMA_PRIO_LOW) ? 8 : 4)
|
|
||||||
|
|
||||||
typedef enum {
|
#define pxa_for_each_dma_prio(ch, prio) \
|
||||||
DMA_PRIO_HIGH = 0,
|
for (ch = prio * 4; ch != (4 << prio); ch++)
|
||||||
DMA_PRIO_MEDIUM = 4,
|
|
||||||
DMA_PRIO_LOW = 8
|
|
||||||
} pxa_dma_prio;
|
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user