The PIC can now be deprogrammed and reprogrammed.

This commit is contained in:
Jonas 'Sortie' Termansen 2012-04-30 17:23:43 +02:00
parent a75b215fe3
commit 00869bcdc1
2 changed files with 36 additions and 15 deletions

View File

@ -87,6 +87,38 @@ const unsigned NUM_INTERRUPTS = 256UL;
Handler interrupthandlers[NUM_INTERRUPTS];
void* interrupthandlerptr[NUM_INTERRUPTS];
extern "C" void ReprogramPIC()
{
uint8_t mastermask = 0;
uint8_t slavemask = 0;
CPU::OutPortB(PIC_MASTER + PIC_COMMAND, PIC_CMD_INIT | PIC_ICW1_ICW4);
CPU::OutPortB(PIC_SLAVE + PIC_COMMAND, PIC_CMD_INIT | PIC_ICW1_ICW4);
CPU::OutPortB(PIC_MASTER + PIC_DATA, IRQ0);
CPU::OutPortB(PIC_SLAVE + PIC_DATA, IRQ8);
CPU::OutPortB(PIC_MASTER + PIC_DATA, 0x04); // Slave PIC at IRQ2
CPU::OutPortB(PIC_SLAVE + PIC_DATA, 0x02); // Cascade Identity
CPU::OutPortB(PIC_MASTER + PIC_DATA, PIC_MODE_8086);
CPU::OutPortB(PIC_SLAVE + PIC_DATA, PIC_MODE_8086);
CPU::OutPortB(PIC_MASTER + PIC_DATA, mastermask);
CPU::OutPortB(PIC_SLAVE + PIC_DATA, slavemask);
}
extern "C" void DeprogramPIC()
{
uint8_t mastermask = 0;
uint8_t slavemask = 0;
CPU::OutPortB(PIC_MASTER + PIC_COMMAND, PIC_CMD_INIT | PIC_ICW1_ICW4);
CPU::OutPortB(PIC_SLAVE + PIC_COMMAND, PIC_CMD_INIT | PIC_ICW1_ICW4);
CPU::OutPortB(PIC_MASTER + PIC_DATA, 0x08);
CPU::OutPortB(PIC_SLAVE + PIC_DATA, 0x70);
CPU::OutPortB(PIC_MASTER + PIC_DATA, 0x04); // Slave PIC at IRQ2
CPU::OutPortB(PIC_SLAVE + PIC_DATA, 0x02); // Cascade Identity
CPU::OutPortB(PIC_MASTER + PIC_DATA, PIC_MODE_8086);
CPU::OutPortB(PIC_SLAVE + PIC_DATA, PIC_MODE_8086);
CPU::OutPortB(PIC_MASTER + PIC_DATA, mastermask);
CPU::OutPortB(PIC_SLAVE + PIC_DATA, slavemask);
}
void Init()
{
initialized = false;
@ -100,18 +132,7 @@ void Init()
}
// Remap the IRQ table on the PICs.
uint8_t mastermask = 0;
uint8_t slavemask = 0;
CPU::OutPortB(PIC_MASTER + PIC_COMMAND, PIC_CMD_INIT | PIC_ICW1_ICW4);
CPU::OutPortB(PIC_SLAVE + PIC_COMMAND, PIC_CMD_INIT | PIC_ICW1_ICW4);
CPU::OutPortB(PIC_MASTER + PIC_DATA, IRQ0);
CPU::OutPortB(PIC_SLAVE + PIC_DATA, IRQ8);
CPU::OutPortB(PIC_MASTER + PIC_DATA, 0x04); // Slave PIC at IRQ2
CPU::OutPortB(PIC_SLAVE + PIC_DATA, 0x02); // Cascade Identity
CPU::OutPortB(PIC_MASTER + PIC_DATA, PIC_MODE_8086);
CPU::OutPortB(PIC_SLAVE + PIC_DATA, PIC_MODE_8086);
CPU::OutPortB(PIC_MASTER + PIC_DATA, mastermask);
CPU::OutPortB(PIC_SLAVE + PIC_DATA, slavemask);
ReprogramPIC();
RegisterRawHandler(0, isr0, false);
RegisterRawHandler(1, isr1, false);

View File

@ -54,7 +54,7 @@ namespace Sortix
return microsecondssinceboot;
}
void RequestIQR0()
extern "C" void RequestIRQ0()
{
// The value we send to the PIT is the value to divide it's input clock
// (1193180 Hz) by, to get our required frequency. Important to note is
@ -95,7 +95,7 @@ namespace Sortix
didUglyIRQ0Hack = false;
RequestIQR0();
RequestIRQ0();
}
void OnIRQ0(CPU::InterruptRegisters* Regs, void* /*user*/)
@ -114,7 +114,7 @@ namespace Sortix
// TODO: There is a horrible bug that causes Sortix to only receive
// one IRQ0 on my laptop, but it works in virtual machines. But
// re-requesting an addtional time seems to work. Hacky and ugly.
if ( !didUglyIRQ0Hack ) { RequestIQR0(); didUglyIRQ0Hack = true; }
if ( !didUglyIRQ0Hack ) { RequestIRQ0(); didUglyIRQ0Hack = true; }
}
// TODO: Implement all the other useful functions regarding time.