dma: add support for standard DMA access to SPU memory

* Mark SPU memory as sleep-blocking.
* Perform 4-byte accesses only in dma_memset() and dma_memcpy() (32-byte
  accesses freeze as one would expect).

This change does *NOT* implement support for SPU's integrated DMAC.
This commit is contained in:
Lephe 2021-06-17 14:32:27 +02:00
parent 5bd04a9613
commit 03ef59521c
No known key found for this signature in database
GPG key ID: 1BBA026E13FC0495
3 changed files with 30 additions and 2 deletions

View file

@ -116,6 +116,11 @@ static int dma_setup(int channel, dma_size_t size, uint blocks,
if(ch->DAR >= 0xe5007000 && ch->DAR <= 0xe5204000) if(ch->DAR >= 0xe5007000 && ch->DAR <= 0xe5204000)
dma_sleep_blocking[channel] = true; dma_sleep_blocking[channel] = true;
if(ch->SAR >= 0xfe200000 && ch->SAR <= 0xfe3fffff)
dma_sleep_blocking[channel] = true;
if(ch->DAR >= 0xfe200000 && ch->DAR <= 0xfe3fffff)
dma_sleep_blocking[channel] = true;
return 0; return 0;
} }

View file

@ -4,6 +4,18 @@
void *dma_memcpy(void * __restrict dst, const void * __restrict src, void *dma_memcpy(void * __restrict dst, const void * __restrict src,
size_t size) size_t size)
{ {
dma_transfer_sync(1, DMA_32B, size >> 5, src, DMA_INC, dst, DMA_INC); int block_size = DMA_32B;
int block_count = size >> 5;
/* Use 4-byte transfers to access SPU memory */
if(((uint32_t)src >= 0xfe200000 && (uint32_t)src < 0xfe400000) ||
((uint32_t)dst >= 0xfe200000 && (uint32_t)dst < 0xfe400000))
{
block_size = DMA_4B;
block_count = size >> 2;
}
dma_transfer_sync(1, block_size, block_count, src, DMA_INC, dst,
DMA_INC);
return dst; return dst;
} }

View file

@ -14,6 +14,17 @@ void *dma_memset(void *dst, uint32_t l, size_t size)
different memory regions, making the DMA faster than the CPU. */ different memory regions, making the DMA faster than the CPU. */
for(int i = 0; i < 8; i++) ILbuf[i] = l; for(int i = 0; i < 8; i++) ILbuf[i] = l;
dma_transfer_sync(1, DMA_32B, size>>5, ILbuf, DMA_FIXED, dst, DMA_INC); int block_size = DMA_32B;
int block_count = size >> 5;
/* Use 4-byte transfers to access SPU memory */
if((uint32_t)dst >= 0xfe200000 && (uint32_t)dst < 0xfe400000)
{
block_size = DMA_4B;
block_count = size >> 2;
}
dma_transfer_sync(1, block_size, block_count, ILbuf, DMA_FIXED, dst,
DMA_INC);
return dst; return dst;
} }