From 19b5451f3b3d4e6dfb2404e972fe4da0ce7d5f6a Mon Sep 17 00:00:00 2001 From: Jonas 'Sortie' Termansen Date: Sat, 28 Jul 2012 01:40:25 +0200 Subject: [PATCH] Refactored the PCI code to become a library of utility functions. --- sortix/include/sortix/kernel/pci.h | 75 +++++ sortix/kernel.cpp | 6 +- sortix/pci.cpp | 431 +++++++++++------------------ sortix/pci.h | 39 --- 4 files changed, 244 insertions(+), 307 deletions(-) create mode 100644 sortix/include/sortix/kernel/pci.h delete mode 100644 sortix/pci.h diff --git a/sortix/include/sortix/kernel/pci.h b/sortix/include/sortix/kernel/pci.h new file mode 100644 index 00000000..6867d66f --- /dev/null +++ b/sortix/include/sortix/kernel/pci.h @@ -0,0 +1,75 @@ +/******************************************************************************* + + Copyright(C) Jonas 'Sortie' Termansen 2011, 2012. + + This file is part of Sortix. + + Sortix is free software: you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation, either version 3 of the License, or (at your option) any later + version. + + Sortix is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + FOR A PARTICULAR PURPOSE. See the GNU General Public License for more + details. + + You should have received a copy of the GNU General Public License along with + Sortix. If not, see . + + pci.h + Functions for handling PCI devices. + +*******************************************************************************/ + +#ifndef SORTIX_PCI_H +#define SORTIX_PCI_H + +namespace Sortix { + +typedef struct +{ + uint16_t deviceid; + uint16_t vendorid; +} pciid_t; + +typedef struct +{ + uint8_t classid; + uint8_t subclassid; + uint8_t progif; + uint8_t revid; +} pcitype_t; + +// memset(&pcifind, 255, sizeof(pcifind)) and fill out rest. +typedef struct +{ + uint16_t deviceid; + uint16_t vendorid; + uint8_t classid; + uint8_t subclassid; + uint8_t progif; + uint8_t revid; +} pcifind_t; + +namespace PCI { + +void Init(); +uint32_t MakeDevAddr(uint8_t bus, uint8_t slot, uint8_t func); +void SplitDevAddr(uint32_t devaddr, uint8_t* vals /* bus, slot, func */); +uint8_t Read8(uint32_t devaddr, uint8_t off); // Host endian +uint16_t Read16(uint32_t devaddr, uint8_t off); // Host endian +uint32_t Read32(uint32_t devaddr, uint8_t off); // Host endian +uint32_t ReadRaw32(uint32_t devaddr, uint8_t off); // PCI endian +void Write32(uint32_t devaddr, uint8_t off, uint32_t val); // Host endian +void WriteRaw32(uint32_t devaddr, uint8_t off, uint32_t val); // PCI endian +pciid_t GetDeviceId(uint32_t devaddr); +pcitype_t GetDeviceType(uint32_t devaddr); +uint32_t SearchForDevice(pcifind_t pcifind); +addr_t ParseDevBar0(uint32_t devaddr); + +} // namespace PCI +} // namespace Sortix + +#endif + diff --git a/sortix/kernel.cpp b/sortix/kernel.cpp index 1c623e92..deeddc87 100644 --- a/sortix/kernel.cpp +++ b/sortix/kernel.cpp @@ -27,6 +27,7 @@ #include #include #include +#include #include #include #include @@ -42,7 +43,7 @@ #include "process.h" #include "scheduler.h" #include "syscall.h" -#include "pci.h" +#include "ata.h" #include "com.h" #include "uart.h" #include "vgatextbuffer.h" @@ -218,6 +219,9 @@ extern "C" void KernelInit(unsigned long magic, multiboot_info_t* bootinfo) // Search for PCI devices and load their drivers. PCI::Init(); + // Initialize ATA devices. + ATA::Init(); + // Alright, now the system's drivers are loaded and initialized. It is // time to load the initial user-space programs and start execution of // the actual operating system. diff --git a/sortix/pci.cpp b/sortix/pci.cpp index db902ed6..6a2d717d 100644 --- a/sortix/pci.cpp +++ b/sortix/pci.cpp @@ -1,6 +1,6 @@ -/****************************************************************************** +/******************************************************************************* - COPYRIGHT(C) JONAS 'SORTIE' TERMANSEN 2011. + Copyright(C) Jonas 'Sortie' Termansen 2011, 2012. This file is part of Sortix. @@ -14,283 +14,180 @@ FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. - You should have received a copy of the GNU General Public License along - with Sortix. If not, see . + You should have received a copy of the GNU General Public License along with + Sortix. If not, see . - pci.h - Handles basic PCI bus stuff. + pci.cpp + Functions for handling PCI devices. -******************************************************************************/ +*******************************************************************************/ #include -#include "cpu.h" -#include -#include "pci.h" -#include -#include "ata.h" +#include +#include +#include "cpu.h" // TODO: Put this in some -using namespace Maxsi; +// TODO: Verify that the endian conversions in this file actually works. I have +// a sneaking suspicion that they won't work on non-little endian platforms. -namespace Sortix +namespace Sortix { +namespace PCI { + +const uint16_t CONFIG_ADDRESS = 0xCF8; +const uint16_t CONFIG_DATA = 0xCFC; + +uint32_t MakeDevAddr(uint8_t bus, uint8_t slot, uint8_t func) { - namespace PCI + //ASSERT(bus < 1UL<<8UL); // bus is 8 bit anyways. + ASSERT(slot < 1UL<<5UL); + ASSERT(func < 1UL<<3UL); + return func << 8U | slot << 11U | bus << 16U | 1 << 31U; +} + +void SplitDevAddr(uint32_t devaddr, uint8_t* vals /* bus, slot, func */) +{ + vals[0] = devaddr >> 16U & ((1UL<<8UL)-1); + vals[1] = devaddr >> 11U & ((1UL<<3UL)-1); + vals[2] = devaddr >> 8U & ((1UL<<5UL)-1); +} + +uint32_t ReadRaw32(uint32_t devaddr, uint8_t off) +{ + CPU::OutPortL(CONFIG_ADDRESS, devaddr + off); + return CPU::InPortL(CONFIG_DATA); +} + +void WriteRaw32(uint32_t devaddr, uint8_t off, uint32_t val) +{ + CPU::OutPortL(CONFIG_ADDRESS, devaddr + off); + CPU::OutPortL(CONFIG_DATA, val); +} + +uint32_t Read32(uint32_t devaddr, uint8_t off) +{ + return LittleToHost(ReadRaw32(devaddr, off)); +} + +void Write32(uint32_t devaddr, uint8_t off, uint32_t val) +{ + WriteRaw32(devaddr, off, HostToLittle(val)); +} + +uint16_t Read16(uint32_t devaddr, uint8_t off) +{ + ASSERT((off & 0x1) == 0); + uint8_t alignedoff = off & ~0x3; + union { uint16_t val16[2]; uint32_t val32; }; + val32 = ReadRaw32(devaddr, alignedoff); + uint16_t ret = off & 0x2 ? val16[0] : val16[1]; + return LittleToHost(ret); +} + +uint8_t Read8(uint32_t devaddr, uint8_t off) +{ + uint8_t alignedoff = off & ~0x1; + union { uint8_t val8[2]; uint32_t val16; }; + val16 = HostToLittle(Read16(devaddr, alignedoff)); + uint8_t ret = off & 0x1 ? val8[0] : val8[1]; + return ret; +} + +uint32_t CheckDevice(uint8_t bus, uint8_t slot, uint8_t func) +{ + return Read32(MakeDevAddr(bus, slot, func), 0x0); +} + +pciid_t GetDeviceId(uint32_t devaddr) +{ + pciid_t ret; + ret.deviceid = Read16(devaddr, 0x00); + ret.vendorid = Read16(devaddr, 0x02); + return ret; +} + +pcitype_t GetDeviceType(uint32_t devaddr) +{ + pcitype_t ret; + ret.classid = Read8(devaddr, 0x08); + ret.subclassid = Read8(devaddr, 0x09); + ret.progif = Read8(devaddr, 0x0A); + ret.revid = Read8(devaddr, 0x0B); + return ret; +} + +static bool MatchesSearchCriteria(uint32_t devaddr, pcifind_t pcifind) +{ + pciid_t id = GetDeviceId(devaddr); + if ( id.vendorid == 0xFFFF && id.deviceid == 0xFFFF ) + return false; + pcitype_t type = GetDeviceType(devaddr); + if ( pcifind.vendorid != 0xFFFF && id.vendorid != pcifind.vendorid ) + return false; + if ( pcifind.deviceid != 0xFFFF && id.deviceid != pcifind.deviceid ) + return false; + if ( pcifind.classid != 0xFF && type.classid != pcifind.classid ) + return false; + if ( pcifind.subclassid != 0xFF && type.subclassid != pcifind.subclassid ) + return false; + if ( pcifind.progif != 0xFF && type.progif != pcifind.progif ) + return false; + if ( pcifind.revid != 0xFF && type.revid != pcifind.revid ) + return false; + return true; +} + +static uint32_t SearchForDeviceOnBus(uint8_t bus, pcifind_t pcifind) +{ + for ( unsigned slot = 0; slot < 32; slot++ ) { - const uint16_t Config_Address = 0xCF8; - const uint16_t Config_Data = 0xCFC; - - uint32_t SwapBytes(uint32_t I) + unsigned numfuncs = 1; + for ( unsigned func = 0; func < numfuncs; func++ ) { - return (I >> 24) | ((I >> 8) & 0x0000FF00) | ((I << 8) & 0x00FF0000) | (I << 24); + uint32_t devaddr = MakeDevAddr(bus, slot, func); + if ( MatchesSearchCriteria(devaddr, pcifind) ) + return devaddr; + uint8_t header = Read8(devaddr, 0x0D); // Secondary Bus Number. + if ( header & 0x80 ) // Multi function device. + numfuncs = 8; + if ( (header & 0x7F) == 0x01 ) // PCI to PCI bus. + { + uint8_t subbusid = Read8(devaddr, 0x1A); + uint32_t recret = SearchForDeviceOnBus(subbusid, pcifind); + if ( recret ) + return recret; + } } + } + return 0; +} - const char* ToDeviceDesc(uint32_t ProductInfo, uint32_t DeviceType) - { - uint32_t Class = (DeviceType) >> 24; - uint32_t SubClass = (DeviceType >> 16) & 0xFF; - uint32_t ProgIF = (DeviceType >> 8) & 0xFF; - uint32_t RevisionID = (DeviceType) & 0xFF; +uint32_t SearchForDevice(pcifind_t pcifind) +{ + // Search on bus 0 and recurse on other detected busses. + return SearchForDeviceOnBus(0, pcifind); +} - if ( Class == 0x00 ) - { - if ( SubClass == 0x00 && ProgIF == 0x00 ) { return "Any device except for VGA-Compatible devices"; } - if ( SubClass == 0x01 && ProgIF == 0x00 ) { return "VGA-Compatible Device"; } - } - if ( Class == 0x01 ) - { - if ( SubClass == 0x00 && ProgIF == 0x00 ) { return "SCSI Bus Controller"; } - if ( SubClass == 0x01 ) { return "IDE Controller"; } - if ( SubClass == 0x02 && ProgIF == 0x00 ) { return "Floppy Disk Controller"; } - if ( SubClass == 0x03 && ProgIF == 0x00 ) { return "IPI Bus Controller"; } - if ( SubClass == 0x04 && ProgIF == 0x00 ) { return "RAID Controller"; } - if ( SubClass == 0x05 && ProgIF == 0x20 ) { return "ATA Controller (Single DMA)"; } - if ( SubClass == 0x05 && ProgIF == 0x30 ) { return "ATA Controller (Chained DMA)"; } - if ( SubClass == 0x06 && ProgIF == 0x00 ) { return "Serial ATA (Direct Port Access)"; } - if ( SubClass == 0x80 && ProgIF == 0x00 ) { return "Other Mass Storage Controller"; } - } - if ( Class == 0x02 ) - { - if ( SubClass == 0x00 && ProgIF == 0x00 ) { return "Ethernet Controller"; } - if ( SubClass == 0x01 && ProgIF == 0x00 ) { return "Token Ring Controller"; } - if ( SubClass == 0x02 && ProgIF == 0x00 ) { return "FDDI Controller"; } - if ( SubClass == 0x03 && ProgIF == 0x00 ) { return "ATM Controller"; } - if ( SubClass == 0x04 && ProgIF == 0x00 ) { return "ISDN Controller"; } - if ( SubClass == 0x05 && ProgIF == 0x00 ) { return "WorldFip Controller"; } - if ( SubClass == 0x05 && ProgIF == 0x00 ) { return "ATA Controller (Chained DMA)"; } - if ( SubClass == 0x06 ) { return "PICMG 2.14 Multi Computing"; } - if ( SubClass == 0x80 && ProgIF == 0x00 ) { return "Other Network Controller"; } - } - if ( Class == 0x03 ) - { - if ( SubClass == 0x00 && ProgIF == 0x00 ) { return "VGA-Compatible Controller"; } - if ( SubClass == 0x00 && ProgIF == 0x01 ) { return "8512-Compatible Controller"; } - if ( SubClass == 0x01 && ProgIF == 0x00 ) { return "XGA Controller"; } - if ( SubClass == 0x02 && ProgIF == 0x00 ) { return "3D Controller (Not VGA-Compatible)"; } - if ( SubClass == 0x80 && ProgIF == 0x00 ) { return "Other Display Controller"; } - } - if ( Class == 0x04 ) - { - if ( SubClass == 0x00 && ProgIF == 0x00 ) { return "Video Device"; } - if ( SubClass == 0x01 && ProgIF == 0x00 ) { return "Audio Device"; } - if ( SubClass == 0x02 && ProgIF == 0x00 ) { return "Computer Telephony Device"; } - if ( SubClass == 0x80 && ProgIF == 0x00 ) { return "Other Multimedia Device"; } - } - if ( Class == 0x05 ) - { - if ( SubClass == 0x00 && ProgIF == 0x00 ) { return "RAM Controller"; } - if ( SubClass == 0x01 && ProgIF == 0x00 ) { return "Flash Controller"; } - if ( SubClass == 0x80 && ProgIF == 0x00 ) { return "Other Memory Controller"; } - } - if ( Class == 0x06 ) - { - if ( SubClass == 0x00 && ProgIF == 0x00 ) { return "Host Bridge"; } - if ( SubClass == 0x01 && ProgIF == 0x00 ) { return "ISA Bridge"; } - if ( SubClass == 0x02 && ProgIF == 0x00 ) { return "EISA Bridge"; } - if ( SubClass == 0x03 && ProgIF == 0x00 ) { return "MCA Bridge"; } - if ( SubClass == 0x04 && ProgIF == 0x00 ) { return "PCI-to-PCI Bridge"; } - if ( SubClass == 0x04 && ProgIF == 0x01 ) { return "PCI-to-PCI Bridge (Subtractive Decode)"; } - if ( SubClass == 0x05 && ProgIF == 0x00 ) { return "PCMCIA Bridge"; } - if ( SubClass == 0x06 && ProgIF == 0x00 ) { return "NuBus Bridge"; } - if ( SubClass == 0x07 && ProgIF == 0x00 ) { return "CardBus Bridge"; } - if ( SubClass == 0x08 ) { return "RACEway Bridge"; } - if ( SubClass == 0x09 && ProgIF == 0x40 ) { return "PCI-to-PCI Bridge (Semi-Transparent, Primary)"; } - if ( SubClass == 0x09 && ProgIF == 0x80 ) { return "PCI-to-PCI Bridge (Semi-Transparent, Secondary)"; } - if ( SubClass == 0x0A && ProgIF == 0x00 ) { return "InfiniBrand-to-PCI Host Bridge"; } - if ( SubClass == 0x80 && ProgIF == 0x00 ) { return "Other Bridge Device"; } - } - if ( Class == 0x07 ) - { - if ( SubClass == 0x00 && ProgIF == 0x00 ) { return "Generic XT-Compatible Serial Controller"; } - if ( SubClass == 0x00 && ProgIF == 0x01 ) { return "16450-Compatible Serial Controller"; } - if ( SubClass == 0x00 && ProgIF == 0x02 ) { return "16550-Compatible Serial Controller"; } - if ( SubClass == 0x00 && ProgIF == 0x03 ) { return "16650-Compatible Serial Controller"; } - if ( SubClass == 0x00 && ProgIF == 0x04 ) { return "16750-Compatible Serial Controller"; } - if ( SubClass == 0x00 && ProgIF == 0x05 ) { return "16850-Compatible Serial Controller"; } - if ( SubClass == 0x00 && ProgIF == 0x06 ) { return "16950-Compatible Serial Controller"; } - if ( SubClass == 0x01 && ProgIF == 0x00 ) { return "Parallel Port"; } - if ( SubClass == 0x01 && ProgIF == 0x01 ) { return "Bi-Directional Parallel Port"; } - if ( SubClass == 0x01 && ProgIF == 0x02 ) { return "ECP 1.X Compliant Parallel Port"; } - if ( SubClass == 0x01 && ProgIF == 0x03 ) { return "IEEE 1284 Controller"; } - if ( SubClass == 0x01 && ProgIF == 0xFE ) { return "IEEE 1284 Target Device"; } - if ( SubClass == 0x02 && ProgIF == 0x00 ) { return "Multiport Serial Controller"; } - if ( SubClass == 0x03 && ProgIF == 0x00 ) { return "Generic Modem"; } - if ( SubClass == 0x03 && ProgIF == 0x01 ) { return "Hayes Compatible Modem (16450-Compatible Interface)"; } - if ( SubClass == 0x03 && ProgIF == 0x02 ) { return "Hayes Compatible Modem (16550-Compatible Interface)"; } - if ( SubClass == 0x03 && ProgIF == 0x03 ) { return "Hayes Compatible Modem (16650-Compatible Interface)"; } - if ( SubClass == 0x03 && ProgIF == 0x04 ) { return "Hayes Compatible Modem (16750-Compatible Interface)"; } - if ( SubClass == 0x04 && ProgIF == 0x00 ) { return "IEEE 488.1/2 (GPIB) Controller"; } - if ( SubClass == 0x05 && ProgIF == 0x00 ) { return "Smart Card"; } - if ( SubClass == 0x80 && ProgIF == 0x00 ) { return "Other Communications Device"; } - } - if ( Class == 0x08 ) - { - if ( SubClass == 0x00 && ProgIF == 0x00 ) { return "Generic 8259 PIC"; } - if ( SubClass == 0x00 && ProgIF == 0x01 ) { return "ISA PIC"; } - if ( SubClass == 0x00 && ProgIF == 0x02 ) { return "EISA PIC"; } - if ( SubClass == 0x00 && ProgIF == 0x10 ) { return "I/O APIC Interrupt Controller"; } - if ( SubClass == 0x00 && ProgIF == 0x20 ) { return "I/O(x) APIC Interrupt Controller"; } - if ( SubClass == 0x01 && ProgIF == 0x00 ) { return "Generic 8237 DMA Controller"; } - if ( SubClass == 0x01 && ProgIF == 0x01 ) { return "ISA DMA Controller"; } - if ( SubClass == 0x01 && ProgIF == 0x02 ) { return "EISA DMA Controller"; } - if ( SubClass == 0x02 && ProgIF == 0x00 ) { return "Generic 8254 System Timer"; } - if ( SubClass == 0x02 && ProgIF == 0x01 ) { return "ISA System Timer"; } - if ( SubClass == 0x02 && ProgIF == 0x02 ) { return "EISA System Timer"; } - if ( SubClass == 0x03 && ProgIF == 0x00 ) { return "Generic RTC Controller"; } - if ( SubClass == 0x03 && ProgIF == 0x01 ) { return "ISA RTC Controller"; } - if ( SubClass == 0x04 && ProgIF == 0x01 ) { return "Generic PCI Hot-Plug Controller"; } - if ( SubClass == 0x80 && ProgIF == 0x00 ) { return "Other System Peripheral"; } - } - if ( Class == 0x09 ) - { - if ( SubClass == 0x00 && ProgIF == 0x00 ) { return "Keyboard Controller"; } - if ( SubClass == 0x01 && ProgIF == 0x00 ) { return "Digitizer"; } - if ( SubClass == 0x02 && ProgIF == 0x00 ) { return "Mouse Controller"; } - if ( SubClass == 0x03 && ProgIF == 0x00 ) { return "Scanner Controller"; } - if ( SubClass == 0x04 && ProgIF == 0x00 ) { return "Gameport Controller (Generic)"; } - if ( SubClass == 0x04 && ProgIF == 0x10 ) { return "Gameport Controller (Legacy)"; } - if ( SubClass == 0x80 && ProgIF == 0x00 ) { return "Other Input Controller"; } - } - if ( Class == 0x0A ) - { - if ( SubClass == 0x00 && ProgIF == 0x00 ) { return "Generic Docking Station"; } - if ( SubClass == 0x80 && ProgIF == 0x00 ) { return "Other Docking Station"; } - } - if ( Class == 0x0B ) - { - if ( SubClass == 0x00 && ProgIF == 0x00 ) { return "386 Processor"; } - if ( SubClass == 0x01 && ProgIF == 0x00 ) { return "486 Processor"; } - if ( SubClass == 0x02 && ProgIF == 0x00 ) { return "Pentium Processor"; } - if ( SubClass == 0x10 && ProgIF == 0x00 ) { return "Alpha Processor"; } - if ( SubClass == 0x20 && ProgIF == 0x00 ) { return "PowerPC Processor"; } - if ( SubClass == 0x30 && ProgIF == 0x00 ) { return "MIPS Processor"; } - if ( SubClass == 0x40 && ProgIF == 0x00 ) { return "Co-Processor"; } - } - if ( Class == 0x0C ) - { - if ( SubClass == 0x00 && ProgIF == 0x00 ) { return "IEEE 1394 Controller (FireWire)"; } - if ( SubClass == 0x00 && ProgIF == 0x10 ) { return "IEEE 1394 Controller (1394 OpenHCI Spec)"; } - if ( SubClass == 0x01 && ProgIF == 0x00 ) { return "ACCESS.bus"; } - if ( SubClass == 0x02 && ProgIF == 0x00 ) { return "SSA"; } - if ( SubClass == 0x03 && ProgIF == 0x00 ) { return "USB (Universal Host Controller Spec)"; } - if ( SubClass == 0x03 && ProgIF == 0x10 ) { return "USB (Open Host Controller Spec)"; } - if ( SubClass == 0x03 && ProgIF == 0x20 ) { return "USB2 Host Controller (Intel Enhanced Host Controller Interface)"; } - if ( SubClass == 0x03 && ProgIF == 0x80 ) { return "USB"; } - if ( SubClass == 0x03 && ProgIF == 0xFE ) { return "USB (Not Host Controller)"; } - if ( SubClass == 0x04 && ProgIF == 0x00 ) { return "Fibre Channel"; } - if ( SubClass == 0x05 && ProgIF == 0x00 ) { return "SMBus"; } - if ( SubClass == 0x06 && ProgIF == 0x00 ) { return "InfiniBand"; } - if ( SubClass == 0x07 && ProgIF == 0x00 ) { return "IPMI SMIC Interface"; } - if ( SubClass == 0x07 && ProgIF == 0x01 ) { return "IPMI Kybd Controller Style Interface"; } - if ( SubClass == 0x07 && ProgIF == 0x02 ) { return "IPMI Block Transfer Interface"; } - if ( SubClass == 0x08 && ProgIF == 0x02 ) { return "SERCOS Interface Standard (IEC 61491)"; } - if ( SubClass == 0x09 && ProgIF == 0x00 ) { return "CANbus"; } - } - if ( Class == 0x0E ) - { - if ( SubClass == 0x00 && ProgIF == 0x00 ) { return "Message FIFO"; } - if ( SubClass == 0x00 ) { return "I20 Architecture"; } - } - if ( Class == 0x0F ) - { - if ( SubClass == 0x01 && ProgIF == 0x00 ) { return "TV Controller"; } - if ( SubClass == 0x02 && ProgIF == 0x00 ) { return "Audio Controller"; } - if ( SubClass == 0x03 && ProgIF == 0x00 ) { return "Voice Controller"; } - if ( SubClass == 0x04 && ProgIF == 0x00 ) { return "Data Controller"; } - } - if ( Class == 0x10 ) - { - if ( SubClass == 0x00 && ProgIF == 0x00 ) { return "Network and Computing Encryption/Decryption"; } - if ( SubClass == 0x10 && ProgIF == 0x00 ) { return "Entertainment Encryption/Decryption"; } - if ( SubClass == 0x80 && ProgIF == 0x00 ) { return "Other Encryption/Decryption"; } - } - if ( Class == 0x11 ) - { - if ( SubClass == 0x00 && ProgIF == 0x00 ) { return "DPIO Modules"; } - if ( SubClass == 0x01 && ProgIF == 0x00 ) { return "Performance Counters"; } - if ( SubClass == 0x10 && ProgIF == 0x00 ) { return "Communications Syncrhonization Plus Time and Frequency Test/Measurment"; } - if ( SubClass == 0x20 && ProgIF == 0x00 ) { return "Management Card"; } - if ( SubClass == 0x80 && ProgIF == 0x00 ) { return "Other Data Acquisition/Signal Processing Controller"; } - } - - return NULL; - } - - void Init() - { - ATA::Init(); -#if 0 - Log::Print("PCI Devices: "); - - for ( nat Bus = 0; Bus < 256; Bus++ ) - { - for ( nat Slot = 0; Slot < 32; Slot++ ) - { - for ( nat Function = 0; Function < 8; Function++ ) - { - uint32_t ProductInfo = CheckDevice(Bus, Slot, Function); - - if ( ProductInfo == 0xFFFFFFFF ) { continue; } - - uint32_t DeviceType = ReadLong(Bus, Slot, Function, 0x08); - - const char* DeviceDesc = ToDeviceDesc(ProductInfo, DeviceType); - - if ( DeviceDesc != NULL ) - { - Log::PrintF("%s, ", DeviceDesc); - } - else - { - Log::PrintF("Unknown PCI Device @ %x:%x.%x (ProductInfo=0x%x, DeviceType=0x%x), ", Bus, Slot, Function, ProductInfo, DeviceType); - } - } - } - } - - Log::Print("\b\b\n"); -#endif - } - - uint32_t ReadLong(uint8_t Bus, uint8_t Slot, uint8_t Function, uint8_t Offset) - { - unsigned long LBus = (unsigned long) Bus; - unsigned long LSlot = (unsigned long) Slot; - unsigned long LFunc = (unsigned long) Function; - - // create configuration address. - unsigned long Address = (unsigned long) ( (LBus << 16) | (LSlot << 11) | (LFunc << 8) | (Offset & 0xFC) | ((uint32_t) 0x80000000)); - - // Write out the address. - CPU::OutPortL(Config_Address, Address); - - // Read in the data. - return CPU::InPortL(Config_Data); - - } - - uint32_t CheckDevice(uint8_t Bus, uint8_t Slot, uint8_t Function) - { - return ReadLong(Bus, Slot, Function, 0); - } +// TODO: This is just a hack but will do for now. +addr_t ParseDevBar0(uint32_t devaddr) +{ + uint32_t bar0 = Read32(devaddr, 0x10); + if ( bar0 & 0x1 ) // IO Space + return bar0 & ~0x7UL; + else // Memory Space + { + //uint32_t type = bar0 >> 1 & 0x3; + //uint32_t prefetchable = bar0 >> 3 & 0x1; + //if ( type == 0x01 ) + // // TODO: Support 16-bit addresses here. + //if ( type == 0x02 ) + // // TODO: Support 64-bit addresses here. + return bar0 & ~0xFUL; } } +void Init() +{ +} + +} // namespace PCI +} // namespace Sortix diff --git a/sortix/pci.h b/sortix/pci.h deleted file mode 100644 index d545c35f..00000000 --- a/sortix/pci.h +++ /dev/null @@ -1,39 +0,0 @@ -/****************************************************************************** - - COPYRIGHT(C) JONAS 'SORTIE' TERMANSEN 2011. - - This file is part of Sortix. - - Sortix is free software: you can redistribute it and/or modify it under the - terms of the GNU General Public License as published by the Free Software - Foundation, either version 3 of the License, or (at your option) any later - version. - - Sortix is distributed in the hope that it will be useful, but WITHOUT ANY - WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS - FOR A PARTICULAR PURPOSE. See the GNU General Public License for more - details. - - You should have received a copy of the GNU General Public License along - with Sortix. If not, see . - - pci.h - Handles basic PCI bus stuff. - -******************************************************************************/ - -#ifndef SORTIX_PCI_H -#define SORTIX_PCI_H - -namespace Sortix -{ - namespace PCI - { - void Init(); - uint32_t ReadLong(uint8_t Bus, uint8_t Slot, uint8_t Function, uint8_t Offset); - uint32_t CheckDevice(uint8_t Bus, uint8_t Slot, uint8_t Function = 0); - } -} - -#endif -