Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
This patch implements Chandler's idea [0] for supporting languages that require support for infinite loops with side effects, such as Rust, providing part of a solution to bug 965 [1]. Specifically, it adds an `llvm.sideeffect()` intrinsic, which has no actual effect, but which appears to optimization passes to have obscure side effects, such that they don't optimize away loops containing it. It also teaches several optimization passes to ignore this intrinsic, so that it doesn't significantly impact optimization in most cases. As discussed on llvm-dev [2], this patch is the first of two major parts. The second part, to change LLVM's semantics to have defined behavior on infinite loops by default, with a function attribute for opting into potential-undefined-behavior, will be implemented and posted for review in a separate patch. [0] http://lists.llvm.org/pipermail/llvm-dev/2015-July/088103.html [1] https://bugs.llvm.org/show_bug.cgi?id=965 [2] http://lists.llvm.org/pipermail/llvm-dev/2017-October/118632.html Differential Revision: https://reviews.llvm.org/D38336 llvm-svn: 317729
- Loading branch information
Dan Gohman
committed
Nov 8, 2017
1 parent
c707c6f
commit 2c74fe9
Showing
31 changed files
with
446 additions
and
6 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,12 @@ | ||
; RUN: opt -S < %s -instcombine | FileCheck %s | ||
|
||
declare void @llvm.sideeffect() | ||
|
||
; Don't DCE llvm.sideeffect calls. | ||
|
||
; CHECK-LABEL: dce | ||
; CHECK: call void @llvm.sideeffect() | ||
define void @dce() { | ||
call void @llvm.sideeffect() | ||
ret void | ||
} |
15 changes: 15 additions & 0 deletions
15
llvm/test/Transforms/DeadStoreElimination/int_sideeffect.ll
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,15 @@ | ||
; RUN: opt -S < %s -dse | FileCheck %s | ||
|
||
declare void @llvm.sideeffect() | ||
|
||
; Dead store elimination across a @llvm.sideeffect. | ||
|
||
; CHECK-LABEL: dse | ||
; CHECK: store | ||
; CHECK-NOT: store | ||
define void @dse(float* %p) { | ||
store float 0.0, float* %p | ||
call void @llvm.sideeffect() | ||
store float 0.0, float* %p | ||
ret void | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,27 @@ | ||
; RUN: opt -S < %s -early-cse | FileCheck %s | ||
|
||
declare void @llvm.sideeffect() | ||
|
||
; Store-to-load forwarding across a @llvm.sideeffect. | ||
|
||
; CHECK-LABEL: s2l | ||
; CHECK-NOT: load | ||
define float @s2l(float* %p) { | ||
store float 0.0, float* %p | ||
call void @llvm.sideeffect() | ||
%t = load float, float* %p | ||
ret float %t | ||
} | ||
|
||
; Redundant load elimination across a @llvm.sideeffect. | ||
|
||
; CHECK-LABEL: rle | ||
; CHECK: load | ||
; CHECK-NOT: load | ||
define float @rle(float* %p) { | ||
%r = load float, float* %p | ||
call void @llvm.sideeffect() | ||
%s = load float, float* %p | ||
%t = fadd float %r, %s | ||
ret float %t | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,21 @@ | ||
; RUN: opt -S < %s -functionattrs | FileCheck %s | ||
|
||
declare void @llvm.sideeffect() | ||
|
||
; Don't add readnone or similar attributes when an @llvm.sideeffect() intrinsic | ||
; is present. | ||
|
||
; CHECK: define void @test() { | ||
define void @test() { | ||
call void @llvm.sideeffect() | ||
ret void | ||
} | ||
|
||
; CHECK: define void @loop() { | ||
define void @loop() { | ||
br label %loop | ||
|
||
loop: | ||
call void @llvm.sideeffect() | ||
br label %loop | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,51 @@ | ||
; RUN: opt -S < %s -gvn | FileCheck %s | ||
|
||
declare void @llvm.sideeffect() | ||
|
||
; Store-to-load forwarding across a @llvm.sideeffect. | ||
|
||
; CHECK-LABEL: s2l | ||
; CHECK-NOT: load | ||
define float @s2l(float* %p) { | ||
store float 0.0, float* %p | ||
call void @llvm.sideeffect() | ||
%t = load float, float* %p | ||
ret float %t | ||
} | ||
|
||
; Redundant load elimination across a @llvm.sideeffect. | ||
|
||
; CHECK-LABEL: rle | ||
; CHECK: load | ||
; CHECK-NOT: load | ||
define float @rle(float* %p) { | ||
%r = load float, float* %p | ||
call void @llvm.sideeffect() | ||
%s = load float, float* %p | ||
%t = fadd float %r, %s | ||
ret float %t | ||
} | ||
|
||
; LICM across a @llvm.sideeffect. | ||
|
||
; CHECK-LABEL: licm | ||
; CHECK: load | ||
; CHECK: loop: | ||
; CHECK-NOT: load | ||
define float @licm(i64 %n, float* nocapture readonly %p) #0 { | ||
bb0: | ||
br label %loop | ||
|
||
loop: | ||
%i = phi i64 [ 0, %bb0 ], [ %t5, %loop ] | ||
%sum = phi float [ 0.000000e+00, %bb0 ], [ %t4, %loop ] | ||
call void @llvm.sideeffect() | ||
%t3 = load float, float* %p | ||
%t4 = fadd float %sum, %t3 | ||
%t5 = add i64 %i, 1 | ||
%t6 = icmp ult i64 %t5, %n | ||
br i1 %t6, label %loop, label %bb2 | ||
|
||
bb2: | ||
ret float %t4 | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
; RUN: opt -S < %s -gvn-hoist | FileCheck %s | ||
|
||
declare void @llvm.sideeffect() | ||
|
||
; GVN hoisting across a @llvm.sideeffect. | ||
|
||
; CHECK-LABEL: scalarsHoisting | ||
; CHECK: = fsub | ||
; CHECK: br i1 %cmp, | ||
; CHECK-NOT: fsub | ||
define float @scalarsHoisting(float %d, float %m, float %a, i1 %cmp) { | ||
entry: | ||
br i1 %cmp, label %if.then, label %if.else | ||
|
||
if.then: | ||
call void @llvm.sideeffect() | ||
%sub0 = fsub float %m, %a | ||
%mul = fmul float %sub0, %d | ||
br label %if.end | ||
|
||
if.else: | ||
%sub1 = fsub float %m, %a | ||
%div = fdiv float %sub1, %d | ||
br label %if.end | ||
|
||
if.end: | ||
%phi = phi float [ %mul, %if.then ], [ %div, %if.else ] | ||
ret float %phi | ||
} | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
; RUN: opt -S < %s -gvn-sink | FileCheck %s | ||
|
||
declare void @llvm.sideeffect() | ||
|
||
; GVN sinking across a @llvm.sideeffect. | ||
|
||
; CHECK-LABEL: scalarsSinking | ||
; CHECK-NOT: fmul | ||
; CHECK: = phi | ||
; CHECK: = fmul | ||
define float @scalarsSinking(float %d, float %m, float %a, i1 %cmp) { | ||
entry: | ||
br i1 %cmp, label %if.then, label %if.else | ||
|
||
if.then: | ||
call void @llvm.sideeffect() | ||
%sub = fsub float %m, %a | ||
%mul0 = fmul float %sub, %d | ||
br label %if.end | ||
|
||
if.else: | ||
%add = fadd float %m, %a | ||
%mul1 = fmul float %add, %d | ||
br label %if.end | ||
|
||
if.end: | ||
%phi = phi float [ %mul0, %if.then ], [ %mul1, %if.else ] | ||
ret float %phi | ||
} | ||
|
Oops, something went wrong.