Commit Graph

2143 Commits

Author SHA1 Message Date
Philipp Schuster
8d11bf7979 vmm: Error for DeviceManagerError
The DeviceManagerError type is among the types missing the Error trait
so far. To streamline the code and to simplify usage on higher levels
of this error type, this type now implements Display and Error.

As not all variant values are Error yet, `#[source]` is not everywhere
where it could be. This is done in the next commits.

The high level goal is: Enable future work to improve the error output
of cloud hypervisor.

Signed-off-by: Philipp Schuster <philipp.schuster@cyberus-technology.de>
On-behalf-of: SAP philipp.schuster@sap.com
2025-05-16 11:42:01 +00:00
Philipp Schuster
05968f5c2c block: introduce advisory locks for disk image files
# What

This commit introduces file-based advisory locking for the files backing
up the block devices by using the fcntl() syscall with OFD locks. The
per-open-file-descriptor (OFD) locks are more robust than traditional
POSIX locks (F_SETLK) as they are not tied to process IDs and avoid
common issues in multithreaded or multi-fd scenarios [1]. Therefore,
we don't use `std::fs::File::try_lock()`, which is backed by F_SETLKW.

The locking mechanism is aware of the `readonly` property and allows
`n` readers or `1` writer (exclusive mode).

As the locks are advisory, multiple cloud-hypervisor processes can
prevent themselves from writing to the same file. However, this is not
a system-wide file-system level locking mechanism preventing to open()
a file.

The introduced new locking mechanism does not cover vhost-user devices.

# Why

To prevent misconfiguration and improve safety, it is good practice to
protect disk image files with a locking mechanism. Experience and common
best practices suggest that advisory locks are preferable over mandatory
locks due to better compatibility and fewer pitfalls (in fs space).

The introduced functionality is aligned with the approach taken by
QEMU [0], and is also recommended in [1].

# Implementation Details

We need to ensure that not only normal operation keeps working but also
state save/resume and live-migration. Especially for live migration,
it is crucial that the sender VMM releases the locks when the VM stops
so the receiver VMM can acquire them right after that.

Therefore, the locking and releasing happen directly on the block
device struct. The device manager knows all block devices and can
forward requests to these types.

Last but not least, this commit uses on explicit lock acquiring
but implicit lock releasing (FD close). It only explicitly releases
the locks where this integrates more smoothly into the existing
code.

# Testing

I tested
- normal operation
- state save/resume,
- device hot plugging,
- and live-migration
with read/shared and write/exclusive locks.

One can use the `fcntl-tool` to test if locks are actually acquired
or released [2].

# Links

[0] 825b96dbce/util/osdep.c (L266)
[1] https://apenwarr.ca/log/20101213
[2] https://crates.io/crates/fcntl-tool

Signed-off-by: Philipp Schuster <philipp.schuster@cyberus-technology.de>
On-behalf-of: SAP philipp.schuster@sap.com
2025-05-16 08:07:32 +00:00
Philipp Schuster
a23d4b7cf2 block: fixing typo, increase clarity
Signed-off-by: Philipp Schuster <philipp.schuster@cyberus-technology.de>
On-behalf-of: SAP philipp.schuster@sap.com
2025-05-16 08:07:32 +00:00
Bo Chen
596d6453c5 vmm: Allow 'VFIO_IOMMU_MAP_DMA' ioctl from the vcpu worker thread
Signed-off-by: Bo Chen <bchen@crusoe.ai>
2025-05-15 20:11:48 +00:00
Bo Chen
10ee003d66 misc: Fix beta clippy issues
Fixing the following clippy issue using `cargo clippy --fix`:

error: variables can be used directly in the `format!` string
  --> build.rs:25:27
   |
25 |         version.push_str(&format!("-{}", extra_version));
   |                           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
   |
   = help: for further information visit https://rust-lang.github.io/rust-clippy/master/index.html#uninlined_format_args

Signed-off-by: Bo Chen <bchen@crusoe.ai>
2025-05-14 03:44:12 +00:00
Jinank Jain
034aa514d7 vmm: Unify address space allocation
It seems like address allocation has been spread into different files
and different location for x86 vs ARM. This makes it hard to follow the
code. Thus, unify it a single location which satisfies all the
requirement.

Signed-off-by: Jinank Jain <jinankjain@microsoft.com>
2025-05-09 16:06:12 +00:00
Jinank Jain
4e48f429eb vmm: Unify loading of payload for IGVM and non-IGVM
It just simplifies code and improves the code read-ability without much
affecting the boot performance.

