Skip to content

Miscompilation with -jump-threading -correlated-propagation and llvm.assume #33264

@alexcrichton

Description

@alexcrichton
Bugzilla Link 33917
Resolution FIXED
Resolved on Jan 29, 2018 03:06
Version 5.0
OS Windows NT
Blocks #33196
CC @aelovikov-intel,@annamthomas,@chandlerc,@zmodem,@kavon,@TimNN

Extended Description

In upgrading rust-lang/rust to LLVM 5.0 we've discovered that the compiler itself will segfault when compiled with LLVM 5.0. This looks like it's a misoptimization during one of the -jump-threading -correlated-propagation passes.

We used bugpoint to shorten the program from ~1 million lines of IR to just a few:

; ModuleID = 'small.ll'
source_filename = "bugpoint-output-834ffe1.bc"
target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128"
target triple = "x86_64-unknown-linux-gnu"

declare i8* @​foo()

declare i32 @​rust_eh_personality() unnamed_addr

; Function Attrs: nounwind
declare void @​llvm.assume(i1) #​0

define void @​bar() personality i32 ()* @​rust_eh_personality {
bb9:
%t9 = invoke i8* @​foo()
to label %good unwind label %bad

bad: ; preds = %bb9
%t10 = landingpad { i8*, i32 }
cleanup
resume { i8*, i32 } %t10

good: ; preds = %bb9
%t11 = icmp ne i8* %t9, null
%t12 = zext i1 %t11 to i64
%cond = icmp eq i64 %t12, 1
br i1 %cond, label %if_true, label %done

if_true: ; preds = %good
call void @​llvm.assume(i1 %t11)
br label %done

done: ; preds = %if_true, %good
ret void
}

attributes #​0 = { nounwind }

This was tested out locally via opt -S -jump-threading -correlated-propagation foo.ll, and then the results from before/after were diffed, yielding:

--- before.ll 2017-07-24 15:52:48.364787248 -0700
+++ after.ll 2017-07-24 15:53:34.701537275 -0700
@@ -21,13 +21,12 @@
resume { i8*, i32 } %t10

good: ; preds = %bb9

  • %t11 = icmp ne i8* %t9, null
  • %t12 = zext i1 %t11 to i64
  • %t12 = zext i1 true to i64
    %cond = icmp eq i64 %t12, 1
    br i1 %cond, label %if_true, label %done

if_true: ; preds = %good

  • call void @​llvm.assume(i1 %t11)
  • call void @​llvm.assume(i1 true)
    br label %done

done: ; preds = %if_true, %good

I think that the transformation here may be invalid? The %t11 temporary is inferred to being always true but that's not always the case coming out of @foo

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugzillaIssues migrated from bugzilla

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions