Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix soundness issues via KvmRunWrapper::as_mut_ref() #255

Merged
merged 3 commits into from
Mar 4, 2024

Conversation

00xc
Copy link
Contributor

@00xc 00xc commented Feb 13, 2024

Summary of the PR

As detailed in #248, and since KvmRunWrapper implements Send and Sync, as_mut_ref() can cause undefined behavior, as two threads can acquire a mutable reference to the kvm_run struct via an immutable reference to KvmRunWrapper.

Fix this by making KvmRunWrapper::as_mut_ref() take &mut self, which also gets rid of a clippy warning suppression, and update the callers. This results in potentially breaking changes in the public interface, as several VcpuFd methods now take &mut self as well.

Fixes: #248

Requirements

Before submitting your PR, please make sure you addressed the following
requirements:

  • All commits in this PR have Signed-Off-By trailers (with
    git commit -s), and the commit message has max 60 characters for the
    summary and max 75 characters for each description line.
  • All added/changed functionality has a corresponding unit/integration
    test.
  • All added/changed public-facing functionality has entries in the "Upcoming
    Release" section of CHANGELOG.md (if no such section exists, please create one).
  • Any newly added unsafe code is properly documented.

Introduce a new method to get an immutable reference to the kvm_run
struct. Replace uses of `as_mut_ref()` with `as_ref()` where possible

Signed-off-by: Carlos López <[email protected]>
CHANGELOG.md Outdated Show resolved Hide resolved
Since KvmRunWrapper implements Send and Sync, this method can cause
undefined behavior, as two threads can acquire a mutable reference to
the kvm_run struct via an immutable reference to KvmRunWrapper.

Fix this by making KvmRunWrapper::as_mut_ref() take &mut self, which
also gets rid of a clippy warning suppression, and update the
callers. This results in potentially breaking changes in the public
interface, as several VcpuFd methods now take &mut self as well.

Fixes: rust-vmm#248
Signed-off-by: Carlos López <[email protected]>
Copy link
Collaborator

@roypat roypat left a comment

Choose a reason for hiding this comment

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

Thanks for fixing this :)

@00xc
Copy link
Contributor Author

00xc commented Feb 28, 2024

Ping for the remaining reviewers.

@JonathanWoollett-Light
Copy link

JonathanWoollett-Light commented Feb 28, 2024

This is a breaking change so it would be good to check if anyone has any other concerns, otherwise LGTM. I've messaged in the rust-vmm public slack, if there are no concerns after some time I will approve.

@00xc
Copy link
Contributor Author

00xc commented Feb 29, 2024

Perhaps there should be a security advisory for this. Producing undefined behavior is pretty simple:

let vcpu = ...;

// Suppose this is a VcpuExit that contains an immutable
// reference to kvm_run, e.g. IoOut, MmioWrite
let exit = vcpu.run().unwrap();

// Suppose this is a VcpuExit of the same type as above.
// This modifies kvm_run again.
vcpu.run().unwrap();

// The value `exit` immutably references has been modified,
// yet the compiler does not complain because `run()` takes
// `&self`. Using `exit` here is UB.
println!("{:?}", exit);

Another way to think about it is that mutable accesses must invalidate all previous immutable references.

@roypat roypat merged commit 8be04f6 into rust-vmm:main Mar 4, 2024
19 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

VcpuFd::set_kvm_immediate_exit may lead to data races/undefined behavior
4 participants