Signed-off-by: Jinank Jain <jinankjain@microsoft.com>
2025-05-09 16:06:12 +00:00
Jinank Jain
50b0493371 vmm: Move vm init after interrupt controller init
This will satisfy the requirement of MSHV i.e., setting the GICD base
address before initializing the VM.

Signed-off-by: Jinank Jain <jinankjain@microsoft.com>
2025-05-09 16:06:12 +00:00
Jinank Jain
df418a2153 vmm: Split device creation from interrupt controller creation
For MSHV guests, we would need interrupt controller to be initialized
before the VM gets initialized. This is because we are registering the
base address of GIC distributor with MSHV as part of interrupt
controller initialization workflow. And MSHV mandates that this property
is set before we initialize the VM.

Signed-off-by: Jinank Jain <jinankjain@microsoft.com>
2025-05-09 16:06:12 +00:00
Jinank Jain
691fe0ca68 hypervisor: arch: Move PMU IRQ definition from arch to hypervisor crate
Since this would be used in other places inside the hypervisor and
hypervisor crate cannot take a dependency on arch crate, as that creates
cyclic dependency.

Signed-off-by: Jinank Jain <jinankjain@microsoft.com>
2025-05-09 16:06:12 +00:00
Jinank Jain
f16d45e86e build: Bump mshv crates from 0.4.0 to 0.5.0
Along with also bump the vfio-bindings crates to use the latest
mshv-bindings.

There is a breaking change in the new mshv crate which requires an
additional step to initialize vm after creating it.

Signed-off-by: Jinank Jain <jinankjain@microsoft.com>
2025-05-05 17:42:30 +00:00
Jinank Jain
fa2b5ca12b vmm: hypervisor: Add a new interface to setup GICR for vcpus
For MSHV arm64 guest, there is an in-hypervisor GICv2M emulation and for
that to work, it needs to be enlightened with the base address of GIC
redistributor exposed to guest via FDT.

Signed-off-by: Jinank Jain <jinankjain@microsoft.com>
2025-05-05 09:57:21 +00:00
Jinank Jain
58f71b0c44 hypervisor: arch: Move common regs from arch to hypervisor crate
There are other potential users of these registers definitions in the
hypervisor crate. And hypervisor crate cannot use definitions from arch
crate because it creates cyclic dependency.

Signed-off-by: Jinank Jain <jinankjain@microsoft.com>
2025-04-30 06:11:26 +00:00
Fabiano Fidêncio
d0225fe68f vmm: api: Be more specific on "Still pending remove vcpu" errors
Although the CPU manager gives us a quite descriptive error, on the
application side (the part calling Cloud Hypervisor) we have absolutely
no way to distinguish such error from any other error that may happen
when resizing a VM.

With this in mind, let's be more specific and return a TooManyRequests
(429) error, allowing the caller to have a chance to decide whether they
want to retry the operation or not.

https://datatracker.ietf.org/doc/html/rfc6585#section-4

Signed-off-by: Fabiano Fidêncio <fidencio@northflank.com>
2025-04-28 16:24:10 +00:00
Jinank Jain
1105243aca vmm: Guard KVM specific unit test with feature guard
Some tests are specifically designed for KVM hypervisor platform. Thus,
guard them using appropriate feature flags.

Signed-off-by: Jinank Jain <jinankjain@microsoft.com>
2025-04-16 03:36:12 +00:00
Ruoqing He
af28569611 build: Bump zerocopy and acpi_tables
Manually bump zerocopy to 0.8.24 since our dependabot could not perform
the upgrade properly.

Manually bump acpi_tabls as well since it's depending on zerocopy.

Signed-off-by: Ruoqing He <heruoqing@iscas.ac.cn>
2025-04-13 08:06:11 +00:00
Bo Chen
0e3733e938 vmm: openapi: Remove path as required for DiskConfig
This aligns with our CLI syntax. The correctness of `DiskConfig` will be
ensured via `VmConfig::validate()`, e.g. `path` and `socket` are
mutually exclusive.

Fixes: #7016

Signed-off-by: Bo Chen <bchen@crusoe.ai>
2025-04-09 16:03:12 +00:00
Jinank Jain
ea4693a091 misc: Fix clippy error from beta compiler
Rust has a new way of constructing other error and clippy complains if
we are still using the older way to construct error message. Thus,
migrate to the new approach suggested by the clippy.

Warning from beta compiler:

error: this can be `std::io::Error::other(_)`
--> block/src/vhdx/mod.rs:142:17
 |
 | /                 std::io::Error::new(
 | |                     std::io::ErrorKind::Other,
 | |                     format!("Failed to update VHDx header: {e}"),
 | |                 )
 | |_________________^
 |
 = help: for further information visit
https://rust-lang.github.io/rust-clippy/master/index.html#io_other_error
help: use `std::io::Error::other`

                 std::io::Error::other(
                     format!("Failed to update VHDx header: {e}"),

Signed-off-by: Jinank Jain <jinankjain@microsoft.com>
2025-04-03 13:11:49 +00:00
Jinrong Liang
9d93df4c8f vm-migration: Optimize downtime by moving stop_dirty_log()
The larger the VM memory, the greater the memory pressure, and the
greater the stop_dirty_log() overhead. Moving stop_dirty_log() outside
the downtime period can reduce downtime.

Signed-off-by: Jinrong Liang <cloudliang@tencent.com>
2025-03-27 21:08:33 +00:00
Jinrong Liang
4c27572b87 vm-migration: Avoid stop_dirty_log() during local migration
Starting and stopping logging dirty pages only occurs during cross-host
migrations.

Signed-off-by: Jinrong Liang <cloudliang@tencent.com>
2025-03-27 21:08:33 +00:00
Jinank Jain
3081d01fc3 vmm: Fix compilation on aarch64 MSHV
Certain MSHV ioctls are only available on x86 architecture. Thus,
conditionally compile seccomp filter for x86 and in general enable
seccomp filters when compiling for MSHV on aarch64.

Signed-off-by: Jinank Jain <jinankjain@microsoft.com>
2025-03-21 03:50:59 +00:00
Andrew Consroe
a38b4c7f17 vmm: tighten landlock rule for PmemConfig
when discard_writes is true, only grant read access in landlock

Signed-off-by: Andrew Consroe <aconz2@gmail.com>
2025-03-20 01:58:10 +00:00
Ruoqing He
c99660a8f9 vmm: Introduce riscv64 architecture support
Integrate all works done previously to enable booting riscv linux on
riscv platforms, example command:

```console
./target/debug/cloud-hypervisor \
        --kernel path/to/kernel \
        --disk path=path/to/disk \
        --cmdline "console=hvc0 root=/dev/vda rw" \
        --cpus boot=1 \
        --memory size=1024M \
        --seccomp false
```

Signed-off-by: Ruoqing He <heruoqing@iscas.ac.cn>
2025-03-14 17:00:57 +00:00
Anatol Belski
524f26abef vmm: api: Expose SEV-SNP and igvm related options
This involves the platform  and VM config.

Signed-off-by: Anatol Belski <anbelski@linux.microsoft.com>
2025-03-11 17:22:20 +00:00
Bo Chen
297b41d615 pci, vmm: vfio: Report device path on host with DMA map/unmap errors
In addition to the BDF information on the guest, reporting the device
path of the VFIO device on the host is more useful when it comes to
debug DMA map/unmap errors particularly ones caused by failing hardware
on the host.

Signed-off-by: Bo Chen <bchen@crusoe.ai>
2025-03-08 10:00:34 +00:00
Ruoqing He
35aaa1333a misc: Fix clippy - more concise repeat().take()
Reported by 1.86.0-beta.1 (f0cb41030 2025-02-17).

Signed-off-by: Ruoqing He <heruoqing@iscas.ac.cn>
2025-03-07 15:09:14 +00:00
Stefan Kober
03bb59db69 seccomp: Allow clock_gettime() on http api thread
Signed-off-by: Stefan Kober <stefan.kober@cyberus-technology.de>
2025-03-05 15:35:37 +00:00
Jinank Jain
171b28ce52 hypervisor, vmm: Avoid leaking hypervisor specific data structure
Currently a bunch of KVM specific interfaces are leaked into the vmm
crate which should ideally does not contain any hypervisor specific data
structures.

Signed-off-by: Jinank Jain <jinankjain@microsoft.com>
2025-02-12 23:08:43 +00:00
Jinank Jain
5b929cb277 hypervisor: Implement hypervisor agnostic variant of VcpuInit
This will help in fixing the build issue for MSHV on ARM64.

Signed-off-by: Jinank Jain <jinankjain@microsoft.com>
2025-02-12 23:08:43 +00:00
Nikolay Edigaryev
27fda753e1 virtio-devices: iommu: allow limiting maximum address width in bits
Currently, Cloud Hypervisor does not set a VIRTIO_IOMMU_F_INPUT_RANGE
feature bit for the VirtIO IOMMU device, which, according to spec[1],
means that the guest may use the whole 64-bit address space is for
IOMMU purposes:

>If the feature is not offered, virtual mappings span over the whole
>64-bit address space (start = 0, end = 0xffffffff ffffffff)

As far as I am aware, there are currently no host platforms on
the market capable of addressing the whole 64-bit address space.

For example, I am currently working with a host platform that reports
39-bit address space for IOMMU purposes:

>DMAR: Host address width 39

When running a VFIO pass-through guest on such a platform, NVIDIA
driver in guest gets DMA mapping failures when working with large data,
and this results in Cloud Hypervisor exiting with the following error:

>cloud-hypervisor: 1501.220535s: <__iommu>
>ERROR:virtio-devices/src/thread_helper.rs:53 -- Error running worker:
>HandleEvent(Failed to process request queue : ExternalMapping(Custom
>{ kind: Other, error: "failed to map memory for VFIO container, iova
>0x7fff00000000, gpa 0x24ce25000, size 0x1000: IommuDmaMap(Error(22))"
>}))

Passing "--platform iommu_address_width=39" to Cloud Hypervisor built
with this change fixes this.

[1]: https://docs.oasis-open.org/virtio/virtio/v1.3/csd01/
virtio-v1.3-csd01.html#x1-5420006

Signed-off-by: Nikolay Edigaryev <edigaryev@gmail.com>
2025-01-14 21:31:47 +00:00
Nikolay Edigaryev
74ca38f7a9 vmm: introduce platform option to limit maximum IOMMU address width
Signed-off-by: Nikolay Edigaryev <edigaryev@gmail.com>
2025-01-14 21:31:47 +00:00
Bo Chen
8f98fabd0b vmm: Cleanup VM being created when VM restore fails
When VM restore fails, the VMM state is left with some side-effects,
such as a VM being created. It would prevent the VMM from creating and
booting a new VM or restoring from a VM snapshot.

To fix this issue, this patch explicitly handles the side effects to the
VMM state when VM restore fails, e.g. clear the VmConfig and shutdown
the VM being created.

Fixes: #6869

Signed-off-by: Bo Chen <bo.arvin.chen@gmail.com>
2025-01-14 00:45:03 +00:00
Bo Chen
07821c08c0 vmm: Always re-generate the 'console_info' with VM restore
With VM restore, the VMM is always re-creating a VM based on the
restored `VmConfig`. We should always re-generate the 'console_info'
from the `Vmm` struct to stay consistent with the new VM being created.

Signed-off-by: Bo Chen <bo.arvin.chen@gmail.com>
2025-01-14 00:45:03 +00:00
Wei Liu
d99f294281 pci: rename as_any to as_any_mut
That trait function returns a mutable reference. Rename it to follow
Rust's convention.

Signed-off-by: Wei Liu <liuwe@microsoft.com>
2025-01-09 21:28:46 +00:00
Wei Liu
703e0cab04 vmm: use C ABI-qualification for packed structures
Signed-off-by: Wei Liu <liuwe@microsoft.com>
2025-01-09 13:51:42 +00:00
Rob Bradford
3e4ed5621e vmm: Automatically fix operator precedence clippy warning
Signed-off-by: Rob Bradford <rbradford@rivosinc.com>
2025-01-07 17:44:41 +00:00
Wei Liu
32482f6634 block: make available VIRTIO_BLK_F_SEG_MAX
This allows the guest to put in more than one segment per request. It
can improve the throughput of the system.

Introduce a new check to make sure the queue size configured by the user
is large enough to hold at least one segment.

Signed-off-by: Wei Liu <liuwe@microsoft.com>
2025-01-01 18:50:39 +00:00
Jinrong Liang
909e1bc3f0 vmm: Add support for cross-host live migration over TCP
Add support for cross-host live migration over TCP, which
significantly improves performance in cross-host live migration
scenarios compared to the Unix socket forwarding method.

Signed-off-by: Jinrong Liang <cloudliang@tencent.com>
2024-12-18 14:02:38 +00:00
Alyssa Ross
50bac1694f vmm: support PCI I/O regions on all architectures
While non-Intel CPU architectures don't have a special concept of IO
address space, support for PCI I/O regions is still needed to be able
to handle PCI devices that use them.

With this change, I'm able to pass through an e1000e device from QEMU
to a cloud-hypervisor VM on aarch64 and use it in the cloud-hypervisor
guest.  Previously, it would hit the unimplemented!().

Signed-off-by: Alyssa Ross <hi@alyssa.is>
2024-12-14 14:12:00 +00:00
Alyssa Ross
dd8a5a7de8 vmm: remove outdated comment
Fixes: def98faf ("vmm, vm-allocator: Introduce an allocator for platform devices")
Signed-off-by: Alyssa Ross <hi@alyssa.is>
2024-12-14 14:12:00 +00:00
Muminul Islam
149c342867 vmm: pass memory size during VM creation
Pass memory size from vmm crate to hypervisor VM
creation API so use for creating Bitmap for SEV-SNP
guest.

Signed-off-by: Muminul Islam <muislam@microsoft.com>
2024-12-12 03:32:22 +00:00
Rob Bradford
81f8a27ef6 pci: vfio: Use MemorySlotAllocator for allocating memory slots
Adapt the existing code to replace the closure with the new of the new
MemorySlotAllocator.

Signed-off-by: Rob Bradford <rbradford@rivosinc.com>
2024-11-24 10:45:15 +00:00
Rob Bradford
e3bd5e9b35 vmm: memory_manager: Adapt for new MemorySlotAllocator
Adapt the existing code to transparently the MemorySlotAllocator. The
MemoryManager is the canonical holder of the these values with them
turned into a MemoryAllocator on demand.

Signed-off-by: Rob Bradford <rbradford@rivosinc.com>
2024-11-24 10:45:15 +00:00
Wojtek Czekalski
8acaeb5c82 vmm: Add serial option to the disk config doc
Signed-off-by: Wojtek Czekalski <wczekalski@me.com>
2024-11-05 19:48:25 +00:00
Rob Bradford
7a637fe1f4 vmm: memory_manager: Use div_ceil()
--> vmm/src/memory_manager.rs:1972:13
     |
1972 | ...   ((self.start_of_device_area.0 + SGX_PAGE_SIZE - 1) / SGX_PAGE_SIZE) * ...
     |       ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using `.div_ceil()`: `self.start_of_device_area.0.div_ceil(SGX_PAGE_SIZE)`
     |
     = help: for further information visit https://rust-lang.github.io/rust-clippy/master/index.html#manual_div_ceil
     = note: `#[warn(clippy::manual_div_ceil)]` on by default

Signed-off-by: Rob Bradford <rbradford@rivosinc.com>
2024-10-21 15:28:17 +00:00
Ruoqing He
0aab960bf1 misc: Elide needless lifetimes
As clippy of rust-toolchain version 1.83.0-beta.1 suggests, elide
needless lifetimes to `'_`.

Signed-off-by: Ruoqing He <heruoqing@iscas.ac.cn>
2024-10-18 17:46:39 +00:00
Ruoqing He
6164aa0885 misc: Replace div_round_up operation with div_ceil
As clippy of rust-toolchain version 1.83.0-beta.1 suggests, replace
manually implemented `div_round_up!` and the like with `div_ceil` from
std.

Signed-off-by: Ruoqing He <heruoqing@iscas.ac.cn>
2024-10-18 17:46:39 +00:00
Alexandru Matei
c891dcb947 vmm: drop device_tree mutex before acquiring pci_bus mutex
AddressManager::move_bar() acquires the device_tree mutex.
The function is called from PciConfigIo::config_space_write()/
PciConfigMmio::config_space_write() while the pci_bus mutex
is acquired.
The functions DeviceManager::pci_resources()/eject_device()
acquire these mutexes in reverse order, which leads to a deadlock.

Fixes: #6775

Signed-off-by: Alexandru Matei <alexandru.matei@uipath.com>
2024-10-03 12:04:00 +00:00
Ruoqing He
297236a7c0 misc: Eliminate use of assert!((...).is_ok())
Asserting on .is_ok()/.is_err() leads to hard to debug failures (as if
the test fails, it will only say "assertion failed: false". We replace
these with `.unwrap()`, which also prints the exact error variant that
was unexpectedly encountered (we can to this these days thanks to
efforts to implement Display and Debug for our error types). If the
assert!((...).is_ok()) was followed by an .unwrap() anyway, we just drop
the assert.

Inspired by and quoted from @roypat.

Signed-off-by: Ruoqing He <heruoqing@iscas.ac.cn>
2024-10-03 12:03:49 +00:00
Rob Bradford
d1c9002c48 vmm: cpu: Fix aarch64 unit test
This fixes commit 2668dbbd8b which changed
the error message.

Signed-off-by: Rob Bradford <rbradford@rivosinc.com>
2024-10-02 14:50:39 +00:00