llvm / llvm-project

The LLVM Project is a collection of modular and reusable compiler and toolchain technologies.
http://llvm.org
Other
28.62k stars 11.83k forks source link

Invalid defs/uses of the FPSW register after register allocation #26765

Closed DimitryAndric closed 5 years ago

DimitryAndric commented 8 years ago
Bugzilla Link 26391
Resolution FIXED
Resolved on Mar 12, 2019 14:35
Version trunk
OS All
Depends On llvm/llvm-project#22277
CC @topperc,@majnemer,@RKSimon,@MatzeB,@qcolombet,@rotateright

Extended Description

+++ This bug was initially created as a clone of Bug #​21903 +++

According to Matthias Braun, this test case is probably exposing a slightly different problem with the internal representation. Minimized C++ test case:

int x0, x1, x2; double x3, x4; int x5(double x6, double x7) { if (x4 && x6 < x7) x0 = 1; else x0 = 0; return x0; } void x8(double x6, double x7, bool &x9, double x10, double x11) { if (x2 == 0) x9 = 0; if (x2 == 1 && x5(x1, 0) && x5(x6, 0) && x5(x7, x11)) x9 = 1; if (x2 == 6) x9 = 0; if (x2 == 7 && x5(x1, x3) && x5(x6, x10) && x5(x7, x11)) x9 = 1; }

Reproduce with: clang -cc1 -triple i386 -emit-obj -target-cpu i686 -O2 -w testcase.cpp

Resulting in:

Bad machine code: MBB exits via conditional branch/fall-through but the CFG successors don't match the actual successors!

Bad machine code: Using an undefined physical register

Bad machine code: Using an undefined physical register

Bad machine code: Using an undefined physical register

Further reduced to .ll form by David Majnemer, to:

target datalayout = "e-m:e-p:32:32-f64:32:64-f80:32-n8:16:32-S128" target triple = "i686--linux-gnu"

define void @​f(double %p1, double %p2, double %p3, double %p4, i32 %p5, i8* %p6, double %p7, double %p8, double %p9) align 2 { entry: %cmp.i54 = fcmp olt double %p2, %p8 %tobool.i45 = fcmp une double %p4, 0.000000e+00 switch i32 %p5, label %if.end20 [ i32 0, label %if.then10 i32 1, label %land.lhs.true i32 2, label %if.then10 i32 4, label %land.lhs.true13 ]

land.lhs.true: ; preds = %entry br i1 undef, label %land.lhs.true3, label %if.end20

land.lhs.true3: ; preds = %land.lhs.true15, %land.lhs.true br i1 %cmp.i54, label %land.lhs.true5, label %if.end20

land.lhs.true5: ; preds = %land.lhs.true3 %cmp.i50 = fcmp olt double %p3, %p9 br i1 %cmp.i50, label %if.then10, label %if.end20

if.then10: ; preds = %land.lhs.true5, %entry, %entry store i8 1, i8* %p6, align 1 br label %if.end20

land.lhs.true13: ; preds = %entry %cmp.i46 = fcmp olt double %p1, %p7 %or.cond.i47 = and i1 %tobool.i45, %cmp.i46 %storemerge.i48 = zext i1 %or.cond.i47 to i32 br i1 %or.cond.i47, label %land.lhs.true15, label %if.end20

land.lhs.true15: ; preds = %land.lhs.true13 %storemerge.i44 = zext i1 %cmp.i54 to i32 br label %land.lhs.true3

if.end20: ; preds = %land.lhs.true13, %if.then10, %land.lhs.true5, %land.lhs.true3, %land.lhs.true, %entry ret void }

DimitryAndric commented 5 years ago

Finally fixed by http://reviews.llvm.org/rL317133 ("[X86] Add CMOV feature to 'i686' processor, making it a proper alias of pentiumpro which I believe it should be")

DimitryAndric commented 8 years ago

An interesting data point is that r253965 ([1], "Let SelectionDAG start to use probability-based interface to add successors") appears to have introduced (or exacerbated) this particular instance of invalid defs/uses.

Cong, any idea whether your changes have only exposed this issue, or is something else wrong?

[1] http://llvm.org/viewvc/llvm-project?view=revision&revision=253965