<html>
    <head>
      <base href="https://bugs.llvm.org/">
    </head>
    <body><table border="1" cellspacing="0" cellpadding="8">
        <tr>
          <th>Bug ID</th>
          <td><a class="bz_bug_link 
          bz_status_NEW "
   title="NEW - [GVN] Miscompile: incorrect replacement of redundant load with PHIs"
   href="https://bugs.llvm.org/show_bug.cgi?id=42733">42733</a>
          </td>
        </tr>

        <tr>
          <th>Summary</th>
          <td>[GVN] Miscompile: incorrect replacement of redundant load with PHIs
          </td>
        </tr>

        <tr>
          <th>Product</th>
          <td>libraries
          </td>
        </tr>

        <tr>
          <th>Version</th>
          <td>trunk
          </td>
        </tr>

        <tr>
          <th>Hardware</th>
          <td>PC
          </td>
        </tr>

        <tr>
          <th>OS</th>
          <td>Linux
          </td>
        </tr>

        <tr>
          <th>Status</th>
          <td>NEW
          </td>
        </tr>

        <tr>
          <th>Severity</th>
          <td>normal
          </td>
        </tr>

        <tr>
          <th>Priority</th>
          <td>P
          </td>
        </tr>

        <tr>
          <th>Component</th>
          <td>Scalar Optimizations
          </td>
        </tr>

        <tr>
          <th>Assignee</th>
          <td>unassignedbugs@nondot.org
          </td>
        </tr>

        <tr>
          <th>Reporter</th>
          <td>suc-daniil@yandex.ru
          </td>
        </tr>

        <tr>
          <th>CC</th>
          <td>llvm-bugs@lists.llvm.org
          </td>
        </tr></table>
      <p>
        <div>
        <pre>In this case GVN eliminates following load:
  %tmp25 = load atomic i64, i64 addrspace(1)* %tmp24 unordered, align 8

by replacing it with a sequence of PHIs and the problem is that the first phi
in this sequence contains undef: 
  bb6:                                              ; preds = %bb19, %bb
    %tmp251 = phi i64 [ undef, %bb ], [ %tmp252, %bb19 ]


This bug is not reproducible without !tbaa metadata on this load:
  %tmp22 = load atomic i64, i64 addrspace(1)* %tmp21 unordered, align 8, !tbaa
!0
even though only BasicAA is used.

>From what I was able to find, it looks like this PHI contains undef because for
some reason MemoryDependenceAnalysis reports incomplete list of dependencies
for that load.


The reproducer:
========================================================
define i64 @foo(i64 addrspace(1)** %arg, i1 %arg1, i1 %arg2, i1 %arg3, i32
%arg4) {
bb:
  %tmp = load atomic i64 addrspace(1)*, i64 addrspace(1)** %arg unordered,
align 8
  %tmp5 = getelementptr inbounds i64, i64 addrspace(1)* %tmp, i64 8
  store atomic i64 0, i64 addrspace(1)* %tmp5 unordered, align 8
  br label %bb6

bb6:                                              ; preds = %bb19, %bb
  %tmp7 = phi i64 [ 0, %bb ], [ %tmp22, %bb19 ]
  br i1 %arg1, label %bb19, label %bb8

bb8:                                              ; preds = %bb6
  %tmp9 = load atomic i64 addrspace(1)*, i64 addrspace(1)** %arg unordered,
align 8
  br i1 %arg2, label %bb11, label %bb10

bb10:                                             ; preds = %bb8
  br label %bb15

bb11:                                             ; preds = %bb8
  br i1 %arg3, label %bb12, label %bb18

bb12:                                             ; preds = %bb11
  %tmp13 = phi i64 addrspace(1)* [ %tmp9, %bb11 ]
  %tmp14 = getelementptr inbounds i64, i64 addrspace(1)* %tmp13, i64 8
  store atomic i64 1, i64 addrspace(1)* %tmp14 unordered, align 8
  ret i64 0

bb15:                                             ; preds = %bb26, %bb10
  %tmp16 = phi i64 addrspace(1)* [ %tmp9, %bb10 ], [ %tmp27, %bb26 ]
  %tmp17 = phi i64 [ %tmp7, %bb10 ], [ 0, %bb26 ]
  switch i32 %arg4, label %bb19 [
    i32 0, label %bb26
    i32 1, label %bb23
  ]

bb18:                                             ; preds = %bb11
  br label %bb19

bb19:                                             ; preds = %bb18, %bb15, %bb6
  %tmp20 = phi i64 addrspace(1)* [ %tmp16, %bb15 ], [ null, %bb6 ], [ %tmp9,
%bb18 ]
  %tmp21 = getelementptr inbounds i64, i64 addrspace(1)* %tmp20, i64 8
  %tmp22 = load atomic i64, i64 addrspace(1)* %tmp21 unordered, align 8, !tbaa
!0
  br label %bb6

bb23:                                             ; preds = %bb15
  %tmp24 = getelementptr inbounds i64, i64 addrspace(1)* %tmp16, i64 8
  %tmp25 = load atomic i64, i64 addrspace(1)* %tmp24 unordered, align 8
  call void @baz(i64 %tmp25) #0
  ret i64 0

bb26:                                             ; preds = %bb15
  call void @bar()
  %tmp27 = load atomic i64 addrspace(1)*, i64 addrspace(1)** %arg unordered,
align 8
  %tmp28 = getelementptr inbounds i64, i64 addrspace(1)* %tmp27, i64 8
  %tmp29 = load atomic i64, i64 addrspace(1)* %tmp28 unordered, align 8
  %tmp30 = getelementptr inbounds i64, i64 addrspace(1)* %tmp27, i64 40
  store atomic i64 %tmp29, i64 addrspace(1)* %tmp30 unordered, align 4
  br label %bb15
}

