What Is New in Rust 1.51
| Category | Highlights |
|---|---|
| New Features | Const generics MVP, std::array::IntoIter, Cargo resolver = "2", split-debuginfo, ptr::addr_of! macros |
| Improvements | Faster macOS debug builds, more ergonomic feature resolution in Cargo |
How does Rust 1.51 enable const generics?
Rust 1.51 stabilizes a minimal const-generics MVP that lets you parameterize types over constant values such as integers, booleans, or chars.
In practice you can now write:
struct Array<T, const LENGTH: usize> {
list: [T; LENGTH],
}
and the compiler will monomorphise Array<u8, 32> into a concrete type with a 32-element array. This opens the door for zero-cost abstractions that depend on compile-time numbers, while still keeping the language stable.
What is the new std::array::IntoIter API and how do I use it?
Rust 1.51 adds std::array::IntoIter, a by-value iterator for arrays, allowing you to consume an array element-by-element without copying.
Example usage:
fn main() {
let arr = [1, 2, 3, 4, 5];
for item in std::array::IntoIter::new(arr) {
println!("{}", item);
}
}
Note that .into_iter() on arrays still yields a slice iterator; the new type avoids the temporary slice and is the ergonomic path forward.
How can I opt-in to Cargo's new feature resolver?
Set resolver = "2" in your Cargo.toml to enable Cargo's second-generation feature resolver.
For a single package:
[package]
resolver = "2"
Or for a workspace:
[workspace]
resolver = "2"
This resolver isolates dev-, build-, and target-specific feature sets, reducing surprising feature bleed-through in no_std or cross-compilation scenarios.
How does split-debuginfo improve macOS build times?
Rust 1.51 introduces the -Csplit-debuginfo=unpacked flag (or the equivalent Cargo profile setting) which skips the costly dsymutil step on macOS.
Configure it in Cargo:
[profile.dev]
split-debuginfo = "unpacked"
The compiler leaves the intermediate object files in the build directory, and the backtrace machinery can locate them directly, yielding faster incremental builds and lower disk usage.
What new pointer macros were stabilized in Rust 1.51?
Two macros, ptr::addr_of! and ptr::addr_of_mut!, are now stable, allowing safe creation of raw pointers to possibly unaligned fields.
Typical usage with a packed struct:
use std::ptr;
#[repr(packed)]
struct Packed {
a: u8,
b: u16,
}
let p = Packed { a: 1, b: 2 };
let raw = ptr::addr_of!(p.b);
unsafe { assert_eq!(raw.read_unaligned(), 2); }
These macros avoid the undefined behavior that arises from taking a reference to an unaligned field.
Frequently Asked Questions
Is const generics available on the stable channel after Rust 1.51?
No, the const-generics MVP is fully stable in the stable release channel.
How do I iterate over an array by value in Rust 1.51?
Use std::array::IntoIter::new(my_array) which returns an iterator that yields owned elements.
What Cargo.toml setting enables the new resolver?
Add resolver = "2" under the [package] or [workspace] section.
Will split-debuginfo affect runtime debugging on macOS?
It does not; backtrace support can still locate the .o files for accurate stack traces.
Can I use ptr::addr_of! on packed structs?
Yes, the macro lets you obtain a raw pointer to a possibly unaligned field without causing undefined behavior.