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