declare void @bar()

; Function Attrs: inaccessiblememonly readonly
declare void @baz(i64) #0

attributes #0 = { inaccessiblememonly readonly }

!0 = !{!1, !2, i64 8}
!1 = !{!"Name", !2, i64 8}
!2 = !{!"tbaa_local_fields", !3, i64 0}
!3 = !{!"tbaa-access-type"}
========================================================
$ opt -aa-pipeline=basic-aa -passes=gvn -S repro.ll -debug-only=gvn
GVN iteration: 0
GVN: load i64 addrspace(1)* %tmp has unknown dependence
GVN: load i64 addrspace(1)* %tmp9 is clobbered by   store atomic i64 0, i64
addrspace(1)* %tmp5 unordered, align 8
GVN: load i64 addrspace(1)* %tmp9 is clobbered by   store atomic i64 %tmp29,
i64 addrspace(1)* %tmp30 unordered, align 4
GVN: load i64 addrspace(1)* %tmp27 is clobbered by   call void @bar()
GVN: load i64 %tmp29 is clobbered by   call void @bar()
GVN removed:   %tmp13 = phi i64 addrspace(1)* [ %tmp9, %bb11 ]
GVN: load i64 %tmp22 is clobbered by   store atomic i64 0, i64 addrspace(1)*
%tmp5 unordered, align 8
GVN iteration: 1
GVN: load i64 addrspace(1)* %tmp has unknown dependence
GVN: load i64 addrspace(1)* %tmp9 is clobbered by   store atomic i64 0, i64
addrspace(1)* %tmp5 unordered, align 8
GVN: load i64 addrspace(1)* %tmp9 is clobbered by   store atomic i64 %tmp29,
i64 addrspace(1)* %tmp30 unordered, align 4
GVN REMOVING NONLOCAL LOAD:   %tmp25 = load atomic i64, i64 addrspace(1)*
%tmp24 unordered, align 8
GVN removed:   %0 = load atomic i64, i64 addrspace(1)* %tmp24 unordered, align
8
GVN: load i64 addrspace(1)* %tmp27 is clobbered by   call void @bar()
GVN: load i64 %tmp29 is clobbered by   call void @bar()
GVN: load i64 %tmp22 is clobbered by   store atomic i64 0, i64 addrspace(1)*
%tmp5 unordered, align 8
GVN iteration: 2
GVN: load i64 addrspace(1)* %tmp has unknown dependence
GVN: load i64 addrspace(1)* %tmp9 is clobbered by   store atomic i64 0, i64
addrspace(1)* %tmp5 unordered, align 8
GVN: load i64 addrspace(1)* %tmp9 is clobbered by   store atomic i64 %tmp29,
i64 addrspace(1)* %tmp30 unordered, align 4
GVN: load i64 addrspace(1)* %tmp27 is clobbered by   call void @bar()
GVN: load i64 %tmp29 is clobbered by   call void @bar()
GVN: load i64 %tmp22 is clobbered by   store atomic i64 0, i64 addrspace(1)*
%tmp5 unordered, align 8
; ModuleID = 'repro.ll'
source_filename = "repro.ll"

