PCI cleanup
[akaros.git] / kern / arch / x86 / pci.h
1 /* Copyright (c) 2009, 2010 The Regents of the University of California
2  * See LICENSE for details.
3  *
4  * Barret Rhoden <brho@cs.berkeley.edu>
5  * Original by Paul Pearce <pearce@eecs.berkeley.edu> */
6
7 #ifndef ROS_ARCH_PCI_H
8 #define ROS_ARCH_PCI_H
9
10 #include <ros/common.h>
11 #include <sys/queue.h>
12
13 #define pci_debug(...)  printk(__VA_ARGS__)  
14
15 #define PCI_CONFIG_ADDR     0xCF8
16 #define PCI_CONFIG_DATA     0xCFC
17 #define INVALID_VENDOR_ID   0xFFFF
18
19 /* TODO: gut this (when the IOAPIC is fixed) */
20 #define INVALID_BUS                     0xFFFF
21
22 #define PCI_NOINT                       0x00
23 #define PCI_INTA                        0x01
24 #define PCI_INTB                        0x02
25 #define PCI_INTC                        0x03
26 #define PCI_INTD                        0x04
27
28 /* PCI Register Config Space */
29 #define PCI_DEV_VEND_REG        0x00    /* for the 32 bit read of dev/vend */
30 #define PCI_VENDID_REG          0x00
31 #define PCI_DEVID_REG           0x02
32 #define PCI_CMD_REG                     0x04
33 #define PCI_STATUS_REG          0x06
34 #define PCI_REVID_REG           0x08
35 #define PCI_PROGIF_REG          0x09
36 #define PCI_SUBCLASS_REG        0x0a
37 #define PCI_CLASS_REG           0x0b
38 #define PCI_CLSZ_REG            0x0c
39 #define PCI_LATTIM_REG          0x0d
40 #define PCI_HEADER_REG          0x0e
41 #define PCI_BIST_REG            0x0f
42 /* Config space for header type 0x00  (Standard) */
43 #define PCI_BAR0_STD            0x10
44 #define PCI_BAR1_STD            0x14
45 #define PCI_BAR2_STD            0x18
46 #define PCI_BAR3_STD            0x1c
47 #define PCI_BAR4_STD            0x20
48 #define PCI_BAR5_STD            0x24
49 #define PCI_BAR_OFF                     0x04
50 #define PCI_CARDBUS_STD         0x28
51 #define PCI_SUBSYSVEN_STD       0x2c
52 #define PCI_SUBSYSID_STD        0x2e
53 #define PCI_EXPROM_STD          0x30
54 #define PCI_CAPAB_STD           0x34
55 #define PCI_IRQLINE_STD         0x3c
56 #define PCI_IRQPIN_STD          0x3d
57 #define PCI_MINGRNT_STD         0x3e
58 #define PCI_MAXLAT_STD          0x3f
59 /* Config space for header type 0x01 (PCI-PCI bridge) */
60 /* None of these have been used, so if you use them, check them against
61  * http://wiki.osdev.org/PCI#PCI_Device_Structure */
62 #define PCI_BAR0_BR                     0x10
63 #define PCI_BAR1_BR                     0x14
64 #define PCI_BUS1_BR                     0x18
65 #define PCI_BUS2_BR                     0x19
66 #define PCI_SUBBUS_BR           0x1a
67 #define PCI_LATTIM2_BR          0x1b
68 #define PCI_IOBASE_BR           0x1c
69 #define PCI_IOLIM_BR            0x1d
70 #define PCI_STATUS2_BR          0x1e
71 #define PCI_MEMBASE_BR          0x20
72 #define PCI_MEMLIM_BR           0x22
73 #define PCI_PREMEMBASE_BR       0x24
74 #define PCI_PREMEMLIM_BR        0x26
75 #define PCI_PREBASEUP32_BR      0x28
76 #define PCI_PRELIMUP32_BR       0x2c
77 #define PCI_IOBASEUP16_BR       0x30
78 #define PCI_IOLIMUP16_BR        0x32
79 #define PCI_CAPAB_BR            0x34
80 #define PCI_EXPROM_BR           0x38
81 #define PCI_IRQLINE_BR          0x3c
82 #define PCI_IRQPIN_BR           0x3d
83 #define PCI_BDGCTL_BR           0x3e
84 /* Config space for header type 0x02 (PCI-Cardbus bridge) */
85 /* None of these have been used, so if you use them, check them against
86  * http://wiki.osdev.org/PCI#PCI_Device_Structure */
87 #define PCI_SOC_BASE_CB         0x10
88 #define PCI_OFF_CAP_CB          0x14
89 #define PCI_SEC_STAT_CB         0x16
90 #define PCI_BUS_NR_CB           0x18
91 #define PCI_CARDBUS_NR_CB       0x19
92 #define PCI_SUBBUS_NR_CB        0x1a
93 #define PCI_CARD_LAT_CB         0x1b
94 #define PCI_MEM_BASE0_CB        0x1c
95 #define PCI_MEM_LIMIT0_CB       0x20
96 #define PCI_MEM_BASE1_CB        0x24
97 #define PCI_MEM_LIMIT1_CB       0x28
98 #define PCI_IO_BASE0_CB         0x2c
99 #define PCI_IO_LIMIT0_CB        0x30
100 #define PCI_IO_BASE1_CB         0x34
101 #define PCI_IO_LIMIT1_CB        0x38
102 #define PCI_IRQLINE_CB          0x3c
103 #define PCI_IRQPIN_CB           0x3d
104 #define PCI_BDGCTL_CB           0x3e
105 #define PCI_SUBDEVID_CB         0x40
106 #define PCI_SUBVENID_CB         0x42
107 #define PCI_16BIT_CB            0x44
108
109 /* Command Register Flags */
110 #define PCI_CMD_IO_SPC          (1 << 0)
111 #define PCI_CMD_MEM_SPC         (1 << 1)
112 #define PCI_CMD_BUS_MAS         (1 << 2)
113 #define PCI_CMD_SPC_CYC         (1 << 3)
114 #define PCI_CMD_WR_EN           (1 << 4)
115 #define PCI_CMD_VGA                     (1 << 5)
116 #define PCI_CMD_PAR_ERR         (1 << 6)
117 /* #define PCI_CMD_XXX          (1 << 7) Reserved */
118 #define PCI_CMD_SERR            (1 << 8)
119 #define PCI_CMD_FAST_EN         (1 << 9)
120 #define PCI_CMD_IRQ_DIS         (1 << 10)
121
122 /* Status Register Flags (Bits 9 and 10 are one field) */
123 /* Bits 0, 1, and 2 are reserved */
124 #define PCI_ST_IRQ_STAT         (1 << 3)
125 #define PCI_ST_CAP_LIST         (1 << 4)
126 #define PCI_ST_66MHZ            (1 << 5)
127 /* #define PCI_CMD_XXX          (1 << 6)  Reserved */
128 #define PCI_ST_FAST_CAP         (1 << 7)
129 #define PCI_ST_MASPAR_ERR       (1 << 8)
130 #define PCI_ST_DEVSEL_TIM       (3 << 9)        /* 2 bits */
131 #define PCI_ST_SIG_TAR_ABRT     (1 << 11)
132 #define PCI_ST_REC_TAR_ABRT     (1 << 12)
133 #define PCI_ST_REC_MAS_ABRT     (1 << 13)
134 #define PCI_ST_SIG_SYS_ERR      (1 << 14)
135 #define PCI_ST_PAR_ERR          (1 << 15)
136
137 /* BARS: Base Address Registers */
138 #define PCI_BAR_IO                      0x1                     /* 1 == IO, 0 == Mem */
139 #define PCI_BAR_IO_MASK         0xfffffffc
140 #define PCI_BAR_MEM_MASK        0xfffffff0
141 #define PCI_MEMBAR_TYPE         (3 << 1)
142 #define PCI_MEMBAR_32BIT        0x0
143 #define PCI_MEMBAR_RESV         0x2                     /* type 0x1 shifted to MEMBAR_TYPE */
144 #define PCI_MEMBAR_64BIT        0x4                     /* type 0x2 shifted to MEMBAR_TYPE */
145
146 #define PCI_MAX_BUS                     256
147 #define PCI_MAX_DEV                     32
148 #define PCI_MAX_FUNC            8
149
150 // Run the PCI Code to loop over the PCI BARs. For now we don't use the BARs,
151 // dont check em.
152 #define CHECK_BARS                      0
153
154 #define MAX_PCI_BAR                     6
155
156 struct pci_bar {
157         uint32_t                                        raw_bar;
158         uint32_t                                        pio_base;
159         uint32_t                                        mmio_base32;
160         uint64_t                                        mmio_base64;
161         uint32_t                                        mmio_sz;
162 };
163
164 /* Struct for some meager contents of a PCI device */
165 struct pci_device {
166         STAILQ_ENTRY(pci_device)        all_dev;        /* list of all devices */
167         SLIST_ENTRY(pci_device)         irq_dev;        /* list of all devs off an irq */
168         bool                                            in_use;         /* prevent double discovery */
169         uint8_t                                         bus;
170         uint8_t                                         dev;
171         uint8_t                                         func;
172         uint16_t                                        dev_id;
173         uint16_t                                        ven_id;
174         uint8_t                                         irqline;
175         uint8_t                                         irqpin;
176         char                                            *header_type;
177         uint8_t                                         class;
178         uint8_t                                         subclass;
179         uint8_t                                         progif;
180         uint8_t                                         nr_bars;
181         struct pci_bar                          bar[MAX_PCI_BAR];
182 };
183
184 /* List of all discovered devices */
185 STAILQ_HEAD(pcidev_stailq, pci_device);
186 SLIST_HEAD(pcidev_slist, pci_device);
187 extern struct pcidev_stailq pci_devices;
188
189 void pci_init(void);
190 void pcidev_print_info(struct pci_device *pcidev, int verbosity);
191 uint32_t pci_config_addr(uint8_t bus, uint8_t dev, uint8_t func, uint8_t reg);
192
193 /* Read and write helpers (Eventually, we should have these be statics, since no
194  * device should touch PCI config space). */
195 uint32_t pci_read32(uint8_t bus, uint8_t dev, uint8_t func, uint8_t offset);
196 void pci_write32(uint8_t bus, uint8_t dev, uint8_t func, uint8_t offset,
197                  uint32_t value);
198 uint32_t pcidev_read32(struct pci_device *pcidev, uint8_t offset);
199 void pcidev_write32(struct pci_device *pcidev, uint8_t offset, uint32_t value);
200 uint16_t pcidev_read16(struct pci_device *pcidev, uint8_t offset);
201 void pcidev_write16(struct pci_device *pcidev, uint8_t offset, uint16_t value);
202 uint8_t pcidev_read8(struct pci_device *pcidev, uint8_t offset);
203 void pcidev_write8(struct pci_device *pcidev, uint8_t offset, uint8_t value);
204
205 /* BAR helpers, some more helpful than others. */
206 uint32_t pci_membar_get_sz(struct pci_device *pcidev, int bar);
207 uint32_t pci_getbar(struct pci_device *pcidev, unsigned int bar);
208 bool pci_is_iobar(uint32_t bar);
209 bool pci_is_membar32(uint32_t bar);
210 bool pci_is_membar64(uint32_t bar);
211 uint32_t pci_getmembar32(uint32_t bar);
212 uint32_t pci_getiobar32(uint32_t bar);
213
214 /* Other common PCI functions */
215 void pci_set_bus_master(struct pci_device *pcidev);
216
217 #endif /* ROS_ARCH_PCI_H */