Skip to content

Replace one of the examples of the aliasing rule #2715

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

Open
wants to merge 4 commits into
base: main
Choose a base branch
from
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
48 changes: 40 additions & 8 deletions src/borrowing/examples.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,21 +17,53 @@ fn main() {
}
```

Similarly, consider the case of iterator invalidation:
We can also look at a case where these rules prevent incorrect optimizations:

```rust,editable,compile_fail
fn swap_and_increment(a: &mut i32, b: &mut i32) {
*a = *a + 1;

let tmp = *a;
*a = *b;
*b = tmp;

*b = *a + 1;
}

fn main() {
let mut vec = vec![1, 2, 3, 4, 5];
for elem in &vec {
vec.push(elem * 2);
}
let mut x = 1;
swap_and_increment(&mut x, &mut x);
}
```

<details>

- In both of these cases, modifying the collection by pushing new elements into
it can potentially invalidate existing references to the collection's elements
if the collection has to reallocate.
- In the first case, modifying the collection by pushing new elements into it
can potentially invalidate existing references to the collection's elements if
the collection has to reallocate.

- In the second case, the aliasing rule prevents mis-compilation: In the C
equivalent of this function, the program produces different results when
compiled with optimizations enabled.

- Show students [the C version of this on Godbolt][unoptimized]. By default,
with no optimizations enabled it will print `x = 3`. But
[enabling optimizations][optimized] causes it to instead print `x = 2`.

- Note the use of the `restrict` keyword in the C example. This tells the
compiler that `a` and `b` cannot alias, but nothing prevents you from
violating that requirement. The compiler will silently produce the wrong
behavior.

- In the Rust version, using `&mut` automatically implies the same
restriction, and the compiler statically prevents violations of this
requirement.

- Rust's aliasing rules provide strong guarantees about how references can
alias, allowing the compiler to apply optimizations without breaking the
semantics of your program.

</details>

[unoptimized]: https://godbolt.org/z/9EGh6eMxE
[optimized]: https://godbolt.org/z/Kxsf8sahT