xref: /aosp_15_r20/external/crosvm/devices/src/pci/mod.rs (revision bb4ee6a4ae7042d18b07a98463b9c8b875e44b39)
1 // Copyright 2018 The ChromiumOS Authors
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 //! Implements pci devices and busses.
6 
7 mod acpi;
8 #[cfg(any(target_os = "android", target_os = "linux"))]
9 mod coiommu;
10 mod msi;
11 mod msix;
12 mod pci_address;
13 mod pci_configuration;
14 mod pci_device;
15 #[cfg(feature = "pci-hotplug")]
16 mod pci_hotplug;
17 mod pci_root;
18 #[cfg(any(target_os = "android", target_os = "linux"))]
19 mod pcie;
20 pub mod pm;
21 mod pvpanic;
22 mod stub;
23 #[cfg(any(target_os = "android", target_os = "linux"))]
24 mod vfio_pci;
25 
26 use libc::EINVAL;
27 use serde::Deserialize;
28 use serde::Serialize;
29 
30 pub use self::acpi::GpeScope;
31 #[cfg(any(target_os = "android", target_os = "linux"))]
32 pub use self::coiommu::CoIommuDev;
33 #[cfg(any(target_os = "android", target_os = "linux"))]
34 pub use self::coiommu::CoIommuParameters;
35 #[cfg(any(target_os = "android", target_os = "linux"))]
36 pub use self::coiommu::CoIommuUnpinPolicy;
37 pub use self::msi::MsiConfig;
38 pub use self::msix::MsixCap;
39 pub use self::msix::MsixConfig;
40 pub use self::msix::MsixStatus;
41 pub use self::pci_address::Error as PciAddressError;
42 pub use self::pci_address::PciAddress;
43 pub use self::pci_configuration::PciBarConfiguration;
44 pub use self::pci_configuration::PciBarIndex;
45 pub use self::pci_configuration::PciBarPrefetchable;
46 pub use self::pci_configuration::PciBarRegionType;
47 pub use self::pci_configuration::PciBaseSystemPeripheralSubclass;
48 pub use self::pci_configuration::PciCapability;
49 pub use self::pci_configuration::PciCapabilityID;
50 pub use self::pci_configuration::PciClassCode;
51 pub use self::pci_configuration::PciConfiguration;
52 pub use self::pci_configuration::PciDisplaySubclass;
53 pub use self::pci_configuration::PciHeaderType;
54 pub use self::pci_configuration::PciInputDeviceSubclass;
55 pub use self::pci_configuration::PciMassStorageSubclass;
56 pub use self::pci_configuration::PciMultimediaSubclass;
57 pub use self::pci_configuration::PciNetworkControllerSubclass;
58 pub use self::pci_configuration::PciProgrammingInterface;
59 pub use self::pci_configuration::PciSerialBusSubClass;
60 pub use self::pci_configuration::PciSimpleCommunicationControllerSubclass;
61 pub use self::pci_configuration::PciSubclass;
62 pub use self::pci_configuration::PciWirelessControllerSubclass;
63 pub use self::pci_device::BarRange;
64 pub use self::pci_device::Error as PciDeviceError;
65 pub use self::pci_device::PciBus;
66 pub use self::pci_device::PciDevice;
67 pub use self::pci_device::PreferredIrq;
68 #[cfg(feature = "pci-hotplug")]
69 pub use self::pci_hotplug::HotPluggable;
70 #[cfg(feature = "pci-hotplug")]
71 pub use self::pci_hotplug::IntxParameter;
72 #[cfg(feature = "pci-hotplug")]
73 pub use self::pci_hotplug::NetResourceCarrier;
74 #[cfg(feature = "pci-hotplug")]
75 pub use self::pci_hotplug::ResourceCarrier;
76 pub use self::pci_root::PciConfigIo;
77 pub use self::pci_root::PciConfigMmio;
78 pub use self::pci_root::PciMmioMapper;
79 pub use self::pci_root::PciRoot;
80 pub use self::pci_root::PciRootCommand;
81 pub use self::pci_root::PciVirtualConfigMmio;
82 #[cfg(any(target_os = "android", target_os = "linux"))]
83 pub use self::pcie::PciBridge;
84 #[cfg(any(target_os = "android", target_os = "linux"))]
85 pub use self::pcie::PcieDownstreamPort;
86 #[cfg(any(target_os = "android", target_os = "linux"))]
87 pub use self::pcie::PcieHostPort;
88 #[cfg(any(target_os = "android", target_os = "linux"))]
89 pub use self::pcie::PcieRootPort;
90 #[cfg(any(target_os = "android", target_os = "linux"))]
91 pub use self::pcie::PcieUpstreamPort;
92 pub use self::pvpanic::PvPanicCode;
93 pub use self::pvpanic::PvPanicPciDevice;
94 pub use self::stub::StubPciDevice;
95 pub use self::stub::StubPciParameters;
96 #[cfg(any(target_os = "android", target_os = "linux"))]
97 pub use self::vfio_pci::VfioPciDevice;
98 
99 /// PCI has four interrupt pins A->D.
100 #[derive(Copy, Clone, Ord, PartialOrd, PartialEq, Eq, Serialize, Deserialize)]
101 pub enum PciInterruptPin {
102     IntA,
103     IntB,
104     IntC,
105     IntD,
106 }
107 
108 impl PciInterruptPin {
to_mask(self) -> u32109     pub fn to_mask(self) -> u32 {
110         self as u32
111     }
112 }
113 
114 // VCFG
115 pub const PCI_VCFG_PM: usize = 0x0;
116 pub const PCI_VCFG_DSM: usize = 0x1;
117 pub const PCI_VCFG_NOTY: usize = 0x2;
118 
119 pub const PCI_VENDOR_ID_INTEL: u16 = 0x8086;
120 pub const PCI_VENDOR_ID_REDHAT: u16 = 0x1b36;
121 
122 #[repr(u16)]
123 #[derive(Debug, Copy, Clone, PartialEq, Eq, Serialize, Deserialize)]
124 pub enum CrosvmDeviceId {
125     Pit = 1,
126     Pic = 2,
127     Ioapic = 3,
128     Serial = 4,
129     Cmos = 5,
130     I8042 = 6,
131     Pl030 = 7,
132     ACPIPMResource = 8,
133     GoldfishBattery = 9,
134     DebugConsole = 10,
135     ProxyDevice = 11,
136     VfioPlatformDevice = 12,
137     DirectGsi = 13,
138     DirectIo = 14,
139     DirectMmio = 15,
140     UserspaceIrqChip = 16,
141     VmWatchdog = 17,
142     Pflash = 18,
143     VirtioMmio = 19,
144     AcAdapter = 20,
145     VirtualPmc = 21,
146     VirtCpufreq = 22,
147     FwCfg = 23,
148 }
149 
150 impl TryFrom<u16> for CrosvmDeviceId {
151     type Error = base::Error;
152 
try_from(value: u16) -> Result<Self, Self::Error>153     fn try_from(value: u16) -> Result<Self, Self::Error> {
154         match value {
155             1 => Ok(CrosvmDeviceId::Pit),
156             2 => Ok(CrosvmDeviceId::Pic),
157             3 => Ok(CrosvmDeviceId::Ioapic),
158             4 => Ok(CrosvmDeviceId::Serial),
159             5 => Ok(CrosvmDeviceId::Cmos),
160             6 => Ok(CrosvmDeviceId::I8042),
161             7 => Ok(CrosvmDeviceId::Pl030),
162             8 => Ok(CrosvmDeviceId::ACPIPMResource),
163             9 => Ok(CrosvmDeviceId::GoldfishBattery),
164             10 => Ok(CrosvmDeviceId::DebugConsole),
165             11 => Ok(CrosvmDeviceId::ProxyDevice),
166             12 => Ok(CrosvmDeviceId::VfioPlatformDevice),
167             13 => Ok(CrosvmDeviceId::DirectGsi),
168             14 => Ok(CrosvmDeviceId::DirectMmio),
169             15 => Ok(CrosvmDeviceId::DirectIo),
170             16 => Ok(CrosvmDeviceId::UserspaceIrqChip),
171             17 => Ok(CrosvmDeviceId::VmWatchdog),
172             18 => Ok(CrosvmDeviceId::Pflash),
173             19 => Ok(CrosvmDeviceId::VirtioMmio),
174             20 => Ok(CrosvmDeviceId::AcAdapter),
175             21 => Ok(CrosvmDeviceId::VirtualPmc),
176             _ => Err(base::Error::new(EINVAL)),
177         }
178     }
179 }
180 
181 /// A wrapper structure for pci device and vendor id.
182 #[derive(Debug, Copy, Clone, PartialEq, Eq, Serialize, Deserialize)]
183 pub struct PciId {
184     vendor_id: u16,
185     device_id: u16,
186 }
187 
188 impl PciId {
new(vendor_id: u16, device_id: u16) -> Self189     pub fn new(vendor_id: u16, device_id: u16) -> Self {
190         Self {
191             vendor_id,
192             device_id,
193         }
194     }
195 }
196 
197 impl From<PciId> for u32 {
from(pci_id: PciId) -> Self198     fn from(pci_id: PciId) -> Self {
199         // vendor ID is the lower 16 bits and device id is the upper 16 bits
200         pci_id.vendor_id as u32 | (pci_id.device_id as u32) << 16
201     }
202 }
203 
204 impl From<u32> for PciId {
from(value: u32) -> Self205     fn from(value: u32) -> Self {
206         let vendor_id = (value & 0xFFFF) as u16;
207         let device_id = (value >> 16) as u16;
208         Self::new(vendor_id, device_id)
209     }
210 }
211