Merge branch 'pcid_int_rework' into 'master'
Add PciFunctionHandle::map_bar method See merge request redox-os/drivers!171
This commit is contained in:
@@ -14,7 +14,7 @@ use std::usize;
|
||||
|
||||
use event::{user_data, EventQueue};
|
||||
use libredox::flag;
|
||||
use pcid_interface::{PciBar, PcidServerHandle};
|
||||
use pcid_interface::{PciBar, PciFunctionHandle};
|
||||
use redox_log::{OutputBuilder, RedoxLogger};
|
||||
use syscall::{EventFlags, Packet, SchemeBlockMut};
|
||||
|
||||
@@ -65,11 +65,9 @@ fn setup_logging() -> Option<&'static RedoxLogger> {
|
||||
}
|
||||
|
||||
fn main() {
|
||||
let mut pcid_handle =
|
||||
PcidServerHandle::connect_default().expect("ac97d: failed to setup channel to pcid");
|
||||
let pci_config = pcid_handle
|
||||
.fetch_config()
|
||||
.expect("ac97d: failed to fetch config");
|
||||
let pcid_handle =
|
||||
PciFunctionHandle::connect_default().expect("ac97d: failed to setup channel to pcid");
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
let mut name = pci_config.func.name();
|
||||
name.push_str("_ac97");
|
||||
|
||||
+8
-10
@@ -16,7 +16,7 @@ use std::cell::RefCell;
|
||||
use std::sync::Arc;
|
||||
|
||||
use event::{user_data, EventQueue};
|
||||
use pcid_interface::{MsiSetFeatureInfo, PcidServerHandle, PciFeature, PciFeatureInfo, SetFeatureInfo};
|
||||
use pcid_interface::{MsiSetFeatureInfo, PciFunctionHandle, PciFeature, PciFeatureInfo, SetFeatureInfo};
|
||||
#[cfg(target_arch = "x86_64")]
|
||||
use pcid_interface::irq_helpers::allocate_single_interrupt_vector_for_msi;
|
||||
use pcid_interface::irq_helpers::read_bsp_apic_id;
|
||||
@@ -76,8 +76,8 @@ fn setup_logging() -> Option<&'static RedoxLogger> {
|
||||
}
|
||||
|
||||
#[cfg(target_arch = "x86_64")]
|
||||
fn get_int_method(pcid_handle: &mut PcidServerHandle) -> File {
|
||||
let pci_config = pcid_handle.fetch_config().expect("ihdad: failed to fetch config");
|
||||
fn get_int_method(pcid_handle: &mut PciFunctionHandle) -> File {
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
let all_pci_features = pcid_handle.fetch_all_features().expect("ihdad: failed to fetch pci features");
|
||||
log::debug!("PCI FEATURES: {:?}", all_pci_features);
|
||||
@@ -121,8 +121,8 @@ fn get_int_method(pcid_handle: &mut PcidServerHandle) -> File {
|
||||
|
||||
//TODO: MSI on non-x86_64?
|
||||
#[cfg(not(target_arch = "x86_64"))]
|
||||
fn get_int_method(pcid_handle: &mut PcidServerHandle) -> File {
|
||||
let pci_config = pcid_handle.fetch_config().expect("ihdad: failed to fetch config");
|
||||
fn get_int_method(pcid_handle: &mut PciFunctionHandle) -> File {
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
if let Some(irq) = pci_config.func.legacy_interrupt_line {
|
||||
// legacy INTx# interrupt pins.
|
||||
@@ -135,18 +135,16 @@ fn get_int_method(pcid_handle: &mut PcidServerHandle) -> File {
|
||||
fn daemon(daemon: redox_daemon::Daemon) -> ! {
|
||||
let _logger_ref = setup_logging();
|
||||
|
||||
let mut pcid_handle = PcidServerHandle::connect_default().expect("ihdad: failed to setup channel to pcid");
|
||||
let mut pcid_handle = PciFunctionHandle::connect_default().expect("ihdad: failed to setup channel to pcid");
|
||||
|
||||
let pci_config = pcid_handle.fetch_config().expect("ihdad: failed to fetch config");
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
let mut name = pci_config.func.name();
|
||||
name.push_str("_ihda");
|
||||
|
||||
let bar = &pci_config.func.bars[0];
|
||||
|
||||
log::info!(" + IHDA {}", pci_config.func.display());
|
||||
|
||||
let address = unsafe { bar.physmap_mem("ihdad") } as usize;
|
||||
let address = unsafe { pcid_handle.map_bar(0).expect("ihdad") }.ptr.as_ptr() as usize;
|
||||
|
||||
//TODO: MSI-X
|
||||
let mut irq_file = get_int_method(&mut pcid_handle);
|
||||
|
||||
@@ -4,7 +4,7 @@ extern crate syscall;
|
||||
use std::fs::File;
|
||||
use std::io::{Read, Write};
|
||||
|
||||
use pcid_interface::PcidServerHandle;
|
||||
use pcid_interface::PciFunctionHandle;
|
||||
use syscall::call::iopl;
|
||||
use syscall::data::Packet;
|
||||
use syscall::scheme::SchemeMut;
|
||||
@@ -16,11 +16,9 @@ mod bga;
|
||||
mod scheme;
|
||||
|
||||
fn main() {
|
||||
let mut pcid_handle =
|
||||
PcidServerHandle::connect_default().expect("bgad: failed to setup channel to pcid");
|
||||
let pci_config = pcid_handle
|
||||
.fetch_config()
|
||||
.expect("bgad: failed to fetch config");
|
||||
let pcid_handle =
|
||||
PciFunctionHandle::connect_default().expect("bgad: failed to setup channel to pcid");
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
let mut name = pci_config.func.name();
|
||||
name.push_str("_bga");
|
||||
|
||||
@@ -27,7 +27,7 @@ use std::fs::File;
|
||||
use std::io::{Read, Write};
|
||||
use std::sync::Arc;
|
||||
|
||||
use pcid_interface::PcidServerHandle;
|
||||
use pcid_interface::PciFunctionHandle;
|
||||
|
||||
use syscall::{Packet, SchemeMut};
|
||||
use virtio_core::transport::{self, Queue};
|
||||
@@ -409,12 +409,12 @@ fn reinit(control_queue: Arc<Queue>, cursor_queue: Arc<Queue>) -> Result<(), tra
|
||||
}
|
||||
|
||||
fn deamon(deamon: redox_daemon::Daemon) -> anyhow::Result<()> {
|
||||
let mut pcid_handle = PcidServerHandle::connect_default()?;
|
||||
let mut pcid_handle = PciFunctionHandle::connect_default()?;
|
||||
|
||||
// Double check that we have the right device.
|
||||
//
|
||||
// 0x1050 - virtio-gpu
|
||||
let pci_config = pcid_handle.fetch_config()?;
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
assert_eq!(pci_config.func.full_device_id.device_id, 0x1050);
|
||||
log::info!("virtio-gpu: initiating startup sequence :^)");
|
||||
|
||||
@@ -6,23 +6,19 @@ use std::rc::Rc;
|
||||
|
||||
use driver_network::NetworkScheme;
|
||||
use event::{user_data, EventQueue};
|
||||
use pcid_interface::PcidServerHandle;
|
||||
use pcid_interface::PciFunctionHandle;
|
||||
use syscall::EventFlags;
|
||||
|
||||
pub mod device;
|
||||
|
||||
fn main() {
|
||||
let mut pcid_handle =
|
||||
PcidServerHandle::connect_default().expect("e1000d: failed to setup channel to pcid");
|
||||
let pci_config = pcid_handle
|
||||
.fetch_config()
|
||||
.expect("e1000d: failed to fetch config");
|
||||
PciFunctionHandle::connect_default().expect("e1000d: failed to setup channel to pcid");
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
let mut name = pci_config.func.name();
|
||||
name.push_str("_e1000");
|
||||
|
||||
let bar = &pci_config.func.bars[0];
|
||||
|
||||
let irq = pci_config
|
||||
.func
|
||||
.legacy_interrupt_line
|
||||
@@ -33,7 +29,10 @@ fn main() {
|
||||
redox_daemon::Daemon::new(move |daemon| {
|
||||
let mut irq_file = irq.irq_handle("e1000d");
|
||||
|
||||
let address = unsafe { bar.physmap_mem("e1000d") } as usize;
|
||||
let address = unsafe { pcid_handle.map_bar(0) }
|
||||
.expect("e1000d")
|
||||
.ptr
|
||||
.as_ptr() as usize;
|
||||
|
||||
let device =
|
||||
unsafe { device::Intel8254x::new(address).expect("e1000d: failed to allocate device") };
|
||||
|
||||
+7
-19
@@ -6,27 +6,21 @@ use std::rc::Rc;
|
||||
|
||||
use driver_network::NetworkScheme;
|
||||
use event::{user_data, EventQueue};
|
||||
use pcid_interface::PcidServerHandle;
|
||||
use pcid_interface::PciFunctionHandle;
|
||||
use syscall::EventFlags;
|
||||
|
||||
pub mod device;
|
||||
#[rustfmt::skip]
|
||||
mod ixgbe;
|
||||
|
||||
const IXGBE_MMIO_SIZE: usize = 512 * 1024;
|
||||
|
||||
fn main() {
|
||||
let mut pcid_handle =
|
||||
PcidServerHandle::connect_default().expect("ixgbed: failed to setup channel to pcid");
|
||||
let pci_config = pcid_handle
|
||||
.fetch_config()
|
||||
.expect("ixgbed: failed to fetch config");
|
||||
PciFunctionHandle::connect_default().expect("ixgbed: failed to setup channel to pcid");
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
let mut name = pci_config.func.name();
|
||||
name.push_str("_ixgbe");
|
||||
|
||||
let (bar, _) = pci_config.func.bars[0].expect_mem();
|
||||
|
||||
let irq = pci_config
|
||||
.func
|
||||
.legacy_interrupt_line
|
||||
@@ -37,17 +31,11 @@ fn main() {
|
||||
redox_daemon::Daemon::new(move |daemon| {
|
||||
let mut irq_file = irq.irq_handle("ixgbed");
|
||||
|
||||
let address = unsafe {
|
||||
common::physmap(
|
||||
bar,
|
||||
IXGBE_MMIO_SIZE,
|
||||
common::Prot::RW,
|
||||
common::MemoryType::Uncacheable,
|
||||
)
|
||||
.expect("ixgbed: failed to map address") as usize
|
||||
};
|
||||
let mapped_bar = unsafe { pcid_handle.map_bar(0) }.expect("ixgbed");
|
||||
let address = mapped_bar.ptr.as_ptr();
|
||||
let size = mapped_bar.bar_size;
|
||||
|
||||
let device = device::Intel8259x::new(address, IXGBE_MMIO_SIZE)
|
||||
let device = device::Intel8259x::new(address as usize, size)
|
||||
.expect("ixgbed: failed to allocate device");
|
||||
|
||||
let mut scheme = NetworkScheme::new(device, format!("network.{name}"));
|
||||
|
||||
@@ -15,7 +15,7 @@ use pcid_interface::irq_helpers::allocate_single_interrupt_vector_for_msi;
|
||||
use pcid_interface::irq_helpers::read_bsp_apic_id;
|
||||
use pcid_interface::msi::{MsixInfo, MsixTableEntry};
|
||||
use pcid_interface::{
|
||||
MsiSetFeatureInfo, PciFeature, PciFeatureInfo, PcidServerHandle, SetFeatureInfo,
|
||||
MsiSetFeatureInfo, PciFeature, PciFeatureInfo, PciFunctionHandle, SetFeatureInfo,
|
||||
SubdriverArguments,
|
||||
};
|
||||
use redox_log::{OutputBuilder, RedoxLogger};
|
||||
@@ -95,8 +95,8 @@ impl MappedMsixRegs {
|
||||
}
|
||||
|
||||
#[cfg(target_arch = "x86_64")]
|
||||
fn get_int_method(pcid_handle: &mut PcidServerHandle) -> File {
|
||||
let pci_config = pcid_handle.fetch_config().expect("rtl8139d: failed to fetch config");
|
||||
fn get_int_method(pcid_handle: &mut PciFunctionHandle) -> File {
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
let all_pci_features = pcid_handle.fetch_all_features().expect("rtl8139d: failed to fetch pci features");
|
||||
log::info!("PCI FEATURES: {:?}", all_pci_features);
|
||||
@@ -135,8 +135,9 @@ fn get_int_method(pcid_handle: &mut PcidServerHandle) -> File {
|
||||
};
|
||||
msix_info.validate(pci_config.func.bars);
|
||||
|
||||
let bar = &pci_config.func.bars[msix_info.table_bar as usize];
|
||||
let bar_address = unsafe { bar.physmap_mem("rtl8139d") } as usize;
|
||||
let bar_address = unsafe { pcid_handle.map_bar(msix_info.table_bar).expect("rtl8139d") }
|
||||
.ptr
|
||||
.as_ptr() as usize;
|
||||
|
||||
let virt_table_base = (bar_address + msix_info.table_offset as usize) as *mut MsixTableEntry;
|
||||
|
||||
@@ -177,8 +178,8 @@ fn get_int_method(pcid_handle: &mut PcidServerHandle) -> File {
|
||||
|
||||
//TODO: MSI on non-x86_64?
|
||||
#[cfg(not(target_arch = "x86_64"))]
|
||||
fn get_int_method(pcid_handle: &mut PcidServerHandle) -> File {
|
||||
let pci_config = pcid_handle.fetch_config().expect("rtl8139d: failed to fetch config");
|
||||
fn get_int_method(pcid_handle: &mut PciFunctionHandle) -> File {
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
if let Some(irq) = pci_config.func.legacy_interrupt_line {
|
||||
// legacy INTx# interrupt pins.
|
||||
@@ -209,9 +210,9 @@ fn find_bar(pci_config: &SubdriverArguments) -> Option<(usize, usize)> {
|
||||
fn daemon(daemon: redox_daemon::Daemon) -> ! {
|
||||
let _logger_ref = setup_logging();
|
||||
|
||||
let mut pcid_handle = PcidServerHandle::connect_default().expect("rtl8139d: failed to setup channel to pcid");
|
||||
let mut pcid_handle = PciFunctionHandle::connect_default().expect("rtl8139d: failed to setup channel to pcid");
|
||||
|
||||
let pci_config = pcid_handle.fetch_config().expect("rtl8139d: failed to fetch config");
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
let mut name = pci_config.func.name();
|
||||
name.push_str("_rtl8139");
|
||||
|
||||
@@ -8,7 +8,7 @@ use std::rc::Rc;
|
||||
|
||||
use driver_network::NetworkScheme;
|
||||
use event::{user_data, EventQueue};
|
||||
use pcid_interface::{MsiSetFeatureInfo, PcidServerHandle, PciFeature, PciFeatureInfo, SetFeatureInfo, SubdriverArguments};
|
||||
use pcid_interface::{MsiSetFeatureInfo, PciFunctionHandle, PciFeature, PciFeatureInfo, SetFeatureInfo, SubdriverArguments};
|
||||
#[cfg(target_arch = "x86_64")]
|
||||
use pcid_interface::irq_helpers::allocate_single_interrupt_vector_for_msi;
|
||||
use pcid_interface::irq_helpers::read_bsp_apic_id;
|
||||
@@ -90,8 +90,8 @@ impl MappedMsixRegs {
|
||||
}
|
||||
|
||||
#[cfg(target_arch = "x86_64")]
|
||||
fn get_int_method(pcid_handle: &mut PcidServerHandle) -> File {
|
||||
let pci_config = pcid_handle.fetch_config().expect("rtl8168d: failed to fetch config");
|
||||
fn get_int_method(pcid_handle: &mut PciFunctionHandle) -> File {
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
let all_pci_features = pcid_handle.fetch_all_features().expect("rtl8168d: failed to fetch pci features");
|
||||
log::info!("PCI FEATURES: {:?}", all_pci_features);
|
||||
@@ -130,8 +130,9 @@ fn get_int_method(pcid_handle: &mut PcidServerHandle) -> File {
|
||||
};
|
||||
msix_info.validate(pci_config.func.bars);
|
||||
|
||||
let bar = &pci_config.func.bars[msix_info.table_bar as usize];
|
||||
let bar_address = unsafe { bar.physmap_mem("rtl8168d") } as usize;
|
||||
let bar_address = unsafe { pcid_handle.map_bar(msix_info.table_bar).expect("rtl8168d") }
|
||||
.ptr
|
||||
.as_ptr() as usize;
|
||||
|
||||
let virt_table_base = (bar_address + msix_info.table_offset as usize) as *mut MsixTableEntry;
|
||||
|
||||
@@ -172,8 +173,8 @@ fn get_int_method(pcid_handle: &mut PcidServerHandle) -> File {
|
||||
|
||||
//TODO: MSI on non-x86_64?
|
||||
#[cfg(not(target_arch = "x86_64"))]
|
||||
fn get_int_method(pcid_handle: &mut PcidServerHandle) -> File {
|
||||
let pci_config = pcid_handle.fetch_config().expect("rtl8168d: failed to fetch config");
|
||||
fn get_int_method(pcid_handle: &mut PciFunctionHandle) -> File {
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
if let Some(irq) = pci_config.func.legacy_interrupt_line {
|
||||
// legacy INTx# interrupt pins.
|
||||
@@ -204,9 +205,9 @@ fn find_bar(pci_config: &SubdriverArguments) -> Option<(usize, usize)> {
|
||||
fn daemon(daemon: redox_daemon::Daemon) -> ! {
|
||||
let _logger_ref = setup_logging();
|
||||
|
||||
let mut pcid_handle = PcidServerHandle::connect_default().expect("rtl8168d: failed to setup channel to pcid");
|
||||
let mut pcid_handle = PciFunctionHandle::connect_default().expect("rtl8168d: failed to setup channel to pcid");
|
||||
|
||||
let pci_config = pcid_handle.fetch_config().expect("rtl8168d: failed to fetch config");
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
let mut name = pci_config.func.name();
|
||||
name.push_str("_rtl8168");
|
||||
|
||||
@@ -5,7 +5,7 @@ use std::io::{Read, Write};
|
||||
use std::mem;
|
||||
|
||||
use driver_network::NetworkScheme;
|
||||
use pcid_interface::PcidServerHandle;
|
||||
use pcid_interface::PciFunctionHandle;
|
||||
|
||||
use scheme::VirtioNet;
|
||||
|
||||
@@ -28,12 +28,12 @@ static_assertions::const_assert_eq!(core::mem::size_of::<VirtHeader>(), 12);
|
||||
const MAX_BUFFER_LEN: usize = 65535;
|
||||
|
||||
fn deamon(daemon: redox_daemon::Daemon) -> Result<(), Box<dyn std::error::Error>> {
|
||||
let mut pcid_handle = PcidServerHandle::connect_default()?;
|
||||
let mut pcid_handle = PciFunctionHandle::connect_default()?;
|
||||
|
||||
// Double check that we have the right device.
|
||||
//
|
||||
// 0x1000 - virtio-net
|
||||
let pci_config = pcid_handle.fetch_config()?;
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
assert_eq!(pci_config.func.full_device_id.device_id, 0x1000);
|
||||
log::info!("virtio-net: initiating startup sequence :^)");
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
use std::fmt;
|
||||
use std::fs::File;
|
||||
use std::io::prelude::*;
|
||||
use std::ptr::NonNull;
|
||||
use std::{env, io};
|
||||
|
||||
use std::os::unix::io::{FromRawFd, RawFd};
|
||||
@@ -222,14 +223,21 @@ pub enum PcidClientResponse {
|
||||
WriteConfig,
|
||||
}
|
||||
|
||||
pub struct MappedBar {
|
||||
pub ptr: NonNull<u8>,
|
||||
pub bar_size: usize,
|
||||
}
|
||||
|
||||
// TODO: Ideally, pcid might have its own scheme, like lots of other Redox drivers, where this kind of IPC is done. Otherwise, instead of writing serde messages over
|
||||
// a channel, the communication could potentially be done via mmap, using a channel
|
||||
// very similar to crossbeam-channel or libstd's mpsc (except the cycle, enqueue and dequeue fields
|
||||
// are stored in the same buffer as the actual data).
|
||||
/// A handle from a `pcid` client (e.g. `ahcid`) to `pcid`.
|
||||
pub struct PcidServerHandle {
|
||||
pub struct PciFunctionHandle {
|
||||
pcid_to_client: File,
|
||||
pcid_from_client: File,
|
||||
config: SubdriverArguments,
|
||||
mapped_bars: [Option<MappedBar>; 6],
|
||||
}
|
||||
|
||||
pub(crate) fn send<W: Write, T: Serialize>(w: &mut W, message: &T) -> Result<()> {
|
||||
@@ -253,14 +261,25 @@ pub(crate) fn recv<R: Read, T: DeserializeOwned>(r: &mut R) -> Result<T> {
|
||||
Ok(bincode::deserialize_from(&data[..])?)
|
||||
}
|
||||
|
||||
impl PcidServerHandle {
|
||||
impl PciFunctionHandle {
|
||||
pub fn connect_default() -> Result<Self> {
|
||||
let pcid_to_client_fd = env::var("PCID_TO_CLIENT_FD")?.parse::<RawFd>().map_err(PcidClientHandleError::EnvValidityError)?;
|
||||
let pcid_from_client_fd = env::var("PCID_FROM_CLIENT_FD")?.parse::<RawFd>().map_err(PcidClientHandleError::EnvValidityError)?;
|
||||
|
||||
let mut pcid_to_client = unsafe { File::from_raw_fd(pcid_to_client_fd) };
|
||||
let mut pcid_from_client = unsafe { File::from_raw_fd(pcid_from_client_fd) };
|
||||
|
||||
send(&mut pcid_from_client, &PcidClientRequest::RequestConfig)?;
|
||||
let config = match recv(&mut pcid_to_client)? {
|
||||
PcidClientResponse::Config(a) => a,
|
||||
other => return Err(PcidClientHandleError::InvalidResponse(other)),
|
||||
};
|
||||
|
||||
Ok(Self {
|
||||
pcid_to_client: unsafe { File::from_raw_fd(pcid_to_client_fd) },
|
||||
pcid_from_client: unsafe { File::from_raw_fd(pcid_from_client_fd) },
|
||||
pcid_to_client,
|
||||
pcid_from_client,
|
||||
config,
|
||||
mapped_bars: [const { None }; 6],
|
||||
})
|
||||
}
|
||||
fn send(&mut self, req: &PcidClientRequest) -> Result<()> {
|
||||
@@ -269,12 +288,8 @@ impl PcidServerHandle {
|
||||
fn recv(&mut self) -> Result<PcidClientResponse> {
|
||||
recv(&mut self.pcid_to_client)
|
||||
}
|
||||
pub fn fetch_config(&mut self) -> Result<SubdriverArguments> {
|
||||
self.send(&PcidClientRequest::RequestConfig)?;
|
||||
match self.recv()? {
|
||||
PcidClientResponse::Config(a) => Ok(a),
|
||||
other => Err(PcidClientHandleError::InvalidResponse(other)),
|
||||
}
|
||||
pub fn config(&self) -> SubdriverArguments {
|
||||
self.config.clone()
|
||||
}
|
||||
|
||||
pub fn get_vendor_capabilities(&mut self) -> Result<Vec<VendorSpecificCapability>> {
|
||||
@@ -329,4 +344,27 @@ impl PcidServerHandle {
|
||||
other => Err(PcidClientHandleError::InvalidResponse(other)),
|
||||
}
|
||||
}
|
||||
pub unsafe fn map_bar(&mut self, bir: u8) -> Result<&MappedBar> {
|
||||
let mapped_bar = &mut self.mapped_bars[bir as usize];
|
||||
if let Some(mapped_bar) = mapped_bar {
|
||||
Ok(mapped_bar)
|
||||
} else {
|
||||
let (bar, bar_size) = self.config.func.bars[bir as usize].expect_mem();
|
||||
let ptr = unsafe {
|
||||
common::physmap(
|
||||
bar,
|
||||
bar_size,
|
||||
common::Prot::RW,
|
||||
// FIXME once the kernel supports this use write-through for prefetchable BAR
|
||||
common::MemoryType::Uncacheable,
|
||||
)
|
||||
}
|
||||
.map_err(|err| io::Error::other(format!("failed to map BAR at {bar:016X}: {err}")))?;
|
||||
|
||||
Ok(mapped_bar.insert(MappedBar {
|
||||
ptr: NonNull::new(ptr.cast::<u8>()).expect("Mapping a BAR resulted in a nullptr"),
|
||||
bar_size,
|
||||
}))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -52,18 +52,4 @@ impl PciBar {
|
||||
PciBar::None => panic!("expected BAR to exist"),
|
||||
}
|
||||
}
|
||||
|
||||
pub unsafe fn physmap_mem(&self, driver: &str) -> *mut () {
|
||||
let (bar, bar_size) = self.expect_mem();
|
||||
unsafe {
|
||||
common::physmap(
|
||||
bar,
|
||||
bar_size,
|
||||
common::Prot::RW,
|
||||
// FIXME once the kernel supports this use write-through for prefetchable BAR
|
||||
common::MemoryType::Uncacheable,
|
||||
)
|
||||
}
|
||||
.unwrap_or_else(|err| panic!("{driver}: failed to map BAR at {bar:016X}: {err}"))
|
||||
}
|
||||
}
|
||||
|
||||
@@ -9,7 +9,7 @@ use std::os::fd::AsRawFd;
|
||||
use std::usize;
|
||||
|
||||
use event::{EventFlags, RawEventQueue};
|
||||
use pcid_interface::PcidServerHandle;
|
||||
use pcid_interface::PciFunctionHandle;
|
||||
use redox_scheme::{RequestKind, Response, SignalBehavior, Socket, V2};
|
||||
use syscall::error::{Error, ENODEV};
|
||||
|
||||
@@ -72,23 +72,19 @@ fn main() {
|
||||
|
||||
fn daemon(daemon: redox_daemon::Daemon) -> ! {
|
||||
let mut pcid_handle =
|
||||
PcidServerHandle::connect_default().expect("ahcid: failed to setup channel to pcid");
|
||||
let pci_config = pcid_handle
|
||||
.fetch_config()
|
||||
.expect("ahcid: failed to fetch config");
|
||||
PciFunctionHandle::connect_default().expect("ahcid: failed to setup channel to pcid");
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
let mut name = pci_config.func.name();
|
||||
name.push_str("_ahci");
|
||||
|
||||
let bar = &pci_config.func.bars[5];
|
||||
|
||||
let irq = pci_config.func.legacy_interrupt_line.expect("ahcid: no legacy interrupts supported");
|
||||
|
||||
let _logger_ref = setup_logging(&name);
|
||||
|
||||
info!(" + AHCI {}", pci_config.func.display());
|
||||
|
||||
let address = unsafe { bar.physmap_mem("ahcid") };
|
||||
let address = unsafe { pcid_handle.map_bar(5).expect("ahcid") }.ptr.as_ptr() as usize;
|
||||
{
|
||||
let scheme_name = format!("disk.{}", name);
|
||||
let socket = Socket::<V2>::nonblock(&scheme_name).expect("ahcid: failed to create disk scheme");
|
||||
|
||||
@@ -2,7 +2,7 @@ use driver_block::Disk;
|
||||
use event::{EventFlags, RawEventQueue};
|
||||
use libredox::flag;
|
||||
use log::{error, info};
|
||||
use pcid_interface::{PciBar, PcidServerHandle};
|
||||
use pcid_interface::{PciBar, PciFunctionHandle};
|
||||
use redox_log::{OutputBuilder, RedoxLogger};
|
||||
use redox_scheme::{RequestKind, Response, SignalBehavior, Socket, V2};
|
||||
use std::{
|
||||
@@ -74,10 +74,10 @@ fn main() {
|
||||
}
|
||||
|
||||
fn daemon(daemon: redox_daemon::Daemon) -> ! {
|
||||
let mut pcid_handle =
|
||||
PcidServerHandle::connect_default().expect("ided: failed to setup channel to pcid");
|
||||
let pcid_handle =
|
||||
PciFunctionHandle::connect_default().expect("ided: failed to setup channel to pcid");
|
||||
|
||||
let pci_config = pcid_handle.fetch_config().expect("ided: failed to fetch config");
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
let mut name = pci_config.func.name();
|
||||
name.push_str("_ide");
|
||||
|
||||
+17
-80
@@ -10,7 +10,7 @@ use std::sync::{Arc, Mutex};
|
||||
use std::{slice, usize};
|
||||
|
||||
use libredox::flag;
|
||||
use pcid_interface::{PciFeature, PciFeatureInfo, PciFunction, PcidServerHandle};
|
||||
use pcid_interface::{PciFeature, PciFeatureInfo, PciFunction, PciFunctionHandle};
|
||||
use redox_scheme::{CallRequest, RequestKind, SignalBehavior, Socket, V2};
|
||||
use syscall::{
|
||||
Event, Mmio, Packet, Result, SchemeBlockMut,
|
||||
@@ -24,53 +24,13 @@ use self::scheme::DiskScheme;
|
||||
mod nvme;
|
||||
mod scheme;
|
||||
|
||||
/// A wrapper for a BAR allocation.
|
||||
pub struct Bar {
|
||||
ptr: NonNull<u8>,
|
||||
physical: usize,
|
||||
bar_size: usize,
|
||||
}
|
||||
impl Bar {
|
||||
pub fn allocate(bar: usize, bar_size: usize) -> Result<Self> {
|
||||
Ok(Self {
|
||||
ptr: NonNull::new(
|
||||
unsafe { common::physmap(
|
||||
bar,
|
||||
bar_size,
|
||||
common::Prot { read: true, write: true },
|
||||
common::MemoryType::Uncacheable,
|
||||
)? as *mut u8 },
|
||||
)
|
||||
.expect("Mapping a BAR resulted in a nullptr"),
|
||||
physical: bar,
|
||||
bar_size,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
impl Drop for Bar {
|
||||
fn drop(&mut self) {
|
||||
let _ = unsafe {
|
||||
libredox::call::munmap(
|
||||
self.ptr.as_ptr().cast(),
|
||||
self.bar_size.next_multiple_of(PAGE_SIZE),
|
||||
)
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
/// The PCI BARs that may be allocated.
|
||||
#[derive(Default)]
|
||||
pub struct AllocatedBars(pub [Mutex<Option<Bar>>; 6]);
|
||||
|
||||
/// Get the most optimal yet functional interrupt mechanism: either (in the order of preference):
|
||||
/// MSI-X, MSI, and INTx# pin. Returns both runtime interrupt structures (MSI/MSI-X capability
|
||||
/// structures), and the handles to the interrupts.
|
||||
#[cfg(target_arch = "x86_64")]
|
||||
fn get_int_method(
|
||||
pcid_handle: &mut PcidServerHandle,
|
||||
pcid_handle: &mut PciFunctionHandle,
|
||||
function: &PciFunction,
|
||||
allocated_bars: &AllocatedBars,
|
||||
) -> Result<(InterruptMethod, InterruptSources)> {
|
||||
log::trace!("Begin get_int_method");
|
||||
use pcid_interface::irq_helpers;
|
||||
@@ -91,26 +51,11 @@ fn get_int_method(
|
||||
_ => unreachable!(),
|
||||
};
|
||||
msix_info.validate(function.bars);
|
||||
fn bar_base(
|
||||
allocated_bars: &AllocatedBars,
|
||||
function: &PciFunction,
|
||||
bir: u8,
|
||||
) -> Result<NonNull<u8>> {
|
||||
let bir = usize::from(bir);
|
||||
let mut bar_guard = allocated_bars.0[bir].lock().unwrap();
|
||||
match &mut *bar_guard {
|
||||
&mut Some(ref bar) => Ok(bar.ptr),
|
||||
bar_to_set @ &mut None => {
|
||||
let (bar, bar_size) = function.bars[bir].expect_mem();
|
||||
|
||||
let bar = Bar::allocate(bar, bar_size)?;
|
||||
*bar_to_set = Some(bar);
|
||||
Ok(bar_to_set.as_ref().unwrap().ptr)
|
||||
}
|
||||
}
|
||||
fn bar_base(pcid_handle: &mut PciFunctionHandle, bir: u8) -> Result<NonNull<u8>> {
|
||||
Ok(unsafe { pcid_handle.map_bar(bir) }.expect("nvmed").ptr)
|
||||
}
|
||||
let table_bar_base: *mut u8 =
|
||||
bar_base(allocated_bars, function, msix_info.table_bar)?.as_ptr();
|
||||
bar_base(pcid_handle, msix_info.table_bar)?.as_ptr();
|
||||
let table_base =
|
||||
unsafe { table_bar_base.offset(msix_info.table_offset as isize) };
|
||||
|
||||
@@ -194,9 +139,8 @@ fn get_int_method(
|
||||
//TODO: MSI on non-x86_64?
|
||||
#[cfg(not(target_arch = "x86_64"))]
|
||||
fn get_int_method(
|
||||
pcid_handle: &mut PcidServerHandle,
|
||||
pcid_handle: &mut PciFunctionHandle,
|
||||
function: &PciFunction,
|
||||
allocated_bars: &AllocatedBars,
|
||||
) -> Result<(InterruptMethod, InterruptSources)> {
|
||||
if let Some(irq) = function.legacy_interrupt_line {
|
||||
// INTx# pin based interrupts.
|
||||
@@ -256,28 +200,16 @@ fn main() {
|
||||
}
|
||||
fn daemon(daemon: redox_daemon::Daemon) -> ! {
|
||||
let mut pcid_handle =
|
||||
PcidServerHandle::connect_default().expect("nvmed: failed to setup channel to pcid");
|
||||
let pci_config = pcid_handle
|
||||
.fetch_config()
|
||||
.expect("nvmed: failed to fetch config");
|
||||
PciFunctionHandle::connect_default().expect("nvmed: failed to setup channel to pcid");
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
let scheme_name = format!("disk.{}-nvme", pci_config.func.name());
|
||||
|
||||
let _logger_ref = setup_logging(&scheme_name);
|
||||
|
||||
let bar = &pci_config.func.bars[0];
|
||||
let (bar_ptr, bar_size) = bar.expect_mem();
|
||||
|
||||
log::debug!("NVME PCI CONFIG: {:?}", pci_config);
|
||||
|
||||
let allocated_bars = AllocatedBars::default();
|
||||
|
||||
let address = unsafe { bar.physmap_mem("nvmed") } as usize;
|
||||
*allocated_bars.0[0].lock().unwrap() = Some(Bar {
|
||||
physical: bar_ptr,
|
||||
bar_size,
|
||||
ptr: NonNull::new(address as *mut u8).expect("Physmapping BAR gave nullptr"),
|
||||
});
|
||||
let address = unsafe { pcid_handle.map_bar(0).expect("nvmed").ptr };
|
||||
|
||||
let socket = Socket::<V2>::create(&scheme_name).expect("nvmed: failed to create disk scheme");
|
||||
|
||||
@@ -285,10 +217,15 @@ fn daemon(daemon: redox_daemon::Daemon) -> ! {
|
||||
|
||||
let (reactor_sender, reactor_receiver) = crossbeam_channel::unbounded();
|
||||
let (interrupt_method, interrupt_sources) =
|
||||
get_int_method(&mut pcid_handle, &pci_config.func, &allocated_bars)
|
||||
get_int_method(&mut pcid_handle, &pci_config.func)
|
||||
.expect("nvmed: failed to find a suitable interrupt method");
|
||||
let mut nvme = Nvme::new(address, interrupt_method, pcid_handle, reactor_sender)
|
||||
.expect("nvmed: failed to allocate driver data");
|
||||
let mut nvme = Nvme::new(
|
||||
address.as_ptr() as usize,
|
||||
interrupt_method,
|
||||
pcid_handle,
|
||||
reactor_sender,
|
||||
)
|
||||
.expect("nvmed: failed to allocate driver data");
|
||||
unsafe { nvme.init() }
|
||||
log::debug!("Finished base initialization");
|
||||
let nvme = Arc::new(nvme);
|
||||
|
||||
@@ -23,7 +23,7 @@ use self::cq_reactor::NotifReq;
|
||||
pub use self::queues::{NvmeCmd, NvmeCmdQueue, NvmeComp, NvmeCompQueue};
|
||||
|
||||
use pcid_interface::msi::{MsiInfo, MsixInfo, MsixTableEntry};
|
||||
use pcid_interface::PcidServerHandle;
|
||||
use pcid_interface::PciFunctionHandle;
|
||||
|
||||
#[cfg(target_arch = "aarch64")]
|
||||
#[inline(always)]
|
||||
@@ -173,7 +173,7 @@ pub type AtomicCmdId = AtomicU16;
|
||||
|
||||
pub struct Nvme {
|
||||
interrupt_method: Mutex<InterruptMethod>,
|
||||
pcid_interface: Mutex<PcidServerHandle>,
|
||||
pcid_interface: Mutex<PciFunctionHandle>,
|
||||
regs: RwLock<&'static mut NvmeRegs>,
|
||||
|
||||
pub(crate) submission_queues: RwLock<BTreeMap<SqId, (Mutex<NvmeCmdQueue>, CqId)>>,
|
||||
@@ -209,7 +209,7 @@ impl Nvme {
|
||||
pub fn new(
|
||||
address: usize,
|
||||
interrupt_method: InterruptMethod,
|
||||
pcid_interface: PcidServerHandle,
|
||||
pcid_interface: PciFunctionHandle,
|
||||
reactor_sender: Sender<NotifReq>,
|
||||
) -> Result<Self> {
|
||||
Ok(Nvme {
|
||||
|
||||
@@ -109,12 +109,12 @@ pub struct BlockVirtRequest {
|
||||
const_assert_eq!(core::mem::size_of::<BlockVirtRequest>(), 16);
|
||||
|
||||
fn deamon(deamon: redox_daemon::Daemon) -> anyhow::Result<()> {
|
||||
let mut pcid_handle = PcidServerHandle::connect_default()?;
|
||||
let mut pcid_handle = PciFunctionHandle::connect_default()?;
|
||||
|
||||
// Double check that we have the right device.
|
||||
//
|
||||
// 0x1001 - virtio-blk
|
||||
let pci_config = pcid_handle.fetch_config()?;
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
assert_eq!(pci_config.func.full_device_id.device_id, 0x1001);
|
||||
log::info!("virtio-blk: initiating startup sequence :^)");
|
||||
|
||||
+4
-8
@@ -6,7 +6,7 @@ use std::os::unix::io::AsRawFd;
|
||||
use std::fs::File;
|
||||
use std::io::{Result, Read, Write};
|
||||
|
||||
use pcid_interface::{PciBar, PcidServerHandle};
|
||||
use pcid_interface::{PciBar, PciFunctionHandle};
|
||||
use syscall::flag::EventFlags;
|
||||
use syscall::io::{Io, Mmio, Pio};
|
||||
|
||||
@@ -181,18 +181,14 @@ impl VboxGuestInfo {
|
||||
|
||||
fn main() {
|
||||
let mut pcid_handle =
|
||||
PcidServerHandle::connect_default().expect("vboxd: failed to setup channel to pcid");
|
||||
let pci_config = pcid_handle
|
||||
.fetch_config()
|
||||
.expect("vboxd: failed to fetch config");
|
||||
PciFunctionHandle::connect_default().expect("vboxd: failed to setup channel to pcid");
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
let mut name = pci_config.func.name();
|
||||
name.push_str("_vbox");
|
||||
|
||||
let bar0 = pci_config.func.bars[0].expect_port();
|
||||
|
||||
let bar1 = &pci_config.func.bars[1];
|
||||
|
||||
let irq = pci_config.func.legacy_interrupt_line.expect("vboxd: no legacy interrupts supported");
|
||||
|
||||
println!(" + VirtualBox {}", pci_config.func.display());
|
||||
@@ -217,7 +213,7 @@ fn main() {
|
||||
let mut irq_file = irq.irq_handle("vboxd");
|
||||
|
||||
let mut port = Pio::<u32>::new(bar0 as u16);
|
||||
let address = unsafe { bar1.physmap_mem("vboxd") };
|
||||
let address = unsafe { pcid_handle.map_bar(1) }.expect("vboxd").ptr.as_ptr();
|
||||
{
|
||||
let vmmdev = unsafe { &mut *(address as *mut VboxVmmDev) };
|
||||
|
||||
|
||||
@@ -8,8 +8,8 @@ use crate::{probe::MappedMsixRegs, MSIX_PRIMARY_VECTOR};
|
||||
|
||||
use pcid_interface::*;
|
||||
|
||||
pub fn enable_msix(pcid_handle: &mut PcidServerHandle) -> Result<File, Error> {
|
||||
let pci_config = pcid_handle.fetch_config()?;
|
||||
pub fn enable_msix(pcid_handle: &mut PciFunctionHandle) -> Result<File, Error> {
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
// Extended message signaled interrupts.
|
||||
let msix_info = match pcid_handle.feature_info(PciFeature::MsiX)? {
|
||||
@@ -18,8 +18,9 @@ pub fn enable_msix(pcid_handle: &mut PcidServerHandle) -> Result<File, Error> {
|
||||
};
|
||||
msix_info.validate(pci_config.func.bars);
|
||||
|
||||
let bar = &pci_config.func.bars[msix_info.table_bar as usize];
|
||||
let bar_address = unsafe { bar.physmap_mem("virtio-core") } as usize;
|
||||
let bar_address = unsafe { pcid_handle.map_bar(msix_info.table_bar)? }
|
||||
.ptr
|
||||
.as_ptr() as usize;
|
||||
let virt_table_base = (bar_address + msix_info.table_offset as usize) as *mut MsixTableEntry;
|
||||
|
||||
let mut info = MappedMsixRegs {
|
||||
@@ -50,7 +51,7 @@ pub fn enable_msix(pcid_handle: &mut PcidServerHandle) -> Result<File, Error> {
|
||||
|
||||
pub fn probe_legacy_port_transport(
|
||||
pci_config: &SubdriverArguments,
|
||||
pcid_handle: &mut PcidServerHandle,
|
||||
pcid_handle: &mut PciFunctionHandle,
|
||||
) -> Result<Device, Error> {
|
||||
let port = pci_config.func.bars[0].expect_port();
|
||||
|
||||
|
||||
@@ -41,7 +41,7 @@ static_assertions::const_assert_eq!(std::mem::size_of::<MsixTableEntry>(), 16);
|
||||
pub const MSIX_PRIMARY_VECTOR: u16 = 0;
|
||||
|
||||
#[cfg(not(target_arch = "x86_64"))]
|
||||
fn enable_msix(pcid_handle: &mut PcidServerHandle) -> Result<File, Error> {
|
||||
fn enable_msix(pcid_handle: &mut PciFunctionHandle) -> Result<File, Error> {
|
||||
panic!("Msi-X only supported on x86_64");
|
||||
}
|
||||
|
||||
@@ -59,8 +59,8 @@ fn enable_msix(pcid_handle: &mut PcidServerHandle) -> Result<File, Error> {
|
||||
///
|
||||
/// ## Panics
|
||||
/// This function panics if the device is not a virtio device.
|
||||
pub fn probe_device(pcid_handle: &mut PcidServerHandle) -> Result<Device, Error> {
|
||||
let pci_config = pcid_handle.fetch_config()?;
|
||||
pub fn probe_device(pcid_handle: &mut PciFunctionHandle) -> Result<Device, Error> {
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
assert_eq!(
|
||||
pci_config.func.full_device_id.vendor_id, 6900,
|
||||
|
||||
+12
-9
@@ -12,7 +12,7 @@ use std::sync::{Arc, Mutex};
|
||||
use std::env;
|
||||
|
||||
use libredox::flag;
|
||||
use pcid_interface::{MsiSetFeatureInfo, PcidServerHandle, PciFeature, PciFeatureInfo, SetFeatureInfo};
|
||||
use pcid_interface::{MsiSetFeatureInfo, PciFunctionHandle, PciFeature, PciFeatureInfo, SetFeatureInfo};
|
||||
#[cfg(target_arch = "x86_64")]
|
||||
use pcid_interface::irq_helpers::allocate_single_interrupt_vector_for_msi;
|
||||
use pcid_interface::irq_helpers::read_bsp_apic_id;
|
||||
@@ -85,8 +85,8 @@ fn setup_logging(name: &str) -> Option<&'static RedoxLogger> {
|
||||
}
|
||||
|
||||
#[cfg(target_arch = "x86_64")]
|
||||
fn get_int_method(pcid_handle: &mut PcidServerHandle, bar0_address: usize) -> (Option<File>, InterruptMethod) {
|
||||
let pci_config = pcid_handle.fetch_config().expect("xhcid: failed to fetch config");
|
||||
fn get_int_method(pcid_handle: &mut PciFunctionHandle, bar0_address: usize) -> (Option<File>, InterruptMethod) {
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
let all_pci_features = pcid_handle.fetch_all_features().expect("xhcid: failed to fetch pci features");
|
||||
log::debug!("XHCI PCI FEATURES: {:?}", all_pci_features);
|
||||
@@ -167,8 +167,8 @@ fn get_int_method(pcid_handle: &mut PcidServerHandle, bar0_address: usize) -> (O
|
||||
|
||||
//TODO: MSI on non-x86_64?
|
||||
#[cfg(not(target_arch = "x86_64"))]
|
||||
fn get_int_method(pcid_handle: &mut PcidServerHandle, address: usize) -> (Option<File>, InterruptMethod) {
|
||||
let pci_config = pcid_handle.fetch_config().expect("xhcid: failed to fetch config");
|
||||
fn get_int_method(pcid_handle: &mut PciFunctionHandle, address: usize) -> (Option<File>, InterruptMethod) {
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
if let Some(irq) = pci_config.func.legacy_interrupt_line {
|
||||
// legacy INTx# interrupt pins.
|
||||
@@ -184,8 +184,9 @@ fn main() {
|
||||
}
|
||||
|
||||
fn daemon(daemon: redox_daemon::Daemon) -> ! {
|
||||
let mut pcid_handle = PcidServerHandle::connect_default().expect("xhcid: failed to setup channel to pcid");
|
||||
let pci_config = pcid_handle.fetch_config().expect("xhcid: failed to fetch config");
|
||||
let mut pcid_handle =
|
||||
PciFunctionHandle::connect_default().expect("xhcid: failed to setup channel to pcid");
|
||||
let pci_config = pcid_handle.config();
|
||||
|
||||
let mut name = pci_config.func.name();
|
||||
name.push_str("_xhci");
|
||||
@@ -193,9 +194,11 @@ fn daemon(daemon: redox_daemon::Daemon) -> ! {
|
||||
let _logger_ref = setup_logging(&name);
|
||||
|
||||
log::debug!("XHCI PCI CONFIG: {:?}", pci_config);
|
||||
let bar = &pci_config.func.bars[0];
|
||||
|
||||
let address = unsafe { bar.physmap_mem("xhcid") } as usize;
|
||||
let address = unsafe { pcid_handle.map_bar(0) }
|
||||
.expect("xhcid")
|
||||
.ptr
|
||||
.as_ptr() as usize;
|
||||
|
||||
let (irq_file, interrupt_method) = (None, InterruptMethod::Polling); //TODO: get_int_method(&mut pcid_handle, address);
|
||||
|
||||
|
||||
@@ -22,7 +22,7 @@ use serde::Deserialize;
|
||||
use crate::usb;
|
||||
|
||||
use pcid_interface::msi::{MsixInfo, MsixTableEntry};
|
||||
use pcid_interface::{PcidServerHandle, PciFeature};
|
||||
use pcid_interface::{PciFunctionHandle, PciFeature};
|
||||
|
||||
mod capability;
|
||||
mod context;
|
||||
@@ -198,7 +198,7 @@ pub struct Xhci {
|
||||
scheme_name: String,
|
||||
|
||||
interrupt_method: InterruptMethod,
|
||||
pcid_handle: Mutex<PcidServerHandle>,
|
||||
pcid_handle: Mutex<PciFunctionHandle>,
|
||||
|
||||
irq_reactor: Mutex<Option<thread::JoinHandle<()>>>,
|
||||
|
||||
@@ -258,7 +258,7 @@ impl EndpointState {
|
||||
}
|
||||
|
||||
impl Xhci {
|
||||
pub fn new(scheme_name: String, address: usize, interrupt_method: InterruptMethod, pcid_handle: PcidServerHandle) -> Result<Xhci> {
|
||||
pub fn new(scheme_name: String, address: usize, interrupt_method: InterruptMethod, pcid_handle: PciFunctionHandle) -> Result<Xhci> {
|
||||
let cap = unsafe { &mut *(address as *mut CapabilityRegs) };
|
||||
debug!("CAP REGS BASE {:X}", address);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user