I am not sure what to call this, the title is my provisional name. I think this is a reasonable feature request to borrow checker, because workaround seems mechanical to me.
Given these definitions:
struct Field;
impl Field {
fn mutate(&mut self) {}
}
struct Context {
source: Field,
destination: Field,
}
struct Packet {
context: Context,
}
This function compiles:
fn process_packet(packet: &mut Packet) {
let source = &mut packet.context.source;
let destination = &mut packet.context.destination;
source.mutate();
destination.mutate();
}
But as soon as you box Context, it doesn’t compile any more.
struct Packet {
context: Box<Context>,
}
error[E0499]: cannot borrow `packet.context` (via `packet.context.destination`) as mutable more than once at a time
--> test.rs:18:28
|
17 | let source = &mut packet.context.source;
| --------------------- first mutable borrow occurs here
18 | let destination = &mut packet.context.destination;
| ^^^^^^^^^^^^^^^^^^^^^^^^^^ second mutable borrow occurs here
This can confuse you so that you think this can’t be done. But since the following rewritten function compiles, I think rustc just should accept the code.
fn process_packet(packet: &mut Packet) {
let context = &mut *packet.context;
let source = &mut context.source;
let destination = &mut context.destination;
source.mutate();
destination.mutate();
}