Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
30 changes: 22 additions & 8 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 2 additions & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -132,13 +132,15 @@ hex = "0.4.3"
http = "1.1.0"
hyper = "1.0"
linkme = "0.3.33"
iddqd = "0.3"
itertools = "0.13.0"
kstat-rs = "0.2.4"
lazy_static = "1.4"
libc = "0.2"
mockall = "0.12"
newtype_derive = "0.1.6"
newtype-uuid = { version = "1.0.1", features = [ "v4" ] }
nix = { version = "0.31", features = [ "poll" ] }
owo-colors = "4"
oxide-tokio-rt = "0.1.2"
paste = "1.0.15"
Expand Down
15 changes: 15 additions & 0 deletions bin/propolis-standalone/src/config.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ use std::sync::Arc;

use anyhow::Context;
use cpuid_utils::CpuidSet;
use propolis::vsock::proxy::VsockPortMapping;
use propolis_types::CpuidIdent;
use propolis_types::CpuidValues;
use propolis_types::CpuidVendor;
Expand Down Expand Up @@ -170,6 +171,20 @@ impl VionaDeviceParams {
}
}

#[derive(Deserialize)]
pub struct VsockDevice {
pub guest_cid: u32,
pub port_mappings: Vec<VsockPortMapping>,
}

impl VsockDevice {
pub fn from_opts(
opts: &BTreeMap<String, toml::Value>,
) -> Result<VsockDevice, anyhow::Error> {
opt_deser(opts)
}
}

// Try to turn unmatched flattened options into a config struct
fn opt_deser<'de, T: Deserialize<'de>>(
value: &BTreeMap<String, toml::Value>,
Expand Down
12 changes: 12 additions & 0 deletions bin/propolis-standalone/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1319,6 +1319,18 @@ fn setup_instance(
guard.inventory.register(&pvpanic);
}
}
"pci-virtio-vsock" => {
let config = config::VsockDevice::from_opts(&dev.options)?;
let bdf = bdf.unwrap();
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

throw in an error message here if no bdf is specified?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Okay if we leave it as is? The rest of standalone has this pattern which is why I copied/pasted it.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

👍 it's the thunderdome after all

let vsock = hw::virtio::PciVirtioSock::new(
512,
config.guest_cid,
log.new(slog::o!("dev" => "vsock")),
config.port_mappings,
);
guard.inventory.register(&vsock);
chipset_pci_attach(bdf, vsock);
}
_ => {
slog::error!(log, "unrecognized driver {driver}"; "name" => name);
return Err(Error::new(
Expand Down
2 changes: 2 additions & 0 deletions lib/propolis/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,8 @@ crucible = { workspace = true, optional = true }
oximeter = { workspace = true, optional = true }
nexus-client = { workspace = true, optional = true }
async-trait.workspace = true
iddqd.workspace = true
nix.workspace = true

# falcon
libloading = { workspace = true, optional = true }
Expand Down
7 changes: 7 additions & 0 deletions lib/propolis/src/hw/virtio/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,10 @@ mod queue;
#[cfg(feature = "falcon")]
pub mod softnpu;
pub mod viona;
pub mod vsock;

#[cfg(test)]
pub mod testutil;

use crate::common::RWOp;
use crate::hw::pci as pci_hw;
Expand All @@ -29,6 +33,7 @@ use queue::VirtQueue;

pub use block::PciVirtioBlock;
pub use viona::PciVirtioViona;
pub use vsock::PciVirtioSock;

bitflags! {
pub struct LegacyFeatures: u64 {
Expand Down Expand Up @@ -165,6 +170,7 @@ impl DeviceId {
match self {
Self::Network => Ok(pci_hw::bits::CLASS_NETWORK),
Self::Block | Self::NineP => Ok(pci_hw::bits::CLASS_STORAGE),
Self::Socket => Ok(pci_hw::bits::CLASS_UNCLASSIFIED),
_ => Err(self),
}
}
Expand Down Expand Up @@ -228,6 +234,7 @@ pub trait VirtioIntr: Send + 'static {
fn read(&self) -> VqIntr;
}

#[derive(Debug)]
pub enum VqChange {
/// Underlying virtio device has been reset
Reset,
Expand Down
2 changes: 1 addition & 1 deletion lib/propolis/src/hw/virtio/queue.rs
Original file line number Diff line number Diff line change
Expand Up @@ -94,7 +94,7 @@ impl VqAvail {
}
if let Some(idx) = mem.read::<u16>(self.gpa_idx) {
let ndesc = Wrapping(*idx) - self.cur_avail_idx;
if ndesc.0 != 0 && ndesc.0 < rsize {
if ndesc.0 != 0 && ndesc.0 <= rsize {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

is this a fix for a previous existing bug?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yup, turns out if you ask for n descriptors and the guest gives you them you should do the right thing!

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

whoops!

let avail_idx = self.cur_avail_idx.0 & (rsize - 1);
self.cur_avail_idx += Wrapping(1);

Expand Down
Loading
Loading