<html>
    <head>
      <base href="https://llvm.org/bugs/" />
    </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 --- - [AArch64] LLVM vectorizer produces erroneous output"
   href="https://llvm.org/bugs/show_bug.cgi?id=30627">30627</a>
          </td>
        </tr>

        <tr>
          <th>Summary</th>
          <td>[AArch64] LLVM vectorizer produces erroneous output
          </td>
        </tr>

        <tr>
          <th>Product</th>
          <td>new-bugs
          </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>new bugs
          </td>
        </tr>

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

        <tr>
          <th>Reporter</th>
          <td>hxy9243@gmail.com
          </td>
        </tr>

        <tr>
          <th>CC</th>
          <td>llvm-bugs@lists.llvm.org
          </td>
        </tr>

        <tr>
          <th>Classification</th>
          <td>Unclassified
          </td>
        </tr></table>
      <p>
        <div>
        <pre>Created <span class=""><a href="attachment.cgi?id=17413" name="attach_17413" title="IR from reduced cpp code.">attachment 17413</a> <a href="attachment.cgi?id=17413&action=edit" title="IR from reduced cpp code.">[details]</a></span>
IR from reduced cpp code.

We noticed ever since patch <a href="https://reviews.llvm.org/rL282418">https://reviews.llvm.org/rL282418</a>, trunk LLVM will
produce errorneous output in the vectorized part of the code with flags "-O3
-cl-fast-relaxed-math", with the command listed below:


clang --target=aarch64-unknown-linux-gnu -O3 -cl-fast-relaxed-math
reduced.O0.strip.ll -emit-llvm -S


The erroneous IR is as following:

; <label>:82:                                     ; preds = %82, %77
  %83 = phi i64 [ 0, %77 ], [ %188, %82 ]
  %84 = phi <2 x i64> [ <i64 0, i64 1>, %77 ], [ %189, %82 ]

  ...

  %108 = add nuw nsw <2 x i64> %84, <i64 1, i64 1>
  %109 = add <2 x i64> %84, <i64 3, i64 3>
  %110 = extractelement <2 x i64> %108, i32 0
  %111 = icmp slt i64 %110, %64
  %112 = extractelement <2 x i64> %109, i32 0
  %113 = icmp slt i64 %112, %64
  %114 = insertelement <2 x i1> undef, i1 %111, i32 0
  %115 = shufflevector <2 x i1> %114, <2 x i1> undef, <2 x i32> zeroinitializer
  %116 = insertelement <2 x i1> undef, i1 %113, i32 0
  %117 = shufflevector <2 x i1> %116, <2 x i1> undef, <2 x i32> zeroinitializer
  %118 = select <2 x i1> %115, <2 x i64> %108, <2 x i64> zeroinitializer
  %119 = select <2 x i1> %117, <2 x i64> %109, <2 x i64> zeroinitializer

  ...


Before the patch, the generated IR should look like the following:


  %43 = add nuw nsw <2 x i64> %vec.ind, <i64 1, i64 1>
  %44 = add <2 x i64> %vec.ind, <i64 3, i64 3>
  %45 = icmp slt <2 x i64> %43, %broadcast.splat158
  %46 = icmp slt <2 x i64> %44, %broadcast.splat158
  %47 = select <2 x i1> %45, <2 x i64> %43, <2 x i64> zeroinitializer
  %48 = select <2 x i1> %46, <2 x i64> %44, <2 x i64> zeroinitializer



Scalar values %111 and %113 are coming from the 1st element of vector %108 and
%109. And these are inserted in both lanes of the vectors %115 and %117, which
are used in the select statement.

Where before the patch the select statements are using values from vector
comparisons %43 and %44, and they're using both values in the vectors.


For example, %108 is <8, 9>, and %64 is 8.
%114 will have the value of the <0, undef>
%115 will propagate the 1st value to the 2nd lane, and %115 is <0, 0>, which is
used in the select.

Before the patch, %43 is <8, 9>, and %broadcast.splat158 is <8, 8>.
%45 is <0, 1>, which is used in the select, producing different result.

We believe it's the problem in the scalarization part of the pass. As the
commit message suggests:


[LV] Scalarize instructions marked scalar after vectorization
This patch ensures that we actually scalarize instructions marked scalar after
vectorization. Previously, such instructions may have been vectorized instead.

Differential Revision: <a href="https://reviews.llvm.org/D23889">https://reviews.llvm.org/D23889</a></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>