define i64 @foo(i64 addrspace(1)** %arg, i1 %arg1, i1 %arg2, i1 %arg3, i32
%arg4) {
bb:
  %tmp = load atomic i64 addrspace(1)*, i64 addrspace(1)** %arg unordered,
align 8
  %tmp5 = getelementptr inbounds i64, i64 addrspace(1)* %tmp, i64 8
  store atomic i64 0, i64 addrspace(1)* %tmp5 unordered, align 8
  br label %bb6

bb6:                                              ; preds = %bb19, %bb
  %tmp251 = phi i64 [ undef, %bb ], [ %tmp252, %bb19 ]
  %tmp7 = phi i64 [ 0, %bb ], [ %tmp22, %bb19 ]
  br i1 %arg1, label %bb19, label %bb8

bb8:                                              ; preds = %bb6
  %tmp9 = load atomic i64 addrspace(1)*, i64 addrspace(1)** %arg unordered,
align 8
  br i1 %arg2, label %bb11, label %bb10

bb10:                                             ; preds = %bb8
  br label %bb15

bb11:                                             ; preds = %bb8
  br i1 %arg3, label %bb12, label %bb18

bb12:                                             ; preds = %bb11
  %tmp14 = getelementptr inbounds i64, i64 addrspace(1)* %tmp9, i64 8
  store atomic i64 1, i64 addrspace(1)* %tmp14 unordered, align 8
  ret i64 0

bb15:                                             ; preds = %bb26, %bb10
  %tmp25 = phi i64 [ %tmp251, %bb10 ], [ %tmp29, %bb26 ]
  %tmp16 = phi i64 addrspace(1)* [ %tmp9, %bb10 ], [ %tmp27, %bb26 ]
  %tmp17 = phi i64 [ %tmp7, %bb10 ], [ 0, %bb26 ]
  switch i32 %arg4, label %bb19 [
    i32 0, label %bb26
    i32 1, label %bb23
  ]

bb18:                                             ; preds = %bb11
  br label %bb19

bb19:                                             ; preds = %bb18, %bb15, %bb6
  %tmp252 = phi i64 [ %tmp25, %bb15 ], [ %tmp251, %bb6 ], [ %tmp251, %bb18 ]
  %tmp20 = phi i64 addrspace(1)* [ %tmp16, %bb15 ], [ null, %bb6 ], [ %tmp9,
%bb18 ]
  %tmp21 = getelementptr inbounds i64, i64 addrspace(1)* %tmp20, i64 8
  %tmp22 = load atomic i64, i64 addrspace(1)* %tmp21 unordered, align 8, !tbaa
!0
  br label %bb6

bb23:                                             ; preds = %bb15
  %tmp24 = getelementptr inbounds i64, i64 addrspace(1)* %tmp16, i64 8
  call void @baz(i64 %tmp25) #0
  ret i64 0

bb26:                                             ; preds = %bb15
  call void @bar()
  %tmp27 = load atomic i64 addrspace(1)*, i64 addrspace(1)** %arg unordered,
align 8
  %tmp28 = getelementptr inbounds i64, i64 addrspace(1)* %tmp27, i64 8
  %tmp29 = load atomic i64, i64 addrspace(1)* %tmp28 unordered, align 8
  %tmp30 = getelementptr inbounds i64, i64 addrspace(1)* %tmp27, i64 40
  store atomic i64 %tmp29, i64 addrspace(1)* %tmp30 unordered, align 4
  br label %bb15
}

declare void @bar()

; Function Attrs: inaccessiblememonly readonly
declare void @baz(i64) #0

attributes #0 = { inaccessiblememonly readonly }

!0 = !{!1, !2, i64 8}
!1 = !{!"Name", !2, i64 8}
!2 = !{!"tbaa_local_fields", !3, i64 0}
!3 = !{!"tbaa-access-type"}
========================================================

Any further simplification of the reproducer breaks it.</pre>
        </div>
      </p>


      <hr>
      <span>You are receiving this mail because:</span>

      <ul>
          <li>You are on the CC list for the bug.</li>
      </ul>
    </body>
</html>