Merge branch 'arrakis'
[barrelfish] / usr / pci / pci.c
1 /**
2  * \file
3  * \brief PCI driver
4  *
5  *  This file walks through the PCI bus, enumarates each device and gathers
6  *  informatiom about each device.
7  */
8
9 /*
10  * Copyright (c) 2007, 2008, 2009, 2010, 2011, ETH Zurich.
11  * All rights reserved.
12  *
13  * This file is distributed under the terms in the attached LICENSE file.
14  * If you do not find this file, copies can be found by writing to:
15  * ETH Zurich D-INFK, Haldeneggsteig 4, CH-8092 Zurich. Attn: Systems Group.
16  */
17
18 #include <stdio.h>
19 #include <stdlib.h>
20
21 #include <barrelfish/barrelfish.h>
22 #include <barrelfish/deferred.h>
23
24 #include <pci/devids.h>
25 #include <mm/mm.h>
26 #include <skb/skb.h>
27 #include <octopus/getset.h>
28 #include <acpi_client/acpi_client.h>
29 #include <dev/pci_sr_iov_cap_dev.h>
30
31 #include "pci.h"
32 #include "driver_mapping.h"
33 #include "ht_config.h"
34 #include <dev/ht_config_dev.h>
35 #include "pci_debug.h"
36
37 #define MIN(a,b)        ((a) < (b) ? (a) : (b))
38
39 #define BAR_PROBE       0xffffffff
40
41 #define PAGE_BITS BASE_PAGE_BITS
42
43 struct device_caps
44 {
45     struct capref *phys_cap;
46     struct capref *frame_cap;
47     size_t nr_caps;
48     uint8_t bar_nr;
49     uint8_t bits;
50     bool assigned;  //false => this entry is not in use
51     uint8_t type;
52 };
53
54 struct device_caps dev_caps[PCI_NBUSES][PCI_NDEVICES][PCI_NFUNCTIONS][PCI_NBARS];
55 const char *skb_bridge_program = "bridge_page";
56 uint16_t max_numvfs = 256;
57
58 static void
59 query_bars(pci_hdr0_t devhdr,
60            struct pci_address addr,
61            bool pci2pci_bridge);
62
63 static uint32_t
64 setup_interrupt(uint32_t bus,
65                 uint32_t dev,
66                 uint32_t fun);
67 static void
68 enable_busmaster(uint8_t bus,
69                  uint8_t dev,
70                  uint8_t fun,
71                  bool pcie);
72
73 static uint32_t bar_mapping_size(pci_hdr0_bar32_t bar)
74 {
75     if (bar.base == 0) {
76         return 0;
77     }
78
79     for (uint32_t mask = 1;; mask <<= 1) {
80         assert(mask != 0);
81         if (bar.base & mask) {
82             return mask << 7;
83         }
84     }
85 }
86
87 static pciaddr_t bar_mapping_size64(uint64_t base)
88 {
89     if (base == 0) {
90         return 0;
91     }
92
93     for (pciaddr_t mask = 1;; mask <<= 1) {
94         assert(mask != 0);
95         if (base & mask) {
96             /*
97              * Note: we get the actual raw register content here and not
98              *       the bar.base value so no shift.
99              *       - 2014-05-03, RA
100              */
101             return mask;
102         }
103     }
104 }
105
106 void pci_init_datastructures(void)
107 {
108     memset(dev_caps, 0, sizeof(dev_caps));
109 }
110
111 int pci_bar_to_caps_index(uint8_t bus,
112                           uint8_t dev,
113                           uint8_t fun,
114                           uint8_t BAR)
115 {
116     uint8_t i;
117     for (i = 0; i < PCI_NBARS && dev_caps[bus][dev][fun][i].assigned; i++) {
118         if (dev_caps[bus][dev][fun][i].bar_nr == BAR) {
119             return i;
120         }
121     }
122     return -1;
123 }
124
125 int pci_get_bar_nr_for_index(uint8_t bus,
126                             uint8_t dev,
127                             uint8_t fun,
128                             uint8_t idx)
129 {
130     return (dev_caps[bus][dev][fun][idx].bar_nr);
131 }
132
133 int pci_get_nr_caps_for_bar(uint8_t bus,
134                             uint8_t dev,
135                             uint8_t fun,
136                             uint8_t idx)
137 {
138     return (dev_caps[bus][dev][fun][idx].nr_caps);
139 }
140
141 struct capref pci_get_cap_for_device(uint8_t bus,
142                                      uint8_t dev,
143                                      uint8_t fun,
144                                      uint8_t idx,
145                                      int cap_nr)
146 {
147     return (dev_caps[bus][dev][fun][idx].frame_cap[cap_nr]);
148 }
149 uint8_t pci_get_cap_type_for_device(uint8_t bus,
150                                     uint8_t dev,
151                                     uint8_t fun,
152                                     uint8_t idx)
153 {
154     return (dev_caps[bus][dev][fun][idx].type);
155 }
156
157 static errval_t alloc_device_bar(uint8_t idx,
158                                  uint8_t bus,
159                                  uint8_t dev,
160                                  uint8_t fun,
161                                  uint8_t BAR,
162                                  pciaddr_t base,
163                                  pciaddr_t high,
164                                  pcisize_t size)
165 {
166     struct acpi_rpc_client* acl = get_acpi_rpc_client();
167
168     struct device_caps *c = &dev_caps[bus][dev][fun][idx];
169     errval_t err;
170
171     // first try with maximally-sized caps (we'll reduce this if it doesn't work)
172     uint8_t bits = log2ceil(size);
173
174     restart: ;
175     pcisize_t framesize = 1UL << bits;
176     c->nr_caps = size / framesize;
177     PCI_DEBUG("nr caps for one BAR of size %"PRIuPCISIZE": %lu\n", size,
178               c->nr_caps);
179
180     c->phys_cap = malloc(c->nr_caps * sizeof(struct capref));
181     if (c->phys_cap == NULL) {
182         return PCI_ERR_MEM_ALLOC;
183     }
184
185     for (int i = 0; i < c->nr_caps; i++) {
186         /*err = mm_alloc_range(&pci_mm_physaddr, bits, base + i * framesize,
187          base + (i + 1) * framesize, &c->phys_cap[i], NULL);*/
188         errval_t error_code;
189         err = acl->vtbl.mm_alloc_range_proxy(acl, bits, base + i * framesize,
190                                              base + (i + 1) * framesize,
191                                              &c->phys_cap[i], &error_code);
192         assert(err_is_ok(err));
193         err = error_code;
194         if (err_is_fail(err)) {
195             PCI_DEBUG("mm_alloc_range() failed: bits = %hhu, base = %"PRIxPCIADDR","
196                       " end = %"PRIxPCIADDR"\n", bits, base + i * framesize,
197                       base + (i + 1) * framesize);
198             if (err_no(err) == MM_ERR_MISSING_CAPS && bits > PAGE_BITS) {
199                 /* try again with smaller page-sized caps */
200                 for (int j = 0; j < i; j++) {
201                     err = acl->vtbl.mm_free_proxy(acl, c->phys_cap[i],
202                                                   base + j * framesize, bits,
203                                                   &error_code);
204                     assert(err_is_ok(err) && err_is_ok(error_code));
205                 }
206
207                 free(c->phys_cap);
208                 bits = PAGE_BITS;
209                 goto restart;
210             } else {
211                 return err;
212             }
213         }
214     }
215
216     c->frame_cap = malloc(c->nr_caps * sizeof(struct capref));
217     if (c->frame_cap == NULL) {
218         /* TODO: mm_free() */
219         free(c->phys_cap);
220         return PCI_ERR_MEM_ALLOC;
221     }
222
223     for (int i = 0; i < c->nr_caps; i++) {
224         err = devframe_type(&c->frame_cap[i], c->phys_cap[i], bits);
225         if (err_is_fail(err)) {
226             PCI_DEBUG("devframe_type() failed: bits = %hhu, base = %"PRIxPCIADDR
227                       ", doba = %"PRIxPCIADDR"\n", bits, base, base + (1UL << bits));
228             return err;
229         }
230     }
231
232     c->bits = bits;
233     c->bar_nr = BAR;
234     c->assigned = true;
235     c->type = 0;
236
237     return SYS_ERR_OK;
238 }
239
240 //XXX: FIXME: HACK: BAD!!! Only needed to allocate a full I/O range cap to
241 //                         the VESA graphics driver
242 static errval_t assign_complete_io_range(uint8_t idx,
243                                          uint8_t bus,
244                                          uint8_t dev,
245                                          uint8_t fun,
246                                          uint8_t BAR)
247 {
248     dev_caps[bus][dev][fun][idx].frame_cap = (struct capref*) malloc(
249                     sizeof(struct capref));
250     errval_t err = slot_alloc(&(dev_caps[bus][dev][fun][idx].frame_cap[0]));
251     assert(err_is_ok(err));
252     err = cap_copy(dev_caps[bus][dev][fun][idx].frame_cap[0], cap_io);
253     assert(err_is_ok(err));
254
255     dev_caps[bus][dev][fun][idx].bits = 16;
256     dev_caps[bus][dev][fun][idx].bar_nr = BAR;
257     dev_caps[bus][dev][fun][idx].assigned = true;
258     dev_caps[bus][dev][fun][idx].type = 1;
259     dev_caps[bus][dev][fun][idx].nr_caps = 1;
260     return SYS_ERR_OK;
261 }
262
263 errval_t device_init(bool enable_irq,
264                      uint8_t coreid,
265                      int vector,
266                      uint32_t class_code,
267                      uint32_t sub_class,
268                      uint32_t prog_if,
269                      uint32_t vendor_id,
270                      uint32_t device_id,
271                      uint32_t *bus,
272                      uint32_t *dev,
273                      uint32_t *fun,
274                      int *nr_allocated_bars)
275 {
276     *nr_allocated_bars = 0;
277
278     errval_t err;
279     char s_bus[10], s_dev[10], s_fun[10], s_vendor_id[10], s_device_id[10];
280     char s_class_code[10], s_sub_class[10], s_prog_if[10];
281     char s_pcie[5];
282     bool pcie;
283     int error_code;
284     int bar_nr;
285     pciaddr_t bar_base, bar_high;
286     pcisize_t bar_size;
287
288     if (*bus != PCI_DONT_CARE) {
289         snprintf(s_bus, sizeof(s_bus), "%"PRIu32"", *bus);
290     } else {
291         strncpy(s_bus, "Bus", sizeof(s_bus));
292     }
293     if (*dev != PCI_DONT_CARE) {
294         snprintf(s_dev, sizeof(s_dev), "%"PRIu32, *dev);
295     } else {
296         strncpy(s_dev, "Dev", sizeof(s_dev));
297     }
298     if (*fun != PCI_DONT_CARE) {
299         snprintf(s_fun, sizeof(s_fun), "%"PRIu32, *fun);
300     } else {
301         strncpy(s_fun, "Fun", sizeof(s_fun));
302     }
303     if (vendor_id != PCI_DONT_CARE) {
304         snprintf(s_vendor_id, sizeof(s_vendor_id), "%"PRIu32, vendor_id);
305     } else {
306         strncpy(s_vendor_id, "Ven", sizeof(s_vendor_id));
307     }
308     if (device_id != PCI_DONT_CARE) {
309         snprintf(s_device_id, sizeof(s_device_id), "%"PRIu32, device_id);
310     } else {
311         strncpy(s_device_id, "DevID", sizeof(s_device_id));
312     }
313     if (class_code != PCI_DONT_CARE) {
314         snprintf(s_class_code, sizeof(s_class_code), "%"PRIu32, class_code);
315     } else {
316         strncpy(s_class_code, "Cl", sizeof(s_class_code));
317     }
318     if (sub_class != PCI_DONT_CARE) {
319         snprintf(s_sub_class, sizeof(s_sub_class), "%"PRIu32, sub_class);
320     } else {
321         strncpy(s_sub_class, "Sub", sizeof(s_sub_class));
322     }
323     if (prog_if != PCI_DONT_CARE) {
324         snprintf(s_prog_if, sizeof(s_prog_if), "%"PRIu32, prog_if);
325     } else {
326         strncpy(s_prog_if, "ProgIf", sizeof(s_prog_if));
327     }
328
329     PCI_DEBUG("device_init(): Searching device %s, %s, %s, %s, %s, %s, %s, %s\n",
330               s_bus, s_dev, s_fun, s_vendor_id, s_device_id, s_class_code,
331               s_sub_class, s_prog_if);
332
333 //find the device: Unify all values
334     error_code = skb_execute_query(
335                     "device(PCIE,addr(%s, %s, %s), %s, %s, %s, %s, %s, _),"
336                     "writeln(d(PCIE,%s,%s,%s,%s,%s,%s,%s,%s)).",
337                     s_bus, s_dev, s_fun, s_vendor_id, s_device_id, s_class_code,
338                     s_sub_class, s_prog_if, s_bus, s_dev, s_fun, s_vendor_id,
339                     s_device_id, s_class_code, s_sub_class, s_prog_if);
340     if (error_code != 0) {
341
342         PCI_DEBUG("pci.c: device_init(): SKB returnd error code %s\n",
343                   err_getcode(error_code));
344
345         PCI_DEBUG("SKB returned: %s\n", skb_get_output());
346         PCI_DEBUG("SKB error returned: %s\n", skb_get_error_output());
347
348         return PCI_ERR_DEVICE_INIT;
349     }
350
351     err = skb_read_output("d(%[a-z], %"PRIu32", %"PRIu32", %"PRIu32", %"PRIu32
352                           ",%"PRIu32", %"PRIu32", %"PRIu32", %"PRIu32").",
353                           s_pcie, bus, dev, fun, &vendor_id, &device_id,
354                           &class_code, &sub_class, &prog_if);
355
356     if (err_is_fail(err)) {
357         DEBUG_ERR(err, "skb read output\n");
358
359         PCI_DEBUG("device_init(): Could not read the SKB's output for the device\n");
360         PCI_DEBUG("device_init(): SKB returned: %s\n", skb_get_output());
361         PCI_DEBUG("device_init(): SKB error returned: %s\n",
362                   skb_get_error_output());
363         return err_push(err, PCI_ERR_DEVICE_INIT);
364     }
365     if (strncmp(s_pcie, "pcie", strlen("pcie")) == 0) {
366         pcie = true;
367     } else {
368         pcie = false;
369     }
370
371     PCI_DEBUG("device_init(): Found device at %u:%u:%u\n", *bus, *dev, *fun);
372     //get the implemented BARs for the found device
373     error_code = skb_execute_query("pci_get_implemented_BAR_addresses(%"PRIu32
374                                    ",%"PRIu32",%"PRIu32",%"PRIu32",%"PRIu32",%"
375                                    PRIu32",%"PRIu32",%"PRIu32",L),length(L,Len)"
376                                    ",writeln(L)", *bus, *dev, *fun, vendor_id,
377                                    device_id, class_code, sub_class, prog_if);
378
379     if (error_code != 0) {
380         PCI_DEBUG("pci.c: device_init(): SKB returnd error code %d\n",
381                   error_code);
382
383         PCI_DEBUG("SKB returned: %s\n", skb_get_output());
384         PCI_DEBUG("SKB error returned: %s\n", skb_get_error_output());
385
386         return PCI_ERR_DEVICE_INIT;
387     }
388
389     struct list_parser_status status;
390     skb_read_list_init(&status);
391
392     //iterate over all buselements
393     while (skb_read_list(&status, "baraddr(%d, %"PRIuPCIADDR", %"PRIuPCIADDR", "
394                          "%"PRIuPCISIZE")", &bar_nr, &bar_base, &bar_high, &bar_size)) {
395         err = alloc_device_bar(*nr_allocated_bars, *bus, *dev, *fun, bar_nr,
396                                bar_base, bar_high, bar_size);
397
398         PCI_DEBUG("device_init(): BAR %d: base = %"PRIxPCIADDR ", size = %"
399                   PRIxPCISIZE"\n", bar_nr, bar_base, bar_size);
400
401         if (err_is_fail(err)) {
402             PCI_DEBUG("device_init(): Could not allocate cap for BAR %d\n", bar_nr);
403             return err_push(err, PCI_ERR_DEVICE_INIT);
404         }
405         (*nr_allocated_bars)++;
406     }
407
408 //XXX: FIXME: HACK: BAD!!! Only needed to allocate a full I/O range cap to
409 //                         the VESA graphics driver
410     if (class_code == PCI_CLASS_DISPLAY) {
411         assert(*nr_allocated_bars < PCI_NBARS);
412         err = assign_complete_io_range(*nr_allocated_bars, *bus, *dev, *fun,
413                                        5 /*very BAAAD */);
414         (*nr_allocated_bars)++;
415     }
416 //end of badness
417
418     PCI_DEBUG("device_init(): Allocated caps for %d BARs\n", *nr_allocated_bars);
419     if (enable_irq) {
420         int irq = setup_interrupt(*bus, *dev, *fun);
421         PCI_DEBUG("pci: init_device_handler_irq: init interrupt.\n");
422         PCI_DEBUG("pci: irq = %u, core = %hhu, vector = %u\n", irq, coreid,
423                   vector);
424         struct acpi_rpc_client* cl = get_acpi_rpc_client();
425         errval_t ret_error;
426         err = cl->vtbl.enable_and_route_interrupt(cl, irq, coreid, vector,
427                                                   &ret_error);
428         assert(err_is_ok(err));
429         assert(err_is_ok(ret_error));  // FIXME
430 //        printf("IRQ for this device is %d\n", irq);
431                         //DEBUG_ERR(err, "enable_and_route_interrupt");
432         pci_enable_interrupt_for_device(*bus, *dev, *fun, pcie);
433     }
434
435     PCI_DEBUG("enable busmaster for device (%u, %u, %u)...\n", *bus, *dev, *fun);
436     enable_busmaster(*bus, *dev, *fun, pcie);
437
438     return SYS_ERR_OK;
439 }
440
441 errval_t device_reregister_interrupt(uint8_t coreid, int vector,
442                  uint32_t class_code, uint32_t sub_class, uint32_t prog_if,
443                  uint32_t vendor_id, uint32_t device_id, uint32_t *bus,
444                  uint32_t *dev,uint32_t *fun)
445 {
446     errval_t err;
447     char s_bus[10], s_dev[10], s_fun[10], s_vendor_id[10], s_device_id[10];
448     char s_class_code[10], s_sub_class[10], s_prog_if[10];
449     char s_pcie[5];
450     bool pcie;
451     int error_code;
452
453     if (*bus != PCI_DONT_CARE) {
454         snprintf(s_bus, sizeof(s_bus), "%"PRIu32"", *bus);
455     } else {
456         strncpy(s_bus, "Bus", sizeof(s_bus));
457     }
458     if (*dev != PCI_DONT_CARE) {
459         snprintf(s_dev, sizeof(s_dev), "%"PRIu32, *dev);
460     } else {
461         strncpy(s_dev, "Dev", sizeof(s_dev));
462     }
463     if (*fun != PCI_DONT_CARE) {
464         snprintf(s_fun, sizeof(s_fun), "%"PRIu32, *fun);
465     } else {
466         strncpy(s_fun, "Fun", sizeof(s_fun));
467     }
468     if (vendor_id != PCI_DONT_CARE) {
469         snprintf(s_vendor_id, sizeof(s_vendor_id), "%"PRIu32, vendor_id);
470     } else {
471         strncpy(s_vendor_id, "Ven", sizeof(s_vendor_id));
472     }
473     if (device_id != PCI_DONT_CARE) {
474         snprintf(s_device_id, sizeof(s_device_id), "%"PRIu32, device_id);
475     } else {
476         strncpy(s_device_id, "DevID", sizeof(s_device_id));
477     }
478     if (class_code != PCI_DONT_CARE) {
479         snprintf(s_class_code, sizeof(s_class_code), "%"PRIu32, class_code);
480     } else {
481         strncpy(s_class_code, "Cl", sizeof(s_class_code));
482     }
483     if (sub_class != PCI_DONT_CARE) {
484         snprintf(s_sub_class, sizeof(s_sub_class), "%"PRIu32, sub_class);
485     } else {
486         strncpy(s_sub_class, "Sub", sizeof(s_sub_class));
487     }
488     if (prog_if != PCI_DONT_CARE) {
489         snprintf(s_prog_if, sizeof(s_prog_if), "%"PRIu32, prog_if);
490     } else {
491         strncpy(s_prog_if, "ProgIf", sizeof(s_prog_if));
492     }
493
494     PCI_DEBUG("device_init(): Searching device %s, %s, %s, %s, %s, %s, %s, %s\n",
495         s_bus, s_dev, s_fun, s_vendor_id, s_device_id, s_class_code,
496         s_sub_class, s_prog_if);
497
498 //find the device: Unify all values
499     error_code = skb_execute_query(
500         "device(PCIE,addr(%s, %s, %s), %s, %s, %s, %s, %s, _),"
501         "writeln(d(PCIE,%s,%s,%s,%s,%s,%s,%s,%s)).",
502         s_bus, s_dev, s_fun, s_vendor_id, s_device_id, s_class_code,
503         s_sub_class, s_prog_if,
504         s_bus, s_dev, s_fun, s_vendor_id, s_device_id, s_class_code,
505         s_sub_class, s_prog_if
506     );
507     if (error_code != 0) {
508
509         PCI_DEBUG("pci.c: device_init(): SKB returnd error code %s\n",
510             err_getcode(error_code));
511
512         PCI_DEBUG("SKB returned: %s\n", skb_get_output());
513         PCI_DEBUG("SKB error returned: %s\n", skb_get_error_output());
514
515         return PCI_ERR_DEVICE_INIT;
516     }
517
518     err = skb_read_output("d(%[a-z], %"PRIu32", %"PRIu32", %"PRIu32", %"PRIu32
519                           ",%"PRIu32", %"PRIu32", %"PRIu32", %"PRIu32").",
520                     s_pcie, bus, dev, fun, &vendor_id,
521                     &device_id, &class_code, &sub_class, &prog_if);
522
523     if (err_is_fail(err)) {
524         DEBUG_ERR(err, "skb read output\n");
525
526         PCI_DEBUG("device_init(): Could not read the SKB's output for the device\n");
527         PCI_DEBUG("device_init(): SKB returned: %s\n", skb_get_output());
528         PCI_DEBUG("device_init(): SKB error returned: %s\n", skb_get_error_output());
529         return err_push(err,PCI_ERR_DEVICE_INIT);
530     }
531     if(strncmp(s_pcie, "pcie", strlen("pcie")) == 0) {
532         pcie = true;
533     } else {
534         pcie = false;
535     }
536
537
538     PCI_DEBUG("device_init(): Found device at %u:%u:%u\n",
539                 *bus, *dev, *fun);
540 //get the implemented BARs for the found device
541
542     int irq = setup_interrupt(*bus, *dev, *fun);
543     PCI_DEBUG("pci: init_device_handler_irq: init interrupt.\n");
544     PCI_DEBUG("pci: irq = %u, core = %hhu, vector = %u\n",
545             irq, coreid, vector);
546     struct acpi_rpc_client* cl = get_acpi_rpc_client();
547     errval_t ret_error;
548     err = cl->vtbl.enable_and_route_interrupt(cl, irq, coreid, vector, &ret_error);
549     assert(err_is_ok(err));
550     assert(err_is_ok(ret_error)); // FIXME
551     //        printf("IRQ for this device is %d\n", irq);
552     //DEBUG_ERR(err, "enable_and_route_interrupt");
553     pci_enable_interrupt_for_device(*bus, *dev, *fun, pcie);
554
555     return SYS_ERR_OK;
556 }
557
558 void pci_enable_interrupt_for_device(uint32_t bus, uint32_t dev, uint32_t fun,
559                                     bool pcie)
560 {
561     struct pci_address addr = { .bus = (uint8_t)(bus & 0xff),
562                                 .device = (uint8_t)(dev & 0xff),
563                                 .function = (uint8_t)(fun % 0xff) };
564
565     pci_hdr0_t hdr;
566     pci_hdr0_initialize(&hdr, addr);
567
568     if (pcie) {
569         pcie_enable();
570     } else {
571         pcie_disable();
572     }
573
574     pci_hdr0_command_t cmd = pci_hdr0_command_rd(&hdr);
575     cmd.int_dis = 0;
576     pci_hdr0_command_wr(&hdr, cmd);
577 }
578
579 /**
580  * This function performs a recursive, depth-first search through the
581  * PCI hierarchy starting at parentaddr (this should initially be a
582  * PCI root complex), with bus number A. It enters whatever it
583  * discovers (bridges and devices) into the SKB.
584  *
585  * Refer to http://www.tldp.org/LDP/tlk/dd/pci.html for an overview of
586  * a similar discovery algorithm.
587  *
588  * Upon discovery of a bridge, it sets the bridge's primary bus number
589  * to A and assigns a secondary bus number of A + 2. The subordinate
590  * bus number is set to A + 3. This way, buses are spaced 2 apart,
591  * which is sometimes required for SR-IOV hot-plugged buses.
592  */
593 static void assign_bus_numbers(struct pci_address parentaddr,
594                                uint8_t *busnum,
595                                uint8_t maxchild,
596                                char* handle)
597 {
598     struct pci_address addr = {
599         .bus = parentaddr.bus
600     };
601
602     pcie_enable();
603
604     // First go through all bridges on this bus and disable them
605     for (addr.device = 0; addr.device < PCI_NDEVICES; addr.device++) {
606         for (addr.function = 0; addr.function < PCI_NFUNCTIONS; addr.function++) {
607             pci_hdr1_t bhdr;
608             pci_hdr1_initialize(&bhdr, addr);
609
610             uint16_t vendor = pci_hdr1_vendor_id_rd(&bhdr);
611
612             if (vendor == 0xffff) {
613                 if (addr.function == 0) {
614                     // this device doesn't exist at all
615                     break;
616                 } else {
617                     // this function doesn't exist, but there may be others
618                     continue;
619                 }
620             }
621
622             pci_hdr1_hdr_type_t hdr_type = pci_hdr1_hdr_type_rd(&bhdr);
623             if (hdr_type.fmt == pci_hdr1_pci2pci) {
624                 PCI_DEBUG("Disabling bridge (%u,%u,%u)\n", addr.bus, addr.device,
625                           addr.function);
626
627                 pci_hdr1_bcfg_t bcfg = pci_hdr1_bcfg_rd(&bhdr);
628                 bcfg.pri_bus = 0;
629                 bcfg.sec_bus = 0;
630                 bcfg.sub_bus = 0;
631                 pci_hdr1_bcfg_wr(&bhdr, bcfg);
632             }
633         }
634     }
635
636     for (addr.device = 0; addr.device < PCI_NDEVICES; addr.device++) {
637         for (addr.function = 0; addr.function < PCI_NFUNCTIONS; addr.function++) {
638             pci_hdr0_t hdr;
639             pci_hdr0_initialize(&hdr, addr);
640
641             pcie_enable();
642             uint16_t pcie_vendor = pci_hdr0_vendor_id_rd(&hdr);
643             uint16_t vendor = pcie_vendor;
644             bool pcie = true;
645             bool extended_caps = false;  // Whether to scan for PCI Express extended caps
646
647             // Disable PCIe if device exists only in PCI
648             if (pcie_vendor != 0xffff) {
649                 vendor = pcie_vendor;
650                 pcie = true;
651             } else {
652                 pcie_disable();
653                 vendor = pci_hdr0_vendor_id_rd(&hdr);
654                 pcie = false;
655             }
656
657             if (vendor == 0xffff) {
658                 if (addr.function == 0) {
659                     // this device doesn't exist at all
660                     break;
661                 } else {
662                     // this function doesn't exist, but there may be others
663                     continue;
664                 }
665             }
666             pci_hdr0_class_code_t classcode = pci_hdr0_class_code_rd(&hdr);
667             uint16_t device_id = pci_hdr0_device_id_rd(&hdr);
668
669             /* Disable all decoders for this device,
670              * they will be re-enabled as devices are setup.
671              * NB: we are using "pci_hdr1" here, but the command field is
672              * common to all configuration header types.
673              */
674             /* PCI_DEBUG("disabling decoders for (%hhu,%hhu,%hhu)\n", */
675             /*     addr.bus, addr.device, addr.function); */
676             pci_hdr0_command_t cmd = pci_hdr0_command_rd(&hdr);
677
678             cmd.mem_space = 0;
679             cmd.io_space = 0;  // XXX: not handled in setup yet
680
681             // Ticket #210
682             //XXX: This should be set to 0 and only enabled if needed
683             //     (whenever a driver attaches to a device).
684             //     For bridges the pci driver enables the bit later when
685             //     programming the bridge window
686 //            cmd.master = 0;
687
688             // Ticket 229
689             //pci_hdr0_command_wr(&hdr, cmd);
690
691             // do we have a bridge?
692             pci_hdr0_hdr_type_t hdr_type = pci_hdr0_hdr_type_rd(&hdr);
693             if (hdr_type.fmt == pci_hdr0_pci2pci) {
694                 pci_hdr1_t bhdr;
695                 pci_hdr1_initialize(&bhdr, addr);
696
697                 //ACPI_HANDLE child;
698                 char* child = NULL;
699                 errval_t error_code;
700                 PCI_DEBUG("get irq table for (%hhu,%hhu,%hhu)\n", (*busnum) + 1,
701                           addr.device, addr.function);
702                 struct acpi_rpc_client* cl = get_acpi_rpc_client();
703                 // XXX: why do we have two different types for the same thing?
704                 acpi_pci_address_t xaddr = {
705                     .bus = addr.bus,
706                     .device = addr.device,
707                     .function = addr.function,
708                 };
709                 cl->vtbl.read_irq_table(cl, handle, xaddr, (*busnum) + 1,
710                                         &error_code, &child);
711                 if (err_is_fail(error_code)) {
712                     DEBUG_ERR(error_code, "Reading IRQs failed");
713                     assert(!"Check ACPI code");
714                 }
715
716                 // Increase by 2 to leave room for SR-IOV
717                 (*busnum) += 2;
718                 //assert(*busnum <= maxchild);
719
720                 PCI_DEBUG("program busses for bridge (%hhu,%hhu,%hhu)\n"
721                           "primary: %hhu, secondary: %hhu, subordinate: %hhu\n",
722                           addr.bus, addr.device, addr.function, addr.bus, *busnum,
723                           (*busnum) + 1);
724
725                 // Disable master abort mode on the bridge
726                 pci_hdr1_brdg_ctrl_mabort_wrf(&bhdr, 0);
727
728                 // Clear all errors
729                 pci_hdr1_status_wr_raw(&bhdr, 0);
730
731                 // program bus numbers for this bridge
732                 pci_hdr1_bcfg_t bcfg = pci_hdr1_bcfg_rd(&bhdr);
733                 bcfg.pri_bus = addr.bus;
734                 bcfg.sec_bus = *busnum;
735                 bcfg.sub_bus = 0xff;
736                 pci_hdr1_bcfg_wr(&bhdr, bcfg);
737
738                 skb_add_fact("bridge(%s,addr(%u,%u,%u),%u,%u,%u,%u,%u, secondary(%hhu)).",
739                              (pcie ? "pcie" : "pci"), addr.bus, addr.device,
740                              addr.function, vendor, device_id, classcode.clss,
741                              classcode.subclss, classcode.prog_if, *busnum);
742
743                 //use the original hdr (pci_hdr0_t) here
744                 query_bars(hdr, addr, true);
745
746                 // assign bus numbers to secondary bus
747                 struct pci_address bridge_addr = {
748                     .bus = *busnum,
749                     .device = addr.device,
750                     .function = addr.function
751                 };
752                 assign_bus_numbers(bridge_addr, busnum, maxchild, child);
753                 // Restore the old state of pcie. The above call changes this
754                 // state according to the devices under this bridge
755                 if (pcie) {
756                     pcie_enable();
757                 } else {
758                     pcie_disable();
759                 }
760
761                 // Set this bridge's subordinate to the maximum of the underlying hierarchy
762                 pci_hdr1_bcfg_sub_bus_wrf(&bhdr, (*busnum) + 1);
763             }
764
765             //is this a normal PCI device?
766             if (hdr_type.fmt == pci_hdr0_nonbridge) {
767                 PCI_DEBUG("Found device (%u, %u, %u), vendor = %x, device = %x\n",
768                           addr.bus, addr.device, addr.function, vendor,
769                           device_id);
770
771                 pci_hdr0_t devhdr;
772                 pci_hdr0_initialize(&devhdr, addr);
773                 skb_add_fact("device(%s,addr(%u,%u,%u),%u,%u,%u, %u, %u, %d).",
774                              (pcie ? "pcie" : "pci"), addr.bus, addr.device,
775                              addr.function, vendor, device_id, classcode.clss,
776                              classcode.subclss, classcode.prog_if,
777                              pci_hdr0_int_pin_rd(&devhdr) - 1);
778
779                 // octopus start
780                 char* record = NULL;
781                 static char* device_fmt = "hw.pci.device. { "
782                                 "bus: %u, device: %u, function: %u, "
783                                 "vendor: %u, device_id: %u, class: %u, "
784                                 "subclass: %u, prog_if: %u }";
785
786                 errval_t err = oct_mset(SET_SEQUENTIAL, device_fmt, addr.bus,
787                                         addr.device, addr.function, vendor,
788                                         device_id, classcode.clss,
789                                         classcode.subclss, classcode.prog_if);
790
791                 assert(err_is_ok(err));
792                 free(record);
793                 // end octopus
794
795                 query_bars(devhdr, addr, false);
796
797                 // Process device capabilities if existing
798                 if (pci_hdr0_status_rd(&devhdr).caplist) {
799                     uint8_t cap_ptr = pci_hdr0_cap_ptr_rd(&devhdr);
800
801                     // Walk capabilities list
802                     while (cap_ptr != 0) {
803                         assert(cap_ptr % 4 == 0 && cap_ptr >= 0x40
804                                && cap_ptr < 0x100);
805                         uint32_t capword = pci_read_conf_header(&addr,
806                                                                 cap_ptr / 4);
807
808                         switch (capword & 0xff) {
809                             case 0x10:  // PCI Express
810                                 PCI_DEBUG("PCI Express device\n");
811                                 extended_caps = true;
812                                 break;
813
814                             default:
815                                 PCI_DEBUG("Unknown PCI device capability 0x%x at 0x%x\n",
816                                           capword & 0xff, cap_ptr);
817                                 break;
818                         }
819
820                         cap_ptr = (capword >> 8) & 0xff;
821                     }
822                 }
823
824                 // Process extended device capabilities if existing
825                 if (pcie && extended_caps && addr.bus < pcie_get_endbus()) {
826                     uint32_t *ad = (uint32_t *) pcie_confspace_access(addr);
827                     assert(ad != NULL);
828                     uint16_t cap_ptr = 0x100;
829
830                     while (cap_ptr != 0) {
831                         uint32_t capword = *(ad + (cap_ptr / 4));
832                         assert(cap_ptr % 4 == 0 && cap_ptr >= 0x100
833                                && cap_ptr < 0x1000);
834
835                         switch (capword & 0xffff) {  // Switch on capability ID
836                             case 0:
837                                 // No extended caps
838                                 break;
839
840                             case 16:
841                                 // SR-IOV capability
842                                 {
843                                 /*
844                                  * XXX: When using our e1000 driver with the
845                                  *      I350 network card (device id 0x152x),
846                                  *      the configuration fails when VF are
847                                  *      enabled: Legacy descriptors are ignored
848                                  *      when VF are enabled.
849                                  */
850                                 if (vendor == 0x8086 && (device_id & 0xFFF0) == 0x1520) {
851                                     debug_printf("skipping SR IOV initialization"
852                                                     "for e1000 card.\n");
853                                     break;
854                                 }
855                                 pci_sr_iov_cap_t sr_iov_cap;
856                                 pci_sr_iov_cap_initialize(&sr_iov_cap,
857                                      (mackerel_addr_t) (ad + (cap_ptr / 4)));
858
859                                 PCI_DEBUG("Found SR-IOV capability\n");
860
861                                 // Support version 1 for the moment
862                                 assert(pci_sr_iov_cap_hdr_ver_rdf(&sr_iov_cap) == 1);
863
864                                 // Support system page size of 4K at the moment
865                                 assert(pci_sr_iov_cap_sys_psize_rd(&sr_iov_cap)
866                                        == 1);
867
868 #if 0   // Dump cap contents
869                                 pci_sr_iov_cap_caps_pr(str, 256, &sr_iov_cap);
870                                 PCI_DEBUG("%s\n", str);
871                                 pci_sr_iov_cap_ctrl_pr(str, 256, &sr_iov_cap);
872                                 PCI_DEBUG("%s\n", str);
873                                 pci_sr_iov_cap_status_pr(str, 256, &sr_iov_cap);
874                                 PCI_DEBUG("%s\n", str);
875                                 pci_sr_iov_cap_initialvfs_pr(str, 256, &sr_iov_cap);
876                                 PCI_DEBUG("%s\n", str);
877                                 pci_sr_iov_cap_totalvfs_pr(str, 256, &sr_iov_cap);
878                                 PCI_DEBUG("%s\n", str);
879                                 pci_sr_iov_cap_numvfs_pr(str, 256, &sr_iov_cap);
880                                 PCI_DEBUG("%s\n", str);
881                                 pci_sr_iov_cap_fdl_pr(str, 256, &sr_iov_cap);
882                                 PCI_DEBUG("%s\n", str);
883                                 pci_sr_iov_cap_offset_pr(str, 256, &sr_iov_cap);
884                                 PCI_DEBUG("%s\n", str);
885                                 pci_sr_iov_cap_stride_pr(str, 256, &sr_iov_cap);
886                                 PCI_DEBUG("%s\n", str);
887                                 pci_sr_iov_cap_devid_pr(str, 256, &sr_iov_cap);
888                                 PCI_DEBUG("%s\n", str);
889                                 pci_sr_iov_cap_sup_psize_pr(str, 256, &sr_iov_cap);
890                                 PCI_DEBUG("%s\n", str);
891                                 pci_sr_iov_cap_sys_psize_pr(str, 256, &sr_iov_cap);
892                                 PCI_DEBUG("%s\n", str);
893 #endif
894
895                                 if (max_numvfs > 0) {
896                                     // Set maximum number of VFs
897                                     uint16_t totalvfs = pci_sr_iov_cap_totalvfs_rd( &sr_iov_cap);
898                                     uint16_t numvfs = MIN(totalvfs, max_numvfs);
899                                     //                  uint16_t numvfs = 8;
900                                     PCI_DEBUG("Maximum supported VFs: %u. Enabling: %u\n",
901                                               totalvfs, numvfs);
902                                     pci_sr_iov_cap_numvfs_wr(&sr_iov_cap, numvfs);
903
904                                     uint16_t offset = pci_sr_iov_cap_offset_rd(&sr_iov_cap);
905                                     uint16_t stride = pci_sr_iov_cap_stride_rd(&sr_iov_cap);
906                                     uint16_t vf_devid = pci_sr_iov_cap_devid_rd(&sr_iov_cap);
907
908                                     PCI_DEBUG("VF offset is 0x%x, stride is 0x%x, "
909                                               "device ID is 0x%x\n",
910                                               offset, stride, vf_devid);
911
912 #if 0
913                                     // Make sure we enable the PF
914                                     cmd = pci_hdr0_command_rd(&hdr);
915                                     cmd.mem_space = 1;
916                                     cmd.io_space = 1;
917                                     /* cmd.master = 1; */
918                                     pci_hdr0_command_wr(&hdr, cmd);
919 #endif
920
921                                     // Start VFs (including memory spaces)
922                                     pci_sr_iov_cap_ctrl_vf_mse_wrf(&sr_iov_cap, 1);
923                                     pci_sr_iov_cap_ctrl_vf_enable_wrf(&sr_iov_cap, 1);
924
925                                     // Spec says to wait here for at least 100ms
926                                     err = barrelfish_usleep(100000);
927                                     assert(err_is_ok(err));
928
929                                     // Add all VFs
930                                     for (int vfn = 0; vfn < numvfs; vfn++) {
931                                         uint8_t busnr = addr.bus + ((((addr.device << 3)
932                                                                  + addr.function)
933                                                                  + offset
934                                                                  + stride * vfn)
935                                                                  >> 8);
936                                         uint8_t devfn = (((addr.device << 3)
937                                                         + addr.function)
938                                                         + offset
939                                                         + stride * vfn)
940                                                         & 0xff;
941                                         struct pci_address vf_addr = {
942                                             .bus = busnr,
943                                             .device = devfn >> 3,
944                                             .function = devfn & 7,
945                                         };
946
947                                         PCI_DEBUG("Adding VF (%u, %u, %u)\n",
948                                                   vf_addr.bus, vf_addr.device,
949                                                   vf_addr.function);
950
951                                         skb_add_fact("device(%s,addr(%u,%u,%u),%u,%u,%u, %u, %u, %d).",
952                                                      (pcie ? "pcie" : "pci"),
953                                                      vf_addr.bus,
954                                                      vf_addr.device,
955                                                      vf_addr.function, vendor,
956                                                      vf_devid, classcode.clss,
957                                                      classcode.subclss,
958                                                      classcode.prog_if, 0);
959
960                                         // octopus start
961                                         device_fmt ="hw.pci.device. { "
962                                                      "bus: %u, device: %u, function: %u, "
963                                                      "vendor: %u, device_id: %u, class: %u, "
964                                                      "subclass: %u, prog_if: %u }";
965                                         err = oct_mset(SET_SEQUENTIAL,
966                                                        device_fmt,
967                                                        vf_addr.bus,
968                                                        vf_addr.device,
969                                                        vf_addr.function,
970                                                        vendor, vf_devid,
971                                                        classcode.clss,
972                                                        classcode.subclss,
973                                                        classcode.prog_if);
974
975                                         assert(err_is_ok(err));
976                                         // end octopus
977
978                                         // We probe the BARs several times. Strictly
979                                         // speaking, this is not necessary, as we
980                                         // can calculate all offsets, but we're
981                                         // lazy...
982                                         pci_hdr0_bar32_t bar, barorigaddr;
983                                         for (int i = 0; i < pci_sr_iov_cap_vf_bar_length; i++) {
984                                             union pci_hdr0_bar32_un orig_value;
985                                             orig_value.raw = pci_sr_iov_cap_vf_bar_rd(&sr_iov_cap, i);
986                                             barorigaddr = orig_value.val;
987
988                                             // probe BAR to see if it is implemented
989                                             pci_sr_iov_cap_vf_bar_wr(&sr_iov_cap, i, BAR_PROBE);
990
991                                             union pci_hdr0_bar32_un bar_value;
992                                             bar_value.raw = pci_sr_iov_cap_vf_bar_rd(&sr_iov_cap, i);
993                                             bar = (union pci_hdr0_bar32_un ) {
994                                                         .raw =bar_value.raw
995                                                    }.val;
996
997                                             //write original value back to the BAR
998                                             pci_sr_iov_cap_vf_bar_wr(&sr_iov_cap,
999                                                                  i, orig_value.raw);
1000
1001                                             /*
1002                                              * We need to check the entire register
1003                                              * here to make sure the bar is not
1004                                              * implemented as it could lie in the
1005                                              * high 64 bit range...
1006                                              */
1007                                             if (bar_value.raw == 0) {
1008                                                 // BAR not implemented
1009                                                 continue;
1010                                             }
1011
1012                                             // SR-IOV doesn't support IO space BARs
1013                                             assert(bar.space == 0);
1014                                             int type = -1;
1015                                             if (bar.tpe == pci_hdr0_bar_32bit) {
1016                                                 type = 32;
1017                                             }
1018                                             if (bar.tpe == pci_hdr0_bar_64bit) {
1019                                                 type = 64;
1020                                             }
1021
1022                                             if (bar.tpe == pci_hdr0_bar_64bit) {
1023                                                 //read the upper 32bits of the address
1024                                                 pci_hdr0_bar32_t bar_high, barorigaddr_high;
1025                                                 union pci_hdr0_bar32_un orig_value_high;
1026                                                 orig_value_high.raw = pci_sr_iov_cap_vf_bar_rd(&sr_iov_cap, i + 1);
1027                                                 barorigaddr_high = orig_value_high.val;
1028
1029                                                 // probe BAR to determine the mapping size
1030                                                 pci_sr_iov_cap_vf_bar_wr(&sr_iov_cap, i + 1, BAR_PROBE);
1031
1032                                                 bar_high = (union pci_hdr0_bar32_un ) {
1033                                                               .raw =pci_sr_iov_cap_vf_bar_rd(&sr_iov_cap,i + 1)
1034                                                             }.val;
1035
1036                                                 //write original value back to the BAR
1037                                                 pci_sr_iov_cap_vf_bar_wr(&sr_iov_cap,
1038                                                           i + 1, orig_value_high.raw);
1039
1040                                                 pciaddr_t base64 = bar_high.base;
1041                                                 base64 <<= 32;
1042                                                 base64 |= bar.base << 7;
1043
1044                                                 pciaddr_t origbase64 = barorigaddr_high.base;
1045                                                 origbase64 <<= 32;
1046                                                 origbase64 |= barorigaddr.base << 7;
1047
1048                                                 PCI_DEBUG("(%u,%u,%u): 64bit BAR %d at 0x%"
1049                                                           PRIxPCIADDR ", size %" PRIx64 ", %s\n",
1050                                                           vf_addr.bus, vf_addr.device,
1051                                                           vf_addr.function, i,
1052                                                           (origbase64 << 7) + bar_mapping_size64(base64) * vfn,
1053                                                           bar_mapping_size64(base64),
1054                                                           (bar.prefetch == 1 ? "prefetchable" : "nonprefetchable"));
1055
1056                                                 skb_add_fact("bar(addr(%u, %u, %u), %d, 16'%"
1057                                                              PRIxPCIADDR", ""16'%" PRIx64 ", vf, %s, %d).",
1058                                                              vf_addr.bus, vf_addr.device, vf_addr.function, i,
1059                                                              (origbase64 << 7) + bar_mapping_size64(base64) * vfn,
1060                                                              bar_mapping_size64(base64),
1061                                                              (bar.prefetch == 1 ? "prefetchable" : "nonprefetchable"),
1062                                                              type);
1063
1064                                                 i++;  //step one forward, because it is a 64bit BAR
1065                                             } else {
1066                                                 PCI_DEBUG("(%u,%u,%u): 32bit BAR %d at 0x%" PRIx32 ", size %x, %s\n",
1067                                                           vf_addr.bus, vf_addr.device, vf_addr.function, i,
1068                                                           (barorigaddr.base << 7) + bar_mapping_size(bar) * vfn,
1069                                                           bar_mapping_size(bar),
1070                                                           (bar.prefetch == 1 ? "prefetchable" : "nonprefetchable"));
1071
1072                                                 //32bit BAR
1073                                                 skb_add_fact("bar(addr(%u, %u, %u), %d, 16'%"PRIx32", 16'%"
1074                                                              PRIx32 ", vf, %s, %d).", vf_addr.bus,
1075                                                              vf_addr.device, vf_addr.function, i,
1076                                                              (uint32_t) ((barorigaddr.base << 7)
1077                                                                          + bar_mapping_size( bar) * vfn),
1078                                                              (uint32_t) bar_mapping_size(bar),
1079                                                              (bar.prefetch == 1 ? "prefetchable" : "nonprefetchable"),
1080                                                              type);
1081                                             }
1082                                         }
1083                                     }
1084                                 }
1085                             }
1086                                 break;
1087
1088                             default:
1089                                 PCI_DEBUG("Unknown extended PCI device capability 0x%x at 0x%x\n",
1090                                           capword & 0xffff, cap_ptr);
1091                                 break;
1092                         }
1093
1094                         cap_ptr = capword >> 20;
1095                     }
1096                 }
1097             }
1098
1099             // is this a multi-function device?
1100             if (addr.function == 0 && !hdr_type.multi) {
1101                 break;
1102             }
1103         }
1104     }
1105
1106     free(handle);
1107 }
1108
1109 #if 0
1110 static void get_bridges(struct pci_address myad)
1111 {
1112     struct pci_address addr = {.bus = myad.bus};
1113
1114     pcie_enable();
1115
1116     // First go through all bridges on this bus and disable them
1117     for (addr.device = 0; addr.device < PCI_NDEVICES; addr.device++) {
1118         for (addr.function = 0; addr.function < PCI_NFUNCTIONS; addr.function++) {
1119             pci_hdr1_t bhdr;
1120             pci_hdr1_initialize(&bhdr, addr);
1121
1122             uint16_t vendor = pci_hdr1_vendor_id_rd(&bhdr);
1123
1124             if (vendor == 0xffff) {
1125                 if (addr.function == 0) {
1126                     // this device doesn't exist at all
1127                     break;
1128                 } else {
1129                     // this function doesn't exist, but there may be others
1130                     continue;
1131                 }
1132             }
1133
1134             pci_hdr1_hdr_type_t hdr_type = pci_hdr1_hdr_type_rd(&bhdr);
1135             if (hdr_type.fmt == pci_hdr1_pci2pci) {
1136                 pci_hdr1_bcfg_t bcfg = pci_hdr1_bcfg_rd(&bhdr);
1137
1138                 PCI_DEBUG("Found bridge (%u,%u,%u), primary %u, secondary %u, subordinate %u\n",
1139                                 addr.bus, addr.device, addr.function,
1140                                 bcfg.pri_bus, bcfg.sec_bus, bcfg.sub_bus);
1141
1142                 struct pci_address bridge_addr= {
1143                     .bus = bcfg.sec_bus, .device = addr.device,
1144                     .function = addr.function
1145                 };
1146
1147                 get_bridges(bridge_addr);
1148             }
1149         }
1150     }
1151 }
1152 #endif
1153
1154 void pci_add_root(struct pci_address addr,
1155                   uint8_t maxchild,
1156                   char* handle)
1157 {
1158     uint8_t busnum = addr.bus;
1159     /* get_bridges(addr); */
1160     assign_bus_numbers(addr, &busnum, maxchild, handle);
1161     /* get_bridges(addr); */
1162 }
1163
1164 errval_t pci_setup_root_complex(void)
1165 {
1166     errval_t err;
1167     char* record = NULL;
1168     char** names = NULL;
1169     size_t len = 0;
1170
1171     // TODO: react to new rootbridges
1172     err = oct_get_names(&names, &len, "r'hw.pci.rootbridge.[0-9]+' "
1173                         "{ acpi_node: _, bus: _, device: _, function: _, maxbus: _ }");
1174     if (err_is_fail(err)) {
1175         DEBUG_ERR(err, "get names");
1176         goto out;
1177     }
1178
1179     for (size_t i = 0; i < len; i++) {
1180         err = oct_get(&record, names[i]);
1181         if (err_is_fail(err)) {
1182             goto out;
1183         }
1184
1185         PCI_DEBUG("found new root complex: %s\n", record);
1186
1187         char* acpi_node = NULL;  // freed in pci_add_root
1188         int64_t bus, device, function, maxbus;
1189         static char* format =
1190                         "_ { acpi_node: %s, bus: %d, device: %d, function: %d, maxbus: %d }";
1191         err = oct_read(record, format, &acpi_node, &bus, &device, &function,
1192                        &maxbus);
1193         if (err_is_fail(err)) {
1194             free(acpi_node);
1195             free(record);
1196             goto out;
1197         }
1198
1199         struct pci_address addr;
1200         addr.bus = (uint8_t) bus;
1201         addr.device = (uint8_t) device;
1202         addr.function = (uint8_t) function;
1203
1204         pcie_enable();
1205         pci_add_root(addr, maxbus, acpi_node);
1206         pcie_disable();
1207
1208         free(record);
1209     }
1210
1211     out: oct_free_names(names, len);
1212     return err;
1213 }
1214
1215 //query all BARs. That means, get the original address, the mapping size
1216 //and all attributes.
1217
1218 // XXX: asq: We are using this function to program also the _two_ BARs
1219 //           of a PCI-to-PCI bridge. They are at the same offset within the
1220 //           PCI header like for any PCI device. PCI HDR0 is misused
1221 //           here for the bridges.
1222
1223 static void query_bars(pci_hdr0_t devhdr,
1224                        struct pci_address addr,
1225                        bool pci2pci_bridge)
1226 {
1227     pci_hdr0_bar32_t bar, barorigaddr;
1228
1229     int maxbars = pci2pci_bridge ? 1 : pci_hdr0_bars_length;
1230     for (int i = 0; i <= maxbars; i++) {
1231         union pci_hdr0_bar32_un orig_value;
1232         orig_value.raw = pci_hdr0_bars_rd(&devhdr, i);
1233         barorigaddr = orig_value.val;
1234
1235         // probe BAR to determine the mapping size
1236         pci_hdr0_bars_wr(&devhdr, i, BAR_PROBE);
1237
1238         uint32_t bar_value = pci_hdr0_bars_rd(&devhdr, i);
1239
1240         bar = (union pci_hdr0_bar32_un ) { .raw = bar_value }.val;
1241
1242         //write original value back to the BAR
1243         pci_hdr0_bars_wr(&devhdr, i, orig_value.raw);
1244
1245         /*
1246          * Cannot just compare the base value, with addresses over 4G there
1247          * will be a problem. Thus we need to check if the entire register is
1248          * zero. If it is a 32bit register, then the address part will be filled.
1249          * If it is a 64bit register, the type will contain a nonzero value.
1250          * - 2014-05-02, RA
1251          */
1252         if (bar_value == 0) {
1253             // BAR not implemented
1254             continue;
1255         }
1256
1257         if (bar.space == 0) {  // memory mapped
1258             //bar(addr(bus, device, function), barnr, orig address, size, space,
1259             //         prefetchable?, 64bit?).
1260             //where space = mem | io, prefetchable= prefetchable | nonprefetchable,
1261             //64bit = 64bit | 32bit.
1262
1263             int type = -1;
1264             if (bar.tpe == pci_hdr0_bar_32bit) {
1265                 type = 32;
1266             }
1267             if (bar.tpe == pci_hdr0_bar_64bit) {
1268                 type = 64;
1269             }
1270
1271             if (bar.tpe == pci_hdr0_bar_64bit) {
1272                 //we must take the next BAR into account and do the same
1273                 //tests like in the 32bit case, but this time with the combined
1274                 //value from the current and the next BAR, since a 64bit BAR
1275                 //is constructed out of two consequtive 32bit BARs
1276
1277                 //read the upper 32bits of the address
1278                 uint32_t orig_value_high = pci_hdr0_bars_rd(&devhdr, i + 1);
1279
1280                 // probe BAR to determine the mapping size
1281                 pci_hdr0_bars_wr(&devhdr, i + 1, BAR_PROBE);
1282
1283                 // read the size information of the bar
1284                 uint32_t bar_value_high = pci_hdr0_bars_rd(&devhdr, i + 1);
1285
1286                 //write original value back to the BAR
1287                 pci_hdr0_bars_wr(&devhdr, i + 1, orig_value_high);
1288
1289                 pciaddr_t base64 = 0, origbase64 = 0;
1290                 base64 = bar_value_high;
1291                 base64 <<= 32;
1292                 base64 |= (uint32_t) (bar.base << 7);
1293
1294                 origbase64 = orig_value_high;
1295                 origbase64 <<= 32;
1296                 origbase64 |= (uint32_t) (barorigaddr.base << 7);
1297
1298                 PCI_DEBUG("(%u,%u,%u): 64bit BAR %d at 0x%" PRIxPCIADDR ", size %"
1299                           PRIx64 ", %s\n", addr.bus, addr.device, addr.function,
1300                           i, origbase64, bar_mapping_size64(base64),
1301                           (bar.prefetch == 1 ? "prefetchable" : "nonprefetchable"));
1302
1303               PCI_DEBUG("(%u,%u,%u): 64bit BAR %d at 0x%" PRIxPCIADDR ", size %" PRIx64 ", %s\n",
1304                         addr.bus, addr.device, addr.function,
1305                         i, origbase64 << 7, bar_mapping_size64(base64),
1306                         (bar.prefetch == 1 ? "prefetchable" : "nonprefetchable"));
1307
1308                 skb_add_fact("bar(addr(%u, %u, %u), %d, 16'%"PRIxPCIADDR", "
1309                              "16'%" PRIx64 ", mem, %s, %d).", addr.bus,
1310                              addr.device, addr.function, i, origbase64,
1311                              bar_mapping_size64(base64),
1312                              (bar.prefetch == 1 ? "prefetchable" : "nonprefetchable"),
1313                              type);
1314
1315                 i++;  //step one forward, because it is a 64bit BAR
1316             } else {
1317               PCI_DEBUG("(%u,%u,%u): 32bit BAR %d at 0x%" PRIx32 ", size %x, %s\n",
1318                         addr.bus, addr.device, addr.function,
1319                         i, barorigaddr.base << 7, bar_mapping_size(bar),
1320                         (bar.prefetch == 1 ? "prefetchable" : "nonprefetchable"));
1321
1322                 //32bit BAR
1323                 skb_add_fact("bar(addr(%u, %u, %u), %d, 16'%"PRIx32", 16'%" PRIx32
1324                              ", mem, %s, %d).", addr.bus, addr.device, addr.function,
1325                              i, (uint32_t) (barorigaddr.base << 7),
1326                              (uint32_t) bar_mapping_size(bar),
1327                              (bar.prefetch == 1 ? "prefetchable" : "nonprefetchable"),
1328                              type);
1329             }
1330         } else {
1331           PCI_DEBUG("(%u,%u,%u): IO BAR %d at 0x%x, size %x\n",
1332                     addr.bus, addr.device, addr.function,
1333                     i, barorigaddr.base << 7, bar_mapping_size(bar));
1334             //bar(addr(bus, device, function), barnr, orig address, size, space).
1335             //where space = mem | io
1336             skb_add_fact("bar(addr(%u, %u, %u), %d, 16'%"PRIx32", 16'%" PRIx32 ", io, "
1337                          "nonprefetchable, 32).", addr.bus, addr.device, addr.function, i,
1338                          (uint32_t) (barorigaddr.base << 7), (uint32_t) bar_mapping_size(bar));
1339         }
1340     }
1341 }
1342
1343 static void program_bridge_window(uint8_t bus,
1344                                   uint8_t dev,
1345                                   uint8_t fun,
1346                                   pciaddr_t base,
1347                                   pciaddr_t high,
1348                                   bool pcie,
1349                                   bool mem,
1350                                   bool pref)
1351 {
1352     struct pci_address addr;
1353     pci_hdr1_prefbl_t pref_reg;
1354     pci_hdr1_command_t cmd;
1355
1356     if (pcie) {
1357         pcie_enable();
1358     } else {
1359         pcie_disable();
1360     }
1361
1362     assert((base & 0x000fffff) == 0);
1363     assert((high & 0x000fffff) == 0x000fffff);
1364
1365     addr.bus = bus;
1366     addr.device = dev;
1367     addr.function = fun;
1368
1369     pci_hdr1_t bridgehdr;
1370     pci_hdr1_initialize(&bridgehdr, addr);
1371
1372     cmd = pci_hdr1_command_rd(&bridgehdr);
1373
1374     if (mem) {
1375         if (pref) {
1376             pci_hdr1_pref_base_upper_wr(&bridgehdr, base >> 32);
1377             pci_hdr1_pref_limit_upper_wr(&bridgehdr, high >> 32);
1378             /*
1379              * The least significant nibble of this register value (1h)
1380              * indicates that a 64 bit address decoder is supported and
1381              * that the Upper Base/Limit Registers are also used.
1382              */
1383             if ((base >> 32)) {
1384                 pref_reg.tpe = pci_hdr1_mem_64bit;
1385             } else {
1386                 pref_reg.tpe = pci_hdr1_mem_32bit;
1387             }
1388             pref_reg.val = base >> 20;
1389             pci_hdr1_pref_base_wr(&bridgehdr, pref_reg);
1390             if ((high >> 32)) {
1391                 pref_reg.tpe = pci_hdr1_mem_64bit;
1392             } else {
1393                 pref_reg.tpe = pci_hdr1_mem_32bit;
1394             }
1395             pref_reg.val = high >> 20;
1396             pci_hdr1_pref_limit_wr(&bridgehdr, pref_reg);
1397         } else {
1398             assert((base & 0xffffffff00000000) == 0);
1399             assert((high & 0xffffffff00000000) == 0);
1400             pci_hdr1_membl_t membl = {
1401                 .base = base >> 16,
1402                 .limit = high >> 16,
1403             };
1404             pci_hdr1_membl_wr(&bridgehdr, membl);
1405             /* pci_hdr1_mem_base_wr(&bridgehdr, base >> 16); */
1406             /* pci_hdr1_mem_limit_wr(&bridgehdr, high >> 16); */
1407         }
1408         // enable the memory decoder
1409         cmd.mem_space = 1;
1410     } else {
1411         // I/O
1412     }
1413
1414     cmd.int_dis = 0;
1415     cmd.master = 1;
1416     pci_hdr1_command_wr(&bridgehdr, cmd);
1417 }
1418
1419 static void program_device_bar(uint8_t bus,
1420                                uint8_t dev,
1421                                uint8_t fun,
1422                                int bar,
1423                                pciaddr_t base,
1424                                pcisize_t size,
1425                                int bits,
1426                                bool memspace,
1427                                bool pcie)
1428 {
1429     struct pci_address addr;
1430     addr.bus = bus;
1431     addr.device = dev;
1432     addr.function = fun;
1433
1434     if (pcie) {
1435         pcie_enable();
1436     } else {
1437         pcie_disable();
1438     }
1439
1440     pci_hdr0_t devhdr;
1441     pci_hdr0_initialize(&devhdr, addr);
1442
1443     //disable the address decoder for programming the BARs
1444     pci_hdr0_command_t cmd = pci_hdr0_command_rd(&devhdr);
1445     if (memspace) {
1446         cmd.mem_space = 0;
1447     } else {
1448         cmd.io_space = 0;
1449     }
1450     //disbale interrupts here. enable them as soon as a driver requests
1451     //interrupts
1452     cmd.int_dis = 1;
1453     pci_hdr0_command_wr(&devhdr, cmd);
1454
1455     if (bits == 64) {
1456         pci_hdr0_bars_wr(&devhdr, bar, base & 0xffffffff);
1457         pci_hdr0_bars_wr(&devhdr, bar + 1, base >> 32);
1458     } else {  // 32-bit
1459         assert(base + size <= 0xffffffff);  // 32-bit BAR
1460         pci_hdr0_bars_wr(&devhdr, bar, base);
1461     }
1462
1463     //re-enable the decoder for the BARs
1464     if (memspace) {
1465         cmd.mem_space = 1;
1466     } else {
1467         cmd.io_space = 1;
1468     }
1469     pci_hdr0_command_wr(&devhdr, cmd);
1470 }
1471
1472 static void enable_busmaster(uint8_t bus,
1473                              uint8_t dev,
1474                              uint8_t fun,
1475                              bool pcie)
1476 {
1477     struct pci_address addr;
1478     addr.bus = bus;
1479     addr.device = dev;
1480     addr.function = fun;
1481
1482     if (pcie) {
1483         pcie_enable();
1484     } else {
1485         pcie_disable();
1486     }
1487
1488     pci_hdr0_t devhdr;
1489     pci_hdr0_initialize(&devhdr, addr);
1490
1491     //enable bus master
1492     pci_hdr0_command_t cmd = pci_hdr0_command_rd(&devhdr);
1493     cmd.master = 1;
1494     pci_hdr0_command_wr(&devhdr, cmd);
1495 }
1496
1497 void pci_program_bridges(void)
1498 {
1499     char element_type[7];  // "device" | "bridge"
1500     char bar_secondary[16];  //[0-6] | secondary(<0-255>)
1501     char space[4];  // "mem" | "io"
1502     char prefetch[16];  // "prefetchable" | "nonprefetchable"
1503     char pcie_pci[5];  // "pcie" | "pci"
1504     int bar;  // the value of bar_secondary after parsing secondary(<nr>) to <nr>
1505     uint8_t bus, dev, fun;
1506     pciaddr_t base, high;
1507     pcisize_t size;
1508     int bits;
1509     bool mem, pcie, pref;
1510     char *output = NULL;
1511     int output_length = 0;
1512     int error_code = 0;
1513
1514     /*
1515      output = NULL;
1516      output_length = 0;
1517      skb_execute("listing.");
1518      output = skb_get_output();
1519      assert(output != NULL);
1520      output_length = strlen(output);
1521      PCI_DEBUG("pci_program_bridges: output = %s\n", output);
1522      PCI_DEBUG("pci_program_bridges: output length = %d\n", output_length);
1523
1524      error_code = skb_read_error_code();
1525      if (error_code != 0) {
1526      printf("pci.c: pci_program_bridges(): SKB returnd error code %d\n",
1527      error_code);
1528
1529      const char *errout = skb_get_error_output();
1530      printf("\nSKB error returned: %s\n", errout);
1531      printf("\nSKB output: %s\n", output);
1532      // XXX: no device can be used...
1533      return;
1534      }
1535      */
1536
1537     output = NULL;
1538     output_length = 0;
1539     char bridge_program[512];
1540     snprintf(bridge_program, 512, "[%s], bridge_programming(P, Nr),"
1541              "flatten(P, F),replace_current_BAR_values(F),"
1542              "write(nrelements(Nr)),writeln(P).",
1543              skb_bridge_program);
1544     skb_execute(bridge_program);
1545     output = skb_get_output();
1546     assert(output != NULL);
1547     output_length = strlen(output);
1548     PCI_DEBUG("pci_program_bridges: output = %s\n", output);
1549     PCI_DEBUG("pci_program_bridges: output length = %d\n", output_length);
1550
1551     error_code = skb_read_error_code();
1552     if (error_code != 0) {
1553         printf("pci.c: pci_program_bridges(): SKB returned error code %d\n",
1554                error_code);
1555
1556         const char *errout = skb_get_error_output();
1557         printf("SKB error returned: %s\n", errout);
1558         printf("SKB output: %s\n", output);
1559         // XXX: no device can be used...
1560         printf("WARNING: CONTINUING, HOWEVER PCI DEVICES WILL BE UNUSABLE\n");
1561         // except IO-space devices which aren't yet affected by bridge programming
1562         return;
1563     }
1564
1565     /*
1566      ********************************************************************************
1567      //for the ASPLOS11 paper:
1568      skb_execute("[bridge_page].");
1569      while (skb_read_error_code() == SKB_PROCESSING) messages_wait_and_handle_next();
1570      char *output = skb_get_output();
1571      assert(output != NULL);
1572      int output_length = strlen(output);
1573      PCI_DEBUG("pci_program_bridges: output = %s\n", output);
1574      PCI_DEBUG("pci_program_bridges: output length = %d\n", output_length);
1575
1576      int error_code = skb_read_error_code();
1577      if (error_code != 0) {
1578      printf("pci.c: pci_program_bridges() <2>: SKB returnd error code %d\n",
1579      error_code);
1580
1581      const char *errout = skb_get_error_output();
1582      printf("\nSKB error returned <2>: %s\n", errout);
1583      printf("\nSKB output <2>: %s\n", output);
1584      // XXX: no device can be used...
1585      return;
1586      }
1587      uint64_t start =rdtsc();
1588      //    uint64_t start =rdtscp();
1589      skb_execute("bridge_programming(P, Nr),write(nrelements(Nr)),writeln(P).");
1590      uint64_t end =rdtsc();
1591      //    uint64_t end =rdtscp();
1592      assert(end >= start);
1593
1594      printf("\n\nTicks: %lu\n\n", end - start);
1595      while (skb_read_error_code() == SKB_PROCESSING) messages_wait_and_handle_next();
1596      output = skb_get_output();
1597      assert(output != NULL);
1598      output_length = strlen(output);
1599      printf("pci_program_bridges: output = %s\n", output);
1600      PCI_DEBUG("pci_program_bridges: output length = %d\n", output_length);
1601
1602      error_code = skb_read_error_code();
1603      if (error_code != 0) {
1604      printf("pci.c: pci_program_bridges() <3>: SKB returnd error code %d\n",
1605      error_code);
1606
1607      const char *errout = skb_get_error_output();
1608      printf("\nSKB error returned <3>: %s\n", errout);
1609      printf("\nSKB output <3>: %s\n", output);
1610      // XXX: no device can be used...
1611      return;
1612      }
1613      ********************************************************************************
1614      */
1615
1616     //get the number of buselements from the output
1617     int nr_elements;
1618     int nr_conversions;
1619     nr_conversions = sscanf(output, "nrelements(%d)", &nr_elements);
1620     if (nr_conversions != 1) {
1621         printf("pci.c: No valid pci plan returned by the SKB\n.");
1622         //XXX: no device can be used
1623         return;
1624     }
1625
1626     //keep a pointer to the current location within the output
1627     char *conv_ptr = output;
1628
1629     //iterate over all buselements
1630     for (int i = 0; i < nr_elements; i++) {
1631         // search the beginning of the next buselement
1632         while ((conv_ptr < output + output_length) && (strncmp(
1633                         conv_ptr, "buselement", strlen("buselement"))
1634                                                        != 0)) {
1635             conv_ptr++;
1636         }
1637         //convert the string to single elements and numbers
1638         nr_conversions = sscanf(conv_ptr, "buselement(%[a-z], addr(%hhu, %hhu, %hhu), "
1639                                 "%[a-z0-9()], %"PRIuPCIADDR", %"PRIuPCIADDR", "
1640                                 "%"PRIuPCISIZE", %[a-z], %[a-z], %[a-z], %d",
1641                                 element_type, &bus, &dev, &fun, bar_secondary,
1642                                 &base, &high, &size, space, prefetch, pcie_pci,
1643                                 &bits);
1644         conv_ptr++;
1645         if (nr_conversions != 12) {
1646             printf("Could not parse output for device or bridge number %d\n"
1647                    "nr conversions: %d\n",
1648                    i, nr_conversions);
1649             continue;
1650         }
1651         if (strncmp(space, "mem", strlen("mem")) == 0) {
1652             mem = true;
1653         } else {
1654             mem = false;
1655         }
1656         if (strncmp(pcie_pci, "pcie", strlen("pcie")) == 0) {
1657             pcie = true;
1658         } else {
1659             pcie = false;
1660         }
1661         if (strncmp(prefetch, "prefetchable", strlen("prefetchable")) == 0) {
1662             pref = true;
1663         } else {
1664             pref = false;
1665         }
1666
1667         // Skip virtual functions
1668         if (strncmp(space, "vf", strlen("vf")) == 0) {
1669             /* PCI_DEBUG("Skipping VF addr(%hhu, %hhu, %hhu)\n", */
1670             /*      bus, dev, fun); */
1671             continue;
1672         }
1673
1674         if (strncmp(element_type, "device", strlen("device")) == 0) {
1675             nr_conversions = sscanf(bar_secondary, "%d", &bar);
1676             if (nr_conversions != 1) {
1677                 printf("Could not determine BAR number while programming BAR\n");
1678                 continue;
1679             }
1680             PCI_DEBUG("programming %s addr(%hhu, %hhu, %hhu), BAR %d, with base = "
1681                       "%"PRIxPCIADDR", high = %"PRIxPCIADDR", size = %"PRIxPCISIZE
1682                       " in" "space = %s, prefetch = %s, %s...\n",
1683                       element_type, bus, dev, fun, bar, base, high, size, space,
1684                       prefetch, pcie ? "PCIe" : "PCI");
1685             program_device_bar(bus, dev, fun, bar, base, size, bits, mem, pcie);
1686
1687         } else {
1688             PCI_DEBUG("programming %s addr(%hhu, %hhu, %hhu), with base = "
1689                       "%"PRIxPCIADDR", high = %"PRIxPCIADDR", size = %"PRIxPCISIZE
1690                       " in space = %s, prefetch = %s...\n",
1691                       element_type, bus, dev, fun, base, high, size, space,
1692                       prefetch);
1693             //a bridge expects the high address excluding the last byte which
1694             //is the base for the next bridge => decrement by one
1695             high--;
1696             program_bridge_window(bus, dev, fun, base, high, pcie, mem, pref);
1697         }
1698     }
1699 }
1700
1701 static uint32_t setup_interrupt(uint32_t bus,
1702                                 uint32_t dev,
1703                                 uint32_t fun)
1704 {
1705     char str[256], ldev[128];
1706
1707     snprintf(str, 256, "[\"irq_routing.pl\"], assigndeviceirq(addr(%"PRIu32
1708                        ", %"PRIu32", %"PRIu32")).",
1709                        bus, dev, fun);
1710     char *output, *error_out;
1711     int32_t int_err;
1712     errval_t err = skb_evaluate(str, &output, &error_out, &int_err);
1713     assert(output != NULL);
1714     assert(err_is_ok(err));
1715
1716     uint8_t irq;
1717     sscanf(output, "%s %hhu", ldev, &irq);
1718
1719     // It's a GSI
1720     if (strcmp(ldev, "fixedGsi") == 0) {
1721         printf("Got GSI %u\n", irq);
1722         return irq;
1723     }
1724
1725     struct acpi_rpc_client* cl = get_acpi_rpc_client();
1726     errval_t error_code;
1727     err = cl->vtbl.set_device_irq(cl, ldev, irq, &error_code);
1728     assert(err_is_ok(err));
1729     if (err_is_fail(error_code)) {
1730         //DEBUG_ERR(error_code, "set device irq failed.");
1731         return 0;
1732     }
1733
1734     return irq;
1735 }