changeset ee307cca6d31 in /z/repo/m5
details: http://repo.m5sim.org/m5?cmd=changeset;node=ee307cca6d31
description:
X86: Add a keyboard controller device.
diffstat:
5 files changed, 731 insertions(+)
src/dev/x86/I8042.py | 43 +++
src/dev/x86/SConscript | 4
src/dev/x86/SouthBridge.py | 13 +
src/dev/x86/i8042.cc | 529 ++++++++++++++++++++++++++++++++++++++++++++
src/dev/x86/i8042.hh | 142 +++++++++++
diffs (truncated from 791 to 300 lines):
diff -r 1758d56964c9 -r ee307cca6d31 src/dev/x86/I8042.py
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/src/dev/x86/I8042.py Sat Jan 31 23:59:01 2009 -0800
@@ -0,0 +1,43 @@
+# Copyright (c) 2008 The Regents of The University of Michigan
+# All rights reserved.
+#
+# Redistribution and use in source and binary forms, with or without
+# modification, are permitted provided that the following conditions are
+# met: redistributions of source code must retain the above copyright
+# notice, this list of conditions and the following disclaimer;
+# redistributions in binary form must reproduce the above copyright
+# notice, this list of conditions and the following disclaimer in the
+# documentation and/or other materials provided with the distribution;
+# neither the name of the copyright holders nor the names of its
+# contributors may be used to endorse or promote products derived from
+# this software without specific prior written permission.
+#
+# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+#
+# Authors: Gabe Black
+
+from m5.params import *
+from m5.proxy import *
+from Device import BasicPioDevice
+from X86IntPin import X86IntSourcePin
+
+class I8042(BasicPioDevice):
+ type = 'I8042'
+ cxx_class = 'X86ISA::I8042'
+ pio_latency = Param.Latency('1ns', "Programmed IO latency in simticks")
+ data_port = Param.Addr('Data port address')
+ command_port = Param.Addr('Command/status port address')
+ mouse_int_pin = Param.X86IntSourcePin(X86IntSourcePin(),
+ 'Pin to signal the mouse has data')
+ keyboard_int_pin = Param.X86IntSourcePin(X86IntSourcePin(),
+ 'Pin to signal the keyboard has data')
diff -r 1758d56964c9 -r ee307cca6d31 src/dev/x86/SConscript
--- a/src/dev/x86/SConscript Sat Jan 31 23:56:46 2009 -0800
+++ b/src/dev/x86/SConscript Sat Jan 31 23:59:01 2009 -0800
@@ -53,6 +53,10 @@
Source('i8237.cc')
TraceFlag('I8237', 'The I8237 dma controller');
+ SimObject('I8042.py')
+ Source('i8042.cc')
+ TraceFlag('I8042', 'The I8042 keyboard controller');
+
SimObject('PcSpeaker.py')
Source('speaker.cc')
TraceFlag('PcSpeaker')
diff -r 1758d56964c9 -r ee307cca6d31 src/dev/x86/SouthBridge.py
--- a/src/dev/x86/SouthBridge.py Sat Jan 31 23:56:46 2009 -0800
+++ b/src/dev/x86/SouthBridge.py Sat Jan 31 23:59:01 2009 -0800
@@ -29,6 +29,7 @@
from m5.params import *
from m5.proxy import *
from Cmos import Cmos
+from I8042 import I8042
from I82094AA import I82094AA
from I8237 import I8237
from I8254 import I8254
@@ -50,6 +51,8 @@
_pic2 = I8259(pio_addr=x86IOAddress(0xA0), mode='I8259Slave')
_cmos = Cmos(pio_addr=x86IOAddress(0x70))
_dma1 = I8237(pio_addr=x86IOAddress(0x0))
+ _keyboard = I8042(data_port=x86IOAddress(0x60), \
+ command_port=x86IOAddress(0x64))
_pit = I8254(pio_addr=x86IOAddress(0x40))
_speaker = PcSpeaker(pio_addr=x86IOAddress(0x61))
_io_apic = I82094AA(pio_addr=0xFEC00000)
@@ -61,6 +64,7 @@
pic2 = Param.I8259(_pic2, "Slave PIC")
cmos = Param.Cmos(_cmos, "CMOS memory and real time clock device")
dma1 = Param.I8237(_dma1, "The first dma controller")
+ keyboard = Param.I8042(_keyboard, "The keyboard controller")
pit = Param.I8254(_pit, "Programmable interval timer")
speaker = Param.PcSpeaker(_speaker, "PC speaker")
io_apic = Param.I82094AA(_io_apic, "I/O APIC")
@@ -75,6 +79,14 @@
self.connectPins(self.cmos.int_pin, self.pic2.pin(0))
self.connectPins(self.pit.int_pin, self.pic1.pin(0))
self.connectPins(self.pit.int_pin, self.io_apic.pin(2))
+# self.connectPins(self.keyboard.keyboard_int_pin,
+# self.pic1.pin(1))
+ self.connectPins(self.keyboard.keyboard_int_pin,
+ self.io_apic.pin(1))
+# self.connectPins(self.keyboard.mouse_int_pin,
+# self.pic2.pin(4))
+ self.connectPins(self.keyboard.mouse_int_pin,
+ self.io_apic.pin(12))
# Tell the devices about each other
self.pic1.slave = self.pic2
self.speaker.i8254 = self.pit
@@ -82,6 +94,7 @@
# Connect to the bus
self.cmos.pio = bus.port
self.dma1.pio = bus.port
+ self.keyboard.pio = bus.port
self.pic1.pio = bus.port
self.pic2.pio = bus.port
self.pit.pio = bus.port
diff -r 1758d56964c9 -r ee307cca6d31 src/dev/x86/i8042.cc
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/src/dev/x86/i8042.cc Sat Jan 31 23:59:01 2009 -0800
@@ -0,0 +1,529 @@
+/*
+ * Copyright (c) 2008 The Regents of The University of Michigan
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met: redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer;
+ * redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution;
+ * neither the name of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * Authors: Gabe Black
+ */
+
+#include "base/bitunion.hh"
+#include "dev/x86/i8042.hh"
+#include "mem/packet.hh"
+#include "mem/packet_access.hh"
+
+// The 8042 has a whopping 32 bytes of internal RAM.
+const uint8_t RamSize = 32;
+const uint8_t NumOutputBits = 14;
+const uint8_t KeyboardID[] = {0xab, 0x83};
+const uint8_t MouseID[] = {0x00};
+const uint8_t CommandAck = 0xfa;
+const uint8_t CommandNack = 0xfe;
+const uint8_t BatSuccessful = 0xaa;
+
+enum Port64Command
+{
+ GetCommandByte = 0x20,
+ ReadControllerRamBase = 0x20,
+ WriteCommandByte = 0x60,
+ WriteControllerRamBase = 0x60,
+ CheckForPassword = 0xA4,
+ LoadPassword = 0xA5,
+ CheckPassword = 0xA6,
+ DisableMouse = 0xA7,
+ EnableMouse = 0xA8,
+ TestMouse = 0xA9,
+ SelfTest = 0xAA,
+ InterfaceTest = 0xAB,
+ DiagnosticDump = 0xAC,
+ DisableKeyboard = 0xAD,
+ EnableKeyboard = 0xAE,
+ ReadInputPort = 0xC0,
+ ContinuousPollLow = 0xC1,
+ ContinuousPollHigh = 0xC2,
+ ReadOutputPort = 0xD0,
+ WriteOutputPort = 0xD1,
+ WriteKeyboardOutputBuff = 0xD2,
+ WriteMouseOutputBuff = 0xD3,
+ WriteToMouse = 0xD4,
+ DisableA20 = 0xDD,
+ EnableA20 = 0xDF,
+ ReadTestInputs = 0xE0,
+ PulseOutputBitBase = 0xF0,
+ SystemReset = 0xFE
+};
+
+enum Port60Command
+{
+ MouseScale1to1 = 0xE6,
+ MouseScale2to1 = 0xE7,
+ SetMouseResolution = 0xE8,
+ MouseGetStatus = 0xE9,
+ MouseReadData = 0xEB,
+ MouseResetWrapMode = 0xEC,
+ LEDWrite = 0xED,
+ DiagnosticEcho = 0xEE,
+ MouseWrapMode = 0xEE,
+ AlternateScanCodes = 0xF0,
+ MouseRemoteMode = 0xF0,
+ ReadKeyboardID = 0xF2,
+ ReadMouseID = 0xF2,
+ TypematicInfo = 0xF3,
+ MouseSampleRate = 0xF3,
+ KeyboardEnable = 0xF4,
+ MouseEnableReporting = 0xF4,
+ KeyboardDisable = 0xF5,
+ MouseDisableReporting = 0xF5,
+ DefaultsAndDisableKeyboard = 0xF6,
+ DefaultsAndDisableMouse = 0xF6,
+ AllKeysToTypematic = 0xF7,
+ AllKeysToMakeRelease = 0xF8,
+ AllKeysToMake = 0xF9,
+ AllKeysToTypematicMakeRelease = 0xFA,
+ KeyToTypematic = 0xFB,
+ KeyToMakeRelease = 0xFC,
+ KeyToMakeOnly = 0xFD,
+ Resend = 0xFE,
+ KeyboardReset = 0xFF,
+ MouseReset = 0xFF
+};
+
+void
+X86ISA::I8042::addressRanges(AddrRangeList &range_list)
+{
+ range_list.clear();
+ range_list.push_back(RangeSize(dataPort, 1));
+ range_list.push_back(RangeSize(commandPort, 1));
+}
+
+bool
+X86ISA::I8042::writeData(uint8_t newData, bool mouse)
+{
+ if (!statusReg.outputFull) {
+ DPRINTF(I8042, "Set data %#02x.\n", newData);
+ dataReg = newData;
+ statusReg.outputFull = 1;
+ statusReg.mouseOutputFull = (mouse ? 1 : 0);
+ return true;
+ } else {
+ return false;
+ }
+}
+
+void
+X86ISA::I8042::keyboardAck()
+{
+ while (!keyboardBuffer.empty())
+ keyboardBuffer.pop();
+ writeKeyboardData(&CommandAck, sizeof(CommandAck));
+}
+
+void
+X86ISA::I8042::writeKeyboardData(const uint8_t *data, int size)
+{
+ assert(data || size == 0);
+ while (size) {
+ keyboardBuffer.push(*(data++));
+ size--;
+ }
+ if (writeData(keyboardBuffer.front())) {
+ keyboardBuffer.pop();
+ if (commandByte.keyboardFullInt) {
+ DPRINTF(I8042, "Sending keyboard interrupt.\n");
+ keyboardIntPin->raise();
+ //XXX This is a hack.
+ keyboardIntPin->lower();
+ }
+ }
+}
+
+void
+X86ISA::I8042::mouseAck()
+{
+ while (!mouseBuffer.empty())
+ mouseBuffer.pop();
+ writeMouseData(&CommandAck, sizeof(CommandAck));
+}
+
+void
+X86ISA::I8042::mouseNack()
+{
+ while (!mouseBuffer.empty())
+ mouseBuffer.pop();
+ writeMouseData(&CommandNack, sizeof(CommandAck));
+}
+
+void
+X86ISA::I8042::writeMouseData(const uint8_t *data, int size)
+{
+ assert(data || size == 0);
+ while (size) {
+ mouseBuffer.push(*(data++));
+ size--;
+ }
_______________________________________________
m5-dev mailing list
[email protected]
http://m5sim.org/mailman/listinfo/m5-dev