mirror of
https://github.com/StrikerX3/StrikeBox.git
synced 2024-06-23 14:53:22 -04:00
A few minor fixes in NV2A
This commit is contained in:
parent
db16858dea
commit
42139f684b
|
@ -145,7 +145,14 @@ typedef struct {
|
|||
} NV2APRMCIO;
|
||||
|
||||
typedef struct {
|
||||
// Interrupt status. Bits 0-30 are hardware interrupts, bit 31 is software interrupt.
|
||||
// 1 if the relevant input interrupt line is active.
|
||||
// Bits 0-30 are read-only, bit 31 can be written to set/clear the software interrupt.
|
||||
// Bit 31 can only be set to 1 if software interrupts are enabled in INTR_MASK_*.
|
||||
uint32_t pendingInterrupts = 0;
|
||||
|
||||
// bit 0: hardware interrupt enable - if 1, and any of bits 0-30 of INTR_* are active, the corresponding output interrupt line will be asserted.
|
||||
// bit 1: software interrupt enable - if 1, bit 31 of INTR_* is active, the corresponding output interrupt line will be asserted.
|
||||
uint32_t enabledInterrupts = 0;
|
||||
} NV2APMC;
|
||||
|
||||
|
|
|
@ -1,3 +1,9 @@
|
|||
/*
|
||||
* Portions of the code are based on XQEMU's Geforce NV2A implementation.
|
||||
* The original copyright header is included below.
|
||||
*
|
||||
* Additional work by Ivan "StrikerX3" Oliveira.
|
||||
*/
|
||||
/*
|
||||
* QEMU Geforce NV2A internal definitions
|
||||
*
|
||||
|
@ -45,6 +51,7 @@
|
|||
#define NV_PMC_INTR_0 0x00000100
|
||||
# define NV_PMC_INTR_0_PFIFO (1 << 8)
|
||||
# define NV_PMC_INTR_0_PGRAPH (1 << 12)
|
||||
# define NV_PMC_INTR_0_PTIMER (1 << 20)
|
||||
# define NV_PMC_INTR_0_PCRTC (1 << 24)
|
||||
# define NV_PMC_INTR_0_PBUS (1 << 28)
|
||||
# define NV_PMC_INTR_0_SOFTWARE (1 << 31)
|
||||
|
|
|
@ -1,6 +1,8 @@
|
|||
/*
|
||||
* Portions of the code are based on XQEMU's Geforce NV2A implementation.
|
||||
* The original copyright header is included below.
|
||||
*
|
||||
* Additional work by Ivan "StrikerX3" Oliveira.
|
||||
*/
|
||||
/*
|
||||
* QEMU Geforce NV2A implementation
|
||||
|
@ -236,7 +238,7 @@ void NV2ADevice::PMCRead(NV2ADevice *nv2a, uint32_t addr, uint32_t *value, uint8
|
|||
return;
|
||||
}
|
||||
|
||||
log_warning("NV2ADevice::PMCRead: Unknown NV2A read! addr = 0x%x, size = %u\n", addr, size);
|
||||
log_warning("NV2ADevice::PMCRead: Unknown NV2A PMC read! addr = 0x%x, size = %u\n", addr, size);
|
||||
*value = 0;
|
||||
}
|
||||
|
||||
|
@ -245,7 +247,9 @@ void NV2ADevice::PMCWrite(NV2ADevice *nv2a, uint32_t addr, uint32_t value, uint8
|
|||
|
||||
switch (addr) {
|
||||
case NV_PMC_INTR_0:
|
||||
nv2a->m_PMC.pendingInterrupts &= ~value;
|
||||
// Only bit 31 is writable
|
||||
nv2a->m_PMC.pendingInterrupts &= ~NV_PMC_INTR_0_SOFTWARE;
|
||||
nv2a->m_PMC.pendingInterrupts |= (value & NV_PMC_INTR_0_SOFTWARE);
|
||||
nv2a->UpdateIRQ();
|
||||
break;
|
||||
case NV_PMC_INTR_EN_0:
|
||||
|
@ -2413,6 +2417,7 @@ void NV2ADevice::PFIFO_Puller_Thread(NV2ADevice *nv2a) {
|
|||
}
|
||||
|
||||
void NV2ADevice::UpdateIRQ() {
|
||||
// Update pending hardware interrupts
|
||||
if (m_PFIFO.pending_interrupts & m_PFIFO.enabled_interrupts) {
|
||||
m_PMC.pendingInterrupts |= NV_PMC_INTR_0_PFIFO;
|
||||
}
|
||||
|
@ -2435,11 +2440,16 @@ void NV2ADevice::UpdateIRQ() {
|
|||
}
|
||||
|
||||
uint8_t irq = Read8(m_configSpace, PCI_INTERRUPT_PIN);
|
||||
if (m_PMC.pendingInterrupts && m_PMC.enabledInterrupts) {
|
||||
m_irqHandler.HandleIRQ(irq, 1);
|
||||
|
||||
// Raise IRQ if one of the following is true:
|
||||
// - Hardware interrupts are enabled and there is any pending interrupt bit set other than software
|
||||
// - Software interrupts are enabled and the pending software interrupt bit is set
|
||||
if ((m_PMC.enabledInterrupts & NV_PMC_INTR_EN_0_HARDWARE) && (m_PMC.pendingInterrupts & ~NV_PMC_INTR_0_SOFTWARE) ||
|
||||
(m_PMC.enabledInterrupts & NV_PMC_INTR_EN_0_SOFTWARE) && (m_PMC.pendingInterrupts & NV_PMC_INTR_0_SOFTWARE)) {
|
||||
m_irqHandler.HandleIRQ(irq, true);
|
||||
}
|
||||
else {
|
||||
m_irqHandler.HandleIRQ(irq, 0);
|
||||
m_irqHandler.HandleIRQ(irq, false);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in a new issue