mirror of
https://github.com/zoriya/ComSquare.git
synced 2026-05-31 01:25:31 +00:00
Mapping the DMA's channels to the bus
This commit is contained in:
+7
-2
@@ -91,8 +91,10 @@ namespace ComSquare::CPU
|
||||
return this->_internalRegisters.joy4l;
|
||||
case 0x1F:
|
||||
return this->_internalRegisters.joy4h;
|
||||
case 0x100 ... 0x180:
|
||||
return this->_dmaChannels[(addr - 0x100) >> 8u].read(addr & 0xF);
|
||||
default:
|
||||
throw InvalidAddress("CPU Internal Registers read", addr);
|
||||
throw InvalidAddress("CPU Internal Registers read", addr + this->getStart());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -189,8 +191,11 @@ namespace ComSquare::CPU
|
||||
case 0x1F:
|
||||
this->_internalRegisters.joy4h = data;
|
||||
break;
|
||||
case 0x100 ... 0x180:
|
||||
this->_dmaChannels[(addr - 0x100) >> 8u].write(addr & 0xF, data);
|
||||
break;
|
||||
default:
|
||||
throw InvalidAddress("CPU Internal Registers write", addr);
|
||||
throw InvalidAddress("CPU Internal Registers write", addr + this->getStart());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -11,6 +11,7 @@
|
||||
#include "../Cartridge/Cartridge.hpp"
|
||||
#include "../Memory/AMemory.hpp"
|
||||
#include "Instruction.hpp"
|
||||
#include "DMA/DMA.hpp"
|
||||
|
||||
namespace ComSquare::CPU
|
||||
{
|
||||
@@ -201,6 +202,8 @@ namespace ComSquare::CPU
|
||||
//! @brief The cartridge header (stored for interrupt vectors..
|
||||
Cartridge::Header &_cartridgeHeader;
|
||||
|
||||
std::array<DMA, 8> _dmaChannels;
|
||||
|
||||
//! @brief True if an addressing mode with an iterator (x, y) has crossed the page. (Used because crossing the page boundary take one more cycle to run certain instructions).
|
||||
bool _hasIndexCrossedPageBoundary = false;
|
||||
|
||||
|
||||
@@ -3,3 +3,57 @@
|
||||
//
|
||||
|
||||
#include "DMA.hpp"
|
||||
#include "../../Exceptions/InvalidAddress.hpp"
|
||||
|
||||
namespace ComSquare::CPU
|
||||
{
|
||||
uint8_t DMA::read(uint8_t addr)
|
||||
{
|
||||
switch (addr) {
|
||||
case 0x0:
|
||||
return this->controlRegister.raw;
|
||||
case 0x1:
|
||||
return this->port;
|
||||
case 0x2:
|
||||
return this->aAddress.bytes[0];
|
||||
case 0x3:
|
||||
return this->aAddress.bytes[1];
|
||||
case 0x4:
|
||||
return this->aAddress.bytes[2];
|
||||
case 0x5:
|
||||
return this->count.bytes[0];
|
||||
case 0x6:
|
||||
return this->count.bytes[1];
|
||||
default:
|
||||
throw InvalidAddress("DMA read", addr);
|
||||
}
|
||||
}
|
||||
|
||||
void DMA::write(uint8_t addr, uint8_t data)
|
||||
{
|
||||
switch (addr) {
|
||||
case 0x0:
|
||||
this->controlRegister.raw = data;
|
||||
break;
|
||||
case 0x1:
|
||||
this->port = data;
|
||||
break;
|
||||
case 0x2:
|
||||
this->aAddress.bytes[0] = data;
|
||||
break;
|
||||
case 0x3:
|
||||
this->aAddress.bytes[1] = data;
|
||||
case 0x4:
|
||||
this->aAddress.bytes[2] = data;
|
||||
break;
|
||||
case 0x5:
|
||||
this->count.bytes[0] = data;
|
||||
break;
|
||||
case 0x6:
|
||||
this->count.bytes[1] = data;
|
||||
break;
|
||||
default:
|
||||
throw InvalidAddress("DMA read", addr);
|
||||
}
|
||||
}
|
||||
}
|
||||
+15
-4
@@ -46,13 +46,24 @@ namespace ComSquare::CPU
|
||||
//! @brief If this is 'xx', the register accessed will be $21xx.
|
||||
uint8_t port;
|
||||
//! @brief The absolute long address of the data from the A bus.
|
||||
uint24_t aAddress;
|
||||
union {
|
||||
uint8_t bytes[3];
|
||||
uint24_t raw: 24;
|
||||
} aAddress;
|
||||
//! @brief The number of bytes to be transferred.
|
||||
uint16_t count;
|
||||
union {
|
||||
uint8_t bytes[2];
|
||||
uint16_t raw;
|
||||
} count;
|
||||
|
||||
//! @brief Bus helper to read from this channel.
|
||||
uint8_t read(uint8_t addr);
|
||||
//! @brief Bus helper to write to this channel.
|
||||
void write(uint8_t addr, uint8_t data);
|
||||
|
||||
DMA() = default;
|
||||
DMA(DMA &) = default;
|
||||
DMA &operator=(DMA &) = default;
|
||||
DMA(const DMA &) = default;
|
||||
DMA &operator=(const DMA &) = default;
|
||||
~DMA() = default;
|
||||
};
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user