mirror of
https://github.com/n64dev/cen64.git
synced 2024-06-22 22:12:45 -04:00
PI: name constants and fixed DMA/reset controller behaviour (#134)
* PI: name constants and fixed DMA/reset controller behaviour. When a reset controller request is performed, only busy and error bits are cleared. When DMAs begin, the DMA busy bit is set, but the interrupt bit shouldn't be touched yet. * Ignore PI register write and flag error when busy.
This commit is contained in:
parent
fd4cb9be51
commit
30f17b2e20
|
@ -38,14 +38,12 @@ void pi_cycle_(struct pi_controller *pi) {
|
|||
|
||||
// XXX: Defer actual movement of bytes until... now.
|
||||
// This is a giant hack; bytes should be DMA'd slowly.
|
||||
// Also, why the heck does the OR do? I know the &
|
||||
// clears the busy bit, but...
|
||||
pi->is_dma_read ? pi_dma_read(pi) : pi_dma_write(pi);
|
||||
|
||||
pi->regs[PI_DRAM_ADDR_REG] += bytes;
|
||||
pi->regs[PI_CART_ADDR_REG] += bytes;
|
||||
pi->regs[PI_STATUS_REG] &= ~0x1;
|
||||
pi->regs[PI_STATUS_REG] |= 0x8;
|
||||
pi->regs[PI_STATUS_REG] &= ~PI_STATUS_DMA_BUSY;
|
||||
pi->regs[PI_STATUS_REG] |= PI_STATUS_INTERRUPT;
|
||||
|
||||
signal_rcp_interrupt(pi->bus->vr4300, MI_INTR_PI);
|
||||
|
||||
|
@ -219,16 +217,21 @@ int write_pi_regs(void *opaque, uint32_t address, uint32_t word, uint32_t dqm) {
|
|||
debug_mmio_write(pi, pi_register_mnemonics[reg], word, dqm);
|
||||
|
||||
if (reg == PI_STATUS_REG) {
|
||||
if (word & 0x1)
|
||||
pi->regs[reg] = 0;
|
||||
if (word & PI_STATUS_RESET_CONTROLLER)
|
||||
pi->regs[reg] &= ~(PI_STATUS_IS_BUSY | PI_STATUS_ERROR);
|
||||
|
||||
if (word & 0x2) {
|
||||
if (word & PI_STATUS_CLEAR_INTERRUPT) {
|
||||
clear_rcp_interrupt(pi->bus->vr4300, MI_INTR_PI);
|
||||
pi->regs[reg] &= ~0x8;
|
||||
pi->regs[reg] &= ~PI_STATUS_INTERRUPT;
|
||||
}
|
||||
}
|
||||
|
||||
else {
|
||||
if (pi->regs[PI_STATUS_REG] & PI_STATUS_IS_BUSY) {
|
||||
pi->regs[PI_STATUS_REG] |= PI_STATUS_ERROR;
|
||||
return 0;
|
||||
}
|
||||
|
||||
pi->regs[reg] &= ~dqm;
|
||||
pi->regs[reg] |= word;
|
||||
|
||||
|
@ -237,8 +240,8 @@ int write_pi_regs(void *opaque, uint32_t address, uint32_t word, uint32_t dqm) {
|
|||
|
||||
else if (reg == PI_WR_LEN_REG) {
|
||||
if (pi->regs[PI_DRAM_ADDR_REG] == 0xFFFFFFFF) {
|
||||
pi->regs[PI_STATUS_REG] &= ~0x1;
|
||||
pi->regs[PI_STATUS_REG] |= 0x8;
|
||||
pi->regs[PI_STATUS_REG] &= ~PI_STATUS_DMA_BUSY;
|
||||
pi->regs[PI_STATUS_REG] |= PI_STATUS_INTERRUPT;
|
||||
|
||||
signal_rcp_interrupt(pi->bus->vr4300, MI_INTR_PI);
|
||||
return 0;
|
||||
|
@ -246,14 +249,14 @@ int write_pi_regs(void *opaque, uint32_t address, uint32_t word, uint32_t dqm) {
|
|||
|
||||
pi->bytes_to_copy = (pi->regs[PI_WR_LEN_REG] & 0xFFFFFF) + 1;
|
||||
pi->counter = pi->bytes_to_copy / 2 + 100; // Assume ~2 bytes/clock?
|
||||
pi->regs[PI_STATUS_REG] |= 0x9; // I'm busy!
|
||||
pi->regs[PI_STATUS_REG] |= PI_STATUS_DMA_BUSY; // I'm busy!
|
||||
pi->is_dma_read = false;
|
||||
}
|
||||
|
||||
else if (reg == PI_RD_LEN_REG) {
|
||||
if (pi->regs[PI_DRAM_ADDR_REG] == 0xFFFFFFFF) {
|
||||
pi->regs[PI_STATUS_REG] &= ~0x1;
|
||||
pi->regs[PI_STATUS_REG] |= 0x8;
|
||||
pi->regs[PI_STATUS_REG] &= ~PI_STATUS_DMA_BUSY;
|
||||
pi->regs[PI_STATUS_REG] |= PI_STATUS_INTERRUPT;
|
||||
|
||||
signal_rcp_interrupt(pi->bus->vr4300, MI_INTR_PI);
|
||||
return 0;
|
||||
|
@ -261,7 +264,7 @@ int write_pi_regs(void *opaque, uint32_t address, uint32_t word, uint32_t dqm) {
|
|||
|
||||
pi->bytes_to_copy = (pi->regs[PI_RD_LEN_REG] & 0xFFFFFF) + 1;
|
||||
pi->counter = pi->bytes_to_copy / 2 + 100; // Assume ~2 bytes/clock?
|
||||
pi->regs[PI_STATUS_REG] |= 0x9; // I'm busy!
|
||||
pi->regs[PI_STATUS_REG] |= PI_STATUS_DMA_BUSY; // I'm busy!
|
||||
pi->is_dma_read = true;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -26,6 +26,19 @@ enum pi_register {
|
|||
extern const char *pi_register_mnemonics[NUM_PI_REGISTERS];
|
||||
#endif
|
||||
|
||||
enum pi_status {
|
||||
PI_STATUS_DMA_BUSY = 1 << 0,
|
||||
PI_STATUS_IO_BUSY = 1 << 1,
|
||||
PI_STATUS_ERROR = 1 << 2,
|
||||
PI_STATUS_INTERRUPT = 1 << 3,
|
||||
PI_STATUS_IS_BUSY = PI_STATUS_DMA_BUSY | PI_STATUS_IO_BUSY
|
||||
};
|
||||
|
||||
enum pi_status_write {
|
||||
PI_STATUS_RESET_CONTROLLER = 1 << 0,
|
||||
PI_STATUS_CLEAR_INTERRUPT = 1 << 1
|
||||
};
|
||||
|
||||
#define FLASHRAM_SIZE 0x20000
|
||||
|
||||
enum flashram_mode {
|
||||
|
|
Loading…
Reference in a new issue