]> pd.if.org Git - zos/commitdiff
pic reprograming
authorNathan Wagner <nw@hydaspes.if.org>
Tue, 25 Oct 2016 01:32:09 +0000 (20:32 -0500)
committerNathan Wagner <nw@hydaspes.if.org>
Tue, 25 Oct 2016 01:40:32 +0000 (20:40 -0500)
pic.c [new file with mode: 0644]
pic.h [new file with mode: 0644]

diff --git a/pic.c b/pic.c
new file mode 100644 (file)
index 0000000..5e53860
--- /dev/null
+++ b/pic.c
@@ -0,0 +1,89 @@
+#include <stdint.h>
+
+#include "kernel.h"
+
+#include "ioport.h"
+
+#include "pic.h"
+#include "interrupt.h"
+
+/* ioports */
+#define MCMD 0x20
+#define SCMD 0xA0
+#define MDATA 0x21
+#define SDATA 0xA1
+
+#define IRR 0x0A
+#define ISR 0x0B
+
+#define EOI 0x20
+#define ICW1_ICW4  0x01
+#define CMD_INIT  0x10
+#define MODE_8086  0x01
+
+static uint16_t readregister(uint8_t ocw3) {
+       outport8(MCMD, ocw3);
+       outport8(SCMD, ocw3);
+       return inport8(MCMD) | inport8(SCMD) << 8;
+}
+
+static uint16_t readirr() {
+       return readregister(IRR);
+}
+
+static uint16_t readisr() {
+       return readregister(ISR);
+}
+
+static void reprogram() {
+       outport8(MCMD, CMD_INIT | ICW1_ICW4);
+       outport8(SCMD, CMD_INIT | ICW1_ICW4);
+       outport8(MDATA, IRQ0);
+       outport8(SDATA, IRQ8);
+       outport8(MDATA, 0x04); /* Slave PIC at IRQ2 */
+       outport8(SDATA, 0x02); /* Cascade Identity */
+       outport8(MDATA, MODE_8086);
+       outport8(SDATA, MODE_8086);
+       /* masks */
+       outport8(MDATA, 0);
+       outport8(SDATA, 0);
+}
+
+static void deprogram() {
+       outport8(MCMD, CMD_INIT | ICW1_ICW4);
+       outport8(SCMD, CMD_INIT | ICW1_ICW4);
+       outport8(MDATA, 0x08);
+       outport8(SDATA, 0x70);
+       outport8(MDATA, 0x04); /* Slave PIC at IRQ2 */
+       outport8(SDATA, 0x02); /* Cascade Identity */
+       outport8(MDATA, MODE_8086);
+       outport8(SDATA, MODE_8086);
+       outport8(MDATA, 0);
+       outport8(SDATA, 0);
+}
+
+static void sendmastereoi() {
+       outport8(MCMD, EOI);
+}
+
+static void sendslaveeoi() {
+       outport8(SCMD, EOI);
+}
+
+static void sendeoi(unsigned int irq) {
+       if (irq >= 8) {
+               sendslaveeoi();
+       }
+       sendmastereoi();
+}
+
+struct pic pic;
+
+void pic_init() {
+       pic.eoi = sendeoi;
+       pic.mastereoi = sendmastereoi;
+       pic.readirr = readirr;
+       pic.readisr = readisr;
+       pic.reprogram = reprogram;
+       pic.deprogram = deprogram;
+}
diff --git a/pic.h b/pic.h
new file mode 100644 (file)
index 0000000..19e00b5
--- /dev/null
+++ b/pic.h
@@ -0,0 +1,18 @@
+#ifndef PIC_H_
+#define PIC_H_
+
+#include <stdint.h>
+
+struct pic {
+       uint16_t (*readirr)();
+       uint16_t (*readisr)();
+       void (*reprogram)();
+       void (*deprogram)();
+       void (*mastereoi)();
+       void (*eoi)(unsigned int irq);
+};
+
+extern struct pic pic;
+void pic_init();
+
+#endif