+libm
[meinos.git] / apps / lib / libmeinos / pci.c
blob141963adb0e141d22c7fac6395818689b63529f7
1 /*
2 meinOS - A unix-like x86 microkernel operating system
3 Copyright (C) 2008 Janosch Gräf <janosch.graef@gmx.net>
5 This program is free software: you can redistribute it and/or modify
6 it under the terms of the GNU Lesser General Public License as published by
7 the Free Software Foundation, either version 3 of the License, or
8 (at your option) any later version.
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU Lesser General Public License for more details.
15 You should have received a copy of the GNU Lesser General Public License
16 along with this program. If not, see <http://www.gnu.org/licenses/>.
19 #include <sys/types.h>
20 #include <stdint.h>
21 #include <ioport.h>
22 #include <stdlib.h>
23 #include <pci.h>
25 /**
26 * Reads dword from config register of PCI device
27 * @param dev PCI device
28 * @param offset Register offset
29 * @return Register content
31 uint32_t pci_config_readd(pcidev_t *dev,size_t offset) {
32 return 0;
35 /**
36 * Writes dword in config register of PCI device
37 * @param dev PCI device
38 * @param offset Register offset
39 * @param val Value to write
41 void pci_config_writed(pcidev_t *dev,size_t offset,uint32_t val) {
46 /**
47 * Finds PCI device by VendorID and DeviceID
48 * @param dev Pointer to PCI device
49 * @param vendorid VendorID
50 * @param deviceid DeviceID
51 * @param index If more than 1 device is found, select n'th one
52 * @return Whether device was found
54 int pci_finddev_byids(pcidev_t *dev,int vendorid,int deviceid,int index) {
55 for (dev->bus=0;dev->bus<PCI_MAXBUSSES;dev->bus++) {
56 for (dev->slot=0;dev->slot<PCI_MAXSLOTS;dev->slot++) {
57 if (pci_get_vendorid(dev)==vendorid && pci_get_deviceid(dev)==deviceid) {
58 if (!index) return 1;
59 else index--;
63 return 0;
66 /**
67 * Finds PCI device by Classcode and Subclass
68 * @param dev Pointer to PCI device
69 * @param classcode Classcode
70 * @param subclass Subclass
71 * @param index If more than 1 device is found, select n'th one
72 * @return Whether device was found
74 int pci_finddev_byclass(pcidev_t *dev,int classcode,int subclass,int index) {
75 for (dev->bus=0;dev->bus<PCI_MAXBUSSES;dev->bus++) {
76 for (dev->slot=0;dev->slot<PCI_MAXSLOTS;dev->slot++) {
77 if (pci_get_subclass(dev)==classcode && pci_get_subclass(dev)==subclass) {
78 if (!index) return 1;
79 else index--;
83 return 0;
86 /**
87 * Returns Pointer to BAR structure
88 * @param dev PCI device
89 * @param barnum Number of BAR register (0..5)
90 * @return Pointer to BAR structure
92 pcibar_t *pci_getbar(pcidev_t *dev,int barnum) {
93 pcibar_t *bar = malloc(sizeof(pcibar_t));
94 uint32_t bar_value = pci_config_readd(dev,barnum*4+0x10);
95 bar->type = bar_value&1;
96 if (bar->type==PCI_BARTYPE_MEMORY) {
97 bar->addr = (void*)(bar_value&0xFFFFFFF0);
98 pci_config_writed(dev,barnum*4+0x10,0xFFFFFFF0|bar->type);
99 bar->size = pci_config_readd(dev,barnum*4+0x10);
100 bar->size = (~bar->size|0xF)+1;
101 pci_config_writed(dev,barnum*4+0x10,bar_value);
103 else bar->ioport = bar_value&0xFFFFFFFC;
104 return bar;