mirror of
https://github.com/cloud-hypervisor/cloud-hypervisor.git
synced 2025-01-22 04:25:21 +00:00
devices, vmm: Move GED device to MMIO region
Move GED device reporting of required device type to scan into an MMIO region rather than an I/O port. Signed-off-by: Rob Bradford <robert.bradford@intel.com>
This commit is contained in:
parent
03108fb88b
commit
5e3c62dc6a
@ -5,6 +5,7 @@
|
|||||||
|
|
||||||
use std::sync::Arc;
|
use std::sync::Arc;
|
||||||
use vm_device::interrupt::InterruptSourceGroup;
|
use vm_device::interrupt::InterruptSourceGroup;
|
||||||
|
use vm_memory::GuestAddress;
|
||||||
use vmm_sys_util::eventfd::EventFd;
|
use vmm_sys_util::eventfd::EventFd;
|
||||||
use BusDevice;
|
use BusDevice;
|
||||||
use HotPlugNotificationFlags;
|
use HotPlugNotificationFlags;
|
||||||
@ -60,14 +61,22 @@ pub struct AcpiGEDDevice {
|
|||||||
interrupt: Arc<Box<dyn InterruptSourceGroup>>,
|
interrupt: Arc<Box<dyn InterruptSourceGroup>>,
|
||||||
notification_type: HotPlugNotificationFlags,
|
notification_type: HotPlugNotificationFlags,
|
||||||
ged_irq: u32,
|
ged_irq: u32,
|
||||||
|
device_base: GuestAddress,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl AcpiGEDDevice {
|
impl AcpiGEDDevice {
|
||||||
pub fn new(interrupt: Arc<Box<dyn InterruptSourceGroup>>, ged_irq: u32) -> AcpiGEDDevice {
|
pub const DEVICE_SIZE: u64 = 1;
|
||||||
|
|
||||||
|
pub fn new(
|
||||||
|
interrupt: Arc<Box<dyn InterruptSourceGroup>>,
|
||||||
|
ged_irq: u32,
|
||||||
|
device_base: GuestAddress,
|
||||||
|
) -> AcpiGEDDevice {
|
||||||
AcpiGEDDevice {
|
AcpiGEDDevice {
|
||||||
interrupt,
|
interrupt,
|
||||||
notification_type: HotPlugNotificationFlags::NO_DEVICES_CHANGED,
|
notification_type: HotPlugNotificationFlags::NO_DEVICES_CHANGED,
|
||||||
ged_irq,
|
ged_irq,
|
||||||
|
device_base,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -82,9 +91,13 @@ impl AcpiGEDDevice {
|
|||||||
pub fn irq(&self) -> u32 {
|
pub fn irq(&self) -> u32 {
|
||||||
self.ged_irq
|
self.ged_irq
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn device_base(&self) -> GuestAddress {
|
||||||
|
self.device_base
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// I/O port reports what type of notification was made
|
// MMIO region reports what type of notification was made
|
||||||
impl BusDevice for AcpiGEDDevice {
|
impl BusDevice for AcpiGEDDevice {
|
||||||
// Spec has all fields as zero
|
// Spec has all fields as zero
|
||||||
fn read(&mut self, _base: u64, _offset: u64, data: &mut [u8]) {
|
fn read(&mut self, _base: u64, _offset: u64, data: &mut [u8]) {
|
||||||
|
@ -192,6 +192,9 @@ pub enum DeviceManagerError {
|
|||||||
|
|
||||||
/// Failed creating IOAPIC.
|
/// Failed creating IOAPIC.
|
||||||
CreateIoapic(ioapic::Error),
|
CreateIoapic(ioapic::Error),
|
||||||
|
|
||||||
|
/// Failed to allocate MMIO area
|
||||||
|
AllocateMMIO,
|
||||||
}
|
}
|
||||||
pub type DeviceManagerResult<T> = result::Result<T, DeviceManagerError>;
|
pub type DeviceManagerResult<T> = result::Result<T, DeviceManagerError>;
|
||||||
|
|
||||||
@ -749,22 +752,28 @@ impl DeviceManager {
|
|||||||
.create_group(PIN_IRQ, ged_irq as InterruptIndex, 1 as InterruptIndex)
|
.create_group(PIN_IRQ, ged_irq as InterruptIndex, 1 as InterruptIndex)
|
||||||
.map_err(DeviceManagerError::CreateInterruptGroup)?;
|
.map_err(DeviceManagerError::CreateInterruptGroup)?;
|
||||||
|
|
||||||
let ged_device = Arc::new(Mutex::new(devices::AcpiGEDDevice::new(
|
let ged_base = address_manager
|
||||||
interrupt_group,
|
|
||||||
ged_irq,
|
|
||||||
)));
|
|
||||||
|
|
||||||
address_manager
|
|
||||||
.allocator
|
.allocator
|
||||||
.lock()
|
.lock()
|
||||||
.unwrap()
|
.unwrap()
|
||||||
.allocate_io_addresses(Some(GuestAddress(0xb000)), 0x1, None)
|
.allocate_mmio_addresses(None, devices::AcpiGEDDevice::DEVICE_SIZE, None)
|
||||||
.ok_or(DeviceManagerError::AllocateIOPort)?;
|
.ok_or(DeviceManagerError::AllocateMMIO)?;
|
||||||
|
|
||||||
|
let ged_device = Arc::new(Mutex::new(devices::AcpiGEDDevice::new(
|
||||||
|
interrupt_group,
|
||||||
|
ged_irq,
|
||||||
|
ged_base,
|
||||||
|
)));
|
||||||
|
|
||||||
address_manager
|
address_manager
|
||||||
.io_bus
|
.mmio_bus
|
||||||
.insert(ged_device.clone(), 0xb000, 0x1)
|
.insert(
|
||||||
|
ged_device.clone(),
|
||||||
|
ged_base.0,
|
||||||
|
devices::AcpiGEDDevice::DEVICE_SIZE,
|
||||||
|
)
|
||||||
.map_err(DeviceManagerError::BusError)?;
|
.map_err(DeviceManagerError::BusError)?;
|
||||||
|
|
||||||
Ok(Some(ged_device))
|
Ok(Some(ged_device))
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1651,7 +1660,7 @@ impl Drop for DeviceManager {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "acpi")]
|
#[cfg(feature = "acpi")]
|
||||||
fn create_ged_device(ged_irq: u32) -> Vec<u8> {
|
fn create_ged_device(ged_base: u64, ged_irq: u32) -> Vec<u8> {
|
||||||
aml::Device::new(
|
aml::Device::new(
|
||||||
"_SB_.GED_".into(),
|
"_SB_.GED_".into(),
|
||||||
vec![
|
vec![
|
||||||
@ -1663,7 +1672,12 @@ fn create_ged_device(ged_irq: u32) -> Vec<u8> {
|
|||||||
true, true, false, false, ged_irq,
|
true, true, false, false, ged_irq,
|
||||||
)]),
|
)]),
|
||||||
),
|
),
|
||||||
&aml::OpRegion::new("GDST".into(), aml::OpRegionSpace::SystemIO, 0xb000, 0x1),
|
&aml::OpRegion::new(
|
||||||
|
"GDST".into(),
|
||||||
|
aml::OpRegionSpace::SystemMemory,
|
||||||
|
ged_base as usize,
|
||||||
|
devices::AcpiGEDDevice::DEVICE_SIZE as usize,
|
||||||
|
),
|
||||||
&aml::Field::new(
|
&aml::Field::new(
|
||||||
"GDST".into(),
|
"GDST".into(),
|
||||||
aml::FieldAccessType::Byte,
|
aml::FieldAccessType::Byte,
|
||||||
@ -1770,14 +1784,21 @@ impl Aml for DeviceManager {
|
|||||||
let s5_sleep_data =
|
let s5_sleep_data =
|
||||||
aml::Name::new("_S5_".into(), &aml::Package::new(vec![&5u8])).to_aml_bytes();
|
aml::Name::new("_S5_".into(), &aml::Package::new(vec![&5u8])).to_aml_bytes();
|
||||||
|
|
||||||
let ged_data = create_ged_device(
|
let ged_irq = self
|
||||||
self.ged_notification_device
|
.ged_notification_device
|
||||||
.as_ref()
|
.as_ref()
|
||||||
.unwrap()
|
.unwrap()
|
||||||
.lock()
|
.lock()
|
||||||
.unwrap()
|
.unwrap()
|
||||||
.irq(),
|
.irq();
|
||||||
);
|
let ged_base = self
|
||||||
|
.ged_notification_device
|
||||||
|
.as_ref()
|
||||||
|
.unwrap()
|
||||||
|
.lock()
|
||||||
|
.unwrap()
|
||||||
|
.device_base();
|
||||||
|
let ged_data = create_ged_device(ged_base.0, ged_irq);
|
||||||
|
|
||||||
bytes.extend_from_slice(pci_dsdt_data.as_slice());
|
bytes.extend_from_slice(pci_dsdt_data.as_slice());
|
||||||
bytes.extend_from_slice(mbrd_dsdt_data.as_slice());
|
bytes.extend_from_slice(mbrd_dsdt_data.as_slice());
|
||||||
|
Loading…
x
Reference in New Issue
Block a user