diff options
Diffstat (limited to 'src/dev')
-rw-r--r-- | src/dev/Pci.py | 19 | ||||
-rw-r--r-- | src/dev/SConscript | 2 | ||||
-rw-r--r-- | src/dev/alpha/Tsunami.py | 17 | ||||
-rw-r--r-- | src/dev/alpha/tsunami.cc | 25 | ||||
-rw-r--r-- | src/dev/alpha/tsunami.hh | 39 | ||||
-rw-r--r-- | src/dev/alpha/tsunami_pchip.cc | 59 | ||||
-rw-r--r-- | src/dev/alpha/tsunami_pchip.hh | 32 | ||||
-rw-r--r-- | src/dev/arm/RealView.py | 30 | ||||
-rw-r--r-- | src/dev/arm/realview.cc | 49 | ||||
-rw-r--r-- | src/dev/arm/realview.hh | 44 | ||||
-rw-r--r-- | src/dev/pci/PciHost.py | 64 | ||||
-rw-r--r-- | src/dev/pci/SConscript | 48 | ||||
-rw-r--r-- | src/dev/pci/host.cc | 228 | ||||
-rw-r--r-- | src/dev/pci/host.hh | 330 | ||||
-rw-r--r-- | src/dev/pci/types.hh | 74 | ||||
-rw-r--r-- | src/dev/pciconfigall.cc | 94 | ||||
-rw-r--r-- | src/dev/pciconfigall.hh | 83 | ||||
-rw-r--r-- | src/dev/pcidev.cc | 77 | ||||
-rw-r--r-- | src/dev/pcidev.hh | 87 | ||||
-rw-r--r-- | src/dev/platform.cc | 22 | ||||
-rw-r--r-- | src/dev/platform.hh | 30 | ||||
-rw-r--r-- | src/dev/x86/Pc.py | 13 | ||||
-rw-r--r-- | src/dev/x86/SouthBridge.py | 1 | ||||
-rw-r--r-- | src/dev/x86/pc.cc | 27 | ||||
-rw-r--r-- | src/dev/x86/pc.hh | 41 |
25 files changed, 901 insertions, 634 deletions
diff --git a/src/dev/Pci.py b/src/dev/Pci.py index ef7137186..4fbe56fd0 100644 --- a/src/dev/Pci.py +++ b/src/dev/Pci.py @@ -41,29 +41,20 @@ from m5.SimObject import SimObject from m5.params import * from m5.proxy import * -from Device import BasicPioDevice, DmaDevice, PioDevice - -class PciConfigAll(BasicPioDevice): - type = 'PciConfigAll' - cxx_header = "dev/pciconfigall.hh" - platform = Param.Platform(Parent.any, "Platform this device is part of.") - bus = Param.UInt8(0x00, "PCI bus to act as config space for") - size = Param.MemorySize32('16MB', "Size of config space") - - pio_latency = '30ns' - pio_addr = 0 # will be overridden by platform-based calculation - +from Device import DmaDevice +from PciHost import PciHost class PciDevice(DmaDevice): type = 'PciDevice' cxx_class = 'PciDevice' cxx_header = "dev/pcidev.hh" abstract = True - platform = Param.Platform(Parent.any, "Platform this device is part of.") - config = SlavePort("PCI configuration space port") + + host = Param.PciHost(Parent.any, "PCI host") pci_bus = Param.Int("PCI bus") pci_dev = Param.Int("PCI device number") pci_func = Param.Int("PCI function code") + pio_latency = Param.Latency('30ns', "Programmed IO latency") config_latency = Param.Latency('20ns', "Config read or write latency") diff --git a/src/dev/SConscript b/src/dev/SConscript index cd99e984a..f2a172287 100644 --- a/src/dev/SConscript +++ b/src/dev/SConscript @@ -73,7 +73,6 @@ Source('ide_disk.cc') Source('intel_8254_timer.cc') Source('mc146818.cc') Source('ns_gige.cc') -Source('pciconfigall.cc') Source('pcidev.cc') Source('pixelpump.cc') Source('pktfifo.cc') @@ -105,7 +104,6 @@ DebugFlag('IdeDisk') DebugFlag('Intel8254Timer') DebugFlag('MC146818') DebugFlag('PCIDEV') -DebugFlag('PciConfigAll') DebugFlag('SimpleDisk') DebugFlag('SimpleDiskData') DebugFlag('Terminal') diff --git a/src/dev/alpha/Tsunami.py b/src/dev/alpha/Tsunami.py index 1a29b25d9..f807e946f 100644 --- a/src/dev/alpha/Tsunami.py +++ b/src/dev/alpha/Tsunami.py @@ -31,7 +31,7 @@ from m5.proxy import * from BadDevice import BadDevice from AlphaBackdoor import AlphaBackdoor from Device import BasicPioDevice, IsaFake, BadAddr -from Pci import PciConfigAll +from PciHost import GenericPciHost from Platform import Platform from Uart import Uart8250 @@ -50,9 +50,19 @@ class TsunamiIO(BasicPioDevice): tsunami = Param.Tsunami(Parent.any, "Tsunami") frequency = Param.Frequency('1024Hz', "frequency of interrupts") -class TsunamiPChip(BasicPioDevice): +class TsunamiPChip(GenericPciHost): type = 'TsunamiPChip' cxx_header = "dev/alpha/tsunami_pchip.hh" + + conf_base = 0x801fe000000 + conf_size = "16MB" + + pci_pio_base = 0x801fc000000 + pci_mem_base = 0x80000000000 + + pio_addr = Param.Addr("Device Address") + pio_latency = Param.Latency('100ns', "Programmed IO latency") + tsunami = Param.Tsunami(Parent.any, "Tsunami") class Tsunami(Platform): @@ -62,7 +72,6 @@ class Tsunami(Platform): cchip = TsunamiCChip(pio_addr=0x801a0000000) pchip = TsunamiPChip(pio_addr=0x80180000000) - pciconfig = PciConfigAll() fake_sm_chip = IsaFake(pio_addr=0x801fc000370) fake_uart1 = IsaFake(pio_addr=0x801fc0002f8) @@ -99,8 +108,6 @@ class Tsunami(Platform): def attachIO(self, bus): self.cchip.pio = bus.master self.pchip.pio = bus.master - self.pciconfig.pio = bus.default - bus.use_default_range = True self.fake_sm_chip.pio = bus.master self.fake_uart1.pio = bus.master self.fake_uart2.pio = bus.master diff --git a/src/dev/alpha/tsunami.cc b/src/dev/alpha/tsunami.cc index 36b1a9ded..300b481de 100644 --- a/src/dev/alpha/tsunami.cc +++ b/src/dev/alpha/tsunami.cc @@ -88,31 +88,6 @@ Tsunami::clearPciInt(int line) cchip->clearDRIR(line); } -Addr -Tsunami::pciToDma(Addr pciAddr) const -{ - return pchip->translatePciToDma(pciAddr); -} - - -Addr -Tsunami::calcPciConfigAddr(int bus, int dev, int func) -{ - return pchip->calcConfigAddr(bus, dev, func); -} - -Addr -Tsunami::calcPciIOAddr(Addr addr) -{ - return pchip->calcIOAddr(addr); -} - -Addr -Tsunami::calcPciMemAddr(Addr addr) -{ - return pchip->calcMemAddr(addr); -} - void Tsunami::serialize(CheckpointOut &cp) const { diff --git a/src/dev/alpha/tsunami.hh b/src/dev/alpha/tsunami.hh index c43f0e023..00df27c5c 100644 --- a/src/dev/alpha/tsunami.hh +++ b/src/dev/alpha/tsunami.hh @@ -86,46 +86,15 @@ class Tsunami : public Platform typedef TsunamiParams Params; Tsunami(const Params *p); - /** - * Cause the cpu to post a serial interrupt to the CPU. - */ - void postConsoleInt() override; + void serialize(CheckpointOut &cp) const override; + void unserialize(CheckpointIn &cp) override; - /** - * Clear a posted CPU interrupt (id=55) - */ + public: // Public Platform interfaces + void postConsoleInt() override; void clearConsoleInt() override; - /** - * Cause the chipset to post a cpi interrupt to the CPU. - */ void postPciInt(int line) override; - - /** - * Clear a posted PCI->CPU interrupt - */ void clearPciInt(int line) override; - - - Addr pciToDma(Addr pciAddr) const override; - - /** - * Calculate the configuration address given a bus/dev/func. - */ - Addr calcPciConfigAddr(int bus, int dev, int func) override; - - /** - * Calculate the address for an IO location on the PCI bus. - */ - Addr calcPciIOAddr(Addr addr) override; - - /** - * Calculate the address for a memory location on the PCI bus. - */ - Addr calcPciMemAddr(Addr addr) override; - - void serialize(CheckpointOut &cp) const override; - void unserialize(CheckpointIn &cp) override; }; #endif // __DEV_TSUNAMI_HH__ diff --git a/src/dev/alpha/tsunami_pchip.cc b/src/dev/alpha/tsunami_pchip.cc index cfd1e69e4..fa3d9d395 100644 --- a/src/dev/alpha/tsunami_pchip.cc +++ b/src/dev/alpha/tsunami_pchip.cc @@ -32,6 +32,7 @@ /** @file * Tsunami PChip (pci) */ +#include "dev/alpha/tsunami_pchip.hh" #include <deque> #include <string> @@ -41,8 +42,9 @@ #include "config/the_isa.hh" #include "debug/Tsunami.hh" #include "dev/alpha/tsunami.hh" -#include "dev/alpha/tsunami_pchip.hh" +#include "dev/alpha/tsunami_cchip.hh" #include "dev/alpha/tsunamireg.h" +#include "dev/pcidev.hh" #include "mem/packet.hh" #include "mem/packet_access.hh" #include "sim/system.hh" @@ -52,7 +54,9 @@ using namespace std; using namespace TheISA; TsunamiPChip::TsunamiPChip(const Params *p) - : BasicPioDevice(p, 0x1000) + : GenericPciHost(p), + pioRange(RangeSize(p->pio_addr, 0x1000)), + pioDelay(p->pio_latency) { for (int i = 0; i < 4; i++) { wsba[i] = 0; @@ -70,9 +74,12 @@ TsunamiPChip::TsunamiPChip(const Params *p) Tick TsunamiPChip::read(PacketPtr pkt) { - assert(pkt->getAddr() >= pioAddr && pkt->getAddr() < pioAddr + pioSize); + // We only need to handle our own configuration registers, pass + // unknown addresses to the generic code. + if (!pioRange.contains(pkt->getAddr())) + return GenericPciHost::read(pkt); - Addr daddr = (pkt->getAddr() - pioAddr) >> 6;; + Addr daddr = (pkt->getAddr() - pioRange.start()) >> 6;; assert(pkt->getSize() == sizeof(uint64_t)); @@ -142,6 +149,7 @@ TsunamiPChip::read(PacketPtr pkt) default: panic("Default in PChip Read reached reading 0x%x\n", daddr); } + pkt->makeAtomicResponse(); return pioDelay; @@ -150,8 +158,12 @@ TsunamiPChip::read(PacketPtr pkt) Tick TsunamiPChip::write(PacketPtr pkt) { - assert(pkt->getAddr() >= pioAddr && pkt->getAddr() < pioAddr + pioSize); - Addr daddr = (pkt->getAddr() - pioAddr) >> 6; + // We only need to handle our own configuration registers, pass + // unknown addresses to the generic code. + if (!pioRange.contains(pkt->getAddr())) + return GenericPciHost::write(pkt); + + Addr daddr = (pkt->getAddr() - pioRange.start()) >> 6; assert(pkt->getSize() == sizeof(uint64_t)); @@ -224,10 +236,21 @@ TsunamiPChip::write(PacketPtr pkt) return pioDelay; } + +AddrRangeList +TsunamiPChip::getAddrRanges() const +{ + return AddrRangeList({ + RangeSize(confBase, confSize), + pioRange + }); +} + + #define DMA_ADDR_MASK ULL(0x3ffffffff) Addr -TsunamiPChip::translatePciToDma(Addr busAddr) +TsunamiPChip::dmaAddr(const PciBusAddr &dev, Addr busAddr) const { // compare the address to the window base registers uint64_t tbaMask = 0; @@ -301,28 +324,6 @@ TsunamiPChip::translatePciToDma(Addr busAddr) return busAddr; } -Addr -TsunamiPChip::calcConfigAddr(int bus, int dev, int func) -{ - assert(func < 8); - assert(dev < 32); - assert(bus == 0); - - return TsunamiPciBus0Config | (func << 8) | (dev << 11); -} - -Addr -TsunamiPChip::calcIOAddr(Addr addr) -{ - return TSUNAMI_PCI0_IO + addr; -} - -Addr -TsunamiPChip::calcMemAddr(Addr addr) -{ - return TSUNAMI_PCI0_MEMORY + addr; -} - void TsunamiPChip::serialize(CheckpointOut &cp) const { diff --git a/src/dev/alpha/tsunami_pchip.hh b/src/dev/alpha/tsunami_pchip.hh index 68bd20e9a..212727d61 100644 --- a/src/dev/alpha/tsunami_pchip.hh +++ b/src/dev/alpha/tsunami_pchip.hh @@ -36,18 +36,16 @@ #define __TSUNAMI_PCHIP_HH__ #include "dev/alpha/tsunami.hh" -#include "dev/io_device.hh" +#include "dev/pci/host.hh" #include "params/TsunamiPChip.hh" /** * A very simple implementation of the Tsunami PCI interface chips. */ -class TsunamiPChip : public BasicPioDevice +class TsunamiPChip : public GenericPciHost { protected: - static const Addr TsunamiPciBus0Config = ULL(0x801fe000000); - /** Pchip control register */ uint64_t pctl; @@ -74,23 +72,27 @@ class TsunamiPChip : public BasicPioDevice return dynamic_cast<const Params *>(_params); } + + void serialize(CheckpointOut &cp) const override; + void unserialize(CheckpointIn &cp) override; + + public: + Tick read(PacketPtr pkt) override; + Tick write(PacketPtr pkt) override; + + AddrRangeList getAddrRanges() const override; + /** * Translate a PCI bus address to a memory address for DMA. * @todo Andrew says this needs to be fixed. What's wrong with it? - * @param busAddr PCI address to translate. + * @param pci_addr PCI address to translate. * @return memory system address */ - Addr translatePciToDma(Addr busAddr); - - Addr calcConfigAddr(int bus, int dev, int func); - Addr calcIOAddr(Addr addr); - Addr calcMemAddr(Addr addr); - - Tick read(PacketPtr pkt) override; - Tick write(PacketPtr pkt) override; + Addr dmaAddr(const PciBusAddr &addr, Addr pci_addr) const override; - void serialize(CheckpointOut &cp) const override; - void unserialize(CheckpointIn &cp) override; + protected: + const AddrRange pioRange; + const Tick pioDelay; }; #endif // __TSUNAMI_PCHIP_HH__ diff --git a/src/dev/arm/RealView.py b/src/dev/arm/RealView.py index db38b6bbd..78154bcfd 100644 --- a/src/dev/arm/RealView.py +++ b/src/dev/arm/RealView.py @@ -45,7 +45,7 @@ from m5.proxy import * from ClockDomain import ClockDomain from VoltageDomain import VoltageDomain from Device import BasicPioDevice, PioDevice, IsaFake, BadAddr, DmaDevice -from Pci import PciConfigAll +from PciHost import * from Ethernet import NSGigE, IGbE_igb, IGbE_e1000 from Ide import * from Platform import Platform @@ -255,10 +255,6 @@ class RealView(Platform): type = 'RealView' cxx_header = "dev/arm/realview.hh" system = Param.System(Parent.any, "system") - pci_io_base = Param.Addr(0, "Base address of PCI IO Space") - pci_cfg_base = Param.Addr(0, "Base address of PCI Configuraiton Space") - pci_cfg_gen_offsets = Param.Bool(False, "Should the offsets used for PCI cfg access" - " be compatible with the pci-generic-host or the legacy host bridge?") _mem_regions = [(Addr(0), Addr('256MB'))] def attachPciDevices(self): @@ -292,6 +288,9 @@ class RealViewPBX(RealView): mcc = VExpressMCC() dcc = CoreTile2A15DCC() gic = Pl390() + pci_host = GenericPciHost( + conf_base=0x30000000, conf_size='256MB', conf_device_bits=16, + pci_pio_base=0) timer0 = Sp804(int_num0=36, int_num1=36, pio_addr=0x10011000) timer1 = Sp804(int_num0=37, int_num1=37, pio_addr=0x10012000) local_cpu_timer = CpuLocalTimer(int_num_timer=29, int_num_watchdog=30, pio_addr=0x1f000600) @@ -356,6 +355,7 @@ class RealViewPBX(RealView): def attachIO(self, bus): self.uart.pio = bus.master self.realview_io.pio = bus.master + self.pci_host.pio = bus.master self.timer0.pio = bus.master self.timer1.pio = bus.master self.clcd.pio = bus.master @@ -363,7 +363,6 @@ class RealViewPBX(RealView): self.kmi0.pio = bus.master self.kmi1.pio = bus.master self.cf_ctrl.pio = bus.master - self.cf_ctrl.config = bus.master self.cf_ctrl.dma = bus.slave self.dmac_fake.pio = bus.master self.uart1_fake.pio = bus.master @@ -471,6 +470,7 @@ class RealViewEB(RealView): def attachIO(self, bus): self.uart.pio = bus.master self.realview_io.pio = bus.master + self.pci_host.pio = bus.master self.timer0.pio = bus.master self.timer1.pio = bus.master self.clcd.pio = bus.master @@ -527,7 +527,6 @@ class RealViewEB(RealView): class VExpress_EMM(RealView): _mem_regions = [(Addr('2GB'), Addr('2GB'))] - pci_cfg_base = 0x30000000 uart = Pl011(pio_addr=0x1c090000, int_num=37) realview_io = RealViewCtrl( proc_id0=0x14000000, proc_id1=0x14000000, @@ -535,6 +534,9 @@ class VExpress_EMM(RealView): mcc = VExpressMCC() dcc = CoreTile2A15DCC() gic = Pl390(dist_addr=0x2C001000, cpu_addr=0x2C002000) + pci_host = GenericPciHost( + conf_base=0x30000000, conf_size='256MB', conf_device_bits=16, + pci_pio_base=0) local_cpu_timer = CpuLocalTimer(int_num_timer=29, int_num_watchdog=30, pio_addr=0x2C080000) generic_timer = GenericTimer(int_phys=29, int_virt=27) timer0 = Sp804(int_num0=34, int_num1=34, pio_addr=0x1C110000, clock0='1MHz', clock1='1MHz') @@ -552,7 +554,6 @@ class VExpress_EMM(RealView): BAR1 = 0x1C1A0100, BAR1Size = '4096B', BAR0LegacyIO = True, BAR1LegacyIO = True) - pciconfig = PciConfigAll(size='256MB') vram = SimpleMemory(range = AddrRange(0x18000000, size='32MB'), conf_table_reported = False) rtc = PL031(pio_addr=0x1C170000, int_num=36) @@ -624,6 +625,7 @@ class VExpress_EMM(RealView): def attachIO(self, bus): self.uart.pio = bus.master self.realview_io.pio = bus.master + self.pci_host.pio = bus.master self.timer0.pio = bus.master self.timer1.pio = bus.master self.clcd.pio = bus.master @@ -633,11 +635,8 @@ class VExpress_EMM(RealView): self.kmi1.pio = bus.master self.cf_ctrl.pio = bus.master self.cf_ctrl.dma = bus.slave - self.cf_ctrl.config = bus.master self.rtc.pio = bus.master - bus.use_default_range = True self.vram.port = bus.master - self.pciconfig.pio = bus.default self.l2x0_fake.pio = bus.master self.uart1_fake.pio = bus.master @@ -654,10 +653,8 @@ class VExpress_EMM(RealView): # Try to attach the I/O if it exists try: self.ide.pio = bus.master - self.ide.config = bus.master self.ide.dma = bus.slave self.ethernet.pio = bus.master - self.ethernet.config = bus.master self.ethernet.dma = bus.slave except: pass @@ -675,7 +672,6 @@ class VExpress_EMM(RealView): self.cf_ctrl.clk_domain = clkdomain self.rtc.clk_domain = clkdomain self.vram.clk_domain = clkdomain - self.pciconfig.clk_domain = clkdomain self.l2x0_fake.clk_domain = clkdomain self.uart1_fake.clk_domain = clkdomain @@ -690,11 +686,13 @@ class VExpress_EMM(RealView): self.energy_ctrl.clk_domain = clkdomain class VExpress_EMM64(VExpress_EMM): - pci_io_base = 0x2f000000 - pci_cfg_gen_offsets = True # Three memory regions are specified totalling 512GB _mem_regions = [(Addr('2GB'), Addr('2GB')), (Addr('34GB'), Addr('30GB')), (Addr('512GB'), Addr('480GB'))] + pci_host = GenericPciHost( + conf_base=0x30000000, conf_size='256MB', conf_device_bits=12, + pci_pio_base=0x2f000000) + def setupBootLoader(self, mem_bus, cur_sys, loc): self.nvmem = SimpleMemory(range = AddrRange(0, size = '64MB')) self.nvmem.port = mem_bus.master diff --git a/src/dev/arm/realview.cc b/src/dev/arm/realview.cc index a4c1191b3..2a6bc63f3 100644 --- a/src/dev/arm/realview.cc +++ b/src/dev/arm/realview.cc @@ -58,26 +58,12 @@ using namespace std; using namespace TheISA; + RealView::RealView(const Params *p) : Platform(p), system(p->system), gic(nullptr) {} void -RealView::initState() -{ - Addr junk; - bool has_gen_pci_host; - has_gen_pci_host = system->kernelSymtab->findAddress("gen_pci_setup", junk); - - if (has_gen_pci_host && !params()->pci_cfg_gen_offsets) - warn("Kernel supports generic PCI host but PCI Config offsets " - "configured for legacy. Set pci_cfg_gen_offsets to True"); - if (has_gen_pci_host && !params()->pci_io_base) - warn("Kernel supports generic PCI host but PCI IO base is set " - "to 0. Set pci_io_base to the start of PCI IO space"); -} - -void RealView::postConsoleInt() { warn_once("Don't know what interrupt to post for console.\n"); @@ -103,39 +89,6 @@ RealView::clearPciInt(int line) gic->clearInt(line); } -Addr -RealView::pciToDma(Addr pciAddr) const -{ - return pciAddr; -} - - -Addr -RealView::calcPciConfigAddr(int bus, int dev, int func) -{ - if (bus != 0) - return ULL(-1); - - Addr cfg_offset = 0; - if (params()->pci_cfg_gen_offsets) - cfg_offset |= ((func & 7) << 12) | ((dev & 0x1f) << 15); - else - cfg_offset |= ((func & 7) << 16) | ((dev & 0x1f) << 19); - return params()->pci_cfg_base | cfg_offset; -} - -Addr -RealView::calcPciIOAddr(Addr addr) -{ - return params()->pci_io_base + addr; -} - -Addr -RealView::calcPciMemAddr(Addr addr) -{ - return addr; -} - RealView * RealViewParams::create() { diff --git a/src/dev/arm/realview.hh b/src/dev/arm/realview.hh index 5129069d4..eaaec9425 100644 --- a/src/dev/arm/realview.hh +++ b/src/dev/arm/realview.hh @@ -79,49 +79,15 @@ class RealView : public Platform */ RealView(const Params *p); - /** In init do some checks to help verify we're setup correctly */ - virtual void initState(); - /** Give platform a pointer to interrupt controller */ void setGic(BaseGic *_gic) { gic = _gic; } - /** - * Cause the cpu to post a serial interrupt to the CPU. - */ - virtual void postConsoleInt(); - - /** - * Clear a posted CPU interrupt - */ - virtual void clearConsoleInt(); - - /** - * Cause the chipset to post a cpi interrupt to the CPU. - */ - virtual void postPciInt(int line); - - /** - * Clear a posted PCI->CPU interrupt - */ - virtual void clearPciInt(int line); - - - virtual Addr pciToDma(Addr pciAddr) const; - - /** - * Calculate the configuration address given a bus/dev/func. - */ - virtual Addr calcPciConfigAddr(int bus, int dev, int func); + public: // Public Platform interfaces + void postConsoleInt() override; + void clearConsoleInt() override; - /** - * Calculate the address for an IO location on the PCI bus. - */ - virtual Addr calcPciIOAddr(Addr addr); - - /** - * Calculate the address for a memory location on the PCI bus. - */ - virtual Addr calcPciMemAddr(Addr addr); + void postPciInt(int line) override; + void clearPciInt(int line) override; }; #endif // __DEV_ARM_RealView_HH__ diff --git a/src/dev/pci/PciHost.py b/src/dev/pci/PciHost.py new file mode 100644 index 000000000..f4f9e45e8 --- /dev/null +++ b/src/dev/pci/PciHost.py @@ -0,0 +1,64 @@ +# Copyright (c) 2015 ARM Limited +# All rights reserved +# +# The license below extends only to copyright in the software and shall +# not be construed as granting a license to any other intellectual +# property including but not limited to intellectual property relating +# to a hardware implementation of the functionality of the software +# licensed hereunder. You may use the software subject to the license +# terms below provided that you ensure that this notice is replicated +# unmodified and in its entirety in all distributions of the software, +# modified or unmodified, in source code or in binary form. +# +# 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: Andreas Sandberg + +from m5.SimObject import SimObject +from m5.params import * +from m5.proxy import * +from Device import PioDevice +from Platform import Platform + +class PciHost(PioDevice): + type = 'PciHost' + cxx_class = 'PciHost' + cxx_header = "dev/pci/host.hh" + abstract = True + +class GenericPciHost(PciHost): + type = 'GenericPciHost' + cxx_class = 'GenericPciHost' + cxx_header = "dev/pci/host.hh" + + platform = Param.Platform(Parent.any, "Platform to use for interrupts") + + conf_base = Param.Addr("Config space base address") + conf_size = Param.Addr("Config space base address") + conf_device_bits = Param.UInt8(8, "Number of bits used to as an " + "offset a devices address space") + + pci_pio_base = Param.Addr(0, "Base address for PCI IO accesses") + pci_mem_base = Param.Addr(0, "Base address for PCI memory accesses") + pci_dma_base = Param.Addr(0, "Base address for DMA memory accesses") diff --git a/src/dev/pci/SConscript b/src/dev/pci/SConscript new file mode 100644 index 000000000..b892a2905 --- /dev/null +++ b/src/dev/pci/SConscript @@ -0,0 +1,48 @@ +# -*- mode:python -*- + +# Copyright (c) 2015 ARM Limited +# All rights reserved. +# +# The license below extends only to copyright in the software and shall +# not be construed as granting a license to any other intellectual +# property including but not limited to intellectual property relating +# to a hardware implementation of the functionality of the software +# licensed hereunder. You may use the software subject to the license +# terms below provided that you ensure that this notice is replicated +# unmodified and in its entirety in all distributions of the software, +# modified or unmodified, in source code or in binary form. +# +# 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: Andreas Sandberg + +Import('*') + +if env['TARGET_ISA'] == 'null': + Return() + +SimObject('PciHost.py') +Source('host.cc') + +DebugFlag('PciHost') diff --git a/src/dev/pci/host.cc b/src/dev/pci/host.cc new file mode 100644 index 000000000..bcf49df86 --- /dev/null +++ b/src/dev/pci/host.cc @@ -0,0 +1,228 @@ +/* + * Copyright (c) 2015 ARM Limited + * All rights reserved + * + * The license below extends only to copyright in the software and shall + * not be construed as granting a license to any other intellectual + * property including but not limited to intellectual property relating + * to a hardware implementation of the functionality of the software + * licensed hereunder. You may use the software subject to the license + * terms below provided that you ensure that this notice is replicated + * unmodified and in its entirety in all distributions of the software, + * modified or unmodified, in source code or in binary form. + * + * 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: Andreas Sandberg + */ + +#include "dev/pci/host.hh" + +#include <utility> + +#include "debug/PciHost.hh" +#include "dev/pcidev.hh" +#include "dev/platform.hh" +#include "params/GenericPciHost.hh" +#include "params/PciHost.hh" + + +PciHost::PciHost(const PciHostParams *p) + : PioDevice(p) +{ +} + +PciHost::~PciHost() +{ +} + +PciHost::DeviceInterface +PciHost::registerDevice(PciDevice *device, PciBusAddr bus_addr, PciIntPin pin) +{ + auto map_entry = devices.emplace(bus_addr, device); + + DPRINTF(PciHost, "%02x:%02x.%i: Registering device\n", + bus_addr.bus, bus_addr.dev, bus_addr.func); + + fatal_if(!map_entry.second, + "%02x:%02x.%i: PCI bus ID collision\n", + bus_addr.bus, bus_addr.dev, bus_addr.func); + + return DeviceInterface(*this, bus_addr, pin); +} + +PciDevice * +PciHost::getDevice(const PciBusAddr &addr) +{ + auto device = devices.find(addr); + return device != devices.end() ? device->second : nullptr; +} + +const PciDevice * +PciHost::getDevice(const PciBusAddr &addr) const +{ + auto device = devices.find(addr); + return device != devices.end() ? device->second : nullptr; +} + +PciHost::DeviceInterface::DeviceInterface( + PciHost &_host, + PciBusAddr &bus_addr, PciIntPin interrupt_pin) + : host(_host), + busAddr(bus_addr), interruptPin(interrupt_pin) +{ +} + +const std::string +PciHost::DeviceInterface::name() const +{ + return csprintf("%s.interface[%02x:%02x.%i]", + host.name(), busAddr.bus, busAddr.dev, busAddr.func); +} + +void +PciHost::DeviceInterface::postInt() +{ + DPRINTF(PciHost, "postInt\n"); + + host.postInt(busAddr, interruptPin); +} + +void +PciHost::DeviceInterface::clearInt() +{ + DPRINTF(PciHost, "clearInt\n"); + + host.clearInt(busAddr, interruptPin); +} + + +GenericPciHost::GenericPciHost(const GenericPciHostParams *p) + : PciHost(p), + platform(*p->platform), + confBase(p->conf_base), confSize(p->conf_size), + confDeviceBits(p->conf_device_bits), + pciPioBase(p->pci_pio_base), pciMemBase(p->pci_mem_base), + pciDmaBase(p->pci_dma_base) +{ +} + +GenericPciHost::~GenericPciHost() +{ +} + + +Tick +GenericPciHost::read(PacketPtr pkt) +{ + const auto dev_addr(decodeAddress(pkt->getAddr() - confBase)); + const Addr size(pkt->getSize()); + + DPRINTF(PciHost, "%02x:%02x.%i: read: offset=0x%x, size=0x%x\n", + dev_addr.first.bus, dev_addr.first.dev, dev_addr.first.func, + dev_addr.second, + size); + + PciDevice *const pci_dev(getDevice(dev_addr.first)); + if (pci_dev) { + // @todo Remove this after testing + pkt->headerDelay = pkt->payloadDelay = 0; + return pci_dev->readConfig(pkt); + } else { + uint8_t *pkt_data(pkt->getPtr<uint8_t>()); + std::fill(pkt_data, pkt_data + size, 0xFF); + pkt->makeAtomicResponse(); + return 0; + } +} + +Tick +GenericPciHost::write(PacketPtr pkt) +{ + const auto dev_addr(decodeAddress(pkt->getAddr() - confBase)); + + DPRINTF(PciHost, "%02x:%02x.%i: write: offset=0x%x, size=0x%x\n", + dev_addr.first.bus, dev_addr.first.dev, dev_addr.first.func, + dev_addr.second, + pkt->getSize()); + + PciDevice *const pci_dev(getDevice(dev_addr.first)); + panic_if(!pci_dev, + "%02x:%02x.%i: Write to config space on non-existent PCI device\n", + dev_addr.first.bus, dev_addr.first.dev, dev_addr.first.func); + + // @todo Remove this after testing + pkt->headerDelay = pkt->payloadDelay = 0; + + return pci_dev->writeConfig(pkt); +} + +AddrRangeList +GenericPciHost::getAddrRanges() const +{ + return AddrRangeList({ RangeSize(confBase, confSize) }); +} + +std::pair<PciBusAddr, Addr> +GenericPciHost::decodeAddress(Addr addr) +{ + const Addr offset(addr & mask(confDeviceBits)); + const Addr bus_addr(addr >> confDeviceBits); + + return std::make_pair( + PciBusAddr(bits(bus_addr, 15, 8), + bits(bus_addr, 7, 3), + bits(bus_addr, 2, 0)), + offset); +} + + +void +GenericPciHost::postInt(const PciBusAddr &addr, PciIntPin pin) +{ + platform.postPciInt(mapPciInterrupt(addr, pin)); +} + +void +GenericPciHost::clearInt(const PciBusAddr &addr, PciIntPin pin) +{ + platform.clearPciInt(mapPciInterrupt(addr, pin)); +} + + +uint32_t +GenericPciHost::mapPciInterrupt(const PciBusAddr &addr, PciIntPin pin) const +{ + const PciDevice *dev(getDevice(addr)); + assert(dev); + + return dev->interruptLine(); +} + + +GenericPciHost * +GenericPciHostParams::create() +{ + return new GenericPciHost(this); +} diff --git a/src/dev/pci/host.hh b/src/dev/pci/host.hh new file mode 100644 index 000000000..0e6d580ab --- /dev/null +++ b/src/dev/pci/host.hh @@ -0,0 +1,330 @@ +/* + * Copyright (c) 2015 ARM Limited + * All rights reserved + * + * The license below extends only to copyright in the software and shall + * not be construed as granting a license to any other intellectual + * property including but not limited to intellectual property relating + * to a hardware implementation of the functionality of the software + * licensed hereunder. You may use the software subject to the license + * terms below provided that you ensure that this notice is replicated + * unmodified and in its entirety in all distributions of the software, + * modified or unmodified, in source code or in binary form. + * + * 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: Andreas Sandberg + */ + +#ifndef __DEV_PCI_HOST_HH__ +#define __DEV_PCI_HOST_HH__ + +#include "dev/io_device.hh" +#include "dev/pci/types.hh" + +struct PciHostParams; +struct GenericPciHostParams; + +class PciDevice; +class Platform; + +/** + * The PCI host describes the interface between PCI devices and a + * simulated system. + * + * The PCI host controller has three main responsibilities: + * <ol> + * <li>Expose a configuration memory space that allows devices to + * be discovered and configured. + * <li>Map and deliver interrupts to the CPU. + * <li>Map memory addresses from the PCI bus's various memory + * spaces (Legacy IO, non-prefetchable memory, and + * prefetchable memory) to physical memory. + * </ol> + * + * PCI devices need to register themselves with a PCI host using the + * PciHost::registerDevice() call. This call returns a + * PciHost::DeviceInterface that provides for common functionality + * such as interrupt delivery and memory mapping. + * + * The PciHost class itself provides very little functionality. Simple + * PciHost functionality is implemented by the GenericPciHost class. + */ +class PciHost : public PioDevice +{ + public: + PciHost(const PciHostParams *p); + virtual ~PciHost(); + + public: + /** + * @{ + * @name Device interface + */ + + /** + * Callback interface from PCI devices to the host. + * + * Devices get an instance of this object when they register + * themselves with the host using the PciHost::registerDevice() + * call. + */ + class DeviceInterface + { + friend class ::PciHost; + + protected: + /** + * Instantiate a device interface + * + * @param host PCI host that this device belongs to. + * @param bus_addr The device's position on the PCI bus + * @param pin Interrupt pin + */ + DeviceInterface(PciHost &host, PciBusAddr &bus_addr, PciIntPin pin); + + public: + DeviceInterface() = delete; + void operator=(const DeviceInterface &) = delete; + + const std::string name() const; + + /** + * Post a PCI interrupt to the CPU. + */ + void postInt(); + + /** + * Clear a posted PCI interrupt + */ + void clearInt(); + + /** + * Calculate the physical address of an IO location on the PCI + * bus. + * + * @param addr Address in the PCI IO address space + * @return Address in the system's physical address space. + */ + Addr pioAddr(Addr addr) const { return host.pioAddr(busAddr, addr); } + + /** + * Calculate the physical address of a non-prefetchable memory + * location in the PCI address space. + * + * @param addr Address in the PCI memory address space + * @return Address in the system's physical address space. + */ + Addr memAddr(Addr addr) const { return host.memAddr(busAddr, addr); } + + /** + * Calculate the physical address of a prefetchable memory + * location in the PCI address space. + * + * @param addr Address in the PCI DMA memory address space + * @return Address in the system's physical address space. + */ + Addr dmaAddr(Addr addr) const { return host.dmaAddr(busAddr, addr); } + + protected: + PciHost &host; + + const PciBusAddr busAddr; + const PciIntPin interruptPin; + }; + + /** + * Register a PCI device with the host. + * + * @param device Device to register + * @param bus_addr The device's position on the PCI bus + * @param pin Interrupt pin + * @return A device-specific DeviceInterface instance. + */ + virtual DeviceInterface registerDevice(PciDevice *device, + PciBusAddr bus_addr, PciIntPin pin); + + /** @} */ + + protected: + /** + * @{ + * @name PciHost controller interface + */ + + /** + * Post an interrupt to the CPU. + * + * @param bus_addr The device's position on the PCI bus + * @param pin PCI interrupt pin + */ + virtual void postInt(const PciBusAddr &bus_addr, PciIntPin pin) = 0; + + /** + * Post an interrupt to the CPU. + * + * @param bus_addr The device's position on the PCI bus + * @param pin PCI interrupt pin + */ + virtual void clearInt(const PciBusAddr &bus_addr, PciIntPin pin) = 0; + + /** + * Calculate the physical address of an IO location on the PCI + * bus. + * + * @param bus_addr The device's position on the PCI bus + * @param pci_addr Address in the PCI IO address space + * @return Address in the system's physical address space. + */ + virtual Addr pioAddr(const PciBusAddr &bus_addr, Addr pci_addr) const = 0; + + /** + * Calculate the physical address of a non-prefetchable memory + * location in the PCI address space. + * + * @param bus_addr The device's position on the PCI bus + * @param pci_addr Address in the PCI memory address space + * @return Address in the system's physical address space. + */ + virtual Addr memAddr(const PciBusAddr &bus_addr, Addr pci_addr) const = 0; + + + /** + * Calculate the physical address of a prefetchable memory + * location in the PCI address space. + * + * @param bus_addr The device's position on the PCI bus + * @param pci_addr Address in the PCI DMA memory address space + * @return Address in the system's physical address space. + */ + virtual Addr dmaAddr(const PciBusAddr &bus_addr, Addr pci_addr) const = 0; + + /** @} */ + + protected: + /** + * Retrieve a PCI device from its bus address. + * + * @return Pointer to a PciDevice instance or nullptr if the + * device doesn't exist. + */ + PciDevice *getDevice(const PciBusAddr &addr); + + /** + * Retrieve a PCI device from its bus address. + * + * @return Pointer to a constant PciDevice instance or nullptr if + * the device doesn't exist. + */ + const PciDevice *getDevice(const PciBusAddr &addr) const; + + private: + /** Currently registered PCI devices */ + std::map<PciBusAddr, PciDevice *> devices; +}; + +/** + * Configurable generic PCI host interface + * + * The GenericPciHost provides a configurable generic PCI host + * implementation. + * + * The generic controller binds to one range of physical addresses to + * implement the PCI subsystem's configuraiton space. The base + * address, size and mapping between memory addresses and PCI devices + * are all configurable as simulation parameters. The basic + * implementation supports both the Configuration Access Mechanism + * (CAM) and Enhanced Configuration Access Mechanism (ECAM) + * configuration space layout. The layouts can be configured by + * changing the number of bits allocated to each device in the + * configuration space. ECAM uses 12 bits per device, while CAM uses 8 + * bits per device. + * + * Interrupts are delivered via the Platform::postInt() and + * Platform::clearInt() calls. Interrupt numbers are mapped statically + * using the interrupt line (PciDevice::interruptLine()) returned from + * the device. Implementations may override mapPciInterrupt() to + * dynamically map a PciBusAddr and PciIntPin to a platform-specific + * interrupt. + * + * All PCI memory spaces (IO, prefetchable, and non-prefetchable) + * support a simple base+offset mapping that can be configured using + * simulation parameters. The base defaults to 0 for all of them. + */ +class GenericPciHost : public PciHost +{ + public: + GenericPciHost(const GenericPciHostParams *p); + virtual ~GenericPciHost(); + + public: // PioDevice + Tick read(PacketPtr pkt) override; + Tick write(PacketPtr pkt) override; + + AddrRangeList getAddrRanges() const override; + + protected: // PciHost + Addr pioAddr(const PciBusAddr &bus_addr, Addr pci_addr) const override { + return pciPioBase + pci_addr; + } + + Addr memAddr(const PciBusAddr &bus_addr, Addr pci_addr) const override { + return pciMemBase + pci_addr; + } + + Addr dmaAddr(const PciBusAddr &bus_addr, Addr pci_addr) const override { + return pciDmaBase + pci_addr; + } + + protected: // Configuration address space handling + /** + * Decode a configuration space address. + * + * + * @param addr Offset into the configuration space + * @return Tuple containing the PCI bus address and an offset into + * the device's configuration space. + */ + virtual std::pair<PciBusAddr, Addr> decodeAddress(Addr address); + + protected: // Interrupt handling + void postInt(const PciBusAddr &addr, PciIntPin pin) override; + void clearInt(const PciBusAddr &addr, PciIntPin pin) override; + + virtual uint32_t mapPciInterrupt(const PciBusAddr &bus_addr, + PciIntPin pin) const; + + protected: + Platform &platform; + + const Addr confBase; + const Addr confSize; + const uint8_t confDeviceBits; + + const Addr pciPioBase; + const Addr pciMemBase; + const Addr pciDmaBase; +}; + +#endif // __DEV_PCI_HOST_HH__ diff --git a/src/dev/pci/types.hh b/src/dev/pci/types.hh new file mode 100644 index 000000000..298fe92f4 --- /dev/null +++ b/src/dev/pci/types.hh @@ -0,0 +1,74 @@ +/* + * Copyright (c) 2015 ARM Limited + * All rights reserved + * + * The license below extends only to copyright in the software and shall + * not be construed as granting a license to any other intellectual + * property including but not limited to intellectual property relating + * to a hardware implementation of the functionality of the software + * licensed hereunder. You may use the software subject to the license + * terms below provided that you ensure that this notice is replicated + * unmodified and in its entirety in all distributions of the software, + * modified or unmodified, in source code or in binary form. + * + * 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: Andreas Sandberg + */ + +#ifndef __DEV_PCI_TYPES_HH__ +#define __DEV_PCI_TYPES_HH__ + +struct PciBusAddr +{ + public: + PciBusAddr() = delete; + + constexpr PciBusAddr(uint8_t _bus, uint8_t _dev, uint8_t _func) + : bus(_bus), dev(_dev), func(_func) {} + + constexpr bool operator<(const PciBusAddr &rhs) const { + return sortValue() < rhs.sortValue(); + } + + uint8_t bus; + uint8_t dev; + uint8_t func; + + protected: + constexpr uint32_t sortValue() const { + return (bus << 16) | (dev << 8) | func; + } +}; + +enum class PciIntPin : uint8_t +{ + NO_INT=0, + INTA, + INTB, + INTC, + INTD +}; + +#endif // __DEV_PCI_TYPES_HH__ diff --git a/src/dev/pciconfigall.cc b/src/dev/pciconfigall.cc deleted file mode 100644 index 882366a42..000000000 --- a/src/dev/pciconfigall.cc +++ /dev/null @@ -1,94 +0,0 @@ -/* - * Copyright (c) 2004-2005 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: Andrew Schultz - * Ali Saidi - */ - -/* @file - * PCI Configspace implementation - */ - -#include "base/trace.hh" -#include "debug/PciConfigAll.hh" -#include "dev/pciconfigall.hh" -#include "dev/pcireg.h" -#include "dev/platform.hh" -#include "mem/packet.hh" -#include "mem/packet_access.hh" -#include "params/PciConfigAll.hh" -#include "sim/system.hh" - -PciConfigAll::PciConfigAll(const Params *p) - : BasicPioDevice(p, p->size) -{ - // the pio_addr Python parameter is ignored, and overridden by - // this caluclated value - pioAddr = p->platform->calcPciConfigAddr(params()->bus,0,0); -} - - -Tick -PciConfigAll::read(PacketPtr pkt) -{ - DPRINTF(PciConfigAll, "read va=%#x size=%d\n", pkt->getAddr(), - pkt->getSize()); - - switch (pkt->getSize()) { - case sizeof(uint32_t): - pkt->set<uint32_t>(0xFFFFFFFF); - break; - case sizeof(uint16_t): - pkt->set<uint16_t>(0xFFFF); - break; - case sizeof(uint8_t): - pkt->set<uint8_t>(0xFF); - break; - default: - panic("invalid access size(?) for PCI configspace!\n"); - } - pkt->makeAtomicResponse(); - return pioDelay; -} - -Tick -PciConfigAll::write(PacketPtr pkt) -{ - panic("Attempting to write to config space on non-existent device\n"); - M5_DUMMY_RETURN -} - - -#ifndef DOXYGEN_SHOULD_SKIP_THIS - -PciConfigAll * -PciConfigAllParams::create() -{ - return new PciConfigAll(this); -} - -#endif // DOXYGEN_SHOULD_SKIP_THIS diff --git a/src/dev/pciconfigall.hh b/src/dev/pciconfigall.hh deleted file mode 100644 index c9a63d2c5..000000000 --- a/src/dev/pciconfigall.hh +++ /dev/null @@ -1,83 +0,0 @@ -/* - * Copyright (c) 2004-2005 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: Andrew Schultz - * Ali Saidi - */ - -/* - * @file - * PCI Config space implementation. - */ - -#ifndef __PCICONFIGALL_HH__ -#define __PCICONFIGALL_HH__ - -#include "dev/io_device.hh" -#include "dev/pcireg.h" -#include "params/PciConfigAll.hh" - -/** - * PCI Config Space - * All of PCI config space needs to return -1 on Tsunami, except - * the devices that exist. This device maps the entire bus config - * space and passes the requests on to TsunamiPCIDevice devices as - * appropriate. - */ -class PciConfigAll : public BasicPioDevice -{ - public: - typedef PciConfigAllParams Params; - const Params *params() const { return (const Params *)_params; } - - /** - * Constructor for PCIConfigAll - * @param p parameters structure - */ - PciConfigAll(const Params *p); - - /** - * Read something in PCI config space. If the device does not exist - * -1 is returned, if the device does exist its PciDevice::ReadConfig - * (or the virtual function that overrides) it is called. - * @param pkt Contains information about the read operation - * @return Amount of time to do the read - */ - virtual Tick read(PacketPtr pkt); - - /** - * Write to PCI config spcae. If the device does not exit the simulator - * panics. If it does it is passed on the PciDevice::WriteConfig (or - * the virtual function that overrides it). - * @param pkt Contains information about the write operation - * @return Amount of time to do the read - */ - - virtual Tick write(PacketPtr pkt); -}; - -#endif // __PCICONFIGALL_HH__ diff --git a/src/dev/pcidev.cc b/src/dev/pcidev.cc index 1c49a9241..5e7c09415 100644 --- a/src/dev/pcidev.cc +++ b/src/dev/pcidev.cc @@ -63,43 +63,9 @@ #include "sim/core.hh" -PciDevice::PciConfigPort::PciConfigPort(PciDevice *dev, int busid, int devid, - int funcid, Platform *p) - : SimpleTimingPort(dev->name() + "-pciconf", dev), device(dev), - platform(p), busId(busid), deviceId(devid), functionId(funcid) -{ - configAddr = platform->calcPciConfigAddr(busId, deviceId, functionId); -} - - -Tick -PciDevice::PciConfigPort::recvAtomic(PacketPtr pkt) -{ - assert(pkt->getAddr() >= configAddr && - pkt->getAddr() < configAddr + PCI_CONFIG_SIZE); - - // technically the packet only reaches us after the header delay, - // and typically we also need to deserialise any payload - Tick receive_delay = pkt->headerDelay + pkt->payloadDelay; - pkt->headerDelay = pkt->payloadDelay = 0; - - const Tick delay(pkt->isRead() ? device->readConfig(pkt) : - device->writeConfig(pkt)); - return delay + receive_delay; -} - -AddrRangeList -PciDevice::PciConfigPort::getAddrRanges() const -{ - AddrRangeList ranges; - if (configAddr != ULL(-1)) - ranges.push_back(RangeSize(configAddr, PCI_CONFIG_SIZE+1)); - return ranges; -} - - -PciDevice::PciDevice(const Params *p) +PciDevice::PciDevice(const PciDeviceParams *p) : DmaDevice(p), + _busAddr(p->pci_bus, p->pci_dev, p->pci_func), PMCAP_BASE(p->PMCAPBaseOffset), PMCAP_ID_OFFSET(p->PMCAPBaseOffset+PMCAP_ID), PMCAP_PC_OFFSET(p->PMCAPBaseOffset+PMCAP_PC), @@ -111,12 +77,15 @@ PciDevice::PciDevice(const Params *p) MSIXCAP_MTAB_OFFSET(p->MSIXCAPBaseOffset+MSIXCAP_MTAB), MSIXCAP_MPBA_OFFSET(p->MSIXCAPBaseOffset+MSIXCAP_MPBA), PXCAP_BASE(p->PXCAPBaseOffset), - platform(p->platform), + + hostInterface(p->host->registerDevice(this, _busAddr, + (PciIntPin)p->InterruptPin)), pioDelay(p->pio_latency), - configDelay(p->config_latency), - configPort(this, params()->pci_bus, params()->pci_dev, - params()->pci_func, params()->platform) + configDelay(p->config_latency) { + fatal_if(p->InterruptPin >= 5, + "Invalid PCI interrupt '%i' specified.", p->InterruptPin); + config.vendor = htole(p->VendorID); config.device = htole(p->DeviceID); config.command = htole(p->Command); @@ -245,18 +214,6 @@ PciDevice::PciDevice(const Params *p) } } } - - platform->registerPciDevice(p->pci_bus, p->pci_dev, p->pci_func, - letoh(config.interruptLine)); -} - -void -PciDevice::init() -{ - if (!configPort.isConnected()) - panic("PCI config port on %s not connected to anything!\n", name()); - configPort.sendRangeChange(); - DmaDevice::init(); } Tick @@ -291,21 +248,21 @@ PciDevice::readConfig(PacketPtr pkt) pkt->set<uint8_t>(config.data[offset]); DPRINTF(PCIDEV, "readConfig: dev %#x func %#x reg %#x 1 bytes: data = %#x\n", - params()->pci_dev, params()->pci_func, offset, + _busAddr.dev, _busAddr.func, offset, (uint32_t)pkt->get<uint8_t>()); break; case sizeof(uint16_t): pkt->set<uint16_t>(*(uint16_t*)&config.data[offset]); DPRINTF(PCIDEV, "readConfig: dev %#x func %#x reg %#x 2 bytes: data = %#x\n", - params()->pci_dev, params()->pci_func, offset, + _busAddr.dev, _busAddr.func, offset, (uint32_t)pkt->get<uint16_t>()); break; case sizeof(uint32_t): pkt->set<uint32_t>(*(uint32_t*)&config.data[offset]); DPRINTF(PCIDEV, "readConfig: dev %#x func %#x reg %#x 4 bytes: data = %#x\n", - params()->pci_dev, params()->pci_func, offset, + _busAddr.dev, _busAddr.func, offset, (uint32_t)pkt->get<uint32_t>()); break; default: @@ -373,7 +330,7 @@ PciDevice::writeConfig(PacketPtr pkt) } DPRINTF(PCIDEV, "writeConfig: dev %#x func %#x reg %#x 1 bytes: data = %#x\n", - params()->pci_dev, params()->pci_func, offset, + _busAddr.dev, _busAddr.func, offset, (uint32_t)pkt->get<uint8_t>()); break; case sizeof(uint16_t): @@ -392,7 +349,7 @@ PciDevice::writeConfig(PacketPtr pkt) } DPRINTF(PCIDEV, "writeConfig: dev %#x func %#x reg %#x 2 bytes: data = %#x\n", - params()->pci_dev, params()->pci_func, offset, + _busAddr.dev, _busAddr.func, offset, (uint32_t)pkt->get<uint16_t>()); break; case sizeof(uint32_t): @@ -424,8 +381,8 @@ PciDevice::writeConfig(PacketPtr pkt) he_new_bar &= ~bar_mask; if (he_new_bar) { BARAddrs[barnum] = BAR_IO_SPACE(he_old_bar) ? - platform->calcPciIOAddr(he_new_bar) : - platform->calcPciMemAddr(he_new_bar); + hostInterface.pioAddr(he_new_bar) : + hostInterface.memAddr(he_new_bar); pioPort.sendRangeChange(); } } @@ -454,7 +411,7 @@ PciDevice::writeConfig(PacketPtr pkt) } DPRINTF(PCIDEV, "writeConfig: dev %#x func %#x reg %#x 4 bytes: data = %#x\n", - params()->pci_dev, params()->pci_func, offset, + _busAddr.dev, _busAddr.func, offset, (uint32_t)pkt->get<uint32_t>()); break; default: diff --git a/src/dev/pcidev.hh b/src/dev/pcidev.hh index 0afcba154..a7a2137b0 100644 --- a/src/dev/pcidev.hh +++ b/src/dev/pcidev.hh @@ -54,7 +54,7 @@ #include "dev/dma_device.hh" #include "dev/pcireg.h" -#include "dev/platform.hh" +#include "dev/pci/host.hh" #include "params/PciDevice.hh" #include "sim/byteswap.hh" @@ -64,46 +64,17 @@ #define BAR_IO_SPACE(x) ((x) & BAR_IO_SPACE_BIT) #define BAR_NUMBER(x) (((x) - PCI0_BASE_ADDR0) >> 0x2); - - /** * PCI device, base implementation is only config space. */ class PciDevice : public DmaDevice { - class PciConfigPort : public SimpleTimingPort - { - protected: - PciDevice *device; - - Tick recvAtomic(PacketPtr pkt) override; - - AddrRangeList getAddrRanges() const override; - - Platform *platform; - - int busId; - int deviceId; - int functionId; - - Addr configAddr; - - public: - PciConfigPort(PciDevice *dev, int busid, int devid, int funcid, - Platform *p); - }; - - public: - typedef PciDeviceParams Params; - const Params * - params() const - { - return dynamic_cast<const Params *>(_params); - } - protected: + const PciBusAddr _busAddr; + /** The current config space. */ PCIConfig config; + /** The capability list structures and base addresses * @{ */ @@ -190,14 +161,7 @@ class PciDevice : public DmaDevice return true; } - private: - Platform *platform; - - protected: - Tick pioDelay; - Tick configDelay; - PciConfigPort configPort; - + public: // Host configuration interface /** * Write to the PCI config space data that is stored locally. This may be * overridden by the device but at some point it will eventually call this @@ -215,21 +179,21 @@ class PciDevice : public DmaDevice */ virtual Tick readConfig(PacketPtr pkt); - public: - Addr pciToDma(Addr pciAddr) const - { return platform->pciToDma(pciAddr); } + protected: + PciHost::DeviceInterface hostInterface; + + Tick pioDelay; + Tick configDelay; - void - intrPost() - { platform->postPciInt(letoh(config.interruptLine)); } + public: + Addr pciToDma(Addr pci_addr) const { + return hostInterface.dmaAddr(pci_addr); + } - void - intrClear() - { platform->clearPciInt(letoh(config.interruptLine)); } + void intrPost() { hostInterface.postInt(); } + void intrClear() { hostInterface.clearInt(); } - uint8_t - interruptLine() - { return letoh(config.interruptLine); } + uint8_t interruptLine() const { return letoh(config.interruptLine); } /** * Determine the address ranges that this device responds to. @@ -241,11 +205,9 @@ class PciDevice : public DmaDevice /** * Constructor for PCI Dev. This function copies data from the * config file object PCIConfigData and registers the device with - * a PciConfigAll object. + * a PciHost object. */ - PciDevice(const Params *params); - - void init() override; + PciDevice(const PciDeviceParams *params); /** * Serialize this object to the given output stream. @@ -260,15 +222,6 @@ class PciDevice : public DmaDevice */ void unserialize(CheckpointIn &cp) override; - - BaseSlavePort &getSlavePort(const std::string &if_name, - PortID idx = InvalidPortID) override - { - if (if_name == "config") { - return configPort; - } - return DmaDevice::getSlavePort(if_name, idx); - } - + const PciBusAddr &busAddr() const { return _busAddr; } }; #endif // __DEV_PCIDEV_HH__ diff --git a/src/dev/platform.cc b/src/dev/platform.cc index c60780786..8c7706b48 100644 --- a/src/dev/platform.cc +++ b/src/dev/platform.cc @@ -56,25 +56,3 @@ Platform::clearPciInt(int line) { panic("No PCI interrupt support in platform."); } - -Addr -Platform::pciToDma(Addr pciAddr) const -{ - panic("No PCI dma support in platform."); - M5_DUMMY_RETURN -} - -void -Platform::registerPciDevice(uint8_t bus, uint8_t dev, uint8_t func, uint8_t intr) -{ - uint32_t bdf = bus << 16 | dev << 8 | func << 0; - if (pciDevices.find(bdf) != pciDevices.end()) - fatal("Two PCI devices have same bus:device:function\n"); - - if (intLines.test(intr)) - fatal("Two PCI devices have same interrupt line: %d\n", intr); - - pciDevices.insert(bdf); - - intLines.set(intr); -} diff --git a/src/dev/platform.hh b/src/dev/platform.hh index 0931d9ece..9e2aee82b 100644 --- a/src/dev/platform.hh +++ b/src/dev/platform.hh @@ -43,12 +43,12 @@ #include "params/Platform.hh" #include "sim/sim_object.hh" -class PciConfigAll; class IntrControl; class Terminal; class Uart; class System; + class Platform : public SimObject { public: @@ -59,21 +59,27 @@ class Platform : public SimObject typedef PlatformParams Params; Platform(const Params *p); virtual ~Platform(); + + /** + * Cause the cpu to post a serial interrupt to the CPU. + */ virtual void postConsoleInt() = 0; + + /** + * Clear a posted CPU interrupt + */ virtual void clearConsoleInt() = 0; - virtual void postPciInt(int line); - virtual void clearPciInt(int line); - virtual Addr pciToDma(Addr pciAddr) const; - virtual Addr calcPciConfigAddr(int bus, int dev, int func) = 0; - virtual Addr calcPciIOAddr(Addr addr) = 0; - virtual Addr calcPciMemAddr(Addr addr) = 0; - virtual void registerPciDevice(uint8_t bus, uint8_t dev, uint8_t func, - uint8_t intr); - private: - std::bitset<256> intLines; - std::set<uint32_t> pciDevices; + /** + * Cause the chipset to post a cpi interrupt to the CPU. + */ + virtual void postPciInt(int line); + + /** + * Clear a posted PCI->CPU interrupt + */ + virtual void clearPciInt(int line); }; #endif // __DEV_PLATFORM_HH__ diff --git a/src/dev/x86/Pc.py b/src/dev/x86/Pc.py index 8740159c4..3100f59b7 100644 --- a/src/dev/x86/Pc.py +++ b/src/dev/x86/Pc.py @@ -30,24 +30,29 @@ from m5.params import * from m5.proxy import * from Device import IsaFake -from Pci import PciConfigAll from Platform import Platform from SouthBridge import SouthBridge from Terminal import Terminal from Uart import Uart8250 +from PciHost import GenericPciHost def x86IOAddress(port): IO_address_space_base = 0x8000000000000000 return IO_address_space_base + port; +class PcPciHost(GenericPciHost): + conf_base = 0xC000000000000000 + conf_size = "16MB" + + pci_pio_base = 0x8000000000000000 + class Pc(Platform): type = 'Pc' cxx_header = "dev/x86/pc.hh" system = Param.System(Parent.any, "system") - pciconfig = PciConfigAll() - south_bridge = SouthBridge() + pci_host = PcPciHost() # "Non-existant" ports used for timing purposes by the linux kernel i_dont_exist1 = IsaFake(pio_addr=x86IOAddress(0x80), pio_size=1) @@ -80,4 +85,4 @@ class Pc(Platform): self.fake_com_3.pio = bus.master self.fake_com_4.pio = bus.master self.fake_floppy.pio = bus.master - self.pciconfig.pio = bus.default + self.pci_host.pio = bus.default diff --git a/src/dev/x86/SouthBridge.py b/src/dev/x86/SouthBridge.py index 911853dd5..704656594 100644 --- a/src/dev/x86/SouthBridge.py +++ b/src/dev/x86/SouthBridge.py @@ -106,7 +106,6 @@ class SouthBridge(SimObject): self.cmos.pio = bus.master self.dma1.pio = bus.master self.ide.pio = bus.master - self.ide.config = bus.master if dma_ports.count(self.ide.dma) == 0: self.ide.dma = bus.slave self.keyboard.pio = bus.master diff --git a/src/dev/x86/pc.cc b/src/dev/x86/pc.cc index dd8e34d9e..fe3119803 100644 --- a/src/dev/x86/pc.cc +++ b/src/dev/x86/pc.cc @@ -141,33 +141,6 @@ Pc::clearPciInt(int line) warn_once("Tried to clear PCI interrupt %d\n", line); } -Addr -Pc::pciToDma(Addr pciAddr) const -{ - return pciAddr; -} - -Addr -Pc::calcPciConfigAddr(int bus, int dev, int func) -{ - assert(func < 8); - assert(dev < 32); - assert(bus == 0); - return (PhysAddrPrefixPciConfig | (func << 8) | (dev << 11)); -} - -Addr -Pc::calcPciIOAddr(Addr addr) -{ - return PhysAddrPrefixIO + addr; -} - -Addr -Pc::calcPciMemAddr(Addr addr) -{ - return addr; -} - Pc * PcParams::create() { diff --git a/src/dev/x86/pc.hh b/src/dev/x86/pc.hh index c999440d2..6cc57cb5d 100644 --- a/src/dev/x86/pc.hh +++ b/src/dev/x86/pc.hh @@ -61,43 +61,12 @@ class Pc : public Platform Pc(const Params *p); - /** - * Cause the cpu to post a serial interrupt to the CPU. - */ - virtual void postConsoleInt(); - - /** - * Clear a posted CPU interrupt - */ - virtual void clearConsoleInt(); - - /** - * Cause the chipset to post a pci interrupt to the CPU. - */ - virtual void postPciInt(int line); - - /** - * Clear a posted PCI->CPU interrupt - */ - virtual void clearPciInt(int line); - - - virtual Addr pciToDma(Addr pciAddr) const; - - /** - * Calculate the configuration address given a bus/dev/func. - */ - virtual Addr calcPciConfigAddr(int bus, int dev, int func); - - /** - * Calculate the address for an IO location on the PCI bus. - */ - virtual Addr calcPciIOAddr(Addr addr); + public: + void postConsoleInt() override; + void clearConsoleInt() override; - /** - * Calculate the address for a memory location on the PCI bus. - */ - virtual Addr calcPciMemAddr(Addr addr); + void postPciInt(int line) override; + void clearPciInt(int line) override; }; #endif // __DEV_PC_HH__ |