-
Notifications
You must be signed in to change notification settings - Fork 13.6k
Open
Labels
C-enhancementCategory: An issue proposing an enhancement or a PR with one.Category: An issue proposing an enhancement or a PR with one.NLL-completeWorking towards the "valid code works" goalWorking towards the "valid code works" goal
Description
The code below doesn't compile due to multiple mutable borrows, however the exact same code without the std::pin::Pin
compiles fine actually. My expectation is however that the code would obviously compile fine in both cases.
use std::pin::Pin;
use slab;
struct Entry {
complete: u64
}
struct Ctx {}
impl Ctx {
fn new() -> Self {
Ctx{}
}
fn pread<T>(&mut self, _key: T) -> std::io::Result<()> {
Ok(())
}
}
struct Foo {
ctx: Ctx,
handles: slab::Slab<Entry>
}
impl Foo {
fn new() -> Self {
Foo {ctx: Ctx::new(),
handles: slab::Slab::with_capacity(20)}
}
fn blah(mut self: Pin<&mut Self>) {
let v = self.handles.vacant_entry();
let key = v.key();
match self.ctx.pread(key) {
Ok(()) => {
v.insert(Entry{complete:123});
},
Err(_) => {
}
}
}
}
fn main() {
Pin::new(&mut Foo::new()).blah();
}
The exception raised is:
error[E0499]: cannot borrow `self` as mutable more than once at a time
--> src/main.rs:31:15
|
29 | let v = self.handles.vacant_entry();
| ---- first mutable borrow occurs here
30 | let key = v.key();
31 | match self.ctx.pread(key) {
| ^^^^ second mutable borrow occurs here
32 | Ok(()) => {
33 | v.insert(Entry{complete:123});
| - first borrow later used here
error: aborting due to previous error
I'm able to get the code to compile also by creating additional scopes around the areas where I'm supposedly borrowing self
like this:
let key = {
let entry = self.handles.vacant_entry();
entry.key()
};
match self.ctx.pread(key) {
Ok(()) => {
*self.handles.get_mut(key).unwrap() =
Entry { complete: 123 };
}
Although obviously that's pretty awkward. I'm told that this could possibly be a bug in the NLL, but I'm pretty new to the language so I'm just reporting this with a short reproducible example.
Hope it helps.
Metadata
Metadata
Assignees
Labels
C-enhancementCategory: An issue proposing an enhancement or a PR with one.Category: An issue proposing an enhancement or a PR with one.NLL-completeWorking towards the "valid code works" goalWorking towards the "valid code works" goal