Skip to content

rustc (>= 1.20.0) fails to optimize moves in trivial cases #63631

Open
@resilar

Description

@resilar

The example code below generates extra stack copies of String (meta)data in function got() which is expected to produce identical optimized code with expect(). For quickly verifying the issue, compare sub rsp, $FRAME_SIZE instructions which initialize stack frames in the beginning of got() & expect() functions compiled with -C opt-level=3 (or measure & compare the generated code sizes). Rust Playground link.

rustc versions before 1.20.0 produce expected optimized assembly.

pub fn got() -> String {
    let mut res = String::new();
    let s0 = String::from("foobar");
    res.push_str(&s0); let s0 = s0;
    res.push_str(&s0); let s0 = s0;
    res.push_str(&s0); let s0 = s0;
    res.push_str(&s0);
    res
}

pub fn expect() -> String {
    let mut res = String::new();
    let s0 = String::from("foobar");
    res.push_str(&s0);
    res.push_str(&s0);
    res.push_str(&s0);
    res.push_str(&s0);
    res
}

/*
 * s0: String required, s0: &str generates correctly optimized assembly
 * res.push_str(...) line repetitions can be increased for a greater effect
 * let s0 = s0 used for illustration purposes (variable names do not matter)
 */

Metadata

Metadata

Assignees

No one assigned

    Labels

    A-LLVMArea: Code generation parts specific to LLVM. Both correctness bugs and optimization-related issues.C-enhancementCategory: An issue proposing an enhancement or a PR with one.C-optimizationCategory: An issue highlighting optimization opportunities or PRs implementing suchI-slowIssue: Problems and improvements with respect to performance of generated code.T-compilerRelevant to the compiler team, which will review and decide on the PR/issue.

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions