Why is this an issue?

In Rust, calling Vec::set_len(new_len) directly after allocating or reserving memory using Vec::with_capacity(), Vec::new(), Vec::default(), or Vec::reserve() can lead to the creation of a Vec with uninitialized elements. This is problematic because most safe Rust operations assume initialized data. Using uninitialized data can result in undefined behavior, including memory corruption and unexpected program crashes.

This rule detects instances where Vec::set_len() is called directly after allocating or reserving memory with Vec::with_capacity(), Vec::new(), Vec::default(), or Vec::reserve(), without any prior initialization of the vector’s elements. The rule performs a local analysis and only checks for these calls within adjacent statements.

Code examples

Noncompliant code example

fn f(reader: &mut dyn std::io::Read) {
    let mut vec: Vec<u8> = Vec::with_capacity(1000);
    unsafe { vec.set_len(1000); } // Noncompliant: Uninitialized vector
    reader.read_exact(&mut vec).unwrap(); // Undefined behavior!
}

Compliant solution

fn f(reader: &mut dyn std::io::Read) {
    let mut vec: Vec<u8> = vec![0; 1000]; // Properly initialized with zeros
    reader.read_exact(&mut vec).unwrap(); // Safe to use
}

Resources

Documentation