Cannot borrow as mutable?

Why doesn't this compile? playground

struct Foo {}

fn do_something(foo:&mut Foo) {
    do_something(&mut foo);
}

I could just pass foo instead of &mut foo ... but the error message seems odd

Hello,

function cannot return without recursing

The compiler do not find an exit in your recursion. It says the function can't return and will always recurse.

yeah that's just to show the idea - a little less noisy than writing another function to show this error :slight_smile:

The type of foo is &mut Foo, but then you're adding another &mut when passing it along, creating a reference to a reference - it's easier to see with an explicit annotation:

fn do_something(foo: &mut Foo) {
    let bar: &mut &mut Foo = &mut foo;
    do_something(bar);
}

To take a mutable reference to a binding (whether that be a let binding or a function argument), it has to be defined as mut - therefore, to take a mutable reference to foo (which is itself a mutable reference!), you need to define it with the mut keyword.

fn do_something(mut foo: &mut Foo) {
    let bar: &mut &mut Foo = &mut foo;
    do_something(bar);
}

The reason you're able to pass in &mut &mut Foo into a function that takes &mut Foo is because the compiler auto-derefs in some cases.

All of that said, I think this was just a typo on your part, and what you meant to do was equivilant to:

fn do_something(foo: &mut Foo) {
    let bar: &mut Foo = foo;
    do_something(bar);
}
2 Likes

I tried to help :smiley:

1 Like

And I appreciate it! :slight_smile: