2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS kernel
5 * PURPOSE: Hardware Abstraction Layer DLL
6 * PROGRAMMER: Samuel SerapiĆ³n
15 * 8259 interrupt controllers
19 Int0ctl
= 0x20, /* control port (ICW1, OCW2, OCW3) */
20 Int0aux
= 0x21, /* everything else (ICW2, ICW3, ICW4, OCW1) */
21 Int1ctl
= 0xA0, /* control port */
22 Int1aux
= 0xA1, /* everything else (ICW2, ICW3, ICW4, OCW1) */
24 Icw1
= 0x10, /* select bit in ctl register */
28 EOI
= 0x20, /* non-specific end of interrupt */
30 Elcr1
= 0x4D0, /* Edge/Level Triggered Register */
36 INT i8259mask
= 0xFFFF; /* disabled interrupts */
47 OldEflags
= __readeflags();
51 * Set up the first 8259 interrupt processor.
52 * Make 8259 interrupts start at CPU vector VectorPIC.
53 * Set the 8259 as master with edge triggered
54 * input with fully nested interrupts.
56 __outbyte(Int0ctl
, 0x20); /* ICW1 - master, edge triggered */
57 __outbyte(Int0aux
, 0x11); /* Edge, cascade, CAI 8, ICW4 */
58 __outbyte(Int0aux
, PRIMARY_VECTOR_BASE
); /* ICW2 - interrupt vector offset */
59 __outbyte(Int0aux
, 0x04); /* ICW3 - have slave on level 2 */
60 __outbyte(Int0aux
, 0x01); /* ICW4 - 8086 mode, not buffered */
61 __outbyte(Int0aux
, 0xFF); /* Mask Interrupts */
63 * Set up the second 8259 interrupt processor.
64 * Make 8259 interrupts start at CPU vector VectorPIC+8.
65 * Set the 8259 as slave with edge triggered
66 * input with fully nested interrupts.
68 __outbyte(Int1ctl
, 0xA0); /* ICW1 - master, edge triggered, */
69 __outbyte(Int1aux
, 0x11); /* Edge, cascade, CAI 8, ICW4 */
70 __outbyte(Int1aux
, PRIMARY_VECTOR_BASE
+8); /* ICW2 - interrupt vector offset */
71 __outbyte(Int1aux
, 0x02); /* ICW3 - I am a slave on level 2 */
72 __outbyte(Int1aux
, 0x01); /* ICW4 - 8086 mode, not buffered */
73 __outbyte(Int1aux
, 0xFF); /* Mask Interrupts */
77 * pass #2 8259 interrupts to #1
80 __outbyte(Int0aux
, i8259mask
& 0xFF);
83 * Set Ocw3 to return the ISR when ctl read.
84 * After initialisation status read is set to IRR.
85 * Read IRR first to possibly deassert an outstanding
89 __outbyte(Int0ctl
, Ocw3
|0x03);
91 __outbyte(Int1ctl
, Ocw3
|0x03);
94 * Check for Edge/Level register.
95 * This check may not work for all chipsets.
96 * First try a non-intrusive test - the bits for
97 * IRQs 13, 8, 2, 1 and 0 must be edge (0). If
98 * that's OK try a R/W test.
100 x
= (__inbyte(Elcr2
) << 8) | __inbyte(Elcr1
);
106 if (__inbyte (Elcr1
) == 0)
108 __outbyte(Elcr1
, 0x20);
110 if (__inbyte (Elcr1
) == 0x20)
114 __outbyte(Elcr1
, x
& 0xFF);
115 DPRINT("ELCR: %4.4uX\n", i8259elcr
);
119 __writeeflags(OldEflags
);
124 HalDisableSystemInterrupt(
133 HalEnableSystemInterrupt(
136 KINTERRUPT_MODE InterruptMode
)