|
| 1 | +// Copyright (C) 2019 Alibaba Cloud. All rights reserved. |
| 2 | +// SPDX-License-Identifier: Apache-2.0 |
| 3 | + |
| 4 | +//! Helper utilities for handling MSI interrupts. |
| 5 | +
|
| 6 | +use super::*; |
| 7 | +use kvm_bindings::{kvm_irq_routing_entry, KVM_IRQ_ROUTING_MSI}; |
| 8 | + |
| 9 | +pub(super) struct MsiConfig { |
| 10 | + pub(super) irqfd: EventFd, |
| 11 | + pub(super) config: Mutex<MsiIrqSourceConfig>, |
| 12 | +} |
| 13 | + |
| 14 | +impl MsiConfig { |
| 15 | + pub(super) fn new() -> Self { |
| 16 | + MsiConfig { |
| 17 | + irqfd: EventFd::new(0).unwrap(), |
| 18 | + config: Mutex::new(Default::default()), |
| 19 | + } |
| 20 | + } |
| 21 | +} |
| 22 | + |
| 23 | +pub(super) fn new_msi_routing_entry( |
| 24 | + gsi: InterruptIndex, |
| 25 | + msicfg: &MsiIrqSourceConfig, |
| 26 | +) -> kvm_irq_routing_entry { |
| 27 | + let mut entry = kvm_irq_routing_entry { |
| 28 | + gsi, |
| 29 | + type_: KVM_IRQ_ROUTING_MSI, |
| 30 | + flags: 0, |
| 31 | + ..Default::default() |
| 32 | + }; |
| 33 | + entry.u.msi.address_hi = msicfg.high_addr; |
| 34 | + entry.u.msi.address_lo = msicfg.low_addr; |
| 35 | + entry.u.msi.data = msicfg.data; |
| 36 | + entry |
| 37 | +} |
| 38 | + |
| 39 | +#[allow(irrefutable_let_patterns)] |
| 40 | +pub(super) fn create_msi_routing_entries( |
| 41 | + base: InterruptIndex, |
| 42 | + configs: &[InterruptSourceConfig], |
| 43 | +) -> Result<Vec<kvm_irq_routing_entry>> { |
| 44 | + let _ = base |
| 45 | + .checked_add(configs.len() as u32) |
| 46 | + .ok_or_else(|| std::io::Error::from_raw_os_error(libc::EINVAL))?; |
| 47 | + let mut entries = Vec::with_capacity(configs.len()); |
| 48 | + for (i, ref val) in configs.iter().enumerate() { |
| 49 | + if let InterruptSourceConfig::MsiIrq(msicfg) = val { |
| 50 | + let entry = new_msi_routing_entry(base + i as u32, msicfg); |
| 51 | + entries.push(entry); |
| 52 | + } else { |
| 53 | + return Err(std::io::Error::from_raw_os_error(libc::EINVAL)); |
| 54 | + } |
| 55 | + } |
| 56 | + Ok(entries) |
| 57 | +} |
0 commit comments