mycelium_kernel/arch/x86_64/
pci.rs

1// TODO(eliza): write a `RwLock`...
2use crate::drivers::pci::*;
3
4pub fn init_pci() {
5    let mut bad = 0;
6    let mut devices = DeviceRegistry::default();
7
8    let _span = tracing::info_span!("enumerating PCI devices").entered();
9    for (addr, config) in config::enumerate_all() {
10        let class = match config.header.classes() {
11            Ok(class) => class,
12            Err(error) => {
13                tracing::error!(
14                    target: "pci",
15                    error = %error,
16                    "[{addr}] bad class"
17                );
18                bad += 1;
19                continue;
20            }
21        };
22
23        let _ = tracing::info_span!(
24            target: "pci",
25            "pci",
26            class = %class.class().name(),
27            subclass = %class.subclass().name(),
28            "[{addr}]"
29        )
30        .entered();
31
32        let id = config.header.id();
33        match id {
34            device::Id::Known(ids) => {
35                tracing::info!(
36                    target: "  pci",
37                    vendor = %ids.vendor().name(),
38                    device = %ids.name(),
39                );
40            }
41            device::Id::Unknown(ids) => {
42                tracing::warn!(
43                    target: "  pci",
44                    vendor = ids.vendor_id,
45                    device = ids.device_id,
46                    "unrecognized vendor or device ID"
47                );
48            }
49        };
50
51        assert!(
52            devices.insert(addr, class, id),
53            "PCI device inserted twice! addr={addr:?}, id={id:?}, class={class:?}",
54        );
55    }
56
57    tracing::info!("found {} PCI devices ({bad} bad)", devices.len());
58
59    DEVICES.init(devices);
60}