Email me

Rust errors / Ownership and borrowing

Rust compiler error · checked with rustc 1.99.0

Rust error E0509: cannot move out of type `DropStruct`, which implements the `Drop` trait

What it meansThis error occurs when an attempt is made to move out of a value whose type implements the Drop trait.

What rustc prints

error[E0509]: cannot move out of type `DropStruct`, which implements the `Drop` trait
  --> main.rs:17:23
   |
17 |     let fancy_field = drop_struct.fancy; // Error E0509
   |                       ^^^^^^^^^^^^^^^^^
   |                       |
   |                       cannot move out of here
   |                       move occurs because `drop_struct.fancy` has type `FancyNum`, which does not implement the `Copy` trait
   |
note: if `FancyNum` implemented `Clone`, you could clone the value
  --> main.rs:1:1
   |
 1 | struct FancyNum {
   | ^^^^^^^^^^^^^^^ consider implementing `Clone` for this type
...
17 |     let fancy_field = drop_struct.fancy; // Error E0509
   |                       ----------------- you could clone this value
help: consider borrowing here
   |
17 |     let fancy_field = &drop_struct.fancy; // Error E0509
   |                       +

Real output of rustc 1.99.0 compiling the official example below (2021 edition). Your names and line numbers will differ; the first line is the part to match.

E0509Ownership and borrowing
Activein rustc 1.99.0
8related errors linked below

The compiler team's explanation

This error occurs when an attempt is made to move out of a value whose type implements the Drop trait.

Erroneous code example:

struct FancyNum {
    num: usize
}

struct DropStruct {
    fancy: FancyNum
}

impl Drop for DropStruct {
    fn drop(&mut self) {
        // Destruct DropStruct, possibly using FancyNum
    }
}

fn main() {
    let drop_struct = DropStruct{fancy: FancyNum{num: 5}};
    let fancy_field = drop_struct.fancy; // Error E0509
    println!("Fancy: {}", fancy_field.num);
    // implicit call to `drop_struct.drop()` as drop_struct goes out of scope
}

Here, we tried to move a field out of a struct of type DropStruct which implements the Drop trait. However, a struct cannot be dropped if one or more of its fields have been moved.

Structs implementing the Drop trait have an implicit destructor that gets called when they go out of scope. This destructor may use the fields of the struct, so moving out of the struct could make it impossible to run the destructor. Therefore, we must think of all values whose type implements the Drop trait as single units whose fields cannot be moved.

This error can be fixed by creating a reference to the fields of a struct, enum, or tuple using the ref keyword:

struct FancyNum {
    num: usize
}

struct DropStruct {
    fancy: FancyNum
}

impl Drop for DropStruct {
    fn drop(&mut self) {
        // Destruct DropStruct, possibly using FancyNum
    }
}

fn main() {
    let drop_struct = DropStruct{fancy: FancyNum{num: 5}};
    let ref fancy_field = drop_struct.fancy; // No more errors!
    println!("Fancy: {}", fancy_field.num);
    // implicit call to `drop_struct.drop()` as drop_struct goes out of scope
}

Note that this technique can also be used in the arms of a match expression:

struct FancyNum {
    num: usize
}

enum DropEnum {
    Fancy(FancyNum)
}

impl Drop for DropEnum {
    fn drop(&mut self) {
        // Destruct DropEnum, possibly using FancyNum
    }
}

fn main() {
    // Creates and enum of type `DropEnum`, which implements `Drop`
    let drop_enum = DropEnum::Fancy(FancyNum{num: 10});
    match drop_enum {
        // Creates a reference to the inside of `DropEnum::Fancy`
        DropEnum::Fancy(ref fancy_field) => // No error!
            println!("It was fancy-- {}!", fancy_field.num),
    }
    // implicit call to `drop_enum.drop()` as drop_enum goes out of scope
}

From rustc --explain E0509 (1.99.0), part of the Rust project, MIT or Apache-2.0. Official page.

Related errors

All 518 Rust error codes · Rust crate data · Glossary

Up next

Often hit nextE0382: borrow of moved valueA related error from the same family.Read it next →

Did this answer your question?

Get the receipts by email.

What my AI agents tried this week, with the real numbers: what worked, what flopped, what made money. One email when there is something worth reading.

No spam, never sold. Every email has a one-click unsubscribe.

Popular in the shop

All 124 tools →

Browse: Bundles and kitsHome, family and schoolMoney and businessAI toolsSports and fitnessMaking and hobbiesFood and drinkIndie dev and launchTrading and quant

Free: Landing page teardown iPhone app cost calculator LLM API cost calculator Paid online: $49 Launch Check App builds Articles FAQ