# Unsafe Code Guidelines
`unsafe` code is extremely dangerous and should be avoided unless absolutely
necessary. When it is absolutely necessary to write `unsafe` code, it should be
done extremely carefully.
This document covers guidelines for writing unsafe code, including pointer casts
and safety comments.
## Pointer Casts
- **Avoid `&slice[0] as *const T`**: Use `slice.as_ptr()`. Accessing subsequent
elements via pointer arithmetic on a single-element pointer is UB.
```rust
let slice = &[1, 2];
let ptr = &slice[0] as *const i32;
let val = unsafe { *ptr.add(1) };
let ptr = slice.as_ptr();
let val = unsafe { *ptr.add(1) };
```
- **Avoid converting `&mut T` to `*const T`**: This reborrows as a shared
reference, restricting permissions. Cast `&mut T` to `*mut T` first.
```rust
let mut val = 42;
let r = &mut val;
let ptr = r as *const i32 as *mut i32;
unsafe { *ptr = 0 };
let ptr = r as *mut i32;
unsafe { *ptr = 0 };
```
## Safety Comments
Every `unsafe` block must be documented with a `// SAFETY:` comment.
- **Requirement:** The comment must prove soundness using *only* text from the
stable [Rust Reference](https://doc.rust-lang.org/reference/) or [standard
library documentation](https://doc.rust-lang.org/std/).
- **Citation:** You must cite and quote the relevant text from the
documentation. Citations must cite a specific version of the documentation
(e.g. https://doc.rust-lang.org/1.91.0/reference/ or
https://doc.rust-lang.org/1.91.0/std/).
- **Prohibition:** Do not rely on "common sense" or behavior not guaranteed by
the docs.
```rust
let offset = unsafe { field.cast::<u8>().offset_from(ptr.cast::<u8>()) };
let offset = unsafe { field.cast::<u8>().offset_from(ptr.cast::<u8>()) };
```